STM32外设驱动篇——DHT11温湿度传感器

发布者:EtherealGlow最新更新时间:2017-09-23 来源: eefocus关键字:STM32  外设驱动  DHT11  温湿度传感器 手机看文章 扫描二维码
随时随地手机看文章

已在STM32上进行过测试。本例使用PC0引脚连接DHT11的data引脚。

main函数中调用下面代码中的DTH11_test函数即可。


  1. //数据定义:  

  2.     //----以下变量均为全局变量--------  

  3.     //----温度高8位== U8T_data_H------  

  4.     //----温度低8位== U8T_data_L------  

  5.     //----湿度高8位== U8RH_data_H-----  

  6.     //----湿度低8位== U8RH_data_L-----  

  7.     //----校验 8位 == U8checkdata-----  

  8. u8  U8T_data_H,U8T_data_L,U8RH_data_H,U8RH_data_L,U8checkdata;  

  9. u8  U8T_data_H_temp,U8T_data_L_temp,U8RH_data_H_temp,U8RH_data_L_temp,U8checkdata_temp;  

  10.   

  11. #define BOOL unsigned char  

  12.   

  13. #ifndef TRUE  

  14. #define TRUE 1  

  15. #endif  

  16.   

  17. #ifndef FALSE  

  18. #define FALSE 0  

  19. #endif  

  20.   

  21. static void DHT11_DataPin_Configure_Output(void)  

  22. {  

  23.      GPIO_InitTypeDef  GPIO_InitStructure;  

  24.       

  25.     //RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, DISABLE);  

  26.     RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE);     //使能PC端口时钟  

  27.                   

  28.      GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;                 //PC.0 端口配置  

  29.      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;          //推挽输出  

  30.      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;  

  31.      GPIO_Init(GPIOC, &GPIO_InitStructure);  

  32. }  

  33.   

  34. static void DHT11_DataPin_Configure_Input(void)  

  35. {  

  36.        GPIO_InitTypeDef  DataPin;       

  37.       

  38.      DataPin.GPIO_Pin = GPIO_Pin_0;                  

  39.      DataPin.GPIO_Mode = GPIO_Mode_IN_FLOATING;         //悬空       

  40.      DataPin.GPIO_Speed = GPIO_Speed_50MHz;  

  41.     GPIO_Init(GPIOC, &DataPin);  

  42. }  

  43. BOOL DHT11_get_databit(void)  

  44. {  

  45.     uint8_t val;  

  46.       

  47.      val = GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_0);  

  48.     if(val == Bit_RESET){  

  49.         return FALSE;  

  50.     }else{  

  51.         return TRUE;  

  52.     }  

  53. }  

  54.   

  55. void DHT11_set_databit(BOOL level)  

  56. {  

  57.     if(level == TRUE){  

  58.         GPIO_SetBits(GPIOC, GPIO_Pin_0);  

  59.     }else{  

  60.         GPIO_ResetBits(GPIOC, GPIO_Pin_0);  

  61.     }  

  62. }  

  63.   

  64. void mdelay(u16 ms)    

  65. {  

  66.     if(ms != 0){  

  67.         delay_ms(ms);  

  68.     }  

  69. }  

  70.   

  71. void udelay(u16 us)    

  72. {  

  73.     if(us != 0){  

  74.         delay_us(us);  

  75.     }  

  76. }  

  77. static uint8_t DHT11_read_byte(void)  

  78. {       

  79.     uint8_t i;    

  80.     uint8_t data = 0;      

  81.                          

  82.     for(i = 0; i < 8; i++)         

  83.     {      

  84.         data <<= 1;          

  85.            while((!DHT11_get_databit()));  

  86.         udelay(10);  

  87.         udelay(10);  

  88.         udelay(10);  

  89.   

  90.         if(DHT11_get_databit())    {  

  91.             data |= 0x1;  

  92.             while(DHT11_get_databit());  

  93.         } else{  

  94.           

  95.         }   

  96.   

  97.      }  

  98.                            

  99.      return data;  

  100. }  

  101.     

  102. static uint8_t DHT11_start_sampling(void)  

  103. {  

  104.     DHT11_DataPin_Configure_Output();  

  105.       //主机拉低18ms     

  106.     DHT11_set_databit(FALSE);  

  107.     mdelay(18);  

  108.     DHT11_set_databit(TRUE);  

  109.      //总线由上拉电阻拉高 主机延时20us  

  110.     udelay(10);  

  111.     udelay(10);  

  112. //    udelay(10);  

  113. //    udelay(10);  

  114.      //主机设为输入 判断从机响应信号   

  115.     DHT11_set_databit(TRUE);  

  116.   

  117.     DHT11_DataPin_Configure_Input();  

  118.   

  119.      //判断从机是否有低电平响应信号 如不响应则跳出,响应则向下运行        

  120.     if(!DHT11_get_databit())         //T !        

  121.     {  

  122.      //判断从机是否发出 80us 的低电平响应信号是否结束       

  123.        while((!DHT11_get_databit()));  

  124.       // printf("DHT11 answers.\r\n");  

  125.      //判断从机是否发出 80us 的高电平,如发出则进入数据接收状态  

  126.        while((DHT11_get_databit()));  

  127.        return 1;  

  128.     }  

  129.   

  130.     return 0;                 

  131. }  

  132.   

  133. void DHT11_get_data(void)  

  134. {        

  135.     u8 temp;  

  136.     if(DHT11_start_sampling()){  

  137.         //printf("DHT11 is ready to transmit data\r\n");  

  138.         //数据接收状态           

  139.         U8RH_data_H_temp = DHT11_read_byte();  

  140.         U8RH_data_L_temp = DHT11_read_byte();  

  141.         U8T_data_H_temp     = DHT11_read_byte();  

  142.         U8T_data_L_temp     = DHT11_read_byte();  

  143.         U8checkdata_temp = DHT11_read_byte();  

  144.   

  145.         /* Data transmission finishes, pull the bus high */  

  146.         DHT11_DataPin_Configure_Output();     

  147.         DHT11_set_databit(TRUE);  

  148.         //数据校验   

  149.   

  150.         temp=(U8T_data_H_temp+U8T_data_L_temp+U8RH_data_H_temp+U8RH_data_L_temp);  

  151.         if(temp==U8checkdata_temp)  

  152.         {  

  153.             U8RH_data_H=U8RH_data_H_temp;  

  154.             U8RH_data_L=U8RH_data_L_temp;  

  155.             U8T_data_H=U8T_data_H_temp;  

  156.             U8T_data_L=U8T_data_L_temp;  

  157.             U8checkdata=U8checkdata_temp;  

  158.   

  159.             printf("DHT11 tempature %d.%d  humidity %d.%d \r\n",   

  160.                 U8T_data_H,  

  161.                 U8T_data_L,  

  162.                 U8RH_data_H,  

  163.                 U8T_data_L);  

  164.   

  165.        }else{  

  166.             printf("checksum failure \r\n");  

  167.        }   

  168.     }else{  

  169.         printf("DHT11 didn't answer. Sampling failed. \r\n");  

  170.     }  

  171. }  

  172.   

  173. void DTH11_test()  

  174. {  

  175.     while(1)  

  176.     {  

  177.         DHT11_get_data();  

  178.         delay_ms(1000);      

  179.     }  

  180. }  


