STM32 ADP900代码

ADP900是一款数字型差压传感器,专为高精度测量差压而设计,具有多种显著特点和广泛应用场景。以下是对ADP900的详细介绍:

一、主要特点

  1. 高精度:ADP900传感器在测量空气、氮气、氧气的压力差值时,表现出高精度,零点精度达到0.3Pa,且在整个测量范围内(-500~+500Pa)内精度读数×3%,保证了测量的准确性。
  2. 快速响应:其响应时间快达10ms,能够快速捕捉压力变化,满足对测量速度有较高要求的场景。
  3. 稳定性强:传感器内部采用先进的技术设计,确保测量过程中无漂移,长期稳定性高。
  4. 内置高处理能力MCU:集成了高性能的微控制器单元(MCU),提高了数据处理能力和效率。
  5. 内置温度补偿:通过内置的温度补偿机制,有效降低了温度变化对测量结果的影响。
  6. 数字I²C接口:提供标准的I²C接口,简化了与微处理器的连接,便于集成和使用。

二、技术参数

  • 工作电压:3.2-5.5V
  • 测量范围:-500~+500Pa
  • 响应时间:10ms
  • 通信方式:I²C接口

三、应用场景

ADP900传感器因其出色的性能和稳定性,被广泛应用于多个领域,包括但不限于:

  • 家电行业:如暖通空调系统、燃气锅炉等。
  • 医疗行业:如呼吸装置、热回收系统、过滤器监测等。
  • 消防领域:如余压监控系统。
  • 其他工业应用:颗粒炉、燃料电池等需要精确测量差压的场景。

四、总结

ADP900数字型差压传感器以其高精度、快速响应、稳定性强等特点,在多个行业中得到了广泛应用。其内置的高处理能力MCU和温度补偿机制,进一步提升了传感器的性能和可靠性。同时,标准的I²C接口简化了与微处理器的连接,为用户提供了便捷的使用体验。无论是家电、医疗还是消防等领域,ADP900传感器都是实现精确测量差压的理想选择。

五、代码如下

c文件代码如下:

#include "MYI2C.h"
#include "main.h"

/**
 * @brief	IIC底层延时函数
 *
 * @param   void
 *
 * @return  void
 */

unsigned char M1sensorAddr;

/***************软件延时***************/
void delay_us(unsigned int t)
{
	unsigned int k;

	while(t--)
	{
		for(k=0; k<14; k++)__nop();
	}
}

void delay_20us()//软件延时20us
{
	unsigned int k=208;
	while(k--);
}
void IIC_Init(void)
{
	GPIO_InitTypeDef  GPIO_InitStructure;

    __HAL_RCC_GPIOD_CLK_ENABLE();               //开启GPIOA时钟
    
	
	GPIO_InitStructure.Pin = M1_SDA_Pin;
	GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_HIGH;
	GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_OD;
	GPIO_InitStructure.Pull = GPIO_NOPULL;
	HAL_GPIO_Init(M1_SDA_GPIO_Port, &GPIO_InitStructure);
	GPIO_InitStructure.Pin = M1_SCL_Pin;
	GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_HIGH;
	GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_OD;
	GPIO_InitStructure.Pull = GPIO_NOPULL;
	HAL_GPIO_Init(M1_SCL_GPIO_Port, &GPIO_InitStructure);
	
	HAL_GPIO_WritePin(M1_SDA_GPIO_Port, M1_SDA_Pin, GPIO_PIN_RESET);//默认输出0
	HAL_GPIO_WritePin(M1_SCL_GPIO_Port, M1_SCL_Pin, GPIO_PIN_RESET);//默认输出0

	M1_SDA_HIGH;
	M1_SCL_HIGH;
}


//************************************************************************* M1
static unsigned int M1_IIC_Start(void)
{
	unsigned int TimeOut=500;
	M1_SDA_HIGH;
	M1_SCL_HIGH;
	delay_us(10);
	
	while((M1_SDA_RD==0)||(M1_SCL_RD==0))
	{
		delay_us(2);
		if(TimeOut-- == 0)
			return 1;
	}
	M1_SDA_LOW;
	IIC_DELAY;
	M1_SCL_LOW;
	IIC_DELAY_S;
	return 0;
}

