LWJGL Indexed VBO,很多混乱

Posted

技术标签:

【中文标题】LWJGL Indexed VBO,很多混乱【英文标题】:LWJGL Indexed VBO, a lot of confusion 【发布时间】:2014-03-12 14:44:22 【问题描述】:

我无法弄清楚如何使用索引 VBO,恕我直言,缺少有关它的信息(例如,索引 vbo 页面缺少 ATM 的 lwjgl 站点)。

我在顶点缓冲区中使用的结构是 pos.x, pos.y pos.z, tex.u, tex.v tex.W 和 norm.x, norm.y norm。 z,我的索引缓冲区结构是 posIndex, texIndex, normIndex 我正在从 .obj 文件中读取所有这些数据,如果缺少 tex 或 norm 我将其设置为 -1,-1,-1。

这是我将数据发送到 GPU 缓冲区的代码部分:

    this.VBOSize = Vertices.size();
    FloatBuffer vbo = BufferUtils.createFloatBuffer(this.VBOSize);
    for (int i = 0; i < this.VBOSize; i++) 
        vbo.put(Vertices.get(i));
    
    vbo.flip();
    glBindBuffer(GL_ARRAY_BUFFER, VBOHandle);
    glBufferData(GL_ARRAY_BUFFER, vbo, GL_STATIC_DRAW);

    this.IBOSize = Indices.size();
    IntBuffer ibo = BufferUtils.createIntBuffer(this.IBOSize);
    for (int i = 0; i < this.IBOSize; i++) 
        ibo.put(Indices.get(i));
    
    ibo.flip();
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, IBOHandle);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, ibo, GL_STATIC_DRAW);

    glBindBuffer(GL_ARRAY_BUFFER, 0);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);

这是我[错误地]渲染它的方式:

    glEnableVertexAttribArray(0);
    glEnableVertexAttribArray(1);
    glEnableVertexAttribArray(2);
    glBindBuffer(GL_ARRAY_BUFFER, Object3D.getVBOHandle());
    glVertexAttribPointer(0, 3, GL_FLOAT, true, 12, 0);//3 floats * 4 sizeof(float)
    glVertexAttribPointer(1, 3, GL_FLOAT, true, 12, 13);
    glVertexAttribPointer(2, 3, GL_FLOAT, true, 12, 25);

    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, Object3D.getIBOHandle());
    glDrawElements(GL_TRIANGLES, Object3D.getIBOSize(), GL_UNSIGNED_INT, 0);

    glDisableVertexAttribArray(0);
    glDisableVertexAttribArray(1);
    glDisableVertexAttribArray(2);

【问题讨论】:

【参考方案1】:

这不是 opengl 的工作方式。在 openGL 中,顶点是一个 set 属性,如位置、法线、颜色、文本坐标等等。索引渲染只引用 vertices。您不能对各种属性有不同的索引,而对整个集合只有一个索引。如果您遇到两个顶点共享其位置的情况,但不是 texcoords,就 GL 而言,它们是完全_不同的_顶点。您不能直接使用来自 lightwave .obj 文件的数据,但必须对数据进行预处理以生成 OpenGL 可以处理的顶点数组。

GL_AMD_interleaved_elements 扩展在某种程度上实现了您想要使用的功能。它仍然使用 32 位索引,但允许将它们拆分为 2 个 16 位或 4 个 8 位索引,以便为不同的属性使用不同的索引,但这种扩展远未在核心 GL 中得到广泛支持,并且还是很有限的。

现在有了可编程管道,人们也可以在着色器中手动取消索引,基本上(错误)使用顶点属性并通过纹理缓冲区对象访问真实的属性数组,但这是相当先进的,并且会影响性​​能不清楚。

【讨论】:

以上是关于LWJGL Indexed VBO,很多混乱的主要内容,如果未能解决你的问题,请参考以下文章

lwjgl 通过 JSlider 更新 VBO(颜色、顶点)

lwjgl 纹理多重绑定到一个 VBO

VBO 没有在 LWJGL 中正确创建

在不同系统上使用 VBO 进行 LWJGL 渲染

使用 VBO 使用 LWJGL 对 3D 立方体进行纹理处理

LWJGL VBO 三角形纹理坐标不起作用