使移动设备开发与其他平台不同的原因之一是,手机或平板电脑装满了传感器和其他硬件,开发人员可以利用这些传感器和其他硬件进行数据输入。 在本教程中,将向您介绍Android传感器框架。 您将学习如何检测设备上可用的传感器以及如何从这些传感器读取数据。
设备传感器
基本传感器要注意三大类:运动,环境和设备位置。 运动传感器检测围绕设备三个轴(X,Y和Z)的力的变化,如下所示:
![移动设备的X Y和Z轴](https://cms-assets.tutsplus.com/uploads/users/798/posts/26985/image/axis_device.png)
运动传感器包括陀螺仪,加速度计和旋转矢量传感器。
环境传感器收集有关手机所处环境的信息。其中包括湿度和环境温度传感器,光线检测和气压计。
基本传感器的最后一类,即设备位置,完全符合您的期望:它可以检测设备的位置。 此类别包括方向传感器和磁力计。
任何不属于基本类别之一的传感器均被视为复合传感器。 这些传感器实际上不是传统意义上的传感器,而是从设备上的多个其他物理传感器收集数据并进行汇总。 示例包括步数计数器,重力传感器和旋转矢量传感器。
读取传感器数据
现在,您已经对移动设备中的传感器类型有所了解,现在该开始从实际硬件中读取数据了。 让我们从发现设备上可用的传感器开始。
在设备上发现传感器
为了访问设备上的传感器,您将需要使用SensorManager
类,您可以从Activity
中将其作为系统服务检索。
mSensorManager = (SensorManager) getSystemService( Context.SENSOR_SERVICE );
拥有SensorManager
,您可以根据类型检索默认的Sensor
,或根据类型参数检索Sensor
对象的List
。 对于此示例,我们将检索所有Sensor
对象的List
,如下所示:
List<Sensor> sensorList = mSensorManager.getSensorList( Sensor.TYPE_ALL );
您会注意到我们在这里使用了TYPE_ALL
。 如果只需要特定的传感器子集,则可以传入任何受支持的类型属性,例如以下(不包括在内)列表中的项目。
TYPE_AMBIENT_TEMPERATURE
TYPE_DEVICE_PRIVATE_BASE
TYPE_GAME_ROTATION_VECTOR
TYPE_GEOMAGNETIC_ROTATION_VECTOR
TYPE_GRAVITY
TYPE_GYROSCOPE
TYPE_GYROSCOPE_UNCALIBRATED
TYPE_HEART_BEAT
TYPE_HEART_RATE
TYPE_LIGHT
TYPE_LINEAR_ACCELERATION
TYPE_MAGNETIC_FIELD
TYPE_MAGNETIC_FIELD_UNCALIBRATED
TYPE_MOTION_DETECT
有了要使用的Sensor
,就可以开始从中检索数据了。
传感器事件侦听器
每个Sensor
对象都包含有关该传感器的物理硬件的信息,例如电源,输入延迟,名称,类型和供应商。 但是,如果要从该传感器检索信息,则需要注册一个SensorEventListener
,它将以设置的时间间隔调用新的信息读数。
mSensorManager.registerListener( this, mSensor, SensorManager.SENSOR_DELAY_UI );
有四种指定的阅读速度:最快,游戏,普通和UI。 有些可以使您更频繁地阅读信息,但会消耗设备更多的电能。 轮询传感器的频率越少,它将使用的功率就越少。
一旦SensorEventListener
注册,听者的onSensorChanged
方法将被一个新的称为SensorEvent
每个传感器进行轮询的时间。 SensorEvent
包装了为其提供数据的Sensor
对象,以及有关时间,传感器的精度和实际输入数据的信息。
输入数据存储在称为values
的float
数组中。 values
的长度可能会因传感器而异。 例如,加速度计将具有三个值(X,Y和Z输入),而气压计将仅具有一个值。 当您使用传感器数据时,了解哪些数据可用以及如何将它们存储在values
数组中对于理解如何构建应用程序非常重要,同时还避免了诸如ArrayIndexOutOfBoundsException
类的问题而导致崩溃。
@Override
public void onSensorChanged(SensorEvent sensorEvent) {
Log.e("Tuts+", "Accuracy: " + sensorEvent.accuracy );
Log.e("Tuts+", "Timestamp: " + sensorEvent.timestamp);
Log.e("Tuts+", "Accelerometer X: " + sensorEvent.values[0]);
Log.e("Tuts+", "Accelerometer Y: " + sensorEvent.values[1]);
Log.e("Tuts+", "Accelerometer Z: " + sensorEvent.values[2]);
}
上面的代码段与设备加速计一起运行时,将提供以下输出:
E/Tuts+: Accuracy: 3
E/Tuts+: Timestamp: 572565573007319
E/Tuts+: Accelerometer X: 0.80444336
E/Tuts+: Accelerometer Y: 1.7597351
E/Tuts+: Accelerometer Z: 9.425964
并且由于侦听器会随着时间的推移提供输入,因此可以将其馈送到图形中以显示类似于以下内容的信息(尽管图形库本身不在本教程的讨论范围之内)。
事件触发
虽然SensorEventListener
会随着时间的推移继续提供信息,但是TriggerEventListener
会侦听事件,然后立即将其自身禁用。 这种侦听器用于诸如重大运动之类的事情。 您可以像这样将TriggerEventListener
添加到SensorManager
。
mSensorManager.requestTriggerSensor(new TriggerEventListener() {
@Override
public void onTrigger(TriggerEvent triggerEvent) {
Log.e("Tuts+", "onTrigger");
for(int i = 0; i < triggerEvent.values.length; i++ ) {
Log.e("Tuts+", "item " + i + ": " + triggerEvent.values[i]);
}
}
}, mSensor);
如果传递给requestTriggerSensor
的Sensor
是重要的运动传感器,则当设备移动时,上面的内容将具有如下输出:
E/Tuts+: onTrigger
E/Tuts+: item 0: 1.0
使用SensorEventListener
和TriggerEventListener
要注意的一件事是,在使用SensorEventListener
它们后(例如在Fragment
或Activity
类中的onDestroy
,应从SensorManager
取消注册它们,以防止应用程序泄漏。
结论
在本教程中,已向您介绍了Android的传感器框架。 您已经了解了如何在设备上查找传感器并从中收集信息。 使用此工具,您可以创建了解其环境,特殊输入和用户操作的复杂应用。 学会很好地使用传感器数据将打开许多有趣的功能,可以用于您的应用程序。
翻译自: https://code.tutsplus.com/tutorials/android-from-scratch-hardware-sensors--cms-26985