Android学习笔记之——手机中几种自带传感器的应用

本文介绍了Android中常见的传感器,如光、接近、温度、压力、陀螺仪、加速度、重力、磁场和方位传感器的使用步骤及示例。通过获取SensorManager,注册监听器,读取传感器数据,展示了如何在Android应用中实现传感器功能。
摘要由CSDN通过智能技术生成

本博文学习一下Android中几种传感器的应用

 

目录

Android传感器

使用传感器步骤

Demo Test

查看手机支持哪些传感器

界面布局

传感器list

光传感器

近距离传感器、温度传感器、气压传感器

陀螺仪

加速传感器

重力测试

磁场传感器

方位传感器(Orientation Sensors)

参考资料


 

Android传感器

传感器就是通过对外界信号的感受和探测,并按照一定的规律把这些信号转成我们需要的信息的一些微型物理设备,比如我们的手机中就存在很多传感器。android中提供了相应的接口,让我们可以访问这些传感器,并使用他们的数据。与传感器交互需要使用Sensor对象。Sennor就是传感器的一个类,包括传感器的类型、精度等等他都可以来描述。

Android提供sensor framework也帮助开发者利用设备的传感器进行开发。传感器是只读的(NFC例外),因此只要设定监听器接受传感器信息即可。手机上有各种各样的传感器

  • 光传感器(Light sensor)
  • 接近感应器(Proximity sensor)
  • 温度传感器(Temperature sensor)
  • 压力传感器(Pressure sensor)
  • 陀螺仪传感器(Gyroscope sensor)
  • 加速感应器(Accelerometer)
  • 磁场感应器(Magnetic field sensor)
  • 方向感应器(Orientation sensor)
  • 重力感应器(Gravity sensor,Android 2.3引入)
  • 线性加速感应器(Linear acceleration sensor ,Android 2.3引入)
  • 旋转矢量传感器(Rotation vector sensor,Android 2.3)
  • 相对湿度传感器(Relative humidity sensor,Android 4.0)
  • 近场通信(NFC)传感器(Android 2.3引入),NFC和其他不一样,具有读写功能。

使用传感器步骤

一般来说,要使用传感器要分三个步骤:

1、获取传感器管理者对象。获取一个传感器管理者SensorManager方便对Sensor的管理

// 获取传感器管理者对象
SensorManager mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);

2. 获取指定的传感器对象。SensorManager有方法是用来获取指定类型传感器的,如getDefaultSensor(int type),其中type可以使用Sensor类中的常量设置,Sensor中提供了很多传感器类型的常量

Sensor sensor = mSensorManager.getDefaultSensor(int type);

其中type就是传感器的类型了

  • 加速度传感器Sensor.TYPE_ACCELEROMETER   
  • 方向传感器Sensor.TYPE_ORIENTATION
  • 磁场传感器Sensor.TYPE_MAGNETIC_FIELD
  • 温度传感器Sensor.TYPE_AMBIENT_TEMPERATURE
  • 光传感器Sensor.TYPE_LIGHT
  • 压力传感器Sensor.TYPE_PRESSURE

3.给传感器添加监听。通过sensorManager来为传感器注册一个监听器,然后程序就可以通过这个监听来获取传感器获取的数据了(一般来说,在onResume()方法中注册)

public boolean registerListener(SensorEventListener listener, Sensor sensor, int samplingPeriodUs);

msensorManager.registerListener(this,sensorManager.getDefaultSensor(Sensor.TYPE_LIGHT),SensorManager.SENSOR_DELAY_GAME);
  • 第一个参数是传感器监听器
  • 第二个参数是上面获取到的传感器对象
  • 第三个参数是指定获取传感器数据的频率

samplingPeriodUs 采样频率支持以下几个频率值

  • SensorManager.SENSOR_DELAY_FASTEST。最快,延迟最小,比较消耗电量,由于传递的为原始数据,如果算法处理不好将会影响应用的性能
  • SensorManager.SENSOR_DELAY_GAME。适合游戏的频率,在一般实时性要求的应用上适合使用这种频率。
  • SensorManager.SENSOR_DELAY_NORMAL。正常的频率,实时性要求不是很高的时候适合这种频率。
  • SensorManager.SENSOR_DELAY_UI。适合普通用户界面的频率,这种模式比较省电,而且系统开销也很小,但是延迟较大,适合在普通的小程序中使用

在实现监听器的时候,要重写两个方法onSensorChanged()和onAccuracyChanged(),第一个是当传感器的值改变时回调,第二个是当传感器精度改变时回调。另外,传感器的值是放在数组中保存的一般有三个值,分别是xyz轴三个方向上的值。

4、最后别忘记解监听
在onStop()和onPause()方法中注销监听器

sensorManager.unregisterListener(this);

 

Demo Test

查看手机支持哪些传感器

界面布局

之前博文《Android学习笔记之——Activity》已经介绍过如何使用Menu,本博文的框架则是基于该框架的。按不同的按钮实现不同sensor

首先在res目录下新建一个menu文件夹,右击res目录→New→Directory,输入文件夹名menu,点击OK。

