Sensore PIR con Arduino e ESP seconda parte
In questo codice è stata utilizzata una libreria il cui scopo è facilitare l’invio dei comandi sul collegamento seriale tra ESP e Arduino. Qui ArduinoEchoCommands è possibile scaricare l’intero codice.
Di seguito le definizioni dei metodi e del costruttore con i relativi parametri.
EchoCommands(HardwareSerial &hserial, SoftwareSerial &sserial, uint32_t baud); void errorHalt(String msg); boolean echoFind(String keyword); void echoFlush(); boolean echoCommand(String cmd, String ack, boolean halt_on_fail); void echoSkip(); void sendWIFIATCommands(String cmd, int t); void wifi_init(String ssid, String pwd); void wakeUpESP(int wakePinESP); void sleepDownESP(unsigned long sleeptime);
Esaminiamo i metodi più importanti che verranno utilizzati nel codice.
Dopo aver inizializzato le due comunicazioni seriali, una verso il monitor che fa da semplice log (Serial) e l’altra di comunicazione con ESP (Serial1) vengono entrambi passati alla classe Echocommands insieme al baud rate.
Il metodo void wifi_init(String ssid, String pwd); Inizializza la connessione WiFI Il primo parametro è SSID e il secondo la password corrispondente.
La chiamata echoc.wakeUpESP(wakePinESP) si occupa di svegliare ESP eseguendo una successione di alto basso alto sul pin di reset ESP.
La chiamata echoc.sleepDownESP(0); si occupa di spegnere ESP per un tempo indefinito (grazie al valore 0 del parametro passato). In seguito ESP potrà essere risvegliato (o meglio resettato) solo dal metodo precedente.
In generale il metodo echoCommand invia dei comandi sulla seriale che connette ESP ad Arduino. La chiamata echoc.echoCommand(cmd, “OK”, CONTINUE); viene utilizzata una prima volta per aprire la connessione TCP (cmd = “AT+CIPSTART=2,\”TCP\”,\””; cmd += DEST_IP; cmd += “\”,8080″) e una seconda volta per inviare il comando http verso il server Domoticz (echoCommand(“AT+CIPSEND=2,” + String(cmd.length())) e una terza volta per chiudere la connessione TCP.
In seguito a questa chiusura viene inviato un segnale di spegnimento a ESP,
Nel rientrare nel metodo loop viene riattivato l’interrupt e quindi viene chiamata la routine per mettere in deep sleep Arduino.
attachInterrupt(digitalPinToInterrupt(wakePin), wakeUp, RISING);//RIATTIVA INTERRUPT delay (1000); sleepNow();
Nell’articolo successivo parlerò di come è stato gestito l’interrupt di Arduino.
Di seguito l’intero listato.
#include <EchoCommands.h> #include<SoftwareSerial.h> #include <Wire.h> #include <avr/sleep.h> SoftwareSerial Serial1(8, 9); // RX, TX uint32_t baud = 9600; EchoCommands echoc(Serial, Serial1, 9600); //LOG initialize const byte wakePin = 2; //Porta per il segnale di risveglio - const byte wakePinESP = 4; //ESP wake up port arduino-to ESP RST PORT String ssid="yourssid"; String pwd="yourssidpwd"; #define DEST_IP "DomoticzIP" //Domoticz IP // *************wake routine **************************** void wakeUp() { sleep_disable(); // disabilita la modalita' sleep (sveglia il sistema) // wake up again //Serial.println("Woke up this morning..."); } // ****************************** sleep routine ****************************************** void sleepNow() { //Serial.println("dormo - sleep.... "); sleep_enable(); // abilita l'addormentamento del sistema delay(100); set_sleep_mode(SLEEP_MODE_PWR_DOWN); // Select "power down mode" to maximize energy saving cli(); // disable interrupts sleep_bod_disable(); // disabilita il controllo interno di alimentazione (brown out detection) sei(); // riabilita l'interrupt - enable interrupts sleep_cpu(); // "addormenta" la cpu - sleep mode on cpu } // ******** SETUP ******** void setup() { //uint32_t baud = 9600; //Serial.begin(baud); // Communication with PC monitor via USB pinMode(wakePin, INPUT); //porta che riceve l'interrupt dal sensore PIR pinMode(wakePinESP, OUTPUT); //porta che genera output per il reset del sensore PIR } // ******** LOOP ******** void loop() { //Serial.print("going tosleep.... "); attachInterrupt(digitalPinToInterrupt(wakePin), wakeUp, RISING);//RIATTIVA INTERRUPT delay (1000); sleepNow(); // call sleep routine // ********** Arduino return in loop section here, after woke detachInterrupt(digitalPinToInterrupt(wakePin)); //DISATTIVA TEMPORANEAMENTE INTERRUPT delay(100); echoc.wakeUpESP(wakePinESP); delay(100); echoc.wifi_init(ssid,pwd); if (!echoc.echoCommand("AT+CIPMUX=1", "OK", CONTINUE)) { echoc.sleepDownESP(0); delay (100); echoc.sleepDownESP(0); return; } // Establish TCP connection String cmd = "AT+CIPSTART=2,\"TCP\",\""; cmd += DEST_IP; cmd += "\",8080"; if (!echoc.echoCommand(cmd, "OK", CONTINUE)) { echoc.sleepDownESP(0); delay (100); echoc.sleepDownESP(0); return; } //delay(500); // Build HTTP request. cmd = "GET /json.htm?type=command¶m=switchlight&idx=25&switchcmd=On"; cmd += " HTTP/1.1\r\nHost: "; cmd += DEST_IP; cmd += ":8080\r\n\r\n"; // Send data to domoticz if (!echoc.echoCommand("AT+CIPSEND=2," + String(cmd.length()), ">", CONTINUE)) { //Serial.println("Connection timeout."); echoc.sleepDownESP(0); delay (100); echoc.sleepDownESP(0); return; } else { // Send the raw HTTP request echoc.echoCommand(cmd, "OK", CONTINUE); // GET to domoticz delay(2000); } //Connection close echoc.echoCommand("AT+CIPCLOSE=2", "OK", CONTINUE); delay(1000); //Serial.println("ESP8266 A nanna"); echoc.sleepDownESP(0); delay (100); echoc.sleepDownESP(0); }