OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 20201|回复: 25

SHT30温湿度传感器,驱动代码(官方例程魔改),亲测可用

[复制链接]

10

主题

80

帖子

0

精华

高级会员

Rank: 4

积分
514
金钱
514
注册时间
2017-5-21
在线时间
82 小时
发表于 2019-7-20 15:45:04 | 显示全部楼层 |阅读模式
本帖最后由 Anyint 于 2019-8-4 13:55 编辑

近几日有一个项目要用到温湿度传感器,网上查阅一大堆代码,发现有些代码使用的时候有一下几个问题:
1. 读取温湿度数据的时候,要再SHT30_Read()后加delay_ms()
2. 初始化sht30后,直接调用读取数据的函数,读出的数据都是0或者是乱的数据,要过一段时间后,才能读出数据,仿佛传感器初始化一直没完成或者寄存器的值有问题,这个不得而知,反正代码上有问题,有缺陷。

以上两个问题一直困扰我好几天,在主函数里调用的时候,时好时坏,而上面的小问题依然没有解决。但是为了产品的稳定性,一定要解决掉上面的问题。
记得买模块的时候,店家是给了一个SHT30的压缩包,包里的文件都是一些参考文档,没有现成封装好的.c/.h文件,尤其是给STM32F103ZET6这块芯片的代码没有说明白,然后痛下决心要把包里关于SHT30的官方说明文档吃透,由于它是PDF文档,脑壳疼不能直接copy代码,在网上找了一个在线PDF转WORD的网站进行转格式,最后将转好的word里的代码一步一步copy自己的项目中进行SHT30外设驱动代码的封装工作。
封装好,看似这份代码很舒服(大佬的代码,满满的英文注释),然后参考它的main的写法,将SHT30初始化函数和SHT30读取温度函数写好,再加入USART1串口初始化,最后在while中写上printf的代码,这样就可以在串口调试助手上查看温湿度数据。

需要的设备:STM32F103ZET6精英开发板、一根USB线接到开发板的串口1、SHT30模块
接线要求:官方代码的I2C接口是接在开发板的PB13、PB14
1. PB13->SCL
2. PB14->SDA
注:除了这两根线,还有RESET、ALERT这两根线,目前不知道它有啥用,而且模块也就四根线(VCC\GND\SDA\SCL),所以就不管这两根线,这部分代码可以屏蔽。

移植的时候报错处理:(1)将system.h和system.c的void SystemInit(void)声明和定义都给屏蔽掉,因为它与系统的SystemInit函数冲突!

代码调试过程中的问题:
1. 出现读取serialNumber的时候,error返回1,说是模块没有返回应答信息。这个时候我怀疑是时序问题,首先查的是delay函数准不准的问题,一般原子的那个delay.h里的delay_us()还是准的,毕竟是滴答时钟的信号过来的,将官方代码的system.c文件里的DelayMicroSeconds函数体里的内容换成delay_us(nbrOfUs),并在system.c中包入delay.h头文件;这个时候在此调试发现数据能读出,时序正常了。
2. 时序对了,error还是返回0,考虑器件接触不良的问题。当时我真的觉得这代码要炸了,想砸了那个SHT30模块,这个让我日日夜夜都惆怅的模块呀,然后我就把SHT30拔出来,摸了一下它,吹了一下它,然后在给它接回去。奇迹发生了,串口调试助手里,突然serialNumber读出,error返回0,表示成功,温湿度数据也传上来了!!!!激动++++++


代码优势:(经过一系列的调试,代码终于稳定,且封装也差不多了)
1. 隔多久读取一次数据随意(它吃的消),读取的时间极短(从开始读取到结束读取,ms级没问题)。好歹I2C的传输速度也挺快的,SHT30这个模块也还不错,读个数据还要delay放中断里那不是要出事,关键它加了delay也不稳定。
2. 官方代码,比较稳定3. 端口随意改,模拟I2C,v1.0版本:它是寄存器操作代码pb14\pb13,改起来不是很方便     v2.0版本:个人把i2c部分改成库函数,端口随意改



