[STM32U5] 【NUCLEO-U5A5ZJ-Q测评】读取NST112温湿度传感器数据

[复制链接]
 楼主| EPTmachine 发表于 2023-12-10 15:57 | 显示全部楼层 |阅读模式
<
1、读取HS3003温度传感器的数据
支持I2C接口的传感器种类有很多,本文对使用STM32U5的I2C读取NST112温湿度传感器的数据进行介绍。
2、 6812565756d993c7ea.png 硬件配置
本次使用一块扩展板上的NST112温度传感器作为硬件,温度传感器为纳芯微的NST112。
700b92e88f62d7035a221add344e342f
拓展板的界限引脚定义为和开发板与传感器器模块的接线图如图所示。
258d31aeaa88bae78ec60d268c3f4d45
9397c5a1f3fb52152a09b8a7cf9ba17e
3、软件编写
首先,在STM32 CubeIDE中创建开发板的工程,选择根据开发板创建工程,
3ea0a23d7070bfe22bf373d48a688e5c
在CubeMX界面中会自动初始化开发板上的部分外设,比如串口、调试口、LED等,本文通过I2C1控制传感器,使用的PB8和PB9,选择对应管脚的复用功能,并在I2C的配置界面选择相应的I2C通讯参数。
b6466146184f5cc5f6bebcb097316768
完成上述操作后,保存配置并生成相应的外设初始化代码。
通过查看数据手册可知,ADD引脚的接线方式决定芯片的从机地址,结合原理图可知传感器的从机地址为0x48。
7c88a25f3e186b4ee1fa1367741b42d9
由于STM32 HAL接口的实现问题,在传入从机地址时,需要将第8位的读写控制位作为从机地址作为函数的参数传入。相关的宏定义如下
查看数据手册,可知NST112的寄存器一共有4个:配置寄存器、温度寄存器、温度上限寄存器以及温度下限寄存器。
在数据手册查看配置寄存器的介绍,在默认状态下,传感器工作在连续转换的工作模式下,转换分辨率为12位。
b36c2a69f59d0361e859dcf3f74075f9
f5b1017f1c5b883376410e8228b525b6
传感器中的寄存器的字长位16位,访问的时序如下图所示。
b7819de06636ce088b30ef505f02f30d
写操作的数据域为寄存器地址和两字节的数据,16位数据的高字节在前。
9544ffbccf98ccec141e9b9f5ccadfb8
读操作的方式位,先写入寄存器地址,后进行读取。
综上,可以写出传感器寄存器的读写函数如下:
  1. void nst112_writeRegister( int reg_address, uint16_t val) {

  2.     uint8_t ii[3]={0x00,0x00,0x00};
  3.     ii[0] = reg_address;
  4.     ii[1] = (uint8_t)((0xFF00 & val)>>8);
  5.     ii[2] = (uint8_t)(0x00FF & val);

  6.         if (HAL_I2C_Master_Transmit(&hi2c1, (uint16_t)NST112_I2C_ADDRESS_W, ii, 0x03,10000) != HAL_OK)
  7.         {
  8.         /* Error_Handler() function is called when error occurs. */
  9.         Error_Handler();
  10.         }

  11.         /*##- Wait for the end of the transfer #################################*/
  12.         /*  Before starting a new communication transfer, you need to check the current
  13.           state of the peripheral; if it�s busy you need to wait for the end of current
  14.           transfer before starting a new one.
  15.           For simplicity reasons, this example is just waiting till the end of the
  16.           transfer, but application may perform other tasks while transfer operation
  17.           is ongoing. */
  18.         while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY)
  19.         {
  20.         }

  21. }

  22. uint16_t nst112_readRegister(uint8_t reg_address) {

  23.         uint16_t value=0;
  24.     uint8_t temp[2]={0x00,0x00};


  25.         if (HAL_I2C_Master_Transmit(&hi2c1, (uint16_t)NST112_I2C_ADDRESS_W, ®_address, 0x01,10000) != HAL_OK)
  26.         {
  27.         /* Error_Handler() function is called when error occurs. */
  28.         Error_Handler();
  29.         }

  30.         /*##- Wait for the end of the transfer #################################*/
  31.         /*  Before starting a new communication transfer, you need to check the current
  32.           state of the peripheral; if it�s busy you need to wait for the end of current
  33.           transfer before starting a new one.
  34.           For simplicity reasons, this example is just waiting till the end of the
  35.           transfer, but application may perform other tasks while transfer operation
  36.           is ongoing. */
  37.         while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY)
  38.         {
  39.         }



  40.     /* Read data back from the I2C slave */

  41.         if (HAL_I2C_Master_Receive(&hi2c1, (uint16_t)NST112_I2C_ADDRESS_R, temp, 0x02,10000) != HAL_OK)
  42.         {
  43.         /* Error_Handler() function is called when error occurs. */
  44.         Error_Handler();
  45.         }

  46.         /*##- Wait for the end of the transfer #################################*/
  47.         /*  Before starting a new communication transfer, you need to check the current
  48.           state of the peripheral; if it�s busy you need to wait for the end of current
  49.           transfer before starting a new one.
  50.           For simplicity reasons, this example is just waiting till the end of the
  51.           transfer, but application may perform other tasks while transfer operation
  52.           is ongoing. */
  53.         while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY)
  54.         {
  55.         }

  56.         value=temp[0];
  57.         value=value<<8;
  58.         value=value | temp[1];

  59.     return value;
  60. }

传感器在默认模式即可以实现温度检测,实现温度的读取,实际上只要实现读取温度寄存器值的函数即可。函数如下
  1. float nst112_readTemp(void) {
  2.     uint16_t Origin_Temp = nst112_readRegister(TEMP_REG);
  3.     float Temp=0;
  4.     Temp = (char)(Origin_Temp>>8);
  5.     unsigned char decimal=(unsigned char)Origin_Temp;
  6.     if(Temp>=0){
  7.             Temp += (float)(decimal>>4)/16;
  8.     }
  9.     else
  10.     {
  11.         Temp -= (float)(((~decimal)>>4)+1)/16;
  12.     }
  13.         return Temp;

  14. }

在主函数中调用以下函数
  1.   while (1)
  2.   {
  3.         HAL_Delay(1000);
  4.         Curr_Temp = nst112_readTemp();
  5.         Chip_Config = nst112_getconfig();
  6.         printf("global temp is %f\r\n",Curr_Temp);
  7.     /* USER CODE END WHILE */

  8.     /* USER CODE BEGIN 3 */
  9.   }

实际的温度通过串口打印效果如图。
405565756dc354d86.png
4、总结
NST112温度寄存器的操作很简单,同时采集的数据为温度信息,在生活十分常见,很适合作为嵌入式入门的练手项目。


NST112-DSTR_Datasheet_Rev_1.9_EN.pdf

1 MB, 下载次数:

IOBV3-ESP32.pdf

99.03 KB, 下载次数: 2

U5A5ZJ_I2C_NST112.zip

1.43 MB, 下载次数: 3

duo点 发表于 2023-12-14 16:26 | 显示全部楼层
在代码示例中,如何处理读取失败的情况?
您需要登录后才可以回帖 登录 | 注册

本版积分规则

26

主题

487

帖子

4

粉丝
快速回复 在线客服 返回列表 返回顶部

26

主题

487

帖子

4

粉丝
快速回复 在线客服 返回列表 返回顶部