Nothing showing up in NSOpenGLView [newb]

Nibbie
Posts: 4
Joined: 2011.11
Post: #1
Hey all,
I'm trying to teach myself OpenGL and Cocoa/Objective-C. I'm a C++/Java developer by trade (so you have some basis of my technical knowledge).

I've been stuck trying to figure out why I can't seem to get, what should be, a simple task working. I'm trying to display a triangle in a window using OpenGL 3.2.

Here is the pertinent method in my AppDelegate.m:
Code:
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification
{
    // Insert code here to initialize your application
    OGLViewController *oglvc = [[OGLViewController alloc] initWithNibName:nil bundle:nil];    
    
    [oglvc setupViewWithRect:[self.window.contentView bounds]];
    
    [self.window.contentView addSubview:oglvc.view];
    
    [oglvc draw];
}

My custom NSViewController, OGLViewController, implementation is as follows (WARNING: wall o' code):
Code:
//
//  OGLViewController.m
//  TriangleMan
//
//  Created by binaryinsomnia on 11/28/11.
//  Copyright (c) 2011 binaryinsomnia. All rights reserved.
//

#import "OGLViewController.h"
#import "GLProgram.h"
#import "error.h"

#import <OpenGL/gl3.h>

@interface OGLViewController()
{
    GLuint positionAttribute;
    GLuint colorAttribute;
}
@property (retain) GLProgram *oglhelper;
@end

@implementation OGLViewController
@synthesize oglhelper = _oglhelper;

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Initialization code here.
    }
    
    return self;
}

-(void)dealloc
{
    [super dealloc];
    
    [_oglhelper release];
}

-(void)setupViewWithRect:(NSRect)aRect
{
    NSOpenGLPixelFormatAttribute pixAttribs[] =
    {
        NSOpenGLPFAOpenGLProfile, NSOpenGLProfileVersion3_2Core,
        NSOpenGLPFAColorSize    , 24                           ,
        NSOpenGLPFAAlphaSize    , 8                            ,
        NSOpenGLPFADoubleBuffer ,
        NSOpenGLPFAAccelerated  ,
        NSOpenGLPFANoRecovery   ,
        0
    };
    
    NSOpenGLPixelFormat *pixFormat = [[NSOpenGLPixelFormat alloc] initWithAttributes:pixAttribs];
    
    self.view = [[NSOpenGLView alloc] initWithFrame:aRect pixelFormat:pixFormat];

    [[(NSOpenGLView*)(self.view) openGLContext] makeCurrentContext];
}

-(void)prepareOpenGL
{    
    self.oglhelper = [[GLProgram alloc] initWithVertexShaderFilename:@"Simple"
                                              fragmentShaderFilename:@"Simple"];
    
    [self.oglhelper addAttribute:@"position"];
    [self.oglhelper addAttribute:@"color"];
    
    if (![self.oglhelper link])
    {
        NSLog(@"Link failed");
        
        NSString *progLog = [self.oglhelper programLog];
        NSLog(@"Program Log: %@", progLog);
        
        NSString *fragLog = [self.oglhelper fragmentShaderLog];
        NSLog(@"Frag Log: %@", fragLog);
        
        NSString *vertLog = [self.oglhelper vertexShaderLog];
        NSLog(@"Vert Log: %@", vertLog);
        
        self.oglhelper = nil;
    }
    
    positionAttribute = [self.oglhelper attributeIndex:@"position"];
    colorAttribute    = [self.oglhelper attributeIndex:@"color"];    
}

-(void)addVertexData
{
    GLfloat positionArray[] =
    {
    //   x    y    z    w
        0.0, 0.0, 0.0, 1.0,
        2.0, 0.0, 0.0, 1.0,
        0.0, 1.0, 0.0, 1.0
    };
    
    GLfloat colorArray[] =
    {
    //   r    g    b    a
        1.0, 0.0, 0.0, 1.0,
        0.0, 1.0, 0.0, 1.0,
        0.0, 0.0, 1.0, 1.0
    };
    
    // first, set up the position vertex into the GPU    
    GLuint posVAOId, posVBOId;
    glGenVertexArrays(1, &posVAOId); // get valid VAO
    GetError();
    glBindVertexArray(posVAOId); // bind it to the vertex array
    GetError();
    
    glGenBuffers(1, &posVBOId); // get a valid VBO
    GetError();
    glBindBuffer(GL_ARRAY_BUFFER, posVBOId);  // make it a VBO
    GetError();
    
    // copy data to VRAM
    glBufferData(GL_ARRAY_BUFFER, 12 * sizeof(GLfloat), positionArray, GL_STATIC_DRAW);
    GetError();
    glVertexAttribPointer(positionAttribute, 3, GL_FLOAT, GL_FALSE, 0, 0);
    GetError();
    glEnableVertexAttribArray(positionAttribute);
    GetError();
    
    // duplication of code... yeah, yeah.
    
    // next, set up the color info into the GPU    
    GLuint colVAOId, colVBOId;
    glGenVertexArrays(1, &colVAOId); // get valid VAO
    GetError();
    glBindVertexArray(colVAOId); // bind it to the vertex array
    GetError();
    
    glGenBuffers(1, &colVBOId); // get a valid VBO
    GetError();
    glBindBuffer(GL_ARRAY_BUFFER, colVBOId);  // make it a VBO
    GetError();
    
    // copy data to VRAM
    glBufferData(GL_ARRAY_BUFFER, 12 * sizeof(GLfloat), colorArray, GL_STATIC_DRAW);
    GetError();
    glVertexAttribPointer(colorAttribute, 3, GL_FLOAT, GL_FALSE, 0, 0);
    GetError();
    glEnableVertexAttribArray(colorAttribute);
    GetError();
    
    glBindVertexArray(0);
}

