2011-05-22 84 views
10

僅使用內置在加速計中的手機(Android),我將如何去尋找其速度?如何僅使用加速度計查找速度?

我一直在修補這個數學,但無論我提出的函數往往會導致速度的指數增長。我的工作原理是在應用程序啓動時,手機處於停滯狀態。這肯定會使速度(至少粗略地)成爲可能。

我在物理學和數學方面也有不錯的背景,所以我不應該對這裏的任何概念有任何困難。

我應該怎麼做?

+0

@Ignacio什麼?恆定加速度意味着速度線性增加。 – Imran 2011-05-22 02:40:52

+0

你有任何工作解決方案,你可以指向我或分享代碼。 – VenomVendor 2013-03-17 15:44:41

+0

嗨,你有沒有考慮過關閉這個問題? – 2016-05-09 19:28:21

回答

1

v =積分(a)?

但是總的來說,我覺得在加速度計的不準確性將使這相當強悍

+0

取決於不準確的類型。你可以校準線性誤差,不是嗎? – 2013-06-11 05:11:53

-2

如果手機是在standstil,你有零加速度,所以你的速度是0。也許你應該找到位置數據GPS並獲取關聯的時間樣本並計算隨時間推移的速度距離。

+0

是的,在應用程序啓動時,速度爲0「。我從這個角度對它進行校準。 – 2011-05-22 02:07:52

+0

「靜止不動」實際上應該很容易察覺。如果來自加速度計的輸入(使用TYPE_LINEAR_ACCELERATION)非常穩定,則手機可能未被處理。 – 2016-06-14 15:24:10

7

首先,您必須從加速計數據中移除因重力引起的加速度。那麼這只是一個整合加速度來獲得速度的問題。不要忘記,加速度和速度是正確的矢量,而不是標量,並且您還必須跟蹤空間中手機的旋轉,以正確確定加速度矢量相對於計算速度矢量的方向。

+0

你可以從編碼的角度來解釋或指向一個鏈接,我可以得到這方面的更多細節。 – VenomVendor 2013-03-17 15:43:00

+3

TYPE_LINEAR_ACCELERATION傳感器會爲您提供經過濾的重力加速度,所以很好。 TYPE_ROTATION_VECTOR將爲您提供設備方向作爲四元數,它可以很容易地轉換爲3x3旋轉矩陣。在每個時間片上,使用旋轉矩陣將加速度轉換爲3維空間中的矢量。積分隨着時間的推移獲得加速度(另一個向量)並將* *整合到相對於開始位置的位置。 (這一切都假定初始速度爲零)。然後去酒吧喝一杯,因爲這對廉價的傳感器來說都是無望的。 – 2016-06-14 15:13:22

7

這將取決於加速度和持續時間。一個溫和的,長時間的加速度可以測量,但是加速度的任何突然增加,然後是一個恆定的速度,將使您的測量非常困難,並容易出錯。

假設加速度恆定,公式非常簡單:a =(V1-V0)/ t。因此,知道時間和加速度,並假設V0 = 0,則V1 = a * t在更現實的世界中,您可能不會有恆定的加速度,因此您應該計算每個測量的Delta V ,並添加所有速度變化以獲得最終速度。始終認爲你不會有連續的加速度數據,所以這是最可行的方法(即實數據與積分數學理論)。

無論如何,即使在最好的情況下,您也會得到非常高的誤差,所以我不建議這種方法適用於任何真正依賴實際速度的應用程序。

+5

如果沒有人注意到,V1 = a * t! – erdomester 2011-09-13 20:58:29

2

積分加速度以獲得速度是一個不穩定的問題,你的錯誤會在幾秒鐘左右發生分歧。手機加速度計也不是很準確,這沒有幫助,有些手機不能很容易地區分傾斜和平移,在這種情況下,您確實遇到了麻煩。

2

手機中的加速度計對於這樣的任務幾乎沒有用處。您需要非常精確的加速度計,漂移極低 - 這遠遠超出了您在手機中所能找到的範圍。充其量,你可能會在幾秒鐘內得到有用的結果,或者如果運氣好一兩分鐘後結果變得毫無意義,那麼結果就會很好。

此外,您需要有一個三軸陀螺儀,您可以使用它來將速度整合到正確的方向。有些手機具有陀螺儀,但就漂移和精度而言,它們甚至比加速度計更差。

一種可能有用的應用程序雖然是使用加速度計與陀螺儀或磁羅盤結合,以填補在用於從所述GPS缺失數據。每次GPS給出了一個很好的修復方法,就會重置位置,速度和方向的初始條件,加速度計將提供數據直到下一次有效的GPS修復。

