【问题标题】:openGL: cannot correctly draw a sphere in front of cameraopenGL:无法在相机前正确绘制球体
【发布时间】:2016-11-17 20:29:25
【问题描述】:

我正在尝试在相机前画一个小球体,假设距离为 5 个单位(C++,openGL 中的新手,对三角函数不太自信!)。 当我进行平移和倾斜运动时,我希望球体始终位于我的相机中间。

在我的渲染循环中,我通过以下方式计算了球体的坐标:

// 1) settimg my camera
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glRotatef(camera_angle[1], 0, 1, 0);
glRotatef(camera_angle[0], 1, 0, 0);
glRotatef(camera_angle[2], 0, 0, 1);
glTranslatef(camera_pos[0],camera_pos[1],camera_pos[2]);

// 2) retrieving camera pan tilt angles in radians:
double phi  = camera_angle[1] *(M_PI/180.0); //pan
double theta = camera_angle[0] *(M_PI/180.0); //tilt

//3) calculating xyz coordinates of the sphere, if 5 units away from    camera
double dist = -5;
double ax = camera_pos[0] + (-1)*(dist*sin(phi)*cos(theta));
double ay = camera_pos[1] + dist*sin(theta);
double az = camera_pos[2] + dist*cos(theta)*cos(phi);

//4) draw sphere
float ndiv = 2.0;
GLfloat f[]={1.0,1.0,1.0,1};

glPushMatrix();
glTranslated(ax, ay, az);
glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, f);
glShadeModel(GL_FLAT);
glBegin(GL_TRIANGLES);
for (int i=0;i<20;i++)
makeTri(vdata[tindices[i][0]], vdata[tindices[i][1]], vdata[tindices[i][2]], ndiv, 0.2);
glEnd();
glPopMatrix(); 

我在这里找到了三角公式 spherical coordinate system

请注意,我反转了一些值,例如 sin 和 cos,因为我猜正确的顺序取决于参考系统(我猜 openGL 有一些反转的轴)。

现在我有一个奇怪的结果,可以在这个视频中看到:

sphere behaviour

请忽略背景中的彩色球体和相机中间的绿色方块,只看相机前面的白色球体。

如您所见,如果我仅执行平移或仅倾斜(查看显示确切摄像机角度的左下方值),白色球体始终位于摄像机的确切中心,正如预期的那样。然而,当平移和倾斜同时执行时,球体会漂移: 平移和倾斜值越远离 0 度,球体漂移越多。而且,漂移的形状遵循圆形轨迹,这对我来说很可疑。

有人有想法吗?谢谢

【问题讨论】:

    标签: c++ opengl


    【解决方案1】:

    要绘制相对于相机不移动的东西,您只需从一个身份模型-视图矩阵从头开始:

    float ndiv = 2.0;
    GLfloat f[]={1.0,1.0,1.0,1};
    
    glPushMatrix();
    glLoadIdentity();          // <------------- zero out transforms
    glTranslated(0, 0, -5);    // <------------- translate 5 units from the camera
    glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, f);
    glShadeModel(GL_FLAT);
    glBegin(GL_TRIANGLES);
    for (int i=0;i<20;i++)
    makeTri(vdata[tindices[i][0]], vdata[tindices[i][1]], vdata[tindices[i][2]], ndiv, 0.2);
    glEnd();
    glPopMatrix(); 
    

    【讨论】:

    • 非常感谢,它有效!无论如何,您知道为什么我的方法无法正常工作吗?我做错了什么数学吗?
    • @valerio_sperati:对不起,我懒得去检查数学了:) 很可能你只是在某个地方混淆了操作顺序——记住旋转不是可交换的,所以如果 openGL首先围绕 X 旋转,然后围绕 Y 旋转,反之则得到不同的结果。
    • 谢谢,你是对的!我现在意识到,在我旋转相机的代码的第一行中,我以这个(错误的)顺序调用了 glRotatef():1,0,2。现在我将顺序更正为 0,1,2,结果我的代码有效!!!再次非常感谢
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-08-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多