当前位置:网站首页>STM32F103ZE+SHT30检测环境温度与湿度(IIC模拟时序)
STM32F103ZE+SHT30检测环境温度与湿度(IIC模拟时序)
2022-07-06 22:23:00 【华为云】
一、环境介绍
工程编译软件: keil5
温湿度传感器: SHT30
MCU : STM32F103ZET6
程序采用模块化编程,iic时序为一个模块(iic.c 和 iic.h),SHT30为一个模块(sht30.c 和 sht30.h);IIC时序采用模拟时序方式实现,IO口都采用宏定义方式,方便快速移植到其他平台使用。
二、SHT30介绍
特点:
\1. 湿度和温度传感器
\2. 完全校准、线性化和温度
\3. 补偿数字输出,宽电源电压范围,从2.4 V到5.5 V
\4. I2C接口,通信速度高达1MHz和两个用户可选地址
\5. 典型精度 ± 2%相对湿度和± 0.3°C
\6. 启动和测量时间非常快
\7. 微型8针DFN封装
这是SHT30的7位IIC设备地址:
三、设备运行效果
这是串口打印的数据:
四、设备代码
4.1 main.c
#include "stm32f10x.h"#include "led.h"#include "delay.h"#include "key.h"#include "usart.h"#include "iic.h"#include "sht3x.h"int main(){ float Humidity; float Temperature; USART1_Init(115200); USART1_Printf("设备运行正常....\r\n"); IIC_Init(); Init_SHT30(); while(1) { //读取温湿度 SHT3x_ReadData(&Humidity,&Temperature); USART1_Printf("温度:%0.2f,湿度:%0.2f\r\n",Temperature,Humidity); delay_ms(1000); }}
4.2 sht30.c
#include "sht3x.h"const int16_t POLYNOMIAL = 0x131;/**************************************************************** 函数名称: SHT30_reset* 说 明: SHT30复位* 参 数: 无* 返 回 值: 无***************************************************************/void SHT30_reset(void){ u8 r_s; IIC_Start(); //发送起始信号 IIC_WriteOneByteData(SHT30_AddrW); //写设备地址 r_s=IIC_GetACK();//获取应答 if(r_s)printf("Init_SHT30_error:1\r\n"); IIC_WriteOneByteData(0x30); //写数据 r_s=IIC_GetACK();//获取应答 if(r_s)printf("Init_SHT30_error:2\r\n"); IIC_WriteOneByteData(0xA2); //写数据 r_s=IIC_GetACK();//获取应答 if(r_s)printf("Init_SHT30_error:3\r\n"); IIC_Stop(); //停止信号 delay_ms(50); }/**************************************************************** 函数名称: Init_SHT30* 说 明: 初始化SHT30,设置测量周期* 参 数: 无* 返 回 值: 无***************************************************************/void Init_SHT30(void){ u8 r_s; IIC_Start(); //发送起始信号 IIC_WriteOneByteData(SHT30_AddrW); //写设备地址 r_s=IIC_GetACK();//获取应答 if(r_s)printf("Init_SHT30_error:1\r\n"); IIC_WriteOneByteData(0x22); //写数据 r_s=IIC_GetACK();//获取应答 if(r_s)printf("Init_SHT30_error:2\r\n"); IIC_WriteOneByteData(0x36); //写数据 r_s=IIC_GetACK();//获取应答 if(r_s)printf("Init_SHT30_error:3\r\n"); IIC_Stop(); //停止信号 delay_ms(200);}/**************************************************************** 函数名称: SHT3x_CheckCrc* 说 明: 检查数据正确性* 参 数: data:读取到的数据 nbrOfBytes:需要校验的数量 checksum:读取到的校对比验值* 返 回 值: 校验结果,0-成功 1-失败***************************************************************/u8 SHT3x_CheckCrc(char data[], char nbrOfBytes, char checksum){ char crc = 0xFF; char bit = 0; char byteCtr ; //calculates 8-Bit checksum with given polynomial for(byteCtr = 0; byteCtr < nbrOfBytes; ++byteCtr) { crc ^= (data[byteCtr]); for ( bit = 8; bit > 0; --bit) { if (crc & 0x80) crc = (crc << 1) ^ POLYNOMIAL; else crc = (crc << 1); } } if(crc != checksum) return 1; else return 0; }/**************************************************************** 函数名称: SHT3x_CalcTemperatureC* 说 明: 温度计算* 参 数: u16sT:读取到的温度原始数据* 返 回 值: 计算后的温度数据***************************************************************/float SHT3x_CalcTemperatureC(unsigned short u16sT){ float temperatureC = 0; // variable for result u16sT &= ~0x0003; // clear bits [1..0] (status bits) //-- calculate temperature [℃] -- temperatureC = (175 * (float)u16sT / 65535 - 45); //T = -45 + 175 * rawValue / (2^16-1) return temperatureC; }/**************************************************************** 函数名称: SHT3x_CalcRH* 说 明: 湿度计算* 参 数: u16sRH:读取到的湿度原始数据* 返 回 值: 计算后的湿度数据***************************************************************/float SHT3x_CalcRH(unsigned short u16sRH){ float humidityRH = 0; // variable for result u16sRH &= ~0x0003; // clear bits [1..0] (status bits) //-- calculate relative humidity [%RH] -- humidityRH = (100 * (float)u16sRH / 65535); // RH = rawValue / (2^16-1) * 10 return humidityRH; }//读取温湿度数据void SHT3x_ReadData(float *Humidity,float *Temperature){ char data[3]; //data array for checksum verification u8 SHT3X_Data_Buffer[6]; //byte 0,1 is temperature byte 4,5 is humidity u8 r_s=0; u8 i; unsigned short tmp = 0; uint16_t dat; IIC_Start(); //发送起始信号 IIC_WriteOneByteData(SHT30_AddrW); //写设备地址 r_s=IIC_GetACK();//获取应答 if(r_s)printf("SHT3X_error:1\r\n"); IIC_WriteOneByteData(0xE0); //写数据 r_s=IIC_GetACK();//获取应答 if(r_s)printf("SHT3X_error:2\r\n"); IIC_WriteOneByteData(0x00); //写数据 r_s=IIC_GetACK();//获取应答 if(r_s)printf("SHT3X_error:3\r\n"); //IIC_Stop(); //停止信号 // DelayMs(30); //等待 //读取sht30传感器数据 IIC_Start(); //发送起始信号 IIC_WriteOneByteData(SHT30_AddrR); r_s=IIC_GetACK();//获取应答 if(r_s)printf("SHT3X_error:7\r\n"); for(i=0;i<6;i++) { SHT3X_Data_Buffer[i]=IIC_ReadOneByteData(); //接收数据 if(i==5) { IIC_SendACK(1); //发送非应答信号 break; } IIC_SendACK(0); //发送应答信号 } IIC_Stop(); //停止信号 // /* check tem */ data[0] = SHT3X_Data_Buffer[0]; data[1] = SHT3X_Data_Buffer[1]; data[2] = SHT3X_Data_Buffer[2]; tmp=SHT3x_CheckCrc(data, 2, data[2]); if( !tmp ) /* value is ture */ { dat = ((uint16_t)data[0] << 8) | data[1]; *Temperature = SHT3x_CalcTemperatureC( dat ); } // /* check humidity */ data[0] = SHT3X_Data_Buffer[3]; data[1] = SHT3X_Data_Buffer[4]; data[2] = SHT3X_Data_Buffer[5]; tmp=SHT3x_CheckCrc(data, 2, data[2]); if( !tmp ) /* value is ture */ { dat = ((uint16_t)data[0] << 8) | data[1]; *Humidity = SHT3x_CalcRH( dat ); }}
4.3 iic.c
#include "iic.h"/*函数功能:IIC接口初始化硬件连接:SDA:PB7SCL:PB6*/void IIC_Init(void){ RCC->APB2ENR|=1<<3;//PB GPIOB->CRL&=0x00FFFFFF; GPIOB->CRL|=0x33000000; GPIOB->ODR|=0x3<<6;}/*函数功能:IIC总线起始信号*/void IIC_Start(void){ IIC_SDA_OUTMODE(); //初始化SDA为输出模式 IIC_SDA_OUT=1; //数据线拉高 IIC_SCL=1; //时钟线拉高 DelayUs(4); //电平保持时间 IIC_SDA_OUT=0; //数据线拉低 DelayUs(4); //电平保持时间 IIC_SCL=0; //时钟线拉低}/*函数功能:IIC总线停止信号*/void IIC_Stop(void){ IIC_SDA_OUTMODE(); //初始化SDA为输出模式 IIC_SDA_OUT=0; //数据线拉低 IIC_SCL=0; //时钟线拉低 DelayUs(4); //电平保持时间 IIC_SCL=1; //时钟线拉高 DelayUs(4); //电平保持时间 IIC_SDA_OUT=1; //数据线拉高}/*函数功能:获取应答信号返 回 值:1表示失败,0表示成功*/u8 IIC_GetACK(void){ u8 cnt=0; IIC_SDA_INPUTMODE();//初始化SDA为输入模式 IIC_SDA_OUT=1; //数据线上拉 DelayUs(2); //电平保持时间 IIC_SCL=0; //时钟线拉低,告诉从机,主机需要数据 DelayUs(2); //电平保持时间,等待从机发送数据 IIC_SCL=1; //时钟线拉高,告诉从机,主机现在开始读取数据 while(IIC_SDA_IN) //等待从机应答信号 { cnt++; if(cnt>250)return 1; } IIC_SCL=0; //时钟线拉低,告诉从机,主机需要数据 return 0;}/*函数功能:主机向从机发送应答信号函数形参:0表示应答,1表示非应答*/void IIC_SendACK(u8 stat){ IIC_SDA_OUTMODE(); //初始化SDA为输出模式 IIC_SCL=0; //时钟线拉低,告诉从机,主机需要发送数据 if(stat)IIC_SDA_OUT=1; //数据线拉高,发送非应答信号 else IIC_SDA_OUT=0; //数据线拉低,发送应答信号 DelayUs(2); //电平保持时间,等待时钟线稳定 IIC_SCL=1; //时钟线拉高,告诉从机,主机数据发送完毕 DelayUs(2); //电平保持时间,等待从机接收数据 IIC_SCL=0; //时钟线拉低,告诉从机,主机需要数据}/*函数功能:IIC发送1个字节数据函数形参:将要发送的数据*/void IIC_WriteOneByteData(u8 data){ u8 i; IIC_SDA_OUTMODE(); //初始化SDA为输出模式 IIC_SCL=0; //时钟线拉低,告诉从机,主机需要发送数据 for(i=0;i<8;i++) { if(data&0x80)IIC_SDA_OUT=1; //数据线拉高,发送1 else IIC_SDA_OUT=0; //数据线拉低,发送0 IIC_SCL=1; //时钟线拉高,告诉从机,主机数据发送完毕 DelayUs(2); //电平保持时间,等待从机接收数据 IIC_SCL=0; //时钟线拉低,告诉从机,主机需要发送数据 DelayUs(2); //电平保持时间,等待时钟线稳定 data<<=1; //先发高位 }}/*函数功能:IIC接收1个字节数据返 回 值:收到的数据*/u8 IIC_ReadOneByteData(void){ u8 i,data; IIC_SDA_INPUTMODE();//初始化SDA为输入模式 for(i=0;i<8;i++) { IIC_SCL=0; //时钟线拉低,告诉从机,主机需要数据 DelayUs(2); //电平保持时间,等待从机发送数据 IIC_SCL=1; //时钟线拉高,告诉从机,主机现在正在读取数据 data<<=1; if(IIC_SDA_IN)data|=0x01; DelayUs(2); //电平保持时间,等待时钟线稳定 } IIC_SCL=0; //时钟线拉低,告诉从机,主机需要数据 (必须拉低,否则将会识别为停止信号) return data;}
边栏推荐
- Analyse approfondie de kubebuilder
- 抖音或将推出独立种草社区平台:会不会成为第二个小红书
- Implementation of JSTL custom function library
- JS input and output
- Tree map: tree view - draw covid-19 array diagram
- How does vscade use the built-in browser?
- JDBC link Oracle reference code
- Intel and Xinbu technology jointly build a machine vision development kit to jointly promote the transformation of industrial intelligence
- If you ask me about R code debugging, I will tell you head, STR, help
- What is JVM? What are the purposes of JVM tuning?
猜你喜欢
What about the collapse of win11 playing pubg? Solution to win11 Jedi survival crash
System framework of PureMVC
JDBC link Oracle reference code
3GPP信道模型路损基础知识
How does vscade use the built-in browser?
This "advanced" technology design 15 years ago makes CPU shine in AI reasoning
The easycvr platform is connected to the RTMP protocol, and the interface call prompts how to solve the error of obtaining video recording?
Field data acquisition and edge calculation scheme of CNC machine tools
The request request is encapsulated in uni app, which is easy to understand
AI 落地新题型 RPA + AI =?
随机推荐
Advertising attribution: how to measure the value of buying volume?
Deeply cultivate the developer ecosystem, accelerate the innovation and development of AI industry, and Intel brings many partners together
Tiktok may launch an independent grass planting community platform: will it become the second little red book
Jetson nano configures pytorch deep learning environment / / to be improved
Mathematical analysis_ Notes_ Chapter 10: integral with parameters
Gavin teacher's perception of transformer live class - rasa project actual combat e-commerce retail customer service intelligent business dialogue robot microservice code analysis and dialogue experim
R language principal component PCA, factor analysis, clustering analysis of regional economy analysis of Chongqing Economic Indicators
树与图的深度优先遍历模版原理
Intel David tuhy: the reason for the success of Intel aoten Technology
Common Oracle SQL statements
一图看懂!为什么学校教了你Coding但还是不会的原因...
九章云极DataCanvas公司获评36氪「最受投资人关注的硬核科技企业」
mpf2_ Linear programming_ CAPM_ sharpe_ Arbitrage Pricin_ Inversion Gauss Jordan_ Statsmodel_ Pulp_ pLU_ Cholesky_ QR_ Jacobi
How to package the parsed Excel data into objects and write this object set into the database?
Terms used in the Web3 community
Win11 control panel shortcut key win11 multiple methods to open the control panel
acwing 843. n-皇后问题
Oracle - views and sequences
Analyse approfondie de kubebuilder
offer如何选择该考虑哪些因素