Таймеры в ардуино: Arduino и прерывания таймера / Хабр

Содержание

Таймер на Ардуино с настройкой включения и выключения

Всем привет! Собрав таймер на Ардуино из этой инструкции, вы сможете контролировать включение и выключение ваших устройств в нужное вам время. Это могут быть ночные фонари, система орошения сада и т.д. Мы воспользуемся Ардуино, дисплеем и RTC 1307, отображающим и управляющим временем. Вы можете задать часы «ВКЛ» и «ВЫКЛ» при помощи 4 кнопок, что позволит вам изменять настройки микросхемы таймера.

Также вы научитесь создавать часы, базирующиеся на Ардуино. Я приложил схему из fritzing и видео, так что вы без проблем соберёте данное устройство.

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

Шаг 1: Материалы

  • Arduino Uno
  • Модуль RTC 1307
  • Дисплей 16X2
  • Модуль реле 5V
  • Подстроечный потенциометр 10K
  • Резистор 1K
  • Резисторы 10K x 4 штуки
  • Кнопки x 4 штуки
  • Макетная плата, джамперы.

Шаг 2: Устанавливаем часы

Следуйте схеме из Fritzing.

Соедините 5V и GND с Ардуино с соответствующими контактами (Красный – 5V, синий – земля)

Дисплей к Ардуино:

  1. VSS к GND
  2. VDD к 5V
  3. VO к центру потенциометра
  4. RS к пину 2
  5. RW к GND
  6. EN или E к пину 3
  7. D0 NC
  8. D1 NC
  9. D2 NC
  10. D3 NC
  11. D4 к пину 4
  12. D5 к пину 5
  13. D6 к пину 6
  14. D7 к пину 7
  15. A к 5V
  16. K к GND через резистор 1K
  17. Остальные контакты потенциометра на 5V и GND

RTC к Arduino:

  • SDA к пину 4
  • SCL у пину 5
  • GND и 5V

Шаг 3: Устанавливаем время

Пришло время настроить часы. Запустите код «Set time RTC». Этот скетч возьмёт данные о дате и времени из вашего компьютера прямо во время компиляции кода и использует их для программирования RTC. Если у вас на компьютере неправильные установки, то поправьте их перед запуском программы. Затем нажмите кнопку Upload, чтобы немедленно загрузить откомпилированный код.

Внимание: Если вы скомпилируете код, а загрузите его позже, то данные о времени устареют.

Далее откройте окно Serial Monitor, чтобы увидеть, что время было установлено.

Файлы

Шаг 4: Часы

После того, как установите время, откройте и загрузите скетч «Clock with RTC LCD». Потенциометр в схеме нужен для настройки контрастности дисплея, покрутите его, чтобы чётко видеть символы.

Файлы

Шаг 5: Устанавливаем таймер

Теперь мы добавим кнопки и реле. Опять же, следуйте схеме Fritzing.

Пины 8,9, 10 и 11 соединены с GND через резисторы 10K. Когда вы нажмете на кнопку, то на контакты пойдёт напряжение 5V.

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

Шаг 6: Таймер

Откройте и загрузите код «Timer with on off set point». Нажимайте кнопки, чтобы сместить время назад или вперёд. Если электронный таймер будет в пределах настроенного интервала, то он начнет работать сразу же. Если же он не попадает в нужный интервал, то будет ждать час «ВКЛ».

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

Файлы

Весь код написан мной, кроме настройки времени на RTC и дата-логгера Adafruit. Надеюсь, эта инструкция как собрать простой таймер своими руками была для вас полезна!

Кухонный таймер [Амперка / Вики]

Проекты на Arduino и Slot Shield

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

Видеоинструкция

Что потребуется

Как собрать

Скетч

Прошейте контроллер скетчем через Arduino IDE.

timer.ino
// Подключаем библиотеку для работы с дисплеем
#include <QuadDisplay2.h>
 
// номер аналогового пина пищалки
#define POT_PIN     A0
// номер цифрового пина пищалки
#define BUZZER_PIN  2
// номер цифрового пина кнопки
#define BUTTON_PIN  4
 
// создаём объект класса QuadDisplay и передаём номер пина CS
QuadDisplay qd(9);
 
// переменная для подсчёта времени
unsigned long prevMillis = 0;
 
// переменная для хранения таймера
int reverseTimer;
 
