2013-03-25 112 views
2

嘿家伙我想做一个Camera类,使用glm库中的lookAt。我有4点,第一个是眼睛,那就是相机在太空中的位置,第二个是相机看的地方,第三个是upp,设置相机的方向,第四是侧面,这是眼睛和眼睛的交叉产物。相机旋转使用lookAt

所以最终我得到了3个向量的基础,所有这些向量的起源都在眼点。我得到了相机的坐标系。

在我的相机类中,我希望能够围绕相机的坐标系旋转,而不是世界的坐标系。所以我正在做的是围绕相机坐标系的一个轴旋转。

我构建具有初始值类是这样的:

void Observer::initialize(glm::vec3 eye, glm::vec3 look, glm::vec3 upp, glm::vec3 side) 
{ 
    this->eye = eye;  // (0.0, 0.0, 0.0) 
    this->look = look;  // (0.0, 0.0, -1.0) 
    this->upp = upp;  // (0.0, 1.0, 0.0) 
    this->side = side;  // (1.0, 0.0, 0.0) 
} 

当欲绕x轴例如我调用该函数从GLM这样旋转坐标系:

void Observer::pitch(GLfloat pitch) 
{ 
    glm::mat4 rotate(1.0f); 

    rotate = glm::rotate(rotate, pitch, side - eye); 

    look = glm::vec3(rotate * glm::vec4(look, 1.0f)); 
    upp = glm::vec3(rotate * glm::vec4(upp, 1.0f)); 
} 

到目前为止,我了解到,我所有的点仍然构成了相机的坐标系,并且所有矢量都相互垂直。

但是,然后我使用这些观点,我用lookAt函数获得了相机在世界上的位置。

glm::mat4 view = glm::lookAt(eye, look, upp); 

,如果我开始转动了很多乘以这个矩阵与OpenGL的

模型视图矩阵,几个旋转后的摄像头“反映”旋转,就像我在其他的方式旋转(我不知道如何以更好的方式描述真正发生的事情)。

我真的不明白发生了什么事。在应用旋转后,我应该对矢量进行归一化处理?我有一个万向节锁的问题(我对万向节锁没有太多了解)?

回答

2

当你像向前一样对矢量进行增量旋转时,数值错误会加载。当错误导致向上看和向量指向几乎相同的方向或彼此相反时,相机转换计算是不稳定的,并且可能发生令人毛骨悚然的事情。万向节锁。长度变化导致不同的问题。

对我而言,解决方案是在每次旋转后重新对正向和向后矢量进行正交化。为此,计算它们的交叉积L,然后通过将L与lookAt交叉来调整(实际替换)向上向量。在所有这些都重新规范化后,再看看单位长度。

尽管正交化归一化是一种快速操作,但您并不需要对每个摄像机运动都进行这种操作。

请注意,当您更正像这样的向量时,您实际上正在执行lookAt矩阵计算的一部分,因此请考虑实施您自己的操作来避免不必要的交叉乘积。见例如this prior SO article on this topic