3

我有一个代码片段来检测加速度计的运动。它有时会通过正确检测轻微运动来工作,但有时它也会在我让设备闲置时检测到运动。Android 上的内置加速度计检测是否存在任何问题?

我使用 HTC G-1 设备。我的代码片段如下。我该如何解决它,以便我可以检测到小的设备移动,但在设备空闲时检测不到任何东西?

private static final int SHAKE_THRESHOLD = 50;

public void onSensorChanged(int sensor, float[] values) {

    if (sensor == SensorManager.SENSOR_ACCELEROMETER) {
        long curTime = System.currentTimeMillis();
        // only allow one update every 100ms.
        if ((curTime - lastUpdate) > 100) {
            long diffTime = (curTime - lastUpdate);
            lastUpdate = curTime;

            x = values[SensorManager.DATA_X];
            y = values[SensorManager.DATA_Y];
            z = values[SensorManager.DATA_Z];

            float speed = Math.abs(x+y+z - last_x - last_y - last_z) / diffTime * 10000;

            if (speed > SHAKE_THRESHOLD) { 
                long curTime = System.currentTimeMillis();
                long diff = (curTime - shakeTime);              
                shakeTime = curTime;

                if (myFlagIgnoreShakeDetection==true)  //Caused unneccessary accelerometer   
                                                       //notification looping when device is idle
                   return;

                // Doing something...
            }
         last_x = x;
         last_y = y;
         last_z = z;
        }

    }

}
4

2 回答 2

1

这里有一些代码差异......

  • last_xlast_y和的更新可能存在问题last_z。我认为它们应该包含if ((curTime - lastUpdate) > 100) {声明中。换句话说,每次onSensorChanged调用它们都会更新它们,而不是每 100 毫秒。您可能应该将这三个变量的更新移动到它们上方的花括号中。

  • 在您计算 的那一行speed,公式以... / diffTime * 10000;您想要乘以diffTime10000 还是整个结果结束?由于/并且*通常在我所知道的大多数语言(例如Java )中具有相同的运算符优先级,因此您的等式将从左到右进行评估,首先除以然后将该结果乘以 10000。diffTime

    我猜你的意思是乘以diffTime10000,从而最终结果除以该数量。这是除以 10000 或乘以 10000 之间的差异,这意味着您可能得到的值speed比您应该得到的值大 10^8,因此即使在设备空闲时也会触发您的阈值。您需要在乘法周围加上括号,例如... / (diffTime * 10000);,以确保在除法之前执行它。

    此外,如果您打算diffTime从毫秒扩展到秒,您的比例因子应该是 1000。

于 2009-10-27T14:12:46.163 回答
0

我个人在我的增强现实库中使用滚动平均值进行更新:

float kFilteringFactor = (float)0.05;    
rollingZ = (float) ((rawZValue * kFilteringFactor) + (rollingZ * (1.0 - kFilteringFactor)));

这往往可以很好地平滑数据,您可以调整过滤因子以获得所需的响应能力。

rawZValue 是来自加速度计的原始值。

于 2009-10-27T21:51:52.063 回答