void setup()
{
  // инициализация дисплея
  qd.begin();
  // функция установки таймера
  settingTimer();
}
void loop()
{
  // если время таймера не дошло до нуля и прошла 1 секунда
  if ((reverseTimer > 0) && ((millis() - prevMillis) > 1000)) {
    // выводим значение на дисплей
    qd.displayInt(--reverseTimer);
    // запоминаем текущее время
    prevMillis = millis();
    // если таймер дошёл до нуля
    if (reverseTimer == 0) {
      // подаём звуковой сигнал и выводим «Off» на дисплей
      qd.displayDigits(QD_NONE, QD_O, QD_f, QD_f);
      tone(BUZZER_PIN, 4000, 200);
    }
  }
  // если нажата кнопка
  if (!digitalRead(BUTTON_PIN)) {
    // подаём звуковой сигнал
    tone(BUZZER_PIN, 500, 500);
    delay(1000);
    // выполняем настройку таймера
    settingTimer();
  }
}
 
// функция настройки таймера
void settingTimer()
{
  // пока кнопка не нажата
  while (digitalRead(BUTTON_PIN)) {
    // считываем значения с потенциометра
    reverseTimer = analogRead(A0);
    // и выводим его на дисплей
    qd.displayInt(reverseTimer);
    delay(30);
  }
  // после нажатия кнопки, подаём звуковой сигнал
  tone(BUZZER_PIN, 2000, 200);
  delay(300);
  tone(BUZZER_PIN, 3000, 200);
  delay(300);
  tone(BUZZER_PIN, 4000, 200);
}

Что дальше?

FAQ

Где скачать и как установить необходимые библиотеки?

У моего модуля QuadDisplay всего три ноги и расположены они слева. Можно ли использовать его в этом проекте?

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

Вставьте QuadDisplay в правый нижний слот

Прошейте контроллер скетчем через Arduino IDE.

timer.ino
// Подключаем библиотеку для работы с дисплеем
#include <QuadDisplay.h>
 
// номер аналогового пина потенциометра
#define POT_PIN     A0
// номер цифрового пина пищалки
#define BUZZER_PIN  2
// номер цифрового пина кнопки
#define BUTTON_PIN  4
// номер цифрового пина дисплея
#define DISPLAY_PIN 11
 
// переменная для подсчёта времени
unsigned long prevMillis = 0;
 
// переменная для хранения таймера
int reverseTimer;
 
void setup()
{
  // функция установки таймера
  settingTimer();
}
void loop()
{
  // если время таймера не дошло до нуля и прошла 1 секунда
  if ((reverseTimer > 0) && ((millis() - prevMillis) > 1000)) {
    // выводим значение на дисплей
    displayInt(DISPLAY_PIN, --reverseTimer);
    // запоминаем текущее время
    prevMillis = millis();
    // если таймер дошёл до нуля
    if (reverseTimer == 0) {
      // подаём звуковой сигнал и выводим «Off» на дисплей
      displayDigits(DISPLAY_PIN, QD_NONE, QD_O, QD_f, QD_f);
      tone(BUZZER_PIN, 4000, 200);
    }
  }
  // если нажата кнопка
  if (!digitalRead(BUTTON_PIN)) {
    // подаём звуковой сигнал
    tone(BUZZER_PIN, 500, 500);
    delay(1000);
    // выполняем настройку таймера
    settingTimer();
  }
}
 
// функция настройки таймера
void settingTimer()
{
  // пока кнопка не нажата
  while (digitalRead(BUTTON_PIN)) {
    // считываем значения с потенциометра
    reverseTimer = analogRead(A0);
    // и выводим его на дисплей
    displayInt(DISPLAY_PIN, reverseTimer);
    delay(30);
  }
  // после нажатия кнопки, подаём звуковой сигнал
  tone(BUZZER_PIN, 2000, 200);
  delay(300);
  tone(BUZZER_PIN, 3000, 200);
  delay(300);
  tone(BUZZER_PIN, 4000, 200);
}

Скачайте и установите библиотеку для работы с «трёхногим» дисплеем.

Прерывания и многозадачность в Arduino

#include <Servo.h>

class Flasher

{

// Переменные-участники класса устанавливаются при запуске

int ledPin; // Номер контакта со светодиодом

long OnTime; // длительность ВКЛ в мс

long OffTime; // длительность ВЫКЛ в мс

 

// Контроль текущего состояния

int ledState; // устанавливает текущее состояние светодиода

unsigned long previousMillis; // время последнего обновления состояния светодиода

 

// Конструктор - создает объект Flasher, инициализирует переменные-участники и состояние

public:

Flasher(int pin, long on, long off)

{

  ledPin = pin;

  pinMode(ledPin, OUTPUT);

 

  OnTime = on;

  OffTime = off;

 

  ledState = LOW;

  previousMillis = 0;

}

 

void Update(unsigned long currentMillis)

{

  if((ledState == HIGH) && (currentMillis - previousMillis >= OnTime))

  {

   ledState = LOW; // ВЫКЛ

   previousMillis = currentMillis; // Запомнить время

   digitalWrite(ledPin, ledState); // Обновить состояние светодиода

  }

  else if ((ledState == LOW) && (currentMillis - previousMillis >= OffTime))

  {

   ledState = HIGH; // ВКЛ

   previousMillis = currentMillis; // Запомнить время

   digitalWrite(ledPin, ledState); // Обновить состояние светодиода

  }

}

};

 

