Уроки arduino: регулятор громкости с кнопками управления

Как подключить регулятор громкости M62429 к Arduino

Микросхема M62429 предназначена для снижения громкости звука в электрических схемах. Микросхема позволяет управлять одновременно и независимо двумя звуковыми каналами. Диапазон регулировки звука – от 0 до −83 дБ, т.е. микросхема способна ослаблять уровень громкости примерно в 100000 раз.

Нам понадобятся:

1Описание регулятора громкостиM62429

Микросхема M62429 выполняется в двух типах корпусов – DIP-8 (8P4) и SOP-8 (8P2S-A). Назначение выводов для обоих типов корпусов приведена на рисунке. Как видно, тут имеется два входа (VIN1, VIN2) и два выхода (VOUT1, VOUT2) для звуковых каналов, питание и земля (VCC и GND), а также две управляющие ножки (DATA и CLOCK).

Питание микросхемы осуществляется напряжением от 4,5 до 5,5 В (абсолютный максимум – 6 вольт).

Расположение выводов на микросхеме M62429

Вот так выглядит микросхема в выводном корпусе:

Микросхеме M62429 в DIP-корпусе

У меня микросхема в корпусе для поверхностного монтажа. К такой микросхеме сложно подключиться без пайки, поэтому для тестирования я буду использовать вот такой переходник с корпуса SOP-8 на соединители типа PLS:

Микросхема M62429 на плате-переходнике

2Схема подключения микросхемы M62429 к Arduino

Подключим микросхему к Arduino и к микрофону вот по такой схеме:

Схема подключения M62429 к Arduino

Производитель рекомендует стабилизировать вход питания VCC с помощью развязывающего конденсатора (соединить вход питания с землёй через ёмкость 0,1…0,33 мкФ).

Также производитель рекомендует поставить на вход электролитический конденсатор ёмкостью 2,2 мкФ (схему см. на последней странице технического описания).

Микрофон и динамик на схеме изображены условно просто чтобы показать, что на вход VIN1 микросхемы M62429 подаётся выход с микрофона или иного источника аудиосигнала, а выход – далее в электрическую цепь и на устройство воспроизведения звука.

3Описание последовательного сигнала управления регулятором громкости M62429

Для управления микросхемой M62429 используется последовательный интерфейс с пакетной передачей данных. Длина одного пакета данных – 11 бит. Структура пакета приведена на рисунке.

Структура пакета управления микросхемой M62429

Первым битом передаётся номер канала, вторым – использовать ли независимое управление каналами или одновременное, далее 7 бит отведены под код громкости, и завершают пакет два бита, равные “1”.

Важно знать параметры импульсов частоты и данных. Микросхема управляется меандром (скважность равна 2), минимальная длительность импульса tWHC (как и tWLC) – 1,6 мкс, а период tcr – 4 мкс. Остальные характеристики импульсов приводятся в техническом описании (datasheet), которое можно скачать по ссылкам ниже.

Временная диаграмма сигнала информационного обмена с микросхемой M62429

4Скетч для управления микросхемой M62429 с помощью Arduino

Зная всё это, напишем скетч, который будет изменять громкость регулятора от максимума до минимума со скоростью 1 децибел в секунду. Сердце программы – процедура setVolume() и два массива кодов громкости, которые составлены из двух таблиц кодов громкости в техническом описании (таблицы “Volume Code”).

Замечу, что в децибелах задавать ослабление громкости не всегда удобно. Можно сделать процедуру, принимающую, допустим, уровень громкости. Типа такого: setVolumeInPercent(0, true, 35), где 0 – второй канал, true говорит о независимом управлении каналами, а 35 – уровень громкости в процентах от максимального (или же наоборот – уровень ослабления аттенюатора).

Загрузим скетч в память Arduino и посмотрим на результат. Я подключил осциллограф к каналам CLOCK и DATA для демонстрации.

Осциллограмма информационного обмена Arduino с микросхемой M62429

Фиолетовый сигнал – CLOCK, зелёный – DATA.

Осциллограмма информационного обмена Arduino с микросхемой M62429

А вот как выглядит осциллограмма напряжения на выходе VOUT1 микросхемы M62429.

Изменение напряжения на выходе микросхемы M62429

