I have a Vertex Array Object (VAO) and a bunch of
vertex attribute arrays enabled in this VAO for
vertices, normals and stuff.
I wonder what could happen when I only use one of
these vertex attribute arrays in the active shader
(i.e. there is only an attribute variable declared
for the vertex array but not for the normal array)?
The thing is that I switch from a shader that uses
all of the enabled attribute arrays to a wireframe
shader which only needs the vertex array and I
wonder if I have to disable all the unused arrays
in the VAO or if I could keep them enabled for
the wireframe shader without crashing the system
on one of the many video cards around.
You cannot enable/disable attribute arrays inside VAO at will. This is the purpose of VAO, to collect client states. You should create another VAO with appropriate attributes enabled, and activate it before drawing wireframe objects.
Or, maybe it is better to cease using VAO. It would be a faster solution.
If attribute arrays are enabled but not properly initialize, it would crash the application for sure. But, if buffers are valid, and you are using proper indices for the attributes, it will probably work.
I’m a little bit confused now because one said it will
not crash and the other “it could crash”. I use “proper”
indices for the attributes but for the wireframe shader
they are not bound after linking since there is no
attribute variable in the shader except for vertices.
So could this crash or not?
Secondly if you say it is not possible to enable/disable
attribute arrays inside VAO at will, does this mean if I
have enabled a vertex attribute array once for a VAO I
could never disable it again for this VAO? So a call
to glDisableVertexAttribArray inside a bound VAO is
You say in this case it is maybe better to cease using
VAO. But isn’t an active VAO mandatory in OpenGL 3.2 core
profile? I remember that nothing worked as soon as I had
no VAO enabled and then read in the 3.2 core profile spec
that a VAO must always be enabled.
Ok thanks Alfonse. Btw the switch to wireframe shader without
disabling the unused attribute arrays works fine here.
And since you said it should also work on any other system
I’ll go the lazy way without creating another VAO
It should work, but you could have problems if you try to increase the size of just one array + use the same VAO without disabling unused attribute arrays, because the spec says that elements from each enabled array are transferred to the GL; it doesn’t say anything about not sending enabled but unused attribute array elements.
If the enabled but unused attribute array elements really are transferred, then it might be worth benchmarking to see if it’s faster to disable them. If they aren’t transferred if unused, then maybe the spec should reflect this.
The life is boring without quarreling with you.
Yes, I know what I’m talking about, but I’m sorry because the post was too short to elaborate what I meant.
Of course that VAO is mutable, but it has to be selected (bound) and changed. It is an expensive operation compared to just enabling/disabling vertex attributes. That is what I meant when I said at will (meaning outside VAO). Sorry, “inside” was not a proper word.
I’m using GL 3.3/4.1 core profiles with forward compatibility bit set, and it works without VAOs. Please, can you point me to the page in the spec where it is written that VAO is mandatory? I’m using NVIDIA drivers and they work just fine without VAO.
And for the performance issues of the VAO, just search this forum to find out what the others mean.
Hey, Schnulla, OpenGL is not a rocket science. You do not have to spend millions of dollars and kill many people to find out if it works. This is why I like programming - you can everything get checked by yourself!
Just to encourage you, no, you probably cannot crash the application. What I was talking about is misuse of attributes’ indices. Sorry for the confusion!
E.2.2 Removed Features
Client vertex and index arrays - all vertex array attribute and element array
index pointers must refer to buffer objects. The default vertex array object
(the name zero) is also deprecated. Calling VertexAttribPointer when no
buffer object or no vertex array object is bound will generate an INVALID_-
OPERATION error, as will calling any array drawing command when no vertex
array object is bound.
NVidia isn’t following (the appendices of) the spec, so it’s something you have to watch out for if you decide to deploy to other vendors who are following the spec in this case. Creating a dummy VAO + binding + forgetting about it is a quick way to follow the spec. It’s not really clear to me why disallowing 0 was required though.
Of course that VAO is mutable, but it has to be selected (bound) and changed. It is an expensive operation compared to just enabling/disabling vertex attributes.
Is it? How much more expensive is it? Got any data on that?
And I also wonder to which location the
data of unused arrays is transferred since there is no
“space” (variable) defined in the shader?
You’re assuming that vertex attributes in GLSL are special locations. They’re really just a block of memory that’s formatted as an array of 16 vec4’s. Which ones GLSL happens to use depend on what attributes were used with the program object when it was linked.
Attributes in unused arrays would be transferred to those compartments of the attribute memory block. The fact that GLSL doesn’t bother to read that location would be inconsequential.
Although English is not my native language, as far as I understand the spec, this is NOT what you said. “Client vertex and index arrays” is related to VA (vertex arrays) what is really deprecated feature. I have to draw your attention to “OR” in the spec. Please read it again and carefully. VBOs can be used without VAOs also according to the spec!
P.S. Maybe it doesn’t work with ATI, but that’s another problem. Hm, probably one more reason to adhere to NVIDIA, at least when OpenGL is concerned.