Mega Hydroponics Controller.
Hydroponics system control and monitoring utilising the duinotech "MEGA with Wi-Fi" and DFRobot "SIM7000C Arduino NB-IoT/LTE/GPRS Expansion Shield".
Components and supplies
8 Channel Relay Board 12VDC XC-4418
Real Time Clock Module XC-4450
Soil Moisture Sensor XC-4604
150mm Plug to Socket Jumper Leads - 40 Pieces
Toggle and Push Button Switches.
Red perspex-195-x-195-x-3mm
MEGA + WiFi (ATmega2560 + ESP8266) XC4421
Temperature & Humidity Sensor Module XC-4520
Mounting posts, screws, nuts and washers.
SIM7000C Arduino NB-IoT/LTE/GPRS/GPS Expansion Shield
Dual Ultrasonic Sensor Module XC-4442
DC-DC Adjustable Step-Down Module XC-4514
1.5" 128x128 RGB Colour OLED Display XC3726
Apps and platforms
Arduino IDE 1.8
Project description
Code
ATmega2560 Code.
cpp
Upgrade to my first hydroponics controller project
1// Hydroponics Controller // 2 3#include <avr/wdt.h> 4#include <Wire.h> 5#include <RTClib.h> 6#include "lcdgfx.h" 7#include "lcdgfx_gui.h" 8#include <DHT_U.h> 9#include <NewPing.h> 10#include <DFRobot_SIM7000.h> 11 12// real time clock 13RTC_DS1307 rtc; 14 15// temperature & humidity sensor 16DHT_Unified dht(49, DHT22); 17 18// ultra-sonic transducer 19NewPing sonar(46, 48, 300); 20 21// {RST, BUS, CS, DC, FREQ (0 = default), CLK, MOSI} 22DisplaySSD1351_128x128x16_SPI 23display(40, { -1, 44, 42, 0, 51, 52}); 24 25// SIM7000 soft serial on pins 7 & 10 26#define PIN_TX 7 27#define PIN_RX 10 28SoftwareSerial mySerial(PIN_RX, PIN_TX); 29 30// jumper pins 8 & 10 on SIM7000 for Mega compatibility 31DFRobot_SIM7000 sim7000(&mySerial); 32 33// digital outputs to relay board 34int Pump = 24, AuxPump = 26, Pump2 = 28, CircFans = 30, 35 CoolFans = 32, TankFan = 34, ShutOFF = 36, LED = 38; 36 37// analog inputs from sensors 38int BattV = A8, UV = A9, Moist1 = A10, Moist2 = A11, 39 Flow1 = A12, Flow2 = A14; 40 41// switch and button digital inputs 42int S1 = 47, S2 = 45, S3 = 43, S4 = 41, S5 = 39, S6 = 37, 43 S7 = 35, S8 = 33, AlmTEST = 27, AlmRST = 25; 44 45// data message format - null, header, terminator, seperator 46String dH[4] = {"", "<", ">", ","}; 47 48// number of data messages to be placed on serial bus 49String dM[10]; 50 51// SMS text message 52String Text; 53 54 55void setup() 56{ 57 // disable WDT 58 wdt_disable(); 59 60 // Mega to WiFi comms 61 Serial.begin(115200); 62 63 // SIM7000C comms 64 Serial3.begin(115200); 65 66 // turn ON SIM7000 67 mySerial.begin(19200); 68 sim7000.turnON(); 69 70 // real time clock 71 rtc.begin();//rtc.adjust(DateTime(22, 12, 30, 12, 43, 00)); 72 73 // SSD1306 colour OLED display 74 display.begin(); 75 display.setFixedFont(ssd1306xled_font6x8); 76 display.fill( 0x0000 ); 77 78 // temperature and humidity sensor 79 dht.begin(); 80 sensor_t sensor; 81 82 // turn on pull-up resistors 83 digitalWrite(S1, HIGH), digitalWrite(S2, HIGH), 84 digitalWrite(S3, HIGH), digitalWrite(S4, HIGH), 85 digitalWrite(S5, HIGH), digitalWrite(S6, HIGH), 86 digitalWrite(S7, HIGH), digitalWrite(S8, HIGH), 87 digitalWrite(AlmRST, HIGH), 88 digitalWrite(AlmTEST, HIGH); 89 90 // set pins to input or output 91 pinMode(Pump, OUTPUT), pinMode(AuxPump, OUTPUT), 92 pinMode(Pump2, OUTPUT), pinMode(CircFans, OUTPUT), 93 pinMode(CoolFans, OUTPUT), pinMode(TankFan, OUTPUT), 94 pinMode(ShutOFF, OUTPUT), pinMode(LED, OUTPUT), 95 pinMode(UV, INPUT), pinMode(Moist1, INPUT), 96 pinMode(Moist2, INPUT), pinMode(Flow1, INPUT), 97 pinMode(Flow2, INPUT); 98 99 100 // check SIM card & display status 101 display.setColor(RGB_COLOR16(0, 255, 255)); 102 display.printFixed(0, 0, "Checking SIM7000C"); 103 display.printFixed(0, 10, "Set baud rate..."); 104 if (sim7000.setBaudRate(19200)) { 105 display.printFixed(80, 10, "- 19200"); 106 } 107 else { 108 display.setColor(RGB_COLOR16(255, 0, 0)); 109 display.printFixed(80, 10, "- ERROR"); 110 } 111 display.setColor(RGB_COLOR16(0, 255, 255)); 112 display.printFixed(0, 20, "SIM card..."); 113 if (sim7000.checkSIMStatus()) { 114 display.printFixed(80, 20, "- READY"); 115 } 116 else { 117 display.setColor(RGB_COLOR16(255, 0, 0)); 118 display.printFixed(80, 20, "- ERROR"); 119 } 120 delay(2000); display.fill( 0x0000 ); 121 122 123 // check RTC & alert to cellphone 124 if (! rtc.begin()) { 125 display.setColor(RGB_COLOR16(255, 0 , 0)); 126 display.printFixed(0, 10, "ALARM - RTC FAULT."); 127 128 //SMS service center address 129 mySerial.print("AT+CSCA=\"+6421600600\"\r"); 130 delay(20); 131 132 //SMS message format 133 mySerial.print("AT+CMGF=1\r"); 134 delay(2000); 135 136 //send SMS message 137 mySerial.print("AT+CMGS=\"0221997187\"\r"); 138 delay(20); 139 140 mySerial.print("RTC FAULT"); 141 display.setColor(RGB_COLOR16(0, 0 , 255)); 142 delay(20); 143 144 //message text 145 display.printFixed(70, 10, "Text Sent."); 146 delay(5000); 147 mySerial.write(0x1A); 148 149 //fill display with black 150 display.fill( 0x0000 ); 151 } 152 else { 153 display.setColor(RGB_COLOR16(173, 255, 47)); 154 display.printFixed(0, 10, "ALARM CLEAR "); 155 }; 156 157 //enable WDT with a timeout of 2 seconds 158 wdt_enable(WDTO_2S); 159} 160 161 162void loop() 163{ 164 for (int i = 0; i < 2; i++) { 165 //reset the watchdog 166 wdt_reset(); 167 168 169 // get time 170 char Date[] = "hh:mm:ss"; DateTime now = rtc.now(); 171 now.toString(Date); 172 int nH = now.hour(), nM = now.minute(); 173 int nD = now.day(), nS = now.second(); 174 175 // display fixed text 176 display.setColor(RGB_COLOR16(0, 255, 0)); 177 display.printFixed(0, 0, "HYDROPONICS"); 178 display.setColor(RGB_COLOR16(255, 255, 255)); 179 display.printFixed(80, 0, (Date)); 180 display.setColor(RGB_COLOR16(0, 255, 255)); 181 display.printFixed(60, 20, "MPPT"); 182 display.printFixed(110, 20, "VDC"); 183 display.printFixed(60, 30, "Tank"); 184 display.printFixed(110, 30, "cm"); 185 display.setColor(RGB_COLOR16(255, 0 , 225)); 186 display.printFixed(60, 40, "Flow:1"); 187 display.printFixed(60, 50, "Flow:2"); 188 display.printFixed(60, 60, "Moist1"); 189 display.printFixed(60, 70, "Moist2"); 190 display.printFixed(60, 80, "UV lvl"); 191 display.printFixed(60, 90, "Temp"); 192 display.drawCircle(114, 90, 1); 193 display.printFixed(117, 90, "C"); 194 display.printFixed(60, 100, "Hum"); 195 display.printFixed(110, 100, "%RH"); 196 display.setColor(RGB_COLOR16(255, 255, 255)); 197 display.printFixed(0, 120, "0 10 20 30 40"); 198 199 200 // read load voltage * cal factor * voltage divider mult 201 char LoadValue[1]; 202 float Volts = ((analogRead(BattV)) * .0047 * 3); 203 dtostrf(Volts, 0, 1, LoadValue); 204 if (Volts >= 12) { 205 display.setColor(RGB_COLOR16(0, 255, 0)); 206 } 207 else if (Volts < 12) { 208 display.setColor(RGB_COLOR16(255, 0, 0)); 209 } 210 display.printFixed(85, 20, LoadValue); 211 dM[0] = dH[0] + (Date) + " : MPPT " 212 + (LoadValue) + " VDC" + dH[3]; 213 214 215 // read nutrient tank level 216 char Lbuf[1]; float uS = sonar.ping(); 217 float Lvl = (111 - (uS / US_ROUNDTRIP_CM)); 218 dtostrf(Lvl, 0, 1, Lbuf); 219 220 // reset ultra-sonic transducer in case of error 221 if (uS == 0) { 222 display.setColor(RGB_COLOR16(173, 255, 47)); 223 display.printFixed(85, 30, "ERR "); 224 dM[1] = dH[0] + "Level Error" + dH[3]; 225 pinMode(46, OUTPUT); delay(20); 226 digitalWrite(46, LOW); delay(20); 227 pinMode(46, INPUT); delay(20); 228 } 229 else if (Lvl < 20 ) { 230 display.setColor(RGB_COLOR16(255, 0, 0)); 231 } 232 else if (Lvl >= 20 && Lvl <= 80) { 233 display.setColor(RGB_COLOR16(173, 255, 47)); 234 } 235 else if (Lvl > 80 && Lvl < 100) { 236 display.setColor(RGB_COLOR16(0, 255 , 0)); 237 } 238 else if (Lvl >= 100) { 239 display.setColor(RGB_COLOR16(0, 255 , 0)); 240 } 241 display.printFixed(85, 30, Lbuf); 242 dM[1] = dH[0] + "Tank Level " + (Lbuf) + " cm" + dH[3]; 243 244 245 // hydroponic gully pump timer 246 if (nH >= 6 && nH <= 21 && nM >= 0 && nM <= 4 ) { 247 digitalWrite (Pump, HIGH); 248 display.setColor(RGB_COLOR16(255, 255 , 255)); 249 display.printFixed(0, 40, "Pump1 ON " ); delay(400); 250 } 251 252 else if ((digitalRead(S1)) == LOW 253 && (digitalRead(S2) == HIGH)) { 254 digitalWrite (Pump, HIGH); 255 display.setColor(RGB_COLOR16(0, 255 , 255)); 256 display.printFixed(0, 40, "Pump1 ON "); delay(400); 257 } 258 259 else if ((digitalRead(S1)) == LOW 260 && (digitalRead(S2) == LOW)) { 261 digitalWrite (Pump, LOW); 262 display.setColor(RGB_COLOR16(255, 0 , 0)); 263 display.printFixed(0, 40, "ManAux ON"); 264 } 265 266 else { 267 digitalWrite (Pump, LOW); 268 display.setColor(RGB_COLOR16(225, 165 , 0)); 269 display.printFixed(0, 40, "Pump1 OFF"); 270 } 271 272 273 // flow sensor gully pump 274 char flow1[1]; int flow1V; 275 flow1V = ((analogRead(A12)) * 5.0 / 1023.0 ); 276 dtostrf(flow1V, 0, 0, flow1); 277 display.setColor(RGB_COLOR16(255, 255, 255)); 278 display.printFixed(100, 120, flow1); 279 280 if ((flow1V < 1) 281 && (digitalRead(Pump) == HIGH) 282 && ((digitalRead(S1)) == HIGH )) 283 { display.setColor(RGB_COLOR16(255, 255 , 255)); 284 display.printFixed(104, 40, "FAIL"); 285 digitalWrite (AuxPump, HIGH); 286 display.printFixed(0, 10, "Alert - AUX ON "); 287 display.setColor(RGB_COLOR16(255, 0 , 0)); 288 display.printFixed(0, 50, "AUX P ON "); 289 dM[2] = "Gully1 - ALARM NO FLOW" + dH[3]; 290 } 291 292 else if ((flow1V < 1) 293 && (digitalRead(Pump) == HIGH) 294 && ((digitalRead(S1)) == LOW )) 295 { display.setColor(RGB_COLOR16(255, 255 , 255)); 296 display.printFixed(104, 40, "FAIL"); 297 digitalWrite (AuxPump, HIGH); 298 display.printFixed(0, 10, "Alert - AUX ON "); 299 display.setColor(RGB_COLOR16(255, 0 , 0)); 300 display.printFixed(0, 50, "AUX P ON "); 301 dM[2] = "(M)Gully1 - ALARM NO FLOW" + dH[3]; 302 } 303 304 else if ((flow1V >= 1) 305 && (flow1V < 2) 306 && (digitalRead(Pump) == HIGH) 307 && ((digitalRead(S1)) == HIGH )) 308 { digitalWrite (AuxPump, LOW); 309 display.setColor(RGB_COLOR16(255, 255 , 255)); 310 display.printFixed(104, 40, "SLOW"); 311 display.printFixed(0, 10, "Gully1 Flow Alert."); 312 display.setColor(RGB_COLOR16(255, 0 , 0)); 313 display.printFixed(0, 50, "AUX P ON "); 314 dM[2] = "Gully1 - Slow Flow Alert" + dH[3]; 315 } 316 317 else if ((flow1V >= 1) 318 && (flow1V < 2) 319 && (digitalRead(Pump) == HIGH) 320 && ((digitalRead(S1)) == LOW )) 321 { digitalWrite (AuxPump, LOW); 322 display.setColor(RGB_COLOR16(255, 255 , 255)); 323 display.printFixed(104, 40, "SLOW"); 324 display.printFixed(0, 10, "Gully1 Flow Alert."); 325 display.setColor(RGB_COLOR16(255, 0 , 0)); 326 display.printFixed(0, 50, "AUX P ON "); 327 dM[2] = "(M)Gully1 - Slow Flow Alert" + dH[3]; 328 } 329 330 else if ((flow1V >= 2) 331 && (digitalRead(Pump) == HIGH) 332 && ((digitalRead(S1)) == HIGH )) 333 { digitalWrite (AuxPump, LOW); 334 display.setColor(RGB_COLOR16(255, 255 , 255)); 335 display.printFixed(104, 40, "GOOD"); 336 display.printFixed(0, 10, " "); 337 display.setColor(RGB_COLOR16(225, 165 , 0)); 338 display.printFixed(0, 50, "AUX P OFF"); 339 dM[2] = "Gully1 - Normal Flow" + dH[3]; 340 } 341 342 else if ((flow1V >= 2) 343 && (digitalRead(Pump) == HIGH) 344 && ((digitalRead(S1)) == LOW )) 345 { digitalWrite (AuxPump, LOW); 346 display.setColor(RGB_COLOR16(255, 255 , 255)); 347 display.printFixed(104, 40, "GOOD"); 348 display.printFixed(0, 10, " "); 349 display.setColor(RGB_COLOR16(225, 165 , 0)); 350 display.printFixed(0, 50, "AUX P OFF"); 351 dM[2] = "(M)Gully1 - Normal Flow" + dH[3]; 352 } 353 354 else { 355 display.setColor(RGB_COLOR16(255, 165 , 0)); 356 display.printFixed(104, 40, "OFF "); 357 display.printFixed(0, 60, "AUX P OFF"); 358 dM[2] = "Gully1 Pump OFF" + dH[3]; 359 } 360 361 // aux pump manual control 362 if ((digitalRead(S2)) == LOW ) { 363 digitalWrite (AuxPump, HIGH); 364 display.setColor(RGB_COLOR16(0, 255 , 255)); 365 display.printFixed(0, 60, "AUX P ON "); 366 } 367 else { 368 digitalWrite (AuxPump, LOW); 369 display.setColor(RGB_COLOR16(255, 165 , 0)); 370 display.printFixed(0, 60, "AUX P OFF"); 371 } 372 373 374 // shed2 pump timer 375 if (nH >= 6 && nH <= 21 && nM >= 40 && nM <= 44 ) { 376 digitalWrite (Pump2, HIGH); 377 display.setColor(RGB_COLOR16(255, 255 , 255)); 378 display.printFixed(0, 50, "Pump2 ON "); 379 } 380 381 else if ((digitalRead(S3)) == LOW ) { 382 (digitalWrite (Pump2, HIGH)); 383 display.setColor(RGB_COLOR16(0, 255 , 225)); 384 display.printFixed(0, 50, "Pump2 ON "); 385 } 386 387 else { 388 digitalWrite (Pump2, LOW); 389 display.setColor(RGB_COLOR16(255, 165 , 0)); 390 display.printFixed(0, 50, "Pump2 OFF"); 391 } 392 393 394 // flow sensor 2 395 char flow2[1]; int flow2V; 396 flow2V = ((analogRead(A14)) * 5.0 / 1023.0 ); 397 dtostrf(flow2V, 0, 0, flow2); 398 display.setColor(RGB_COLOR16(255, 255, 255)); 399 display.printFixed(110, 120, flow2); 400 401 if ((flow2V < 1) 402 && (digitalRead(Pump2) == HIGH) 403 && ((digitalRead(S3)) == HIGH )) 404 { display.setColor(RGB_COLOR16(255, 255 , 255)); 405 display.printFixed(104, 50, "FAIL"); 406 display.printFixed(0, 10, "Gully2 Flow Alert."); 407 dM[3] = "Gully2- ALARM NO FLOW." + dH[3]; 408 } 409 410 else if ((flow2V < 1) 411 && (digitalRead(Pump2) == HIGH) 412 && ((digitalRead(S3)) == LOW )) 413 { display.setColor(RGB_COLOR16(255, 255 , 255)); 414 display.printFixed(104, 50, "FAIL"); 415 display.printFixed(0, 10, "Gully2 Flow Alert."); 416 dM[3] = "(M)Gully2- ALARM NO FLOW." + dH[3]; 417 } 418 419 else if ((flow2V >= 1) && (flow2V <= 3) 420 && (digitalRead(Pump2) == HIGH) 421 && ((digitalRead(S3)) == HIGH )) 422 { display.setColor(RGB_COLOR16(255, 255 , 255)); 423 display.printFixed(104, 50, "SLOW"); 424 display.printFixed(0, 10, "Gully2 Flow Alert."); 425 dM[3] = "Gully2 - Slow Flow Alert." + dH[3]; 426 } 427 428 else if ((flow2V >= 1) && (flow2V <= 3) 429 && (digitalRead(Pump2) == HIGH) 430 && ((digitalRead(S3)) == LOW )) 431 { display.setColor(RGB_COLOR16(255, 255 , 255)); 432 display.printFixed(104, 50, "SLOW"); 433 display.printFixed(0, 10, "Gully2 Flow Alert."); 434 dM[3] = "(M)Gully2 - Slow Flow Alert." + dH[3]; 435 } 436 437 else if ((flow2V > 3) 438 && (digitalRead(Pump2) == HIGH) 439 && ((digitalRead(S3)) == HIGH )) 440 { display.setColor(RGB_COLOR16(255, 255 , 255)); 441 display.printFixed(104, 50, "GOOD"); 442 display.printFixed(0, 10, " "); 443 dM[3] = "Gully2 - Normal Flow." + dH[3]; 444 } 445 446 else if ((flow2V > 3) 447 && (digitalRead(Pump2) == HIGH) 448 && ((digitalRead(S3)) == LOW )) 449 { display.setColor(RGB_COLOR16(255, 255 , 255)); 450 display.printFixed(104, 50, "GOOD"); 451 display.printFixed(0, 10, " "); 452 dM[3] = "(M)Gully2 - Normal Flow." + dH[3]; 453 } 454 455 else { 456 display.setColor(RGB_COLOR16(255, 165 , 0)); 457 display.printFixed(104, 50, "OFF "); 458 dM[3] = "Gully2 Pump OFF" + dH[3]; 459 } 460 461 462 // moisture sensor 1 463 char sm1[1]; int sm1V; 464 sm1V = (analogRead(A10)); dtostrf(sm1V, 0, 0, sm1); 465 if (sm1V >= 500) { 466 display.setColor(RGB_COLOR16(255, 0 , 0)); 467 display.printFixed(104, 60, "WET "); 468 dM[4] = dH[0] + "Autopot Moisture : WET" + dH[3]; 469 } 470 471 else if (sm1V >= 250 && sm1V < 500) { 472 display.setColor(RGB_COLOR16(0, 255 , 0)); 473 display.printFixed(104, 60, "NORM"); 474 dM[4] = dH[0] + "Autopot Moisture : Normal" + dH[3]; 475 } 476 477 else { 478 display.setColor(RGB_COLOR16(255, 0 , 0)); 479 display.printFixed(104, 60, "DRY "); 480 dM[4] = dH[0] + "Autopot Moisture : DRY" + dH[3]; 481 } 482 483 484 // moisture sensor 2 485 char sm2[1]; int sm2V; "Normal Flow", 486 sm2V = (analogRead(A11) ); dtostrf(sm2V, 0, 0, sm2); 487 if (sm2V >= 500) { 488 display.setColor(RGB_COLOR16(255, 0 , 0)); 489 display.printFixed(104, 70, "WET "); 490 dM[5] = dH[0] + "Gully Moisture : WET" + dH[3]; 491 } 492 493 else if (sm2V >= 250 && sm2V < 500) { 494 display.setColor(RGB_COLOR16(0, 255 , 0)); 495 display.printFixed(104, 70, "NORM"); 496 dM[5] = dH[0] + "Gully Moisture : Normal" + dH[3]; 497 } 498 499 else { 500 display.setColor(RGB_COLOR16(255, 0 , 0)); 501 display.printFixed(104, 70, "DRY "); 502 dM[5] = dH[0] + "Gully Moisture : DRY" + dH[3]; 503 } 504 505 506 // nutrient tank air circulation timer 507 if (nH >= 6 && nH <= 21 && nM >= 30 && nM <= 34 ) { 508 digitalWrite (TankFan, HIGH); 509 display.setColor(RGB_COLOR16(255, 255 , 255)); 510 display.printFixed(0, 90, "T-Fan ON "); 511 dM[6] = "Tank Circ Fan ON" + dH[3]; 512 } 513 514 else if ((digitalRead(S6)) == LOW ) { 515 (digitalWrite (TankFan, HIGH)); 516 display.setColor(RGB_COLOR16(0, 255 , 225)); 517 display.printFixed(0, 90, "T-Fan ON "); 518 dM[6] = "(M)Tank Circ Fan ON" + dH[3]; 519 } 520 521 else { 522 digitalWrite (TankFan, LOW); 523 display.setColor(RGB_COLOR16(255, 165 , 0)); 524 display.printFixed(0, 90, "T-Fan OFF"); 525 dM[6] = "Tank Circ Fan OFF" + dH[3]; 526 } 527 528 529 // read temperature 530 char Temp[1]; sensors_event_t event; 531 dht.temperature().getEvent(&event); 532 dtostrf(event.temperature, 0, 1, Temp); 533 display.setColor(RGB_COLOR16(255, 255 , 0)); 534 display.printFixed(86, 90, Temp); 535 536 // air cooling fan timer 537 if (nH >= 6 && nH <= 21 && nM >= 10 && nM <= 14 ) { 538 digitalWrite (CoolFans, HIGH); 539 display.setColor(RGB_COLOR16(255, 255 , 255)); 540 display.printFixed(0, 80, "Cool ON "); 541 dM[7] = dH[0] + "Temp " + (Temp) + 542 " °C : Cool Fans ON" + dH[3]; 543 } 544 545 else if ((digitalRead(S5)) == LOW ) { 546 (digitalWrite (CoolFans, HIGH)); 547 display.setColor(RGB_COLOR16(0, 255 , 225)); 548 display.printFixed(0, 80, "Cool ON "); 549 dM[7] = dH[0] + "Temp " + (Temp) + 550 " °C : (M)Cool Fans ON" + dH[3]; 551 } 552 553 else { 554 digitalWrite (CoolFans, LOW); 555 display.setColor(RGB_COLOR16(255, 165 , 0)); 556 display.printFixed(0, 80, "Cool OFF"); 557 dM[7] = dH[0] + "Temp " + (Temp) + 558 " °C : Cool Fans OFF" + dH[3]; 559 } 560 561 562 // read humidity 563 char Hum[1]; dht.humidity().getEvent(&event); 564 dtostrf(event.relative_humidity, 0, 1, Hum); 565 display.setColor(RGB_COLOR16(255, 255 , 0)); 566 display.printFixed(86, 100, Hum); 567 568 569 // air cirulation fans timer 570 if (nH >= 6 && nH <= 21 && nM >= 20 && nM <= 24 ) { 571 digitalWrite (CircFans, HIGH); 572 display.setColor(RGB_COLOR16(255, 255 , 255)); 573 display.printFixed(0, 70, "Circ ON "); 574 dM[8] = dH[0] + "Hum " + (Hum) + 575 " %RH : Circ Fans ON" + dH[3]; 576 } 577 578 else if ((digitalRead(S4)) == LOW ) { 579 (digitalWrite (CircFans, HIGH)); 580 display.setColor(RGB_COLOR16(0, 255 , 225)); 581 display.printFixed(0, 70, "Circ ON "); 582 dM[8] = dH[0] + "Hum " + (Hum) + 583 " %RH : (M)Circ Fans ON" + dH[3]; 584 } 585 586 else { 587 digitalWrite (CircFans, LOW); 588 display.setColor(RGB_COLOR16(255, 165 , 0)); 589 display.printFixed(0, 70, "Circ OFF"); 590 dM[8] = dH[0] + "Hum " + (Hum) + 591 " %RH : Circ Fans OFF" + dH[3]; 592 } 593 594 595 // UV sensor 596 char uv[1]; float uvV; 597 uvV = (analogRead(UV)); dtostrf(uvV, 0, 1, uv); 598 display.setColor(RGB_COLOR16(153, 205, 50)); 599 display.printFixed(104, 80, uv); 600 601 602 // LED panels light sensor activation timer 603 if (nH >= 22 && nH <= 23 && nM >= 55 && nM <= 56 ) { 604 digitalWrite (LED, LOW); 605 display.setColor(RGB_COLOR16(255, 255 , 255)); 606 display.printFixed(0, 110, "LEDs ON "); 607 dM[9] = "LED Lights ON" + dH[3]; 608 } 609 610 else if ((digitalRead(S8)) == LOW ) { 611 (digitalWrite (LED, HIGH)); 612 display.setColor(RGB_COLOR16(0, 255 , 225)); 613 display.printFixed(0, 110, "LEDs ON "); 614 dM[9] = "(M)LED Lights ON" + dH[3]; 615 } 616 617 else { 618 digitalWrite (LED, LOW); 619 display.setColor(RGB_COLOR16(255, 165 , 0)); 620 display.printFixed(0, 110, "LEDs OFF"); 621 dM[9] = "LED Lights OFF"; 622 } 623 624 // shut-OFF valve control. TBC 625 if ((digitalRead(S7)) == LOW ) { 626 digitalWrite (ShutOFF, HIGH); 627 display.setColor(RGB_COLOR16(0, 255 , 225)); 628 display.printFixed(0, 100, "ShutV ON "); 629 } 630 631 else { 632 digitalWrite (ShutOFF, LOW); 633 display.setColor(RGB_COLOR16(255, 165 , 0)); 634 display.printFixed(0, 100, "ShutV OFF"); 635 } 636 637 // send system status message to Firebird database via WiFi 638 Serial3.print((dH[1]) + (dM[0]) + (dM[1]) 639 + (dM[2]) + (dM[3]) + (dM[4]) 640 + (dM[5]) + (dM[6]) + (dM[7]) 641 + (dM[8]) + (dM[9]) + (dH[2])); 642 643 // send system status message to cellphone 644 Text = ((dM[0]) + (dM[1]) + (dM[7]) 645 + (dM[8]) + (dM[4]) + (dM[5])); 646 647 if ((nH == 17 && nM == 0 && nM == 0 && nS == 0 ) 648 || (digitalRead(AlmTEST)) == LOW ) 649 { 650 mySerial.print("AT+CSCA=\"+6421600600\"\r"); delay(20); 651 mySerial.print("AT+CMGF=1\r"); delay(20); 652 mySerial.print("AT+CMGS=\"0221997187\"\r"); delay(20); 653 mySerial.print(Text); 654 display.setColor(RGB_COLOR16(255, 255 , 0)); 655 display.printFixed(0, 10, "Calling 022 1997187"); 656 mySerial.write(0x1A); delay(500); 657 } 658 659 // alarm clear 660 if ((digitalRead(AlmRST)) == LOW ) 661 { 662 display.setColor(RGB_COLOR16(173, 255, 47)); 663 display.printFixed(0, 10, "ALARM CLEAR "); 664 } 665 666 } 667 while (1); //watchdog timer trigger 668}
ESP8266 WiFi Code.
cpp
Status to Firebird realtime database via WiFi
1#include <Arduino.h> 2#include <ESP8266WiFi.h> 3#include <Firebase_ESP_Client.h> 4#include <WiFiUdp.h> 5#include "addons/TokenHelper.h" // Provide the token generation process info. 6#include "addons/RTDBHelper.h" // Provide the RTDB payload printing info and other helper functions. 7 8#define WIFI_SSID "*******" 9#define WIFI_PASSWORD "***************" 10#define API_KEY "****************************" 11#define USER_EMAIL "*********@gmail.com" 12#define USER_PASSWORD "*****************" 13#define DATABASE_URL "https://esp-firebase-demo-cba62-default-rtdb.asia-southeast1.firebasedatabase.app/" 14 15// Define Firebase objects 16FirebaseData fbdo; // defines FirebaseData object. 17FirebaseAuth auth; // defines FirebaseData object needed for authentication. 18FirebaseConfig config; // defines FirebaseData object needed for configuration data. 19 20String uid; // Variable to save USER UID 21String databasePath; // Database main path (to be updated in setup with the user UID) 22String n0,n1,n2,n3,n4,n5,n6,n7,n8,n9; // Database child nodes 23String parentPath; // Parent Node (to be updated in every loop) 24const byte numChars = 220; // Max characters in serial string for parsing. 25char receivedChars[numChars]; 26char tempChars[numChars]; // temporary array for use when parsing 27char d1[numChars] = {0}, d2[numChars] = {0}, d3[numChars] = {0}, d4[numChars] = {0}, // variables to hold the parsed data 28 d5[numChars] = {0}, d6[numChars] = {0}, d7[numChars] = {0}, d8[numChars] = {0}, d9[numChars] = {0}, 29 d10[numChars] = {0}; 30boolean newData = false; 31 32FirebaseJson json; 33 34// Timer variables (send new readings every three minutes) 35unsigned long sendDataPrevMillis = 0; 36unsigned long timerDelay = 10000; 37 38// Initialize WiFi 39void initWiFi() { 40 WiFi.begin(WIFI_SSID, WIFI_PASSWORD); Serial.print("Connecting to WiFi .."); 41 while (WiFi.status() != WL_CONNECTED) { 42 Serial.print('.'); 43 delay(1000); 44 } 45 Serial.println(WiFi.localIP()); Serial.println(); 46} 47 48void setup() { 49 Serial.begin(115200); 50 initWiFi(); 51 config.api_key = API_KEY; // Assign the api key (required) 52 auth.user.email = USER_EMAIL; // Assign the user sign in credentials 53 auth.user.password = USER_PASSWORD; 54 config.database_url = DATABASE_URL; // Assign the RTDB URL (required) 55 Firebase.reconnectWiFi(true); 56 fbdo.setResponseSize(4096); 57 58 // Assign the callback function for the long running token generation task */ 59 config.token_status_callback = tokenStatusCallback; //see addons/TokenHelper.h 60 61 // Assign the maximum retry of token generation 62 config.max_token_generation_retry = 5; 63 64 // Initialize the library with the Firebase authen and config 65 Firebase.begin(&config, &auth); 66 67 // Getting the user UID might take a few seconds 68 Serial.println("Getting User UID"); 69 while ((auth.token.uid) == "") { 70 Serial.print('.'); 71 delay(1000); 72 } 73 // Print user UID 74 uid = auth.token.uid.c_str(); 75 Serial.print("User UID: "); 76 Serial.println(uid); 77 78 // Update database path 79 databasePath = "/UsersData/" + uid + "/readings"; 80 81 // Update database path for data readings. 82 n0 = databasePath + "/a"; n1 = databasePath + "/b"; n2 = databasePath + "/c"; 83 n3 = databasePath + "/d"; n4 = databasePath + "/e"; n5 = databasePath + "/f"; 84 n6 = databasePath + "/g"; n7 = databasePath + "/h"; n8 = databasePath + "/i"; 85 n9 = databasePath + "/j"; 86} 87 88void loop() { 89 recvWithStartEndMarkers(); 90 if (newData == true) { 91 strcpy(tempChars, receivedChars); // this temporary copy is necessary to protect the original data 92 // because strtok() used in parseData() replaces the commas with \0 93 parseData(); 94 SendData(); 95 newData = false; 96 } 97} 98 99void recvWithStartEndMarkers() { 100 static boolean recvInProgress = false; 101 static byte ndx = 0; 102 char startMarker = '<'; 103 char endMarker = '>'; 104 char rc; 105 106 while (Serial.available() > 0 && newData == false) { 107 rc = Serial.read(); 108 109 if (recvInProgress == true) { 110 if (rc != endMarker) { 111 receivedChars[ndx] = rc; 112 ndx++; 113 if (ndx >= numChars) { 114 ndx = numChars - 1; 115 } 116 } 117 else { 118 receivedChars[ndx] = '\0'; // terminate the string 119 recvInProgress = false; 120 ndx = 0; 121 newData = true; 122 } 123 } 124 125 else if (rc == startMarker) { 126 recvInProgress = true; 127 } 128 } 129} 130 131//============ 132 133void parseData() { // split the data into its parts & assign to database child nodes. 134 135 char * strtokIndx; // this is used by strtok() as an index 136 137 strtokIndx = strtok(tempChars, ","); strcpy(d1, strtokIndx);json.set(n0.c_str(), String(d1)); 138 strtokIndx = strtok(NULL, ","); strcpy(d2, strtokIndx); json.set(n1.c_str(), String(d2)); 139 strtokIndx = strtok(NULL, ","); strcpy(d3, strtokIndx); json.set(n2.c_str(), String(d3)); 140 strtokIndx = strtok(NULL, ","); strcpy(d4, strtokIndx); json.set(n3.c_str(), String(d4)); 141 strtokIndx = strtok(NULL, ","); strcpy(d5, strtokIndx); json.set(n4.c_str(), String(d5)); 142 strtokIndx = strtok(NULL, ","); strcpy(d6, strtokIndx); json.set(n5.c_str(), String(d6)); 143 strtokIndx = strtok(NULL, ","); strcpy(d7, strtokIndx); json.set(n6.c_str(), String(d7)); 144 strtokIndx = strtok(NULL, ","); strcpy(d8, strtokIndx); json.set(n7.c_str(), String(d8)); 145 strtokIndx = strtok(NULL, ","); strcpy(d9, strtokIndx); json.set(n8.c_str(), String(d9)); 146 strtokIndx = strtok(NULL, ","); strcpy(d10, strtokIndx); json.set(n9.c_str(), String(d10)); 147 148} 149 150void SendData() { 151 // Send new readings to database 152 if (Firebase.ready() && (millis() - sendDataPrevMillis > timerDelay || sendDataPrevMillis == 0)) { 153 sendDataPrevMillis = millis(); 154 155 parentPath = databasePath + "/"; 156 157 Serial.printf("Set json... %s\n", Firebase.RTDB.setJSON(&fbdo, parentPath.c_str(), &json) ? "ok" : fbdo.errorReason().c_str()); 158 } 159}
Comments
Only logged in users can leave comments