Акселерометр: как вычислить угол наклона

Тема в разделе "Схемотехника, компоненты, модули", создана пользователем egordorichev, 8 окт 2015.

Метки:
  1. egordorichev

    egordorichev Гик

    Здравствуйте! На вики написано:

    А как вычислить крен? Спасибо!
     
  2. DrProg

    DrProg Вечный нерд

    Тоже скоро буду озабочен этим вопросом. Нужно будет сделать пульт управления работающий по наклону. Пока что первые результаты поиска такие.
     
    ИгорьК нравится это.
  3. geher

    geher Гуру

    Смотря для чего нужен крен.
    Если не заморачиваться особой точностью при управлении, например, моделью машины, то можно использовать значения на осях X и Y, считая за нулевое положение осью z вверх.
    Получается примерно следующее (map использован для приведения показаний акселерометра к диапазону аналогового джойстика, смещенному на -512):
    Код (Text):

      signed int speed=map((int)accel.readY_G()*10,-100,100,-512,511);
      signed int rotate = map((int)accel.readX_G()*10,-100,100,-512,511);
     
    Для того, чтобы система не дергалась на каждое небольшое качание пульта, можно передавать сигнал, только если они существенно изменились (на какое-то подобранное значение). Кроме того, чтобы при лежащем на столе ПДУ все было в нуле, нужно показания в определенной области возле нуля считать нулевыми.
    Код (Text):

      if (abs(speed)<STOPZONE) speed=0;
      if (abs(rotate)<STOPZONE) rotate=0;
      if ((abs(speed-oldspeed)>=SPEED_QUANT)||
          ((abs(rotate-rotate)>=ROTATE_QUANT))
      {
          Передаем управляющую команду.
      }
     
    При этом speed характеризует крен по оси Y, а rotate - по оси X.

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

    Во-вторых, возможно, придется более точно оценивать крен, задействовав геометрию. Вычисления простые.
    В нулевом положении вектор силы тяжести направлен строго вниз по оси Z, соответственно, значение на оси Z будет равно силе тяжести, а по остальным осям будет 0.
    При крене, будет проекция этого вектора на все оси, которую мы и считаем с акселерометра.
    В результате получим катеты углов между вектором и осями. Гипотенузой будет значение вектора силы тяжести по оси Z в покое. Дальше считаем синус (или косинус) и функцией арксинус (арккосинус соответственно) получаем угол.

    Кроме того, наверное, хорошо будет компенсировать погрешности показаний акселерометра, возникающие от его движения, за счет учета показаний гироскопа (это отдельная история, тут я ничего не подскажу).
     
    Arc-dc и egordorichev нравится это.
  4. vvr

    vvr Инженерище

    если захочется хоть какой то точности придётся прилепить и гироскоп и компас