陀螺儀、加速計、磁力計等傳感器彙總 (轉)

轉自 http://blog.csdn.net/a345017062/article/details/6459643html

陀螺儀就是內部有一個陀螺,它的軸因爲陀螺效應始終與初始方向平行,這樣就能夠經過與初始方向的誤差計算出實際方向。手機裏陀螺儀其實是一個結構很是精密的芯片,內部包含超微小的陀螺。
加速計是用來檢測手機受到的加速度的大小和方向的,而手機靜置的時候是隻受到重力加速度(這個高中學過)的.因此不少人把加速計功能又叫作重力感應功能。
磁力計是測試磁場強度和方向的。


陀螺儀測量是參考標準是內部中間在與地面垂直的方向上進行轉動的陀螺。經過設備與陀螺的夾角獲得結果。
加速計是之內部測量組件在各個方向上的受力狀況來獲得結果。
磁力計的原理就是中學物理中涉及到的那個最簡單的指南針了(那記得那根被磁化的鋼針麼)。


它們分別有本身的強項:
陀螺儀的強項在於測量設備自身的旋轉運動。對設備自身運動更擅長。但不能肯定設備的方位。
加速計的強項在於測量設備的受力狀況。對設備相對外部參考物(好比,地面)的運動更擅長。但用來測量設備相對於地面的擺放姿式,則精確度不高。
磁力計的強項在於定位設備的方位。能夠測量出當前設備與東南西北四個方向上的夾角。


舉幾個例子:
陀 螺儀對設備旋轉角度的檢測是瞬時的並且是很是精確的,能知足一些須要高分辨率和快速反應的應用好比FPS遊戲的瞄準。並且陀螺儀配合加速計能夠在沒有衛星 和網絡的狀況下進行導航,這是陀螺儀的經典應用。加速度計可用於有固定的重力參考座標系、存在線性或傾斜運動但旋轉運動被限制在必定範圍內的應用。同時處 理直線運動和旋轉運動時,就須要把加速度和陀螺儀計結合起來使用。若是還想設備在運動時不至於迷失方向,就再加上磁力計。


對於一個發射出去的導彈來講,要想精確追蹤並調整導彈的軌道的話,下面幾組數據必不可少:
GPS定位它的位置
加速計測量當前加速度
磁力計肯定導彈頭的方向(只能知道東南西北四個方向上的夾角),陀螺儀知道導彈的角速度。這兩個儀器結合才能肯定導彈的準確的立體運動方向。


加速計獲得的結果就是XYZ三個值,分別表明三個方向的加速度。關於XYZ三值的介紹,能夠看這裏:
android 重力感應和屏幕旋轉關係
http://blog.csdn.net/lzx_bupt/archive/2010/04/20/5507165.aspx


用加速計和磁力計能夠計算出orientation(方位計),orientation涉及到了三個概念:
Roll:左右傾斜角度,也叫滾轉角 http://baike.baidu.com/view/1769672.htm
Pitch:先後傾斜,也叫俯仰角 http://baike.baidu.com/view/3832041.htm
Yaw:左右搖擺,也叫偏航角 http://baike.baidu.com/view/1769448.htm


下 面代碼是Android2.3中/development/samples/Compass的源碼,演示瞭如何使用加速計和磁力計來肯定手機的擺放姿式和 方位。由於手機運動的加速度不高,精確度也沒有太大的要求,用加速計替代陀螺儀也能夠。但若是作一些精度比較高的遊戲的話,最好仍是有陀螺儀。java

 

