生活随笔
收集整理的這篇文章主要介紹了
玩转Android之加速度传感器的使用,模仿微信摇一摇
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
Android系統帶的傳感器有很多種,最常見的莫過于微信的搖一搖了,那么今天我們就來看看Anroid中傳感器的使用,做一個類似于微信搖一搖的效果。
OK ,廢話不多說,我們就先來看看效果圖吧:
當我搖動手機的時候這里的動畫效果基本和微信上的動畫效果一致,這里請大家自行腦補微信搖一搖畫面。
那我們就動手吧。
1.布局文件
好,那我們先來看看布局文件吧,在布局文件的正中央是一個花的圖片,上圖大家看到的手機圖片實際上是兩張圖片拼接在一起,將花的那張圖片遮住了,當搖一搖的時候,這兩張圖片分別向上或者向下移動,然后花的圖片就可以顯示出來。OK,基本原理就是這樣,我們來看看代碼:
[java] view plaincopy print?
<?xml?version="1.0"?encoding="utf-8"?>??<RelativeLayout??????xmlns:android="http://schemas.android.com/apk/res/android"??????xmlns:tools="http://schemas.android.com/tools"??????android:layout_width="match_parent"??????android:layout_height="match_parent"??????android:background="#1f1f1f">????????<ImageView??????????android:layout_width="wrap_content"??????????android:layout_height="wrap_content"??????????android:src="@drawable/flower"/>????????<LinearLayout??????????android:layout_width="wrap_content"??????????android:layout_height="wrap_content"??????????android:layout_centerInParent="true"??????????android:orientation="vertical">????????????<ImageView??????????????android:id="@+id/up"??????????????android:layout_width="wrap_content"??????????????android:layout_height="wrap_content"??????????????android:src="@drawable/up"/>????????????<ImageView??????????????android:id="@+id/down"??????????????android:layout_width="wrap_content"??????????????android:layout_height="wrap_content"??????????????android:src="@drawable/down"/>??????</LinearLayout>??</RelativeLayout>?? 2.傳感器監聽手機晃動
既然要監聽手機加速度的變化,那我首先需要獲取系統的傳感器:
[java] view plaincopy print?
????????sensorManager?=?(SensorManager)?getSystemService(SENSOR_SERVICE);??????????????????Sensor?sensor?=?sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);?? 這兩行代碼首先是獲取一個傳感器管理器,然后獲取加速度傳感器,因為關于傳感器的API 有很多,這里你需要指明自己要獲取的是哪一個傳感器。拿到傳感器之后,需要注冊監聽,如下:
[java] view plaincopy print?
sensorManager.registerListener(listener,?sensor,?SensorManager.SENSOR_DELAY_GAME);?? 注冊傳感器的監聽一共需要三個參數,第一個是監聽器,第二個是加速度傳感器,第三個是傳感器的靈敏度,傳感器的靈敏度一共分為四級,如下,從上往下靈敏度依次降低:
1. SENSOR_DELAY_FASTEST
2. SENSOR_DELAY_GAME
3. SENSOR_DELAY_UI
4. SENSOR_DELAY_NORMAL
OK ,注冊完之后,我們還是來看看這個監聽器是什么吧:
[java] view plaincopy print?
private?SensorEventListener?listener?=?new?SensorEventListener()?{??????????????????@Override??????????public?void?onSensorChanged(SensorEvent?event)?{??????????????????????????float?valuesX?=?Math.abs(event.values[0]);??????????????float?valuesY?=?Math.abs(event.values[1]);??????????????float?valuesZ?=?Math.abs(event.values[2]);????????????????if?(valuesX?>?17?||?valuesY?>?17?||?valuesZ?>?17)?{??????????????????startAnimation();??????????????????playSound();??????????????}??????????}????????????@Override??????????public?void?onAccuracyChanged(Sensor?sensor,?int?accuracy)?{????????????}??????};?? 這個listener中一共就兩個方法,一個是當手機的加速度發生改變的時候調用,還有一個是當傳感器的靈敏度發生改變的時候調用,當手機的加速度發生改變的時候,我們可以獲取到手機在X 、Y、Z 三個維度上的變化值,拿到這個值之后,我們只需要進行簡單的比較即可,如果有任意一個方向的值大于17,則認為有人在晃動手機,這個時候開啟動畫和聲音的播放。
3.開啟動畫和聲音
動畫實際上就是兩個平移動畫,我們來看看:
[java] view plaincopy print?
private?void?startAnimation()?{??????????long?currentTimeMillis?=?System.currentTimeMillis();??????if?(currentTimeMillis?-?lastTime?<?1000)?{??????????return;??????}??????lastTime?=?currentTimeMillis;??????AnimationSet?upSet?=?new?AnimationSet(true);??????TranslateAnimation?upUp?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?-1);??????upUp.setDuration(1000);??????TranslateAnimation?upDown?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?1);??????upDown.setDuration(1000);??????upDown.setStartOffset(1000);??????upSet.addAnimation(upUp);??????upSet.addAnimation(upDown);??????up.startAnimation(upSet);??????AnimationSet?downSet?=?new?AnimationSet(true);??????TranslateAnimation?downUp?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?1);??????downUp.setDuration(1000);??????TranslateAnimation?downDown?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?-1);??????downDown.setDuration(1000);??????downDown.setStartOffset(1000);??????downSet.addAnimation(downUp);??????downSet.addAnimation(downDown);??????down.startAnimation(downSet);??}?? 至于聲音,由于我這里只是播放比較短小的音效而已,所以并沒有必要使用MediaPlayer,我可以通過一個聲音池來解決這個問題,代碼如下:
[java] view plaincopy print?
private?void?initSoundPool()?{??????if?(Build.VERSION.SDK_INT?>?20)?{??????????SoundPool.Builder?builder?=?new?SoundPool.Builder();??????????????????builder.setMaxStreams(3);??????????AudioAttributes.Builder?aaBuilder?=?new?AudioAttributes.Builder();??????????aaBuilder.setLegacyStreamType(AudioManager.STREAM_MUSIC);??????????builder.setAudioAttributes(aaBuilder.build());??????????soundPool?=?builder.build();??????}?else?{??????????soundPool?=?new?SoundPool(3,?AudioManager.STREAM_MUSIC,?0);??????}??????????sound1?=?soundPool.load(this,?R.raw.awe,?1);??}?? 在創建一個聲音池的時候我采取了兩種不同的方案,如果系統的版本大于20,則是用第一種方式獲取聲音池,否則使用第二種方式獲取聲音池。獲取聲音池之后,再通過聲音池加載一個音頻文件。加載完成之后,我就可以對這個音頻文件進行播放了,如下:
[java] view plaincopy print?
soundPool.play(sound1,?1,?1,?0,?0,?1);?? 每個參數的含義都寫的很清楚了,大家又不清楚的地方可以直接看源碼,這里的源碼注釋很好懂。
?
最后一步就是開啟手機震動了,開啟手機震動,我需要首先獲取震動服務,如下:
[java] view plaincopy print?
???????vibrator?=?(Vibrator)?getSystemService(VIBRATOR_SERVICE);?? 然后調用Vibrator類中的vibrator方法執行震動,如下:
[java] view plaincopy print?
????????????????vibrator.vibrate(new?long[]{100,?200,?100,?200,?100,?200},?-1);?? 手機震動一定要記得添加震動權限哦,如下:
[java] view plaincopy print?
<uses-permission?android:name="android.permission.VIBRATE"?/>?? OK ,最后,在銷毀Activity的時候要解除對傳感器的監聽,同時釋放聲音池資源,如下:
[java] view plaincopy print?
@Override??protected?void?onDestroy()?{??????super.onDestroy();??????????sensorManager.unregisterListener(listener);??????if?(soundPool?!=?null)?{??????????????????soundPool.release();??????}??}?? 完整的Activity 代碼如下:
[java] view plaincopy print?
public?class?MainActivity?extends?AppCompatActivity?{??????private?ImageView?up;??????private?ImageView?down;??????????private?long?lastTime;??????private?SoundPool?soundPool;??????private?int?sound1;??????private?Vibrator?vibrator;??????private?SensorEventListener?listener?=?new?SensorEventListener()?{??????????????????@Override??????????public?void?onSensorChanged(SensorEvent?event)?{??????????????????????????float?valuesX?=?Math.abs(event.values[0]);??????????????float?valuesY?=?Math.abs(event.values[1]);??????????????float?valuesZ?=?Math.abs(event.values[2]);????????????????if?(valuesX?>?17?||?valuesY?>?17?||?valuesZ?>?17)?{??????????????????startAnimation();??????????????????playSound();??????????????}??????????}????????????@Override??????????public?void?onAccuracyChanged(Sensor?sensor,?int?accuracy)?{????????????}??????};??????private?SensorManager?sensorManager;????????private?void?playSound()?{??????????????????????????????????????????????????soundPool.play(sound1,?1,?1,?0,?0,?1);??????????????????????????????????vibrator.vibrate(new?long[]{100,?200,?100,?200,?100,?200},?-1);??????}????????private?void?startAnimation()?{??????????????????long?currentTimeMillis?=?System.currentTimeMillis();??????????if?(currentTimeMillis?-?lastTime?<?1000)?{??????????????return;??????????}??????????lastTime?=?currentTimeMillis;??????????AnimationSet?upSet?=?new?AnimationSet(true);??????????TranslateAnimation?upUp?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?-1);??????????upUp.setDuration(1000);??????????TranslateAnimation?upDown?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?1);??????????upDown.setDuration(1000);??????????upDown.setStartOffset(1000);??????????upSet.addAnimation(upUp);??????????upSet.addAnimation(upDown);??????????up.startAnimation(upSet);??????????AnimationSet?downSet?=?new?AnimationSet(true);??????????TranslateAnimation?downUp?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?1);??????????downUp.setDuration(1000);??????????TranslateAnimation?downDown?=?new?TranslateAnimation(TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,??????????????????0,?TranslateAnimation.RELATIVE_TO_SELF,?0,?TranslateAnimation.RELATIVE_TO_SELF,?-1);??????????downDown.setDuration(1000);??????????downDown.setStartOffset(1000);??????????downSet.addAnimation(downUp);??????????downSet.addAnimation(downDown);??????????down.startAnimation(downSet);??????}????????@Override??????protected?void?onCreate(Bundle?savedInstanceState)?{??????????super.onCreate(savedInstanceState);??????????setContentView(R.layout.activity_main);??????????up?=?((ImageView)?findViewById(R.id.up));??????????down?=?((ImageView)?findViewById(R.id.down));??????????initSensor();??????????initSoundPool();??????????????????vibrator?=?(Vibrator)?getSystemService(VIBRATOR_SERVICE);??????}????????????private?void?initSoundPool()?{??????????if?(Build.VERSION.SDK_INT?>?20)?{??????????????SoundPool.Builder?builder?=?new?SoundPool.Builder();??????????????????????????builder.setMaxStreams(3);??????????????AudioAttributes.Builder?aaBuilder?=?new?AudioAttributes.Builder();??????????????aaBuilder.setLegacyStreamType(AudioManager.STREAM_MUSIC);??????????????builder.setAudioAttributes(aaBuilder.build());??????????????soundPool?=?builder.build();??????????}?else?{??????????????soundPool?=?new?SoundPool(3,?AudioManager.STREAM_MUSIC,?0);??????????}??????????????????sound1?=?soundPool.load(this,?R.raw.awe,?1);??????}????????????private?void?initSensor()?{??????????????????sensorManager?=?(SensorManager)?getSystemService(SENSOR_SERVICE);??????????????????Sensor?sensor?=?sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);??????????????????????????????????????????????????????????????????????????????????sensorManager.registerListener(listener,?sensor,?SensorManager.SENSOR_DELAY_GAME);??????}????????@Override??????protected?void?onDestroy()?{??????????super.onDestroy();??????????????????sensorManager.unregisterListener(listener);??????????if?(soundPool?!=?null)?{??????????????????????????soundPool.release();??????????}??????}??}?? 以上。
?
轉載于:https://www.cnblogs.com/Free-Thinker/p/6544174.html
總結
以上是生活随笔為你收集整理的玩转Android之加速度传感器的使用,模仿微信摇一摇的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。