/* Modified by ETIEL 2015-07-27 This sketch send to IoTserver instantaneus line power based in power meter whith 1600 p/kwh and send the digital state of a door... Created by Igor Jarc See http://iot-playground.com for details Please use community fourum on website do not contact author directly Code based on https://github.com/DennisSc/easyIoT-ESPduino/blob/master/sketches/ds18b20.ino External libraries: - https://github.com/adamvr/arduino-base64 - https://github.com/milesburton/Arduino-Temperature-Control-Library This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License version 2 as published by the Free Software Foundation. Hardware: ESP8266 ESP201 IDE config: Generic ESP8266, Serial,80MHz,40MHz,DIO,115200,512K(64K SPIFFS) Led buzzer ESP201 (IOPIN) PIN 15 connected to GND whith 4k7 resitor and 4k7 resistor + LED (Status led) PIN program (IO0) connected to 3V3 with 4K7 resistor and push button to GND PIN Reset (RST) connected to 3V3 with 4K7 resistor and push button to GND PIN 2 connect to +3v3 whith 4k7 resistor and +pim of energy counter (Chinise one) */ #include #include //#include //AP definitions #define AP_SSID "xxxxxxxxxxxx" #define AP_PASSWORD "yyyyyyyyy" // EasyIoT server definitions #define EIOT_USERNAME "admin" #define EIOT_PASSWORD "test" #define EIOT_IP_ADDRESS "192.168.0.11" #define EIOT_PORT 80 #define EIOT_NODE "N2S0" // Analog ENERGY #define EIOT_NODE_1 "N1S0" // Digital Input DOOR #define REPORT_INTERVAL 60 // in sec #define USER_PWD_LEN 40 #define INPUT_PIN 5 // Digital input DOOR char unameenc[USER_PWD_LEN]; bool oldInputState; unsigned long previousMillis = 0; // will store last temp was read const long interval = 2000; // interval at which to read sensor volatile boolean pulse=1; // 1º pulse rise go 0n, 2º pulse rise go off volatile float nowTime; volatile float oldTime; volatile float pulseTime=5000; float energy; // used in Led blink function unsigned long PreviousMillis[4] = {0,0,0,0}; // Tracks the last time event fired int LEDstate[4] = {1,1,1,1}; // Used to track if LED should be on or off int T_interval[4] = {10,10,10,10}; // Interval is how long we wait bool WiFiConnect = 0; // flag WiFiServer server(80); // interrupt service routine by James Lewis, thanks!! // pulseTime, time between two consecutives pulse void shutter () { nowTime = millis (); if(!pulse) pulseTime = nowTime-oldTime; oldTime = nowTime; pulse=1; } // end of shutter void LEDblink(int index, int LEDpin, unsigned int onTime, unsigned int offTime) { unsigned long currentMillis = millis(); // Compare to previous capture to see if enough time has passed if ((unsigned long)(currentMillis - PreviousMillis[index]) >= T_interval[index]) { // Change wait interval, based on current LED state if (LEDstate[index]) { // LED is currently on, set time to stay off T_interval[index] = offTime; } else { // LED is currently off, set time to stay on T_interval[index] = onTime; } // Toggle the LED's state, Fancy, eh!? LEDstate[index] = !(LEDstate[index]); digitalWrite(LEDpin, LEDstate[index]); // Save the current time to compare "later" PreviousMillis[index] = currentMillis; } } void wifiConnect() { Serial.print("Connecting to AP"); WiFi.begin(AP_SSID, AP_PASSWORD); while (WiFi.status() != WL_CONNECTED) { delay(1000); Serial.print("."); LEDblink(1,15,100,2000); WiFiConnect = 0; } WiFiConnect = 1; Serial.println(""); Serial.println("WiFi connected"); } void sendAnalog(float value, const String& NODE) { WiFiClient client; while(!client.connect(EIOT_IP_ADDRESS, EIOT_PORT)) { Serial.println("connection failed"); wifiConnect(); } String url = ""; url += "/Api/EasyIoT/Control/Module/Virtual/"+ String(NODE) + "/ControlLevel/"+String(value); // generate EasIoT server node URL Serial.print("POST data to URL: "); Serial.println(url); client.print(String("POST ") + url + " HTTP/1.1\r\n" + "Host: " + String(EIOT_IP_ADDRESS) + "\r\n" + "Connection: close\r\n" + "Authorization: Basic " + unameenc + " \r\n" + "Content-Length: 0\r\n" + "\r\n"); delay(100); while(client.available()){ String line = client.readStringUntil('\r'); Serial.print(line); } Serial.println(); Serial.println("Connection closed"); } // end send void sendInputState(bool inputState) { WiFiClient client; while(!client.connect(EIOT_IP_ADDRESS, EIOT_PORT)) { Serial.println("connection failed"); wifiConnect(); } String url = ""; String command = ""; if (inputState) command = "ControlOn"; else command = "ControlOff"; url = "/Api/EasyIoT/Control/Module/Virtual/"+ String(EIOT_NODE_1) + "/"+command; // generate EasIoT server node URL Serial.print("POST data to URL: "); Serial.println(url); client.print(String("POST ") + url + " HTTP/1.1\r\n" + "Host: " + String(EIOT_IP_ADDRESS) + "\r\n" + "Connection: close\r\n" + "Authorization: Basic " + unameenc + " \r\n" + "Content-Length: 0\r\n" + "\r\n"); delay(100); while(client.available()){ String line = client.readStringUntil('\r'); Serial.print(line); } Serial.println(); Serial.println("Connection closed"); } void readServer() { // wifiConnect(); // Check if a client has connected WiFiClient client = server.available(); if (!client) { return; } // Wait until the client sends some data Serial.println("new client"); while(!client.available()){ delay(1); } // Read the first line of the request String req = client.readStringUntil('\r'); Serial.println(req); client.flush(); // Match the request int val; if (req.indexOf("/gpio/0") != -1) val = 0; else if (req.indexOf("/gpio/1") != -1) val = 1; else { Serial.println("invalid request"); client.stop(); return; } // Set GPIO4 according to the request digitalWrite(4, val); client.flush(); // Prepare the response String s = "HTTP/1.1 200 OK\r\nContent-Type: text/html\r\n\r\n\r\n\r\nGPIO is now "; s += (val)?"high":"low"; s += "\n"; // Send the response to the client client.print(s); delay(1); Serial.println("Client disonnected"); // The client will actually be disconnected // when the function returns and 'client' object is detroyed } void setup() { Serial.begin(115200); attachInterrupt (2, shutter, RISING); // PIN 2 energy pulse input pinMode(INPUT_PIN, INPUT); pinMode(15, OUTPUT); // Blink pin pinMode(4, OUTPUT); // Buzzer pin wifiConnect(); // Start the server server.begin(); Serial.println("Server started"); // Print the IP address Serial.println(WiFi.localIP()); // match the automation software char uname[USER_PWD_LEN]; String str = String(EIOT_USERNAME)+":"+String(EIOT_PASSWORD); str.toCharArray(uname, USER_PWD_LEN); memset(unameenc,0,sizeof(unameenc)); base64_encode(unameenc, uname, strlen(uname)); oldInputState = !digitalRead(INPUT_PIN); } void loop() { if(WiFiConnect) LEDblink(1,15,10,5000); // GPIO15 ON 10mS OFF 5000mS else LEDblink(1,15,100,2000); readServer(); // function to set buzzer int inputState = digitalRead(INPUT_PIN); if (inputState != oldInputState) { sendInputState(inputState); oldInputState = inputState; } if (pulse) { energy=2250/pulseTime*1000; // 1600 pulses per kwh (1pulse=2,25s) Serial.print ("Electricity "); Serial.print (energy); Serial.println (" Wh."); sendAnalog(energy,"N2S0"); pulse = 0; } /* revised: 2015-09-10 - If power < 1 wh let energy = 0 */ if(!pulse && energy != 0 && millis()-oldTime > 2250000) { energy=0; sendAnalog(energy,"N2S0"); } }