使用 atan2 将 - 1 到 1 的范围转换为度数
Using atan2 to turn a range from - 1 to 1 into degrees
我正在尝试使用 atan2 将 - 1 到 1 的范围转换为弧度,然后从弧度转换为度数。
但是 atan2(0,1) 在应该等于 90.0 时等于 0,我这里做错了什么?
float radians = atan2(0, 1);
float degrees = (radians * 180 / PI);
if(radians < 0)
{
degrees += 360;
}
编辑:好的,这次我以正确的方式插入了值。
float xaxisval = controller->left_stick_x_axis();
float yaxisval = controller->left_stick_y_axis();
// plug values into atan2
float radians = atan2(yaxisval, xaxisval);
float degrees = (radians * 180 / PI);
if (radians < 0)
{
degrees += 360;
}
对于上下文,xaxisval 和 yaxisval 正在从模拟棒中获取一个值,右侧的最大值为 1,左侧的最小值为 -1。所以当我向右按下模拟摇杆时,yaxisval 等于 0,xaxisval 等于 1。
这应该 return 90 度,就像您将模拟摇杆想象成一个完整的 360 度圆圈一样。向上方向是360/0 右边是90 向下是180 左边是270 等等
我将这些值插入调试器,这就是它 returned 的内容。
xaxisval: 1.00000
yaxisval: 0.00000
degrees: 0.00000
但是我希望这个方向出现 90 度,它似乎向上跳了 90 度,我测试了向下位置,它等于 90。有什么建议吗?
调试输出:
操纵杆向上位置
xaxisval: 0.00000
yaxisval: -1.00000
degrees: 270.00000
操纵杆右侧位置
xaxisval: 1.00000
yaxisval: 0.00000
degrees: 0.00000
操纵杆向下位置
xaxisval: 0.00000
yaxisval: 1.00000
degrees: 90.00000
操纵杆左侧位置
xaxisval: -1.00000
yaxisval: 0.00000
degrees: 180.00000
操纵杆东北位置
xaxisval: 0.929412
yaxisval: 0.592157
degrees: 327.497528
您以错误的顺序传递参数。 std::atan2
期望参数的顺序为 y,x
,而不是 x,y
。
是的,这非常愚蠢,但这首先与正切函数的定义方式有关(定义为 y 分量与 x 分量的比率,而不是相反) ,就像数学中的许多符号错误一样,惯性在几千年前就已经形成,你不能不成为一个怪人就反对它。
所以这样写你的代码:
float radians = atan2(1, 0);
或者,如果您希望一切都尽可能明确:
float x = 0, y = 1;
float radians = atan2(y, x); //Yes, that's the correct order, don't @ me
你会得到你期望的结果。
你的第二个问题是 atan2
对应的值与你想要的方向不匹配。你想要的是一个圆,上面是0°,右边是90°,下面是180°,左边是270°。将值打入 atan2
将生成右侧为 0°、向上为 90°、左侧为 180°、向下为 270° 的值。
此外,与我自己的硬件相比,我的 y 轴与您的相比翻转了。我的是 y+↑,而你的设置似乎是 y-↑
所以如果你想将正常的 atan2
旋转变换成你想要的旋转,你需要像这样变换它:
float radians = atan2(yaxisval, xaxisval);
float degrees = (radians * 180 / PI);
degrees = 90 - degrees;
if(degrees < 0)
degrees += 360;
然后,你所要做的就是根据你 期望 将操纵杆推到 return 正向还是负向来变换 y 轴价值。这取决于您的程序领域。
我正在尝试使用 atan2 将 - 1 到 1 的范围转换为弧度,然后从弧度转换为度数。
但是 atan2(0,1) 在应该等于 90.0 时等于 0,我这里做错了什么?
float radians = atan2(0, 1);
float degrees = (radians * 180 / PI);
if(radians < 0)
{
degrees += 360;
}
编辑:好的,这次我以正确的方式插入了值。
float xaxisval = controller->left_stick_x_axis();
float yaxisval = controller->left_stick_y_axis();
// plug values into atan2
float radians = atan2(yaxisval, xaxisval);
float degrees = (radians * 180 / PI);
if (radians < 0)
{
degrees += 360;
}
对于上下文,xaxisval 和 yaxisval 正在从模拟棒中获取一个值,右侧的最大值为 1,左侧的最小值为 -1。所以当我向右按下模拟摇杆时,yaxisval 等于 0,xaxisval 等于 1。
这应该 return 90 度,就像您将模拟摇杆想象成一个完整的 360 度圆圈一样。向上方向是360/0 右边是90 向下是180 左边是270 等等
我将这些值插入调试器,这就是它 returned 的内容。
xaxisval: 1.00000
yaxisval: 0.00000
degrees: 0.00000
但是我希望这个方向出现 90 度,它似乎向上跳了 90 度,我测试了向下位置,它等于 90。有什么建议吗?
调试输出: 操纵杆向上位置
xaxisval: 0.00000
yaxisval: -1.00000
degrees: 270.00000
操纵杆右侧位置
xaxisval: 1.00000
yaxisval: 0.00000
degrees: 0.00000
操纵杆向下位置
xaxisval: 0.00000
yaxisval: 1.00000
degrees: 90.00000
操纵杆左侧位置
xaxisval: -1.00000
yaxisval: 0.00000
degrees: 180.00000
操纵杆东北位置
xaxisval: 0.929412
yaxisval: 0.592157
degrees: 327.497528
您以错误的顺序传递参数。 std::atan2
期望参数的顺序为 y,x
,而不是 x,y
。
是的,这非常愚蠢,但这首先与正切函数的定义方式有关(定义为 y 分量与 x 分量的比率,而不是相反) ,就像数学中的许多符号错误一样,惯性在几千年前就已经形成,你不能不成为一个怪人就反对它。
所以这样写你的代码:
float radians = atan2(1, 0);
或者,如果您希望一切都尽可能明确:
float x = 0, y = 1;
float radians = atan2(y, x); //Yes, that's the correct order, don't @ me
你会得到你期望的结果。
你的第二个问题是 atan2
对应的值与你想要的方向不匹配。你想要的是一个圆,上面是0°,右边是90°,下面是180°,左边是270°。将值打入 atan2
将生成右侧为 0°、向上为 90°、左侧为 180°、向下为 270° 的值。
此外,与我自己的硬件相比,我的 y 轴与您的相比翻转了。我的是 y+↑,而你的设置似乎是 y-↑
所以如果你想将正常的 atan2
旋转变换成你想要的旋转,你需要像这样变换它:
float radians = atan2(yaxisval, xaxisval);
float degrees = (radians * 180 / PI);
degrees = 90 - degrees;
if(degrees < 0)
degrees += 360;
然后,你所要做的就是根据你 期望 将操纵杆推到 return 正向还是负向来变换 y 轴价值。这取决于您的程序领域。