OpenGL投影缩放

时间:2013-02-27 08:58:41

标签: c++ opengl

我有一个代表简单3D场景的学习项目。 我正在修改模型视图矩阵,使用gluLookAt()将视点移动到某个非原点,然后我将线球放在原点中。最后我使用glOrtho()修改投影矩阵以接收带有一些参数的正交投影。但是当调整窗口大小时,球体会变形。我想我应该修改reshape()glOrtho()函数,但是如何修改?

void display(void){
    glClear(GL_COLOR_BUFFER_BIT);
    glColor3b(197, 96, 63);
    glLoadIdentity();    
    gluLookAt(2, 0.5 ,2, 0, 0, 0, 0, 1, 0);
    glutWireSphere(0.2, 20, 10);  
    glFlush();
}

void reshape(int w, int h){
    glViewport(0, 0, (GLsizei) w, (GLsizei) h);
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    glOrtho(-1, 1, -1, 1, 0.8 , 100);
    glMatrixMode(GL_MODELVIEW);
}

3 个答案:

答案 0 :(得分:3)

正如我在评论中所说,您需要设置正交投影以适合您的窗口。假设您的OpenGL窗口在调整大小之前以方形开始,(-1, 1, -1, 1, ...)假定为方形坐标系。如果您更改它以更好地反映窗口的宽高比,您应该看得更好。请尝试以下方法:

glOrtho ((float)w/(float)h, (float)-w/(float)h, -1, 1, 0.8, 100);

这应该保持坐标系统的设置,但要考虑宽高比(宽度)。

答案 1 :(得分:2)

首先,与您的问题完全无关:立即移动reshape中显示的所有内容。是的,我知道许多教程都是按照你的方式进行的,但是请相信我,这样做会让事情变得更加清晰。


现在关于你的问题:Ortho在视图空间中设置音量,即被映射到视口坐标。 glOrtho的(下,左)角被映射到glViewport的(x,y),(top,right)被映射到glViewport的(x,y)+(宽度,高度)。

因此,您必须将glOrtho参数调整为视口的宽高比。很容易:

void display(void)
{
    int const win_width  = glutGet(GLUT_WINDOW_WIDTH);
    int const win_height = glutGet(GLUT_WINDOW_HEIGHT);
    float const win_aspect = (float)win_width / (float)win_height;

    glClear(GL_COLOR_BUFFER_BIT);
    glViewport(0, 0, win_width, win_height);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    glOrtho(-win_aspect, win_aspect, -1, 1, 0.8 , 100);

    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();    
    gluLookAt(2, 0.5 ,2, 0, 0, 0, 0, 1, 0);

    glColor3b(197, 96, 63);
    glutWireSphere(0.2, 20, 10);  
    glFlush();
}

答案 2 :(得分:0)

目前,您将窗口投影到具有glOrtho(-1, 1, -1, 1, 0.8 , 100);的二次输出,因为宽度和高度相等。您应该将前四个参数更改为窗口的当前宽高比,以防止失真。像

glOrtho(-w/2f, w/2f, -h/2f, h/2f, 0.8 , 100);

(在我的例子中,你必须让你的球体更大,因为投影平面会比你的更大。)