【2024 DigiKey Creative Competition】Home Weather Station Based on STM32F411+BME680 (Completed)
[Copy link]
This post was last edited by dwwzl on 2024-10-28 21:08
Home Weather Station Based on STM32F411+BME680
Author:dwwzl
1. Introduction to the work
Figure 1.1
This work can measure the temperature, humidity, atmospheric pressure and air quality index of indoor and outdoor air in real time. It is designed to serve both home and outdoor use. When the air indoors and outdoors changes, it can promptly remind family members to add or remove clothes, turn on or off humidifiers and air purifiers.
The materials used in this work are as follows Table 1.1:
Table 1.1
Serial number
|
name
|
Manufacturer
|
Digi-Key Part Number
|
Introduction
|
1
|
NUCLEO-F411RE Development Board
|
ST
|
497-14711-ND
|
NUCLEO-F411RE is a Cortex-M4 development board designed for the STM32F4 series launched by ST. It has mbed functions and supports Arduino. It also provides ST Morpho expansion pin headers to connect all peripherals of the microcontroller. The development board is based on the STM32F411RET6 design. The development board also integrates the ST-LINK/V2-1 emulator downloader (but only provides SWD interface to the outside), eliminating the trouble of purchasing emulators or downloaders separately. It also has an Arduino interface and can be connected to various Shield expansion boards in the huge Arduino ecosystem, allowing you to easily and quickly add special functions.
|
2
|
BME680
|
Adafruit Industries LLC
|
1528-2444-ND
|
BME680 is a Qwiic, STEMMA QT platform evaluation expansion board that can detect atmospheric pressure, ambient temperature, relative humidity, and VOC gas changes (combined with Bosch's software package, it can calculate the IAQ air quality coefficient).
|
3
|
D6T-1A-02
|
Omron Electronics Inc - EMC Div
|
Z10316-ND
|
Omron infrared thermal imaging temperature sensor D6T-1A-02 is a highly sensitive human body sensing sensor that can detect even stationary people. By using self-made MEMS and ASIC, a high level of SNR is achieved. (Except D6T-32L-01A) Digital output, excellent anti-interference. Through the field of view characteristics of low crosstalk, more accurate regional temperature detection is achieved.
|
4
|
0.96-inch OLED display
|
Zhongjingyuan Electronics
|
Buy separately
|
The 0.96-inch OLED LCD display module has a display area of 128X64 dot matrix (resolution 128*64). Each dot can emit light independently, so no backlight is required. It can display Chinese characters, ASIIC codes, patterns, etc.
|
2. System Block Diagram
The design ideas of this work are as follows:
Figure 2.1
- First, start with the system development platform, familiarize yourself with the NUCLEO-F411RE development board used in this work, download the relevant compilation software and code library files, create a new project, write and debug the basic resource configuration code, and light up the running indicator light;
- Take BME680 as an example to write and debug the IIC low-level read and write code. Similarly, transplant it to the IIC read and write driver file of D6T-1A-02 and 0.96-inch OLED display, and debug it.
- According to the data content to be displayed, write the 0.96-inch OLED display interface code and display the relevant data.
The system hardware is shown below:
- NUCLEO-F411RE development board, Figure 2.2
NUCLEO-F411RE is a Cortex-M4 development board designed for the STM32F4 series launched by ST. It has mbed functions and supports Arduino. It also provides ST Morpho expansion pin headers to connect all peripherals of the microcontroller. The development board is based on the STM32F411RET6 design. The development board also integrates the ST-LINK/V2-1 emulator downloader (but only provides SWD interface to the outside), eliminating the trouble of purchasing emulators or downloaders separately. It also has an Arduino interface and can be connected to various Shield expansion boards in the huge Arduino ecosystem, allowing you to easily and quickly add special functions.
- BME680 module, Figure 2.3
BME680 is a Qwiic, STEMMA QT platform evaluation expansion board that can detect atmospheric pressure, ambient temperature, relative humidity, and VOC gas changes (combined with Bosch's software package, it can calculate the IAQ air quality coefficient).
- D6T-1A-02 module, Figure 2.4
Omron infrared thermal imaging temperature sensor D6T-1A-02 is a highly sensitive human body sensing sensor that can detect even stationary people. By using self-made MEMS and ASIC, a high level of SNR is achieved. (Except D6T-32L-01A) Digital output, excellent anti-interference. Through the field of view characteristics of low crosstalk, more accurate regional temperature detection is achieved.
- 0.96-inch OLED display, Figure 2.5
The 0.96-inch OLED LCD display module has a display area of 128X64 dot matrix (resolution 128*64). Each dot can emit light independently, so no backlight is required. It can display Chinese characters, ASIIC codes, patterns, etc.
The system block diagram is as follows: Figure 2.6
3. Functional description of each part
- Indoor and outdoor temperature, humidity, atmospheric pressure and air quality data collection
The BME680 module is used to collect indoor and outdoor temperature and humidity values, atmospheric pressure and air parameters.
As shown in Figure 3.1,
The BME680 module uses a 4-pin IIC interface, 3.3V~5V power supply, and power consumption as low as 0.1mA, so it can be powered by the IO port.
The key codes are as follows:
voidBME680_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE);
GPIO_InitStructure.GPIO_Pin=BME680_SCL1_Pin;// SCL
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_UP;
GPIO_Init(BME680_SCL1_GPIO_Port, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_0 |GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_UP;
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_ResetBits(GPIOC, GPIO_Pin_0);// 开通电源-
GPIO_SetBits(GPIOC, GPIO_Pin_1);// 开通电源+
}
int8_tbme680_iic_read(uint8_tdev_id, uint8_treg_addr, uint8_t*data, uint16_tlen)
{
u8 i=0;
BME_IIC_Start();
BME_IIC_Send_Byte(BME_IIC_ADDR);
BME_IIC_Wait_Ack();
BME_IIC_Send_Byte(reg_addr);
BME_IIC_Wait_Ack();
BME_IIC_Stop();
BME_IIC_Start();
BME_IIC_Send_Byte(BME_IIC_ADDR|0x01);
BME_IIC_Wait_Ack();
len--;
for(i=0; i<len;i++)
{
data[i] =BME_IIC_Read_Byte(1);
}
data[i] =BME_IIC_Read_Byte(0);
BME_IIC_Stop();
return0;
}
int8_tbme680_iic_write(uint8_tdev_id, uint8_treg_addr, uint8_t*data, uint16_tlen)
{
u8 cnt=0;
BME_IIC_Start();
BME_IIC_Send_Byte(BME_IIC_ADDR);
BME_IIC_Wait_Ack();
BME_IIC_Send_Byte(reg_addr);
BME_IIC_Wait_Ack();
while(len--)
{
BME_IIC_Send_Byte(data[cnt]);
BME_IIC_Wait_Ack();
cnt++;
}
BME_IIC_Stop();
return0;
}
voidmy_bme_init(void)
{
uint8_tset_required_settings;
u8 rslt;
BME680_Init(); // IO初始化
bme680_soft_reset(&gas_sensor);
gas_sensor.chip_id=BME680_CHIP_ID;// 芯片ID
gas_sensor.dev_id =BME680_I2C_ADDR_SECONDARY;
gas_sensor.amb_temp=25;
gas_sensor.read =bme680_iic_read;// 数据读取函数的指针
gas_sensor.write =bme680_iic_write;// 写数据的指针
gas_sensor.intf =BME680_I2C_INTF;// 通讯方式的选择
gas_sensor.delay_ms=bme_delay_ms;// 延时函数的函数指针
gas_sensor.power_mode =BME680_FORCED_MODE;// 读取方式
gas_sensor.calib =calib_struct;
gas_sensor.tph_sett =tph_sett_struct;
gas_sensor.gas_sett =gas_sett_struct;
/* Set the temperature, pressure and humidity & filter settings */
gas_sensor.tph_sett.filter =BME680_FILTER_SIZE_1;
gas_sensor.tph_sett.os_hum =BME680_OS_1X;// 这里是 数据结构体下的 过采样率
gas_sensor.tph_sett.os_temp=BME680_OS_1X;
gas_sensor.tph_sett.os_pres=BME680_OS_1X;
/* Set the remaining gas sensor settings and link the heating profile */
gas_sensor.gas_sett.run_gas=BME680_ENABLE_GAS_MEAS;
/* Create a ramp heat waveform in 3 steps */
gas_sensor.gas_sett.heatr_temp=350;// degree Celsius
gas_sensor.gas_sett.heatr_dur=2000;// 150 milliseconds
/* Set the required sensor settings needed */
set_required_settings=(BME680_OST_SEL|BME680_OSP_SEL|BME680_OSH_SEL|BME680_FILTER_SEL|BME680_GAS_SENSOR_SEL);
rslt=bme680_init(&gas_sensor); // 调用初始化函数
if(rslt)printf("result of bme680_init() is %d",rslt); // 有问题的话输出调试信息
/* Set the desired sensor configuration */
rslt=bme680_set_sensor_settings(set_required_settings,&gas_sensor);
if(rslt)printf("result of bme680_set_sensor_settings() is %d",rslt);
/* Set the power mode */
rslt=bme680_set_sensor_mode(&gas_sensor);
if(rslt)printf("result of bme680_set_sensor_mode() is %d",rslt);
}
数据输出如下:
- Human body temperature collection
Use the D6T-1A-02 module to sense and collect human body temperature.
Figure 3.2
The D6T-1A-02 module uses a 4-wire IIC interface, with a power supply voltage of 5V and an operating current of 3.5mA.
The key code implementation is as follows:
voidD6T_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
// RCC
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA |RCC_AHB1Periph_GPIOB,
ENABLE );
// SCL
GPIO_InitStructure.GPIO_Pin =D6T_SCL_Pin;
GPIO_InitStructure.GPIO_Mode =GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType =GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd =GPIO_PuPd_NOPULL;
GPIO_InitStructure.GPIO_Speed =GPIO_Speed_100MHz;
GPIO_Init(D6T_SCL_GPIO_Port, &GPIO_InitStructure);
D6T_SDA_OUT();
D6T_IIC_SDA=1;
D6T_IIC_SCL=1;
}
/*
*******************************************************************************************
** =0 正常,=-1 传感器缺失,=1 时序异常
*******************************************************************************************
*/
intD6T_ReadData()
{
unsignedcharD6Tbuff[5];
unsignedcharD6T_Data;
unsignedchari;
unsignedinttPTAT_l;
unsignedinttP_l;
D6T_IIC_Start();
D6T_IIC_Send_Byte(D6T_Addr+0);
D6T_IIC_Wait_Ack();
D6T_IIC_Send_Byte(D6T_CMD);
D6T_IIC_Wait_Ack();
D6T_IIC_Start();
D6T_IIC_Send_Byte(D6T_Addr+1);
D6T_IIC_Wait_Ack();
// READ Data of Temperature
D6T_Data=0;
for(i=0;i<(5-1);i++)
{
D6Tbuff[D6T_Data++] =D6T_IIC_Read_Byte(1);
}
D6Tbuff[D6T_Data] =D6T_IIC_Read_Byte(0);
D6T_IIC_Stop();
tPTAT_l=D6Tbuff[1] *256+D6Tbuff[0];
tP_l=D6Tbuff[3] *256+D6Tbuff[2];
D6T_Temp_f=(float)tPTAT_l/10;// 单位 ℃
D6T_Temp_f=(float)tP_l/10;// 单位 ℃
return0;
}
The data output is as follows:
- Data Display
The 0.96-inch OLED display screen is used to display indoor and outdoor temperature and humidity values, atmospheric pressure, air parameters and human body temperature values.
Figure 3.3
The 0.96-inch OLED display uses a 7-pin IIC interface, with a power supply voltage of 3.3V. The power supply current is about 25mA when fully lit and about 1.5mA when fully off.
Adjust the resistor configuration according to the table below.
The key code implementation is as follows:
//OLED的初始化
voidOLED_Init(void)
{
// 端口配置
GPIO_InitTypeDef GPIO_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);//使能GPIOA时钟
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB, ENABLE);//使能GPIOB时钟
//初始化设置
GPIO_InitStructure.GPIO_Pin=OLED_G_Pin|OLED_V_Pin|OLED_D0_Pin;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_OUT;//普通输出模式
GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;//推挽输出
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_100MHz;//100MHz
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化
GPIO_ResetBits(GPIOA,OLED_G_Pin);//电源-
GPIO_SetBits(GPIOA,OLED_V_Pin);//电源+
GPIO_ResetBits(GPIOA,OLED_D0_Pin);//D0
GPIO_InitStructure.GPIO_Pin=OLED_D1_Pin|OLED_DC_Pin|OLED_RES_Pin|OLED_CS_Pin;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_OUT;//普通输出模式
GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;//推挽输出
GPIO_InitStructure.GPIO_Speed=GPIO_Speed_100MHz;//100MHz
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOB, &GPIO_InitStructure);//初始化
GPIO_ResetBits(GPIOB,OLED_D1_Pin);//D1
GPIO_ResetBits(GPIOB,OLED_DC_Pin);//DC
GPIO_SetBits(GPIOB,OLED_RES_Pin);//RES
GPIO_ResetBits(GPIOB,OLED_CS_Pin);//CS
delay_ms(200);
//初始化命令
OLED_WR_Byte(0xAE,OLED_CMD);//关闭显示--turn off oled panel
OLED_WR_Byte(0x00,OLED_CMD);//第1点列地址---set low column address
OLED_WR_Byte(0x10,OLED_CMD);//高1点列地址---set high column address
OLED_WR_Byte(0x40,OLED_CMD);//显示开始线--set start line address Set Mapping RAM Display Start Line (0x00~0x3F)
OLED_WR_Byte(0x81,OLED_CMD);//设置对比度--set contrast control register
OLED_WR_Byte(0xCF,OLED_CMD);// Set SEG Output Current Brightness
OLED_WR_Byte(0xA1,OLED_CMD);//设置段复用--Set SEG/Column Mapping 0xa0左右反置 0xa1正常
OLED_WR_Byte(0xC8,OLED_CMD);//设置扫描方向--Set COM/Row Scan Direction 0xc0上下反置 0xc8正常
OLED_WR_Byte(0xA6,OLED_CMD);//设置正常显示或反显--set normal display
OLED_WR_Byte(0xA8,OLED_CMD);//设置复用比--set multiplex ratio(1 to 64)
OLED_WR_Byte(0x3f,OLED_CMD);//--1/64 duty
OLED_WR_Byte(0xD3,OLED_CMD);//设置显示偏移量--set display offset Shift Mapping RAM Counter (0x00~0x3F)
OLED_WR_Byte(0x00,OLED_CMD);//-not offset
OLED_WR_Byte(0xd5,OLED_CMD);//设置时钟分频因子--set display clock divide ratio/oscillator frequency
OLED_WR_Byte(0x80,OLED_CMD);//--set divide ratio, Set Clock as 100 Frames/Sec
OLED_WR_Byte(0xD9,OLED_CMD);//设置充电周期--set pre-charge period
OLED_WR_Byte(0xF1,OLED_CMD);//Set Pre-Charge as 15 Clocks & Discharge as 1 Clock
OLED_WR_Byte(0xDA,OLED_CMD);//设置引脚配置--set com pins hardware configuration
OLED_WR_Byte(0x12,OLED_CMD);
OLED_WR_Byte(0xDB,OLED_CMD);//设置取消等级--set vcomh
OLED_WR_Byte(0x30,OLED_CMD);//[6:4] 000,0.65*vcc;001,0.77*vcc;011,0.83*vcc;
OLED_WR_Byte(0x40,OLED_CMD);//显示开始线--Set VCOM Deselect Level
OLED_WR_Byte(0x20,OLED_CMD);//内存水平地址模式--Set Page Addressing Mode (0x00/0x01/0x02)
OLED_WR_Byte(0x02,OLED_CMD);//
OLED_WR_Byte(0x8D,OLED_CMD);//--set Charge Pump enable/disable
OLED_WR_Byte(0x14,OLED_CMD);//--set(0x10) disable
OLED_WR_Byte(0xA4,OLED_CMD);// Disable Entire Display On (0xa4/0xa5)
OLED_WR_Byte(0xA6,OLED_CMD);// Disable Inverse Display On (0xa6/a7)
OLED_WR_Byte(0xAF,OLED_CMD);
OLED_Clear();
}
//清屏函数
voidOLED_Clear(void)
{
unsignedchari,n;
for(i=0;i<8;i++)
{
for(n=0;n<128;n++)
{
OLED_GRAM[n][i]=0;//清除所有数据
}
}
OLED_Refresh();//更新显示
}
//显示字符串
//x,y:起点坐标
//size1:字体大小
//*chr:字符串起始地址
voidOLED_ShowString(unsignedcharx,unsignedchary,unsignedchar*chr,unsignedcharsize1)
{
while((*chr>=' ')&&(*chr<='~'))//判断是不是非法字符!
{
OLED_ShowChar(x,y,*chr,size1);
x+=size1/2;
if(x>128-size1)//换行
{
x=0;
y+=2;
}
chr++;
}
}
//显示汉字
//x,y:起点坐标
//num:汉字对应的序号
//取模方式 列行式
voidOLED_ShowChinese(unsignedcharx,unsignedchary,unsignedcharnum,unsignedcharsize1)
{
unsignedchari,m,n=0,temp,chr1;
unsignedcharx0=x,y0=y;
unsignedcharsize3=size1/8;
while(size3--)
{
chr1=num*size1/8+n;
n++;
for(i=0;i<size1;i++)
{
if(size1==16)
{temp=Hzk1[chr1][i];}//调用16*16字体
elseif(size1==24)
{temp=Hzk2[chr1][i];}//调用24*24字体
elseif(size1==32)
{temp=Hzk3[chr1][i];}//调用32*32字体
elseif(size1==64)
{temp=Hzk4[chr1][i];}//调用64*64字体
elsereturn;
for(m=0;m<8;m++)
{
if(temp&0x01)OLED_DrawPoint(x,y);
elseOLED_ClearPoint(x,y);
temp>>=1;
y++;
}
x++;
if((x-x0)==size1)
{x=x0;y0=y0+8;}
y=y0;
}
}
}
Finally, the display interface is as follows:
4. Source Code
The source code link of this work is as follows:
https://download.eeworld.com.cn/detail/dwwzl/634616
5. Demonstration video of the work’s functions
The video is as follows:
VID_20241027-1
6. Project Summary
In the process of realizing this work, I came into contact with MEMS sensors such as BME680 and D6T-1A-02. The reading and writing operations are not difficult to do. The difficulty lies in the algorithm calculation and practical application of the sensor's output data, so that advanced sensing technology can truly serve life and work scenarios.
This work can subsequently consider adding a wireless communication module, powered by a lithium battery, to enable distributed sensor data collection and upload it to the data computing center. After comprehensive calculation and judgment, a reasonable conclusion can be drawn and sent to the human-machine interface terminal, making the output results clear at a glance.
The sharing link is as follows:
【2024 DigiKey Creative Competition】Home Weather Station-Material Unboxing-DigiKey Technology Zone-Electronic Engineering World-Forumhttps ://en.eeworld.com/bbs/thread-1291454-1-1.html
【2024 DigiKey Creative Competition】Home Weather Station - Material Preparation - DigiKey Technology Zone - Electronic Engineering World - Forum https://en.eeworld.com/bbs/thread-1293100-1-1.html
[2024 DigiKey Creative Competition] Home Weather Station - Debugging IIC Interface Communication - DigiKey Technology Zone - Electronic Engineering World - Forum https://en.eeworld.com/bbs/thread-1296584-1-1.html
VII. Attachments
【2024 DigiKey创意大赛】基于STM32F411+BME680 家居气象台.doc
(4.01 MB, downloads: 0)
|