我已经让我的OpenGL代码正常运行,但我想要提高一下它的性能(希望在旧设备上提高帧速率)。我正在尝试使用一个顶点缓冲对象来实现这个目标。
我的所有代码都只是绘制了一系列360个GL_TRIANGLES,并将纹理应用于它们。我将坐标和纹理坐标编织到一个数据结构中。
这是我的初始化相关部分:
然后我绑定缓冲区。
最后进行绘制。
我的所有代码都只是绘制了一系列360个GL_TRIANGLES,并将纹理应用于它们。我将坐标和纹理坐标编织到一个数据结构中。
typedef struct {
GLfloat vertex[2];
GLfloat texture[2];
GLfloat padding[4];
} TextureVertex2D;
typedef struct {
TextureVertex2D textureVertex[3];
} TextureTriangle2D;
这是我的初始化相关部分:
textureTriangles = (TextureTriangle2D*)malloc(360 * sizeof(TextureTriangle2D));
glGenTextures(1, &texture[0]);
glBindTexture(GL_TEXTURE_2D, texture[0]);
// This section is the only new code introduced for the VBOs.
glGenBuffers(1, &buffer[0]);
glBindBuffer(GL_ARRAY_BUFFER, buffer[0]);
glBufferData(GL_ARRAY_BUFFER, sizeof(TextureTriangle2D)*360, textureTriangles[0].textureVertex[0].vertex, GL_DYNAMIC_DRAW);
// end new code
glVertexPointer(2, GL_FLOAT, sizeof(TextureVertex2D), textureTriangles[0].textureVertex[0].vertex);
glTexCoordPointer(2, GL_FLOAT, sizeof(TextureVertex2D), textureTriangles[0].textureVertex[0].texture);
/*
textureTriangles is filled and the texture image is loaded in
*/
对于保存到实际VBO的操作,我尝试了两种方法(这两种方法都得到了相同的结果)
// Option 1
GLvoid* vbo_buffer = glMapBufferOES(GL_ARRAY_BUFFER, GL_WRITE_ONLY_OES);
memcpy(vbo_buffer, textureTriangles[0].textureVertex[0].vertex, 360 * sizeof(TextureTriangle2D));
glUnmapBufferOES(GL_ARRAY_BUFFER);
// Option 2
glBufferSubData(GL_ARRAY_BUFFER, sizeof(TextureVertex2D), 360 * sizeof(TextureTriangle2D), textureTriangles[0].textureVertex[0].vertex);
然后我绑定缓冲区。
glBindBuffer(GL_ARRAY_BUFFER, buffer[0]);
最后进行绘制。
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glDrawArrays(GL_TRIANGLES, 0, 3*360);
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
如果没有使用VBO,绘图可以正常工作。但是当我添加以上的VBO代码后,绘图位置不再正确(偏移几个像素),并且整个应用程序会锁死。有什么想法吗?
glBufferSubData
中,第二个参数应该是0
而不是sizeof(TextureVertex2D)
。但是,当更新整个缓冲区时,你应该使用glBufferData
。 - Christian Rau