[java] view plain copy
  1. // 打開加速計和磁力計兩個傳感器。 Sensor gsensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER); Sensor msensor = mSensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD); mSensorManager.registerListener(this, gsensor, SensorManager.SENSOR_DELAY_GAME);mSensorManager.registerListener(this, msensor, SensorManager.SENSOR_DELAY_GAME);// 加速計數據。private float[] mGData = new float[3];//磁力計數據。 private float[] mMData = new float[3];//旋轉矩陣(rotation matrix),用於計算手機自身相對 於地面座標系的旋轉角度。好比手機如今是橫着仍是豎着的。反映的是手機的立體擺放位置。這個數據最好用陀螺儀來測量,沒有陀螺儀的話,藉助於加速計和重力 加速度也能夠,只是精度不夠強罷了。private float[] mR = new float[16];//傾斜矩陣 (inclination matrix),用於計算手機方位。好比手機的頭部如今朝南仍是朝北。是針對一個平面上的東南西北四個方向而言的。 private float[] mI = new float[16];//存放最終的旋轉角度數據 private float[] mOrientation = new float[3]; public void onSensorChanged(SensorEvent event) {        int type = event.sensor.getType();        float[] data;        if (type == Sensor.TYPE_ACCELEROMETER) {            data = mGData;        } else if (type == Sensor.TYPE_MAGNETIC_FIELD) {            data = mMData;        } else {            // we should not be here.            return;        }        for (int i = 0; i & lt; 3; i++)            data[i] = event.values[i];//這一步的目的是獲取mR和mI兩個矩 陣。        SensorManager.getRotationMatrix(mR, mI, mGData, mMData);//用矩陣 mR獲取手機的旋轉角度。        SensorManager.getOrientation(mR, mOrientation);//用矩陣 mI獲取手機在東南西北四個方向上的夾 角。        float incl = SensorManager.getInclination(mI);        final float rad2deg = (float) (180.0f / Math.PI);        Log.d("Compass", "yaw: " + (int)(mOrientation[0] * rad2deg) + "  pitch: " + (int)(mOrientation[1] * rad2deg) + "  roll: " + (int)(mOrientation[2] * rad2deg) + "  incl: " + (int)(incl * rad2deg));}  

 

補充於2011.7.14android

gsensor的較正比較容易完成,通常是讓機器以某個固定角度(好比水平)放置,而後連續取N個值(好比20個)進行一系列計算。Android和iphone中,屏幕會隨着設備的旋轉方向變化而改變,其實應用的只是gsensor。
msensor 的較正分爲水平較正和傾斜補償。水平較正有平面較正、8字較正、十面較正等幾種方法。通過水平較正後,msensor在水平放置時已經可使用了,但設備 與水平面有必定的傾斜角時,這個傾斜角會對msensor的精度形成影響。所以,還須要進行傾斜角補償較正。先經過較正好的gsensor得出傾斜角,然 後使用傾斜角(pitch,roll)進行補償較正計算。
orientation sensor能夠由一個單獨芯片來實現,也能夠由gsensor和msensor共同計算出來的(我看android2.3的Sample中的 Compass就已經這樣幹了)。orientation sensor輸出三個值:roll,pitch,yaw。其中,roll和pitch分別表明手機的X軸和Y軸與水平面的夾角,因此這兩個值能夠由 gsensor計算出來。yaw表明手機y軸水平面上的投影與正北方向的夾角,由msensor計算出來。
陀螺儀能夠捕捉很微小的運動軌跡變化,所以能夠作高分辨率和快速反應的旋轉檢測。但不能像msensor或orientation sensor那樣測量當前的運行方向。飛機當中就用它記錄運動角度改變,從而造成運動軌跡。缺點就是隨着時間增加會有偏差積累,網絡

補充於2011.7.19iphone

陀螺儀的XYZ分別表明設備圍繞XYZ三個軸旋轉的角速度:radians/second。至於XYZ使用的座標系與gsensor相同。逆時針方向旋轉時,XYZ的值是正的。下面是使用陀螺儀進行開發時的演示代碼:測試

[java] view plain copy
  1. private static final float NS2S = 1.0f / 1000000000.0f;  
  2. private float timestamp;  
  3. public void onSensorChanged(SensorEvent event)  
  4. {  
  5.    if (timestamp != 0) {  
  6.        final float dT = (event.timestamp - timestamp) * NS2S;  
  7.        angle[0] += event.data[0] * dT;  
  8.        angle[1] += event.data[1] * dT;  
  9.        angle[2] += event.data[2] * dT;  
  10.    }  
  11.    timestamp = event.timestamp;  
  12. }  

另外,陀螺儀運轉一段時間之後,noise和offset會致使數據誤差,須要藉助其它傳感器進行較正。this

 

補充於2011.7.20spa

 

利用加速計(gsensor),磁力計(msensor)模擬出方位傳感器(orientation)來

