在MSDN上(http://msdn.microsoft.com/en-us/library/windows/desktop/bb281710%28v=vs.85%29.aspx)对于LookAt函数是这个数学:
zaxis = normal(cameraTarget - cameraPosition)
xaxis = normal(cross(cameraUpVector, zaxis))
yaxis = cross(zaxis, xaxis)
xaxis.x yaxis.x zaxis.x 0
xaxis.y yaxis.y zaxis.y 0
xaxis.z yaxis.z zaxis.z 0
-dot(xaxis, cameraPosition) -dot(yaxis, cameraPosition) -dot(zaxis, cameraPosition) 1
据我所知,最后一行是翻译。你能解释一下为什么不能把cameraPosition放在这一行上并且需要点功能吗?
答案 0 :(得分:3)
这是因为View矩阵将对象从世界空间转换为相机空间。将摄像机置于其位置不是转换。这将是逆变换。 考虑一个简单的2D坐标系:
黑色坐标系是世界系统。蓝色的是带有系统的相机。绿色箭头是世界空间中摄像机的平移向量。
View矩阵会将相机从当前位置移回原点。第一步是旋转,以便两个系统的相应轴指向相同的方向:
这是通过矩阵的其他条目(m_11到m_33)来实现的。
现在剩下一个翻译。但翻译矢量被转换。幸运的是,我们知道如何。平移向量等于摄像机位置(注意,DirectX使用转置矩阵。为了显示背后的数学,我将它们转换回来):
/ xAxis.x xAxis.y xAxis.z ...\ / camPos.X \ / camPos.x * xAxis.x + camPos.Y * xAxis.y + camPos.z * xAxis.z \
| yAxis.x yAxis.y yAxis.z ...| | camPos.Y | | camPos.x * yAxis.x + camPos.Y * yAxis.y + camPos.z * yAxis.z |
| zAxis.x zAxis.y zAxis.z ...| * | camPos.Z | = | camPos.x * zAxis.x + camPos.Y * zAxis.y + camPos.z * zAxis.z |
\ 0 0 0 .../ \ 0 / \ 0 /
如果你看一下结果:
camPos.X * xAxis.x + xamPos.Y * xAxis.y + camPos.z * xAxis.z
然后你会发现这等于
dot ( camPos, xAxis)
结论,点积用于补偿旋转。如果没有它,摄像机会稍微移位(例如在右上方太远)。