I have a simple OpenGL program and trying to draw an instanced array that stored in a vertex shader. I’m using two follow shaders for rendering:
Vertex Shader:
#version 330 core
uniform mat4 MVP;
const int VertexCount = 4;
const vec2 Position[VertexCount] = vec2[](
vec2(-100.0f, -100.0f),
vec2( -100.0f, 100.0f),
vec2( 100.0f, -100.0f),
vec2(100.0f, 100.0f));
void main()
{
gl_Position = MVP * vec4(Position[gl_VertexID], 0.0, 1.0);
}
Fragment Shader:
#version 330 core
#define FRAG_COLOR 0
layout(location = FRAG_COLOR, index = 0) out vec4 Color;
void main()
{
Color = vec4(0, 1, 0, 1); //let it will be green.
}
After I’ve compiled and validated these shader I create a vertex array object and draw it like triangle strips:
glUseProgram(programHandle); //handle is checked and valid.
glBindVertexArray(vao);
glDrawArraysInstanced(GL_TRIANGLE_STRIP, 0, 4, 1);
The viewport of drawing is set to the window size like glViewport(0, 0, 800, 600). I pass to MVP a simple orthographic matrix with fallow code:
glUniformMatrix4fv(handle, 1, GL_FALSE, (GLfloat*)&matrix); //handle is checked and valid
where the matrix was initialized:
Matrix::CreateOrthographicOffCenter(-200, 200, -200, 200, 1.0f, -1.0f, &matrix);
...
void Matrix::CreateOrthographicOffCenter(float left, float right, float bottom, float top, float zNearPlane, float zFarPlane, Matrix* matrix)
{
memset(matrix, 0, sizeof(Matrix));
matrix->M11 = 2.0f / (right - left);
matrix->M14 = (-right - left) / (right - left);
matrix->M22 = 2.0f / (top - bottom);
matrix->M24 = (-top - bottom) / (top - bottom);
matrix->M33 = 1.0f / (zFarPlane - zNearPlane);
matrix->M34 = (-zNearPlane) / (zFarPlane - zNearPlane);
matrix->M44 = 1.0f;
}
The problem is I got no triangle strips on my screen. I tried to draw vertex without MVP matrix (gl_Position = vec4(Position[gl_VertexID], 0.0, 1.0)) but also got nothing. How to detect where the problem is?
And what exactly is stored in that VAO? I’m guessing your answer will be “nothing.”
If so, then you have run afoul of several problems. If this is a compatibility context (or GL 2.1 or before), then OpenGL does not allow you to render with a VAO that has nothing in it. That is, you can’t render with all attributes disabled. You will get a GL_INVALID_OPERATION error.
However, if you are in a core context 3.2 or above, then you can render with a disabled VAO.
Of course, that’s just what the OpenGL specification says. What NVIDIA’s drivers say is that you can render with a disabled VAO in both core and compatibility. What ATI’s drivers say is that you can’t render with a disabled VAO in both core and compatibility.
In short, if you want your code to work, bind something. Enable an array and put a buffer object there. It doesn’t matter what is in it, since your shader simply won’t care. But if you want it to work on different implementations, bind something.