class Sweeper

{

Servo servo; // объект servo

int pos; // текущее положение сервопривода

int increment; // определяем увеличение перемещения на каждом интервале

int updateInterval; // определяем время между обновлениями

unsigned long lastUpdate; // определяем последнее обновление положения

 

public:

Sweeper(int interval)

{

  updateInterval = interval;

  increment = 1;

}

void Attach(int pin)

{

  servo.attach(pin);

}

void Detach()

{

  servo.detach();

}

void reset()

{

  pos = 0;

  servo.write(pos);

  increment = abs(increment);

}

 

void Update(unsigned long currentMillis)

{

  if((currentMillis - lastUpdate) > updateInterval) //время обновиться

  {

   lastUpdate = millis();

   pos += increment;

   servo.write(pos);

   if ((pos >= 180) || (pos <= 0)) // инициализируем конец вращения

   {

    // инициализируем обратное направление

    increment = -increment;

   }

  }

}

};

 

Flasher led1(11, 123, 400);

Flasher led2(12, 350, 350);

Flasher led3(13, 200, 222);

 

Sweeper sweeper1(25);

Sweeper sweeper2(35);

 

void setup()

{

sweeper1.Attach(9);

sweeper2.Attach(10);

 

// Timer0 уже используется millis() - прерываемся примерно посередине и вызываем ниже функцию "Compare A"

OCR0A = 0xAF;

TIMSK0 |= _BV(OCIE0A);

 

pinMode(2, INPUT_PULLUP);

attachInterrupt(0, Reset, FALLING);

}

 

void Reset()

{

sweeper1.reset();

sweeper2.reset();

}

 

// Прерывание вызывается один раз в миллисекунду, ищет любые новые данные, и если нашло, сохраняет их

SIGNAL(TIMER0_COMPA_vect)

{

unsigned long currentMillis = millis();

sweeper1.Update(currentMillis);

 

// if(digitalRead(2) == HIGH)

{

  sweeper2.Update(currentMillis);

  led1.Update(currentMillis);

}

 

led2.Update(currentMillis);

led3.Update(currentMillis);

}

 

void loop()

{

}

Простой таймер на Ардуино с реле и обратным отсчётом

Сегодня покажу как легко и просто  сделать таймер для управления реле  к которому можно подключить любую нагрузку.
Нам понадобятся. Ардуино, LCD индикатор, реле, пищалка для подачи сигнала и 4 кнопки.
Чтобы не тянуть, сразу покажу как это работает, а потом посмотрим схему подключения.
Слева на экране я буду управлять кнопками всеми настройками, а справа я вывел более крупное изображение дисплея, что бы лучше видеть все изменения.
При нажатии на 1 кнопку можно выбрать установку времени. Это секунды, минуты и часы.
После выбора режима, кнопками плюс и минус можно настроить время таймера. Отсчёт времени будет идти в обратную сторону. И при достижении нуля, раздастся сигнал  и включится или выключится реле. Это будет завесить от того какой режим у вас запрограммирован.
После установки нужного времени надо нажать четвёртую кнопку и таймер начнёт работу. Для примера я поставил время срабатывания 14 секунд, и режим работы Отключение. После нажатия ОК, реле включит нагрузку, которая отключится через 14 секунд.

Установленное время сохраняется в памяти Ардуино, и если вы захотите снова использовать это же время, вам надо просто нажать ОК.
Теперь изменим режим и будем включать лампу при срабатывании таймера. Как менять режимы я покажу дальше в видео.

Установим новое время в одну минуту 14 секунд. Как можно заметить сейчас реле включено и лампа светится. Она погаснет когда будет запущен режим таймера.
Ждём срабатывание таймера. Я ускорю видео, чтобы не тратить ваше время.
Таймер сработал и лампа загорелась.

Для работы вам надо установить библиотеки.
Библиотеку таймера и библиотеку для работы с LCD дисплеем. Так как я в скетче использую русский шрифт, то вам надо установить вот эту библиотеку. Если вам что-то будет непонятно, то посмотрите вот это видео, там я подробно всё рассказал.

Здесь указано к каким пинам подключены кнопки. А здесь куда подключены пищалка и реле.

Эти две переменные отвечают за выбор режима работы. Сейчас установлен режим Выключение. То есть при срабатывании таймера, реле будет отключено.
Если вы поменяете эти значения на противоположные. Сделаете OFF равным единице, а ON равным нулю, то измените режим на включение и при срабатывании таймера он включит нагрузку.

