// Подключаем библиотеку для работы с четырёхразрядным дисплеем #include // Подключаем библиотеку для работы с кнопками #include // Создаём объект дисплея на шине SPI и пине 10 QuadDisplay qd(10); // Создаём объекты кнопок на пинах: 2, 3, 4 и 5 TroykaButton buttonS1(5); TroykaButton buttonS2(2); TroykaButton buttonS3(3); TroykaButton buttonS4(4); // Даём понятное имя пину A2 с пищалкой constexpr uint8_t BUZZER_PIN = A2; // Даём понятное имя пину A0 с потенциометром constexpr uint8_t POT_PIN = A0; // Создаём переменную для хранения счетчика таймера int timerCount; // Создаём переменную для работы таймера unsigned long timeLastUpdate = 0; // Создаём перечисление состояний таймера с соответствующей переменной enum { TIMER_SETUP, // «Установка таймера» TIMER_TICK, // «Таймер тикает» TIMER_DONE // «Таймер завершен» } timerState; void setup() { // Инициализируем дисплей qd.begin(); // Инициализируем кнопки buttonS1.begin(); buttonS2.begin(); buttonS3.begin(); buttonS4.begin(); // Настраиваем пин с пищалкой в режим выхода pinMode(BUZZER_PIN, OUTPUT); // Настраиваем пин с потенциометром в режим входа pinMode(POT_PIN, INPUT); // Устанавливаем режим «Установка таймера» timerState = TIMER_SETUP; } void loop() { // Если установлен режим «Установка таймера» if (timerState == TIMER_SETUP) { // Переходим в функцию обработки режима «Установка таймера» handleTimerSetup(); } // Если установлен режим «Таймер тикает» if (timerState == TIMER_TICK) { // Переходим в функцию обработки режима «Таймер тикает» handleTimerTick(); } // Если установлен режим «Таймер завершен» if (timerState == TIMER_DONE) { // Переходим в функцию обработки режима «Таймер завершен» handleTimerDone(); } } // Функция обработки режима «Установка таймера» void handleTimerSetup() { // Выводим на индикатор выводим символы «----» qd.displayDigits(QD_MINUS, QD_MINUS, QD_MINUS, QD_MINUS); // Подаём звуковой сигнал про установку таймера playMelodyTimerSetup(); // Считываем состояние с кнопки S1 buttonS1.read(); // Пока на нажата кнопка S1 while (!buttonS1.isClick()) { // Считываем показания с потенциометра timerCount = readPot(POT_PIN); // Выводим полученные показания на дисплей qd.displayInt(timerCount); // Обновляем состояние с кнопки S1 buttonS1.read(); } // Подаём звуковой сигнал о старте таймера playMelodyTimerBegin(); // Устанавливаем режим «Таймер тикает» timerState = TIMER_TICK; } // Функция обработки режима «Таймер тикает» void handleTimerTick() { // Передаем константе состояние таймера const auto updateDone = timer(); // Если таймер обновил данные, т.е. прошла 1 секунда if (updateDone) { // Выводим счётчик таймера на дисплей qd.displayInt(timerCount); // Если счётчик дошёл до ноля if (timerCount == 0) { // Отображаем на индикаторе строку про завершения таймера qd.displayDigits(QD_NONE, QD_E, QD_n, QD_d); // Подаём звуковой сигнал на пищалку про завершения таймера playMelodyTimerEnd(); // Устанавливаем режим «Таймер завершен» timerState = TIMER_DONE; } } } // Функция обработки режима «Таймер завершен» void handleTimerDone() { do { // Считываем состояние с кнопки S1 buttonS1.read(); // Пока не нажата кнопка S1 } while (!buttonS1.isClick()); // Устанавливаем режим «Установка таймера» timerState = TIMER_SETUP; } // Функция для отсчёта времени посекундно bool timer() { // Запоминаем текущее время long timeNow = millis(); // Если прошла одна секунда if (timeNow - timeLastUpdate > 1000) { // Обновляем текущее время timeLastUpdate = timeNow; // Уменьшаем текущий счётчик на единицу timerCount--; // Да, таймер досчитал return true; } // Нет, таймер не досчитал return false; } // Функция считывания показаний с потенциометра int readPot(int pin) { // Создаём переменную для хранения // аналогового сигнала с потенциометра в отчётах АЦП int sensorADC = 0; // Создаём переменную для хранения // преобразованных показаний с потенциометра int sensorValue = 0; // Считываем усреднённый аналоговый сигнал с потенциометра for (int i = 0; i < 16; i++) { sensorADC += analogRead(pin); delay(5); } sensorADC = sensorADC / 16; // Преобразуем диапазон значений с потенциометра [0;1023] // в диапазон значений для таймера [0;360] sensorValue = map(sensorADC, 0, 1023, 360, 0); // Возвращаем полученное значение return sensorValue; } // Функция мелодии «Установки таймера» void playMelodyTimerSetup() { tone(BUZZER_PIN, 330, 100); delay(150); tone(BUZZER_PIN, 330, 100); delay(300); tone(BUZZER_PIN, 330, 100); delay(300); tone(BUZZER_PIN, 262, 100); delay(100); tone(BUZZER_PIN, 330, 100); delay(300); tone(BUZZER_PIN, 392, 100); delay(550); tone(BUZZER_PIN, 523, 100); delay(575); } // Функция мелодии «Старт таймера» void playMelodyTimerBegin() { tone(BUZZER_PIN, 2000, 200); delay(300); tone(BUZZER_PIN, 3000, 200); delay(300); tone(BUZZER_PIN, 4000, 200); } // Функция мелодии «Завершение таймера» void playMelodyTimerEnd() { for (int i = 0; i <= 5; i++) { tone(BUZZER_PIN, 1000, 200); delay(400); } }