/* * Hencoop with automatic lamp and door timer, TM1637 display, two buttons and magnetically operated sealed switch */ #include #include #include #include #include // Extended TM1637 library https://github.com/bremme/arduino-tm1637 long maxOpenDoorVar = 8765; // Interval for maximum door opening time // long openDoorVar = 3750; // Interval for door opening long closeDoorVar = 3999; // Interval for door closing const byte redButton = 4; // RedButton: light on, open door const byte blackButton = 5; // BlackButton: light off, close door const byte pinLight = 6; // Light power relay const byte pinDC = 7; // DC motor power relay const byte pinRelay3 = 8; // Motor relay control const byte pinRelay4 = 9; // Motor relay control const byte PIN_CLK = 10; // Define CLK pin (for 4-Digit Display) const byte PIN_DIO = 11; // Define DIO pin (for 4-Digit Display) const byte doorSwitch = 12; // Door's magnetically operated sealed switch // const byte led = 13; SevenSegmentExtended display(PIN_CLK, PIN_DIO); // long ledPulse = 1000; // Interval for LED blinking pulse long buttonCheck = 200; // Interval for checking button state byte buttonCommand = 0; // Variable for buttons value: 0 - nothing, 1 - light on, 2 - light off byte displayWork = 0; // Variable for display status: 0 - nothing, 1 - work long previousButtonMillis = 0; // Button previous press counter long buttonPressed = 0; // Button ms pressed counter long buttonLongPress = 5000; // Interval for long press button action long buttonShortPress = 600; // Interval for short press button action unsigned long lastButtonPressed; // Threads: Thread pressButtonThread = Thread(); // Create thread for button state checking // Thread ledThread = Thread(); // Create thread for LED pulse indication void setup() { Serial.begin(9600); // Initializes the Serial connection @ 9600 baud for debug serStr("starting setup..."); display.begin(); // Initializes the display display.setBacklight(100); // Set the brightness to 100 % display.print("INIT"); // Display INIT on the display pinMode(pinRelay3, OUTPUT); pinMode(pinRelay4, OUTPUT); pinMode(pinDC, OUTPUT); pinMode(pinLight, OUTPUT); // pinMode(led, OUTPUT); pinMode(redButton, INPUT); pinMode(blackButton, INPUT); pinMode(doorSwitch, INPUT); digitalWrite(pinRelay3, HIGH); digitalWrite(pinRelay4, HIGH); digitalWrite(pinDC, HIGH); digitalWrite(pinLight, HIGH); while (!Serial); // Wait until Arduino Serial Monitor opens setSyncProvider(RTC.get); // The function to get the time from the RTC if(timeStatus()!= timeSet) Serial.println("Unable to sync with the RTC"); else Serial.println("RTC has set the system time"); // LED blinking thread: // ledThread.onRun(ledBlink); // ledThread.setInterval(ledPulse); // Interval for LED blinking // Button state cheking thread: pressButtonThread.onRun(pressButton); pressButtonThread.setInterval(buttonCheck); // Interval for checking button pressing delay (1000); display.off(); serStr("...setup finished"); } void loop() { // Threads init: // if (ledThread.shouldRun()) // ledThread.run(); if (pressButtonThread.shouldRun()) pressButtonThread.run(); if (timeStatus() == timeSet) { // If RTC works - call the checkTime function checkTime(); } else { display.on(); display.print("SET TIME"); } /* } else { // Fast blinking indicates that time is int i; // not set or DS1307RTC is not plugged for (i = 1; i <= 500; i++) { digitalWrite(led, LOW); delay(50); digitalWrite(led, HIGH); delay(50); } } */ } /* // LED pulse blinking thread void ledBlink() { static bool ledStatus = false; // LED status bool ledStatus = !ledStatus; // Invert LED state digitalWrite(led, ledStatus); // Activate LED state } */ // Check button pressing thread void pressButton() { unsigned long currentMillis = millis(); if (((currentMillis - previousButtonMillis) > 20000) && (displayWork == 1)) { display.off(); displayWork = 0; } if (digitalRead(redButton) == HIGH || digitalRead(blackButton) == HIGH) { // if (digitalRead(redButton) == HIGH) serStr("Red button pressed, time showed"); // if (digitalRead(blackButton) == HIGH) serStr("Black button pressed, time showed"); display.on(); displayWork = 1; display.printTime(hour(), minute(), true); buttonPressed = buttonPressed + 200; if (buttonPressed > buttonShortPress) { if (digitalRead(redButton) == HIGH) buttonCommand = 1; if (digitalRead(blackButton) == HIGH) buttonCommand = 2; } if (buttonPressed > buttonLongPress) { buttonPressed = 0; buttonCommand = 0; if (digitalRead(redButton) == HIGH) serStr("Red button long press"); if (digitalRead(redButton) == HIGH) openDoor(); if (digitalRead(blackButton) == HIGH) serStr("Black button long press"); if (digitalRead(blackButton) == HIGH) closeDoor(); } previousButtonMillis = currentMillis; } else { buttonPressed = 0; } if (digitalRead(redButton) == LOW && digitalRead(blackButton) == LOW) { if (buttonCommand == 1) serStr("Red button short press"); if (buttonCommand == 1) lightOn(); if (buttonCommand == 2) serStr("Black button short press"); if (buttonCommand == 2) lightOff(); } } void lightOn() { buttonCommand = 0; digitalWrite(pinLight, LOW); serStr("Light on"); } void lightOff() { buttonCommand = 0; digitalWrite(pinLight, HIGH); serStr("Light off"); } void openDoor() { unsigned long openStart = millis(); if (digitalRead(doorSwitch) == LOW) { serStr("Door opening started..."); digitalWrite(pinRelay3, HIGH); digitalWrite(pinRelay4, HIGH); delay(1000); digitalWrite(pinDC, LOW); // DC on delay(3000); digitalWrite(pinRelay4, LOW); while (digitalRead(doorSwitch) == LOW) { if ((millis() - openStart) > maxOpenDoorVar) { break; } delay(55); } digitalWrite(pinRelay4, HIGH); delay(2000); digitalWrite(pinDC, HIGH); // DC off delay(1000); digitalWrite(pinRelay3, HIGH); digitalWrite(pinRelay4, HIGH); serStr("...door opening finished"); } else { serStr("Can't open door, magnet shows that door is open"); display.on(); display.print("can't - door is open"); display.off(); } } void closeDoor() { if (digitalRead(doorSwitch) == HIGH) { serStr("Door closing started..."); digitalWrite(pinRelay3, HIGH); digitalWrite(pinRelay4, HIGH); delay(1000); digitalWrite(pinDC, LOW); // DC on delay(3000); digitalWrite(pinRelay3, LOW); delay(closeDoorVar); digitalWrite(pinRelay3, HIGH); delay(2000); digitalWrite(pinDC, HIGH); // DC off delay(1000); digitalWrite(pinRelay3, HIGH); digitalWrite(pinRelay4, HIGH); serStr("...door closing finished"); } else { serStr("Can't close door, magnet shows that door is closed"); display.on(); display.print("can't - door is closed"); display.off(); } } // Send string to serial monitor with millis() counter and date/time void serStr(const char* serString) { long currentTime = millis(); String space = " "; String stringToPrint = currentTime + space + serString; Serial.println(stringToPrint); // RTC mark Serial.print("RTC time = "); Serial.print(hour()); Serial.write(':'); Serial.print(minute()); Serial.write(':'); Serial.print(second()); Serial.print(", date (D/M/Y) = "); Serial.print(day()); Serial.write('/'); Serial.print(month()); Serial.write('/'); Serial.print(year()); Serial.println(); } void checkTime() { // Winter // 6:56 open door, 7:01 light on, 10:01 light off, // 16:01 light on, 19:01 light off, 19:05 close door if (month()==11 || month()==12 || month()==1 ) { if (hour() == 6 && minute() == 56) { openDoor(); delay(60000); } if (hour() == 7 && minute() == 1) { lightOn(); delay(60000); } if (hour() == 10 && minute() == 1) { lightOff(); delay(60000); } if (hour() == 16 && minute() == 1) { lightOn(); delay(60000); } if (hour() == 19 && minute() == 1) { lightOff(); delay(60000); } if (hour() == 19 && minute() == 5) { closeDoor(); delay(60000); } } // Spring // 6:30 door open, 17:01 light on, 20:01 light off, 20:05 door close if (month()==2 || month()==3 || month()==4 ) { if (hour() == 6 && minute() == 30) { openDoor(); delay(40000); } if (hour() == 17 && minute() == 1) { lightOn(); delay(60000); } if (hour() == 20 && minute() == 1) { lightOff(); delay(60000); } if (hour() == 20 && minute() == 5) { closeDoor(); delay(60000); } } // Summer // 5:30 open door, 22:05 close door if (month()==5 || month()==6 || month()==7 ) { if (hour() == 5 && minute() == 30) { openDoor(); delay(60000); } if (hour() == 22 && minute() == 5) { closeDoor(); delay(60000); } } // Autumn // 6:01 open door, 17:01 light on, 20:01 light off, 21:05 close door if (month()==8 || month()==9 || month()==10 ) { if (hour() == 6 && minute() == 1) { openDoor(); delay(60000); } if (hour() == 17 && minute() == 1) { lightOn(); delay(60000); } if (hour() == 20 && minute() == 1) { lightOff(); delay(60000); } if (hour() == 21 && minute() == 5) { closeDoor(); delay(60000); } } }