Скачать техническое описание на микросхему M62429

Управление регулятором громкости M62429

Источник: https://soltau.ru/index.php/arduino/item/497-kak-podklyuchit-regulyator-gromkosti-m62429-k-arduino

Урок 55. Работа с инкрементальным энкодером в Ардуино. Библиотека Encod_er.h

В уроке расскажу о принципе действия инкрементального энкодера, о подключении его к плате Ардуино. Покажу способ программной обработки сигналов энкодера и представлю библиотеку для работы с ним.

Предыдущий урок     Список уроков     Следующий урок

Мне заказали разработку программы для устройства, в котором в качестве управляющего элемента используется инкрементальный энкодер. Поэтому я решил написать внеплановый урок о работе с энкодером в системе Ардуино.

Совсем коротко, о чем идет речь, т.е. о классификации энкодеров.

Энкодеры это цифровые датчики угла поворота. Другими словами преобразователи угол-код.

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

Энкодеры бывают абсолютные и накапливающие (инкрементальные).

Абсолютные энкодеры формируют на выходе код, соответствующий текущему углу положения вала. У них нет памяти. Можно выключить устройство, повернуть вал энкодера, включить и на выходе будет новый код, показывающий новое положение вала. Такие энкодеры сложные, дорогие, часто используют для подключения стандартные цифровые интерфейсы RS-485 и им подобные.

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

Но в большинстве случаев нет необходимости знать абсолютное значение текущего угла. Если мы энкодером, например,  регулируем уровень громкости, то нам надо увеличить ее на несколько градаций или уменьшить.

Мы не смотрим на ручку энкодера, на ней нет шкалы. Нам необходимо определить изменение угла относительно текущего положения. То же самое касается установки параметров на дисплее.

Мы крутим ручку энкодера и смотрим, как изменяется значение параметра на экране дисплея.

В подобных случаях инкрементальные энкодеры становятся идеальными устройствами управления, установки параметров, выбора меню. Они намного удобнее, чем кнопки ”+” и ”-”.

В этих случаях можно использовать самые простые механические инкрементальные энкодеры, которые отличаются низкой ценой.

По моей партнерской ссылке механический инкрементальный энкодер с кнопкой EC11 стоит всего 50 руб. При покупке 5 штук 45 руб., при 10 – 40 руб.

Принцип действия механического инкрементального энкодера.

Импульсы на выходе инкрементального энкодера должны сообщать не только о повороте вала, но и о направлении поворота. Поэтому необходимо использовать 2 сигнала, которые обычно обозначаются A и B. Эти сигналы подключены к механическим контактам энкодера, другие выводы которых соединены на выводе C.

Если подключить к сигналам A и B подтягивающие резисторы, то диаграмма выходных сигналов при вращении энкодера будет выглядеть так.

Если вы покрутите вал энкодера, то заметите, что у него есть фиксированные положения. У моего энкодера 20 таких положений на оборот. Т.е. точность определения угла 360° / 20 = 18° или 20 импульсов на оборот.

Эти, механически зафиксированные, положения отмечены на диаграмме стрелочками снизу вверх. В этот момент оба контакта разомкнуты, сигналы A и B находятся в высоком уровне.

На первых 2 отрезках диаграммы энкодер повернули по часовой стрелке. Сначала в низкий уровень упал сигнал A, затем B. На 3 и 4 интервалах вал вращают против часовой стрелки. После фиксированного положения сначала становится равным нулю сигнал B. По последовательности изменения сигналов можно определить, в какую сторону повернули энкодер.

Формализованный алгоритм анализа сигналов энкодера выглядит так.

  • Если в момент перехода сигнала A в низкое состояние сигнал B находится в высоком уровне, то произошел поворот по часовой стрелке.
  • Если в момент перехода сигнала A в низкое состояние сигнал B находится в низком уровне, то был поворот против часовой стрелки.

Возможны другие кодировки положения энкодера. Все, что я пишу верно, относительно EC11.

Параметры инкрементальных энкодеров.

