I'm currently trying to set up a function that renders a textured 2D quad using VBOs. The function changes the vertex data of the VBO every time it's called so that you can stretch it, but the texture data of the VBO doesn't change. In other words I want to be able to change the vertex data without having to change the texture data of the VBO.

When I store my VBO I have a struct that contains 4 GLfloats (VertexData2D), the first two GLfloats represent the vertex data and the last two GLfloats represent the texture data. My problem is that I can't find a way to only change the vertex data without having to change the texture data, since the entire VBO contains both vertex data and texture data.

(the VBO is set with GL_DYNAMIC_DRAW). I update the VBO starting at index 0, VData is the VBO that's going to replace the current one. Each vertex has the size

4 * sizeof(GLfloat)

and since I'm rendering a quad, the stride results in

4 * 4 * sizeof(GLfloat)

It's in glBufferSubData() that the problem is, my VBO contains both the vertex data and texture data, but I only want to change the vertex data. glBufferSubData() overwrites the current VBO, but I only want it to overwrite parts of it. This is essentially how I want it to work:

For this kind of thing you're really better off using a vertex shader to manipulate your positions. The function that changes positions can be coded in GLSL (perhaps with a uniform or two to control it), with all of the vertex data remaining static.

Otherwise you can achieve a similar effect by loading a new modelview matrix that represents your stretching.

Whichever way you choose, you need to be aware that VBOs are not intended for this kind of partial update. You can certainly do it, but the best use of VBOs comes from either having completely static data in them, from replacing the entire set of data, or from appending to existing data up to the maximum size of the buffer object. But trying to brute-force their usage in the same way as if you were still using immediate mode is extremely unlikely to end well.

It appears that the gentleman thought C++ was extremely difficult and he was overjoyed that the machine was absorbing it; he understood that good C++ is difficult but the best C++ is well-nigh unintelligible.

But trying to brute-force their usage in the same way as if you were still using immediate mode is extremely unlikely to end well.

I feel like GLSL is a little too much for me at this point. Would you say that it's better to replace both the vertex data and the texture coordinates rather than partially update in this case when it comes to performance?

But trying to brute-force their usage in the same way as if you were still using immediate mode is extremely unlikely to end well.

I feel like GLSL is a little too much for me at this point. Would you say that it's better to replace both the vertex data and the texture coordinates rather than partially update in this case when it comes to performance?

No, I'd say it's better to profile and see which approach is fastest in your own program.

As a general guideline however, (1) interleaved data is going to be faster than non-interleaved data, and (2) updating all of a contiguous region in a VBO is going to be faster than jumping around to update smaller non-contiguous regions. Using non-interleaved data can help you avoid (2) (as you've discovered) but then you get bitten by (1).

To be honest, there are still some situations where not even using VBOs at all may be the best approach, and it looks as though you've got one here. If you've just got a single quad in that VBO, and if you need to update the data dynamically each frame, then glBegin/glEnd may even be faster. Remember - Quake used glBegin/glEnd and didn't suffer too much from it, so while it may not be the most optimal, it's still not as slow as some people might lead you to believe.

It appears that the gentleman thought C++ was extremely difficult and he was overjoyed that the machine was absorbing it; he understood that good C++ is difficult but the best C++ is well-nigh unintelligible.

Quake used glBegin/glEnd and didn't suffer too much from it, so while it may not be the most optimal, it's still not as slow as some people might lead you to believe.

You should rephrase it as "Quake used glBegin/glEnd with 90s GPU hardware if they had GPU hardware at all".

And it still runs nowadays.

The point is not to be a glBegin/glEnd lover, the point is to pick the appropriate solution for the problem you're trying to solve. Using buffer objects the wrong way will be slower.

It appears that the gentleman thought C++ was extremely difficult and he was overjoyed that the machine was absorbing it; he understood that good C++ is difficult but the best C++ is well-nigh unintelligible.