Android自动的SensorManager使用起来已经很方便,但由于一些情况我们希望对其中的功能进行封装:

  • 只使用个别的sensor,功能相对单一
  • 要对sensor返回的raw data进行算法处理方可使用
  • 程序中多处频繁调用禁用sensor的数据

由于项目需要在很多页面调用手机的方向信息,故而对sensor的方向感应器进行简单的封装,源码如下:

package com.weicheche.android.service;

import java.util.ArrayList;
import com.****.android.bean.ApplicationContext;
import android.hardware.Sensor;
import android.hardware.SensorEvent;
import android.hardware.SensorEventListener;
import android.hardware.SensorManager;
import android.os.Handler;
import android.os.SystemClock; /**
*
* @ClassName: OrientationService
* @Description: TODO(对android SDk自带的方向感应器进行封装)
* @author xuyong yxy8023@gmail.com
* @date 2014年7月14日 上午2:24:10
*/
public class OrientationService implements SensorEventListener { /*
* 对于想要监听方向变化的类,需要继承实现这个接口
*/
public static abstract interface OrientationListener{
public abstract void onOrientationChanged(float orientatoin);
} protected final Handler mHandler = new Handler();
private SensorManager sensorManager;
private Sensor mOrientationSensor;
private float mTargetDirection = 0;
private ArrayList<OrientationListener> listenerList = new ArrayList<OrientationListener>();
private long delayMillis = 20; public OrientationService() {
// TODO Auto-generated constructor stub
init();
} /**
*
* @Title: registerListener
* @Description: TODO(将需要监听方向变化的类注册到OrientationService里,service中的sensor自动打开)
* @param listener
* @throws
* @date 2014年7月14日 上午2:29:26
* Xuyong
*/
public void registerListener(OrientationListener listener){
listenerList.add(listener);
if(1 == listenerList.size()){
// 刚刚有新的listener加入的时候打开方向感应器并启动更新线程
startService();
mHandler.postDelayed(mCompassViewUpdater, delayMillis); // delayMillis毫秒执行一次方向更新
}
} /**
* @Title: unregisterListener
* @Description: TODO(再activity pause或者销毁时,讲listener从service移除,service会根据情况自动停止方向感应器的工作)
* @param listener
* @throws
* @date 2014年7月14日 上午2:30:45
* Xuyong
*/
public void unregisterListener(OrientationListener listener){
if((listenerList.remove(listener)) && 0 == listenerList.size()){
// 如果成功移除listener后导致没有任何listener监听方向变化,暂停方向感应器
stopService();
}
} /**
* @Title: setDelayMillis
* @Description: TODO(设置更新时间间隔,不得低于10ms)
* @param delayMillis
* @throws
* @date 2014年7月14日 上午2:34:10
* Xuyong
*/
public void setDelayMillis(long delayMillis){
if(delayMillis>10){
this.delayMillis = delayMillis;
}
} /**
* @Title: onDestory
* @Description: TODO(移除所有的监听类,并停止方向感应器)
* @throws
* @date 2014年7月14日 上午2:34:46
* Xuyong
*/
public void onDestory(){
listenerList.clear();
stopService();
} /**
* @Title: init
* @Description: TODO(初始化方向感应器)
* @throws
* @date 2014年7月14日 上午12:36:53
* Xuyong
*/
@SuppressWarnings("deprecation")
private void init(){
sensorManager = (SensorManager) ApplicationContext.getInstance().getContext().getSystemService(android.content.Context.SENSOR_SERVICE);
try {
mOrientationSensor = sensorManager.getSensorList(
Sensor.TYPE_ORIENTATION).get(0);
} catch (Exception e) {
// TODO: handle exception
mOrientationSensor = null;
}
} private void stopService(){
if (mOrientationSensor != null && sensorManager != null) {
sensorManager.unregisterListener(this);
}
} private void startService(){
if (mOrientationSensor != null && sensorManager != null) {
sensorManager.registerListener(this, mOrientationSensor, SensorManager.SENSOR_DELAY_GAME);
}
} /**
* 这个是更新指南针旋转的线程,handler的灵活使用,每delayMillis毫秒检测方向变化值(这样的机制不太好,可能会出现线程阻滞)
*/
protected Runnable mCompassViewUpdater = new Runnable() {
@Override
public void run() {
if (listenerList.size() > 0) {// 有监听的时候,传递下去,并且注意传入顺序为倒序,保证最近的层最先响应。
long startTime = SystemClock.uptimeMillis();
for(int i = listenerList.size()-1; i>=0; i--){
((OrientationListener) listenerList.get(i)).onOrientationChanged(mTargetDirection);
}
// 由于线程阻滞,可能带来延时,通过时间控制来弥补
long endTime = SystemClock.uptimeMillis();
long delayTime = endTime - startTime;
delayTime = (delayTime > delayMillis)? 2:(delayMillis-delayTime);
mHandler.postDelayed(mCompassViewUpdater, delayTime); // 比定时器好
}
}
}; /*
* no use currently
*/
@Override
public void onAccuracyChanged(Sensor arg0, int arg1) {
// TODO Auto-generated method stub
} /**
* @Title: onSensorChanged
* @Description: TODO(直接调用SDK自带的API获取方向信息,以后需要修改为根据加速度和地磁数据的方向计算)
* @param event
* @throws
* @date 2014年7月11日 下午4:52:36
* Xuyong
*/
@SuppressWarnings("deprecation")
@Override
public void onSensorChanged(SensorEvent event) {
// TODO Auto-generated method stub
switch (event.sensor.getType()) {
// Note:改方法已经不鼓励使用,考虑在此处修改数据获取方向重新计算方向值
case Sensor.TYPE_ORIENTATION:
float direction = event.values[SensorManager.DATA_X] * -1.0f;
mTargetDirection = (direction + 720) % 360; // 赋值给全局变量,让指南针旋转
break;
default:
break;
}
}
}

