AVR для начинающих. Урок 8. АЦП.

Автор: | 10.08.2016

Урок 8.

Аналого-Цифровой преобразователь — устройство, преобразующее входной аналоговый сигнал в цифровой код. Под аналоговой величиной подразумевается ток, напряжение, сопротивление, емкость, частота, и так далее. На выходе АЦП мы получаем цифровое представление входной величины. Именно благодаря АЦП микроконтроллер может оперировать аналоговыми сигналами.

Однако АЦП микроконтроллера может измерять только напряжение. Поэтому любую другую величину, например ток, перед измерением необходимо преобразовать в напряжение.

Преобразование входного сигнала в численное представление происходит относительно опорного напряжения. Опорное напряжение(Vref) — эталонное напряжение, относительно которого происходит преобразование входной величины. При использовании АЦП микроконтроллера AtMega8, опорное напряжение необходимо подавать на соответствующую ножку контроллера.

Измерение напряжения производится в диапазоне от 0 до Vref.Весь этот диапазон делится в соответствии с разрядностью. То есть если разрядность АЦП — 10 Бит, то диапазон делится на 1023, если 8 бит, то на 255 и так далее. Предполагая, что Vref = 5 Вольтам, при разрядности 10 Бит мы получим шаг измерения 5/1023 = 0.0049 Вольт, а при разрядности 8 бит, шаг измерения станет 5/255 = 0.02 Вольт. То есть, чем меньше разрядность — тем ниже точность преобразования.

Предположим, что мы подаем на вход 10 битного АЦП, c Vref =5 Вольтам, напряжение 3 вольта. На выходе АЦП мы получим численное представление входного напряжения. Легко подсчитать, что шаг измерения равен 0.0049 Вольт, значит, на выходе АЦП мы получим . То есть, для получения значения входного напряжения, необходимо шаг измерения умножить на выходное значение АЦП.

Давайте рассмотрим регистры, отвечающие за конфигурацию АЦП микроконтроллера AtMega8. АЦП в AtMega8 всего один, однако, имеет 8 входных каналов. За выбор входного канала, а так же настройку опорного напряжения отвечает регистр ADMUX.

ADMUX:

  • Биты REFS0-REFS1 отвечают за выбор опорного напряжения.
  • Биты MUX0-MUX3 отвечают за выбор входного канала.
  • Бит ADLAR. Определяет порядок записи результатов преобразования в регистры ADCL и ADCH.
Читайте также  Bluetooth модуль HC-05 для AVR.

АЦП микроконтроллера AtMega8, может работать как в режиме однократного преобразования, так и в режиме непрерывного преобразования (Следующее преобразование начинается сразу после предыдущего). За настройку режима преобразования, прерываний, а так же тактирования АЦП, отвечает регистр ADCSRA.

ADCSRA:

  • Бит ADEN включает и выключает АЦП микроконтроллера.

           ADEN = 1 — АЦП включен.

           ADEN = 0 — АЦП выключен.

  • При записи 1 в бит ADSC, в режиме однократного преобразования запускается преобразование.
  • Бит ADFR, отвечает за выбор режима преобразования.

           ADFR = 1 — Непрерывное преобразование.

           ADFR = 0 — Однократное преобразование.

  • Бит ADIF, флаг окончания преобразования, становится равен 1 при окончании преобразования
  • Бит ADIE, разрешает прерывание АЦП.

           ADIE = 1 — Прерывание разрешено.

           ADIE = 0 — Прерывание запрещено.

  • Биты ADPS0-ADPS2 отвечают за выбор предделителя между частотой тактирования микроконтроллера и АЦП.

Результат преобразования помещается в пару регистров ADCH и ADCL, в виде заданным значением бита ADLAR.

В качестве примера соберем простой вольтметр с применением LCD WH1602, и встроенного АЦП микроконтроллера AtMega8.

Соберем в Proteus следующую схему:

Код прошивки на C:

В результате получаем:

Если у вас ещё остались вопросы на тему использования АЦП микроконтроллера, мы будем рады ответить на них в комментариях!

Читайте также  AVR для начинающих.Урок 0.Знакомство с микроконтроллерами.

До новых уроков!

