/*
https://blynk.cloud/dashboard/login
https://blynk.cloud/dashboard/334784/global/filter/2410351/organization/334784/devices/1619448/dashboard
*/
#define BLYNK_PRINT Serial
#define BLYNK_TEMPLATE_ID "TMPXXXXX-XXXX"
#define BLYNK_TEMPLATE_NAME "Wokwi"
#define BLYNK_AUTH_TOKEN "RKQ9-I422tq0XSc2Ffs0XXXX-XXXXXXX"
#define BLYNK_FIRMWARE_VERSION "0.1.0"
#include <WiFi.h>
#include <WiFiClient.h>
#include <BlynkSimpleEsp32.h>
#include <TimeLib.h>
#include <Wire.h>
#include <RTClib.h>
#include <ezButton.h>
char auth[] = BLYNK_AUTH_TOKEN;
char ssid[] = "Wokwi-GUEST";
char pass[] = "";
#define MANUAL 0 //Manual Operation
#define AUTO 1 //Automaytic Operation
boolean modeChT = MANUAL; //กำหนดให้ modeChT เป็น MANUAL
struct schedule{
boolean setup;
int SThour;
int STmin;
int STsec;
int SPhour;
int SPmin;
int SPsec;
boolean day[7];
};
boolean modeOperate = false;
boolean timer0_Active = false;
boolean timer1_Active = false;
#define RTC_DATA_PIN 21 // Pin SDA
#define RTC_CLK_PIN 22 // Pin SCL
RTC_DS1307 rtc;
schedule timer0, timer1;
BlynkTimer timer;
//unsigned char day_of_week;
//long rtc_sec;
unsigned long period = 1000; //ระยะเวลาที่ต้องการรอ
unsigned long last_time = 0; //ประกาศตัวแปรเป็น global เพื่อเก็บค่าไว้ไม่ให้ reset จากการวนloop
#define LED4 4 // BLUE
#define LED3 5 // GREEN
#define LED2 19 // YELLOW
#define LED1 23 // RED
#define SW 34 // Operation Mode (AUTO or MANUAL)
#define S1 26 // Button 1
#define S2 27 // Button 2
#define S3 14 // Button 3
#define S4 12 // Button 4
ezButton button1(S1);
ezButton button2(S2);
ezButton button3(S3);
ezButton button4(S4);
BLYNK_CONNECTED(){ // เรียกค่าเริ่มต้น เมื่อสามารถกลับมา Connect ได้
Serial.println("BLYNK SERVER CONNECTED !!!");
Blynk.syncVirtual(V0);
Blynk.syncVirtual(V1);
Blynk.syncVirtual(V2);
Blynk.syncVirtual(V3);
Blynk.syncVirtual(V4);
Blynk.syncVirtual(V5);
}
BLYNK_WRITE (V4)
{
TimeInputParam t(param);
// Process start time
if (t.hasStartTime())
{
timer0.setup = true;
timer0.SThour = t.getStartHour();
timer0.STmin = t.getStartMinute();
timer0.STsec = t.getStartSecond();
Serial.println(String("Start: ") +
timer0.SThour + ":" +
timer0.STmin + ":" +
timer0.STsec);
}
else if (t.isStartSunrise())
{
Serial.println("Start at sunrise");
}
else if (t.isStartSunset())
{
Serial.println("Start at sunset");
}
else
{
// Do nothing
timer0.setup = false;
}
// Process stop time
if (t.hasStopTime())
{
timer0.SPhour = t.getStopHour();
timer0.SPmin = t.getStopMinute();
timer0.SPsec = t.getStopSecond();
Serial.println(String("Stop: ") +
timer0.SPhour + ":" +
timer0.SPmin + ":" +
timer0.SPsec);
}
else if (t.isStopSunrise())
{
Serial.println("Stop at sunrise");
}
else if (t.isStopSunset())
{
Serial.println("Stop at sunset");
}
else
{
// Do nothing: no stop time was set
}
// Process timezone
// Timezone is already added to start/stop time
Serial.println(String("Time zone: ") + t.getTZ());
// Get timezone offset (in seconds)
Serial.println(String("Time zone offset: ") + t.getTZ_Offset());
// Process weekdays (1. Mon, 2. Tue, 3. Wed, ...)
for (int i = 1; i <= 7; i++) {
if (t.isWeekdaySelected(i)) {
//Serial.println(String("Day ") + i + " is selected");
timer0.day[i] = true;
} else {
timer0.day[i] = false;
}
}
Serial.println();
}
BLYNK_WRITE (V5)
{
TimeInputParam t(param);
// Process start time
if (t.hasStartTime())
{
timer1.setup = true;
timer1.SThour = t.getStartHour();
timer1.STmin = t.getStartMinute();
timer1.STsec = t.getStartSecond();
Serial.println(String("Start: ") +
timer1.SThour + ":" +
timer1.STmin + ":" +
timer1.STsec);
}
else if (t.isStartSunrise())
{
Serial.println("Start at sunrise");
}
else if (t.isStartSunset())
{
Serial.println("Start at sunset");
}
else
{
// Do nothing
timer1.setup = false;
}
// Process stop time
if (t.hasStopTime())
{
Serial.println(String("Stop: ") +
t.getStopHour() + ":" +
t.getStopMinute() + ":" +
t.getStopSecond());
timer1.SPhour = t.getStopHour();
timer1.SPmin = t.getStopMinute();
timer1.SPsec = t.getStopSecond();
}
else if (t.isStopSunrise())
{
Serial.println("Stop at sunrise");
}
else if (t.isStopSunset())
{
Serial.println("Stop at sunset");
}
else
{
// Do nothing: no stop time was set
}
// Process timezone
// Timezone is already added to start/stop time
Serial.println(String("Time zone: ") + t.getTZ());
// Get timezone offset (in seconds)
Serial.println(String("Time zone offset: ") + t.getTZ_Offset());
// Process weekdays (1. Mon, 2. Tue, 3. Wed, ...)
for (int i = 1; i <= 7; i++) {
if (t.isWeekdaySelected(i)) {
//Serial.println(String("Day ") + i + " is selected");
timer1.day[i] = true;
} else {
timer1.day[i] = false;
}
}
Serial.println();
}
BLYNK_WRITE (V0)
{
int SW_State_V0 = param.asInt();
if (SW_State_V0 == 1)
{
digitalWrite(LED1, HIGH);
Serial.println("RED ON");
}
else
{
digitalWrite(LED1, LOW);
Serial.println("RED OFF");
}
}
BLYNK_WRITE (V1)
{
int SW_State_V1 = param.asInt();
if (SW_State_V1 == 1)
{
digitalWrite(LED2, HIGH);
Serial.println("YELLOW ON");
}
else
{
digitalWrite(LED2, LOW);
Serial.println("YELLOW OFF");
}
}
BLYNK_WRITE (V2)
{
int SW_State_V2 = param.asInt();
if (SW_State_V2 == 1)
{
digitalWrite(LED3, HIGH);
Serial.println("GREEN ON");
}
else
{
digitalWrite(LED3, LOW);
Serial.println("GREEN OFF");
}
}
BLYNK_WRITE (V3)
{
int SW_State_V3 = param.asInt();
if (SW_State_V3 == 1)
{
digitalWrite(LED4, HIGH);
}
else
{
digitalWrite(LED4, LOW);
Serial.println("BLUE OFF");
}
}
void controlOutPut()
{
if (digitalRead(SW)==AUTO) {
if (modeChT==MANUAL) {
modeChT = AUTO;
if (!timer0_Active && !timer1_Active) Blynk.virtualWrite(V6, "Automatic");
if (!timer0_Active) {
Blynk.setProperty(V0, "isDisabled", "false");
Blynk.setProperty(V0, "color", "#D3435C");
}
if (!timer1_Active) {
Blynk.setProperty(V1, "isDisabled", "false");
Blynk.setProperty(V1, "color", "#FFBB29");
}
Blynk.setProperty(V2, "isDisabled", "false");
Blynk.setProperty(V3, "isDisabled", "false");
Blynk.setProperty(V2, "color", "#23C48E");
Blynk.setProperty(V3, "color", "#04C0F8");
}
} else {
if (modeChT==AUTO) {
modeChT = MANUAL;
Blynk.virtualWrite(V6, "Manual");
//Blynk.setProperty(V6, "label", "Manual Mode");
Blynk.setProperty(V0, "isDisabled", "true");
Blynk.setProperty(V1, "isDisabled", "true");
Blynk.setProperty(V2, "isDisabled", "true");
Blynk.setProperty(V3, "isDisabled", "true");
}
}
DateTime now = rtc.now();
Serial.println(String("CurrentTime: ")+now.hour() + ":" + now.minute() + ":"+now.second());
if (modeChT == AUTO){
// --------- Timer 0 Operation ---------
if (!timer0_Active && timer0.setup && now.hour() == timer0.SThour && now.minute() == timer0.STmin){
timer0_Active = true;
digitalWrite(LED1, HIGH);
Blynk.virtualWrite(V0, HIGH);
Blynk.setProperty(V0, "isDisabled", "true");
Blynk.virtualWrite(V6, "Automatic - Timer 0 Active");
Serial.println("RED ON");
} else if(timer0_Active && timer0.setup && now.hour() == timer0.SPhour && now.minute() == timer0.SPmin) {
timer0_Active = false;
digitalWrite(LED1, LOW);
Blynk.virtualWrite(V0, LOW);
Blynk.setProperty(V0, "isDisabled", "false");
Blynk.virtualWrite(V6, "Automatic");
Serial.println("RED OFF");
}
// --------- Timer 1 Operation ---------
if (!timer1_Active && timer1.setup && now.hour() == timer1.SThour && now.minute() == timer1.STmin){
timer1_Active = true;
digitalWrite(LED2, HIGH);
Blynk.virtualWrite(V1, HIGH);
Blynk.setProperty(V1, "isDisabled", "true");
Blynk.virtualWrite(V6, "Automatic - Timer 1 Active");
Serial.println("YELLOW ON");
} else if(timer1_Active && timer1.setup && now.hour() == timer1.SPhour && now.minute() == timer1.SPmin) {
timer1_Active = false;
digitalWrite(LED2, LOW);
Blynk.virtualWrite(V1, LOW);
Blynk.setProperty(V1, "isDisabled", "false");
Blynk.virtualWrite(V6, "Automatic");
Serial.println("YELLOW OFF");
}
}
}
void setup()
{
Wire.begin();
rtc.begin();
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(SW, INPUT);
pinMode(S1, INPUT);
pinMode(S2, INPUT);
pinMode(S3, INPUT);
pinMode(S4, INPUT);
Serial.begin(9600);
button1.setDebounceTime(20);
button2.setDebounceTime(20);
button3.setDebounceTime(20);
button4.setDebounceTime(20);
Blynk.begin(auth, ssid, pass);
}
void loop()
{
button1.loop(); // MUST call the loop() function first
button2.loop();
button3.loop();
button4.loop();
Blynk.run();
timer.run();
if( millis() - last_time > period) {
last_time = millis();
controlOutPut();
}
if (modeChT == MANUAL) {
if (button1.isReleased()) {
digitalWrite(LED1, !digitalRead(LED1));
if (digitalRead(LED1)) Blynk.virtualWrite(V0, HIGH);
else Blynk.virtualWrite(V0, LOW);
}
if (button2.isReleased()) {
digitalWrite(LED2, !digitalRead(LED2));
if (digitalRead(LED2)) Blynk.virtualWrite(V1, HIGH);
else Blynk.virtualWrite(V1, LOW);
}
if (button3.isReleased()) {
digitalWrite(LED3, !digitalRead(LED3));
if (digitalRead(LED3)) Blynk.virtualWrite(V2, HIGH);
else Blynk.virtualWrite(V2, LOW);
}
if (button4.isReleased()) {
digitalWrite(LED4, !digitalRead(LED4));
if (digitalRead(LED4)) Blynk.virtualWrite(V3, HIGH);
else Blynk.virtualWrite(V3, LOW); }
}
}