0
votes

I want to render a Quad via VAO, IBO and VBO but nothing is drawn. I'm using glDrawRangeElements in OS X OpenGL 3.2 Core context. The screen is completely black without any error. GLFW3 is used to create window and context.

Window opening/Context creation code

glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
_mainWindow  = glfwCreateWindow(width, height, title, monitor, NULL);
if(_mainWindow == NULL)
{
    return false;
}
_mainWindowWidth  = width;
_mainWindowHeight = height;
glfwSetKeyCallback(_mainWindow, _onKeyEvent);
glfwMakeContextCurrent(_mainWindow);

glewExperimental = GL_TRUE;
glewInit();

_openGLVersion = reinterpret_cast<const char*>(glGetString(GL_VERSION));

Shader sources (compiled successfully). Custom FragColor is binded.

_vertexShaderSource =
            "#version 150 core\n"
            "in vec3 in_Position;\n"
            "in vec3 in_Normal;\n"
            "in vec2 in_TexCoord;\n"
            "uniform mat4 ModelViewProjection;\n"
            "void main()\n"
            "{\n"
            "   gl_Position = ModelViewProjection * vec4(in_Position, 1.0);\n"
            "}\n";
_fragmentShaderSource =
            "#version 150 core\n"
            "out vec4 FColor;"
            "void main()\n"
            "{\n"
            "   FColor = vec4(1.0, 1.0, 1.0, 1.0);\n"
            "}\n";

Vertices

Vertex* vertices = new Vertex[6];

vertices[0].nz = 1.0f;
vertices[1].nz = 1.0f;
vertices[2].nz = 1.0f;
vertices[3].nz = 1.0f;
vertices[4].nz = 1.0f;
vertices[5].nz = 1.0f;

vertices[1].y  = height;
vertices[1].v0 = 1.0f;

vertices[2].x  = width;
vertices[2].y  = height;
vertices[2].u0 = 1.0f;
vertices[2].v0 = 1.0f;

vertices[4].x  = width;
vertices[4].u0 = 1.0f;

vertices[5].x  = width;
vertices[5].y  = height;
vertices[5].u0 = 1.0f;
vertices[5].v0 = 1.0f;

_mesh->setVertices(vertices, 6);
vertices = NULL;

Uint16* indices = new Uint16[6];

indices[0] = 0;
indices[1] = 2;
indices[2] = 3;
indices[3] = 0;
indices[4] = 1;
indices[5] = 3;

_mesh->setIndices(indices);
indices = NULL;

Buffer update (checked the data, it seems to be correct)

// Update VBO
if(_vertexBufferObjectID == 0)
{
        glGenBuffers(1, &_vertexBufferObjectID);
}
glBindBuffer(GL_ARRAY_BUFFER, _vertexBufferObjectID);

float* data = new float[_vertexCount * sizeof(Vertex) / sizeof(float)];
Uint64 begin = 0;
for(Uint32 i = 0; i < _vertexCount; i++)
{
    begin = i * 8;
    data[begin]     = _vertices[i].x;
    data[begin + 1] = _vertices[i].y;
    data[begin + 2] = _vertices[i].z;
    data[begin + 3] = _vertices[i].nx;
    data[begin + 4] = _vertices[i].ny;
    data[begin + 5] = _vertices[i].nz;
    data[begin + 6] = _vertices[i].u0;
    data[begin + 7] = _vertices[i].v0;
}

glBufferData(GL_ARRAY_BUFFER, sizeof(Vertex) * _vertexCount, &data[0], GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, 0);

delete[] data;
data = NULL;

// Update IBO
if(_indexBufferObjectID == 0)
{
    glGenBuffers(1, &_indexBufferObjectID);
}
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, _indexBufferObjectID);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(Uint16) * _vertexCount, &_indices[0], GL_STATIC_DRAW);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);

// Update VAO
if(_vertexArrayObjectID == 0)
{
    glGenVertexArrays(1, &_vertexArrayObjectID);
}
glBindVertexArray(_vertexArrayObjectID);

glBindBuffer(GL_ARRAY_BUFFER, _vertexBufferObjectID);
// Vertices
glEnableVertexAttribArray(0);
glEnableVertexAttribArray(1);
glEnableVertexAttribArray(2);

glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), ((char*)NULL + (0)));
// Normals
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), ((char*)NULL + (12)));
// TexCoords
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), ((char*)NULL + (24)));

glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, _indexBufferObjectID);

glBindVertexArray(0);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);

Rendering code

glUseProgram(material->_programID);
GLuint mvp = glGetUniformLocation(material->_programID, "ModelViewProjection");
glUniformMatrix4fv(mvp, 1, false, glm::value_ptr(camera_mvp));

glBindVertexArray(node->_mesh->_vertexArrayObjectID);

// Draw
glDrawRangeElements(GL_TRIANGLES, 0, 3, node->_mesh->_vertexCount, GL_UNSIGNED_SHORT, NULL);
glBindVertexArray(0);

Note: camera_mvp is Orthographic

0.00333333_0___________0 0 
0__________0.00333333__0 0 
0__________0__________-1 0 
599________599_________0 1

Program Linking

_programID = glCreateProgram();
glAttachShader(_programID, vertex_shader);
glAttachShader(_programID, fragment_shader);

glLinkProgram(_programID);
glGetProgramiv(_programID, GL_LINK_STATUS, &result);
glGetProgramiv(_programID, GL_INFO_LOG_LENGTH, &loglen);

if(loglen > 0)
{
    char* log = new char[loglen];

    glGetProgramInfoLog(_programID, loglen, 0, log);
    _lastInfoLog = log;

    delete log;
    log = NULL;
}

if(result == GL_FALSE)
{
    glDeleteProgram(_programID);
    glDeleteShader(vertex_shader);
    glDeleteShader(fragment_shader);
    return false;
}

glUseProgram(_programID);
glBindAttribLocation(_programID, 0, "in_Position");
glBindAttribLocation(_programID, 1, "in_Normal");
glBindAttribLocation(_programID, 2, "in_TexCoord");
glBindFragDataLocation(_programID, 0, "FColor");
glUseProgram(0);

glDeleteShader(vertex_shader);
glDeleteShader(fragment_shader);
1

1 Answers

0
votes

You don't have layout in #version 150 so you have to use glGetAttribLocation() to ask OpenGL where it put your attributes and adjust the first parameter of your glVertexAttribPointer() calls appropriately.

Make sure you bind your program before calling glGetAttribLocation().