使用 GL_ARRAY_BUFFER 创建索引缓冲区和使用 GL_ELEMENT_ARRAY_BUFFER 创建索引缓冲区在 OpenGL 中有什么区别吗?
Is there any difference in OpenGL between creating Index Buffers with GL_ARRAY_BUFFER and creating them with GL_ELEMENT_ARRAY_BUFFER?
我研究 OpenGL 有一段时间了,现在,在做一个项目时,我发现,当我创建索引缓冲区时,如果我将它绑定到 GL_ARRAY_BUFFER
而不是GL_ELEMENT_ARRAY_BUFFER
有(显然)相同的结果。
我的意思是,顶点缓冲区总是绑定到 GL_ARRAY_BUFFER
,但是如果我创建这样的索引缓冲区:
glCreateBuffers(1, &m_BufferID);
glBindBuffer(GL_ARRAY_BUFFER, m_BufferID);
glBufferData(GL_ARRAY_BUFFER, count * sizeof(uint), vertices, GL_STATIC_DRAW);
然后,例如在绘制几何图形时,我将其绑定到 GL_ELEMENT_ARRAY_BUFFER
,工作正常,但我不知道为什么我认为必须使用 [=14= 创建索引缓冲区] 也是,但是……其实有什么“内在”的区别吗?
是的。 ARRAY_BUFFER
绑定是全局状态,而 ELEMENT_ARRAY_BUFFER
绑定在顶点数组对象中说明。参见 Index buffers。
因此,glBindBuffer(GL_ELEMENT_ARRAY_BUFFER m_BufferID)
更改当前绑定的顶点数组对象中的状态。
请注意,与 index buffer (ELEMENT_ARRAY_BUFFER
), the vertex buffer 绑定 (ARRAY_BUFFER
) 相比,它是一个全局状态。
VAOs 状态向量中声明的每个属性可能引用不同的 ARRAY_BUFFER
。在调用 glVertexAttribPointer
时存储此引用。然后将当前绑定到目标ARRAY_BUFFER
的缓冲区关联到指定的属性索引,并将对象的名称(值)存储在当前绑定的VAO的状态向量中。
然而,索引缓冲区是 VAO 的一种状态。如果缓冲区绑定到目标 ELEMENT_ARRAY_BUFFER
,则此缓冲区分配给当前绑定的顶点数组对象。
就缓冲区对象本身的性质而言?不。所有缓冲区对象都是相同的,并且可以用于适合缓冲区对象的任何任务。缓冲区对象不具有最初用于绑定的特殊属性。
但是,GL_ELEMENT_ARRAY_BUFFER
绑定点本身有点不寻常。它不是全局上下文状态的一部分;它是 VAO 州的一部分。因此,如果您没有绑定 VAO(在核心配置文件上下文下),那么您无法将任何内容绑定到该绑定点。当您绑定到该绑定点时,您正在影响当前绑定的 VAO 的状态。如果您更改当前绑定的 VAO,您将更改哪个缓冲区绑定到元素数组绑定点。
所以一般来说,如果您打算要做的是将缓冲区附加到当前绑定的 VAO,那么您应该只绑定到那个点。
我研究 OpenGL 有一段时间了,现在,在做一个项目时,我发现,当我创建索引缓冲区时,如果我将它绑定到 GL_ARRAY_BUFFER
而不是GL_ELEMENT_ARRAY_BUFFER
有(显然)相同的结果。
我的意思是,顶点缓冲区总是绑定到 GL_ARRAY_BUFFER
,但是如果我创建这样的索引缓冲区:
glCreateBuffers(1, &m_BufferID);
glBindBuffer(GL_ARRAY_BUFFER, m_BufferID);
glBufferData(GL_ARRAY_BUFFER, count * sizeof(uint), vertices, GL_STATIC_DRAW);
然后,例如在绘制几何图形时,我将其绑定到 GL_ELEMENT_ARRAY_BUFFER
,工作正常,但我不知道为什么我认为必须使用 [=14= 创建索引缓冲区] 也是,但是……其实有什么“内在”的区别吗?
是的。 ARRAY_BUFFER
绑定是全局状态,而 ELEMENT_ARRAY_BUFFER
绑定在顶点数组对象中说明。参见 Index buffers。
因此,glBindBuffer(GL_ELEMENT_ARRAY_BUFFER m_BufferID)
更改当前绑定的顶点数组对象中的状态。
请注意,与 index buffer (ELEMENT_ARRAY_BUFFER
), the vertex buffer 绑定 (ARRAY_BUFFER
) 相比,它是一个全局状态。
VAOs 状态向量中声明的每个属性可能引用不同的 ARRAY_BUFFER
。在调用 glVertexAttribPointer
时存储此引用。然后将当前绑定到目标ARRAY_BUFFER
的缓冲区关联到指定的属性索引,并将对象的名称(值)存储在当前绑定的VAO的状态向量中。
然而,索引缓冲区是 VAO 的一种状态。如果缓冲区绑定到目标 ELEMENT_ARRAY_BUFFER
,则此缓冲区分配给当前绑定的顶点数组对象。
就缓冲区对象本身的性质而言?不。所有缓冲区对象都是相同的,并且可以用于适合缓冲区对象的任何任务。缓冲区对象不具有最初用于绑定的特殊属性。
但是,GL_ELEMENT_ARRAY_BUFFER
绑定点本身有点不寻常。它不是全局上下文状态的一部分;它是 VAO 州的一部分。因此,如果您没有绑定 VAO(在核心配置文件上下文下),那么您无法将任何内容绑定到该绑定点。当您绑定到该绑定点时,您正在影响当前绑定的 VAO 的状态。如果您更改当前绑定的 VAO,您将更改哪个缓冲区绑定到元素数组绑定点。
所以一般来说,如果您打算要做的是将缓冲区附加到当前绑定的 VAO,那么您应该只绑定到那个点。