本文將展示如何基于涂鴉智能平臺搭建一個屬于自己的超聲波氣象站!
超聲波氣象站的測量維度包括:
- 溫度測量(DHT22)
- 濕度測量(DHT22)
- 氣壓測量(BMP180)
- 風向、風速測量(防水超聲波測距模組)
- PM2.5測量(GP2Y1014AU)
也就是六個維度的氣象信息的測量!
氣象站采用ESP32作為主控,使用Arduino平臺進行開發,開發IDE為Visual Studio Code + Platform IO。
物聯網通訊方面使用涂鴉WBR3模組,使用低代碼MCU開發形式。控制界面(APP)使用涂鴉的客制化面板。
Q1: 什么是超聲波氣象站?
A1: 超聲波氣象站是利用超聲波模組對聲速進行測量的一種氣象站。由于風速會引起聲速的變化:超聲波順風傳播時,聲速會加快;逆風時風速將減慢;通過測量一組正交的聲速矢量,進行合成分析后可以分析出當前的風速、風向信息。
Q2: 超聲波氣象站有什么優點?
A2: 傳統的氣象站對于風向和風速的測量通常使用風向儀和風速儀,這兩種儀器都具有轉動的機械結構,體積龐大、壽命較短。使用超聲波對風速、風向測量可以壓縮氣象站體積、提高氣象站壽命。
Q3: 為什么選擇涂鴉平臺?
A3: 涂鴉平臺的開發比較省事。在MCU低代碼開發的方式中,可以通過網頁實現對APP的設計,而且一些常用的組件也非常精美。
系統框架
如何利用超聲波對風速進行測量
超聲波探頭布置如圖所示,兩組探頭互相垂直分布。
- 此時若A組探頭間距離S已知,聲速C已知,且此時風速為0。則此時超聲波的行進速度T為聲速,可算出無風時超聲波從發射探頭移動到接收探頭的時間T1=S/C。
- 若此時存在風向為發射探頭指向接收探頭,風速為1m/s的風,則超聲波行進速度變為C+1m/s,同樣可以算出該情況下超聲波從發射探頭移動到接收探頭的時間T2=S/(C+1)。
在距離已知、聲速已知的情況下,通過獲取超聲波模塊返回的超聲波行進時間T2,可以推算出A組探頭方向的風速V1=(S / T2) - (S / T1)。同理可推算出B組探頭方向的風速V2。
由于A、B組探頭垂直分布,故當存在任意方向、任意大小的風時,可通過矢量合成的方法計算出風速和風向。
模塊及驅動
DHT22
DHT22使用DHT-Sensor-Library進行驅動,詳細方法參考GitHub頁面,使用該庫需要依賴Adafruit Unified Sensor Driver庫。
DHT dht(DHT_PIN, DHT_TYPE);
float h = dht.readHumidity();
float t = dht.readTemperature();
if(isnan(h) || isnan(t)){
Serial.println("Failed to read from DHT sensor.");
return;
}
此處h獲取值為濕度,t獲取值為溫度。
BMP180
BMP180使用Adafruit BMP085 Library驅動,同上,需要依賴Adafruit BrushIO庫。
Adafruit_BMP085 bmp;
air_pressure = bmp.readPressure()
超聲波模組
// Clears the trigPin condition
digitalWrite(TRIG_1, LOW);
delayMicroseconds(2);
// Sets the trigPin HIGH (ACTIVE) for 10 microseconds
digitalWrite(TRIG_1, HIGH);
delayMicroseconds(20);
digitalWrite(TRIG_1, LOW);
// Reads the echoPin, returns the sound wave travel time in microseconds
duration = pulseIn(ECHO_1, HIGH);
超聲波模組使用脈沖測量獲取反射時間,代碼如上。后續通過布置探頭位置,分析兩組超聲波模組的反射時間可獲得風速、風向信息。
CJMCU-GUVA-S12SD紫外線模組
該紫外線模組輸出為電壓模擬量,analogRead()函數可以實現紫外線等級的測量。
GP2Y1014AU PM2.5模組
digitalWrite(DUST_IN, LOW);
delayMicroseconds(SAMPLING_TIME);
int voMeasured = analogRead(DUST_OUT);
?
delayMicroseconds(DELTA_TIME);
digitalWrite(DUST_IN, HIGH);
通過給模組的LED驅動腳施加脈沖,測量輸出腳電壓,可以實現對pm2.5的濃度測量。
涂鴉智能接入
這次的開發方式為MCU低代碼開發,即是利用涂鴉模組進行開發。涂鴉模組負責物聯網信息處理,MCU僅需要通過串口控制涂鴉模組進行物聯網信息的通訊。
創建產品
在進行涂鴉智能的開發時,需要進行產品創建。作為氣象站開發,可以選擇溫濕度傳感器。
DP點創建
在涂鴉智能中,每個氣象數據維度可以被抽象為DP(功能點)。在選擇了溫濕度傳感器這個產品后,涂鴉提供了常用的功能點:
DP ID | 功能點名稱 | 標識符 | 數據傳輸類型 | 數據類型 | 功能點屬性 |
1 | 溫度 | temp_current | 只上報(ro) | 數值型(Value) | 數值范圍: -200-600, 間距: 1, 倍數: 1, 單位: ℃ |
2 | 濕度 | humidity_value | 只上報(ro) | 數值型(Value) | 數值范圍: 0-100, 間距: 1, 倍數: 0, 單位: % |
4 | 電池電量 | battery_percentage | 只上報(ro) | 數值型(Value) | 數值范圍: 0-100, 間距: 1, 倍數: 0, 單位: % |
除了這些標準功能中的DP點之外,因為我們還需要風速、風向這些數據,所以還需要添加自定義的DP點:
| 功能點名稱 | 標識符 | 數據傳輸類型 | 數據類型 | 功能點屬性 |
101 | PM2.5濃度 | pm25 | 只上報(ro) | 數值型(Value) | 數值范圍: 0-100, 間距: 1, 倍數: 0, 單位: |
102 | 風向角 | wind_value | 只上報(ro) | 數值型(Value) | 數值范圍: 0-364, 間距: 1, 倍數: 1, 單位: |
103 | 風向 | wind_direction | 只上報(ro) | 字符型(String) | |
104 | 風速 | wind_speed | 只上報(ro) | 數值型(Value) | 數值范圍: 0-100, 間距: 1, 倍數: 1, 單位: |
105 | 紫外線等級 | uv_level | 只上報(ro) | 數值型(Value) | 數值范圍: 0-10, 間距: 1, 倍數: 0, 單位: |
106 | 氣壓 | pressure | 只上報(ro) | 數值型(Value) | 數值范圍: 0-1999, 間距: 1, 倍數: 0, 單位: hPa |
在功能點中,DP ID為該功能點的標識,MCU在控制涂鴉模組進行數據上傳時需要用到。
功能點屬性中的倍數為0時,MCU上傳的數據被識別為上傳的數據本身。若倍數為1,則此時若上傳數據為50時,該數據將被涂鴉除以10^1,即50會被識別為5。
面板編輯
在產品開發的面板選項卡,可以對自己的APP面板進行自定義。
我使用的面板類型為:面板類型:Studio 面板-個人面板
下面是在手機中的實機效果:
硬件開發
在完成了傳感器驅動、電源板管理后,需要與涂鴉模組進行通訊,實現信息上報。
在這里我選擇的是WBR3 Wi-Fi & Bluetooth 模組。
該模組在初次上電時,可以打開智能生活APP實現配網和面板加載,在完成了配網之后就可以進行實時開發了。
// define dp
#define temp_pid 1
#define humi_pid 2
#define battery_pid 4
#define pm25_pid 101
#define wind_angle_pid 102
#define wind_direct_pid 103
#define wind_speed_pid 104
#define uv_level_pid 105
#define pressure_pid 106
?
// Create TuyaWifi object
TuyaWifi my_device;
?
// input your device pid here
unsigned char pid[] = {""};
// select mcu version, 1.0.0 as commonly use
unsigned char mcu_ver[] = {"1.0.0"};
?
// create an array to restore the datapoint
unsigned char dp_array[][2] =
{
{temp_pid, DP_TYPE_VALUE},
{humi_pid, DP_TYPE_VALUE},
{battery_pid, DP_TYPE_VALUE},
{pm25_pid, DP_TYPE_VALUE},
{wind_angle_pid, DP_TYPE_VALUE},
{wind_direct_pid, DP_TYPE_STRING},
{wind_speed_pid, DP_TYPE_VALUE},
{uv_level_pid, DP_TYPE_VALUE},
{pressure_pid, DP_TYPE_VALUE},
};
?
unsigned char dp_process(unsigned char dpid,const unsigned char value[], unsigned short length)
{
/* all DP only report */
return TY_SUCCESS;
}
?
void dp_update_all(void)
{
}
?
void setup(){
...
my_device.init(pid, mcu_ver);
my_device.set_dp_cmd_total(dp_array, 9);
// register call back function
my_device.dp_process_func_register(dp_process);
my_device.dp_update_all_func_register(dp_update_all);
}
?
void loop() {
// SDK handle
my_device.uart_service();
// Check the wifi connection
if ((my_device.mcu_get_wifi_work_state() == WIFI_CONNECTED) || (my_device.mcu_get_wifi_work_state() == WIFI_CONN_CLOUD)) {
update_sensor();
// report all the data
my_device.mcu_dp_update(temp_pid, temp, 1);
my_device.mcu_dp_update(humi_pid, humi, 1);
my_device.mcu_dp_update(battery_pid, battery_level, 1);
my_device.mcu_dp_update(pm25_pid, pm25, 1);
my_device.mcu_dp_update(wind_angle_pid, wind_angle, 1);
my_device.mcu_dp_update(wind_speed_pid, wind_speed, (sizeof(dp_string_value) / sizeof(dp_string_value[0])));
my_device.mcu_dp_update(wind_speed_pid, wind_speed, 1);
my_device.mcu_dp_update(uv_level_pid, uv_index, 1);
my_device.mcu_dp_update(pressure_pid, air_pressure, 1);
}
...
MCU工作流程
-
物聯網
+關注
關注
2912文章
44912瀏覽量
375886 -
超聲波
+關注
關注
63文章
3039瀏覽量
138577 -
模組
+關注
關注
6文章
1515瀏覽量
30537 -
氣象站
+關注
關注
1文章
759瀏覽量
15719 -
涂鴉智能
+關注
關注
7文章
217瀏覽量
19512
發布評論請先 登錄
相關推薦
評論