0-5V 高精度输出

转载

1、需求分析

在很多信号采集系统中,都有标准化输入接口,工业上常用的有0-5V、4-20mA、0-10V等,虽然比较简单,但如何搭建高精度的信号输出电路成为制约传感器精度的一个瓶颈。对于刚入门硬件设计的小白而言,采用集成化的芯片完成电压输出电路不仅能够保证电路可靠性,而且可以简化设计流程,缩短开发周期。
有的单片机会自带DAC模块,但是精度并不太高,而且输出范围有限,无法满足输出需求。因此需要额外的DAC电路,完成模拟量输出。模拟输出电路包括两个部分:电压基准和数模转化电路。电压基准为数模转化电路提供标准的电压,为模-数转化提供参考,数模转化则能将所需的数字量转化为模拟量。
2、电压基准

电压基准的作用是为DAC提供参考电压。下图为一个DAC的典型框图,由下图可知,如果没有一个稳定精确的电压基准,即使采用精度再高的DAC,也无法输出所需要的模拟量。
一个DAC的内部结构框图
此处采用REF3450作为基准电路芯片。REF34xx 器件是低温漂(6 ppm/°C)、低功耗、高精度 CMOS 电压基准,具有±0.05% 初始精度、低运行电流以及小于 95μA 的功耗。该器件还提供 3.8μVp-p/V 的极低输出噪声,这使
得它在用于噪声关键型系统中的高分辨率数据转换器时能够保持较高的信号完整性。REF3450的一个典型应用电路如下图所示:
REF3450参考电路
值得注意的是,该芯片要求的输入电压需要比输出参考电压略高,在电路设计的时候要尤其注意。
输入电压范围
3、模-数转换电路

DAC采用TI的DAC8751作为应用芯片。DAC8751是一个低功耗、16位电压输出数模转换器。其工作电流为160uA@5V,输入电压为2.7-5.5V,偏置误差为±1mV,最高输出误差为±3mV。其典型应用如下图所示:
DAC模块
此处也需要注意VREF和VDD之间的关系,由数据手册可知,输入电压范围为-0.3V - +6V,VREF范围为0-VDD,输出电压范围为0-VREF。因此要确保供电电压高于参考电压,否则在输出的时候达不到预期的输出值。
4、模数转化驱动代码

完成硬件电路设计后还需要写代码对其进行驱动。我这里用的是STM32F1系列单片机作为控制其输出的MCU。开发环境为STM32CuBeIDE1.1.0。当然,在开发的过程中参考了https://download.csdn.net/download/bluesky0801/12003797?utm_source=iteye

原代码中采用的是STM32自带的硬件IIC作为控制信号,但我之前在做别的项目的过程中一直采用的是模拟IIC,而且运行稳定,所以对其进行了一定更改,ADC控制代码如下:

/***********************************************************
功能:写一个字节的数据到I2C器件中
DAC8571_ADDRESS_WRITE:I2C器件地址0x98
dat:传进来的16bit数据 高8位+低8位(需进行转换的D值)
control_byte:控制字节 control byte ---为0x10
NumByteToWrite:需要写的数据的字节数---取2个字节(16bit的数据拆分为2个8bit的数据)
***********************************************************/
void ADC_I2C_Write(uint16_t dat, uint8_t control_byte)
{
  uint8_t temp1,temp2;
  temp1=(uint8_t)((dat&0xff00)>>8);
  temp2=(uint8_t)(dat&0x00ff);

  /* Send STRAT condition */
  IIC_Start();

  /* Test on EV5 and clear it */

  /* Send EEPROM address for write */
  IIC_Send_Byte(DAC8571_ADDRESS_WRITE);         //发送写器件指令
 
  /* Test on EV6 and clear it */
  IIC_Wait_Ack();
      
  /* Send the DAC8571 control byte */
  IIC_Send_Byte(control_byte);
 
  /* Test on EV8 and clear it */
  IIC_Wait_Ack();

//  I2C_SendData(I2C1, temp1);  /*send data MSB*/
  IIC_Send_Byte(temp1);
  IIC_Wait_Ack();
  IIC_Send_Byte(temp2);
  IIC_Wait_Ack();

  /* Send STOP condition */
  IIC_Stop();
}

总结

至此,在单片机中设计高精度模拟量输出的功能基本完成。该功能并不复杂,但还是有一些需要注意的点,比如芯片各电压之间的关系等。实验结果表明该电路工作稳定,精确度高,我用六位半的万用表测试,基本上只有最后一位会稍有跳动,达到了预期效果。
————————————————
版权声明:本文为CSDN博主「zhoujiesxhsjy」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/u013096454/article/details/107149522/

posted @ 2021-05-31 23:35  braveheart007  阅读(671)  评论(0编辑  收藏  举报