当前位置:   article > 正文

STM32读取HX711压力传感器芯片数据_hx711 stm32

hx711 stm32

目录

一、HX711压力传感器芯片介绍

1.1 HX711芯片介绍

1.2 芯片管脚与描述

1.3 芯片特点

二、测量原理

2.1 芯片原理图

2.2 压力传感器输出电压值

2.3 芯片原理概述

2.4 数据输出,输入通道和增益选择时序图

2.5 程序计算原理

2.5.1 如何计算传感器供电电压?

 2.5.2 如何将 AD 值反向转换为重力值?

三、单片机介绍

3.1 STM32F103C8T6最小系统板

四、接线说明

4.1 称重模块实物图

4.2 压力传感器与HX711芯片接线图

4.3 HX711芯片与单片机接线

五、代码编写

5.1 HX711.C

5.2 HX711.H 

5.3 MAIN.C

5.3.1 添加头文件

 5.3.2 初始化

 5.3.3 初始化完成后首先进行一次去皮

5.3.4 测重函数

5.3.5 完整main函数(带显示屏显示)

六、测量效果


一、HX711压力传感器芯片介绍

1.1 HX711芯片介绍

       HX711 是一款专为高精度电子秤而设计的 24 位 A/D 转 换器芯片。与同类型其它芯片相比,该芯片集 成了包括稳压电源、片内时钟振荡器等其它同 类型芯片所需要的外围电路,具有集成度高、 响应速度快、抗干扰性强等优点。降低了电子 秤的整机成本,提高了整机的性能和可靠性。

        该芯片与后端 MCU 芯片的接口和编程非常 简单,所有控制信号由管脚驱动,无需对芯片 内部的寄存器编程。输入选择开关可任意选取 通道 A 或通道 B,与其内部的低噪声可编程放 大器相连。通道 A 的可编程增益为 128 或 64, 对应的满额度差分输入信号幅值分别为±20mV 或±40mV。通道 B 则为固定的 32 增益,用于系 统参数检测。芯片内提供的稳压电源可以直接 向外部传感器和芯片内的 A/D 转换器提供电 源,系统板上无需另外的模拟电源。芯片内的 时钟振荡器不需要任何外接器件。上电自动复 位功能简化了开机的初始化过程。

1.2 芯片管脚与描述

VCC和GND引脚分别为HX711芯片的电源输入端口,供电2.6-5.5V。

DOUT是HX711芯片的数据输出引脚,它输出经过传感器A/D转换处理后的24位压力数据。

SCK是HX711芯片的时钟输入引脚,用于控制传感器进行A/D转换的时钟信号。

1.3 芯片特点

1.两路可选择差分输入

2.片内低噪声可编程放大器,可选增益为 32,64 和 128

3.片内稳压电路可直接向外部传感器和芯片内 A/D 转换器提供电源

4.片内时钟振荡器无需任何外接器件,必要时 也可使用外接晶振或时钟

5.上电自动复位电路 • 简单的数字控制和串口通讯:所有控制由管 脚输入,芯片内寄存器无需编程

6. 可选择 10Hz 或 80Hz 的输出数据速率

7.同步抑制 50Hz 和 60Hz 的电源干扰

8.耗电量(含稳压电源电路): 典型工作电流:< 1.6mA, 断电电流:< 1µA

9.工作电压范围:2.6 ~ 5.5V

10.工作温度范围:-40 ~ +85℃

11.16 管脚的 SOP-16 封装

二、测量原理

2.1 芯片原理图

2.2 压力传感器输出电压值

满量程输出电压=激励电压*灵敏度 1.0mv/v 例如:供电电压是 5v 乘以灵敏度 1.0mv/v=满量程 5mv。 相当于有 5Kg 重力产生时候产生 5mV 的电压。

2.3 芯片原理概述

711 模块 A 通道带有 128 倍信号增益,可以将 5mV 的电压放大 128 倍,然后采样输 出 24bit AD 转换的值,单片机通过指定时序将 24bit 数据读出。

2.4 数据输出,输入通道和增益选择时序图

1. 当DOUT(数据输出引脚)为高电平时,表明A/D转换器还未准备好输出数据,此时串口时钟输入信号PD_SCK应为低电平;

2. 当DOUT从高电平变低电平后,PD_SCK应输入25至27个不等的时钟脉冲(其中前24各时钟脉冲输出的是传感器测得的ADC数据,第25-27个时钟脉冲与数据无关,仅用于选择下一次传感器的输出增益和输出通道)。

 3. 在第一个时钟脉冲的上升沿会读取出输出的24位数据的最高位(即最高有效位,MSB),然后在接下来的时钟脉冲中,逐位输出这24位数据,从最高位到最低位。这个过程会一直持续,直到24位数据全部输出完成。传感器的数据输出是从高位到低位的。

2.5 程序计算原理

