树莓派处理温湿度监控,红外蔽障传感器,超声波测距传感器,激光传感器,有害气体检测,人体感应器,倾斜开关,雨滴传感器,土壤监测
DHT11數(shù)字濕溫度傳感器
1.性能指標(biāo)和特性:
工作電壓范圍:3.5V-5.5V
工作電流:平均0.5mA
濕度測(cè)量范圍:20-90%RH
溫度測(cè)量范圍:0-50℃
濕度分辨率:1%RH???8?位
溫度分辨率:1℃??????8位
采樣周期:1S
2.DHT11?數(shù)據(jù)結(jié)構(gòu)
DHT11數(shù)字濕溫度傳感器采用單總線數(shù)據(jù)格式。即,單個(gè)數(shù)據(jù)引腳端口完成輸
入輸出雙向傳輸。其數(shù)據(jù)包由5Byte(40Bit)組成。數(shù)據(jù)分小數(shù)部分和整數(shù)部分,具
體格式在下面說明。
一次完整的數(shù)據(jù)傳輸為40bit,高位先出。
數(shù)據(jù)格式:8bit濕度整數(shù)數(shù)據(jù)+8bit濕度小數(shù)數(shù)據(jù)
+8bit溫度整數(shù)數(shù)據(jù)+8bit溫度小數(shù)數(shù)據(jù)
+8bit校驗(yàn)和
校驗(yàn)和數(shù)據(jù)為前四個(gè)字節(jié)相加。
傳感器數(shù)據(jù)輸出的是未編碼的二進(jìn)制數(shù)據(jù)。數(shù)據(jù)(濕度、溫度、整數(shù)、小數(shù))之間
應(yīng)該分開處理。如果,某次從傳感器中讀取如下5Byte數(shù)據(jù):
byte4 ? ? ? ? ? ?byte3 ? ? ? ?byte2 ? ? ? ? ?byte1 ? ? ? byte0
00101101?00000000??00011100??00000000?01001001
整數(shù) ? ? ? ? ? ? ? 小數(shù) ? ? ? ? ?整數(shù) ? ? ? ? 小數(shù) ? ? ? ? ?校驗(yàn)和
? ? ? ? ? ? 濕度 ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?溫度 ? ? ? ? ? ? ? ?校驗(yàn)和
由以上數(shù)據(jù)就可得到濕度和溫度的值,計(jì)算方法:
humi (濕度)= byte4 . byte3=45.0 (%RH)
temp (溫度)= byte2 . byte1=28.0 (?℃)
jiaoyan(校驗(yàn))= byte4+ byte3+ byte2+ byte1=73(=humi+temp)(校驗(yàn)正確)
注意:DHT11一次通訊時(shí)間最大3ms,主機(jī)連續(xù)采樣間隔建議不小于100ms。
使用公對(duì)公杜邦線直接與樹莓派連接:
DHT11的正極(+/VCC)連接4號(hào)引腳(5V);數(shù)據(jù)腳連接18號(hào)引腳(BCM 24);負(fù)極(-/GND)連接20號(hào)引腳(GND)。*注意勿將正負(fù)極接反,模塊會(huì)燒毀。
?
使用Adafruit?讀取DHT11?溫濕度傳感器
- 更新軟件包
sudo apt-get update
sudo apt-get install build-essential python-dev
- 從GitHub獲取Adafruit庫
sudo git clone?
https://github.com/adafruit/Adafruit_Python_DHT.git
- 安裝完成后pi文件夾下新增Adafruit_Python_DHT文件夾,進(jìn)入該文件夾安裝該庫。
cd Adafruit_Python_DHT
sudo python setup.py install
sudo python3 setup.py install
- 安裝完成后進(jìn)入examples文件夾運(yùn)行AdfruitDHT.py可以獲得結(jié)果。
cd examples
Python AdafruitDHT.py 11 24
*后面兩個(gè)數(shù)值11代表使用的是DHT11模塊,24代表著所接的GIPO引腳編號(hào)(BCM)。
---------------------------------------------------
手頭上正好有一個(gè)紅外蔽障傳感器,只為測(cè)試簡(jiǎn)單的接法:BCM=4? ?3.3v
#!/usr/bin/python #-*-coding:utf-8-*-import time import RPi.GPIO as GPIO import os GPIO.setmode(GPIO.BCM)GPIO_OUT=4 GPIO.setup(GPIO_OUT,GPIO.IN)a=1def warn():print(a)time.sleep(0.5)while True:if GPIO.input(GPIO_OUT)==0:warn()else:print("i'm OK!!!")GPIO.cleanup()-----------------------------------------------------------------------------------------------
超聲波測(cè)距傳感器HC-SR04
import RPi.GPIO as GPIO import timeTrig_Pin=20 Echo_Pin=21GPIO.setmode(GPIO.BCM)GPIO.setup(Trig_Pin,GPIO.OUT,initial=GPIO.LOW) GPIO.setup(Echo_Pin,GPIO.IN)time.sleep(2)def checkdist():GPIO.output(Trig_Pin,GPIO.HIGH)time.sleep(0.00015)GPIO.output(Trig_Pin,GPIO.LOW)while not GPIO.input(Echo_Pin):passt1=time.time()while GPIO.input(Echo_Pin):passt2=time.time()return (t2-t1)*340*100/2try:while True:print "Distance:%0.2f cm" % checkdist()time.sleep(1) except KeyboardInterrupt:GPIO.cheanup()--------------------------------------------------------------------------------------------------------------
激光傳感器KY-008,寫個(gè)簡(jiǎn)單的范例:當(dāng)超聲測(cè)距低于20cm時(shí)打開激光槍
import RPi.GPIO as GPIO import timeGPIO.setmode(GPIO.BCM)Trig_Pin=20 Echo_Pin=21 JiGuang_Pin=4GPIO.setup(Trig_Pin,GPIO.OUT,initial=GPIO.LOW) GPIO.setup(Echo_Pin,GPIO.IN) GPIO.setup(JiGuang_Pin,GPIO.OUT,initial=GPIO.LOW)time.sleep(2)def checkdist():GPIO.output(Trig_Pin,GPIO.HIGH)time.sleep(0.00015)GPIO.output(Trig_Pin,GPIO.LOW)while not GPIO.input(Echo_Pin):passt1=time.time()while GPIO.input(Echo_Pin):passt2=time.time()return (t2-t1)*340*100/2def open():GPIO.output(JiGuang_Pin,GPIO.HIGH)time.sleep(0.5)GPIO.output(JiGuang_Pin,GPIO.LOW)time.sleep(0.5)while True:d1=checkdist()print "Distance:%0.2f cm" % d1time.sleep(1)if d1<20:open()GPIO.cheanup()------------------------------------------------------------------------------------------
MQ-2有害氣體檢測(cè)傳感器
Python的GPIO庫只能接受引腳的高低電平的變化,因此只需要接線三個(gè)引腳就好:5V電源,地線,和DO接口,這是一款廣泛應(yīng)用于家庭和工廠的氣體泄漏檢測(cè)裝置,適用于液化氣、甲烷、丙烷、丁烷、酒精、氫氣、煙霧等有害氣體的檢測(cè)。
#! /usr/bin/env python3 # encoding=utf-8import RPi.GPIO as GPIO # 導(dǎo)入庫,并進(jìn)行別名的設(shè)置 import timeCHANNEL=20 # 確定引腳口。按照真實(shí)的位置確定 GPIO.setmode(GPIO.BCM) # 選擇引腳系統(tǒng),這里我們選擇了BCM,也可以換BOARD GPIO.setup(CHANNEL,GPIO.IN,pull_up_down=GPIO.PUD_DOWN) #初始化引腳,將引腳設(shè)置為輸入下拉電阻,因?yàn)樵诔跏蓟臅r(shí)候不確定的的引電平,因此這樣設(shè)置是用來保證精準(zhǔn),(但是也可以不寫“pull_up_down=GPIO.PUD_DOWN”)# 帶有異常處理的主程序 try:while True: # 執(zhí)行一個(gè)while死循環(huán)status=GPIO.input(CHANNEL) # 檢測(cè)引腳口的輸入高低電平狀態(tài)#print(status) # 實(shí)時(shí)打印此時(shí)的電平狀態(tài)if status == True: # 如果為高電平,說明MQ-2正常,并打印“OK”print ( ' 正常 ' ) else: # 如果為低電平,說明MQ-2檢測(cè)到有害氣體,并打印“dangerous”print ( ' 檢測(cè)到危險(xiǎn)氣體 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ' )time.sleep(0.1) # 睡眠0.1秒,以后再執(zhí)行while循環(huán) except KeyboardInterrupt: # 異常處理,當(dāng)檢測(cè)按下鍵盤的Ctrl+C,就會(huì)退出這個(gè)>腳本GPIO.cleanup() # 清理運(yùn)行完成后的殘余HC-SR501人體感應(yīng)模塊
代碼實(shí)例:感應(yīng)到有人,二極管點(diǎn)亮
import RPi.GPIO as GPIO import timeGPIO.setwarnings(False) GPIO.setmode(GPIO.BOARD) GPIO.setup(13, GPIO.OUT) #hc-sr501-out GPIO.setup(7, GPIO.IN) #ledwhile True:if GPIO.input(7)==1:nowtime = time.strftime('%m-%d %H:%M:%S',time.localtime(time.time()))print(nowtime)print("狼來了!")GPIO.output(13,GPIO.HIGH)else: passtime.sleep(0.5)GPIO.output(13,GPIO.LOW)time.sleep(5)傾斜傳感器
#!/usr/bin/env python import RPi.GPIO as GPIOTiltPin = 11 #YL-38 Rpin = 12 #led-red Gpin = 13 #led-grendef setup():GPIO.setmode(GPIO.BOARD) # Numbers GPIOs by physical locationGPIO.setup(Gpin, GPIO.OUT) # Set Green Led Pin mode to outputGPIO.setup(Rpin, GPIO.OUT) # Set Red Led Pin mode to outputGPIO.setup(TiltPin, GPIO.IN, pull_up_down=GPIO.PUD_UP) # Set BtnPin's mode is input, and pull up to high level(3.3V)GPIO.add_event_detect(TiltPin, GPIO.BOTH, callback=detect, bouncetime=200)def Led(x): #控制雙色LED燈閃爍的函數(shù)if x == 0:GPIO.output(Rpin, 1) #紅燈亮GPIO.output(Gpin, 0) #綠燈滅if x == 1:GPIO.output(Rpin, 0)GPIO.output(Gpin, 1)def Print(x): #打印按鍵是否傾斜的提示消息if x == 0:print ' *************'print ' * Tilt! *'print ' *************'def detect(chn):Led(GPIO.input(TiltPin)) #控制雙色LED燈閃爍Print(GPIO.input(TiltPin)) #打印按鍵是否傾斜的提示消息def loop():while True:passdef destroy():GPIO.output(Gpin, GPIO.LOW) # Green led offGPIO.output(Rpin, GPIO.LOW) # Red led offGPIO.cleanup() # Release resourceif __name__ == '__main__': # Program start from heresetup()try:loop()except KeyboardInterrupt: # When 'Ctrl+C' is pressed, the child program destroy() will be executed.destroy()雨滴傳感器(數(shù)字信號(hào))
import RPi.GPIO as GPIO import timeGPIO.setmod(GPIO.BCM) GPIO.setup(4,GPIO.IN)while True:if GPIO.input(4):print("no rain")else:print("rain")time.sleep(1)
土壤濕度檢測(cè)傳感器
獲取濕度信息的方式(2種可同時(shí)使用):
從傳感器的D0引腳:土壤濕度大于某個(gè)閾值,則D0輸出0,否則輸出1
從傳感器的A0引腳:獲取到模擬量,更加精確。土壤濕度越大,獲取的模擬量值越大。
樹莓派使用D0
#!/usr/bin/python #coding=utf-8 import RPi.GPIO as GPIO import time #針腳 channel = 21 GPIO.setmode(GPIO.BCM) #定義針腳為input口 GPIO.setup(channel, GPIO.IN) #回調(diào)函數(shù) def callback(channel):if GPIO.input(channel):print ('土壤有點(diǎn)干')else:print ('土壤太濕了')#添加簡(jiǎn)單事件 GPIO.add_event_detect(channel, GPIO.BOTH, bouncetime=200) #添加時(shí)間觸發(fā)的回調(diào)函數(shù) GPIO.add_event_callback(channel, callback)#保持主進(jìn)程不退出 while True:time.sleep(0.1)
ESP32單片機(jī)micropython:數(shù)字量輸出
from machine import Pin import timetr=23 g23 = Pin(tr, Pin.IN) #土壤23信號(hào)def callback(tr):if g23.value()==1:print('太干了')else:print('太濕了')while 1:time.sleep(1)callback(tr)ESP32單片機(jī)micropython:模擬量輸出
?
擴(kuò)展:
————————————————————————————————————
有多種方式將GPIO的輸入導(dǎo)入到程序中,polling( 輪詢 )式 和 interrupt( 中斷 )式( edge detection 邊緣檢測(cè) ),“輪詢”式如果程序在錯(cuò)誤的時(shí)間讀取值,可能會(huì)錯(cuò)過輸入。我們這里采用中斷式。
??如果您沒有將輸入引腳連接到任何東西,它將“浮動(dòng)”。換句話說,讀取的值是未定義的,因?yàn)樗鼪]有連接到任何東西,直到你按下按鈕或開關(guān)。它可能會(huì)由于接收電源干擾而改變很大的值。
??為了解決這個(gè)問題,我們使用一個(gè)向上拉或向下拉電阻器。這樣,就可以設(shè)置輸入的默認(rèn)值。可以使用硬件或者軟件實(shí)現(xiàn)上下拉電阻。在硬件方式中,常常在輸入通道與3.3V(上拉)或0V(下拉)之間使用10K電阻。GPIO模塊允許您在編程中這樣配置:
??我們很多時(shí)候并不關(guān)心電平值, 而關(guān)心電平從低到高,或從高到低的變化(如編碼器測(cè)速/按鍵按下彈開等), 為避免主程序忙于其它事情錯(cuò)過引腳的電平改變, 有兩種方式:
??wait_for_edge() 函數(shù)
??event_detected() 函數(shù)
??wait_for_edge()函數(shù)是為了阻止程序的執(zhí)行,直到檢測(cè)到邊緣為止。換句話說,等待按鈕按下的示例可以改寫成:
?? 注意檢測(cè)的邊緣參數(shù)有 GPIO.RISING, GPIO.FALLING , GPIO.BOTH (上升沿, 下降沿 或 升降沿), 這樣用幾乎不占用CPU,如果你只希望在確定的時(shí)間段內(nèi)查詢,可以使用 timeout 參數(shù):
# wait for up to 5 seconds for a rising edge (timeout is in milliseconds) channel = GPIO.wait_for_edge(channel, GPIO_RISING, timeout=5000) if channel is None:print('Timeout occurred') else:print('Edge detected on channel', channel)??event_detected()函數(shù)被設(shè)計(jì)用來與其他事物一起在循環(huán)中使用, 不同于polling輪詢, 它不會(huì)在CPU忙于處理其他事物時(shí)錯(cuò)過輸入狀態(tài)的變化。 這使得使用Pygame 或 PyQt 時(shí)非常有用,因?yàn)槠渲杏幸粋€(gè)主循環(huán)監(jiān)聽和及時(shí)響應(yīng)GUI事件的基礎(chǔ)。
??只要檢測(cè)到指定參數(shù)的邊緣事件(上升沿, 下降沿 或 升降沿)發(fā)生時(shí),調(diào)用GPIO.event_detected(channel)的值就為"ture"(真)。
??不過需要自己新建一個(gè)線程去循環(huán)檢測(cè)event_detected()的值,還算是比較麻煩的。
??可采用另一種辦法輕松檢測(cè)狀態(tài),這種方式是直接傳入一個(gè)回調(diào)函數(shù):GPIO通過在add_event_detect()函數(shù)中添加callback參數(shù),RPI.GPIO為回調(diào)函數(shù)運(yùn)行第二個(gè)線程。這意味著回調(diào)函數(shù)可以與主程序同時(shí)運(yùn)行,以立即響應(yīng)邊緣。
??例如:
??如果你想要不止一個(gè)回調(diào)函數(shù):
def my_callback_one(channel):print('Callback one') def my_callback_two(channel):print('Callback two') GPIO.add_event_detect(channel, GPIO.RISING) GPIO.add_event_callback(channel, my_callback_one) GPIO.add_event_callback(channel, my_callback_two)??請(qǐng)注意,在這種情況下,回調(diào)函數(shù)是按順序運(yùn)行的,而不是并發(fā)的。這是因?yàn)橹挥幸粋€(gè)線程用于回調(diào),其中每個(gè)回調(diào)都按照它們被定義的順序運(yùn)行。
??由于存在開關(guān)抖動(dòng)(用示波器可以看到),每次按下開關(guān)會(huì)調(diào)用多次回調(diào)函數(shù),這不是我們希望的,有兩種方式處理開關(guān)抖動(dòng):
??①在開關(guān)兩個(gè)引腳之間添加一個(gè)0.1uF的電容
??②軟件消抖
??③二者結(jié)合使用
??使用軟件消抖時(shí), 給回調(diào)函數(shù)添加一個(gè)彈跳時(shí)間的參數(shù)( bouncetime= ), 彈跳時(shí)間(參照單片機(jī)可以為10~20ms)在ms級(jí)別, 下面的程序用200ms來消抖:
??由于某些原因, 你的程序可能不希望用邊緣檢測(cè)了,可以停止它們:
GPIO.remove_event_detect(channel)總結(jié)
以上是生活随笔為你收集整理的树莓派处理温湿度监控,红外蔽障传感器,超声波测距传感器,激光传感器,有害气体检测,人体感应器,倾斜开关,雨滴传感器,土壤监测的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 图片轮转
- 下一篇: C++ 高级数据类型(一)—— 数组