调用办法:
1. 导入那个SHT3x的文件夹至工程目录下的HARDWARE文件夹下,主函数包入sht3x.h、system.h
2. mian函数中定义2个变量
    ft        temperature; // temperature [°C]
    ft        humidity;        // relative humidity [%RH]

    再插入初始化代码SHT3X_Init(0x44);//0x44为I2C器件地址,根据实际情况来改
    delay_ms(50);        //wait 50ms after power on//加入一个50ms延时,等待稳定数据,只需调用一次,后面读取数据不用了。
3. SHT3X_GetTempAndHumi(&temperature, &humidity, REPEATAB_HIGH, MODE_CLKSTRETCH, 50);//!!!!!!!!这行代码的最后一个参数timeout超时设置为50,读取一次数据要15ms,timeout设置成10,读取一次数据要1~2ms
    printf("temperature=%.1f℃\thumidity=%.1f%%RH\terror=%d\r\n",(float)temperature,(float)humidity,(u8)error);
该代码可以放入while(1){........}中,或者放在另外的中断服务函数TIMX_IRQHandler中都可以。
  1. /*
  2. * 文件名称:main
  3. * 作    者:Anyint
  4. * 版    本:v1.0
  5. * 说    明:工程模板
  6. * 修改记录:2019/07/19 建立模板
  7. */

  8. #include "stm32f10x.h"
  9. #include "delay.h"
  10. #include "usart.h"
  11. #include "sht3x.h"
  12. #include "system.h"

  13. /*
  14. * 函数名称:mian
  15. * 函数功能:主函数,程序入口函数
  16. * 入口参数:void
  17. * 出口参数:int
  18. * 备    注:
  19. */
  20. int main(void)
  21. {
  22.     ft        temperature;        // temperature [°C]
  23.     ft        humidity;                // relative humidity [%RH]
  24.     etError   error;        // error code
  25.     delay_init();
  26.     uart_init(9600);
  27.     SHT3X_Init(0x44);
  28.     delay_ms(50);
  29.    
  30.     while(1)
  31.     {
  32.         SHT3X_GetTempAndHumi(&temperature, &humidity, REPEATAB_HIGH, MODE_CLKSTRETCH, 50);
  33.         printf("temperature=%.1f℃\thumidity=%.1f%%RH\terror=%d\r\n",(float)temperature,(float)humidity,(u8)error);
  34.     }
  35. }
复制代码
sht3x template(v2.0).rar (4.89 MB, 下载次数: 7663)
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
2
金钱
2
注册时间
2022-7-4
在线时间
0 小时
发表于 2022-7-4 10:49:06 | 显示全部楼层
回复 支持 1 反对 0

使用道具 举报

17

主题

46

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
251
金钱
251
注册时间
2016-9-9
在线时间
92 小时
发表于 2019-8-7 21:53:50 | 显示全部楼层
楼主你好,我把代码直接放在F1是正常的,但是放在F0上面获取的温湿度都是0,请问可能是什么原因呢?
回复 支持 反对

使用道具 举报

0

主题

3

帖子

0

精华

新手入门

积分
5
金钱
5
注册时间
2019-8-9
在线时间
1 小时
发表于 2019-8-9 17:04:35 | 显示全部楼层
很好用
回复 支持 反对

使用道具 举报

10

主题

80

帖子

0

精华

高级会员

Rank: 4

积分
514
金钱
514
注册时间
2017-5-21
在线时间
82 小时
 楼主| 发表于 2019-8-10 09:55:23 | 显示全部楼层
xmlhttp 发表于 2019-8-7 21:53
楼主你好,我把代码直接放在F1是正常的,但是放在F0上面获取的温湿度都是0,请问可能是什么原因呢?

可能原因:1.时序不对,官方代码的delay有误差,你F0是48MHz,而F1是72MHz,delay可能要修改一下,多加或者减少1到2个us试试,这个器件对时序要求高。
2.SHT3X_GetTempAndHumi(&temperature, &humidity, REPEATAB_HIGH, MODE_CLKSTRETCH, 50);//!!!!!!!!这行代码的最后一个参数timeout超时设置为50,读取一次数据要15ms,timeout设置成10,读取一次数据要1~2ms。这个地方你改成50或者100的试试看。
3.接触不良,重新插拔一下
4.还解决不了,一步一步调试它的官方代码的每一步,先获取它的Ser……Num这个看,如果能获取后面获取温湿度应该就有了
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
2
金钱
2
注册时间
2019-9-17
在线时间
0 小时
发表于 2019-9-17 10:03:14 | 显示全部楼层
非常感谢楼主的分享,正准备使用这个温湿度传感器
回复 支持 反对