2.5.1 如何计算传感器供电电压?

       HX711 可以在产生 VAVDD 和 AGND 电压,即 711 模块上的 E+和 E-电压。 该电压通过 VAVDD=VBG(R1 +R2 )/R2 计算。 VBG 为模块儿基准电压 1.25v R1 = 20K,R2 = 8.2K 因此得出 VAVDD = 4.3V (为了降低功耗,该电压只在采样时刻才有输出,因此用万用表读取的值可能低于 4.3v,因 为万用表测量的是有效值。)

 2.5.2 如何将 AD 值反向转换为重力值?

        假设重力为 A Kg,(x<5Kg),测量出来的 AD 值为 y 传感器输出,发送给 AD 模块儿的电压为 A Kg * 4.3mV / 5Kg = 0.86A mV 经过 128 倍增益后为 128 * 0.86A = 110.08AmV 转换为 24bit 数字信号为 110.08A mV * 224 / 4.3V = 429496.7296A 所以 y = 429496.7296A 因此得出 A = y / 429496.7296 。

所以得出程序中计算公式 Weight_Shiwu = (unsigned long)((float)Weight_Shiwu/429.5);

特别注意: 因为不同的传感器斜率特性曲线不是完全一样,因此,每一个传感器需要矫正这里的 429.5 这个除数,才能达到精度很高。

#define GapValue 430

当发现测试出来的重量偏大时,增加该数值。 如果测试出来的重量偏小时,减小改数值。该值可以为小数,例如 429.5 等。

三、单片机介绍

3.1 STM32F103C8T6最小系统板

本文使用的开发板为STM32F103C8T6最小系统板,HX711芯片使用到的引脚为PB0和PB1引脚。

四、接线说明

4.1 称重模块实物图

4.2 压力传感器与HX711芯片接线图

4.3 HX711芯片与单片机接线

HX711芯片与单片机的接线取决于HX711.H中的引脚宏定义:

  1. #define HX711_SCK PBout(0)// PB0
  2. #define HX711_DOUT PBin(1)// PB1

此处定义了SCK时钟引脚为PB0,DOUT输出引脚为PB1,则模块上的SCK接PB0,DT接PB1。

如果需要修改引脚,直接修改此处的宏定义。

注意:这两个引脚在HX711.C中会先初始化,修改了宏定义之后需要去HX711.C中将初始化的引脚也进行修改! 引脚初始化函数为:void Init_HX711pin(void);

五、代码编写

5.1 HX711.C

  1. #include "HX711.h"
  2. #include "delay.h"
  3. u32 HX711_Buffer;
  4. u32 Weight_Maopi;
  5. s32 Weight_Shiwu;
  6. u8 Flag_Error = 0;
  7. //校准参数
  8. //因为不同的传感器特性曲线不是很一致,因此,每一个传感器需要矫正这里这个参数才能使测量值很准确。
  9. //当发现测试出来的重量偏大时,增加该数值。
  10. //如果测试出来的重量偏小时,减小改数值。
  11. //该值可以为小数
  12. #define GapValue 106.5
  13. void Init_HX711pin(void)
  14. {
  15. GPIO_InitTypeDef GPIO_InitStructure;
  16. RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); //使能PF端口时钟
  17. //HX711_SCK
  18. GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; // 端口配置
  19. GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; //推挽输出
  20. GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //IO口速度为50MHz
  21. GPIO_Init(GPIOB, &GPIO_InitStructure); //根据设定参数初始化GPIOB
  22. //HX711_DOUT
  23. GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
  24. GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;//输入上拉
  25. GPIO_Init(GPIOB, &GPIO_InitStructure);
  26. GPIO_SetBits(GPIOB,GPIO_Pin_0); //初始化设置为0
  27. }
  28. //****************************************************
  29. //读取HX711
  30. //****************************************************
  31. u32 HX711_Read(void) //增益128
  32. {
  33. unsigned long count;
  34. unsigned char i;
  35. HX711_DOUT=1;
  36. delay_us(1);
  37. HX711_SCK=0;
  38. count=0;
  39. while(HX711_DOUT);
  40. for(i=0;i<24;i++)
  41. {
  42. HX711_SCK=1;
  43. count=count<<1;
  44. delay_us(1);
  45. HX711_SCK=0;
  46. if(HX711_DOUT)
  47. count++;
  48. delay_us(1);
  49. }
  50. HX711_SCK=1;
  51. count=count^0x800000;//25个脉冲下降沿来时,转换数据
  52. delay_us(1);
  53. HX711_SCK=0;
  54. return(count);
  55. }
  56. //****************************************************
  57. //获取毛皮重量
  58. //****************************************************
  59. void Get_Maopi(void)
  60. {
  61. Weight_Maopi = HX711_Read();
  62. }
  63. //****************************************************
  64. //称重
  65. //****************************************************
  66. void Get_Weight(void)
  67. {
  68. HX711_Buffer = HX711_Read();
  69. if(HX711_Buffer > Weight_Maopi)
  70. {
  71. Weight_Shiwu = HX711_Buffer;
  72. Weight_Shiwu = Weight_Shiwu - Weight_Maopi; //获取实物的AD采样数值。
  73. Weight_Shiwu = (s32)((float)Weight_Shiwu/GapValue); //计算实物的实际重量
  74. //因为不同的传感器特性曲线不一样,因此,每一个传感器需要矫正这里的GapValue这个除数。
  75. //当发现测试出来的重量偏大时,增加该数值。
  76. //如果测试出来的重量偏小时,减小改数值。
  77. }
  78. }

