使用OpenGL渲染3D对象(.obj文件)时闪烁

vir*_*raj 3 c++ windows opengl wavefront glfw

在尝试使用OpenGL(和GLFW库)渲染3D对象时,模型会经历大量闪烁.我正在.obj使用我自己编写的库来读取文件.

下面写的是我的渲染函数:不幸的是,为了理解面和顶点是如何输入的,我将不得不提供所有链接的代码:压缩代码以及可执行文件和示例.obj: Source

我从这里使用.obj文件来测试程序.现在,该程序不支持法线和纹理,这不是问题,因为网站上的大多数模型都没有它们.此外,(现在)它只读取"123.obj"所以该文件不应该被命名为其他任何东西.它只接受一个空间,而不是更多.

 float render()
    {
        glfwSetTime(0.0f);
        int win_width;
        int win_height;
        glfwGetWindowSize(&win_width, &win_height);
        float win_aspect = (float)win_width / (float)win_height;
        glViewport(0, 0, win_width, win_height);

        glMatrixMode(GL_PROJECTION);
        glLoadIdentity();
        gluPerspective(90, win_aspect, 0, 100.0);

        glMatrixMode(GL_MODELVIEW);
        glLoadIdentity();
        gluLookAt(0, 0, 50.0, 0, 0, 0, 0.0, 1.0, 0.0);

        glEnable(GL_DEPTH);
        glEnable(GL_DEPTH_TEST);
        glEnable(GL_COLOR_MATERIAL);
        glEnable(GL_NORMALIZE); 
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

        glRotatef(angle , 0 , 1, 0);
        glColor3f(0.0f, 0.0f, 0.0f);
        int index = 0;
        for(int a = 0; a < faces.size(); a++)
        {
            if(faces[a].vertices.size() == 3)
            {
                glBegin(GL_TRIANGLES);
            }
            else
            {
                glBegin(GL_QUADS);
            }
            for(int b = 0; b < faces[a].vertices.size(); b++)
            {
                index = faces[a].vertices[b];
                glVertex3f(vertices[index].Dimensions[_x], vertices[index].Dimensions[_y], vertices[index].Dimensions[_z]);
            }
            glEnd();
        }
        glfwSwapBuffers();
        return (float)glfwGetTime();
Run Code Online (Sandbox Code Playgroud)

Han*_*esh 7

这是问题所在

gluPerspective(90, win_aspect, 0, 100.0);
Run Code Online (Sandbox Code Playgroud)

您不能将0设置为近距离,将其设置为大于0.1或1.0的值.

gluPerspective(90, win_aspect, 1.0, 100.0);
Run Code Online (Sandbox Code Playgroud)

当nearclip为0时,你的所有深度都被映射到z = 1,你就会得到z格斗.

编辑:如果你有兴趣,这里有一些关于透视深度的理论:

对于距摄像机x的给定距离,您的透视变换输出certian深度值z.在farclip处,此值将是最大值1,而在nearclip处它将为0.但是,在这些值之间,关系不像您预期​​的那样是线性的.曲线类似于下图:

当您将近距离设置为0时,您的曲线会发生剧烈扭曲,因此现在所有距离都会映射到z = 1.

因为这一切,你还应该尽量保持比率远:接近小于10000:1

  • 是的,有一种更简单的方法.在循环之前,添加一个**glPushMatrix();**,然后执行所有的旋转和转换(glTranslate(...),glRotate(...)).完成绘制该模型后,请写入**glPopMatrix();**.这一切都归结为glPushMatrix之前的情况. (2认同)