Подробно технические характеристики и параметры энкодера EC11 в формате PDF можно посмотреть по этой ссылке EC11.pdf. Я приведу и поясню основные.

  • Главный параметр – число импульсов на оборот. Определяет точность измерения угла. У моего датчика 20 импульсов на оборот, точность 18°.
  • Предельно допустимые электрические параметры определяют предельные значения тока и напряжения для контактов. В моем случае это 10 мА и 5 В. Эти параметры влияют на выбор подтягивающих резисторов. Сопротивление резисторов не должно быть ниже 500 Ом.
  • Прочность изоляции. Я бы не рискнул использовать подобный энкодер в цепях, гальванически связанных с высоким напряжением.
  • Износоустойчивость. Разработчики гарантируют от 15 000 до 1 000 000 циклов, в зависимости от модификации.
  • Рабочий диапазон температур -30 … +85 °C.
  • Механические параметры: габаритные и установочные размеры, моменты вращения и т.п.
Читайте также:  Покупка нового смартфона cubot s550 на aliexpress.com - arduino+

Подключение энкодера к плате Ардуино.

С электрической точки зрения энкодер это 3 кнопки: сигналы A, B и кнопка. Я использовал внутренние подтягивающие резисторы, но в рабочих схемах лучше добавить внешние резисторы сопротивлением 2 – 10 кОм.

Программная обработка сигналов энкодера.

Сначала приведу простую программу, позволяющую определить кодировку энкодера.

void setup() {
  Serial.

begin(9600); // инициализируем порт, скорость 9600
  pinMode(2, INPUT_PULLUP); // определяем вывод как вход
  pinMode(8, INPUT_PULLUP); // определяем вывод как вход
}
void loop() {
  if( digitalRead(2) == HIGH ) Serial.print(“H “);
  else Serial.print(“L “);
  if( digitalRead(8) == HIGH ) Serial.println(“H”);
  else Serial.println(“L”);
  delay(200);
}

У меня энкодер подключен к выводам 2 и 8. Программа в цикле выводит через последовательный порт состояния сигналов A и B.

Если я плавно вращаю вал по часовой стрелке у меня монитор последовательного порта выводит:
HH -> LH -> LL -> HL -> HH

При вращении  против часовой стрелки:
HH -> HL -> LL -> LH -> HH

Все как на диаграмме выше.

Алгоритм обработки сигналов энкодера простой:

  • выделяем отрицательный фронт сигнала A;
  • считываем состояние сигнала B;
  • если у сигнала B:
    • высокий уровень – был поворот по часовой стрелке;
    • низкий  уровень – был поворот против часовой стрелки.

Но у механического энкодера механические контакты. Им свойственно явление дребезга. К тому же энкодеры часто устанавливаю на передней панели устройства, и подключают к контроллеру достаточно длинными проводами. Т.е. нужна цифровая фильтрация сигналов и устранение дребезга. Все это реализовано в моей библиотеке Button.h. Ее вполне можно использовать для работы с энкодером.

Ну и самая главная мысль в каждом моем уроке. Давайте сделаем обработку энкодера параллельным процессом. Программа в основном цикле занимается своими задачами, а параллельный процесс обрабатывает сигналы энкодера в прерывании по таймеру.

#include
#include<\p>

Button encoderA (2, 4); // сигнал A
Button encoderB (8, 4); //  сигнал B
Button encoderButton(10, 40); // кнопка

long pos=0; // пооложение энкодера

void setup() {
  Serial.

begin(9600); // инициализируем порт, скорость 9600
  Timer1.initialize(250); // инициализация таймера 1, период 250 мкс
  Timer1.attachInterrupt(timerInterrupt, 250); // задаем обработчик прерываний
}

void loop() {
// сброс положения 
  if( encoderButton.flagClick == true ) {
    encoderButton.flagClick= false;
    pos= 0;
  }
  Serial.println(pos); // вывод положения
}

// обработчик прерывания 250 мкс
void timerInterrupt() {
  encoderA.filterAvarage(); // вызов метода фильтрации
  encoderB.filterAvarage(); // вызов метода фильтрации 
  encoderButton.filterAvarage(); // вызов метода фильтрации

// обработка сигналов энкодера
  if( encoderA.flagClick == true ) {
    encoderA.flagClick= false;
      if( encoderB.flagPress == true) {
        // против часовой стрелки
        pos–;
      }
      else {
        // по часовой стрелке
        pos++;
      }
  }
}

