用HC-SR501检测人接近,控制L9110风扇模块启动,用DHT11检测环境温度,在OLED屏幕上实时显示温度,自动调整风扇转速,人离开后关闭风扇,STM32F103ZET6生成代码
时间: 2023-06-18 19:06:02 浏览: 106
很好,接下来我们就来一步步实现这个功能。
1. 硬件连接
首先,我们需要将 HC-SR501 模块和 DHT11 模块连接到 STM32F103ZET6 上,连接方式如下:
- HC-SR501 模块:
- VCC -> 5V
- GND -> GND
- OUT -> PB12(作为输入)
- DHT11 模块:
- VCC -> 5V
- GND -> GND
- DATA -> PB10(作为输入)
此外,我们还需要将 L9110 风扇模块连接到 STM32F103ZET6 上,连接方式如下:
- L9110 风扇模块:
- VCC -> 5V
- GND -> GND
- IN1 -> PA0(作为输出)
最后,我们需要将 OLED 屏幕连接到 STM32F103ZET6 上,连接方式如下:
- OLED 屏幕:
- VCC -> 5V
- GND -> GND
- SCL -> PB8(作为输出)
- SDA -> PB9(作为输出)
2. 编写程序
接下来,我们需要编写程序来控制这些硬件模块。首先,我们需要定义一些变量和引入一些库文件,如下所示:
```c
#include "stm32f10x.h"
#include "delay.h"
#include "i2c.h"
#include "oled.h"
#include "dht11.h"
#define HC_SR501_GPIO GPIOB
#define HC_SR501_PIN GPIO_Pin_12
#define L9110_GPIO GPIOA
#define L9110_PIN GPIO_Pin_0
volatile uint16_t temp, humi;
void GPIO_Configuration(void);
void TIM2_PWM_Init(u16 arr,u16 psc);
int main(void)
{
GPIO_Configuration();
TIM2_PWM_Init(899,0);
OLED_Init();
DHT11_Init();
while(1)
{
if(GPIO_ReadInputDataBit(HC_SR501_GPIO, HC_SR501_PIN) == 1)
{
OLED_ShowString(0,0,"Someone is here !");
TIM_SetCompare1(TIM2, 899);
}
else
{
OLED_ShowString(0,0," ");
TIM_SetCompare1(TIM2, 0);
}
DHT11_Read_TempAndHumidity(&temp, &humi);
OLED_ShowNum(0,2,temp,0,16);
OLED_ShowString(3,2,"C");
delay_ms(500);
}
}
void GPIO_Configuration(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB, ENABLE);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Pin = L9110_PIN;
GPIO_Init(L9110_GPIO, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPD;
GPIO_InitStructure.GPIO_Pin = HC_SR501_PIN;
GPIO_Init(HC_SR501_GPIO, &GPIO_InitStructure);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
}
void TIM2_PWM_Init(u16 arr,u16 psc)
{
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
TIM_TimeBaseStructure.TIM_Period = arr;
TIM_TimeBaseStructure.TIM_Prescaler = psc;
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OC1Init(TIM2, &TIM_OCInitStructure);
TIM_OC1PreloadConfig(TIM2, TIM_OCPreload_Enable);
TIM_Cmd(TIM2, ENABLE);
}
```
以上代码中,我们定义了一个 `temp` 变量和一个 `humi` 变量,分别用来存储 DHT11 模块读取到的温度和湿度。我们还定义了一个 `HC_SR501_GPIO` 变量和一个 `HC_SR501_PIN` 变量,分别用来表示 HC-SR501 模块连接到 STM32F103ZET6 的 GPIO 端口和引脚。类似地,我们还定义了一个 `L9110_GPIO` 变量和一个 `L9110_PIN` 变量,用来表示 L9110 风扇模块连接到 STM32F103ZET6 的 GPIO 端口和引脚。最后,我们还定义了一个 `GPIO_Configuration` 函数和一个 `TIM2_PWM_Init` 函数,用来初始化 GPIO 和 TIM2。
在 `main` 函数中,我们首先调用 `GPIO_Configuration` 函数和 `TIM2_PWM_Init` 函数来初始化硬件模块。然后,我们进入一个无限循环,不断地读取 HC-SR501 模块和 DHT11 模块的数据,并根据读取到的数据来控制 L9110 风扇模块的转速和在 OLED 屏幕上显示温度值。
具体来说,我们首先使用 `GPIO_ReadInputDataBit` 函数读取 HC-SR501 模块的数据。如果读取到的数据为 1,说明有人接近了,此时我们就让 L9110 风扇模块启动,并且调用 `TIM_SetCompare1` 函数来调整风扇的转速。如果读取到的数据为 0,说明没有人接近,此时我们就关闭风扇,并且也调用 `TIM_SetCompare1` 函数来停止风扇的转动。
接着,我们调用 `DHT11_Read_TempAndHumidity` 函数来读取 DHT11 模块的温度和湿度数据,并将其存储到 `temp` 和 `humi` 变量中。然后,我们调用 `OLED_ShowNum` 函数和 `OLED_ShowString` 函数来在 OLED 屏幕上显示温度值和一些提示信息。
最后,我们使用 `delay_ms` 函数来延时 500 毫秒,以保证程序不会一直占用 CPU 资源。
3. 编译和下载程序
最后,我们使用 Keil 或者其他编译工具来编译我们的程序,并将其下载到 STM32F103ZET6 开发板上。接着,我们就可以将 HC-SR501 模块、DHT11 模块、L9110 风扇模块和 OLED 屏幕连接到 STM32F103ZET6 上,并且开启电源,测试我们的程序是否正常工作了。
阅读全文