Leo
Leo

Reputation: 3143

OpenGL ES triangles drawing mistake on iOS

I try to draw multiple triangles using OpenGL ES and iOS. I create vertices array with float values with following structure

{x, y, z, r, g, b, a}

for each vertex. Final array for one triangle is:

{x1, y1, z1, r1, g1, b1, a1, x2, y2, z2, r2, g2, b2, a2, x3, y3, z3, r3, g3, b3, a3}

Here is my update method:

-(void)update {
    float aspect = fabsf(self.view.bounds.size.width / self.view.bounds.size.height);
    GLKMatrix4 projectionMatrix = GLKMatrix4MakePerspective(GLKMathDegreesToRadians(65.0f), aspect, 1.0, 100.0);
    self.effect.transform.projectionMatrix = projectionMatrix;
}

and render:

-(void)glkView:(GLKView *)view drawInRect:(CGRect)rect
{
    [self drawShapes]; // here I fill vertices array

    glClearColor(0.65f, 0.65f, 0.8f, 1.0f);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    int numItems = 3 * trianglesCount;

    glBindVertexArrayOES(vao);

    [self.effect prepareToDraw];

    glUseProgram(shaderProgram);

    glBindBuffer(GL_ARRAY_BUFFER, vbo);
    glBufferData(GL_ARRAY_BUFFER, sizeof(float) * itemSize, convertedVerts, GL_DYNAMIC_DRAW);

    glVertexAttribPointer(vertexPositionAttribute, 3, GL_FLOAT, false, stride, 0);
    glEnableVertexAttribArray(GLKVertexAttribPosition);

    glVertexAttribPointer(vertexColorAttribute, 4, GL_FLOAT, false, stride, (GLvoid*)(3 * sizeof(float)));
    glEnableVertexAttribArray(GLKVertexAttribColor);

    glDrawArrays(GL_TRIANGLES, 0, numItems);
}

Context setup. Here I bind my vertex array and generate vertex buffer:

-(void)setupContext
{
    self.context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2];

    if(!self.context) {
        NSLog(@"Failed to create OpenGL ES Context");
    }

    GLKView *view = (GLKView *)self.view;
    view.context = self.context;
    view.drawableDepthFormat = GLKViewDrawableDepthFormat24;

    [EAGLContext setCurrentContext:self.context];

    self.effect = [[GLKBaseEffect alloc] init];

    glEnable(GL_DEPTH_TEST);
    glDisable(GL_BLEND);
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

    glGenVertexArraysOES(1, &vao);
    glBindVertexArrayOES(vao);

    glGenBuffers(1, &vbo);
}

Fragment and vertex shaders are pretty simple:

//fragment
varying lowp vec4 vColor;
void main(void) {
    gl_FragColor = vColor;
}

//vertex
attribute vec3 aVertexPosition;
attribute vec4 aVertexColor;
varying lowp vec4 vColor;

void main(void) {
    gl_Position = vec4(aVertexPosition, 1.0);
    vColor = aVertexColor;
}

Result. Triangles aren't shown:

enter image description here

Where is mistake? I guess problem is with projection matrix. Here is github link to Xcode project.

Upvotes: 0

Views: 343

Answers (1)

skagzilla
skagzilla

Reputation: 335

Downloaded your code and tried it out. I see the purplish screen and no triangles, so I'm guessing that's the problem. I see two things that could be the problem:

1) You'll need to pass glBufferData the total number of bytes you're sending it, like this: glBufferData(GL_ARRAY_BUFFER, sizeof(float) * itemSize * numItems, convertedVerts, GL_DYNAMIC_DRAW);. Any data related to how to chunk the data stays glVertexAttribPointer.

2) That doesn't seem to be the only thing since I still can't get triangles to show up. I've never used GLKit before (I just have a little experience with OpenGL on the desktop platform). That being said, if I replace GLKVertexAttributePosition and GLKVertexAttribColor with 0 and 1 respectively. And apply the glBufferData fix from 1 I see artifacts flashing on the simulator screen when I move the mouse. So there's gotta be something fishy with those enum values and glVertexAttribPointer.

Edit - clarification for 2:

After changing the glBufferData line as described in 1. I also modified the glEnableVertexAttribArray lines so the looked like this:

glVertexAttribPointer(vertexPositionAttribute, 3, GL_FLOAT, false, stride, 0);
glEnableVertexAttribArray(0);

glVertexAttribPointer(vertexColorAttribute, 4, GL_FLOAT, false, stride, (GLvoid*)(3 * sizeof(float)));
glEnableVertexAttribArray(1);

After both of those changes I can see red triangles flickering on the screen. A step closer, since I couldn't see anything before. But I haven't been able to figure it out any further than that :(

Upvotes: 1

Related Questions