c++ - OpenGL 避免多次调用 glDrawElements

标签 c++ opengl glsl opengl-3

我正在将我们的图形从使用旧的固定管道功能迁移到使用可编程管道。我们最简单的模型只是空间中点的集合,其中每个点都可以用不同的形状表示。其中之一是立方体。

我的代码基于立方体 example来自 OpenGL 精湛。

在这个例子中,立方体被放置在有些随机的地方,而我将在空间中有固定点亮。我想知道是否有办法将该列表传递给我的着色器,以便在每个点绘制一个立方体,而不是循环遍历列表并每次调用 glDrawElements。这是否值得麻烦(性能方面)?

PS 我们仅限于 OpenGL 3.3 功能。

最佳答案

Is that even worth the trouble (performance wise)?

可能是的,但还是要尝试分析。

你要找的是实例化渲染,看看glDrawElementsInstancedglVertexAttribDivisor .

您要做的是将一个通用立方体(以原点为中心)的 8 个顶点存储在一个缓冲区中,并将每个立方体的中心坐标存储在另一个顶点属性缓冲区中。

然后您可以使用 glDrawElementsInstanced 绘制 N 个立方体,从第一个缓冲区获取顶点,并使用存储在第二个缓冲区中的特定位置在着色器中转换它们。

像这样:

glVertexAttribPointer( vertexPositionIndex, /** Blah .. */ );
glVertexAttribPointer( cubePositionIndex, /** Blah .. */ );
glVertexAttribDivisor( cubePositionIndex, 1 ); // Advance one vertex attribute per instance

glDrawElementsInstanced( GL_TRIANGLES, 36, GL_UNSIGNED_BYTE, indices, NumberOfCubes );

在你的顶点着色器中你需要两个属性:

 vec3 vertexPosition; // The coordinates of a vertex of the generic cube
 vec3 cubePosition; // The coordinates of the center the specific cube being rendered

 // .... 
 vec3 vertex = vertexPosition + cubePosition;

显然,您还可以有一个缓冲区来存储每个立方体的大小,或者另一个缓冲区来存储方向,这个想法是一样的。

关于c++ - OpenGL 避免多次调用 glDrawElements,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24701223/

相关文章:

c++ - 在 OpenGL 中更新模板缓冲区时出现问题

C++:使用模板折叠具有不同类型和功能的重复代码

c++ - OpenGL:点在无穷远的三角形

opengl - GLSL 中可以进行可变参数宏扩展吗?

opengl - 如何在 GLSL 中创建纬度(水平)等高线?

java - 如何获取片段着色器的坐标? gl_FragCoord 不工作

c++ - 为arm-linux-gnueabi-gcc交叉编译libcurl

c++ - std::unordered_map内部的std::array的值初始化

c++ - 适用于 Windows 7 的 OpenGL

performance - 10,000 个静态立方体的 OpenGL 性能