尽管这个问题的背景是关于制作 2d/3d 游戏,但我遇到的问题归结为一些数学问题。虽然它是一个 2.5D 的世界,但让我们假装它只是 2d 这个问题。
// xa: x-accent, the x coordinate of the projection
// mapP: a coordinate on a map which need to be projected
// _Dist_ values are constants for the projection, choosing them correctly will result in i.e. an isometric projection
xa = mapP.x * xDistX + mapP.y * xDistY;
ya = mapP.x * yDistX + mapP.y * yDistY;
xDistX 和 yDistX 确定 x 轴的角度,xDistY 和 yDistY 确定投影上 y 轴的角度(以及网格的大小,但为了简单起见,我们假设这是 1 像素)。
x-axis-angle = atan(yDistX/xDistX)
y-axis-angle = atan(yDistY/yDistY)
像这样的“正常”坐标系
--------------- x
|
|
|
|
|
y
has values like this:
xDistX = 1;
yDistX = 0;
xDistY = 0;
YDistY = 1;
因此,x 方向上的每一步都将导致投影到右端 1 个像素,向下 0 个像素。投影的 y 方向上的每一步都将导致向右 0 步和向下 1 个像素。选择正确的 xDistX、yDistX、xDistY、yDistY 时,您可以投影任何三度或二度系统(这就是我选择这个的原因)。
到目前为止一切顺利,当它被绘制时,一切都很好。如果“我的系统”和思维定势清晰,让我们继续展望。我想为这个网格添加一些视角,所以我添加了一些额外的,如下所示:
camera = new MapPoint(60, 60);
dx = mapP.x - camera.x; // delta x
dy = mapP.y - camera.y; // delta y
dist = Math.sqrt(dx * dx + dy * dy); // dist is the distance to the camera, Pythagoras etc.. all objects must be in front of the camera
fac = 1 - dist / 100; // this formula determines the amount of perspective
xa = fac * (mapP.x * xDistX + mapP.y * xDistY) ;
ya = fac * (mapP.x * yDistX + mapP.y * yDistY );
现在真正困难的部分......如果你在投影上有一个(xa,ya)点并想要计算原始点(x,y)怎么办。对于第一种情况(没有透视),我确实找到了反函数,但是对于具有透视的公式,如何做到这一点。可能数学技能还不足以解决这个问题。
(我依稀记得很久以前mathematica可以为某些特殊情况创建反函数......它可以解决这个问题吗?有人可以试试吗?)