4-20mA校准电路设计思路分享
目录
硬件部分
声明:该段引用自电子科技大学仿生青的硬件设计,本人未验证,仅作为参考保存资料以便后续研究,如有需要完善,感谢原作者及后续的完善者,谢谢
该系统采用ADS8864和STM32F302C8T6,使用单个24V直流电源处理4 mA至20 mA的输入信号。室温校准前的总误差为±4 LSB,即室温(27℃)下能够达到±0.06%FSR的误差。
该系统中使用的传感器是Sick的DT35,但输入端子可以修改以满足各种不同的工业传感器接口(只要是4-20mA便可)。
电路说明

该电路由电平转换电路、输入电流-电压转换器、ADC级和输出数字信号处理级组成。电阻 R 25 R_{25}R25 将4 mA至20 mA的输入信号转换为电压。当 R 25 = 120 Ω R_{25} = 120 \ \OmegaR25=120 Ω 且输入电流在4至20 mA之间时,电平转换电路的输入电压范围为0.48 V至2.4 V。二极管D1用于限制电压以防止输入为电压而不是电流的情况,二极管D2用于输入电流源防反接。
U5A运算放大器是双AD8606的其中一个,其转换电平并衰减 R 25 R_{25}R25 两端的电压。运算放大器的输出范围为0.1 V至2.4 V,具有100 mV的余量以确保线性,与ADC的输入范围(0 V至2.5 V)相匹配。使用剩下的一个AD1582来跟随缓冲参考电压(VREF=2.5 V)。
最小输出电压(范围下限)设置为100mV,以提供安全余量,同时考虑到元件的公差。为了在ADC输入端为正摆幅提供100 mV的余量,输出范围的最大值限制为2.4 V。因此,运算放大器的标称输出电压范围为0.1 V至2.4 V。AD8606(U5B)的后半部分用于缓冲ADS8864(U6)ADC的2.5 V参考电压。
由于其低偏置电压(最大值65μV)、低偏置电流(最大值1 pA)和低噪声(最大值12 nV/√Hz),选择AD8606用于此应用。使用3.3V电源时,功耗仅为9.2mW。此外,也可以使用其他运算放大器。替代品可以是OPA2320、OPA2376和其他选项,如上图所示。
运算放大器输出级之后是单极点RC滤波器(R21/C26),以降低带外噪声。RC滤波器的截止频率设置为339kHz。为了应对低频工业噪声,可以进一步降低滤波器截止频率,即级联额外的滤波器(R20/C24)。在这种情况下,由于信号带宽较窄,ADS8864的采样率可以降低更大范围。
其在100kSPS下0.65mW的超低功率使得ADS8864(U6)16位400kSPS SAR ADC成为本次设计的选择,同时SPI与其高速串行接口兼容。受STM32F302C8T6处理速度受限,奈奎斯特频率设置为66.6KHz。
电路设计


而且,由于电路的主要误差来源于电阻,因此必须进行增益和偏移校准,以尽可能消除标准值与之间理论值的误差以及电阻公差引起的误差。
两点校准
为了获得更高的性能,需要调整电路增益。可选择两点校准。
首先,向输入端输送4 mA以开始两点校准,ADC输出代码记为 C o d e 1 Code_1Code1。在提供20mA输入电流后,ADC输出代码被记录为 C o d e 2 Code_2Code2。增益系数为:
剩下的电路