В прерывании по таймеру программа обрабатывает сигналы энкодера и вычисляет его абсолютный угол.  В основном цикле выводит текущее положение вала в монитор последовательного порта. При нажатии на кнопку сбрасывает текущее положение в 0. По сути, мы сделали абсолютный энкодер, только до момента выключения питания.

Вопрос, с какой частотой необходимо опрашивать энкодер. У меня в программе цикл прерывания 250 мкс и 4 выборки при фильтрации. В итоге период реакции на изменения состояния сигналов 1 мс.

Все зависит от того с какой частотой сигналы энкодера могут изменять свое состояние. А это определяют максимальная скорость вращения энкодера и параметр – число импульсов на оборот.

Если вы сделаете период опроса больше, например, несколько миллисекунд, то увидите в окне монитора порта, что импульсы пропускаются при резком повороте. Все это вы можете посчитать сами. Но я бы рекомендовал в итоге проверить работу энкодера на этой программе.

  • Запомнить механическое положение вала.
  • Сбросить вычисленное положение кнопкой (привязать к механическому положению).
  • Теперь сколько бы вы ни вращали вал, при попадании в механическое положение, к которому он был привязан, на экране должно быть значение кратное числу импульсов на оборот. В моем случае это 0,20, 40…

Библиотека Encod_er.h.

Представленный выше способ обработки энкодера вполне имеет право на жизнь. Но в моей задаче надо было определять, с какой скоростью вращают энкодер.

Энкодером перемещался шпиндель сверлильного станка. С одной стороны нужна была высокая точность позиционирования.  С другой – приходилось долго крутить ручку, чтобы переместить шпиндель в нижнее положение.

Решили при медленном вращении энкодера перемещать шпиндель по одному шагу, а при увеличении скорости вращения – увеличивать число шагов перемещения шпинделя на каждый шаг энкодера. Т.е. если медленно крутить энкодер, то шпиндель перемещается точно и медленно. При быстром вращении – шпиндель перемещается быстро.

Для реализации этого алгоритма необходимо вычислять скорость вращения энкодера. Я разработал библиотеку обработки энкодера с этой функцией.

Загрузить библиотеку Encod_er.h можно по этой ссылке:

 Зарегистрируйтесь и оплатите. Всего 25 руб. в месяц за доступ ко всем ресурсам сайта! 

Описание класса Encod_er.

Я привел только public свойства и методы.

class Encod_er {
  public:
    Encod_er(byte pinA, byte pinB, byte timeFilter);
    byte timeRight; // время/признак вращения вправо (* 8 периодов)
    byte timeLeft; // время/признак вращения влево (* 8 периодов)
    long position; // текущее положение 
    void scanState(); // метод проверки состояния
    long read(); // метод чтения положения 
};

Encod_er(byte pinA, byte pinB, byte timeFilter)  – конструктор.

  • pinA – вывод сигнала A;
  • pinB – вывод сигнала B;
  • timeFilter – число выборок фильтрации сигналов.

Encod_er myEncoder(2, 3, 5);   // энкодер к выводам 2 и 3, 5 выборок фильтрации

void  scanState() – метод сканирования состояния энкодера. Должен вызываться регулярно в параллельном процессе.

// обработчик прерывания 250 мкс
void timerInterrupt() {
  myEncoder.scanState();
}

byte timeRight и timeLeft – признаки поворота энкодера соответственно вправо и влево. Если равны 0, то поворота не было. Если не равны 0, то содержат время поворота на один шаг. Время вычисляется, как

Tповорота = Tвызова scanState()  * 8 * timeRight.

Т.е. единица значения timeRight или timeLeft это период вызова scanState(),  умноженный на 8. В моей программе это 250 мкс * 8 = 2 мс. На 8 я умножил, чтобы использовать один байт. Значение переменных  timeRight или timeLeft ограничиваются на уровне 255.

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

if(encoder.timeRight != 0) {
  encoder.timeRight= 0;
………..
}

long  position – текущее положение энкодера. Может быть прочитано или записано.

long  read() – метод чтения положения энкодера. Возвращает переменную position.

Все просто. Предыдущую программу можно переписать с использованием библиотеки Encod_er.h.

Читайте также:  Уроки ардуино: измеряем скорость вращения спинера

#include
#include<\p>

Encod_er encoder( 2, 8, 4);