Другие уроки цикла.


Любое копирование, воспроизведение, цитирование материала, или его частей разрешено только с письменного согласия администрации MKPROG.RU. Незаконное копирование, цитирование, воспроизведение преследуется по закону!

AVR для начинающих. Урок 8. АЦП.: 21 комментарий

  1. Антон

    void Send_Str (char* str,char length)// Отправить строку LCD, длины length
    {
    for (int i = ;i<length;i++)
    {
    Send_Byte(*str);
    str++;
    _delay_us(60);
    }
    }
    при компиляции в AVRStudio 6.2 ругается что i ничему не равно

  2. Сергей

    unsigned int counter;
    for ( counter = 0; counter < length; counter++)
    {
    Send_Byte (*str);
    str++;
    delay_ms (1);
    }

    я на это поменял и все ок

  3. Павел

    Здравствуйте. А если надо измерить напряжение 12-15 вольт, то как это реализовать при помощи atmega8?
    Ведь если правильно понял, то можно измерять до 5 вольт.

    1. DamiKK Автор записи

      Здравствуйте, Павел!
      Я бы использовал простейший делитель напряжения на двух резисторах)

  4. Павел

    Спасибо Вам, DamiKK.
    Подаем мы 15 вольт. Делитель делит и на микроконтроллер подается допустим 5 вольт. А как снятое значение с ножки увеличивается до 15? Да, я читал Ваши объяснения в уроке про биты и шаги измерения. Но так и не смог пристроить объяснения к своему вопросу. Хотя получается что надо снятое значение умножить на 3. Объясните, пожалуйста. Желательно с куском кода, обрабатывающем эту операцию)

    1. DamiKK Автор записи

      На делитель напряжения подается 12-15в,с него снимается пропорциональное входному напряжение.
      Допустим при номиналах 1кОм,470Ом, если на входе 12вольт, то на выходе примерно 3.85в.При подаче 15в, на выходе будет почти 5 вольт. А это уже напряжение которое можно подать на АЦП.
      Думаю, все понятно?

  5. Павел

    Спасибо. Понятно. Но я ведь спросил о том, как эти самые 3.58в. внутри кристалла увеличиваются до 12в. для дальнейшего вывода на экран. Какой участок кода за это отвечает?

    1. DamiKK Автор записи

      Просто умножайте коэффицент делителя напряжения на значение полученное АЦП.Если я Вас правильно понял.

  6. Павел

    Понятно. Спасибо. У меня еще вопрос. При симуляции в протеусе вместо U=2.50V показывает U=?V. Не могу понять в чем дело.

      1. DamiKK Автор записи

        Ошибки в схеме или свойствах компонентов

  7. Павел

    Схему проверил. А вот по свойствам не знаю. Атмга — 8 МГц. Кристалл так же. Питание везде 5v. LCD не трогал. Переменный — LOG и 10 кОм. Единственное различие которое нашел, так это XTAL1 и XTAL2 у меня синие при симуляции, а у Вас красные.

  8. Сергей

    Какая=то проблема в функции «sprintf(buffer,»U=%.2f V»,Voltage);»
    Выводит на дисплей «U=? V» при любом раскладе

    1. DamiKK Автор записи

      Здравствуйте,Сергей!
      Необходимо настроить среду разработки. Как это сделать, смотрите в гугле по запросу «Atmel Studio sprintf float»

  9. Алан

    Добрый день! А если я вместо ATMEGA8 возьму ATMEGA16 в корпусе DIP-40, что нужно будет переписывать в коде?

    1. DamiKK Автор записи

      Здравствуйте!
      Сверьте регистры микроконтроллеров, и расположение выводов. Тогда все станет понятно)
      Если нет, пишите.

  10. Егор

    for (int i = 0;i<length;i++)
    в этом цикле выдает ошибку,в чем может быть проблема?
    В AVR studio

    1. Егор

      Error 2 ‘for’ loop initial declarations are only allowed in C99 mode
      Вот такая вот ошибка.
      Или это можно как то включить?

      1. DamiKK Автор записи

        Объявите переменную i до начала исполняемого кода прошивки.
        То есть в самом начале функции или программы.

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *