无法使用 Java OpenGL VBO 同时显示 2 个项目

Posted

技术标签:

【中文标题】无法使用 Java OpenGL VBO 同时显示 2 个项目【英文标题】:Unable to show 2 items simultaneously with Java OpenGL VBO's 【发布时间】:2016-01-04 07:28:01 【问题描述】:

我开始学习 OpenGL,并尝试通过 VBO 扩展我的程序。我有以下代码:

public void init(GLAutoDrawable d) 

        [...]

            int perVertexFloats = (3+4+2+3);
            float vertexData[] = loadVertexData("ball.vbo", perVertexFloats);
            float vertexData1[] = loadVertexData("bar.vbo", perVertexFloats);

            vertNo = vertexData.length / perVertexFloats;
            FloatBuffer dataIn = Buffers.newDirectFloatBuffer(vertexData.length);
            dataIn.put(vertexData);
            dataIn.flip();

            vertNo1 = vertexData1.length / perVertexFloats;
            FloatBuffer dataIn1 = Buffers.newDirectFloatBuffer(vertexData1.length);
            dataIn1.put(vertexData1);
            dataIn1.flip();

         // generating vertex VBO
            gl.glGenBuffers(1, vertBufID, 0);
            gl.glBindBuffer(GL2.GL_ARRAY_BUFFER, vertBufID[0]);
            gl.glBufferData(GL2.GL_ARRAY_BUFFER, dataIn.capacity()*Buffers.SIZEOF_FLOAT, dataIn, GL2.GL_STATIC_DRAW);

         // generating vertex VBO2
            gl.glGenBuffers(1, vertBufID, 1);
            gl.glBindBuffer(GL2.GL_ARRAY_BUFFER, vertBufID[1]);
            gl.glBufferData(GL2.GL_ARRAY_BUFFER, dataIn1.capacity()*Buffers.SIZEOF_FLOAT, dataIn1, GL2.GL_STATIC_DRAW);

        

public void display(GLAutoDrawable d) 

[...]

        // activating VBO
        gl.glTranslatef(-0.1f, -0.85f, 0.0f);
        gl.glScalef(0.3f, 0.3f, 0.3f);                              // resize the ball
        gl.glBindBuffer(GL2.GL_ARRAY_BUFFER, vertBufID[0]);
        int stride = (3+4+2+3)*Buffers.SIZEOF_FLOAT;
        int offset = 0;

     // activating VBO2
        gl.glTranslatef(2.0f, -0.2f, 0.0f);             
        gl.glScalef(3.0f, 3.0f, 3.0f);                              //resize the bar
        gl.glRotatef(90, 0.0f, 0.0f, 1.0f);     
        gl.glBindBuffer(GL2.GL_ARRAY_BUFFER, vertBufID[1]);


     // position
        gl.glVertexPointer(3, GL2.GL_FLOAT, stride, offset);
        gl.glEnableClientState(GL2.GL_VERTEX_ARRAY);

     // color
        offset = 0 + 3*Buffers.SIZEOF_FLOAT;
        gl.glColorPointer(4, GL2.GL_FLOAT, stride, offset);
        gl.glEnableClientState(GL2.GL_COLOR_ARRAY);

     // texture
        offset = 0 + (3+4)*Buffers.SIZEOF_FLOAT;
        gl.glTexCoordPointer(2, GL2.GL_FLOAT, stride, offset);
        gl.glEnableClientState(GL2.GL_TEXTURE_COORD_ARRAY);

        // normals
        offset = 0 + (3+4+2)*Buffers.SIZEOF_FLOAT;
        gl.glNormalPointer(GL2.GL_FLOAT, stride, offset);
        gl.glEnableClientState(GL2.GL_NORMAL_ARRAY);

     // bind texture
        if(mode == 0) 
          gl.glEnable(GL2.GL_TEXTURE_2D);
          gl.glBindTexture(GL2.GL_TEXTURE_2D, texID);
          gl.glBindTexture(GL2.GL_TEXTURE_2D, texID1);
        else
          gl.glDisable(GL2.GL_TEXTURE_2D);
          gl.glBindTexture(GL2.GL_TEXTURE_2D, 0);
        

        // render data
        gl.glDrawArrays(GL2.GL_TRIANGLES, 0, vertNo);

     // render data2
        gl.glDrawArrays(GL2.GL_TRIANGLES, 0, vertNo1);


        gl.glDisableClientState(GL2.GL_VERTEX_ARRAY);
        gl.glDisableClientState(GL2.GL_COLOR_ARRAY);
        gl.glDisableClientState(GL2.GL_TEXTURE_COORD_ARRAY);
        gl.glDisableClientState(GL2.GL_NORMAL_ARRAY);
        gl.glDisable(GL2.GL_TEXTURE_2D);

        gl.glFlush();
    

我的对象是一个球和一个酒吧。首先,我只用球测试了代码。它出现。然后我还想添加栏。酒吧出现了。我的问题是,当酒吧出现时,球消失了。我希望同时显示球和横杆。有人可以帮助我并告诉我我的错误在哪里吗?

【问题讨论】:

【参考方案1】:

问题在于显示功能:您只为第二个缓冲区绑定指定 Vertex/Color/... 指针。这样做的原因是 OpenGL 总是在当前状态下运行。因此,如果您绑定另一个缓冲区,则第一个缓冲区不再存在。因此,顶点指针仅在最后绑定的缓冲区上操作。绘图函数也一样,它也只对当前设置的顶点指针起作用。

如果你想同时绘制,那么逻辑顺序必须看起来像这样:

//First object
glTranslatef/glScalef/... for object1
glBindBuffer(buffer1)

gl.glVertexPointer(...) and all the other pointers/glEnableClientStates

gl.glDrawArrays(vertNo);

//Now second object

glTranslatef/glScalef/... for object2
glBindBuffer(buffer2)

gl.glVertexPointer(...) and all the other pointers/glEnableClientStates

gl.glDrawArrays(vertNo1);

【讨论】:

以上是关于无法使用 Java OpenGL VBO 同时显示 2 个项目的主要内容,如果未能解决你的问题,请参考以下文章

OpenGL:尝试使用 VBO(顶点缓冲区对象)绘制线条,它不显示

OpenGL VBO 不显示

OpenGL ES 2.0:似乎无法渲染第二个 VBO?

OpenGL VBO 绘图

OpenGL VBO 绘制顺序

OpenGL ES 1.1:无法转换为 VBO