深度的Android传感器:近距离和陀螺仪 (有源码)

为什么总是期望用户点击触摸屏上的按钮?通过使用中端Android手机上可用的一些硬件传感器,您可以创建提供更加吸引人的用户体验的应用程序。

传感器框架是Android SDK的一部分,它允许您以简单和一致的方式从大多数传感器(无论是硬件还是软件)读取原始数据。在本教程中,我将向您展示如何使用框架从两个非常常见的传感器读取数据:接近和陀螺仪。我还将向您介绍旋转矢量传感器,一种复合传感器,在大多数情况下,它可以作为陀螺仪更简单,更准确的替代方案。

您可以阅读以下教程,了解Android的硬件传感器:

  • ANDROID SDK
    Android从头开始:硬件传感器
    保罗Trebilcox-Ruiz

要跟随,您将需要以下内容:

  • 具有接近传感器和陀螺仪的Android设备
  • 最新版本的Android Studio

如果您的应用程序在不需要所有硬件传感器的设备上无法使用,则不能在此类设备上安装。您可以通过在<uses-feature>Android Studio项目的清单文件中添加一个或多个标签来让Google Play和其他应用程式市场了解应用程式的硬体要求

我们将在本教程中创建的应用程序将不适用于缺少接近传感器和陀螺仪的设备。因此,将以下行添加到清单文件中:

但是请注意,<uses-feature>如果用户使用其APK文件手动安装应用程序,则该标签无法帮助,则在使用传感器之前,仍必须以编程方式检查传感器是否可用。

为了避免意外的触摸事件,您的手机的触摸屏在通话期间会变黑,当它非常接近您的耳朵时。曾经想过你的手机如何确定它是否接近你的耳朵?那么它使用接近传感器,这是一个硬件传感器,可以判断物体是否接近它。一些接近传感器也可以告诉物体有多远,尽管它们的最大范围通常只有约5厘米。

现在让我们创建一个活动,其背景颜色在每次将您的手悬停在设备的接近传感器上时变为红色。

要访问任何硬件传感器,您需要一个SensorManager对象。要创建它,请使用getSystemService()您的Activity方法并将SENSOR_SERVICE常量传递给它。

您现在可以Sensor通过调用该getDefaultSensor()方法并将TYPE_PROXIMITY常量传递给它来为接近传感器创建一个对象

在继续之前,始终确保Sensor对象不是null如果是,则表示接近传感器不可用。

为了能够读取传感器生成的原始数据,您必须SensorEventListener通过调用对象registerListener()方法来与它相关联SensorManager在执行此操作时,您还必须指定从传感器读取数据的频率。

以下代码注册一个监听器,您可以每两秒读取一次接近传感器的数据:

我建议您始终在onResume()活动方法内注册该监听器,并在方法内取消注册onPause()以下是注销侦听器的方法:

SensorEvent方法中可用对象onSensorChanged()具有包含values相关传感器生成的所有原始数据数组。在接近传感器的情况下,阵列包含指定传感器和附近物体之间距离(​​厘米)的单个值。

如果该值等于传感器的最大范围,则可以安全地假定附近没有。相反,如果它小于最大范围,则意味着附近有些东西。您可以使用getMaximumRange()相关Sensor对象方法确定任何硬件传感器的最大范围

要根据接近传感器的数据实际更改活动的背景颜色,可以使用setBackgroundColor()顶级窗口的装饰视图的方法。

因此,onSensorChanged()在上一步中创建方法中添加以下代码

如果您现在运行该应用程序并将手悬停在手机的顶部边缘,则应该会看到屏幕变红。

当附近检测到物体时,背景颜色会发生变化

陀螺仪允许您在任何给定时刻确定Android设备的角速度。简单来说,它告诉您设备绕X,Y和Z轴旋转的速度有多快。最近,即使是预算手机正在制造,陀螺仪内置,增强现实和虚拟现实应用程序变得如此受欢迎。

通过使用陀螺仪,您可以开发可以响应设备方向的微小更改的应用程序。要了解如何,现在让我们创建一个活动,其背景颜色每次沿Z轴沿逆时针方向旋转手机时,蓝色变为蓝色,否则为黄色。

要创建Sensor陀螺仪对象,所有您需要做的是将TYPE_GYROSCOPE常量传递对象getDefaultSensor()方法SensorManager

创建陀螺仪传感器的监听器与为接近传感器创建侦听器没有什么不同。但是,注册时,您必须确保其采样频率非常高。因此,我建议您使用SENSOR_DELAY_NORMAL常量,而不是以微秒为单位指定轮询间隔

陀螺传感器的原始数据由三个float组成  ,指定器件沿X,Y和Z轴的角速度。每个值的单位是每秒弧度。在沿着任何轴的逆时针旋转的情况下,与该轴相关联的值将为正。在顺时针旋转的情况下,它将为负。

因为我们目前只对沿着Z轴的旋转感兴趣,所以我们将只使用对象values数组中的第三个元素SensorEvent如果超过0.5f,我们可以在很大程度上确保旋转是逆时针旋转的,并将背景颜色设置为蓝色。类似地,如果它小于-0.5f,我们可以将背景颜色设置为黄色。

如果您现在运行该应用程序,请将手机置于纵向模式,然后将其向左倾斜,您应该看到活动变为蓝色。如果倾斜方向相反,则应变黄。

基于角速度的背景颜色变化

但是,如果您将手机转到太多,屏幕方向将变为横向,您的活动将重新启动。为了避免这种情况,我建议您在清单文件中设置screenOrientation活动portrait

大多数开发者今天都喜欢软件,复合传感器超过硬件传感器 软件传感器结合了来自多个硬件传感器的低级原始数据,生成不仅易于使用的新数据,而且更准确。接近传感器没有替代软件。然而,陀螺仪具有两个:游戏旋转矢量传感器和旋转矢量传感器。在本教程中,我们将仅关注后者。

