LDR Sensor With MQTT Broker , Node-Red
參考來源
http://yhhuang1966.blogspot.com/2015/10/arduino.html
https://youyouyou.pixnet.net/blog/post/120260848-%E7%AC%AC%E5%85%AD%E7%AF%87-esp32%E9%A1%9E%E6%AF%94%E8%AE%80%E5%8F%96%28analogread%29%EF%BC%9A%E5%B0%8F%E5%A4%9C%E7%87%88
http://www.esp32learning.com/code/esp32-and-ldr-example.php
https://iotbyhvm.ooo/interface-ldr-module-with-nodemcu/
Arduino程式
#include <WiFi.h>
#include <PubSubClient.h>
#include <SPI.h>
#include <AutoConnect.h>
#include <WebServer.h>
WebServer server;
AutoConnect Portal(server);
//==============================================
#define BUILTIN_LED 2
#define CDS 34
//==============================================
/* Photocell simple testing sketch.
Connect one end of the photocell to 5V, the other end to Analog 0.
Then connect one end of a 10K resistor from Analog 0 to ground
Connect LED from pin 11 through a resistor to ground
For more information see http://learn.adafruit.com/photocells */
// Update these with values suitable for your network.
#define MQTTid "" //id of this mqtt client
#define MQTTip "broker.mqtt-dashboard.com" //ip address or hostname of the mqtt broker
#define MQTTport 1883 //port of the mqtt broker
#define MQTTuser "alex9ufo" //username of this mqtt client
#define MQTTpsw "alex1234" //password of this mqtt client
//#define MQTTuser "your_username" //username of this mqtt client
//#define MQTTpsw "your_password" //password of this mqtt client
#define MQTTpubQos 2 //qos of publish (see README)
#define MQTTsubQos 1 //qos of subscribe
//Variables
long lastMsg = 0;
char jsonChar1[100];
int photocellReading; // the analog reading from the sensor divider
int LEDbrightness; //
int LightValue1;//宣告變數LightValue
float new_value;
//=============================================================================
boolean pendingDisconnect = false;
void mqttConnectedCb(); // on connect callback
void mqttDisconnectedCb(); // on disconnect callback
void mqttDataCb(char* topic, byte* payload, unsigned int length); // on new message callback
WiFiClient wclient;
PubSubClient client(MQTTip, MQTTport, mqttDataCb, wclient);
//======================================================
void rootPage() {
char content[] = "Hello, world";
server.send(200, "text/plain", content);
}
//=======================================================
void mqttConnectedCb() {
Serial.println("connected");
// Once connected, publish an announcement...
client.publish("alex9ufo/outTopic/ldr/ldr_value", jsonChar1, MQTTpubQos, true); // true means retain
// ... and resubscribe
client.subscribe("alex9ufo/inTopic/led/led_event", MQTTsubQos);
}
//=======================================================
void mqttDisconnectedCb() {
Serial.println("disconnected");
}
//=======================================================
void mqttDataCb(char* topic, byte* payload, unsigned int length) {
/*
you can convert payload to a C string appending a null terminator to it;
this is possible when the message (including protocol overhead) doesn't
exceeds the MQTT_MAX_PACKET_SIZE defined in the library header.
you can consider safe to do so when the length of topic plus the length of
message doesn't exceeds 115 characters
*/
char* message = (char *) payload;
message[length] = 0;
Serial.print("Message arrived [");
Serial.print(topic);
Serial.print("] ");
Serial.println(message);
String s = message;
s.trim();
// Switch on the LED if an 1 was received as first character
if (s == "OFF") {
digitalWrite(BUILTIN_LED, LOW); // Turn the LED on (Note that LOW is the voltage level
// but actually the LED is on; this is because
Serial.println("Received OFF , Send LOW TO BuildIn_LED");
} // if (s == "OFF")
if (s == "ON") {
digitalWrite(BUILTIN_LED, HIGH); // Turn the LED off (Note that HIGH is the voltage level
// but actually the LED is on; this is because
Serial.println("Received ON , Send HIGH TO BuildIn_LED");
} //if (s == "ON")
}
//======================================================
void process_mqtt() {
if (WiFi.status() == WL_CONNECTED) {
if (client.connected()) {
client.loop();
} else {
// client id, client username, client password, last will topic, last will qos, last will retain, last will message
if (client.connect(MQTTid, MQTTuser, MQTTpsw, MQTTid "/status", 2, true, "0")) {
pendingDisconnect = false;
mqttConnectedCb();
}
}
} else {
if (client.connected())
client.disconnect();
}
if (!client.connected() && !pendingDisconnect) {
pendingDisconnect = true;
mqttDisconnectedCb();
}
}
//======================================================
void setup(void) {
Serial.begin(115200);
// We'll send debugging information via the Serial monitor
pinMode(CDS, INPUT);//選告GPIO 13作為輸入(光敏電阻)
pinMode(BUILTIN_LED, OUTPUT);
Serial.println("Configuring your Mobile WiFi to esp32ap...");
Serial.println("Configuring another WiFi SSID,PWD...");
server.on("/", rootPage);
if (Portal.begin()) {
Serial.println("HTTP server:" + WiFi.localIP().toString());
}
else {
Serial.println("Connection failed");
while(true) {yield();}
}
//===================================================
Serial.println(F("Ready!"));
Serial.println(F("Control Build LED ON,OFF"));
//輸出值採前次佔 3 成, 本次佔 7 成方式處理, 這樣數值變化經過積分器濾波後變化就不會那麼劇烈了.
LightValue1=analogRead(CDS);
new_value=0.3*LightValue1 + 0.7*analogRead(CDS);
photocellReading= floor(new_value);
Serial.println(photocellReading);
}
//======================================================
void loop(void) {
process_mqtt();
long now = millis();
if (now - lastMsg > 10000) { // 等3秒
lastMsg = now;
//輸出值採前次佔 3 成, 本次佔 7 成方式處理, 這樣數值變化經過積分器濾波後變化就不會那麼劇烈了.
LightValue1=analogRead(CDS);
new_value=0.3*LightValue1 + 0.7*analogRead(CDS);
photocellReading= floor(new_value);
Serial.print(photocellReading);
/*用光敏電阻感測現場亮度數值,0代表亮度最大,4095代表亮度最小,並依據亮度明暗開啟不同數量的LED作為補光。
環境很亮時(0~500)燈號全關
普通亮時(500~1000)開一顆燈
普通暗時(1000~2000)開兩顆燈
非常暗時(2000以上)燈號全開
這些500、1000、2000的門檻值,請使用者依據現場環境進行調整。 */
//analogWrite(photocellPin, LEDbrightness);
// We'll have a few threshholds, qualitatively determined
if (photocellReading < 500) {
Serial.println(" - ery bright"); //環境很亮時(0~500)燈號全關
} else if (photocellReading>= 500 && photocellReading < 1000) { //普通亮時(500~1000)開一顆燈
Serial.println(" - Bright");
} else if (photocellReading>=1000 && photocellReading < 2000) { //普通暗時(1000~2000)開兩顆燈
Serial.println(" - Light");
} else {
Serial.println(" - Dark"); // 非常暗時(2000以上)燈號全開Dark
}
// Convert data to JSON string
String json1 =
"{\"data\":{"
"\"photocellReading\": \"" + String(photocellReading) + "\"}"
"}";
// Convert JSON string to character array
json1.toCharArray(jsonChar1, json1.length()+1);
if (client.connected()) {
Serial.print("Publish message: ");
Serial.println(json1);
// Publish JSON character array to MQTT topic
client.publish("alex9ufo/outTopic/ldr/ldr_value",jsonChar1);
} //if (client.connected()
} //if (now - lastMsg > 10000) { // 等3秒
Portal.handleClient();
}//loop
//==============================================
Node-Red程式
[{"id":"c518e61b.672778","type":"mqtt out","z":"65ae4e3c.34958","name":"","topic":"alex9ufo/inTopic/led/led_event","qos":"2","retain":"","broker":"41a78e1b.8ebeb","x":650,"y":400,"wires":[]},{"id":"a7e36fff.8b915","type":"mqtt in","z":"65ae4e3c.34958","name":"","topic":"alex9ufo/outTopic/ldr/ldr_value","qos":"2","datatype":"auto","broker":"41a78e1b.8ebeb","x":260,"y":40,"wires":[["e8f87cb5.36583","75e61099.21317"]]},{"id":"e8f87cb5.36583","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","x":550,"y":40,"wires":[]},{"id":"57fd5632.74c838","type":"ui_gauge","z":"65ae4e3c.34958","name":"","group":"2d22b189.273a2e","order":0,"width":0,"height":0,"gtype":"gage","title":"LDR 數值 = ","label":"%","format":"{{value}}","min":0,"max":"4096","colors":["#00b3d9","#0073e6","#1851c3"],"seg1":"500","seg2":"2000","x":750,"y":80,"wires":[]},{"id":"75e61099.21317","type":"function","z":"65ae4e3c.34958","name":"","func":"var thenum = msg.payload.replace( /^\\D+/g, ''); // replace all leading non-digits with nothing\nmsg.payload=thenum;\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","x":530,"y":80,"wires":[["57fd5632.74c838","423b18ad.bbe4c8","e75cdadb.48b458","168c878c.780bf8"]]},{"id":"423b18ad.bbe4c8","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":750,"y":160,"wires":[]},{"id":"d88e47b9.565648","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":510,"y":480,"wires":[]},{"id":"fb7e73aa.f9c64","type":"mqtt in","z":"65ae4e3c.34958","name":"","topic":"alex9ufo/inTopic/led/led_event","qos":"2","datatype":"auto","broker":"e4d9b72d.d14398","x":260,"y":540,"wires":[["d88e47b9.565648","787e3fa5.91af1","d81b8836.54b4d8"]]},{"id":"faeb097f.41f908","type":"ui_led","z":"65ae4e3c.34958","group":"2d22b189.273a2e","order":0,"width":"4","height":"2","label":"LED 狀態","labelPlacement":"left","labelAlignment":"center","colorForValue":[{"color":"red","value":"false","valueType":"bool"},{"color":"green","value":"true","valueType":"bool"}],"allowColorForValueInMessage":false,"name":"","x":730,"y":500,"wires":[]},{"id":"787e3fa5.91af1","type":"function","z":"65ae4e3c.34958","name":"","func":"msg.payload = (msg.payload === \"ON\") ? true : false ;\n\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","x":530,"y":540,"wires":[["faeb097f.41f908","dbdf2765.11f9a8"]]},{"id":"dbdf2765.11f9a8","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":730,"y":540,"wires":[]},{"id":"3a3c185e.072b08","type":"inject","z":"65ae4e3c.34958","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"OFF","payloadType":"str","x":270,"y":440,"wires":[["34c04a5d.cc0506"]]},{"id":"9d1606d1.36afc8","type":"inject","z":"65ae4e3c.34958","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"ON","payloadType":"str","x":270,"y":360,"wires":[["498a399.6df10c8"]]},{"id":"e75cdadb.48b458","type":"ui_chart","z":"65ae4e3c.34958","name":"","group":"2d22b189.273a2e","order":0,"width":0,"height":0,"label":"chart","chartType":"line","legend":"false","xformat":"HH:mm:ss","interpolate":"linear","nodata":"","dot":false,"ymin":"0","ymax":"4096","removeOlder":1,"removeOlderPoints":"","removeOlderUnit":"3600","cutout":0,"useOneColor":false,"useUTC":false,"colors":["#1f77b4","#aec7e8","#ff7f0e","#2ca02c","#98df8a","#d62728","#ff9896","#9467bd","#c5b0d5"],"outputs":1,"x":730,"y":120,"wires":[[]]},{"id":"168c878c.780bf8","type":"function","z":"65ae4e3c.34958","name":"","func":"var va1= parseFloat(msg.payload);\nvar st1=global.get('set1')\nmsg.payload='';\n \nif (st1 === 'auto')\n{\n if (va1 > 2000 ){\n msg.payload= 'ON';\n }\n else\n {\n msg.payload= 'OFF';\n }\n}\n\nif (st1 === 'manual')\n{\n st2=global.get('set2') || '';\n st2=msg.payload=st2;\n}\n\n\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","x":730,"y":200,"wires":[["47b99bfc.4f70f4","e4f4a5f5.390bd8"]]},{"id":"b58076fe.a2dfd8","type":"ui_dropdown","z":"65ae4e3c.34958","name":"","label":"LED 依照亮度 ","tooltip":"","place":"Select option","group":"2d22b189.273a2e","order":4,"width":0,"height":0,"passthru":true,"multiple":false,"options":[{"label":"自動","value":"auto","type":"str"},{"label":"手動","value":"manual","type":"str"}],"payload":"","topic":"","x":240,"y":140,"wires":[["a743c022.61ec1"]]},{"id":"a743c022.61ec1","type":"function","z":"65ae4e3c.34958","name":"","func":"var gset1=global.get('set1') || '';\ngset1=msg.payload;\nglobal.set('set1',gset1);\n//return global.set('set1',gset1);\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","x":390,"y":200,"wires":[["773faef8.87c59"]]},{"id":"47b99bfc.4f70f4","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":930,"y":200,"wires":[]},{"id":"125ea3f8.4ef76c","type":"ui_button","z":"65ae4e3c.34958","name":"","group":"2d22b189.273a2e","order":34,"width":"3","height":"1","passthru":false,"label":" 控制 LED ON ","tooltip":"","color":"","bgcolor":"","icon":"","payload":"ON","payloadType":"str","topic":"","x":240,"y":320,"wires":[["498a399.6df10c8"]]},{"id":"ca5ee38e.13169","type":"ui_button","z":"65ae4e3c.34958","name":"","group":"2d22b189.273a2e","order":35,"width":"3","height":"1","passthru":false,"label":" 控制 LED OFF","tooltip":"","color":"","bgcolor":"","icon":"","payload":"OFF","payloadType":"str","topic":"","x":240,"y":400,"wires":[["34c04a5d.cc0506"]]},{"id":"498a399.6df10c8","type":"function","z":"65ae4e3c.34958","name":"","func":"var st1=global.get('set1')\nvar st2='';\nif (st1 === 'auto')\n{\n st2='';\n}\nelse\n{\n st2=msg.payload;\n}\n\nif (st1 === 'manual')\n{\n st2=global.get('set2') || '';\n st2=msg.payload;\n global.set('set2',st2);\n}\n\nmsg.payload=st2;\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","x":410,"y":320,"wires":[["c518e61b.672778","d817b5ce.b81628"]]},{"id":"34c04a5d.cc0506","type":"function","z":"65ae4e3c.34958","name":"","func":"var st1=global.get('set1')\nvar st2='';\nif (st1 === 'auto')\n{\n st2='';\n}\nelse\n{\n st2=msg.payload;\n}\n\nif (st1 === 'manual')\n{\n st2=global.get('set2') || '';\n st2=msg.payload;\n global.set('set2',st2);\n}\n\nmsg.payload=st2;\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","x":410,"y":400,"wires":[["c518e61b.672778","5bf8f311.85bacc"]]},{"id":"d817b5ce.b81628","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":610,"y":320,"wires":[]},{"id":"5bf8f311.85bacc","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":610,"y":360,"wires":[]},{"id":"e4f4a5f5.390bd8","type":"mqtt out","z":"65ae4e3c.34958","name":"","topic":"alex9ufo/inTopic/led/led_event","qos":"2","retain":"","broker":"41a78e1b.8ebeb","x":950,"y":260,"wires":[]},{"id":"773faef8.87c59","type":"debug","z":"65ae4e3c.34958","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":530,"y":200,"wires":[]},{"id":"8d650f14.7622d","type":"inject","z":"65ae4e3c.34958","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"auto","payloadType":"str","x":230,"y":200,"wires":[["a743c022.61ec1"]]},{"id":"ef6c54f0.9ae408","type":"inject","z":"65ae4e3c.34958","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"manual","payloadType":"str","x":230,"y":240,"wires":[["a743c022.61ec1"]]},{"id":"8a6c240f.e38eb8","type":"ui_text","z":"65ae4e3c.34958","group":"2d22b189.273a2e","order":6,"width":0,"height":0,"name":"","label":"自動模式下 LDR 大於 2000 時 LED ON","format":"{{msg.payload}}","layout":"row-spread","x":290,"y":100,"wires":[]},{"id":"d81b8836.54b4d8","type":"ui_text","z":"65ae4e3c.34958","group":"2d22b189.273a2e","order":34,"width":"4","height":"2","name":"","label":"LED 狀態","format":"{{msg.payload}}","layout":"row-left","x":540,"y":600,"wires":[]},{"id":"41a78e1b.8ebeb","type":"mqtt-broker","name":"mqtt","broker":"broker.mqtt-dashboard.com","port":"1883","clientid":"","usetls":false,"compatmode":true,"keepalive":"60","cleansession":true,"birthTopic":"","birthQos":"0","birthPayload":"","closeTopic":"","closePayload":"","willTopic":"","willQos":"0","willPayload":""},{"id":"2d22b189.273a2e","type":"ui_group","name":"LDR Sensor","tab":"53b8c8f9.cfbe48","order":2,"disp":true,"width":"6","collapse":false},{"id":"e4d9b72d.d14398","type":"mqtt-broker","name":"","broker":"broker.mqtt-dashboard.com","port":"1883","clientid":"","usetls":false,"compatmode":true,"keepalive":"15","cleansession":true,"birthTopic":"","birthQos":"0","birthPayload":"","closeTopic":"","closePayload":"","willTopic":"","willQos":"0","willPayload":""},{"id":"53b8c8f9.cfbe48","type":"ui_tab","name":"Home","icon":"dashboard","order":2,"disabled":false,"hidden":false}]
沒有留言:
張貼留言