Log in or register to post comments

How to convert ImageTargets to use VBOs?

March 27, 2012 - 3:58pm #1

Hi guys,

The title says it all really. I have followed Apple's sample code for using VBO's, but nothing is displaying. Here is my code:
In EAGLView.h I have:

typedef struct _vertexStruct
{
    GLfloat position[3];
    GLfloat normal[3];
    GLfloat texCoord[2];
} vertexStruct;

enum {
    ATTRIB_POSITION,
    ATTRIB_NORMAL,
    ATTRIB_TEXCOORD,
    NUM_ATTRIBUTES
};

@interface AR_EAGLView : UIView <UIGLViewProtocol>

{
@public
    NSMutableArray *textureList; // list of textures to load
    
    GLuint    vertexBuffer;
    GLuint    indexBuffer;
    const vertexStruct* vertices;
    const GLushort* indices;

Then, from EAGLView.mm:

-(void) createVertexBuffers
{
    static const vertexStruct const_vertices[4] = {
        {{-0.5,-0.5, 0.0,},{0,0,1,},{0,0,}},
        {{ 0.5,-0.5, 0.0,},{0,0,1,},{1,0,}},
        {{-0.5, 0.5, 0.0,},{0,0,1,},{0,1,}},
        {{ 0.5, 0.5, 0.0,},{0,0,1,},{1,1,}},
    };
    
    // index array.
    static GLushort const_indices[6] = {
        0,1,3,3,2,0,
    };
    
    vertices    = const_vertices;
    indices     = const_indices;
    
    glGenBuffers(1, &vertexBuffer);
    glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
    glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
    
    glGenBuffers(1, &indexBuffer);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);
}

.. which I call at the end of setup3dObjects() with:

[self createVertexBuffers];

Then, in my renderFrameQCAR function in EAGLView.mm I have:

- (void)renderFrameQCAR
{
...
                glUseProgram(shaderProgramID);
                glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
                glVertexAttribPointer(vertexHandle,         3, GL_FLOAT, GL_FALSE,  sizeof(vertexStruct), (void*)offsetof(vertexStruct,position));
                glEnableVertexAttribArray(vertexHandle);
                
                glVertexAttribPointer(normalHandle,         3, GL_FLOAT, GL_FALSE,  sizeof(vertexStruct), (void*)offsetof(vertexStruct,normal));
                glEnableVertexAttribArray(normalHandle);
                
                glVertexAttribPointer(textureCoordHandle,   2, GL_FLOAT, GL_TRUE,   sizeof(vertexStruct), (void*)offsetof(vertexStruct,texCoord));
                glEnableVertexAttribArray(textureCoordHandle);
                                      
                glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
                glDrawElements(GL_TRIANGLE_STRIP, sizeof(indices)/sizeof(GLubyte), GL_UNSIGNED_BYTE, (void*)0);
                ShaderUtils::checkGlError("EAGLView renderFrameQCAR");

...
}

Can anyone tell me what I'm doing wrong?

Thanks,

Josh

Re: How to convert ImageTargets to use VBOs?

March 30, 2012 - 7:23pm #6

I definitely suggest starting with our sample and integrating the VBOs, it should be the easier approach.

Maybe this is an issue of scale? Note the targets are about 250 units across, you'll need to scale up the model.

This also seems suspect:

glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);

Shouldn't this be sizeof(vertices) * sizeof(vertexStruct)? Same for the index buffer.

Try turning culling off just in case.

Also, make sure you really want to use GL_TRIANGLE_STRIP and not GL_TRIANGLES.

- Kim

Re: How to convert ImageTargets to use VBOs?

March 30, 2012 - 5:03am #5

Thanks Kim,

Yes my code works in the OpenGL Template. But I think that a better way might be to rephrase the question a little:

Basically, I want to create an app that can play animated high-density meshes. For efficiency, and according to Apple's recommendations, I will need to use VBO's. So I think my current options are:

a) Start with the Image Targets sample app and try to convert the code. (This is what I posted at the beginning but nothing seems to be showing up) or

b) Start with XCode's OpenGL Game template (which uses GLKit) and try to integrate the Vuforia SDK into it. This would be the preferable option, since that template already uses VBO's but I don't really know where to start. Is there some sample code that might show how to achieve this?

Thanks again,

Josh

Re: How to convert ImageTargets to use VBOs?

March 28, 2012 - 9:11pm #4

I might be mistaken about the offset macro, I've never used it.

I suggest starting with the basic iOS OpenGL starting project, and trying out your VBO rendering code there first. Once it's working in that context, let us know if you're having trouble integrating it with the Vuforia sample.

- Kim

Re: How to convert ImageTargets to use VBOs?

March 28, 2012 - 6:06am #3

Thanks ksiva, good catches. Unfortunately I still see nothing (whereas I do when I'm not using VBO's).

I changed the glDrawElements call to:

[CODE" />glDrawElements(GL_TRIANGLE_STRIP, sizeof(indices)/sizeof(GLushort), GL_UNSIGNED_SHORT, (void*)0);[/CODE" />

I then added this call immediately before it:

[CODE" />glUniformMatrix4fv(mvpMatrixHandle, 1, GL_FALSE, (const GLfloat*)&modelViewProjection.data[0" />);[/CODE" />

But I'm confused about your comment on the offset macro. How should I be using it? My code is lifted pretty much directly from listing 9-3 here:

http://developer.apple.com/library/ios/#DOCUMENTATION/3DDrawing/Conceptual/OpenGLES_ProgrammingGuide/TechniquesforWorkingwithVertexData/TechniquesforWorkingwithVertexData.html

Thanks,

Josh

Re: How to convert ImageTargets to use VBOs?

March 27, 2012 - 8:48pm #2

A few things:

You are defining the indices as an array of shorts but using bytes in the call to glDrawElements.

I think offsetof returns the offset in bytes, not a pointer value.

Make sure you call glUniformMatrix4fv to set the mvpMatrixHandle.

- Kim

Log in or register to post comments