void setup() {
  Serial.

begin(9600); // инициализируем порт, скорость 9600
  Timer1.initialize(250); // инициализация таймера 1, период 250 мкс
  Timer1.attachInterrupt(timerInterrupt, 250); // задаем обработчик прерываний
}

void loop() {
  if(encoder.timeRight != 0) {
    Serial.print(“R=”);
    Serial.print(encoder.timeRight);
    Serial.print(” Pos=”);
    Serial.println(encoder.read()); // вывод текущего положения 
    encoder.

timeRight= 0;
  }
  if(encoder.timeLeft != 0) {
    Serial.print(“L=”);
    Serial.print(encoder.timeLeft);
    Serial.print(” Pos=”);
    Serial.println(encoder.read()); // вывод текущего положения
    encoder.

timeLeft= 0;
  }
}

// обработчик прерывания 250 мкс
void timerInterrupt() {
  encoder.scanState();
}

На каждый поворот вала в монитор последовательного порта выводится направление вращение и значение timeRight или timeLeft.

Обработку кнопки энкодера я в библиотеку не включил. Кнопку лучше обрабатывать библиотекой Button.h.

С помощью этой библиотеки я реализовал управление перемещением шпинделя сверлильного станка по описанному выше алгоритму.

Анализировал признаки timeRight и timeLeft. При ненулевом значении признаков шаговый двигатель перемещения шпинделя делал количество шагов в зависимости от значения активного признака. Зависимость задал в массиве.

Предыдущий урок     Список уроков     Следующий урок

Источник: http://mypractic.ru/urok-55-rabota-s-inkrementalnym-enkoderom-v-arduino-biblioteka-encod_er-h.html

Медиа энкодер на ARDUINO MICRO

   Здесь я хочу вам рассказать как управлять громкостью и музыкой при помощи Поворотного энкодера (иначе – датчик угла поворота), это устройство, преобразующее угол поворота вращающегося объекта (вала) в электрические сигналы, позволяющие определить этот угол.

Будет работать и на Windows и на Android Здесь я хочу вам рассказать как управлять громкостью и музыкой при помощи Поворотного энкодера (иначе – датчик угла поворота), это устройство, преобразующее угол поворота вращающегося объекта (вала) в электрические сигналы, позволяющие определить этот угол.

Сейчас вам я не буду объяснять принцип действия энкодера, благо в интернете огромное количество информации и если интересен прнцип действия можете прочтать. Перейдём напрямую к поставленной задаче. А именно управлять мультимедиа функциями компьютера или планшета.

 Видео версия, медиа энкодер на Arduino Micro

Как и в прошлом уроке про рулевое управлерие планшетом, для начала нам необходимо приобрести плату Arduino Leonadro или ArduinoMicro, главное отличие этих контроллеров в том что на них установлены микропроцессоры Atmega32u4 которая имеет на борту встроенную поддержку USB-соединения, благодаря чему не требуется вспомогательный процессор. Это позволяет устройствам на Atmega32u4 появляться на подключенном планшете (с поддержкой OTG) или компьютере в качестве мыши или клавиатуры в дополнение к виртуальному (CDC) последовательному порту (COM). В общем подойдет любой arduino совместимый контроллер который построен на Atmega32u4. + нам ещё потребуется сам повортный энкодер его можете приобрести на алиэкспресс.

Вторым шагом после того как приобрели необходимый вам контроллер необходимо скачать ArduinoIDE и установить для того чтобы установились драйвера, затем чтобы работали все функции скачайте подготовленную мной портативную версию ArduinoIDE вот ЗДЕСЬ, в этот архив уже добавлены все необходимые библиотеки и изменены файлы для работы в качестве медиа клавиатуры.

Подключение максимально простое, потребуется всего 5 проводков, и необходимо их соеденить следующим образом.

энкодер GND – GND arduino Microэнкодер 5v – 5v arduino Microэнкодер SW – D8 arduino Microэнкодер DT – D10 arduino Microэнкодер SLK – D9 arduino MicroВыводы SW, DT, SLK можете поменять на свои какие угодно в скетче. 

 Далее расписаны команды для управления мультимедиа функциями.