Подведу итог работы, но не видео.
В таймере можно устанавливать время. Часы, минуты и секунды. Режим работы может быть как на включение или отключение нагрузки.
 Давайте посмотрим схему. Индикатор подключается по стандартной схеме к шине I2C.
Пищалка подключается в пину d6, а реле к пину d5. И то и другое питается от 5 вольт Ардуино. Если у вас будет тускнеть дисплей, то вам надо подключить реле к выводу WIN Ардуино, если вы питаете плату от USB или запитать от отдельного источника.
Кнопки подключены к выводам А0 – А3. Другой вывод кнопки надо подключить к земле. Так как в скетче я включил внутреннюю подтяжку, то вам не обязательно устанавливать внешние резисторы.

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

А пока на этом всё.

 

Timelapse таймер на Arduino

Одним из моих хобби является, как ни банально, фотография. Недавно задумался над созданием таймлапсов. Для создания таймлапсов требуется таймер, на котором можно будет выставлять частоту срабатывания затвора фотоаппарата. В поисках готового и дешевого решения были попытки заказать устройство на ebay, но так как Почта России дважды теряла мой долгожданный таймер, я решил сделать его сам.

Разработка принципиальной схемы

Идея устройства проста: сигнал с потенциометра поступает на АЦП контроллера, тем самым задает интервал выходного сигнала на камеру. Этот интервал будет отображаться на 2 индикаторах, 3-й индикатор будет обозначать нам единицу измерения интервала (секунды или минуты), а также зажигать точку в случае, если значение потенциометра не менялось дольше 1 секунды. Данная индикация нужна была для решения одной проблемы, о которой будет сказано ниже, в конце концов она не оказалось лишней. Так же на устройстве я предусмотрел пару кнопок для ручной подачи сигнала на затвор и фокус.

Управление 7 сегментными индикаторами довольно простое.

Принципиальная схема устройства

Развел плату в Eagle-Cad. Естественно старался все делать на SMD элементах и настолько компактно насколько это позволяет печать на фольге и травление в хлорном железе. В результате вышла плата размером 5х5 см.

В живую.

После этого перевел рисунок на текстолит, вытравил и залудил. Результат:

Попытался впервые нанести маску, но первый блин комом.

Прошивка

После напайки большей части компонентов настала очередь поработать с прошивкой. Во-первых, залить на ATmega8L бутлоадер Arduino NG. Во-вторых, написать код программы. И уже на первом этапе я понял, что задача не так проста, потому что Arduino NG производится на базе ATmega8 и работает с кварцем на 16 МГц, в отличие от ATmega8L, которая работает с кварцем на 8 МГц. Но благо в интернете много информации по этой теме, например бутлоадер, который помогает сделать Аrduino с кварцем на 8 МГц на 8L. Его я и залил через Arduino IDE. Увы загрузчик постоянно слетал после прошивки первого скетча. Эту проблему я так и не смог устранить, поэтому так и приходилось заново его заливать

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

Основная проблема состояла в поддержании цикла динамической индикации с одновременным отсчетом таймера для произведения снимка. Благо, в Arduino предусмотрена славная функция mills(), возвращающая кол-во миллисекунд с момента включения устройства. Так как не предусматривалось использование устройства в течении более 1 суток, то эта функция идеально подходила для тайминга.

Данная программа считывает значение с АЦП, проверяет, не изменился ли выбор времени, и если уж он изменился, то производит снимок с новым таймером. Так как значение АЦП довольно таки ощутимо бегает даже если не трогать потенциометр, то было решено брать не более 16 значений времени.

Для пущей экономии было решено выключать индикацию через 10 секунд после последней смены значения потенциометра. Сэкономили 30 мА — мелочь, а приятно.

Все файлы прошивки и схемотехники можно найти здесь.

Сборка устройства

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

До

После

В итоге вышло неплохое устройство себестоимостью 200 р., которое, мать его, работает.

Конечно, можно было пойти по протоптанной тропинке и сделать все на NE 555, но очень уж хотелось индикацию и более удобный выбор времени таймера.

В этот же день и сняли свой первый таймлапс прямо из окна рабочего места gif.

А потом я нашел проект Magic Lantern и необходимость внешнего таймера совсем отпала 🙂

Кухонный таймер на Arduino (3)

Итак, начнем перенос схемы с макетной платы в реальный мир. Поскольку на кухне нет стабилизированного источника +5В, будем полагаться на стандартную схему питания со стабилизатором 7805 (чтобы можно было питать, например, от такого БП на +9В).

Кроме того, надо окончательно определиться с номиналом токоогрничительных резисторов.

При выборе надо учитывать не только максимальный ток через вывод ATmega - 40 мА, но и общий ток на кристалл. Для ATmega8 он составляет 300 мА, но это значение поделено на две части - 100 мА может протекать через порты C0..С5 и 200 мА через все остальные. Пины отдельных сегментов я расположил как раз на выводах C0..C5, следовательно ток через сегмент не может превышать 100/6 = 16,7 мА (будем считать, что все сегменты засвечены - т.е. надо выводить восьмерку).

