本教程将介绍如何在STM32微控制器上使用温湿度传感器。我们将使用一款常用的温湿度传感器模块DHT11,并将其连接到STM32的GPIO引脚上。我们将使用STM32CubeMX和Keil MDK来进行开发,因此你需要安装这两个软件。
在本教程中,我们将使用STM32F4 Discovery开发板,但是这里提供的代码也适用于其他型号的STM32。我们将使用C语言来编写代码。
教程将涵盖以下内容:
- 硬件连接
- STM32CubeMX配置
- 初始化代码
- 读取温湿度传感器数据
- 主函数代码
- 编译和烧录代码
让我们开始吧!
- 硬件连接
首先,将DHT11传感器模块的VCC引脚连接到STM32的3.3V引脚,GND引脚连接到GND引脚,DATA引脚连接到STM32的任意GPIO引脚(例如PB0引脚)。
- STM32CubeMX配置
打开STM32CubeMX软件,并创建一个新工程。
在"Pinout & Configuration"选项卡中,找到你选择的STM32型号,并选择一个未使用的GPIO引脚作为DHT11的DATA引脚。
在"Configuration"选项卡中,找到"Peripherals"下的"GPIO",并设置DATA引脚为"GPIO Output"。
在"Project"菜单中,将工程命名为你想要的名称,并选择你喜欢的路径。
点击"Project"菜单中的"Generate Code"按钮,生成代码。
- 初始化代码
打开生成的代码文件,找到"main.c"文件,并添加以下代码到"USER CODE BEGIN Includes"和"USER CODE BEGIN PV"之间:
#include "dht11.h"
然后找到"USER CODE BEGIN 2"之后的位置,并添加以下代码:
DHT11_DataTypedef DHT11_DataStruct;
- 读取温湿度传感器数据
在生成的代码文件中,创建一个新的头文件"dht11.h",并添加以下代码:
#ifndef __DHT11_H
#define __DHT11_H
#include "stm32f4xx_hal.h"
typedef struct {
uint8_t humidity_integer;
uint8_t humidity_decimal;
uint8_t temperature_integer;
uint8_t temperature_decimal;
} DHT11_DataTypedef;
void DHT11_Init(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);
DHT11_DataTypedef DHT11_ReadData(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);
#endif /* __DHT11_H */
在同一文件夹下创建一个新的源文件"dht11.c",并添加以下代码:
#include "dht11.h"
#define DHT11_DATA_PIN_HIGH() (HAL_GPIO_WritePin(DHT11_DATA_GPIO_Port, DHT11_DATA_Pin, GPIO_PIN_SET))
#define DHT11_DATA_PIN_LOW() (HAL_GPIO_WritePin(DHT11_DATA_GPIO_Port, DHT11_DATA_Pin, GPIO_PIN_RESET))
#define DHT11_DATA_PIN_READ() (HAL_GPIO_ReadPin(DHT11_DATA_GPIO_Port, DHT11_DATA_Pin))
void DHT11_DelayUs(uint32_t n)
{
n *= (SystemCoreClock / 1000000) / 9;
while(n--) {
__NOP();
}
}
void DHT11_Init(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)
{
HAL_GPIO_WritePin(GPIOx, GPIO_Pin, GPIO_PIN_SET);
HAL_Delay(1000);
}
DHT11_DataTypedef DHT11_ReadData(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)
{
DHT11_DataTypedef DHT11_DataStruct = {0};
//发送起始信号
DHT11_DATA_PIN_LOW();
DHT11_DelayUs(18000);
DHT11_DATA_PIN_HIGH();
DHT11_DelayUs(20);
HAL_GPIO_WritePin(GPIOx, GPIO_Pin, GPIO_PIN_RESET);
DHT11_DelayUs(40);
HAL_GPIO_WritePin(GPIOx, GPIO_Pin, GPIO_PIN_SET);
//等待DHT11响应
while(DHT11_DATA_PIN_READ() == GPIO_PIN_SET);
//确认DHT11响应完成
while(DHT11_DATA_PIN_READ() == GPIO_PIN_RESET);
//开始读取数据
for(uint8_t i = 0; i < 40; i++) {
//等待数据位开始
while(DHT11_DATA_PIN_READ() == GPIO_PIN_RESET);
//开始计时
uint32_t t = 0;
while(DHT11_DATA_PIN_READ() == GPIO_PIN_SET) {
t++;
DHT11_DelayUs(1);
}
if(t > 40) {
DHT11_DataStruct.humidity_integer = 0;
DHT11_DataStruct.humidity_decimal = 0;
DHT11_DataStruct.temperature_integer = 0;
DHT11_DataStruct.temperature_decimal = 0;
break;
}
if(i < 8) {
DHT11_DataStruct.humidity_integer <<= 1;
if(t > 20) {
DHT11_DataStruct.humidity_integer |= 1;
}
}
else if(i < 24) {
DHT11_DataStruct.humidity_decimal <<= 1;
if(t > 20) {
DHT11_DataStruct.humidity_decimal |= 1;
}
}
else if(i < 32) {
DHT11_DataStruct.temperature_integer <<= 1;
if(t > 20) {
DHT11_DataStruct.temperature_integer |= 1;
}
}
else if(i < 40) {
DHT11_DataStruct.temperature_decimal <<= 1;
if(t > 20) {
DHT11_DataStruct.temperature_decimal |= 1;
}
}
}
return DHT11_DataStruct;
}
- 主函数代码
在"main.c"文件中找到"USER CODE BEGIN 3"之后的位置,并添加以下代码:
while (1)
{
HAL_Delay(2000);
DHT11_DataStruct = DHT11_ReadData(DHT11_DATA_GPIO_Port, DHT11_DATA_Pin);
printf("Humidity: %d.%d%%\r\n", DHT11_DataStruct.humidity_integer, DHT11_DataStruct.humidity_decimal);
printf("Temperature: %d.%dC\r\n", DHT11_DataStruct.temperature_integer, DHT11_DataStruct.temperature_decimal);
}
- 编译和烧录代码
使用Keil MDK编译代码,并将生成的hex文件烧录到STM32F4 Discovery开发板中。
现在你已经完成了在STM32上使用温湿度传感器的入门教程。当你运行代码时,你将能够从DHT11传感器读取温度和湿度数据,并在串口终端上显示出来。
希望本教程能帮助你入门STM32的温湿度传感器应用!