-(void)draw
{
    glClearColor(0.0, 0.0, 1.0, 1.0);
    glClear(GL_COLOR_BUFFER_BIT);
    GetError();
    
    [self prepareOpenGL];
    [self addVertexData];
    
    [self.oglhelper use];
    glDrawArrays(GL_TRIANGLE_FAN, 0, 3);
    
    [[(NSOpenGLView *)(self.view) openGLContext] flushBuffer];
}
@end

I'm using Jeff LaMarche's GLProgram class (https://github.com/jlamarche/iOS-OpenGLE...e/Classes) to help simplify setting up the shaders/compiling/linking.

So, everything compiles and runs without crashing. But, all I see is a window with nothing drawn or colored. I was hoping to at least have the window colored blue, as I'm not entirely sure that my vertex array was correctly setup.

Do you guys see what can be causing this issue?

Thanks,
binaryinsomnia
Quote this message in a reply
Luminary
Posts: 5,143
Joined: 2002.04
Post: #2
There's so much code here to sift through, and so much done oddly (creating the whole GL view in code?) that it's hard to guess where the problem lies. Perhaps you could post the whole project?

You should also be aware that not all GPUs supported by Lion support OpenGL 3.2. What are you running this on?
Quote this message in a reply
Nibbie
Posts: 4
Joined: 2011.11
Post: #3
Hey OneSadCookie,
Thanks for the reply!

I'm trying to setup the GL View programmatically instead of going through InterfaceBuilder. My GL View is taking up the whole window frame, so didn't think I need to work with IB. Of course, perhaps my assumption is incorrect. Smile I was looking at this, https://github.com/beelsebob/Cocoa-GL-Tutorial, to help me get started.

Here's my project: http://www.2shared.com/file/XEUDnkaJ/bin...omnia.html

I'm using the 2011 Mac Mini with the AMD discrete GPU.

Thanks,
binaryinsomnia
Quote this message in a reply
Luminary
Posts: 5,143
Joined: 2002.04
Post: #4
Fixed it for you:
http://cl.ly/0O0k2J3d1J361k322O27

1) you can't draw until the view is visible, which doesn't happen until after applicationDidFinishLaunching
2) you were unbinding the VAO but never rebinding the VAO you put data in.

Your code is set up extremely oddly Rasp
Quote this message in a reply
Nibbie
Posts: 4
Joined: 2011.11
Post: #5
Sweet! Thank you!

I just checked the changes you'd made. Hmmm... I see you used a block to send the draw message to my view controller. While I've not yet learned about blocks, it seems to me that that is kind of a hack to cover for my extremely odd code. Smile

Speaking of extremely odd code, what makes it odd? How would you go about writing this simple app in the "right way?" I need all the pointers I can get from experienced Cocoa/OpenGL devs as I can get!

In regards to your numerated list...
1) Ah, ok. I need to read up on the lifecycle of a Cocoa app.
2) I have a vague idea what you're talking about there. I'll look over the code to see if I can spot where I'm unbinding and not rebinding the VAO.

Thanks for your time, OneSadCookie!

binaryinsomnia
Quote this message in a reply
Luminary
Posts: 5,143
Joined: 2002.04
Post: #6
Code:
diff -cr binaryinsomnia-cookies/ binaryinsomnia/ | open -f

Yes, both changes were hacks. I imagined you'd take the concept and make it work in a nicer way Wink

You can see what I consider the "normal" way of doing things in https://github.com/OneSadCookie/ either ZeroHour or ObjCGameBase (each slightly different with slightly different flaws).
Quote this message in a reply
Nibbie
Posts: 4
Joined: 2011.11
Post: #7
Heh! I fully intend to write this in a more proper form. Smile

Alright, I'll study those examples.

Thanks!
Quote this message in a reply
Post Reply 

Possibly Related Threads...
Thread: Author Replies: Views: Last Post
  showing off new space game gooncorp 1 3,244 Nov 8, 2012 02:35 PM
Last Post: PythonBlue
  Cocoa controls on top of NSOpenGLView wadesworld 5 5,941 Apr 6, 2009 01:38 AM
Last Post: arekkusu
  Antialiasing and NSOpenGLView attributes Jar445 2 6,561 Jan 20, 2009 10:42 AM
Last Post: maximile
  Adding NSOpenGLView class in Xcode/Interface Builder 3.0 Graphic Ace 2 3,716 Dec 5, 2007 02:15 PM
Last Post: Blacktiger
  Double-Buffering with NSOpenGLView DesertPenguin 3 5,741 Aug 1, 2006 07:17 AM
Last Post: DesertPenguin