Дополнительный фильтр Гироскопический акселерометр

Я использую дополнительный фильтр для гироскопа и акселерометра только для азимута... Я получил его с этого сайта: http://www.thousand-thoughts.com/2012/03/android-sensor-fusion-tutorial/1/

ядро фильтра:

         /*
         * Fix for 179° <--> -179° transition problem:
         * Check whether one of the two orientation angles (gyro or accMag) is negative while the other one is positive.
         * If so, add 360° (2 * math.PI) to the negative value, perform the sensor fusion, and remove the 360° from the result
         * if it is greater than 180°. This stabilizes the output in positive-to-negative-transition cases.
         */

        // azimuth
        if (gyroOrientation[0] < -0.5 * Math.PI && accMagOrientation[0] > 0.0) {
            fusedOrientation[0] = (float) (FILTER_COEFFICIENT * (gyroOrientation[0] + 2.0 * Math.PI) + oneMinusCoeff * accMagOrientation[0]);
            fusedOrientation[0] -= (fusedOrientation[0] > Math.PI) ? 2.0 * Math.PI : 0;
            Log.d("test","gyro Is Negative");
        }
        else if (accMagOrientation[0] < -0.5 * Math.PI && gyroOrientation[0] > 0.0) {
            fusedOrientation[0] = (float) (FILTER_COEFFICIENT * gyroOrientation[0] + oneMinusCoeff * (accMagOrientation[0] + 2.0 * Math.PI));
            fusedOrientation[0] -= (fusedOrientation[0] > Math.PI)? 2.0 * Math.PI : 0;
            Log.d("test","accel Is Negative");

        }
        else {
            fusedOrientation[0] = FILTER_COEFFICIENT * gyroOrientation[0] + oneMinusCoeff * accMagOrientation[0];
        }
        gyroMatrix = getRotationMatrixFromOrientation(fusedOrientation);
        System.arraycopy(fusedOrientation, 0, gyroOrientation, 0, 3);

Я хочу сравнить это с реальными данными гироскопа, которые имеют дрейф... для этого я использовал gyroOreintationReal... и добавил несколько кодов для сохранения gyroOreintation, например:

 if(initState) {
        float[] initMatrix = new float[9];
        initMatrix = getRotationMatrixFromOrientation(accMagOrientation);
        float[] test = new float[3];
        SensorManager.getOrientation(initMatrix, test);
        gyroMatrix = matrixMultiplication(gyroMatrix, initMatrix);
        gyroMatrixReal = matrixMultiplication(gyroMatrixReal, initMatrix);

        initState = false;
    }

    // copy the new gyro values into the gyro array
    // convert the raw gyro data into a rotation vector
    float[] deltaVector = new float[4];
    float[] deltaVectorReal = new float[4];

    if(timestamp != 0) {
        final float dT = (event.timestamp - timestamp) * NS2S;


    System.arraycopy(event.values, 0, gyro, 0, 3);
    System.arraycopy(event.values, 0, gyroReal, 0, 3);


    getRotationVectorFromGyro(gyro, deltaVector, dT / 2.0f);
    getRotationVectorFromGyro(gyroReal, deltaVectorReal, dT / 2.0f);

    }

    // measurement done, save current time for next interval
    timestamp = event.timestamp;

    // convert rotation vector into rotation matrix
    float[] deltaMatrix = new float[9];
    float[] deltaMatrixReal = new float[9];

    SensorManager.getRotationMatrixFromVector(deltaMatrix, deltaVector);
    SensorManager.getRotationMatrixFromVector(deltaMatrixReal, deltaVectorReal);


    // apply the new rotation interval on the gyroscope based rotation matrix
    gyroMatrix = matrixMultiplication(gyroMatrix, deltaMatrix);
    gyroMatrixReal = matrixMultiplication(gyroMatrixReal, deltaMatrixReal);


    // get the gyroscope based orientation from the rotation matrix
    SensorManager.getOrientation(gyroMatrix, gyroOrientation);
    SensorManager.getOrientation(gyroMatrixReal, gyroOrientationReal);     

и я сохранил результат и построил их с помощью Matlab ... но график показывает, что ориентация гироскопа отрицательна ... но fusedOreientation меньше +150, а ориентация ускорения чуть больше +150 ...

как можно решить проблему?? Я добавляю несколько кодов в ядро ​​дополнительного фильтра:

//RealGyro
       if (gyroOrientationReal[0] < -0.5 * Math.PI && accMagOrientation[0] > 0.0) {
            gyroOrientationReal[0] =  (float) (gyroOrientation[0] + 2.0 * Math.PI);
            gyroOrientationReal[0] -= (gyroOrientationReal[0] > Math.PI) ? 2.0 * Math.PI : 0;
       }        

иногда это нормально, но я не знаю, что мне делать, если у меня отрицательные данные ускорения и положительные данные гироскопа?


person soodabeh    schedule 06.01.2015    source источник


Ответы (2)


когда я попытался повернуть телефон на 360 градусов. Я получил этот график от Matlab: http://www.uppic.com/uploads/14205374821.jpg

зеленый — для гироскопа, красный — для объединенной ориентации, а синий — для ускорения.

  • почему время Джайро сместилось?? причина в дрейфе?? сюжет правильный?
  • как я могу использовать период 0-360 вместо 0_180 и -180_0?
person soodabeh    schedule 06.01.2015
comment
попробуйте это для периода 0-360 if (fusedAzimuth ‹ 0) { fusedAzimuth = (360 - Math.abs(fusedAzimuth)); } - person Xäiñ Ul Abideen; 29.01.2019

Ссылка на изображение, которое вы разместили, не работает, поэтому я не мог проверить сюжет из матлаба. Дрейф гироскопа не добавляет к данным смещения по времени. Возможно, смещение вызвано какой-то внутренней задержкой (маловероятно) или, что более вероятно, задержкой в ​​алгоритме. Я не могу точно сказать, потому что не вижу, насколько велико смещение по времени.

Если вам нужны только данные гироскопа, часть, которую вы добавили к дополнительному фильтру, не нужна. Все данные гироскопа уже должны быть в векторе gyroOrientationReal. Дальнейшая обработка не требуется. На реальные данные гироскопа не должно влиять accMagOrientation (что вы делаете, изменяя gyroOrientationReal, если accMagOrientation[0] > 0.0.

Если вы хотите перейти от периода [0, 360] к периоду [0, 180, -180, 0], вам просто нужно вычесть 180 из вашего результата, и все готово.

Я надеюсь, что смог помочь вам с этим.

person pLaw    schedule 13.01.2015