jsi*_*ons 9 c opengl 2d vbo scenegraph
虽然OpenGL 3.x本身的最新参考文献似乎很少,但OpenGL的实际低级操作相对简单.然而,我在试图甚至概念化如何操纵VBO以呈现动态世界时遇到了严重的麻烦.
显然,旧的直接模式方式是不适用的,但从那里我去哪里?我是否编写了某种场景结构,然后将其转换为一组顶点并将其传输到VBO,我将如何存储翻译数据?如果是这样,那么代码看起来会如何?
基本上真的不确定如何继续.
如果您的整个世界都是真正的动态,您可以使用GL_STREAM_DRAW_ARB
使用标记并重置每个帧上的数据.不要费心操纵它,只是尝试尽可能高效地流.
但是,我假设您有一个由多个相对于彼此移动的刚性对象组成的场景.在这种情况下,为每个对象使用一个VBO并指定GL_STATIC_DRAW_ARB
使用标志.然后,您可以为对象的每个实例设置modelview变换,并使用每个实例的一个绘制调用来渲染它们.
经验法则(在PC上)是每CPU的CPU发出不超过一次的绘图调用.这是一个粗略的估计,但它有一些道理.如果您保持低于此限制,请不要担心将多个独立对象放入单个VBO或其他性能技巧.
小智 9
简短回答:
使用glMapBufferRange并仅更新需要修改的子范围.
答案很长:
诀窍是用glMapBufferRange映射已经存在的缓冲区,然后只映射你需要的范围.鉴于这些假设:
然后,您可以使用glMapBufferRange仅更新更改的部分,并保留其余数据.使用glBufferData的完整上传作为乌龟很慢,因为它们删除旧的内存存储并分配一个新的内存存储.这是上传新数据的补充.glMapBufferRange只允许您读/写现有数据,它不进行分配或释放.
但是,如果使用骨架动画,而是将顶点变换作为每顶点4x4矩阵传递到顶点着色器,并在那里进行计算.每个顶点数据当然是用glVertexAttribPointer指定的.
另外,请记住,您可以在顶点着色器中读取纹理数据,并且OpenGL 3.1引入了一些新的实例绘制调用; glDrawArraysInstanced和glDrawElementsInstanced.这些组合可用于特定于实例的查找.也就是说,您可以使用相同的几何数据绑定来实例绘制调用,但是发送位置或您需要的每个顶点数据作为纹理或纹理数组.这可以避免混合和匹配不同的顶点数组数据集.
想象一下,如果要渲染相同模型的100个实例,但具有不同的位置或颜色方案.甚至纹理贴图.
使用VBO并不意味着您只需要使用单个绘制调用来渲染整个场景.您仍然可以发出多个绘制调用,并在此过程中设置不同的转换矩阵.
例如,如果您使用的是场景图,则场景图中的每个模型都可以对应一个绘图调用.在这种情况下,使用VBO的最简单方法是为每个模型创建一个单独的VBO.
作为优化,您可以将多个模型组合到一个VBO中,然后在进行绘制调用时传递非零偏移; 这从VBO中剔除了正确的模型.将多个绘制调用组合成单个绘制调用也是可取的,但如果它们需要独立的变换则不可能.(实际上,如果你使用实例化或顶点混合,在某些情况下是可能的,但我建议首先将基础知识排除在外.)
归档时间: |
|
查看次数: |
6550 次 |
最近记录: |