关于不正确的轴的旋转(第一人称相机实现)

时间:2014-08-12 12:29:32

标签: c++ opengl camera rotation trigonometry

我正在使用键盘上的箭头键实现第一人称相机移动场景。当我只绕一个轴(X或Y)旋转时似乎工作正常,但是如果我绕两个轴旋转它也会让我绕第三个Z轴旋转。我很确定问题是我的相机不是围绕全局轴旋转而是旋转本地轴,当我只想要偏航和俯仰时会导致“滚动”。在我的代码中,我从X和Y旋转中推导出一个前向向量,存储在两个变量中。最相关的代码段如下:

glm::mat4 CameraManager::rotateWorld(float angle, glm::vec3 rot){
static float yRot = 0.0f;
static float xRot = 0.0f;

glm::vec3 degrees = rot * angle;
glm::vec3 radians = glm::vec3(degrees.x * (M_PI/180.0f),
                                 degrees.y * (M_PI/180.0f),
                                 degrees.z * (M_PI/180.0f));

yRot += radians.y;
xRot += radians.x;

forwardVector = glm::vec3(sinf(yRot) * cosf(xRot),
                          -sinf(xRot),
                          -cosf(yRot) * cosf(xRot));

return glm::rotate(glm::mat4(1.0f), angle, rot);
}

rotateWorld函数补充了moveForward函数:

glm::mat4 CameraManager::moveForward(float dist){
glm::vec3 translation = forwardVector/glm::vec3(sqrt(forwardVector.x * forwardVector.x +
                                                     forwardVector.y * forwardVector.y +
                                                     forwardVector.z * forwardVector.z)) * dist;
return glm::translate(glm::mat4(1.0f), -translation);

}

其中yRot相当于偏航,而xRot相当于俯仰。 旋转和平移矩阵简单地在程序的主要部分中相乘。

然后我继续用这个向量乘以距离d来更新位置。

xRot和yRot是static double,当用户按下箭头键时,它会递增/递减。

enter image description here

程序启动时,这是视图。飞机和猴子头朝向“正确的方向”。增加/减少俯仰和偏航单独按预期工作。但是,当我说,增加音高然后偏航时,场景会向侧面翻转! (如下图所示。)任何想法如何解决这个问题?

enter image description here

1 个答案:

答案 0 :(得分:0)

如果我理解正确,您遇到的问题是您的“向上”矢量并不总是相对于观察平面的预期Y轴垂直向上指向。

确定正确的“向上”向量通常需要针对视口的X和Y轴上的向量进行叉积运算的组合。

您可以为gluLookAt函数找到一些有用的提示in the documentation,其目的是计算具有所需方向(即没有滚动)的视图矩阵,给定眼睛位置和预期中心的坐标该领域。