使用道具 举报

10

主题

61

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
334
金钱
334
注册时间
2019-9-15
在线时间
126 小时
发表于 2019-11-26 14:08:28 | 显示全部楼层
xmlhttp 发表于 2019-8-7 21:53
楼主你好,我把代码直接放在F1是正常的,但是放在F0上面获取的温湿度都是0,请问可能是什么原因呢?

你好,我把代码移植到F0系列上也遇到了输出都是0的问题 请问你解决了吗?
回复 支持 反对

使用道具 举报

0

主题

3

帖子

0

精华

新手入门

积分
3
金钱
3
注册时间
2019-11-4
在线时间
3 小时
发表于 2019-11-26 21:02:18 | 显示全部楼层
请问这两个版本的程序有什么不同吗?
我都V2.0的没有用
但是V1.0的可用
回复 支持 反对

使用道具 举报

1

主题

4

帖子

0

精华

初级会员

Rank: 2

积分
79
金钱
79
注册时间
2019-10-22
在线时间
24 小时
发表于 2020-2-21 20:28:30 | 显示全部楼层
请问这个是什么错误[20:27:53.333]收←◆temperature=0.0℃        humidity=0.0%RH        error=134225888
回复 支持 反对

使用道具 举报

17

主题

46

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
251
金钱
251
注册时间
2016-9-9
在线时间
92 小时
发表于 2020-4-13 17:19:03 | 显示全部楼层
人生得意须尽欢 发表于 2019-11-26 14:08
你好,我把代码移植到F0系列上也遇到了输出都是0的问题 请问你解决了吗?

这个很久了,记得不是很清楚了,好像是F0不支持开漏读取电平,把sda作输入和输出时重置一下。
回复 支持 反对

使用道具 举报

0

主题

24

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
483
金钱
483
注册时间
2014-2-9
在线时间
91 小时
发表于 2020-4-16 14:43:55 | 显示全部楼层
A1098834549 发表于 2020-2-21 20:28
请问这个是什么错误[20:27:53.333]收←◆temperature=0.0℃        humidity=0.0%RH        error=134225888

检查一下IIC代码引脚定义,楼主代码里IIC引脚定义是PE3和PE5,不是PB13和PB14
回复 支持 反对

使用道具 举报

0

主题

24

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
483
金钱
483
注册时间
2014-2-9
在线时间
91 小时
发表于 2020-4-16 14:51:33 | 显示全部楼层
本帖最后由 dcp1989 于 2020-4-16 14:56 编辑

补充一下,楼主代码里IIC引脚定义是PE3和PE5,要使用得按自己的接线进行修改,今天测试这个传感器时发现的
源代码:
/* 端口声明 */
#define Sht30_I2C_Sda_GPIO GPIOE
#define Sht30_I2C_Sda_ClockCmd RCC_APB2Periph_GPIOE
#define Sht30_I2C_Sda_PIN GPIO_Pin_5
#define Sht30_I2C_Scl_GPIO GPIOE
#define Sht30_I2C_Scl_ClockCmd RCC_APB2Periph_GPIOE
#define Sht30_I2C_Scl_PIN GPIO_Pin_3

另外串口输出信息中“error”值是函数“SHT3X_GetTempAndHumi”的返回值,需要输出这个值得改成
error=SHT3X_GetTempAndHumi(&temperature, &humidity, REPEATAB_HIGH, MODE_CLKSTRETCH, 50);

不然“error”值就会是一串随机数字,“error”值的含义在“system.h”文件里有说明

// Error codes
typedef enum{
    NO_ERROR = 0x00, // no error
    ACK_ERROR = 0x01, // no acknowledgment error
    CHECKSUM_ERROR = 0x02, // checksum mismatch error
    TIMEOUT_ERROR = 0x04, // timeout error
    PARM_ERROR = 0x80, // parameter out of range error
}etError;