调用方法:

对任意activity,继承实现OrientationListener,在onResume和onPause中分别注册和注下销listener,代码如下:

 public class xxxxActivity  implements  OrientationListener {

     @Override
protected void onPause() {
super.onPause();
    ApplicationContext.getInstance().getOrientationService().unregisterListener(this);
} 9 @Override
public void onResume() {
  super.onResume();
  ApplicationContext.getInstance().getOrientationService().registerListener(this);
} @Override
public void onOrientationChanged(float orientatoin) {
// TODO Auto-generated method stub
adapter.setOrientation(orientatoin);
}
}

Android对方向感应器的封装调用的更多相关文章

  1. okhttputils【 Android 一个改善的okHttp封装库】使用(一)

    版权声明:本文为HaiyuKing原创文章,转载请注明出处! 前言 本文使用的OKHttp封装库是张鸿洋(鸿神)写的,因为在项目中一直使用这个库,所以对于一些常用的请求方式都验证过,所以特此整理下. ...

  2. okhttputils【 Android 一个改善的okHttp封装库】使用(三)

    版权声明:本文为HaiyuKing原创文章,转载请注明出处! 前言 这一篇主要讲一下将OkHttpUtils运用到mvp模式中. 数据请求地址:http://www.wanandroid.com/to ...

  3. 社会化登录分享-Android SDK的二次封装和使用

    本系列文章将第三方的登录分享功能进行二次封装,统一接口调用,简化了接不同平台登录分享的步骤. 0 系列文章 系列一 Android SDK的二次封装和使用 系列二 源码解析 系列三 微信SDK接入 系 ...

  4. 解析android framework下利用app_process来调用java写的命令及示例

    解析android framework下利用app_process来调用java写的命令及示例 在android SDK的framework/base/cmds目录下了,有不少目录,这些目的最终都是b ...

  5. 有关ViewPager的使用及解决Android下ViewPager和PagerAdapter中调用notifyDataSetChanged失效的问题

    ViewPager是android-support-v4.jar包中的一个系统控件,继承自ViewGroup,专门用以实现左右滑动切换View的效果,使用时需要首先在Project->prope ...

  6. android系统中对ffmpeg封装最好的免费SDK

    android系统中对ffmpeg封装最好的免费SDK; 无论个人还是公司,都免费商用, 欢迎下载. https://github.com/LanSoSdk/LanSoEditor_common 可能 ...

  7. python(面向对象-类封装调用)

    一.面对对象思想 (1)大家肯定听过 Python 中”一切皆对象“的说法,但可能并不了解它的具体含义,只是在学习的时候听说 Python 是面向对象的编程语言,本节将向大家详细介绍 Python 面 ...

  8. Android 一个改进的okHttp封装库

    一.概述 之前写了篇Android OkHttp完全解析 是时候来了解OkHttp了,其实主要是作为okhttp的普及文章,当然里面也简单封装了工具类,没想到关注和使用的人还挺多的,由于这股热情,该工 ...

  9. Android开发之使用Handler封装下载图片工具类(源码分享)

    假设每下载一张图片,就得重写一次Http协议,多线程的启动和handler的信息传递就显得太麻烦了,我们直接来封装一个工具类,便于我们以后在开发时随时能够调用. (1)在清单文件加入权限 <us ...