static void M1_IIC_Stop(void)
{
	M1_SCL_LOW;
	IIC_DELAY_S;
	M1_SDA_LOW;
	IIC_DELAY;
	M1_SCL_HIGH;
	IIC_DELAY;
	M1_SDA_HIGH;
}

static void M1_IIC_Ack(unsigned char Ack)
{
	M1_SCL_LOW;
	if(Ack)
	{
		M1_SDA_LOW;
	}
	else
	{
		M1_SDA_HIGH;
	}
	IIC_DELAY_S;
	M1_SCL_HIGH;
	IIC_DELAY;
	
	M1_SCL_LOW;
	IIC_DELAY_S;
	M1_SDA_HIGH;
	IIC_DELAY_S;
}

static unsigned char M1_IIC_TxByte(unsigned char dat)
{
	unsigned char i=8;
	while(i--)
	{
		IIC_DELAY_S;
		if(dat&0x80)
		{
			M1_SDA_HIGH;
		}
		else
		{
			M1_SDA_LOW;
		} 
		IIC_DELAY_S;
		M1_SCL_HIGH;
		IIC_DELAY;
		M1_SCL_LOW;	
		dat <<= 1;  
	}
	IIC_DELAY_S;
	M1_SDA_HIGH;
	IIC_DELAY_S;
	
	M1_SCL_HIGH;
	IIC_DELAY_S;
	i = M1_SDA_RD;
	IIC_DELAY_S;
	M1_SCL_LOW;
	IIC_DELAY_S;
	return i;
}

static unsigned char M1_IIC_RecvByte(void)
{
	unsigned char i=8;
	unsigned char dat=0;
	M1_SDA_HIGH;
	while(i--)
	{
		M1_SCL_HIGH;
		dat <<= 1;
		IIC_DELAY;
		if(M1_SDA_RD==1)
			dat++;
		M1_SCL_LOW;
		IIC_DELAY;
	}
	return dat;
}

//IIC通信速度为20K
unsigned int M1_IIC_Writedata(const unsigned char *pBuf, unsigned int Num)
{
	unsigned int Cnt;
	for(Cnt=0; Cnt<3; Cnt++)
	{
		if(M1_IIC_Start()) return 1;
		if(M1_IIC_TxByte(M1sensorAddr)==0)
		{
			while(Num--)
			{
				if(M1_IIC_TxByte(*pBuf++))
				{
					M1_IIC_Stop();
					return 1;
				}
			}
			M1_IIC_Stop();
			return 0;
		}
		M1_IIC_Stop( );	
		delay_us(100);	
	}
	return 1;
}

//IIC通信速度为20K
unsigned int M1_IIC_Readdata(unsigned char *pBuf, unsigned int Num)
{
	unsigned int Cnt;
	for(Cnt=0; Cnt<3; Cnt++)
	{
		if(M1_IIC_Start()) return 1;
		if(M1_IIC_TxByte(M1sensorAddr+1)==0)
		{
			while(--Num)
			{
				*pBuf++ = M1_IIC_RecvByte();
				M1_IIC_Ack(1);
			}
			*pBuf = M1_IIC_RecvByte();
			M1_IIC_Ack(0);
			M1_IIC_Stop();
			return 0;		
		}
		M1_IIC_Stop( );	
		delay_us(100);	
	}
	return 1;

}




/*************************************************
  * @函数名:Calc_CRC8 
  * @参  数:data: [输入/出] 
**			 Num: [输入/出] 
  * @Data    2022-07-06
 ************************************************/
u8 Calc_CRC8(u8 *data, u8 Num)
{
    u8 bit, byte, crc = 0xFF;

    for(byte = 0; byte < Num; byte++)
    {
        crc ^= (data[byte]);

        for(bit = 8; bit > 0; --bit)
        {
            if(crc & 0x80) crc = (crc << 1) ^ 0x31;
            else crc = (crc << 1);
        }
    }

    return crc;
}

union data_ucharTOint tdata;

