共计 1930 个字符,预计需要花费 5 分钟才能阅读完成。
核心概念
AB 相正交信号特性
AB 相编码器通过两路相位差 90°的方波信号(A 相和 B 相)输出位置信息。这种设计允许我们通过检测两路信号的相对相位来判断旋转方向:
- A 相领先 B 相 90°时,表示正转
- B 相领先 A 相 90°时,表示反转
编码器类型对比
光电式编码器(如 CUI AMT102):
– 分辨率高(可达 5000PPR)
– 对污染敏感
– 成本较高
磁电式编码器(如 AS5048A):
– 抗污染能力强
– 温度稳定性好
– 分辨率通常较低(12 位绝对值输出)
4 倍频计数原理
通过同时在 A 相和 B 相的上升沿和下降沿触发计数,可以将原始分辨率提高 4 倍。Z 相(零位信号)每转一圈产生一个脉冲,用于绝对位置校准。

痛点分析
信号抖动问题
长线传输时容易引入噪声,导致信号边沿抖动。使用普通示波器可以观察到明显的信号振荡:
计数丢失风险
高速旋转时,如果 MCU 中断响应不够快,可能会错过脉冲。测试数据表明:
- STM32H7 在 400MHz 主频下最大跟踪转速约 5000RPM
- ESP32 在 240MHz 下仅能稳定跟踪约 2000RPM
技术方案
硬件设计
推荐使用 RS422 差分传输,典型电路包括:
- SN75172 差分驱动器
- 120Ω 终端电阻
- 双绞屏蔽电缆
软件实现
中断消抖处理
// STM32 HAL 库示例
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin) {
static uint32_t last_time = 0;
uint32_t now = HAL_GetTick();
// 10ms 消抖时间
if((now - last_time) > 10) {if(GPIO_Pin == ENCODER_A_Pin) {// 处理 A 相跳变}
last_time = now;
}
}
定时器正交解码模式
// STM32 编码器模式配置
TIM_Encoder_InitTypeDef sConfig = {0};
sConfig.EncoderMode = TIM_ENCODERMODE_TI12;
sConfig.IC1Polarity = TIM_ICPOLARITY_RISING;
sConfig.IC1Selection = TIM_ICSELECTION_DIRECTTI;
sConfig.IC1Prescaler = TIM_ICPSC_DIV1;
sConfig.IC1Filter = 6; // 适当滤波
// 类似配置 IC2...
HAL_TIM_Encoder_Init(&htim3, &sConfig);
PID 控制实现
// 带抗积分饱和的 PID
typedef struct {
float Kp, Ki, Kd;
float integral;
float prev_error;
float out_max, out_min;
} PID_Handle;
float PID_Update(PID_Handle *h, float error, float dt) {
float p_term = h->Kp * error;
h->integral += error * dt;
// 抗积分饱和
if(h->integral > h->out_max) h->integral = h->out_max;
else if(h->integral < h->out_min) h->integral = h->out_min;
float d_term = h->Kd * (error - h->prev_error) / dt;
h->prev_error = error;
return p_term + h->Ki * h->integral + d_term;
}
避坑指南
中断服务优化
- 避免在中断中进行浮点运算(Cortex-M4/M7 除外)
- 使用
__attribute__((section(".ramfunc")))将关键代码放在 RAM 中执行
线缆长度限制
| 波特率 | 最大线缆长度 |
|---|---|
| 1Mbps | 10m |
| 500kbps | 20m |
| 100kbps | 50m |
卡尔曼滤波应用
# Python 简化实现
def kalman_filter(z, x_est, p_est, q=0.1, r=0.1):
# 预测
x_pred = x_est
p_pred = p_est + q
# 更新
k = p_pred / (p_pred + r)
x_est = x_pred + k * (z - x_pred)
p_est = (1 - k) * p_pred
return x_est, p_est
性能验证
测试数据
| 转速(RPM) | 平均误差(脉冲) | 最大误差(脉冲) |
|---|---|---|
| 500 | 0.2 | 1 |
| 1500 | 0.8 | 3 |
| 3000 | 2.1 | 7 |
逻辑分析仪捕获
进阶思考
- 如何利用电池供电的 FRAM 实现多圈绝对位置记录?
- 在 CAN 总线系统中,怎样实现多个编码器的同步采样?
- 当需要亚微米级定位时,有哪些提升分辨率的方法?
通过本文介绍的技术方案,我们成功实现了 AB 相编码器在工业自动化设备中的高精度位置控制。实际项目中,建议根据具体需求选择合适的硬件方案,并通过充分的测试验证系统稳定性。
正文完
