使用 Atan2 时移动角度

Shifting angles while using Atan2

我目前正在使用 Atan2 来计算玩家航向角。

然而,经过反复试验后,我发现游戏中的角度与“正常”布局的角度大不相同:

        ReturnedAngle = Math.Atan2(Y2 - Y1, X2 - X1);  /// ArcTan2 the difference in our Y axis is always passed first followed by X

        ReturnedAngle = (180 / Math.PI) * ReturnedAngle; /// Converting our radians to Degrees the convervion ends at 358 not the full 360 degrees.

        ReturnedAngle = Math.Round(ReturnedAngle + 360, MidpointRounding.AwayFromZero) % 360; /// MOD and round our angle.

以上是我用来计算航向角的 C# 代码。我的问题是如何将这个角度从“正常”角度系统转换为游戏中的角度系统。

我想这就是你的情况。你有一个右手坐标系,但你测量的是顺时针方向的角度,这是不一致的。

无论如何,从360(下图红色)画一个小的正角,形成一个正边的直角三角形(下图紫色)。

要测量三角形的角度θ,测量短边Δx和长边Δy并计算。

var θ = Math.Atan2(Δx, Δy);

这适用于两侧的任何正值或负值。例如,如果角度超过 90°,则 Δy 会翻转标志,因为您的目标点将低于原点。但是 Atan2() 的美妙之处在于您无需担心这些情况,因为如果您使其适用于较小的正角,它适用于所有四个象限。

反过来你有

var Δx = R*Math.Sin(Θ);
var Δy = R*Math.Cos(Θ);

其中R是目标和参考点之间的距离。

Math.Atan2(Y2 - Y1, X2 - X1) 从 x 轴逆时针计算角度。 Math.Atan2(X2 - X1, Y2 - Y1) 计算从y轴顺时针方向的角度,这就是你想要的。

'clockwise from north' 约定用于导航和地图绘制。多年来,我发现用具有北、东分量的向量来思考是最容易的。也就是说atan2的调用方式是一样的,就是从p:

得到q的方向
dirn = atan2( q[1]-p[1], q[0]-p[0]);

如果您将 p 和 q 视为 x,y 向量,这将为您提供从 x 轴逆时针旋转的角度。如果您将 p 和 q 视为 n,e 向量,它会为您提供从北向顺时针方向的角度。

这也意味着旋转矩阵的公式是相同的。要旋转角度 a,您可以使用矩阵

R = ( cos(a)  -sin(a) )
    ( sin(a)   cos(a) )

同样,如果您将向量视为 x,y,则应用 R 旋转并从轴逆时针旋转角度 a,而如果您将向量视为 n,则应用 R 旋转通过角度a,从北顺时针。