DHT11 stm32 源碼分享
#include "DHT11.h"
//#include "THComPro.h"
#include "RTC_Time.h"
#include "EEProm.h"
//void delay_us(u32 nus);
//void delay_ms(u32 nms);
void Systick_us(unsigned int time)
{
SysTick->LOAD = time * 9;
SysTick->VAL = 0;
SysTick->CTRL |= 0x01;
while (((SysTick->CTRL >> 16) & 0x01) == 0);
SysTick->CTRL &= 0xFFFFE;
}
void Systick_ms(unsigned int time)
{
SysTick->LOAD = time * 9000;
SysTick->VAL = 0;
SysTick->CTRL |= 0x01;
while (((SysTick->CTRL >> 16) & 0x01) == 0);
SysTick->CTRL &= 0xFFFFE;
}
void DHT11_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOE, ENABLE);
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_1;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP;
GPIO_Init(GPIOE,&GPIO_InitStructure);
}
/**
* @brief 設置端口為輸出模式
*/
static void DHT11_IN_Init(void)
{
//P0DIR &= 0x00;
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_1;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_IN_FLOATING;
GPIO_Init(GPIOE,&GPIO_InitStructure);
}
/**
* @brief 設置端口為輸出模式
*/
static void DHT11_OUT_Init(void)
{
//P0DIR |= 0x40;
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_1;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP;
GPIO_Init(GPIOE,&GPIO_InitStructure);
}
/**
* @brief 初始化DHT11,并檢測,檢測成功返回0,否則返回1
*/
void DHT11_Rst(void)
{
DHT11_OUT_Init(); //設置引腳為輸出模式
DHT11_DQ_RESET; //DHT11_DQ = 0;
Systick_ms(19); //Delay_ms(19); //拉低至少18ms
// delay_us(19000);
DHT11_DQ_SET; //DHT11_DQ = 1; //總線拉高20~40us,DHT11會返回一個低電平
Systick_us(10); //Delay_10us();
Systick_us(10); //Delay_10us();
Systick_us(10); //Delay_10us();
//delay_us(10);
DHT11_IN_Init(); //設置管腳為輸入模式,用于讀取DHT11的值
}
/**
* @brief 檢測DHT11,檢測成功返回0,否則返回1
*/
static unsigned int DHT11_Check(void)
{
int retry=0;
while (DHT11_DQ && retry < 100) //復位后,DHT11 響應信號(低電平)會維持 80us
{
retry++;
Systick_us(10); //Delay_us();
}
if(retry >= 100)
{
return 1;
}
else
{
return 0;
}
}
/**
* @brief 從DHT11讀取一個字節
*/
static unsigned int DHT11_Read_Byte(void)
{
unsigned char i;
unsigned char tmp;
unsigned int Data = 0;
for(i=0;i<8;i++)
{
while((!DHT11_DQ)); //開始傳送數據1BIt,會拉低50us,之后拉高
Systick_us(10); //Delay_10us();
Systick_us(10); //Delay_10us();
Systick_us(10); //Delay_10us(); //0信號維持26~28us,1信號維持70us
if(DHT11_DQ)
{
tmp=1; //說明此時信號為高信號
}
else
{
tmp=0; //說明此時信號為低信號
}
Data <<= 1;
Data |= tmp;
while(DHT11_DQ);
}
return Data;
}
unsigned char HumidityVal = 0;
unsigned char TempVal = 0;
/**
* @brief 從DHT11讀取8位數據包
*/
//extern unsigned char MonitorTempReadTime;
void DHT11_Read_Data()
{
unsigned char i = 0;
unsigned char Data_Buff[5];
DHT11_Rst();
if (DHT11_Check() == 0)
{
while((!DHT11_DQ)); //響應信號之后,DHT信號會被拉高80us左右
while(DHT11_DQ); //之后開始傳輸數據,1bit,維持低電平50us左右
for (i = 0; i < 5; i++)
{
Data_Buff[i] = DHT11_Read_Byte();
}
if ((Data_Buff[0]+Data_Buff[1]+Data_Buff[2]+Data_Buff[3]) == Data_Buff[4])
{
HumidityVal = Data_Buff[0];
TempVal = Data_Buff[2];
// DispFlag = 1;
// MonitorTempReadTime = 0;
// OSTaskResume(DISPLAY_TASK_PRIO);
// OSMboxPost(DispMbox, &DispFlag);
// OSTaskDel(SENSOR_TASK_PRIO);
// OSTaskSuspend(PROTOCAL_TASK_PRIO);
// OSTaskSuspend(SENSOR_TASK_PRIO);
}
}
}
//void delay_us(u32 nus)
//{
//// TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStruct;
//// TIM_SetCounter(TIM2, 0);
//// TIM_TimeBaseInitStruct.TIM_Period = nus - 1;
//// TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStruct);
//// TIM_Cmd(TIM2, ENABLE);
//// while (TIM_GetFlagStatus(TIM2, TIM_FLAG_Update) != SET);
//// TIM_Cmd(TIM2, DISABLE);
//// TIM_ClearFlag(TIM2, TIM_FLAG_Update);
//
// TIM1->ARR = nus - 1;
// TIM1->CR1 |= 1;
// TIM1->CNT = 0;
// //while ((TIM2->SR & TIM_FLAG_Update) == (uint16_t)RESET);
// while (TIM1->CNT != TIM1->ARR);
// TIM1->CR1 &= (uint16_t)(~((uint16_t)1));
// TIM1->SR = (uint16_t)~TIM_FLAG_Update;
//}
//void delay_ms(u32 nms)
//{
//// TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStruct;
//// TIM_SetCounter(TIM2, 0);
//// TIM_TimeBaseInitStruct.TIM_Period = nms*1000 - 1;
//// TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStruct);
//// TIM_Cmd(TIM2, ENABLE);
//// while (TIM_GetFlagStatus(TIM2, TIM_FLAG_Update) != SET);
//// TIM_Cmd(TIM2, DISABLE);
//// TIM_ClearFlag(TIM2, TIM_FLAG_Update);
//
// TIM1->ARR = nms*1000 - 1;
// TIM1->CR1 |= 1;
// TIM1->CNT = 0;
// //while ((TIM2->SR & TIM_FLAG_Update) == (uint16_t)RESET);
// while (TIM1->CNT != TIM1->ARR);
// TIM1->CR1 &= (uint16_t)(~((uint16_t)1));
// TIM1->SR = (uint16_t)~TIM_FLAG_Update;
//}
|