接着在这个文件夹下再新建一个名叫menu_main的菜单文件,右击menu文件夹→New→Menu resource file。定义菜单文件如下

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:title="传感器列表" android:id="@+id/test_sensor_list"/>
    <item android:title="光传感器" android:id="@+id/test_light_sensor"/>
    <item android:title="近距离传感器" android:id="@+id/test_proximity_sensor"/>
    <item android:title="陀螺仪" android:id="@+id/test_gyroscope_sensor"/>
    <item android:title="加速测量仪" android:id="@+id/test_accelerometer_sensor"/>
    <item android:title="重力测量" android:id="@+id/test_accelerometer_2_sensor"/>
    <item android:title="磁场传感器" android:id="@+id/test_magnetic_sensor"/>
    <item android:title="方位测量" android:id="@+id/test_orientation"/>
</menu>

在主文件下定义整个界面如下

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 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"
    tools:context=".MainActivity">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="android Sensor Test"

        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

</androidx.constraintlayout.widget.ConstraintLayout>
package com.example.sensortest;

import androidx.appcompat.app.AppCompatActivity;

import android.content.Intent;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // TODO Auto-generated method stub
        getMenuInflater().inflate(R.menu.menu_main, menu);
        //inflate() 方法接收两个参数,
        //第一个参数用于指定我们通过哪一个资源文件来创建菜单,这里当然传入R.menu.menu_main 。
        //第二个参数用于指定我们的菜单项将添加到哪一个Menu 对象当中,这里直接使用onCreateOptionsMenu() 方法中传入的menu 参数。
        return super.onCreateOptionsMenu(menu);
    }

    //然后给这些按键定义内容(不同的按菜单按键启动不一样的activity)
    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // TODO Auto-generated method stub
        switch(item.getItemId()){
            //通过Intent来启动别的activity
            case R.id.test_sensor_list:
                startActivity(new Intent(this,SensorListActivity.class));
                break;
            case R.id.test_light_sensor:
//                startActivity(new Intent(this,LightSensorActivity.class));
                break;
            case R.id.test_proximity_sensor:
//                startActivity(new Intent(this,ProximitySensorActivity.class));
                break;
            case R.id.test_gyroscope_sensor:
//                startActivity(new Intent(this,GyroscopeSensorActivity.class));
                break;
            case R.id.test_accelerometer_sensor:
//                startActivity(new Intent(this,AccelerometerSensorActivity.class));
                break;
            case R.id.test_accelerometer_2_sensor:
//                startActivity(new Intent(this,GravityActivity.class));
                break;
            case R.id.test_magnetic_sensor:
//                startActivity(new Intent(this,MagneticFieldSensorActivity.class));
                break;
            case R.id.test_orientation:
//                startActivity(new Intent(this,VirtualJax.class));
                break;
            default:
                break;
        }
        return true;
    }


}

结果如下

传感器list

package com.example.sensortest;

import androidx.appcompat.app.AppCompatActivity;

import android.hardware.Sensor;
import android.hardware.SensorManager;
import android.os.Bundle;
import android.util.Log;
import android.widget.TextView;

import java.util.HashMap;
import java.util.List;

public class SensorListActivity extends AppCompatActivity {

    private TextView tv=null;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_sensor_list);

        tv=(TextView) findViewById(R.id.sensor_list_text);
        showSensorList();//自定义的函数,展示手机所带有的sensor
    }

    private HashMap<Integer, String> sensorTypes = new HashMap<Integer,String>();
    {
        sensorTypes.put(Sensor.TYPE_ACCELEROMETER, "TYPE_ACCELEROMETER");
        sensorTypes.put(Sensor.TYPE_AMBIENT_TEMPERATURE, "TYPE_AMBIENT_TEMPERATURE");
        sensorTypes.put(Sensor.TYPE_GAME_ROTATION_VECTOR, "TYPE_GAME_ROTATION_VECTOR");
        sensorTypes.put(Sensor.TYPE_GEOMAGNETIC_ROTATION_VECTOR, "TYPE_GEOMAGNETIC_ROTATION_VECTOR");
        sensorTypes.put(Sensor.TYPE_GRAVITY, "TYPE_GRAVITY");
        sensorTypes.put(Sensor.TYPE_GYROSCOPE, "TYPE_GYROSCOPE");
        sensorTypes.put(Sensor.TYPE_GYROSCOPE_UNCALIBRATED,"TYPE_GYROSCOPE_UNCALIBRATED");
        sensorTypes.put(Sensor.TYPE_LIGHT, "TYPE_LIGHT");
        sensorTypes.put(Sensor.TYPE_LINEAR_ACCELERATION, "TYPE_LINEAR_ACCELERATION");
        sensorTypes.put(Sensor.TYPE_MAGNETIC_FIELD, "TYPE_MAGNETIC_FIELD");
        sensorTypes.put(Sensor.TYPE_MAGNETIC_FIELD_UNCALIBRATED, "TYPE_MAGNETIC_FIELD_UNCALIBRATED");
        sensorTypes.put(Sensor.TYPE_ORIENTATION,"TYPE_ORIENTATION (deprecated)");//use SensorManager.getOrientation() instead.
        sensorTypes.put(Sensor.TYPE_PRESSURE, "TYPE_PRESSURE");
        sensorTypes.put(Sensor.TYPE_PROXIMITY, "TYPE_PROXIMITY");
        sensorTypes
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值