PDA

View Full Version : GL_ARB_vertex_array_object



Groovounet
11-05-2008, 04:52 AM
I installed 180 nvidia drivers to play a bit with the new extensions :D

First try ... first failure ...
How are we supose to use VAOs?

Here is how I did:

Create a vertex object:


glGenVertexArrays(1, &positionArrayName);
glBindVertexArray(positionArrayName);
glVertexAttribPointer(positionBufferAttrib, 2, GL_FLOAT, GL_FALSE, 0, 0);


Create a buffer object:


glGenBuffers(1, &positionBufferName);
glBindBuffer(GL_ARRAY_BUFFER, positionBufferName);
glBufferData(GL_ARRAY_BUFFER, PositionSize, PositionData, GL_STATIC_DRAW);


Draw:


glBindVertexArray(positionArrayName);
glBindBuffer(GL_ARRAY_BUFFER, positionBufferName);
glEnableVertexAttribArray(positionBufferAttrib);
glDrawArrays(GL_TRIANGLES, 0, VertexCount);
glDisableVertexAttribArray(positionBufferAttrib);


Result:
Black screen ...

any idea?

Groovounet
11-05-2008, 05:16 AM
I make something working but ... I don't understand!

What I would like to do it is something like:

A: Create a single vertex array object. (VAO)
B: Create several buffer objects. (BO)
C: Bind the VAO
D: Loop over all BOs by binding them as array buffer object and draw.

This results to crashes.

If I unbind a buffer object it just crashes ... (even at creation stage!)

_NK47
11-05-2008, 05:41 AM
are function pointers resolved? should be != NULL.

Groovounet
11-05-2008, 06:08 AM
Oki I get it all ... I'm a bit disappointed by this extension ...

This is nice:



for(std::size_t i = 0; i < positionArrayName.size(); ++i)
{
glBindVertexArray(positionArrayName[i]);
glDrawArrays(GL_TRIANGLES, 0, VertexCount);
}
glBindVertexArray(0);


But I was expecting a feature that allow fast buffer bind not a calls wrapper.

I would like somting like this:



glBindVertexArray(positionArrayName);
for(std::size_t i = 0; i < positionBufferName.size(); ++i)
{
glActiveArray(GL_ARRAY0);
glBindBuffer(positionBufferName[i]);
glDrawArrays(GL_TRIANGLES, 0, VertexCount);
}
glBindVertexArray(0);


Or even better the direct state access way:


glBindVertexArray(positionArrayName);
for(std::size_t i = 0; i < positionBufferName.size(); ++i)
{
"glVertexArrayBindBuffer"(positionArrayName, GL_ARRAY0, positionBufferName[i]);
glDrawArrays(GL_TRIANGLES, 0, VertexCount);
}
glBindVertexArray(0);

_NK47
11-05-2008, 06:10 AM
Vertex buffer objects? i get it, should be an array.

Korval
11-05-2008, 11:28 AM
But I was expecting a feature that allow fast buffer bind not a calls wrapper.

I would like somting like this:

The point of VAO is to get rid of the overhead of calling the gl*Pointer calls when using buffer objects. So the VAO must naturally store the buffer objects that the pointers are bound to.

Groovounet
11-05-2008, 11:30 AM
Yes, but could they be improved to allow changing buffers? Seams possible to me.

Brolingstanz
11-05-2008, 12:05 PM
One pattern with VAO might be to create a limited set of (ring) buffers (with a correspondingly limited set of formats) - pretty common nowadays. You could, at least in theory, utilize a single VAO for the whole enchilada.

Steps to creating and using a VAO are roughly

// Create vertex buffer
uint vb;
GenBuffers(1, &vb);
BindBuffer(...);
BufferData(...);
BindBuffer(0);

// Create vertex array object
uint vao;
GenVertexArrays(1, &vao);

// Establish vertex array buffer and format
BindVertexArray(vao);
BindBuffer(VERTEX_ARRAY_BUFFER, vb);
VertexAttribPointer(0, ...);
VertexAttribPointer(1, ...);
VertexAttribPointer(2, ...);
...
BindBuffer(0);
BindVertexArray(0);


// Then to draw...
BindVertexArray(vao);
DrawArrays(...);
BindVertexArray(0);

I'm not exactly sure what the ring buffer patter would look like in GL3, but the new buffer mapping API looks like a good candidate for some trial and error...

Groovounet
11-05-2008, 01:41 PM
So you mean using few buffers but big ones and put all the meshes with the same format in this buffer?

jeffb
11-05-2008, 07:58 PM
I believe the problem with your example code (first post) is that you're not calling VertexAttribPointer after binding the VBO. Remember, VertexAttribPointer latches whatever is currently bound to ARRAY_BUFFER. i.e. it should be:

glGenVertexArrays(1, &positionArrayName);
glGenBuffers(1, &positionBufferName);
glBindVertexArray(positionArrayName);
glBindBuffer(GL_ARRAY_BUFFER, positionBufferName);
glBufferData(GL_ARRAY_BUFFER, PositionSize, PositionData, GL_STATIC_DRAW);
glVertexAttribPointer(positionBufferAttrib, 2, GL_FLOAT, GL_FALSE, 0, 0);
glEnableVertexAttribArray(positionBufferAttrib);
glDrawArrays(GL_TRIANGLES, 0, VertexCount);

> Yes, but could they be improved to allow changing buffers?

This is legal and should work.