最近有個需求如下:
1.需要在工作站偵測溫、溼度。
2.需要用MQTT協定回傳資料。
3.無線傳輸。
4.可以用Arduino IDE來寫程式
因而選用Node MCU 搭配DHT 22 。
以下是Node MCU的連結
http://www.nodemcu.com/index_cn.html
Node MCU 可以用Lua語言進行開發,亦可用Arduino IDE進行開發,本篇使用後者。
本次購買的是 LoLin V3 NodeMcu Lua WIFI Development Board
接線圖如下(我買的模組己經裝4.7K做在電路板上了,這只是示意圖)
DHT22 可以運作在3.3 及5V,所以不必擔心電壓問題。
這裡紀錄一個遇到的問題,
在程式碼,我指定DHT22 的腳位為2 , 但指的不是D2, 而是GPIO2(D4), 參考下圖(圖片取自網路,如有侵權請來信告知)。
接下來在Arduino IDE中安裝相關的Lib
A
dafruit_Sensor
從以下URL下載ZIP檔
https://github.com/adafruit/Adafruit_Sensor
DHT-sensor-lib
https://github.com/adafruit/DHT-sensor-library
下載此ZIP檔
加入.ZIP程式庫。
找到剛才下載的ZIP檔
接下來下載pubsubclient
https://github.com/knolleary/pubsubclient
接下來安裝板子, 打開Arduino的偏好設定,在額外的板子管理員網址加入一行
http://arduino.esp8266.com/stable/package_esp8266com_index.json
按下"好"
接著到板子管理員
安裝一下ESP8266
接下來將板子選擇為Node MCU 1.0 (ESP-12E Module)
接下來要安裝一下USB to UART 驅動,它用的不是和Arduino的一樣,需要額外裝,
否則在序列埠中什麼都看不到。
到這個網址,下載驅動程式,安裝完成後一定要"
重開機"
http://www.wch.cn/download/CH341SER_ZIP.html
重開機後開啟Arduino ,輸入以下程式碼。每六秒左右,就會送一次溫溼度到MQTT Server
程式碼如下:
#include "DHT.h"
#include <ESP8266WiFi.h>
#include <PubSubClient.h>
#define DHTPIN 2 // what digital pin we're connected to
#define DHTTYPE DHT22 // DHT 22 (AM2302), AM2321
// NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1
// to 3.3V instead of 5V!
// Connect pin 2 of the sensor to whatever your DHTPIN is
// Connect pin 4 (on the right) of the sensor to GROUND
// Initialize DHT sensor.
// Note that older versions of this library took an optional third parameter to
// tweak the timings for faster processors. This parameter is no longer needed
// as the current DHT reading algorithm adjusts itself to work on faster procs.
DHT dht(DHTPIN, DHTTYPE);
// Update these with values suitable for your network.
const char* ssid = "your ssid";
const char* password = "your pw";
const char* mqtt_server = "MQTT Server IP";
const char* topic="your Topic";
// WiFi Client
WiFiClient espClient;
// PubSub Client
PubSubClient client(espClient);
long lastMsg = 0;
char msg[50];
int value = 0;
void setup() {
Serial.begin(9600);
Serial.println("DHTxx test!");
setup_wifi();
client.setServer(mqtt_server, 1883);
client.setCallback(callback);
dht.begin();
}
void loop() {
// Wait a few seconds between measurements.
delay(2000);
//Check Wi-Fi is Connected
if (WiFi.status() != WL_CONNECTED)
{
setup_wifi();
}
//Check MQTT Connection
if (!client.connected()) {
reconnect();
}
client.loop();
// Reading temperature or humidity takes about 250 milliseconds!
// Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
float h = dht.readHumidity();
// Read temperature as Celsius (the default)
float t = dht.readTemperature();
// Read temperature as Fahrenheit (isFahrenheit = true)
float f = dht.readTemperature(true);
// Check if any reads failed and exit early (to try again).
if (isnan(h) || isnan(t) || isnan(f)) {
Serial.println("Failed to read from DHT sensor!");
return;
}
// Compute heat index in Fahrenheit (the default)
float hif = dht.computeHeatIndex(f, h);
// Compute heat index in Celsius (isFahreheit = false)
float hic = dht.computeHeatIndex(t, h, false);
Serial.print("Humidity: ");
Serial.print(h);
Serial.print(" %\t");
Serial.print("Temperature: ");
Serial.print(t);
Serial.print(" *C ");
Serial.print(f);
Serial.print(" *F\t");
Serial.print("Heat index: ");
Serial.print(hic);
Serial.print(" *C ");
Serial.print(hif);
Serial.println(" *F");
long now = millis();
// read DHT22 sensor every 6 seconds
if (now - lastMsg > 6000) {
lastMsg = now;
String msg=String(h)+","+String(t);
Serial.println(msg);
char message[msg.length()];
msg.toCharArray(message,msg.length());
//publish sensor data to MQTT broker
client.publish(topic, message);
}
}
void setup_wifi() {
delay(100);
// We start by connecting to a WiFi network
Serial.print("Connecting to ");
Serial.println(ssid);
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED)
{
delay(500);
Serial.print(".");
}
randomSeed(micros());
Serial.println("");
Serial.println("WiFi connected");
Serial.println("IP address: ");
Serial.println(WiFi.localIP());
}
// recieve Topic message handler , I don't implements it
void callback(char* topic, byte* payload, unsigned int length)
{
}
void reconnect() {
// Loop until we're reconnected
while (!client.connected())
{
Serial.print("Attempting MQTT connection...");
// Create a random client ID
String clientId = "ESP8266Client-";
clientId += String(random(0xffff), HEX);
// Attempt to connect
//if you MQTT broker has clientID,username and password
//please change following line to if (client.connect(clientId,userName,passWord))
if (client.connect(clientId.c_str()))
{
Serial.println("connected");
//once connected to MQTT broker, subscribe command if any
client.subscribe(topic);
} else {
Serial.print("failed, rc=");
Serial.print(client.state());
Serial.println(" try again in 5 seconds");
// Wait 6 seconds before retrying
delay(6000);
}
}
} //end reconnect()
燒錄完成後,建議按一下RST按鈕,讓它重啟。