Почему мои акселерометры реагируют так медленно? - PullRequest
1 голос
/ 11 мая 2009

Я спрашиваю их с частотой 50 Гц / 50 раз в секунду для данных. Когда я неожиданно переворачиваю устройство на оси x на 90 градусов, пока устройство было плоским на столе с дисплеем, обращенным вверх, значения довольно медленно перемещаются к «целевому» значению для этой позиции.

Теперь странная вещь: если я увеличу скорость измерения, значение переместится быстрее к этому новому значению после внезапного переворачивания устройства на 90 градусов. Но если я просто спрашиваю раз в секунду новое значение, это займет очень много времени, пока значение не достигнет цели. Что может быть причиной этого?

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

- (void)accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration {
    // Use a basic low-pass filter to only keep the gravity in the accelerometer values for the X and Y axes
    // accelerationX is an instance variable
    accelerationX = acceleration.x * 0.05 + accelerationX * (1.0 - 0.05);

    // round
    int i = accelerationX * 100;
    float clippedAccelerationValue = i;
    clippedAccelerationValue /= 100;

    [self moveViews:clippedAccelerationValue];
}

позже, в моем -moveViews: метод, я делаю это:

-(IBAction)moveSceneForPseudo3D:(float)accelerationValue {
    if(fabs(lastAccelerationValue - accelerationValue) > 0.02) { // some little treshold to prevent flickering when it lays on a table
        float viewAccelerationOffset = accelerationValue * 19 * -1;

        newXPos = initialViewOrigin + viewAccelerationOffset;
        myView.frame = CGRectMake(newXPos, myView.frame.origin.y, myView.frame.size.width, myView.frame.size.height);

        lastAccelerationValue = accelerationValue;
    }
}

В результате устройство поворачивается на 90 градусов по оси x, или на 180 градусов, вид довольно медленно перемещается к своей целевой позиции. Я не знаю, связано ли это с физикой акселерометров, или это ошибка в моем фильтрующем коде. Я знаю только, что есть игры с быстрым темпом, в которых акселерометры используются для рулевого управления, поэтому я почти не могу представить, что это аппаратная проблема.

1 Ответ

8 голосов
/ 11 мая 2009

Эта строка:

accelerationX = acceleration.x * 0.05 + accelerationX * (1.0 - 0.05);

- это фильтр нижних частот, который работает путем вычисления скользящего среднего значения x-ускорения. Другими словами, каждый раз, когда вызывается обратный вызов, вы только перемещаете accelerationX на 5% к новому значению акселерометра. Вот почему требуется много итераций, прежде чем accelerationX отражает новую ориентацию.

Что вам нужно сделать, это увеличить значение 0.05, скажем 0.2. Я бы сделал глобальный #define и поиграл бы с разными значениями вместе с разными частотами обновления.

...