CAN用于通信,光电耦合器用于检测DT35设置的距离阈值。
照片
2 4~20mA输入校准硬件电路设计详解
在4~20mA电流采集系统中,增加专用的校准硬件电路是实现高精度、高稳定性和现场可维护性的关键。校准电路的核心目标是提供精确、可重复的基准电流源,用于系统两点校准,并消除电阻温漂、运放偏移、ADC非线性等误差源的影响。
1. 校准电路的架构与设计原则
一个完整的4~20mA输入校准硬件系统通常包含三个主要部分:精密基准电流源、多路切换网络和校准控制逻辑。其设计需遵循以下原则:
| 设计原则 | 具体实现要求 | 参考来源 |
|---|---|---|
| 精度优先 | 基准源精度需高于系统目标精度3-5倍 | |
| 温度稳定性 | 关键元件温漂 ≤25 ppm/°C | |
| 隔离保护 | 校准电路与主信号通道光耦/继电器隔离 | |
| 低噪声设计 | 电源去耦、PCB屏蔽层、Guard Ring布局 |
2. 核心电路模块设计
2.1 精密可编程电流源电路
采用数模转换器(DAC)+ 电压-电流(V-I)转换的方案,可生成4.000mA和20.000mA的精确校准电流。
// 基于STM32 DAC和运放的精密电流源控制代码
#include "stm32f3xx_hal.h"
// 定义DAC输出对应电流值(以16位DAC为例,参考电压Vref=2.5V)
#define DAC_CODE_4MA 3277 // 对应4.000mA输出
#define DAC_CODE_20MA 16384 // 对应20.000mA输出
#define DAC_FULL_SCALE 65535 // 16位DAC满量程
void CalibrationCurrentSource_SetOutput(float target_mA) {
uint16_t dac_code;
float voltage;
// 计算所需输出电压:Vout = I_target * R_set * (1 + Rf/Rg)
// 假设:R_set=100Ω,运放增益=1,则Vout(mV) = I_target(mA) * 100
voltage = target_mA * 0.1f; // 转换为电压值(V)
// 转换为DAC码值
dac_code = (uint16_t)((voltage / 2.5f) * DAC_FULL_SCALE);
// 设置DAC输出
HAL_DAC_SetValue(&hdac1, DAC_CHANNEL_1, DAC_ALIGN_12B_R, dac_code);
HAL_DAC_Start(&hdac1, DAC_CHANNEL_1);
}
硬件电路实现(基于运放的Howland电流泵):
// 精密V-I转换电路(Howland电流源)
//
// R1 R2
// V_DAC ──┬──/\/\/\──┬──┐
// │ 10kΩ │ │
// │ │ │
// └──/\/\/\──┘ │
// R3 10kΩ │ I_out
// │ 4-20mA
// R4 R5│ │
// GND ────/\/\/\────/\/\/\─┘
// 10kΩ R_set
// 100Ω
// │
// GND
//
// 计算公式:I_out = V_DAC / R_set * (R2/R1)
// 当R1=R2=R3=R4时,I_out = V_DAC / R_set
关键元件选型表:
| 元件 | 型号/参数 | 关键特性 | 作用 |
|---|---|---|---|
| DAC芯片 | AD5689R | 16位,±2LSB INL,2.5V基准 | 提供精密电压基准 |
| 运放 | OPA2188 | 低偏移:25μV max,低噪声:5.5nV/√Hz | V-I转换核心 |
| 基准电阻 | Vishay PTF56 | 100Ω,±0.01%,5ppm/°C | 决定电流精度 |
| 多路开关 | ADG1419 | 低导通电阻:2.5Ω,低漏电流:100pA | 信号路由切换 |
2.2 多路切换与隔离电路
校准电路需能在正常工作模式和校准模式间无缝切换,确保校准过程不影响正常测量。
// 校准通道切换控制逻辑
typedef enum {
MODE_NORMAL = 0, // 正常测量模式:传感器→ADC
MODE_CAL_4MA, // 校准模式:4mA基准源→ADC
MODE_CAL_20MA, // 校准模式:20mA基准源→ADC
MODE_SELF_TEST // 自检模式:内部短接
} OperationMode;
void SwitchCalibrationMode(OperationMode mode) {
switch(mode) {
case MODE_NORMAL:
// 闭合传感器通道,断开校准源
HAL_GPIO_WritePin(CAL_RELAY_GPIO_Port, CAL_RELAY_Pin, GPIO_PIN_RESET);
HAL_GPIO_WritePin(SENSOR_RELAY_GPIO_Port, SENSOR_RELAY_Pin, GPIO_PIN_SET);
break;
case MODE_CAL_4MA:
// 断开传感器,连接4mA校准源
HAL_GPIO_WritePin(SENSOR_RELAY_GPIO_Port, SENSOR_RELAY_Pin, GPIO_PIN_RESET);
HAL_GPIO_WritePin(CAL_RELAY_GPIO_Port, CAL_RELAY_Pin, GPIO_PIN_SET);
CalibrationCurrentSource_SetOutput(4.000f); // 输出4.000mA
break;
case MODE_CAL_20MA:
// 断开传感器,连接20mA校准源
HAL_GPIO_WritePin(SENSOR_RELAY_GPIO_Port, SENSOR_RELAY_Pin, GPIO_PIN_RESET);
HAL_GPIO_WritePin(CAL_RELAY_GPIO_Port, CAL_RELAY_Pin, GPIO_PIN_SET);
CalibrationCurrentSource_SetOutput(20.000f); // 输出20.000mA
break;
}
HAL_Delay(50); // 等待继电器稳定
}
隔离保护设计要点:
- 光耦隔离:控制信号使用TLP281-4光耦,隔离电压5000Vrms
- 继电器选择:Omron G6K-2F低热电势继电器,接触电阻<100mΩ
- TVS保护:在输入端口并联SMBJ24A,防止过压冲击
2.3 采样电阻网络与ADC接口
校准电路的采样电阻需与主测量通道完全一致,以确保校准的有效性。
# 采样电阻网络配置与误差分析
import numpy as np
class SamplingResistorNetwork:
def __init__(self):
# 主测量通道电阻(与校准通道一致)
self.R_main = 120.0 # 单位:Ω
self.temp_coeff = 25e-6 # 25 ppm/°C
# 校准通道电阻(需与R_main匹配)
self.R_cal = 120.0
self.cal_mismatch = 0.001 # 0.1%的失配误差
def calculate_voltage(self, current_ma, temperature=25.0):
"""计算采样电阻两端电压,考虑温漂和失配"""
# 电阻值随温度变化
R_temp = self.R_main * (1 + self.temp_coeff * (temperature - 25.0))
# 校准通道与主通道的失配
R_cal_temp = self.R_cal * (1 + self.temp_coeff * (temperature - 25.0))
mismatch_factor = 1 + self.cal_mismatch
# 电压计算
voltage_main = current_ma * 1e-3 * R_temp # 主通道电压
voltage_cal = current_ma * 1e-3 * R_cal_temp * mismatch_factor # 校准通道电压
return {
'V_main': voltage_main,
'V_cal': voltage_cal,
'error_percent': abs(voltage_cal - voltage_main) / voltage_main * 100
}
# 示例:分析4mA和20mA点的误差
network = SamplingResistorNetwork()
for current in [4.0, 20.0]:
result = network.calculate_voltage(current, temperature=60.0) # 高温环境
print(f"{current}mA @60°C: V_main={result['V_main']:.3f}V, "
f"误差={result['error_percent']:.4f}%")
3. 完整校准电路原理图设计
以下是完整的4~20mA输入校准硬件电路模块:
// 4~20mA校准电路完整架构
//
// ┌─────────────────────────────────────────────────────────┐
// │ 校准控制模块 │
// │ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
// │ │ 精密基准 │ │ 16位DAC │ │ STM32F3 │ │
// │ │ 电压源 │──▶ AD5689R │◀─▶ 控制器 │ │
// │ │ ADR4540 │ │ │ │ │ │
// │ └─────────────┘ └─────────────┘ └─────────────┘ │
// │ │ │ │ │
// └──────────┼─────────────────────┼──────────────┼────────┘
// │ │ │
// ▼ ▼ ▼
// ┌─────────────────────────────────────────────────────────┐
// │ V-I转换与切换模块 │
// │ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
// │ │ Howland │ │ 多路模拟 │ │ 隔离 │ │
// │ │ 电流泵 │──▶ 开关 │──▶ 继电器 │ │
// │ │ OPA2188 │ │ ADG1419 │ │ G6K-2F │ │
// │ └─────────────┘ └─────────────┘ └─────────────┘ │
// │ │ │ │ │
// └──────────┼─────────────────────┼──────────────┼────────┘
// │ │ │
// ▼ ▼ ▼
// ┌─────────────────────────────────────────────────────────┐
// │ 采样与保护模块 │
// │ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
// │ │ 采样电阻 │ │ RC滤波 │ │ 保护电路 │ │
// │ │ 120Ω±0.1% │──▶ 339kHz │──▶ TVS+二极管 │ │
// │ │ PTF56 │ │ R21/C26 │ │ SMBJ24A │ │
// │ └─────────────┘ └─────────────┘ └─────────────┘ │
// │ │ │ │
// └──────────┼────────────────────────────────────┼────────┘
// │ │
// ▼ ▼
// ┌──────────┐ ┌──────────┐
// │ 主ADC │ │外部传感器│
// │ ADS8864 │ │ 输入 │
// └──────────┘ └──────────┘
4. PCB布局与抗干扰设计
为确保校准精度,PCB布局需特别注意:
| 布局区域 | 设计要点 | 实施方法 |
|---|---|---|
| 模拟区域 | 严格与数字区域分离 | 使用分地技术,AGND与DGND单点连接 |
| 电流路径 | 短而粗的走线 | 线宽≥20mil,避免90°拐角 |
| 基准源 | 远离发热元件 | 距离MCU、LDO等≥10mm |
| 屏蔽 | 关键信号屏蔽 | 采样电阻周围加Guard Ring,接模拟地 |
| 去耦 | 每个IC电源引脚 | 0.1μF陶瓷电容 + 10μF钽电容并联 |
Guard Ring设计示例:
# PCB布局的Guard Ring计算
def calculate_guard_ring_parameters(signal_freq=100e3, pcb_thickness=1.6):
"""计算保护环参数"""
# 介电常数(FR4)
epsilon_r = 4.5
# 保护环到信号线距离(经验公式)
# 对于100kHz信号,保护环宽度应≥2倍线宽
signal_width = 0.3 # 信号线宽0.3mm
guard_width = 2 * signal_width # 保护环宽度0.6mm
# 保护环间隙(防止电弧)
gap = 0.2 # 0.2mm间隙
# 电容耦合计算(保护环与信号线之间)
# 平行板电容公式:C = ε₀ε_r * A / d
area = guard_width * 10e-3 # 假设长度10mm
distance = gap
epsilon_0 = 8.854e-12
capacitance = epsilon_0 * epsilon_r * area / (distance * 1e-3)
return {
'guard_width_mm': guard_width,
'gap_mm': gap,
'capacitance_pf': capacitance * 1e12,
'recommendation': '保护环应完全包围敏感模拟信号,并通过过孔连接到模拟地平面'
}
5. 校准流程与精度验证
完整的硬件校准应包含以下步骤:
// 基于硬件的自动校准流程
typedef struct {
uint16_t adc_code_4ma;
uint16_t adc_code_20ma;
float gain_factor;
float offset;
uint8_t calibration_status;
} SystemCalibration;
SystemCalibration PerformAutoCalibration(void) {
SystemCalibration cal = {0};
// 步骤1:切换到4mA校准模式
SwitchCalibrationMode(MODE_CAL_4MA);
HAL_Delay(100); // 等待稳定
// 采集4mA点数据(多次平均)
cal.adc_code_4ma = ADC_GetAverageValue(100); // 100次平均
// 步骤2:切换到20mA校准模式
SwitchCalibrationMode(MODE_CAL_20MA);
HAL_Delay(100);
// 采集20mA点数据
cal.adc_code_20ma = ADC_GetAverageValue(100);
// 步骤3:计算校准参数
if (cal.adc_code_20ma > cal.adc_code_4ma) {
cal.gain_factor = 16.0f / (cal.adc_code_20ma - cal.adc_code_4ma);
cal.offset = 4.0f - cal.gain_factor * cal.adc_code_4ma;
cal.calibration_status = 1; // 校准成功
// 保存到EEPROM
EEPROM_SaveCalibration(&cal);
} else {
cal.calibration_status = 0; // 校准失败
}
// 步骤4:切换回正常工作模式
SwitchCalibrationMode(MODE_NORMAL);
return cal;
}
// 精度验证函数
float VerifyCalibrationAccuracy(SystemCalibration cal) {
float max_error = 0;
float test_points[] = {4.0, 8.0, 12.0, 16.0, 20.0}; // 测试点
for (int i = 0; i < 5; i++) {
// 设置校准源输出测试电流
CalibrationCurrentSource_SetOutput(test_points[i]);
SwitchCalibrationMode(MODE_CAL_4MA + i); // 切换到对应模式
HAL_Delay(50);
uint16_t adc_code = ADC_GetAverageValue(50);
// 使用校准参数计算电流
float calculated_ma = cal.offset + cal.gain_factor * adc_code;
float error = fabs(calculated_ma - test_points[i]);
if (error > max_error) {
max_error = error;
}
}
// 返回最大绝对误差(mA)
return max_error;
}
6. 温度补偿与长期稳定性
为应对环境温度变化,校准电路需集成温度传感器和补偿算法:
// 温度补偿实现
#include "max31865.h" // PT100温度传感器驱动
typedef struct {
float gain_temp_coeff; // 增益温度系数(%/°C)
float offset_temp_coeff; // 偏移温度系数(mA/°C)
float ref_temp; // 参考温度(通常25°C)
} TemperatureCompensation;
float ApplyTemperatureCompensation(float raw_current, float temperature,
TemperatureCompensation *comp) {
// 计算温度引起的增益变化
float temp_delta = temperature - comp->ref_temp;
----
## 参考来源
- [4-20 mA 电流采集系统设计](https://blog.csdn.net/ChingHsien/article/details/128501820)
- [嵌入式系统中的信号链设计:PWM如何驱动4~20mA工业标准接口](https://blog.csdn.net/agile9scrum/article/details/156172471)
- [4-20mA采样:电路设计与软件实现](https://blog.csdn.net/si15166622538/article/details/155073166)
- [GP8302 I2C转4-20mA电流输出模块原理图设计,已量产](https://blog.csdn.net/m0_38106923/article/details/157554910)
- [硬件电路设计采集电路](https://blog.csdn.net/qq_37999850/article/details/153789544)
- [4-20mA传感器信号处理指南:从采样电阻选型到STM32ADC校准全流程](https://blog.csdn.net/weixin_30369041/article/details/159406052)更多推荐


所有评论(0)