回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
7
金钱
7
注册时间
2020-4-20
在线时间
2 小时
发表于 2020-4-20 15:30:31 | 显示全部楼层
先感谢楼主无私奉献,再看看代码。正好需要
回复 支持 反对

使用道具 举报

13

主题

36

帖子

0

精华

初级会员

Rank: 2

积分
132
金钱
132
注册时间
2018-9-16
在线时间
33 小时
发表于 2020-5-7 21:33:31 | 显示全部楼层
最近我也在用这个东西,感觉间隔1秒读一次都会偶尔有错,把间隔拉长到3秒读一次,错误才少了很多
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
11
金钱
11
注册时间
2020-5-10
在线时间
3 小时
发表于 2020-5-11 11:28:52 来自手机 | 显示全部楼层
V2.0版本sht3X.C里SHT3X()函数里用的是不是PB10和PB12,咋和I2C引脚定义的PE3 PE5不一致
回复 支持 反对

使用道具 举报

4

主题

14

帖子

0

精华

初级会员

Rank: 2

积分
50
金钱
50
注册时间
2018-5-15
在线时间
9 小时
发表于 2020-5-30 22:09:10 | 显示全部楼层
谢谢楼主的分享!
回复 支持 反对

使用道具 举报

1

主题

19

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
282
金钱
282
注册时间
2015-8-10
在线时间
76 小时
发表于 2020-6-18 10:35:50 | 显示全部楼层
谢谢楼主的分享!
回复 支持 反对

使用道具 举报

2

主题

8

帖子

0

精华

初级会员

Rank: 2

积分
133
金钱
133
注册时间
2019-7-29
在线时间
46 小时
发表于 2020-6-18 18:00:32 | 显示全部楼层
我用的是STH10温湿度传感器,发送数据后起码要延时15ms才能读出来,不然也是显示一串0
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
5
金钱
5
注册时间
2020-3-22
在线时间
1 小时
发表于 2020-9-3 23:26:07 | 显示全部楼层
楼主你好,感谢你的分享,我使用了某宝买的SHT30,代码植入后显示很灵敏。然后我用了另一个电器里拆下的STH30,温度报0.1?湿度是0,error=0。请问这种情况下我从哪个方向去改比较好呢?谢谢~
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
4
金钱
4
注册时间
2020-9-27
在线时间
0 小时
发表于 2020-9-27 09:06:22 | 显示全部楼层
感谢分享!
回复 支持 反对

使用道具 举报

5

主题

30

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
269
金钱
269
注册时间
2019-1-3
在线时间
33 小时
发表于 2021-3-11 19:57:54 | 显示全部楼层
感谢楼主分享
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手上路

积分
40
金钱
40
注册时间
2020-8-26
在线时间
7 小时
发表于 2021-5-7 12:56:49 | 显示全部楼层
前面出问题的注意了,这个产品对时序要求特别高,所以尽量不要用杜邦线外接,尽量靠近io口
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
7
金钱
7
注册时间
2021-9-2
在线时间
1 小时
发表于 2021-9-4 19:40:39 | 显示全部楼层
andrewzjc 发表于 2020-9-3 23:26
楼主你好,感谢你的分享,我使用了某宝买的SHT30,代码植入后显示很灵敏。然后我用了另一个电器里拆下 ...

您好你解决问题了吗 我也遇到相似的问题希望能分享一下解决办法
回复 支持 反对

使用道具 举报

0

主题

4

帖子

0

精华

新手上路

积分
33
金钱
33
注册时间
2022-3-5
在线时间
16 小时
发表于 2022-3-25 16:12:31 | 显示全部楼层
亲测可用,非常不错,感谢楼主无私分享。
回复 支持 反对

使用道具 举报

1

主题

3

帖子

0

精华

新手上路

积分
31
金钱
31
注册时间
2022-11-15
在线时间
5 小时
发表于 2022-11-16 09:20:09 | 显示全部楼层

你好,请问你的成功了吗,引脚应该怎么接,PB10,12和PB13,14我都试过了数据都是0
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
11
金钱
11
注册时间
2024-6-21
在线时间
4 小时
发表于 2024-6-21 13:23:50 | 显示全部楼层
11111111
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2024-11-23 22:12

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表