Из документации на семисегментный дисплей выясняем, что максимальный ток сегмента в нормальном режиме - 30 мА, падение напряжения - 2.0 В при токе 20 мА. Зная, что при последовательном включении сумма падений напряжений на диоде и резисторе равна питанию ( +5В ), получается, что на резисторе "упадет" 5-2=3 В, из чего можно вычислить минимальное сопротивление: R=U/I или 3/0.0167 = 180 Ом. Я решил не рисковать и поставил 220 (ток 13,6 мА).

Тут надо заметить, что есть еще пины, через которые протекает ток всего знакоместа, собирая токи всех сегментов. Простой подсчет показывает, что этот суммарный ток 13,6 x 8 = 109 мА более, чем в два раза первышает 40 мА.

Увы, тут сказывается грубость моих теоретических выкладок - на практике всё вполне надежно работает. Я не учел пару моментов: во-первых, у пина ATmega тоже есть свое внутреннее сопротивление, следовательно реально ток должен быть меньше. во-вторых - при мультиплексировании знакоместо светится только одну миллисекунду, со скважностью 4, что дает возможность скорректировать значение тока 109/4 = 27,25 мА.

Видимо, если вывести на дисплей четыре восьмерки и остановить мультиплексирование, один вывод у ATmega должен выйти из строя. Пока мне жалко губить МК ради такого эксперимента, но, думаю, рано или поздно это у меня получится, хотя бы и случайно 😉

Последнее дополнение, которого нет на схеме: я нашел место для уголовой вилки PLSR, для оперативного заливания новых версии скетчей (конечно, можно было бы установить и ICSP, но так мне показалось удобнее с точки зрения взамодействия с Arduino IDE).

Для размещения я выбрал такой корпус:

На верхней панели надо поместить дисплей и две кнопки, где-то сбоку - тумблер и гнездо питания 2.1/5.5 мм. Сопоставив между собой габариты всех элементов, я пришел к выводу, что схему надо разнести на две платы через вилки и гребенки PLS/PBS: вверху будут кнопки и дисплей, внизу - все остальное. По высоте как раз подходит - заодно не будет болтаться лишних проводов к кнопкам и дисплею.

Первым делом надо вырезать два кусочка макетной платы, под размер корпуса. Можно сразу вставить в них вилки и гребенки PLS/PBS, чтобы убедиться в правильной центровке собранной двуплатной конструкции. Для отрезания гетинакса удобно пользоваться ножницами по металлу, в крайнем случае электролобзиком или мелкой ножовкой по металлу. Надфилем можно аккуратно скруглить углы, чтобы лучше входило в корпус (да и порезаться шансов будет меньше).

Дальше, надо обратить внимание на крепление в корпусе - в данном случае 4 отверстия в нижней плате. Отверстия обычно намечаются маркером и сверлятся мини-дрелью. К сожалению, фирменного DREMEL у меня нет, обхожусь китайской CT-800, хотя - на самом деле, можно воспользоваться даже бытовой ударной дрелью/шуруповертом, главное - аккуратность и точность. Диаметр отверстий можно подбирать под размер саморезов (для этого корпуса подойдет 2,5 мм).

Теоретически, в макетной ничего сверлить не надо, но практически - у нас есть гнездо питания 2,1/5,5 мм с широкими выводами, которое надо еще и расположить на краю платы таким образом, чтобы оно получалось "заподлицо" с одетым внешним корпусом.4 пФ) надо располагать максимально близко к МК.

На этом фото показано подключение адаптера USB-TTL к вилке PLSR4, на которой, как нетрудно догадаться, Vcc (+5В), GND, Rx и Tx. Соединения удобно делать однопиновыми проводами с разъемами BLS:

Однако, если USB-TTL под рукой не оказалось, придется искать другие способы: например, адаптер COM-TTL, легко собираемый на одной микросхеме MAX232CPE. Или классический - установить вилку ICSP и прошивать HEX-файл, получающийся после компиляции из Arduino IDE (ищите в каталоге скетча, там создается подкаталог applet со всеми промежуточными данными), но для этого понадобится программатор, например - тот же Usbasp.

Пьезоэлемент пришлось расположить на нижней плате из-за толщины, но это все равно оказалось приемлемо: слышно его очень хорошо.

Теперь пора приниматься за верхнюю плату:

Часть соединительных проводов можно "пропустить" под корпусом индикатора, но это надо делать до его установки, а сам индикатор не опускать "до упора" на плату.

Самое время проверить правильность монтажа: соединить две платы и посмотреть, как оно заработает.

Как видите - все компоненты на нижней плате аккуратно уместились в межплатное расстояние.

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

Отверстия под разъем питания и тумблер вырезаются скальпелем:

Подаем питание на устройство, и... ждем 10 секунд, пока появятся мигающие нули. Почему так долго? Это происходит из-за бутлоадера, который был прошит в ATmega8, если вы дали хотя бы раз команду "Burn Bootloader" из Arduino IDE. Кстати, именно он может стать причиной активизации злых аппаратных духов.

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

На 3-4 итерации я решил внимательно разобраться, в чем же, собственно, дело. Для этого я добился повторения состояния "поломки" таймера, после чего прочитал флеш-память ATmega8: обнаружились отличия в 16 байтах по сравнению с тем, что зашивали изначально. Следовательно, память ATmega была чем-то испорчена. И, как вы уже догадались, это был опрометчиво оставленный в памяти Bootloader.

Рекомендую в готовом изделии выключить бутлоадер и запретить запись в память программ (не путать с возможностью программирования через ICSP) при помощи установки соответствующих fuse-и lock-битов. Если бутлоадер все-таки нужен - как правило, для отладки - советую обязательно включить BOD - Brown-out Detector, встроенный в ATmega и по умолчанию в Arduino выключенный. Корень проблемы в том, что бутлоадер может исполнять SPM-инструкции (Store Program Memory), которые модифицируют код программной секции. В момент включения питания происходит масса переходных процессов: возрастает напряжение питания, разгоняется резонатор. Необходимо дождаться их стабилизации, прежде чем начинать выполнение инструкций, иначе поведение МК может быть непредсказуемым - с чем я и столкнулся. Для нейтрализации этого эффекта применяют стандартные схемы - т.н. "супервизоры" питания, которые следят за уровнем входного напряжения и удерживают сигнал сброса контроллера до тех пор, пока оно не достигнет нормального уровня. Но поскольку в ATmega оно уже есть (BOD), остается просто активировать его через fuse-биты и выбрать напряжение триггера (в нашем случае Vcc = 5В, поэтому выбираем 4В).

Финальные значения fuse-битов: HFUSE = 0xCB, LFUSE = 0x1F.

Вот, пожалуй, и всё. С помощью доступных компонентов и минимальных навыков программирования/паяния получено имеющее практическую ценность изделие - простой кухонный таймер. Таким образом я завоевал для своего хобби "место под солнцем", очистив его в глазах родственников от ярлыка бесцельного и дорогостоящего времяпрепровождения.

Что может быть прекраснее? 😉

Кухонный таймер на Ардуино. ⋆ ОБЪЕМНИК

Простой кухонный таймер с обратным отсчетом позволяет выставить время от одной минуты до 99 часов 99 минут. Время выводится на дисплей tm1637. Для установки времени использована мембранная клавиатура с четырьмя кнопками, кнопки: +1 , +10, +60 минут и Сброс настроек. Таймер работает на  литиевом li-on аккумуляторе типоразмер 18650 и заряжается от стандартного 5В зарядного устройства для телефона, через micro USB разъем. Мозгом устройства является Arduino ProMini. Скетч написан в IDE Arduino 1.6.7 для Arduino UNO или ProMini.

Arduino — торговая марка аппаратно-программных средств для построения простых систем автоматики.

с обратным отсчетом. С возможностью подключить реле на 3-й пин.

Принципиальная схема кухонного таймера

Для заряда аккумулятора установлен  контроллер  TP4056 с защитой от разряда.

В схеме питания таймера есть повышающий модуль mt3608 DC-DC Step Up, для повышения напряжения до 5В. Выходное напряжение  с платы защиты 4В, для работы Arduino ProMini и высокой яркости свечения led дисплея требуется напряжение 5В.

Вывод времени в конструкции таймера применен led дисплей tm1637.

Модуль звука Buzzer активный 5v.

Обозначение контактов:
VCC – напряжение питания;
I/O – управляющий сигнал;
GND – общий контакт.

Указанные элементы, на принципиальной схеме кухонного таймера: резистор, транзистор и буззер, уже установлены в модуль звука Buzzer, поэтому этот элемент схемы можно заменить модулем.

Модуль адаптер micro USB.

Скетч и библиотеки скачать одним архивом. https://yadi.sk/d/yV8bp2UYHA9A3g 
В Скетч добавил выход на реле 3pin https://yadi.sk/d/3LDD01zEnptOvQ

Используемые компоненты (заказать в Китае):

