将XYZ转换为XY(世界坐标到屏幕坐标)

问题描述 投票:2回答:2

有没有办法转换这些数据:

  • 对象位置是3D点(X,Y,Z),
  • 相机位置是3D点(X,Y,Z),
  • 相机偏航,俯仰,滚动(-180:180,-90:90,0)
  • 视场(-45°:45°)
  • 屏幕宽度和高度

进入屏幕上的2D点(X,Y)?

我正在根据这组确切的数据寻找合适的数学计算。

math 3d projection
2个回答
2
投票

这很困难,但有可能为自己做。

有很多库可以帮到你,但如果你自己这样做,它会更令人满意:

这个问题是可能的,我已经编写了自己的3D引擎,使用javascriptHTML5 Canvas中的对象执行此操作。你可以看到我的代码here并解决了我写的here的3D迷宫游戏,试图理解我将在下面谈论的内容......

基本的想法是分步工作。首先,你必须忘记相机角度(yaw, pitch and roll),因为这些后来,只是想象你正在向下看y axis。然后基本思想是使用trig计算俯仰角和偏航到你的物体坐标。通过这个我的意思是想象你正在通过一个信箱看,偏航角将是从中心/中线和你的坐标上下左右坐标左右的角度(正负两个角度)。采用这些角度,您可以将它们映射到x和y 2D坐标系。

角度的计算是:

pitch = atan((coord.x - cam.x) / (coord.y - cam.y))
yaw   = atan((coord.z - cam.z) / (coord.y - cam.y))

coord.x, coord.y and coord.z是对象的坐标,对于凸轮来说是相同的(cam.x, cam.y and cam.z)。这些计算也假设你使用的是不同轴的笛卡尔坐标系:z upy forwardx right

从这里开始,下一步是将3D世界中的这个角度映射到可以在2D图形表示中使用的坐标。

要将这些角度映射到屏幕,您需要将它们放大到距中线的距离。这意味着将它们乘以你的screen width / fov。最后,这些距离现在是正的或负的(因为它是与中线的角度),所以要在画布上实际绘制它,你需要将它添加到屏幕宽度的一半。

所以这意味着你的画布坐标将是:

x = width / 2 + (pitch * (width / fov)
y = height / 2 + (yaw * (height / fov)

其中widthheight是你屏幕的尺寸,fov是相机的fov和yawpitch是物体与相机的相应角度。

您现在已经实现了将3D坐标向下映射到2D的第一个重要步骤。如果你已经设法让这一切都有效,我建议尝试多个点并将它们连接成形状。还可以尝试移动相机位置以查看视角如何变化,因为您很快就会看到它看起来有多逼真。

此外,如果这对你来说很好,你可以继续让相机不仅能够改变它在3D世界中的位置,而且还能改变它在yaw, pitch and roll角度的视角。我现在不会完全讨论这个问题,但基本思想是使用3D世界转换矩阵。你可以读一下他们here,但他们确实变得非常复杂,但如果你走得这么远,我可以给你计算。


1
投票

阅读(旧式)OpenGL规范可能会有所帮助:

https://www.khronos.org/registry/OpenGL/specs/gl/glspec14.pdf

见2.10节

也:

https://www.khronos.org/opengl/wiki/Vertex_Transformation

可以帮助更具体的例子。

此外,对于“正确的数学”,查找4x4矩阵,投影和齐次坐标。

https://en.wikipedia.org/wiki/Homogeneous_coordinates

© www.soinside.com 2019 - 2024. All rights reserved.