关键字:STM32  外设驱动  DHT11  温湿度传感器 引用地址:STM32外设驱动篇——DHT11温湿度传感器

上一篇:STM32调试485(sp3485)技术总结
下一篇:STM32外设驱动篇——AT24C02(I2C接口)

推荐阅读最新更新时间:2024-03-16 15:38

STM32中断优先级谁更高 主要根据两个方面来判断
一:综述 STM32 目前支持的中断共为 84 个(16 个内核+68 个外部), 16 级可编程中断优先级 的设置(仅使用中断优先级设置 8bit 中的高 4 位)和16个抢占优先级(因为抢占优先级最多可以有四位数)。 二:优先级判断 STM32(Cortex-M3)中有两个优先级的概念——抢占式优先级和响应优先级,有人把响应优先级称作‘亚优先级’或‘副优先级’,每个中断源都需要被指定这两种优先级。 具有高抢占式优先级的中断可以在具有低抢占式优先级的中断处理过程中被响应,即中断嵌套,或者说高抢占式优先级的中断可以嵌套低抢占式优先级的中断。 当两个中断源的抢占式优先级相同时,这两个中断将没有嵌套关系,当一个中断到来后,如果正在
[单片机]
STM32笔记记录
串口记录: STM32有好几个串口。比如说STM32F103ZET6有5个串口,串口1的引脚对应的IO为PA9,PA10.PA9,PA10默认功能是GPIO,所以当PA9,PA10引脚作为串口1的TX,RX引脚使用的时候,那就是端口复用。 复用端口初始化有几个步骤: 1) GPIO端口时钟使能。要使用到端口复用,当然要使能端口的时钟了。 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); 2) 复用的外设时钟使能。比如你要将端口PA9,PA10复用为串口,所以要使能串口时钟。 RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,
[单片机]
<font color='red'>STM32</font>笔记记录
STM32 HSE初始化失败的解决以及HSI初始化
偶然遇到一个问题,假设HSE初始化失败怎么办,库函数内没有提供处理只是写了 if (HSEStatus == (uint32_t)0x01) { 。。。 } else { /* If HSE fails to start-up, the application will have wrong clock configuration. User can add here some code to deal with this error */ } 让我们自己处理。平常我们都是用SysClk =72M。这是在HSE的情况下才能达到的。如果HSE初始化不成功只能使用HSI。注意上图时钟树HS
[单片机]
<font color='red'>STM32</font> HSE初始化失败的解决以及HSI初始化
玩转STM32(11)CPU的心跳历程
前面说CPU怎么样才有脉搏,也就是给CPU装了一个心脏,这样这个由泥沙组成的CPU才能开始拥有像生命的力量了。在前文后面,提到了使用25MHz晶振作为外部的频率来源,但是我们的目标是让CPU工作在168MHz的频率,这样才可以让CPU工作得更快,运行代码更快,效率更高。当然,如果你想让CPU工作在25MHz也是可以的,只是有点不值得,用这么贵的硬件,运行这么低的频率。要想快,就得提高CPU运行的频率,那么怎么样才可以把25MHz的频率转换为168MHz的频率呢?可以看到168M是比25M频率高很多,显然要使用到倍频电路,也要使用到分频电路。比如把25M按25分频系数来分频,那么得到频率就是1M,然后再使用倍频电路,比如使用336作
[单片机]
玩转<font color='red'>STM32</font>(11)CPU的心跳历程
STM32学习:ADC/DMA/USART
  学习STM32的ADC转换,在开发板上写程序调试。   四个任务:   1.AD以中断方式(单次)采集一路   2.AD以中断方式连续采集四路   3.AD以DMA方式采集一路,DMA深度为一级   4.AD以DMA方式采集四路,每路DMA深度为28级,并滤波,说明滤波原理。   总结:   第一个任务:ADC以中断方式采集一路ADC,通过配置ADC_InitStructure结构体中的ADC_ScanConvMode,它规定模数转换工作在扫描模式(多通道)还是单次模式(单通道),   ADC_InitStructure.ADC_ScanConvMode=DISABLE,为单通道单次模式。   ADC_ContinuousCo