1. Arduino promini; http://got.by/2snd5z
2. Мембранная клавиатура 1х4; http://ali.pub/2sng3r
3. Модуль звука Buzzer; http://ali.pub/2sngdh
4. led дисплей tm1637; http://ali.pub/2sng7g
5. Тумблер 2 Pin; http://ali.pub/2snfxx
6. Повышающий модуль mt3608; http://ali.pub/2snfo0 или http://ali.pub/2snfoz
7. контроллер  TP4056; http://got.by/2snfa0 или http://ali.pub/28346d
8. Честные аккумуляторы 18650, 3400 мА⋅ч; http://ali.pub/5gxdx6
9. Модуль micro USB; http://ali.pub/2sng09
10. Холдер 18650; http://ali.pub/5gxe89
11. Коробочка для поделок; http://ali.pub/5gxedi  , http://ali.pub/5gxeik
12. Реле модуль 1 канал http://ali.pub/2s42mk или  http://ali.pub/2s419r или http://ali.pub/2s42aw

Похожие Статьи

с вашего сайта.

таймерных прерываний: улучшите свои навыки работы с Arduino | Ардуино

Таймеры

являются жизненно важной частью работы с микроконтроллерами. Продолжая серию «Улучшение навыков Arduino», я покажу вам, как с ними работать, чтобы раскрыть всю мощь таймеров и счетчиков!

Для чего используются таймеры?

Таймеры играют жизненно важную роль в управлении различными аспектами микроконтроллера, в нашем случае, Arduino, некоторые из приложений следующие:

1.) ШИМ

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

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

2.) Прерывания по таймеру

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

Необходимые вещи:

Arduino Uno

Светодиоды

BreadBoard

Перемычки

Таймеры в Arduino

В Arduino Uno есть часы с частотой 16 МГц, которые служат базовыми часами, обычно 16 МГц слишком быстро для нашего приложения поэтому мы должны разделить его на какое-то число, чтобы сделать его полезным для наших повседневных приложений, это число, которое мы используем для деления, известно как Prescaler, оно помогает нам снизить базовую частоту высоких частот, чтобы соответствовать наше приложение.

В Arduino Uno есть три регистра счетчика, а именно Timer0, Timer1 и Timer2.

Timer0 и timer2 - это 8-битные таймеры, что означает, что они могут хранить максимальное значение счетчика 255. Timer1 - это 16-битный таймер, что означает, что он может хранить максимальное значение счетчика 65535. Как только счетчик достигнет своего максимума, он начнет отсчет до нуля (это называется переполнением). Это означает, что на частоте 16 МГц, даже если мы установим регистр сравнения сравнения на максимальное значение счетчика, прерывания будут происходить каждые 256/16 000 000 секунд (~ 16 мкс) для 8-битных счетчиков и каждые 65 536/16 000 000 (~ 4 мс) секунд для 16-битный счетчик.Ясно, что это не очень полезно, если вы хотите прерывать только один раз в секунду.

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

(скорость таймера (Гц)) = (тактовая частота Arduino (16 МГц)) / предварительный делитель

Таким образом, предварительный делитель 1 увеличивает счетчик на 16 МГц, предварительный делитель 8 будет увеличивать его до 2 МГц, предделитель 64 = 250 кГц и так далее.Как указано в таблицах выше, предварительный делитель может быть равен 1, 8, 64, 256 и 1024. (Я объясню значение CS12, CS11 и CS10 на следующем шаге.)

Теперь вы можете рассчитать прерывание. частота с помощью следующего уравнения:

частота прерывания (Гц) = (тактовая частота Arduino 16000000 Гц) / (предварительный делитель * (регистр сопоставления + 1))

+1 присутствует, потому что регистр сопоставления сопоставления имеет нулевой индекс

изменив приведенное выше уравнение, вы можете найти значение регистра сопоставления, которое даст желаемую частоту прерывания:

регистр сопоставления сравнения = [16000000 Гц / (предварительный делитель * желаемая частота прерывания)] - 1

помните, что при использовании для таймеров 0 и 2 это число должно быть меньше 256 и меньше 65536 для таймера 1

, поэтому, если вы хотите прерывание каждую секунду (частота 1 Гц):

регистр сравнения совпадений = [16,000,000 / (предделитель * 1)] - 1

с предварительным делителем 1024 y или получить:

регистр сравнения совпадений = [16,000,000 / (1024 * 1)] -1

= 15,624

, поскольку 256 <15,624 <65,536, вы должны использовать таймер 1 для этого прерывания.

Код настройки таймера выполняется внутри функции setup () {} в скетче Arduino.

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

Основная структура настройки прерывания выглядит так:

Таймер увеличения / уменьшения | Контроллер ПЛК на базе Arduino для промышленных приложений от Industrial Shields

Страна