Remote.next();             //следующая песняRemote.previous();       //предыдущая песняRemote.play_pause();   //плей и паузуRemote.increase();       //громкость прибавитьRemote.decrease();      //громкость убавитьRemote.mute();            //Убрать звукRemote.play();             // ВоспроизвестиRemote.stop();             //Остановить воспроизведениеRemote.forward();        //Ускорить воспроизведениеRemote.rewind();         //Обратное воспроизведениеи конечно же скетч для arduino//GENMC.ru управление мультимедиа при помощи энкодера #include

Источник: http://dixom.ru/instruktsii-i-uroki/media-enkoder-na-arduino-micro

Arduino UNO урок 6 – Энкодер

В очередном уроке мы рассмотрим работу Arduino с энкодером (который служит для преобразования угла поворота в эл. сигнал). С энкодера мы получаем 2 сигнала (А и В), которые противоположны по фазе.

В данном уроке мы будем использовать энкодер фирмы SparkFun COM-09117, который имеет 12 положений на один оборот (каждое положение 30°).

На приведенной ниже диаграмме вы можете видеть, как зависят выход А и В друг от друга при вращении энкодера по часовой или против часовой стрелки.

Каждый раз, когда сигнал А переходит от положительного уровня к нулю, мы считываем значение выхода В. Если В в этот момент находится в положительном состоянии, значит энкодер вращается по часовой стрелке, если В нуль, то энкодер вращается против часовой стрелки.

Считывая оба выхода, мы при помощи МК можем определить направление вращения, и при помощи подсчета импульсов с А выхода – угол поворота. Конечно можно пойти еще дальше и при помощи вычисления частоты, можно определить насколько быстро происходит вращение энкодера.

Как вы видите, энкодер имеет много преимуществ по сравнению с обычным потенциометром.

Используя энкодер мы будем управлять яркостью LED светодиода при помощи ШИМ выхода. Для считывания данных энкодера мы будем использовать простейший метод, основанный на программных таймерах, которые мы изучали в третьем уроке.

Как было сказано выше, мы будем использовать энкодер sparkfun. Первое, что необходимо сделать, это определить как часто нам нужно обращаться к выходам энкодера для считывания значений. Итак, представим себе, что в лучшем случае, мы можем повернуть ручку энкодера на 180° за 1/10 сек, т.е.

