#include <GyverTM1637.h>
#include <microDS3231.h>
// 328p часы школьные
MicroDS3231 rtc;
#define CLK 2 //pins definitions for TM1637 and can be changed to other ports
#define DIO 3
GyverTM1637 disp(CLK, DIO);
int val=0, curr_val=0; bool flag=false, flag3=false, bell=false; int curr_sec, block=0, bell_sec=2;
byte troll[4] = {_3, _B, _O, _H};
void setup() {
pinMode(7, OUTPUT); pinMode(8, OUTPUT); // выход на часы
pinMode(4, INPUT); // вход 1 Гц
pinMode(11, INPUT_PULLUP); // кнопка ускор. перевода
pinMode(10, INPUT_PULLUP); // кнопка коррекции
pinMode(9, INPUT_PULLUP); // кнопка управления индикатором
pinMode(12, INPUT_PULLUP); // кнопка внепланового включения звонков
pinMode(13, OUTPUT); // выход на звонок
//rtc.setTime(COMPILE_TIME); // установка времени компьютера
disp.clear(); disp.brightness(1); // яркость дисплея: 0 - 7 (минимум - максимум)
Serial.begin(9600);
}
void loop() {
DateTime now = rtc.getTime(); curr_sec=now.second; // получаем значение текущего времени и даты
Serial.println(rtc.getTimeString()); Serial.println(rtc.getDateString());
if (digitalRead(11)) { // нормальный ход часов
if (now.second==0 && !flag3) {
if (now.minute %2==0) digitalWrite(7, HIGH); else digitalWrite(8, HIGH); flag3=true;
}
if (now.second>=1) {flag3=false; digitalWrite(7, LOW); digitalWrite(8, LOW);}
}
else { // ускоренный перевод часов
if (now.second %2==0) {digitalWrite(7, HIGH); digitalWrite(8, LOW);}
else {digitalWrite(8, HIGH); digitalWrite(7, LOW);}
}
// управление звонком
if (now.day>5 && !bell) delay (1); // исключаем субботу и воскресенье
else if (now.month==1 && now.date<9 && !bell) delay (1); // исключаем новогодние каникулы
else if (now.month>5 && now.month<9 && !bell) delay (1); // исключаем летние месяцы
else if (now.month==2 && now.date==23) delay (1); // исключаем 23 февраля
else if (now.month==3 && now.date==8) delay (1); // исключаем 8 марта
else if (now.month==5 && (now.date==1 || now.date==9)) delay (1); // исключаем майские праздники
else if (now.month==11 && now.date==4) delay (1); // исключаем 4 ноября
else if (now.second==1) { // здесь расписание звонков
if (now.hour==8 && now.minute==29) digitalWrite(13, HIGH), bell_sec=4; // за минуту до начала урока
if (now.hour==8 && now.minute==30) digitalWrite(13, HIGH), bell_sec=3; // начало урока 1
if (now.hour==9 && now.minute==15) digitalWrite(13, HIGH), bell_sec=3; // конец урока
if (now.hour==9 && now.minute==19) digitalWrite(13, HIGH), bell_sec=4; // за минуту до начала урока
if (now.hour==9 && now.minute==20) digitalWrite(13, HIGH), bell_sec=3; // начало урока 2
if (now.hour==10 && now.minute==5) digitalWrite(13, HIGH), bell_sec=3; // конец урока
if (now.hour==10 && now.minute==9) digitalWrite(13, HIGH), bell_sec=4; // за минуту до начала урока
if (now.hour==10 && now.minute==10) digitalWrite(13, HIGH), bell_sec=3; // начало урока 3
if (now.hour==10 && now.minute==55) digitalWrite(13, HIGH), bell_sec=3; // конец урока
if (now.hour==10 && now.minute==59) digitalWrite(13, HIGH), bell_sec=4; // за минуту до начала урока
if (now.hour==11 && now.minute==00) digitalWrite(13, HIGH), bell_sec=3; // начало урока 4
if (now.hour==11 && now.minute==45) digitalWrite(13, HIGH), bell_sec=3; // конец урока
if (now.hour==11 && now.minute==59) digitalWrite(13, HIGH), bell_sec=4; // за минуту до начала урока
if (now.hour==12 && now.minute==0) digitalWrite(13, HIGH), bell_sec=3; // начало урока 5
if (now.hour==12 && now.minute==45) digitalWrite(13, HIGH), bell_sec=3; // конец урока
if (now.hour==12 && now.minute==59) digitalWrite(13, HIGH), bell_sec=4; // за минуту до начала урока
if (now.hour==13 && now.minute==0) digitalWrite(13, HIGH), bell_sec=3; // начало урока 6
if (now.hour==13 && now.minute==45) digitalWrite(13, HIGH), bell_sec=3; // конец урока
}
if (curr_sec>=bell_sec) digitalWrite(13, LOW);
if (digitalRead(12)==LOW) {bell=true; val=4;} // включение звонков в неурочный день
else if (now.hour==0 && bell) bell=false; // в полночь неурочный день окончен
if (block>0) --block; // коррекция не повторяется раньше, чем через 20 сек.
if (digitalRead(10)==LOW && !block) { // коррекция секунд в ноль
if (now.second>30) {if (now.minute==59) ++now.hour, now.minute=0; else ++now.minute; }
now.second=0; block=20;
rtc.setTime(now); // загружаем в RTC
}
else if (digitalRead(10)==LOW) Serial.println("correction blocked");
switch (val) {
case 1: {disp.displayClock(now.minute, now.second);} // вывести минуты и секунды
break;
case 2: {disp.displayClock(now.date, now.month);} // вывести день и месяц
break;
case 3: {disp.displayInt(now.year);} // вывести год
break;
case 4: {disp.displayByte(troll);} // вывести "звон"
break;
default: {disp.displayClock(now.hour, now.minute);} // вывести часы и минуты
break;
}
if (digitalRead(9)==LOW && !flag) {if (val<3) ++ val; else val=0; flag=true;}
while (curr_sec==rtc.getSeconds()) delay (1); //ждём следующую секунду
flag=false; if (val==4) val=0; curr_val=val;
}
void yield() { // точки на индикаторе
if (val==2) disp.point(true); else if (val>2) disp.point(false);
else {if (digitalRead(4)==LOW) disp.point(true); else disp.point(false);}
}