代码 u32 HX711_Read(void) 说明:

函数中,count是一个无符号长整型变量,用于存储从HX711获取的数据。

i是一个无符号字符型变量,用于循环读取HX711芯片数据的次数。

延时1微秒用于确保时序的准确性。

函数通过设置HX711_DOUT和HX711_SCK的电平,使HX711传感器进入读取状态。接下来,函数使用while语句来等待DOUT的第一个脉冲到来。当DOUT为高电平时,表示HX711传感器还没有准备好,此时需要等待。当DOUT为低电平时,表示HX711传感器已经准备好,可以开始读取数据了。

当传感器准备好读取后,函数使用一个for循环来读取HX711芯片的i个数据位。在每个时钟周期中,函数将SCK设为高电平,然后将count左移一位。如果此时DOUT为高电平,则表示在该时钟周期内,HX711传感器向count的当前位中写入了1,此时需要将count的最低位设为1。

读取完24个数据位后,此时count变量中存储着24位的数据。此时需要将count的最高位设为1,以便扩展到32位。这可以通过将count异或0x800000来实现。

最后,函数将SCK设为高电平,并延时一个周期,然后将SCK设为低电平。该函数返回count变量作为结果,即为从HX711传感器读取到的数据。经过转换后即可得到被测物体的重量。

5.2 HX711.H 

  1. #ifndef __HX711_H
  2. #define __HX711_H
  3. #include "sys.h"
  4. #define HX711_SCK PBout(0)// PB0
  5. #define HX711_DOUT PBin(1)// PB1
  6. extern void Init_HX711pin(void);
  7. extern u32 HX711_Read(void);
  8. extern void Get_Maopi(void);
  9. extern void Get_Weight(void);
  10. extern u32 HX711_Buffer;
  11. extern u32 Weight_Maopi;
  12. extern s32 Weight_Shiwu;
  13. extern u8 Flag_Error;
  14. #endif

5.3 MAIN.C

5.3.1 添加头文件

  1. #include "delay.h"
  2. #include "HX711.h"

 5.3.2 初始化

  1. Init_HX711pin();
  2. delay_init();

延时函数需要自己加入,用于确保读取的准确性。

 5.3.3 初始化完成后首先进行一次去皮

  1. Get_Maopi(); //称毛皮重量
  2. delay_ms(2000);
  3. Get_Maopi(); //重新获取毛皮重量

系统初始化过程中,需要确保压力传感器上没有物品,否则系统初始化会将当前的重量作为初始值,影响后面物体的实际重量。

5.3.4 测重函数

  1. while(1)
  2. {
  3. Get_Weight();
  4. }

5.3.5 完整main函数(带显示屏显示)

  1. #include "stm32f10x.h"
  2. #include "delay.h"
  3. #include "HX711.h"
  4. #include "oled.h"
  5. #include "stdio.h"
  6. int main(void)
  7. {
  8. Init_HX711pin();
  9. delay_init();
  10. OLED_Init();
  11. OLED_ColorTurn(0);//0正常显示,1 反色显示
  12. OLED_DisplayTurn(0);//0正常显示 1 屏幕翻转显示
  13. OLED_Clear();
  14. Get_Maopi(); //称毛皮重量
  15. delay_ms(2000);
  16. Get_Maopi(); //重新获取毛皮重量
  17. OLED_ShowChinese(0,0,0,16,1); //当
  18. OLED_ShowChinese(16,0,1,16,1); //前
  19. OLED_ShowChinese(32,0,2,16,1); //重
  20. OLED_ShowChinese(48,0,3,16,1); //量
  21. OLED_ShowChar(64,0,':',16,1); //:
  22. OLED_ShowChar(112,0,'g',16,1); //g
  23. while(1)
  24. {
  25. OLED_Refresh();
  26. Get_Weight();
  27. }
  28. }

显示屏相关教学看我主页另外一篇文章:

0.96寸OLED显示屏显示字符串、汉字(stm32标准库)_stm32oled文字库-CSDN博客

六、测量效果

当前重量即单片机读取HX711芯片数据后经过转换得到的重量。

声明:本文内容由网友自发贡献,转载请注明出处:【wpsshop博客】
推荐阅读
相关标签
  

闽ICP备14008679号