это будет 6 импульсов за 1/10 сек или 60 импульсов в секунду. В реальности быстрее вращать не сможете. Т.к. нам необходимо отслеживать все полупериоды, то частота должна быть минимум 120 Герц. Для полной уверенности, давайте примем 200 Гц. (Примечание: т.к.

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

По сигналам программного таймера нам необходимо постоянно сравнивать текущее значение выхода А энкодера с предыдущим значением. Если состояние изменилось от положительного к нулю, то мы проверяем значение выхода В и смотрим положительное оно или нет. В зависимости от полученного результата мы увеличиваем или уменьшаем счетчик значения яркости светодиода.

Программа для данного урока приведена ниже. Она построена на базе предыдущего урока Fade, где использовалась функция millis() для задания временных интервалов. Временной интервал у нас будет 5 мс (200 Гц)

/*
** Энкодер
** Для управлением яркостью LED используется энкодер Sparkfun
*/ int brightness = 120; // яркость LED, начинаем с половины
int fadeAmount = 10; // шаг изменения яркости LED
unsigned long currentTime;
unsigned long loopTime;
const int pin_A = 12; // pin 12
const int pin_B = 11; // pin 11
unsigned char encoder_A;
unsigned char encoder_B;
unsigned char encoder_A_prev=0; void setup() { // declare pin 9 to be an output: pinMode(9, OUTPUT); // устанавливаем pin 9 как выход pinMode(pin_A, INPUT); pinMode(pin_B, INPUT); currentTime = millis(); loopTime = currentTime; } void loop() { currentTime = millis(); if(currentTime >= (loopTime + 5)){ // проверяем каждые 5мс (200 Гц) encoder_A = digitalRead(pin_A); // считываем состояние выхода А энкодера encoder_B = digitalRead(pin_B); // считываем состояние выхода B энкодера if((!encoder_A) && (encoder_A_prev)){ // если состояние изменилось с положительного к нулю if(encoder_B) { // выход В в полож. сост., значит вращение по часовой стрелке // увеличиваем яркость, не более чем до 255 if(brightness + fadeAmount = 0) brightness -= fadeAmount; } } encoder_A_prev = encoder_A; // сохраняем значение А для следующего цикла analogWrite(9, brightness); // устанавливаем яркость на 9 ножку loopTime = currentTime; } }

Читайте также:  Уроки ардуино: контролируем платы через бумагу

Оригинал статьи

Источник: http://cxem.net/arduino/arduino8.php

Код программы к уроку 5. arduino и кнопки

/* * Набор для экспериментов ArduinoKit * Код программы для опыта №5: sketch 05 * * КНОПКИ * * Написано для сайта http://arduinokit.ru * * * Помощь сообщества Arduino. * Посетите сайт http://www.arduino.cc * * Комментарий к программе написан * 22 января 2014 * специально для http://arduinokit.ru

*/

КНОПКИ.

Использование кнопок на цифровых входах.

Ранее мы использовали аналоговые порты (пины) для ввода данных, теперь же мы посмотрим в действии и цифровые порты. Поскольку цифровые порты знают только о двух уровнях сигналов — высоких «+5» и низких «0», они идеально подходят для взаимодействия с кнопками и переключателями, которые тоже имеют только два положения — «Вкл» и «Выкл».

Мы будем подключать один контакт кнопки проводом к заземлению, а другой контакт к цифровому порту. Когда Вы надавите на кнопку, произойдет замыкание цепи и земленой конец «-» присоединится к цифровому порту, а следовательно, полученный сигнал, Arduino будет считать как «низкий».

Но подождите — что происходит, когда кнопка не нажата? В этом состоянии, порт отключен от всего, т.е висит в воздухе, и это не понятное состояние мы называем «неопределенным», или плавующим.

То есть, мы не можем с уверенностью сказать, как отреагирует на такое состояние Arduino.

В зависимости от различных условий окружающей среды это может быть воспринято ей и как HIGH («ВЫСОКИЙ» +5 Вольт), и как LOW («НИЗКИЙ» — логический ноль).

Чтобы не возникало никакий разночтений, и микроконтроллер точно знал что в данный момент у него на входе, мы дополнительно соединим порт Arduino через ограничивающий резистор (подойдет любой с номиналом от 1КОм — 10KОм) с шиной +5 Вольт. Эта «подтяжка» будет гарантировать наличие постоянного ВЫСОКОГО +5V сигнала, а при нажатии, на кнопку цепь замкнется на Землю — «0», а значит для ардуино, сигнал на входе изменится с HIGH, на LOW, т.е. с ВЫСОКОГО +5V, на НИЗКИЙ «0».

(Дополнительно: Когда вы привыкнете к резисторами, и будете знать когда они необходимы, вы сможете активировать внутренние резисторы подтяжки, находящиеся в самом процессоре ATmega. Для информации смотрите http://arduino.cc/en/Tutorial/DigitalPins).

Подсоединение оборудования:

Кнопки:

У кнопок есть два контакта, если кнопка нажата — контакт замкнут, если не нажата — разомкнут.

В кнопках мы будем использовать и два, и четыре контакта, но надо заметить, что в кнопках которые мы будем использовать сейчас, два контакта запараллелены.

Самый простой способ подключить кнопку — подключить провода к клеммам — наискосок (по диагонали).

Подключите любой контакт кнопки 1 к земле (GND).
Подключите другой контакт кнопки к цифровому порту 2.

Подключите любой контакт кнопки 2 к земле (GND).
Подключите другой контакт кнопки к цифровому порту 3.

На ножки кнопок идущие к цифровым портам 2,3, подключите «подтягивающие» резисторы по 10Kом (коричневый/черный/красный), а вторые выводы этих резисторов подключите к общему «-» (GND).

Эти резисторы гарантируют, что на входе будет либо +5V (кнопка не нажата), либо «0», при нажатии, и не чего другого.

(И не забывайте, что в отличии от аналоговых входов у цифровых всего два состояния ВЫСОКОЕ и НИЗКИЙ.)

Светодиод:

Большинство плат Arduino, в том числе и UNO, уже имеют установленный светодиод, с токоограничивающим резистором, подключенный к порту 13. И Вам не обязательно ставить свой.

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

Подсоедините положительный вывод светодиода к цифровому порту Arduino №13 Подсоедините отрицательный вывод светодиода к резистору 330 Ом.

Подсоедините другой вывод резистора к GND «-«.

// Сначало мы создадим константы, т.е. дадим имена кнопкам, которые будут // неизменны до конца кода программы, и привяжем эти имена к портам Arduino. // Это облегчает понимание и работу с кодом программы, а также позволяет

// обращаться к порту по имени.

const int button1Pin = 2; // кнопка №1 — порт 2 const int button2Pin = 3; // кнопка №2 — порт 3

const int ledPin = 13; // порт 13, для светодиода

void setup() { // Установим порты кнопок как входящие: pinMode(button1Pin, INPUT);

pinMode(button2Pin, INPUT);

// Установим порт светодиода как исходящий: pinMode(ledPin, OUTPUT);

}

void loop() {

int button1State, button2State; // переменные для сохранения состояния кнопок

// Поскольку кнопки имеют только два состояния (нажаты и не нажаты) мы будем // работать с ними используя цифровые порты ввода. Для того чтобы считывать // информацию мы воспользуемся функцией digitalRead(). Эта функция позволяет // получить один параметр с цифрового порта и возвратить либо HIGH (+5V),

// либо LOW («0»).

// Здесь мы читаем текущее состояние кнопок и помещаем их значение
// в две переменные:

button1State = digitalRead(button1Pin);
button2State = digitalRead(button2Pin);

// Вспомните, если кнопка нажата, то порт будет соединен с массой («-«).
// Если кнопка не нажата, порт, через подтягивающий резистор будет подключен к +5 вольт.

// Таким образом, состояние порта будет LOW (низким), когда кнопка нажата,
// и HIGH (высоким), когда она не нажата.

// Теперь мы будем использовать состояние портов чтобы контролировать светодиод.

// Что мы хотим сделать, условие: // «Если какая-либо кнопка нажата, загорается светодиод», // «Но, если окажутся нажатыми обе кнопки, светодиод не загорится»

// Давайте переведем это в программный код.

// У Arduino есть специальные логические операторы, и операторы сравнения,
// которые часто используются при проверке условий, в частности:

// «==» (равенство) — Истинно, если обе стороны являются одинаковыми // Пример: // if (x == y) { // тело условия

//}

// «&&» (логическое И) — Истинно только при выполнении обоих условий // Пример: // Истинно, если оба выражения Истинно (true) // if (x > 0 && x < 5) { // тело условия

//}

// «!» (логическое НЕ) // Истинно если оператор ложен (false) // Пример: //if (!x) { // тело условия

//}

// «||» (логическое ИЛИ) — Истинно, если хотя бы одно из условий выполняется // Пример: //if (x > 0 || y > 0) { // тело условия

// }

// В данном случае Мы будем использовать конструкцию «if» для перевода всего // выше сказанного в логические цепочки программы.

// (Не забудьте, НИЗКИЙ (LOW), означает что кнопка нажата)

// «Если одна из кнопок нажата, светодиод светится» // получится:

// if ((button1State == LOW) || (button2State == LOW)) // зажечь светодиод

// «Если обе кнопки нажатые, светодиод не загорается» // получится:

// if ((button1State == LOW) && (button2State == LOW)) // не зажигать светодиод

// Теперь давайте используем вышеуказанные функции и объединим их в одной инструкции:

if (((button1State == LOW) || (button2State == LOW)) // сравниваем, нажата ли одна из кнопок && ! // и если нет ((button1State == LOW) && (button2State == LOW))) // сравниваем, нажаты ли обе кнопки // тогда… { digitalWrite(ledPin, HIGH); // включаем светодиод } else // в противном случае { digitalWrite(ledPin, LOW); // выключаем светодиод

}

// Как вы могли заметить, операторы могут быть объединены
// для решения комплексных задачь

// Не забудьте: Нельзя использовать оператор «=» при сравнении значений вместо // «==», потому что оператор «=» присваивает значение переменным!

}

В следующей статье мы опубликуем код к уроку №5 в виде архива.

Источник: http://arduinokit.ru/arduino/lessons-arduino/buttons-sketch.html

Ссылка на основную публикацию
Adblock
detector