Афганистан Албания Алжир американское Самоа Андорра Ангола Ангилья Антарктида Антигуа и Барбуда Аргентина Армения Аруба Австралия Австрия Азербайджан Багамы Бахрейн Бангладеш Барбадос Беларусь Бельгия Белиз Бенин Бермуды Бутан Боливия Бонэйр, Синт-Эстатиус и Саба Босния и Герцеговина Ботсвана Остров Буве Бразилия Британская территория Индийского океана Бруней-Даруссалам Болгария Буркина-Фасо Бурунди Камбоджа Камерун Канада Кабо-Верде Каймановы острова Центрально-Африканская Республика Чад Чили Китай Остров Рождества Кокосовые (Килинг) острова Колумбия Коморские острова Конго Острова Кука Коста-Рика Хорватия Куба Кюрасао Кипр Чехия Берег Слоновой Кости Демократическая Республика Конго Дания Джибути Доминика Доминиканская Республика Эквадор Египет Сальвадор Экваториальная Гвинея Эритрея Испания Эстония Эфиопия Фолклендские острова Фарерские острова Фиджи Филиппинки Финляндия Франция Французская Гвиана Французская Полинезия Южные Французские Территории Габон Гамбия Грузия Германия Гана Гибралтар Греция Гренландия Гренада Гваделупа Гуам Гватемала Гернси Гвинея Гвинея-Бисау Гайана Гаити Остров Херд и острова Макдональд Святой Престол (государство-город Ватикан) Гондурас Гонконг Венгрия Исландия Индия Индонезия Иран Ирак Ирландия Ислас Маршалл Остров Мэн Израиль Италия Ямайка Япония Джерси Иордания Казахстан Кения Кирибати Косово Кувейт Кыргызстан Лаос Латвия Ливан Лесото Либерия Ливия Лихтенштейн Литва Люксембург Макао Македония, бывшая югославская Республика Мадагаскар Малави Малайзия Мальдивы Мали Мальта Мартиника Мавритания Маврикий Майотта Микронезия Молдова Монако Монголия Черногория Монтсеррат Марокко Мозамбик Мьянма Мексика Намибия Науру Непал Нидерланды Новая Каледония Новая Зеландия Никарагуа Нигер Нигерия Ниуэ Остров Норфолк Северная Корея Северные Марианские острова Норвегия Оман Пакистан Палау Панама Папуа - Новая Гвинея Парагвай Перу Острова Питкэрн Польша Португалия Пуэрто-Рико Катар Румыния Российская Федерация Руанда Реюньон Сен-Бартелеми Святой Елены, Вознесения и Тристан-да-Кунья Сент-Китс и Невис Санкт-Люсия Сен-Мартен (французская часть) Сен-Пьер и Микелон Святой Винсент и Гренадины Самоа Сан-Марино Саудовская Аравия Сенегал Сербия Сейшельские острова Сьерра-Леоне Сингапур Синт-Мартен (нидерландская часть) Словакия Словения Соломоновы острова Сомали Южная Африка Южная Георгия и Южные Сандвичевы острова Южная Корея южный Судан Шри-Ланка Государство Палестина Судан Суринам Шпицберген и Ян Майен Свазиленд Швеция Швейцария Сирия Сан-Томе и Принсипи Тайвань Таджикистан Танзания Таиланд Тимор-Лешти Идти Токелау Тонга Тринидад и Тобаго Тунис Турция Туркменистан Острова Теркс и Кайкос Тувалу Внешние малые острова США Уганда Украина Объединенные Арабские Эмираты Объединенное Королевство Соединенные Штаты Уругвай Узбекистан Вануату Венесуэла Вьетнам Виргинские острова (британские) Виргинские острова (США) Уоллис и Футуна Западная Сахара страна чудес Йемен Замбия Зимбабве этип Аландские острова

Блог

Hobby Components - Блог Hobby Components посвящен предоставлению вам полезных руководств, проектов и новостей.

Последний

Новые продукты

Привет! Мы добавили новый модуль датчика в нашу эксклюзивную линейку SmartRFy и хотели бы поделиться им здесь для тех, кто не видит наши сообщения в facebook / twitter / IG. Наслаждаться!

Подробнее

Руководства по продукту

Серия плат для разработки Black Pill предлагает удивительный уровень функций и вычислительной мощности по сравнению с популярной линейкой плат для разработки Arduino.Даже какие-то

Подробнее

Программное обеспечение - новичок

Еще в 2015 году мы написали руководство по установке для Arduino IDE, поскольку в настоящее время нет планов по выпуску новых версий Windows, мы решили

Подробнее

Новые продукты

Подробнее

Учебники

Платы разработки Arduino - отличные устройства для встроенного управления. На нижнем уровне находятся недорогие Arduinos на базе ATMega328, такие как Uno, Nano и Pro Mini.

Подробнее

Новые продукты

Тройное основание Wemos Тройное основание Wemos (HCWEMO0016) предназначено для подключения экрана Wemos к плате Wemos D1 без использования

Подробнее

Новые продукты

Sonoff SCÂ Sonoff SC - это устройство мониторинга окружающей среды WiFi на базе ESP8266.

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

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