Таймер для сушилки белья с дисплеем реле и энкодером

Добрый день.
У супруги сдохла механическая ручка таймер на сушилке белья. Решил на ардуино нано + тм1637 реле и энкодере сделать таймер.
В сети нужного мне не встречал.

// Инициализация необходимых переменных
int hrs = 0;
int mins = 0;

// Подключение библиотеки TM1637 для работы с 4-х цифровым дисплеем
// Создание объекта disp для управления дисплеем, подключенным к портам 6 и 7
#include "TM1637.h"
TM1637 disp(6, 7);

// Время последнего обновления
unsigned long last_time = 0;

// Переменные для отслеживания и управления временем
boolean flag;

// Буферы для отображения символов на дисплее
static byte buff1[4] = {_S, _E, _t};
static byte buff2[4] = {_E, _n, _d};

// Подключение библиотеки Encoder для работы с энкодером
// Создание объекта encoder_1 для управления энкодером, подключенным к портам 4 и 5
#include <Encoder.h>
Encoder encoder_1(4, 5);

// Переменная для сохранения предыдущего положения энкодера
int oldPosition = -999;

// Настройка начального состояния Arduino
void setup() {
  // Очистка дисплея и установка максимального уровня яркости
  disp.clear();
  disp.brightness(7);

  // Настройка портов для кнопки энкодера 3, звукового сигнала 8, реле 13.
  pinMode(3, INPUT_PULLUP);
  pinMode(8, OUTPUT);
  pinMode(13, OUTPUT);

  // Вызов сообщения "_Set" на дисплее
  disp.twistByte(buff1, 50);
}

// Основной цикл программы
void loop() {
  // Чтение и нормализация позиции энкодера, отслеживание изменения позиции энкодера
  int newPosition = (encoder_1.read() / 4);
  if (newPosition != oldPosition) {
      oldPosition = newPosition;
  }

  // Защита от отрицательных значений
  if (newPosition < 0) {
    encoder_1.write(0);
  }

  // Если новая позиция больше нуля, обновить часы и минуты и отобразить их на дисплее
  if (newPosition > 0) {
    hrs = newPosition / 60;
    mins = newPosition % 60;
    disp.point(flag);
    disp.displayClock(hrs, mins);
  }

  // Если пользователь нажал кнопку энкодера на пине 3, и значение энкодера больше 0 включаем таймер.
  if (newPosition > 0 && digitalRead(3) == 0) {
    // 'flag' устанавливается в 'false', Пищалка пищит на пине 8 с частотой 1000 Hz в течение 500 мс
    flag = false;
    tone(8, 1000, 500);

    // включаем реле
    digitalWrite(13, 1);

    // Инициализация временных переменных
    unsigned long last_time_flag = 0;
    unsigned long last_time_mins = 0;

    // Начинаем отсчет времени
    while (newPosition > 0) {
      unsigned long current_time = millis();

      // Флаг мигания
      if (current_time - last_time_flag >= 500) {
        flag = !flag;
        disp.point(flag);
        last_time_flag = current_time;
      }

      // Уменьшение минут и часов через каждую минуту и отображение времени на дисплее
      if (current_time - last_time_mins >= 60000) {
        mins --;
        if (hrs > 0 && mins < 0) {
          mins = 59;
          hrs--;
        }

        disp.displayClockScroll(hrs, mins, 70);
        newPosition --;
        last_time_mins = current_time;
      }
    }

    // Если таймер дошел до ноля
    if (hrs == 0 && mins == 0) {
      disp.point(0);  // Отключение точки на дисплее
      disp.twistByte(buff2, 50);  // Вывод сообщения 'End'
      digitalWrite(13, 0);  // Выключение реле

      // Пищалка пищит три раза в течение секунды
      for (int count = 0; count < 3; count++) {
        tone(8, 1000, 500);
        delay(1000);
      }

      // Сброс энкодера до 0 после завершения отсчета
      encoder_1.write(0);
    }

    // Восстановление исходного состояния
    flag = true;
  }
}

И решили поделиться ?

Да. Мне не жалко

2 лайка

Энкодер стоит пересадить на D2 и D3, если МК - ATMega328. Так они окажутся на прерываниях и с меньшей вероятностью пропустят щелчки при кручении.

1 лайк

Долго искал обработчики энкодера. Этот вариант более менее. Спасибо за совет. Попробую как вы сказали. Видео работы

Timer1
Timer1

Действительно. В сети ни одного таймера на ардуино…)

1 лайк

Я не отвечаю таким.
Пояснение. Скетч работает с этой библиотекой для TM1637

А я и не спрашивал)

бывает…

1 лайк