+0

假設我想獲得控制遊戲的傾斜信息。在這種情況下,我將能夠做出很多假設。例如,我可以假設用戶以某種方式持有該設備。那麼,是否有可能以突發變化突出並變得對輸入有用的方式來平滑數據? – 2013-04-06 23:27:49

4

沒有別的可以做,但與合理的參數在上述所有偉大的答案提出的同意,但是如果你是務實型和我一樣,我需要拿出的作品在某種程度上的解決方案。

我遭遇了類似的問題和你,我決定把我自己的解決方案沒有發現任何上線之後。我只需要一個簡單的「傾斜」輸入來控制遊戲,所以這個解決方案可能不適用於更復雜的需求,但是我決定分享它以防其他人尋找類似的東西。

注:I have pasted my entire code here,並且它是免費的,可以用於任何目的。

基本上我在我的代碼做的是尋找加速度傳感器。如果沒有找到,傾斜反饋將被禁用。如果加速度傳感器存在,我尋找磁場傳感器,如果存在,我通過結合加速度計和磁場數據得到我的傾斜角度是推薦的方式。

public TiltSensor(Context c) { 
    man = (SensorManager) c.getSystemService(Context.SENSOR_SERVICE); 
    mag_sensor = man.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD); 
    acc_sensor = man.getDefaultSensor(Sensor.TYPE_ACCELEROMETER); 
    has_mag = man.registerListener(this, mag_sensor, delay); 
    has_acc = man.registerListener(this, acc_sensor, delay); 
    if (has_acc) { 
     tiltAvailble = true; 
     if (has_mag) { 
      Log.d("TiltCalc", "Using accelerometer + compass."); 
     } 
     else { 
      Log.d("TiltCalc", "Using only accelerometer."); 
     } 
    } 
    else { 
     tiltAvailble = false; 
     Log.d("TiltCalc", "No acceptable hardware found, tilt not available."); 
     //No use in having listeners registered 
     pause(); 
    } 
} 

然而,如果只有加速度傳感器存在,我回落到累加的加速度,被連續衰減(乘以0.99)以除去任何漂移。對於我的簡單傾斜需求,這很有用。

@Override 
public void onSensorChanged(SensorEvent e) { 
    final float[] vals = e.values; 
    final int type = e.sensor.getType(); 
    switch (type) { 
     case (Sensor.TYPE_ACCELEROMETER): { 
      needsRecalc = true; 
      if (!has_mag) { 
       System.arraycopy(accelerometer, 0, old_acc, 0, 3); 
      } 
      System.arraycopy(vals, 0, accelerometer, 0, 3); 
      if (!has_mag) { 
       for (int i = 0; i < 3; i++) { 
        //Accumulate changes 
        final float sensitivity = 0.08f; 
        dampened_acc[i] += (accelerometer[i] - old_acc[i]) * sensitivity; 
        //Even out drift over time 
        dampened_acc[i] *= 0.99; 
       } 
      } 
     } 
      break; 
     case (Sensor.TYPE_MAGNETIC_FIELD): { 
      needsRecalc = true; 
      System.arraycopy(vals, 0, magnetic_field, 0, 3); 
     } 
      break; 
    } 
} 

最後,我只會重複這可能是不以任何方式「正確」的,它只是可以作爲一個簡單的輸入到遊戲中。要使用此代碼,我只需執行類似以下操作(是的魔術常數是不好的mkay):

Ship ship = mShipLayer.getShip(); 
mTiltSensor.getTilt(vals); 
float deltaY = -vals[1] * 2;//1 is the index of the axis we are after 
float offset = ((deltaY - (deltaY/1.5f))); 
if (null != ship) { 
    ship.setOffset(offset); 
} 

Enjoi!

2

重力會破壞你所有的測量。處於靜止狀態的手機正在經歷一個很高的持續向上(是,向上)加速。加速度計無法區分加速度和重力(技術上它們是相同的),所以在幾秒鐘後它會達到極高的速度。 如果你永遠不會傾斜你的加速度計,那麼你可以簡單地從z軸減去常量重力拉(或任一軸向上/向下),但那是不太可能的。

基本上,你必須使用陀螺儀/ magnetometor的一個複雜的系統和加速計來計算重力方向精確然後減去加速度。

+0

傳感器融合可以爲您過濾。只需使用TYPE_LINEAR_ACCELERATION傳感器。 – 2016-06-14 15:22:49