旋转矩阵是通过首先应用横滚,然后是俯仰,最后是偏航旋转来定义的。如果你先应用俯仰,然后滚动,最后再偏航,你可以让手机处于相同的位置。这就是为什么您期望某个音高,但您得到的值不准确。
为了向自己证明这一点,通过按一定顺序应用角度旋转将手机置于某个随机位置,然后尝试通过不同的旋转顺序到达相同位置(一个好的尝试位置是手机处于垂直位置,例如保持在您的脸前并稍微向一侧倾斜)。
大多数时候你会使用这样的代码
int rotation = ((WindowManager) getApplicationContext().getSystemService(Context.WINDOW_SERVICE)).getDefaultDisplay().getRotation();
if(rotation == 0) // Default display rotation is portrait
SensorManager.remapCoordinateSystem(Rmat, SensorManager.AXIS_MINUS_X, SensorManager.AXIS_Y, R2);
else // Default display rotation is landscape
SensorManager.remapCoordinateSystem(Rmat, SensorManager.AXIS_Y, SensorManager.AXIS_MINUS_X, R2);
使其更直观。这就是你 实际上 会改变顺序的方式,因为你仍然有通过首先应用滚动,然后是俯仰,最后是偏航旋转来定义旋转矩阵,但是这个旋转是针对新定义的XYZ坐标系。
public abstract void onSensorChanged (int sensor, float[] values)
在 API 级别 1 中添加
当传感器值改变时调用。值数组的长度和内容因被监控的传感器而异。有关可能的传感器类型的详细信息,请参阅 SensorManager。
下面使用的坐标系的定义。
X 轴指屏幕的水平轴(竖屏时为小边,横屏时为长边),指向右侧。
Y轴是指屏幕的垂直轴,指向屏幕的顶部(原点在左下角)。
当设备仰卧在桌子上时,Z 轴指向天空。
重要提示:当设备的屏幕方向改变时,轴会被交换。要访问未交换的值,请在 values[] 中使用索引 3、4 和 5。
SENSOR_ORIENTATION、SENSOR_ORIENTATION_RAW:
所有值都是以度为单位的角度。
values[0]:方位角,绕 Z 轴旋转(0
values[1]:pitch,绕X轴旋转(-180
values[2]:滚动,绕 Y 轴旋转 (-90
请注意,偏航、俯仰和横滚的定义不同于航空中使用的传统定义,其中 X 轴沿飞机的长边(机尾到机头)。
以及预期的手机之间的差异。