[单片机]
Stm32定时器中断使LED灯闪烁
知识点: Stm32共有11个定时器: 1.两个高级定时器:TIM1、TIM8-------------------------APB2 2.四个通用定时器:TIM2~TIM5-------------------------APB1 3.两个基本定时器:TIM6、TIM7-------------------------APB1 4.两个看门狗 5.一个系统嘀嗒定时器(SysTick) 主程序main.c: /* *说明: *PA0:KEY1;PA1:KEY2; *PA2:LED1;PA3:LED2; *PA9:USART1_TX;PA10:USART1_RX */ #inclu
[单片机]
8051单片机和STM32单片机的编程环境对比
单片机编程是一门实战性的技术,程序要在单片机平台上跑起来才能看到效果、才能积累编程经验。在学校学习单片机课程时,可能会感觉到一直有一种脱节的感觉,因为一直没有用武之地。其实学习单片机很简单,第一步就是搞清楚编程环境。 入门单片机时,我们常用51型8051单片机和STM32单片机。这两种单片机比较典型,因为学校里单片机课程是基于51单片机的,而STM32的单片机则具有较多的学习资料。下面就这两种单片机介绍一下编程环境。 1、单片机常用的编程环境 比较流行的单片机环境有keil和IAR,这两种环境可以覆盖市面上90%的单片机型号,而且都提供了函数库。根据单片机位数不同,这两个编程环境也有不同的版本。 1.1 Keil的常用版本
[单片机]
8051单片机和<font color='red'>STM32</font>单片机的编程环境对比
STM32 EXIT
这张图是一条外部中断线或外部事件线的示意图,途中信号线上划有一条斜线,旁边标志19字样的注释,表示这样的线路共有19套,途中的蓝色虚线箭头,标出了外部中断信号的传输路径,首先外部信号从编号1的芯片管脚进入,经过编号2的边沿检测电路,通过编号3的或门进入中断挂起请求寄存器,最后经过编号4的与门输入到NVIC中断控制器,在这个通道上游4个控制选项,外部的信号收件经过边沿检测电路,这个边沿检测电路受上升沿或下降沿选择寄存器控制,用户可以使用这两个寄存器控制需要哪一个边沿产生中断,因为选择上升沿或下降沿是分别受2个平行的寄存器控制,所以用户可以同时选择上升沿或是下降沿,而如果只有一个寄存器控制,那么只能选择一个边沿了,接下
[单片机]
<font color='red'>STM32</font> EXIT
小广播
添点儿料...
无论热点新闻、行业分析、技术干货……
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved