我能得到一个更全面/一般的描述吗?
我整个星期都在尝试研究这些东西,但我只进入超级技术解释或示例。
有人能解释一下这些VAO的总体流程或目标吗?也许可以概述一点在OpenGL中设置VAO的“分步”流程图?
我从来不是一个以身作则的人......因此,到目前为止,我在网上找到的所有东西都非常无济于事。
顶点缓冲区对象(VBO)包含顶点数据。您可以设置属性指针,指定如何访问和解释数据以绘制顶点-每个顶点有多少个组件,它们是如何存储的(例如GL_FLOAT)等。
顶点数组对象(VAO)保存了所有这些属性。它们的目的是允许您设置这些属性一次,然后在需要使用它们时通过一次状态更改来恢复它们。
这样做的好处是,您可以轻松地设置多个状态并恢复它们-如果我想绘制一个立方体和一个三角形,这是两个不同的状态-我为每个状态创建一个VAO,VAO为每个状态保存状态。当我想绘制立方体时,我只恢复立方体的状态。
设置
安装有四个步骤:
创建 VAO 非常简单:
GLuint vao_name;
glGenVertexArrays(1, &vao_name);
这将生成一个顶点数组,并将其名称存储在vao_name中。
创建 VAO 后,您需要绑定它:
glBindVertexArray(vao_name);
现在,对属性指针或元素数组缓冲区绑定所做的任何更改都将被保存。这是对以下任何一项的调用:
每当您进行这些调用之一时,相应的状态都会保存在当前绑定的 VAO 中。稍后再次绑定 VAO 时,状态将恢复。
一旦设置了状态,就可以解除VAO的绑定。通过绑定VAO 0:
glBindVertexArrays(0);
您还可以绑定不同的 VAO 并为其设置不同的状态。发生这种情况时,可以安全地更改属性指针,而不会中断以前的状态。
绘图
当你想画一些东西时,你所要做的就是恢复VAO:
glBindVertexArray(cube_vao)
glDrawArrays(GL_TRIANGLES, 0, 36);
glBindVertexArray(triangle_vao);
glDrawArrays(GL_TRIANGLES, 0, 3);
glBindVertexArray(0); //Unbind the VAO
编辑:
当我试图理解VAOs时,这些答案对我很有帮助:glVertex AttribPoenter覆盖,glVertex Attrib指针澄清,什么时候应该调用glVertex AttribPointer?
此外,一旦您了解了基本知识,OpenGL规范就很好地解释了这一点:https://www.opengl.org/registry/
VAO保存关于如何从VBOs读取属性的所有信息。
这包括每个属性在哪个VBO;偏移量、步距、编码方式(int、float、normalized或not)、每个属性有多少个值。换句话说,< code > glvertexattributepointer 的参数(以及调用时绑定的GL_ARRAY_BUFFER。
它还保存保存索引的元素数组缓冲区。
对于VAO是什么,请参阅@ratchet怪胎的答案。
至于VAO的目标,这是一个通过允许单个状态更改来设置所有顶点属性绑定来提高性能的问题,这不仅意味着更少的函数调用,而且还意味着OpenGL实现有更多的机会针对整个状态进行优化。