如何选择最短旋转方向的角度

时间:2014-08-26 12:59:46

标签: java math

我的游戏中有一个角色必须平滑旋转才能达到理想的角度。将angle视为当前角度,将touchAngle视为所需的角度,该角度始终介于0到360之间。我想在每次游戏更新中将+ 1 / -1添加到当前角度以获得所需的{ {1}}。问题首先是它必须选择方向,它必须在0到360之间。这是我的伪代码:

touchAngle

2 个答案:

答案 0 :(得分:5)

由于您的值在[0 360]区间内始终是标准化的,因此这不应该太难。 您只需要区分两种不同的情况:

angle < touchAngle
angle > touchAngle

在第一种情况下,我们想要逆时针旋转,因此更新必须是angle =+ 1(假设您希望每个更新周期都转1)。 在第二种情况下,我们想要顺时针转动,因此更新应该是angle -= 1

问题是这并不总是最简单的旋转方式。例如,如果:

angle == 359
touchAngle == 1

我们不想一直使用358,357,356 ...而是我们想要逆时针旋转2个单位:360,1。 这可以通过比较角度abs(angle - touchAngle)之间的距离来实现。

如果此值大于180,则意味着我们走错路,所以我们必须绕道而行

if(angle < touchAngle) {
    if(abs(angle - touchAngle)<180)
       angle += 1;
    else angle -= 1;
}

else {
    if(abs(angle - touchAngle)<180)
       angle -= 1;
    else angle += 1;
}

当然所有这一切直到((int)angale != touchAngle)。 我可能在案件中犯了错误,但这是原则。

答案 1 :(得分:0)

通常,您希望为方程带来时间,以便您可以平滑地改变角度time。大多数设置都有一种方法可以获得渲染前一帧的时间,而这样做的典型方法就是说..

int touchAngle;
float angle;
float deltaTime; //Time it took to render last frame, typically in miliseconds
float amountToTurnPerSecond;
public void update()
{
    if((int)angle != touchAngle) angle += (deltaTime * amountToTurnPerSecond);
}

这将使每一秒,你的角度改变amountToTurnPerSecond,但在每一帧上缓慢改变正确的变化量,使其平滑。需要注意的是,大部分时间都不会在touchAngle平均结束,所以检查一下你是否过了而不是设置为touchAngle会是一个好主意。

编辑以跟进评论:

我认为获得正确转弯方向的最简单方法实际上根本不是使用角度。您需要在二维空间中获得从触摸到角色的相对方向。通常你从屏幕空间到世界空间进行触摸,然后在那里进行计算(至少这是我过去所做的)。首先触摸世界空间,然后使用矢量十字产品来确定方向。这看起来有点像......

character position = cx, cy
target position = tx, ty
current facing direction of character = rx, ry

首先我们取角色和目标位置之间的距离:

dx = tx - cx
dy = ty - cy

这不仅告诉我们距离我们有多远,而且基本上告诉我们如果我们在0,0,那么目标在2d空间中的哪个象限?

接下来我们做一个交叉产品:

cross_product = dx * ry - dy * rx

如果这是肯定的,你会走一条路,如果它是负面的,你就去另一条路。这样做的原因是,如果距离是(-5, 2),那么我们知道如果我们正对着北方,那么我们的左边是5,前进是2.所以我们向左转。