Android最近的新版本已經不建議咱們在開發的時候像下面這樣直接用方位傳感器了:
Sensor ori = mSensorManager.getDefaultSensor(Sensor.TYPE_ORIENTATION);
mSensorManager.registerListener(this, ori, SensorManager.SENSOR_DELAY_GAME);
而 是建議使用SensorManager.getOrientation(mR, mOrientation)這個API本身在應用程序的onSensorChanged中計算出方位傳感器。但咱們在作HAL層時,卻不得不考慮一些 APK仍是像上面代碼那樣直接使用方位傳感器的狀況,因此,咱們必須在sensor.c中模擬出一個方位傳感器來:
激活方位傳感器時,同時激活加速計和磁力計,關閉方位傳感器時也要同時關閉加速計和磁力計,同時還要考慮若是用戶註冊了加速計或磁力計,而且正在使用的狀況。操作系統

  1. //默認狀態,0表明關閉。  
  2. static int accStatus = 0;  
  3. static int magStatus = 0;  
  4. static int switchSensor(int fd, int handle, int enabled) {  
  5.     int status = 0;  
  6.     switch (handle) {  
  7.     case ID_ACCELERATION:  
  8.         if (enabled) {  
  9.             if (!accStatus) {//=0說明當前狀態是關閉時,執行打開操做。不然,說明已經打開過。  
  10.                 status = ioctl(fd, ACC_FLAG, 1);  
  11.                 LOGW("open gsensor");  
  12.             }  
  13.             accStatus++;  
  14.         } else {  
  15.             if (accStatus > 0) {//>0說明當前狀態是打開,這個時候纔會嘗試關閉gsensor。  
  16.                 accStatus--;  
  17.                 if (!accStatus) {//減1後若是==0,說明orientation沒有使用gsensor,能夠關閉gsensor了  
  18.                     status = ioctl(fd, ACC_FLAG, 0);  
  19.                     LOGW("close gsensor");  
  20.                 }  
  21.             }  
  22.         }  
  23.         break;  
  24.     case ID_MAGNETIC:  
  25.         if (enabled) {  
  26.             if (!magStatus) {  
  27.                 status = ioctl(fd, MAG_FLAG, 1);  
  28.                 LOGW("open msensor");  
  29.             }  
  30.             magStatus++;  
  31.         } else {  
  32.             if (magStatus > 0) {  
  33.                 magStatus--;  
  34.                 if (!magStatus) {  
  35.                     status = ioctl(fd, MAG_MFLAG, 0);  
  36.                     LOGW("close msensor");  
  37.                 }  
  38.             }  
  39.         }  
  40.         break;  
  41.     case ID_ORIENTATION:  
  42.         if (enabled) {  
  43.             if (!accStatus) {//=0說明gsensor沒有打開過,直接打開。  
  44.                 status = ioctl(fd, ACC_AFLAG, 1);  
  45.                 LOGW("open msensor");  
  46.             }  
  47.             if (!magStatus) {  
  48.                 status = ioctl(fd, MAG_FLAG, 1);  
  49.                 LOGW("open msensor");  
  50.             }  
  51.             accStatus++;  
  52.             magStatus++;  
  53.         } else {  
  54.             if (accStatus > 0) {//>0說明被打開過,嘗試關閉gsensor。  
  55.                 accStatus--;  
  56.                 if (!accStatus) {//減1後=0說明用戶沒有直接使用gsensor,只是使用了orientation,能夠關閉gsensor了。  
  57.                     status = ioctl(fd, ACC_AFLAG, 0);  
  58.                     LOGW("close gsensor");  
  59.                 }  
  60.             }  
  61.             if (magStatus > 0) {  
  62.                 magStatus--;  
  63.                 if (!magStatus) {  
  64.                     status = ioctl(fd, MAG_FLAG, 0);  
  65.                     LOGW("close msensor");  
  66.                 }  
  67.             }  
  68.         }  
  69.         break;  
  70.     default:  
  71.         LOGW("unsupported sensor type");  
  72.     }  
  73.     return status;  
  74. }  



參考文章:.net

加速度計和陀螺儀的區別

http://www.cnblogs.com/liuq0s/archive/2010/09/02/1816394.html

三軸陀螺儀與加速度計如何輔助Iphone定位的

http://www.weizhiquan.com/archives/1072

ST集成傳感器方案實現電子羅盤功能

http://www.eeworld.com.cn/gykz/2011/0408/article_5352.html

Android設備中實現陀螺儀(Orientation Sensor)

http://blog.csdn.net/beeboobeeboo/article/details/6536941

簡單易懂的文字 帶你認識iPhone 4陀螺儀

http://mobile.zol.com.cn/187/1876651.html

Android操做系統11種傳感器介紹

http://hi.baidu.com/aokikyon/blog/item/f9a539d74a4f5fc4a044df40.html

相關文章
相關標籤/搜索