1. 三维坐标系
在现实中确定方向需要一个由 X、Y、Z 轴 组成的三维坐标。安卓给我们返回的方向值就是一个长度为 3 的 flaot 数组,包含三个方向的值。
坐标轴参考释义
轴 |
参考 |
X 轴 |
沿着屏幕水平方向从左到右 |
Y 轴 |
从屏幕的左下角开始沿着屏幕的的垂直方向指向屏幕的顶端 |
Z 轴 |
当设备水平放置时,指向天空的方向 |
2. 方向传感器数据值
传感器的回调方法 onSensorChanged 中的参数 SensorEvent event 是一个最多包含三个元素的 Float[] 数组,对应含义见下表:
数据下标 |
数据名称 |
含义 |
values[0] |
方位角 |
手机绕着 Z 轴旋转的角度。 0 表示正北(North),90 表示正东(East),180表示正南(South),270表示正西(West)。 假如 values[0] 的值刚好是这四个值的话,并且手机沿水平放置的话,那么当前手机的正前方就是这四个方向,可以利用这一点来实现指南针 |
values[1] |
倾斜角 |
手机翘起来的程度,当手机绕着 X 轴倾斜时该值会发生变化。取值范围是 [-180, 180] 之间。假如把手机放在桌面上,而桌面是完全水平的话,这个值应该为0,当然很少桌子是绝对水平的。从手机顶部开始抬起,直到手机沿着 X 轴旋转180°(此时屏幕向下水平放在桌面上)。在这个旋转过程中,这个值会在 [0, -180] 之间变化,即手机抬起时,这个值会逐渐变小,直到等于 -180°;而假如从手机底部开始抬起,直到手机沿着 X 轴旋转180°,这个值会在 [0, 180] 之间变化。可以利用这些特性结合 values[2] 来实现一个水平尺 |
values[2] |
滚转角 |
沿着Y轴的滚动角度,取值范围为 [-90, 90],假设将手机屏幕朝上水平放在桌面上,这时如果桌面是平的,这个值应为 0。将手机从左侧逐渐抬起,这个值将逐渐减小,直到垂直于手机放置,此时这个值为 -90,相反,从右侧抬起则是 90;假如在垂直位置时继续向右或者向左滚动,这个值将会继续在 [-90, 90] 之间变化 |
好了,看了这么多文字想必都犯困了吧。那么接下来上代码
3. Demo:监听坐标轴变化
activity_main.xml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37
| <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" android:padding="15dp" tools:context=".MainActivity">
<TextView android:id="@+id/val1" android:layout_width="match_parent" android:layout_height="wrap_content" android:textSize="20sp" android:textStyle="bold" android:text="方位角" />
<TextView android:id="@+id/val2" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="15dp" android:textSize="20sp" android:textStyle="bold" android:text="倾斜角" />
<TextView android:id="@+id/val3" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="15dp" android:textSize="20sp" android:textStyle="bold" android:text="滚转角" /> </LinearLayout>
|
MainActivity.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
| public class MainActivity extends AppCompatActivity implements SensorEventListener {
private TextView val1, val2, val3;
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main);
SensorManager sensorManager = (SensorManager) getSystemService(SENSOR_SERVICE); Sensor sensor = sensorManager.getDefaultSensor(Sensor.TYPE_ORIENTATION); sensorManager.registerListener(this, sensor, SensorManager.SENSOR_DELAY_UI);
val1 = findViewById(R.id.val1); val2 = findViewById(R.id.val2); val3 = findViewById(R.id.val3); }
@SuppressLint("SetTextI18n") @Override public void onSensorChanged(SensorEvent event) { val1.setText("方位角:" + (float) Math.round(event.values[0] * 100) / 100); val2.setText("倾斜角:" + (float) Math.round(event.values[1] * 100) / 100); val3.setText("滚转角:" + (float) Math.round(event.values[2] * 100) / 100); }
@Override public void onAccuracyChanged(Sensor sensor, int accuracy) {
} }
|
TODO: Compass demo