You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

150 lines
5.7 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

# 使用方法: 接线 DHT11的三个引脚(如果是四个引脚NC不连接) VCC接5V GND接地 数据D接任意树莓派GPIO口
# 并将数据D接的树莓派GPIO口BCM编号设置为下面的pin
# 然后你可以直接运行本文件得到数值也可以使用import dht11_drive导入模块
# 导入后使用 dht11_drive.dht11() 函数获取湿度与温度 返回值是一个元组
import RPi.GPIO as GPIO
import time
import jiqiren as jqr
import MySQL as m
def celiang(pin):
GPIO.setup(pin, GPIO.OUT) # 設置引腳輸出
GPIO.output(pin, True) # 高电平
# 树莓派下拉19ms
GPIO.output(pin, False)
time.sleep(0.02)
# GPIO.output(pin,True)
GPIO.setup(pin, GPIO.IN) # 设置引腳输入
time_data_list = [] # 保存数据(高电平持续)时间的列表
pan_duan = 1 # 判断数据是否正确
end_times = 0 # 数据是否接收完毕 决定是否结束大循环
start_time = 0 # 防止start_time未定义
end_time = 0 # 防止end_time未定义
while 1:
start_time_total = time.time() # 记录每次运行循环开始时间
if end_times == 1: # 数据接收完毕
break
while GPIO.input(pin) == 0: # 等待电平不为低
start_time = time.time() # 得到高电平开始时间
if (start_time - start_time_total) > 0.1: # 判断循环时间过长 电平已经不再变化
end_times = 1
break
while GPIO.input(pin) == 1: # 等待电平不为高
end_time = time.time() # 得到高电平结束时间
if (end_time - start_time_total) > 0.1: # 判断循环时间过长 电平已经不再变化
end_times = 1
break
time_data = end_time - start_time # 计算出高电平持续时间
time_data_list.append(time_data) # 高电平持续时间数据写入列表
# print(str(time_data)+', ', end='')
# print(time_data_list)
# print(len(time_data_list))
new_time_data_list = [] # 保存筛选过的时间
for i in range(len(time_data_list)):
if (time_data_list[i] > 1.9e-5) and (time_data_list[i] < 7.8e-5):
new_time_data_list.append(time_data_list[i])
# print(new_time_data_list)
# print(len(new_time_data_list))
if len(new_time_data_list) != 40:
pan_duan = 0 # 判断数据是否正确
return pan_duan, '接收到的数据位数不足,请重新尝试'
if pan_duan == 1: # 判断数据是否正确
Binary_list = [] # 保存二进制数据
for i in new_time_data_list:
if i > 5.0e-5:
Binary_list.append(1)
elif i < 5.0e-5:
Binary_list.append(0)
if len(Binary_list) != 40:
pan_duan = 0 # 判断数据是否正确
return pan_duan, '数据位数不足,请重新尝试'
# print(Binary_list)
# print(len(Binary_list))
if pan_duan == 1: # 判断数据是否正确
# 转字符串格式
str_Binary_list = []
for i in Binary_list:
str_Binary_list.append(str(i))
if pan_duan == 1: # 判断数据是否正确
# 分割数据 并合并成字符串
# 共40位数据 0-8为湿度整数 9-16为湿度小数 17-24为温度整数 25-32为湿度小数 33-40为校验和前四个数据直接相加
str_shidu_zhengshu = ''.join(str_Binary_list[0:8])
str_shidu_xiaoshu = ''.join(str_Binary_list[8:16])
str_wendu_zhengshu = ''.join(str_Binary_list[16:24])
str_wendu_xiaoshu = ''.join(str_Binary_list[24:32])
str_yanzheng = ''.join(str_Binary_list[32:40])
# 转换为十进制
int_shidu_zhengshu = int(str_shidu_zhengshu, 2)
int_shidu_xiaoshu = int(str_shidu_xiaoshu, 2)
int_wendu_zhengshu = int(str_wendu_zhengshu, 2)
int_wendu_xiaoshu = int(str_wendu_xiaoshu, 2)
int_yanzheng = int(str_yanzheng, 2)
if int_yanzheng != (int_shidu_zhengshu + int_shidu_xiaoshu + int_wendu_zhengshu + int_wendu_xiaoshu):
pan_duan = 0 # 数据不正确
return pan_duan, '校验和不匹配,请重新尝试'
if int_yanzheng == (int_shidu_zhengshu + int_shidu_xiaoshu + int_wendu_zhengshu + int_wendu_xiaoshu):
pan_duan = 1 # 数据正确
str_shidu = str(int_shidu_zhengshu) + '.' + str(int_shidu_xiaoshu)
str_wendu = str(int_wendu_zhengshu) + '.' + str(int_wendu_xiaoshu)
float_shidu = float(str_shidu)
float_wendu = float(str_wendu)
return pan_duan, (float_shidu, float_wendu) # 返回 湿度 温度
def dht11(pin): # 循环五次
for i in range(5):
pan_duan_01, return_data = celiang(pin)
if pan_duan_01 == 1:
return return_data
# time.sleep(0.5)
# print('错误')
return 0, 0
def wsd():
#############################################################
pin = 4 # 这里填写GPIO号BCM引脚编号模式 手动改变此行
#############################################################
GPIO.setmode(GPIO.BCM) # 设置使用BCM引脚编号模式
while True:
shidu, wendu = dht11(pin)
if shidu and wendu:
num = m.th_select("max(number)")[0][0]+1
t = time.strftime('%Y-%m-%d %H:%M:%S')
m.th_insert(str(num), t, str(wendu), str(shidu)) # 将数据保存至数据库
text = '湿度为' + str(shidu) + '%' + ',温度为' + str(wendu) + '℃。'
print("小溪说:", text)
txt = '湿度为百分之' + str(shidu) + ',温度为' + str(wendu) + '摄氏度。'
jqr.robotSay.say(txt)
GPIO.cleanup(pin)
break
else:
continue
GPIO.cleanup(pin)