OpenGL仅适用于第二帧

时间:2013-07-26 22:10:30

标签: c++ opengl render

我正在使用SFML,OpenGL和VC ++编译器。当我渲染某些东西时,它只会在第二次运行时正确弹出(?)。这是我的代码:

void Renderer::initializeOpenGL() {
    glEnable(GL_DEPTH_TEST);
    glEnableClientState(GL_VERTEX_ARRAY);
    glOrtho(0, 1024, 0, 576, 0, 1024);
}

void Renderer::drawWorld(World* world) {
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glColor3f(1.F, 1.F, 1.F);
    std::vector<int> vertices;
    for(unsigned int x = 0; x < world->width; x++) {
        bool left = false, right = false;
        if(x == 0)
            left = true;
        else if(x == world->width -1)
            right = true;
        for(unsigned int z = 0; z < world->depth; z++) {
            bool front = false, back = false;
            if(z == 0)
                front = true;
            else if(z == world->depth -1)
                back = true;
            for(unsigned int y = 0; y < world->height; y++) {
                if(!world->blocks[x][z][y])
                    continue;
                if(left == true || !world->blocks[x-1][z][y]) {
                    vertices.push_back(x);
                    vertices.push_back(y);
                    vertices.push_back(z);

                    vertices.push_back(x);
                    vertices.push_back(y);
                    vertices.push_back(z+1);

                    vertices.push_back(x);
                    vertices.push_back(y+1);
                    vertices.push_back(z+1);

                    vertices.push_back(x);
                    vertices.push_back(y+1);
                    vertices.push_back(z);
                }
                if(right == true || !world->blocks[x+1][z][y]) {
                    vertices.push_back(x+1);
                    vertices.push_back(y);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y);
                    vertices.push_back(z+1);

                    vertices.push_back(x+1);
                    vertices.push_back(y+1);
                    vertices.push_back(z+1);

                    vertices.push_back(x+1);
                    vertices.push_back(y+1);
                    vertices.push_back(z);
                }

                if(front == true || !world->blocks[x][z-1][y]) {
                    vertices.push_back(x);
                    vertices.push_back(y);
                    vertices.push_back(z+1);

                    vertices.push_back(x+1);
                    vertices.push_back(y);
                    vertices.push_back(z+1);

                    vertices.push_back(x+1);
                    vertices.push_back(y+1);
                    vertices.push_back(z+1);

                    vertices.push_back(x);
                    vertices.push_back(y+1);
                    vertices.push_back(z+1);
                }
                if(back == true || !world->blocks[x][z+1][y]) {
                    vertices.push_back(x);
                    vertices.push_back(y);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y+1);
                    vertices.push_back(z);

                    vertices.push_back(x);
                    vertices.push_back(y+1);
                    vertices.push_back(z);
                }

                if(y == 0 || !world->blocks[x][z][y-1]) {
                    vertices.push_back(x);
                    vertices.push_back(y);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y);
                    vertices.push_back(z+1);

                    vertices.push_back(x);
                    vertices.push_back(y);
                    vertices.push_back(z+1);
                }
                if(y == world->height -1 || !world->blocks[x][z][y+1]) {
                    vertices.push_back(x);
                    vertices.push_back(y+1);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y+1);
                    vertices.push_back(z);

                    vertices.push_back(x+1);
                    vertices.push_back(y+1);
                    vertices.push_back(z+1);

                    vertices.push_back(x);
                    vertices.push_back(y+1);
                    vertices.push_back(z+1);
                }
            }
        }
    }

    glVertexPointer(3, GL_INT, 0, &vertices[0]);
    glDrawArrays(GL_QUADS, 0, vertices.size() /3);
    std::cout << "Vertices: " << vertices.size() << std::endl;
}

以下是我的结果:
第一次使用drawWorld:http://i.imgur.com/yMchEG9.png
drawWorld的第二次召唤:http://i.imgur.com/d9swgao.png

显然,在第一次调用之前,initializeOpenGL只被调用一次。提供的代码之外没有OpenGL语句。

1 个答案:

答案 0 :(得分:0)

<强>更新

显然,正如通过我的回答评论所讨论的,我的做法是错误的。用户derhass在评论中指出了什么是正确的。引自derhass:

  

没有。 GL是状态机。无论国家如何设定都无关紧要   当他们不使用。对于顶点数组状态,重要的是   画电话。您必须确保启用所需的所有阵列   并且在绘制调用时禁用所有不需要的东西。   实际上,最好避免不必要的状态变化。

导致此次更新的错误假设:

void Renderer::initializeOpenGL() {
    glEnable(GL_DEPTH_TEST);
    glEnableClientState(GL_VERTEX_ARRAY);
    glOrtho(0, 1024, 0, 576, 0, 1024);
}

glEnableClientState实际上不是这样的。 您需要在绘制调用之前启用客户端状态,并在之后禁用它。

所以我看到你在抽签结束后错过了glDisableClientState(GL_VERTEX_ARRAY);。 同样从initializeOpenGL()函数中删除glEnableClientState(GL_VERTEX_ARRAY);并将其放在drawWorld函数中(编辑:在你的vertexpointer调用之前)。

这可能会导致您的问题。