假设我使用新的(从OpenGL 4.3开始)glBindVertexBuffer机制设置了两个VAO:
glGenVertexArrays(1, &vaoIndex0);
glGenVertexArrays(1, &vaoIndex1);
Run Code Online (Sandbox Code Playgroud)
...
glBindVertexArray(vaoIndex0)
glBindVertexBuffer(bindingIndex0, ...)
glEnableVertexAttribArray(0)
glVertexAttribFormat(0, ...)
glVertexAttribBinding(0, bindingIndex0)
...
glBindVertexArray(0)
Run Code Online (Sandbox Code Playgroud)
...
glBindVertexArray(vaoIndex1)
glBindVertexBuffer(bindingIndex1, ...)
glEnableVertexAttribArray(0)
glVertexAttribFormat(0, ...)
glVertexAttribBinding(0, bindingIndex1)
...
glBindVertexArray(0)
Run Code Online (Sandbox Code Playgroud)
并且假设两者是独立的,除非它们存在于相同的OpenGL上下文中; 它们绑定不同的缓冲区,用于绘制不同的东西.
bindingIndex0需要与bindingIndex1不同吗?两个指数的平等(或不平等)是否有任何意义?
...
编辑:
在收到答案后,我开始明白,对于一个真正知道"顶点缓冲区绑定点"是什么的人,特别是它的范围是什么,我的问题似乎是在问一些与我的意图不同的东西.也许一个更好的措辞就是" 为了防止冲突,是否需要尽力避免重复使用OpenGL顶点缓冲区绑定点索引,甚至跨多个VAO?" 但无论如何,似乎现在已经回答了这两个问题:不,你不能重复使用"绑定点",并且不需要以这种方式避免索引冲突.
所有这些调用都会修改VAO状态.所以不,你不能在VAO中重复使用这些设置.您当然可以在多个VAO中将它们设置为相同,但是在设置每个VAO时必须进行一次必要的状态设置调用.
该bindingIndex0
和bindingIndex1
你在你的代码片段使用值没有任何特殊含义.它们只是建立绑定到绑定索引的缓冲区与glBindVertexBuffer()
使用该绑定索引指定的属性之间的连接.
唯一的条件是绑定索引必须小于您可以查询的值MAX_VERTEX_ATTRIB_BINDINGS
,保证至少为16.由于这些调用修改了每个VAO状态,因此绝对可以对多个VAO使用相同的绑定索引.
查看这些较新的状态设置调用的一种方法是,它们引入了以前不可用的间接级别:
glVertexAttribPointer()
在绑定所需缓冲区时调用,在顶点属性和缓冲区之间建立直接连接.glVertexAttribBinding()
.然后将绑定索引连接到缓冲区,该缓冲区与之建立glBindVertexBuffer()
.换句话说,在旧式中,连接是:
attribute index --> buffer
Run Code Online (Sandbox Code Playgroud)
这些4.3+通话的新风格:
attribute index --> buffer index --> buffer
Run Code Online (Sandbox Code Playgroud)
这种新灵活性的一个优点是,您可以通过一次调用将新缓冲区绑定到多个属性.只要所有这些属性具有相同的缓冲区索引,您只需要一次调用即可glBindVertexBuffer()
为所有属性指定新缓冲区.
以下不是官方标记.我刚刚完成了.但我认为通过写下一些伪数据结构来更正式地定义关系可能是有用的.
假设每个VAO包含两个数组来捕获上面解释的连接:
struct VAO {
...
uint bufferIndexBindings[MAX_VERTEX_ATTRIB_BINDINGS];
uint attribBufferIndices[MAX_VERTEX_ATTRIBS];
}
Run Code Online (Sandbox Code Playgroud)
这里讨论的两个调用将修改这个结构,如下所示:
glBindVertexBuffer(uint bindingIndex, uint buffer, ...) {
CurrentVAO.bufferIndexBindings[bindingIndex] = buffer;
}
glVertexAttribBinding(uint attribIndex, uint bindingIndex) {
CurrentVAO.attribBufferIndices[attribIndex] = bindingIndex;
}
Run Code Online (Sandbox Code Playgroud)
然后,此状态用于获取具有索引的给定属性的缓冲区attribIndex
:
CurrentVAO.bufferIndexBindings[CurrentVAO.attribBufferIndices[attribIndex]]
Run Code Online (Sandbox Code Playgroud)
这也说明了我在上面解释的间接,它在这里显示为状态表的两个级别的查找.
归档时间: |
|
查看次数: |
1352 次 |
最近记录: |