具体实现
完整代码开源地址-Gitee
完整代码开源地址-Github
采集温度、湿度
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
|
u8 DHT11_Read_Data(u8 *temp,u8 *humi) { u8 buf[5]; u8 i; DHT11_Rst(); if(DHT11_Check()==0) { for(i=0;i<5;i++) { buf[i]=DHT11_Read_Byte(); } if((buf[0]+buf[1]+buf[2]+buf[3])==buf[4]) { *humi=buf[0]; *temp=buf[2]; } }else return 1; return 0; }
|
color:green DHT11相关代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50
|
u8 DHT11_Init() { GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOG,ENABLE);
GPIO_InitStructure.GPIO_Pin=DHT11; GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; GPIO_Init(GPIO_DHT11,&GPIO_InitStructure); GPIO_SetBits(GPIO_DHT11,DHT11);
DHT11_Rst(); return DHT11_Check(); }
void DHT11_Rst() { DHT11_IO_OUT(); DHT11_DQ_OUT=0; delay_ms(20); DHT11_DQ_OUT=1; delay_us(30); }
u8 DHT11_Check() { u8 retry=0; DHT11_IO_IN(); while (DHT11_DQ_IN&&retry<100) { retry++; delay_us(1); }; if(retry>=100)return 1; else retry=0; while (!DHT11_DQ_IN&&retry<100) { retry++; delay_us(1); }; if(retry>=100)return 1; return 0; }
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
|
u8 DHT11_Read_Bit(void) { u8 retry=0; while(DHT11_DQ_IN&&retry<100) { retry++; delay_us(1); } retry=0; while(!DHT11_DQ_IN&&retry<100) { retry++; delay_us(1); } delay_us(40); if(DHT11_DQ_IN)return 1; else return 0; }
u8 DHT11_Read_Byte(void) { u8 i,dat; dat=0; for (i=0;i<8;i++) { dat<<=1; dat|=DHT11_Read_Bit(); } return dat; }
|
采集光照
通过ADC3模数转换器采集电压(为模拟量)
1 2 3 4 5 6 7 8 9 10 11 12 13
| u8 Lsens_Get_Val(void) { u32 temp_val=0; u8 t; for(t=0;t<LSENS_READ_TIMES;t++) { temp_val+=Get_ADC3(ADC_Channel_6); delay_ms(5); } temp_val/=LSENS_READ_TIMES; if(temp_val>4000)temp_val=4000; return (u8)(100-(temp_val/40)); }
|
color:green ADC3初始化及读取数据代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
| void Lsens_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; ADC_InitTypeDef ADC_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOF,ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC3, ENABLE ); RCC_APB2PeriphResetCmd(RCC_APB2Periph_ADC3, ENABLE); RCC_APB2PeriphResetCmd(RCC_APB2Periph_ADC3, DISABLE); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN; GPIO_Init(GPIOF, &GPIO_InitStructure); ADC_DeInit(ADC3);
ADC_InitStructure.ADC_Mode = ADC_Mode_Independent; ADC_InitStructure.ADC_ScanConvMode = DISABLE; ADC_InitStructure.ADC_ContinuousConvMode = DISABLE; ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None; ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right; ADC_InitStructure.ADC_NbrOfChannel = 1; ADC_Init(ADC3, &ADC_InitStructure);
ADC_Cmd(ADC3, ENABLE); ADC_ResetCalibration(ADC3); while(ADC_GetResetCalibrationStatus(ADC3)); ADC_StartCalibration(ADC3); while(ADC_GetCalibrationStatus(ADC3)); }
u16 Get_ADC3(u8 ch) { ADC_RegularChannelConfig(ADC3, ch, 1, ADC_SampleTime_239Cycles5 ); ADC_SoftwareStartConvCmd(ADC3, ENABLE); while(!ADC_GetFlagStatus(ADC3, ADC_FLAG_EOC ));
return ADC_GetConversionValue(ADC3); }
u8 Lsens_Get_Val(void) { u32 temp_val=0; u8 t; for(t=0;t<LSENS_READ_TIMES;t++) { temp_val+=Get_ADC3(ADC_Channel_6); delay_ms(5); } temp_val/=LSENS_READ_TIMES; if(temp_val>4000)temp_val=4000; return (u8)(100-(temp_val/40)); }
|
串口(USART2)获取数据
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36
| char USART2_RX_BUF[RX_BUF_MAX_LEN]; u16 USART2_RX_STA = 0;
void USART2_IRQHandler(void){ u8 r; if(USART_GetITStatus(USART2, USART_IT_RXNE) != RESET) { r = USART_ReceiveData(USART2); if((USART2_RX_STA&0x8000)==0) { if(USART2_RX_STA&0x4000) { if(r!=0x0a)USART2_RX_STA=0; else { USART2_RX_STA = 0; } } else { if(r==0x0d)USART2_RX_STA|=0x4000; else { USART2_RX_BUF[USART2_RX_STA&0X3FFF]=r; USART2_RX_STA++; if(USART2_RX_STA>(RX_BUF_MAX_LEN-1))USART2_RX_STA=0; } } } }
}
|
color:green USART2初始化等代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45
| void usart2_init( void ) { GPIO_InitTypeDef GPIO_InitStructure; USART_InitTypeDef USART_InitStructure; NVIC_InitTypeDef NVIC_InitStructure; RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOA, ENABLE ); RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE); GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOA, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING; GPIO_Init(GPIOA, &GPIO_InitStructure);
USART_InitStructure.USART_BaudRate = 115200; USART_InitStructure.USART_WordLength = USART_WordLength_8b; USART_InitStructure.USART_StopBits = USART_StopBits_1; USART_InitStructure.USART_Parity = USART_Parity_No; USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; USART_Init(USART2, &USART_InitStructure);
USART_ClearFlag(USART2, USART_FLAG_TC); USART_ITConfig(USART2, USART_IT_RXNE, ENABLE); USART_Cmd(USART2, ENABLE); NVIC_InitStructure.NVIC_IRQChannel = USART2_IRQn; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=3 ; NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); }
|
串口数据处理
提取时间、天气信息;为了方便,ESP8266发给STM32的数据都是用逗号隔开的,如 时间,天气,气温,湿度,
……
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78
| struct WeatherData processWdata3(char data[]){ u8 i=0, j=0, i0=0, k=0; u8 ind=0, jnd=0; int slen = strlen(data); struct WeatherData weather; for(ind=0; ind<8; ind++){ switch(ind){ case 0: { for(jnd=0; jnd<20; jnd++){ weather.datetime[jnd]='\0'; } };break; case 1: { for(jnd=0; jnd<10; jnd++){ weather.city[jnd]='\0'; } };break; case 2: { for(jnd=0; jnd<10; jnd++){ weather.humi[jnd]='\0'; } };break; case 3: { for(jnd=0; jnd<10; jnd++){ weather.temp[jnd]='\0'; } };break; case 4: { for(jnd=0; jnd<10; jnd++){ weather.weather[jnd]='\0'; } };break; case 5: { for(jnd=0; jnd<10; jnd++){ weather.windpower[jnd]='\0'; } };break; case 6: { for(jnd=0; jnd<10; jnd++){ minLsens_str[jnd]='\0'; } };break; case 7: { for(jnd=0; jnd<10; jnd++){ alarmTemp_str[jnd]='\0'; } };break; } } strcpy(weather.city, "西安"); for(i=0; i<slen; i++){ if(data[i]==',') { i0++; for(j=k; j<i; j++){
if(i0==1) weather.datetime[j-k]=data[j]; else if(i0==2) weather.weather[j-k]=data[j]; else if(i0==3) weather.temp[j-k]=data[j]; else if(i0==4) weather.humi[j-k]=data[j]; else if(i0==5) weather.windpower[j-k]=data[j]; else if(i0==6) alarmTemp_str[j-k]=data[j]; else if(i0==7) minLsens_str[j-k]=data[j]; } k=i+1; }
} return weather; }
|
发送数据
通过定时器TIM2定时1s发送一次数据(json字符串格式)给ESP8266模块
1 2 3 4 5 6 7 8 9 10
| void TIM2_IRQHandler(void){ if(TIM_GetITStatus(TIM2, TIM_IT_Update) != RESET){
ESP8266_Usart("{\"temp\":\"%d\",\"humi\":\"%d\",\"light\":\"%d\",\"ledsta\":\"%d\",\"beepsta\":\"%d\"}\r\n", dhtData.temp, dhtData.humi, lsens, ledSta, beepSta); TIM_ClearITPendingBit(TIM2, TIM_IT_Update); } }
|
color:green 初始化TIM2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
| void TIM2_init(u16 arr, u16 psc){ TIM_TimeBaseInitTypeDef TIM_Structure; NVIC_InitTypeDef NVIC_Structure; RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE); TIM_Structure.TIM_Period = arr - 1; TIM_Structure.TIM_Prescaler = psc-1; TIM_Structure.TIM_ClockDivision = 0; TIM_Structure.TIM_CounterMode = TIM_CounterMode_Up; TIM_TimeBaseInit(TIM2, &TIM_Structure); TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE); TIM_ClearITPendingBit(TIM2, TIM_IT_Update); NVIC_Structure.NVIC_IRQChannel = TIM2_IRQn; NVIC_Structure.NVIC_IRQChannelPreemptionPriority = 6; NVIC_Structure.NVIC_IRQChannelSubPriority = 4; NVIC_Structure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_Structure);
TIM_ClearFlag(TIM2, TIM_FLAG_Update); TIM_Cmd(TIM2, ENABLE); }
|
LED与蜂鸣器控制
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| void ledBeepOnOrNot(u8 lsens, u8 mlsens, u8 t, u8 alarmT){ if(lsens < mlsens){ LED1 = 0; ledSta = 1; } else{ LED1 = 1; ledSta = 0; } if(t>alarmT){ BEEP=1; beepSta = 1; } else{ BEEP=0; beepSta = 0; } }
|