随机推荐

  1. DeepMind:所谓SACX学习范式

    机器人是否能应用于服务最终还是那两条腿值多少钱,而与人交互,能真正地做"服务"工作,还是看那两条胳膊怎么工作.大脑的智能化还是非常遥远的,还是先把感受器和效应器做好才是王道. 关于 ...

  2. linux nohup & 简单使用

    线上通常nohup配合&启动程序,同时免疫SIGINT和SIGHUP信号,从而保证程序在后台稳定运行 & 1.后台运行,输出默认到屏幕 2.免疫SIGINT信号,比如Ctrl+c不会杀 ...

  3. Windows提高_2.3第三部分:内核区同步

    第三部分:内核区同步 等待函数(WaitForObject) 等待函数的形式 单个:WaitForSingleObject 多个:WaitForMultipleObjects 一个可以被等待的对象通常 ...

  4. eclipse配置Tomcat服务器server locations的方法

    最近放弃了使用Myeclipse,转而使用eclipse作为开发工具,确实Myeclipse集成了太多东西,使得开发人员的配置越来越少,这不是个好事,使用eclipse后,有些地方就得自己去配置,比如 ...

  5. Intel要在中国投35亿美金造这种闪存,3DxPoint技术牛在哪里?

    Repost: https://www.leiphone.com/news/201508/bbCUJqS2M3glCY3m.html 编者按: 今年的IDF上,Intel 再次强调了3DxPoint闪 ...

  6. 总结struts2 iterator status的用法

    1:#status.odd 是否奇数行 2:#status.count 当前行数 3:#status.index 当前行的序号,从0开始『#status.count=#status.index+1』 ...

  7. xmpp消息回执(6)

    原始地址:XMPPFrameWork IOS 开发(七)消息回执 请参考:XEP-0184协议 协议内容: 发送消息时附加回执请求 <message from='northumberland@s ...

  8. 支持向量机(SVM)原理浅析

    因为网页博客输入公式很麻烦,所以就在word上面写了,然后截图发上来. 后续关于SVM和FC在深度学习当中得使用对比分析,我再补充.

  9. C++ 实现Golang里的defer

    不多说了,直接贴代码.就一个hpp文件. 1 #include <functional> 2 3 #define CONCAT_(a, b) a##b 4 #define CONCAT(a ...

  10. MyBatis 的基本要素—核心配置文件

    MyBatis 核心配置文件( mybatis-config.xml),该文件配置了 MyBatis 的一些全局信息,包含数据库连接信息和 MyBatis 运行时所需的各种特性,以及设置和影响 MyB ...