unsigned char IICRecebuf[32];
unsigned int ADP800_Value;
float  ADP800_Press;
float  ADP800_Temp;
const unsigned char ADP800CMD361E[2] = {0x36, 0x1E};


//**********************************************************
//函数名称:ReadValue
//功能    :读取ADP800的数据
//参数    :无
//返回    :ADP800_Press(压差值)
//          ADP800_Temp(温度值)
//**********************************************************
unsigned char ReadValue(void)
{
    M1sensorAddr = 0x4a; //IIC器件地址

    if(M1_IIC_Writedata(ADP800CMD361E, 2)) //发送指令361E
    {
        return 1;
    }

    HAL_Delay(5);//ms
    M1_IIC_Readdata(IICRecebuf, 9);

    if(Calc_CRC8(IICRecebuf, 2) != IICRecebuf[2] || Calc_CRC8(IICRecebuf + 3, 2) != IICRecebuf[5] || Calc_CRC8(IICRecebuf + 6, 2) != IICRecebuf[8])
    {
        //错误
    }
    else
    {
        tdata.a[0] = IICRecebuf[1];
        tdata.a[1] = IICRecebuf[0];
																																																																																																													ADP800_Value = tdata.b;
        ADP800_Press = (float)tdata.b / 60;
        ADP800_Temp = (float)(IICRecebuf[3] * 0x100 + IICRecebuf[4]) / 200;
    }

    return 0;
}

h 文件代码如下

#ifndef _MYI2C_h_
#define _MYI2C_h_
#include <main.h>



void delay_2us(void);
void delay_us(unsigned int t);

extern unsigned char M1sensorAddr;

//M1:SDA--PA6 SCL--PA5
#define M1_SDA_HIGH     M1_SDA_GPIO_Port->MODER &= ~((u32)0x3<<(2*3))//设置为输入,因为默认上拉为高电平
#define M1_SDA_LOW      M1_SDA_GPIO_Port->MODER |=  ((u32)0x1<<(2*3))//设置为输出,初始化IIC时已经输出0
#define M1_SCL_HIGH     M1_SCL_GPIO_Port->MODER &= ~((u32)0x3<<(2*2))//设置为输入,因为默认上拉为高电平
#define M1_SCL_LOW      M1_SCL_GPIO_Port->MODER |=  ((u32)0x1<<(2*2))//设置为输出,初始化IIC时已经输出0
#define M1_SDA_RD       HAL_GPIO_ReadPin(M1_SDA_GPIO_Port,M1_SDA_Pin)
#define M1_SCL_RD       HAL_GPIO_ReadPin(M1_SCL_GPIO_Port,M1_SCL_Pin)

#define IIC_DELAY        delay_20us();delay_20us();
#define IIC_DELAY_S      delay_20us();

void IIC_Init(void);
unsigned int M1_IIC_Writedata(const unsigned char *pBuf, unsigned int Num);
unsigned int M1_IIC_Readdata(unsigned char *pBuf, unsigned int Num);

extern unsigned char IICRecebuf[32];
extern const unsigned char ADP800CMD361E[2];
extern unsigned char IICRecebuf[32];
extern unsigned int ADP800_Value;
extern float ADP800_Press;
extern float ADP800_Temp;

union data_ucharTOint
{
   unsigned char a[2];
   short int b;
};
extern union data_ucharTOint tdata;


u8 Calc_CRC8(u8 *data, u8 Num);
unsigned char ReadValue(void);



#endif //_MYI2C_h_

主程序如下:

int main(void)
{
  /* USER CODE BEGIN 1 */
  

  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();

	
		IIC_Init();//IIC初始化

  while (1)
  {
		
		
		    if(ReadValue() == 0) //读取ADP800的数据
        {
            WriteFourByteValueToBianLiangMemory(0x1112, (u32)(ADP800_Press*100));
            HAL_Delay(1000);//延时1秒
					
					
        }  WriteFourByteValueToBianLiangMemory(0x1112		, (u32)(ADP800_Press*100));


//		MYI2C_Delay_us(10500); //根据MCU调整为10ms延时
  }
  /* USER CODE END 3 */
}

上述代码即可实现ADP900压力差获取,用于流量计设计等领域。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值