在上一步的例子中,我们每次沿着Z轴的角速度顺时针或逆时针方向大于0.5rad / s时,改变了活动的背景颜色。然而,使用角速度并不直观。此外,我们不知道设备在旋转之前或之后的实际角度。

通过使用旋转矢量传感器,让我们现在创建一个活动,其背景颜色只有在旋转了特定角度时才会改变。例如,我们可以将其沿着Z轴的旋转度大于45°时变为黄色,当其旋转在-10°和10°之间时为白色,当旋转小于-45°时,它们为蓝色。

要获取旋转矢量传感器,必须将TYPE_ROTATION_VECTOR常量传递对象getDefaultSensor()方法SensorManager

使用软件传感器与使用硬件传感器没有什么不同。因此,您必须将侦听器与旋转矢量传感器相关联才能读取其数据。您可以再次使用SENSOR_DELAY_NORMAL常量进行轮询间隔。


步骤2:使用数据

旋转矢量传感器组合由陀螺仪,加速度计和磁力计产生的原始数据,以产生四元数因此,valuesSensorEvent对象数组有以下五个元素:

  • 四元数的X,Y,Z和W分量
  • 标题精度

您可以通过使用该类getRotationMatrixFromVector()方法将四元数转换为旋转矩阵,即4x4矩阵SensorManager

如果您正在开发OpenGL应用程序,则可以直接使用旋转矩阵来转换3D场景中的对象。然而,现在,我们将旋转矩阵转换成方向阵列,指定器件沿着Z,X和Y轴的旋转。为此,我们可以使用该类getOrientation()方法SensorManager

在调用该getOrientation()方法之前,必须重新映射旋转矩阵的坐标系。更准确地说,您必须旋转旋转矩阵,使新坐标系的Z轴与原始坐标系的Y轴重合。

默认情况下,orientations数组包含弧度而不是度数的角度。如果您习惯于弧度,请直接使用它。否则,使用以下代码将其所有角度转换为度数:

您现在可以根据orientations数组的第三个元素更改活动的背景颜色

如果您现在运行该应用程序,请将手机置于肖像模式,并顺时针或逆时针倾斜45度以上,您应该会看到背景颜色的变化。

基于角度的背景颜色变化

在本教程中,您学习了如何使用Android的传感器框架来创建可以响应接近传感器和陀螺仪生成的数据的应用程序。您还学习了如何使用旋转矢量传感器,这是陀螺仪更受欢迎的替代品。随意使用传感器的创意方式。请注意,使用低效传感器的应用程序可能会很快耗尽设备的电池。

要了解有关硬件传感器及其生成的数据的更多信息,可参考官方传感器API指南并在Envato Tuts +上查看我们的其他硬件和传感器内容!


原文地址   传送门

无意中看到这篇文章 感觉很有意思 就学习了下   三种传感器我都集成在了一起 测试的时候最好注释掉其他两个 要不会混乱 整个屏幕 五颜六色跳动个不停 源码我注释掉了其他两个 只留下了距离传感器   其他两个自行放开

源码




  • 6
    点赞
  • 42
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
Android 陀螺仪和加速度计传感器可以结合使用来测量设备的旋转角度。加速度计可以测量设备在 X、Y、Z 轴上的加速度值,通过这些值可以计算设备的倾斜角度。陀螺仪传感器可以测量设备在 X、Y、Z 轴上的角速度值,通过这些值可以计算设备的旋转角度。 具体实现方法如下: 1. 注册陀螺仪和加速度计传感器的 SensorEventListener。 2. 在 onSensorChanged() 方法中,分别获取陀螺仪和加速度计传感器的数值。 3. 计算设备的倾斜角度。可以使用以下公式: float[] accelerationValues = event.values; float x = accelerationValues[0]; float y = accelerationValues[1]; float z = accelerationValues[2]; float pitch = (float) Math.atan2(x, Math.sqrt(y*y + z*z)); float roll = (float) Math.atan2(y, Math.sqrt(x*x + z*z)); 4. 计算设备的旋转角度。可以使用以下公式: float[] angularVelocityValues = event.values; float deltaTime = (event.timestamp - mLastTimestamp) * NS2S; mLastTimestamp = event.timestamp; if (mLastAngularVelocityValues != null) { float angularVelocityX = angularVelocityValues[0]; float angularVelocityY = angularVelocityValues[1]; float angularVelocityZ = angularVelocityValues[2]; float deltaRotationX = angularVelocityX * deltaTime; float deltaRotationY = angularVelocityY * deltaTime; float deltaRotationZ = angularVelocityZ * deltaTime; float[] deltaRotationMatrix = new float[9]; SensorManager.getRotationMatrixFromVector(deltaRotationMatrix, new float[] {deltaRotationX, deltaRotationY, deltaRotationZ}); float[] rotationMatrix = new float[9]; SensorManager.getRotationMatrixFromVector(rotationMatrix, angularVelocityValues); float[] resultMatrix = new float[9]; Matrix.multiplyMM(resultMatrix, 0, deltaRotationMatrix, 0, rotationMatrix, 0); float[] orientationValues = new float[3]; SensorManager.getOrientation(resultMatrix, orientationValues); float azimuth = orientationValues[0]; float pitch = orientationValues[1]; float roll = orientationValues[2]; } 需要注意的是,陀螺仪传感器的数值是角速度,需要根据时间积分才能得到旋转角度。同时,陀螺仪传感器的数值可能会受到漂移等干扰,需要进行校准。加速度计传感器的数值可能会受到震动等干扰,需要进行滤波处理。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值