第 3 章:PWM 舵机与 ESC 控制
3.1 知识要点
- 标准 RC PWM 协议:50 Hz 周期,1000–2000 µs 脉宽
- LEDC 14-bit 分辨率下的占空比计算
- ESC 上电解锁流程(中立位保持 2 秒)
- 双通道同步配置(油门 + 转向)
3.2 课程内容
电调(ESC)和舵机均使用标准 RC PWM 协议控制:50 Hz 重复频率,脉宽 1000 µs 对应最小值,1500 µs 对应中立,2000 µs 对应最大值。OSRCORE 使用 LEDC TIMER0 的两个通道分别驱动 GPIO1(油门)和 GPIO2(转向)。
3.3 基础学习
RC PWM 时序
周期 = 20 ms (50 Hz)
脉宽范围:1000 µs(最小)~ 2000 µs(最大)
中立位:1500 µs14-bit 分辨率下的占空比计算
APB 时钟 80 MHz,14-bit 分辨率(16384 步):
period_ticks = 80_000_000 / 50 = 1_600_000
1 µs = 80 ticks
duty = pulse_us × 80例:1500 µs → duty = 120000;2000 µs → duty = 160000。
宏定义:#define US_TO_DUTY(us) ((us) * 80)
ESC 解锁流程
大多数 ESC 上电后需要检测到中立位信号(1500 µs)才会解锁,通常需要保持 1–3 秒。未解锁的 ESC 不响应油门指令。
3.4 程序学习
定时器与双通道初始化:
c
ledc_timer_config_t timer = {
.speed_mode = LEDC_LOW_SPEED_MODE,
.duty_resolution = LEDC_TIMER_14_BIT,
.timer_num = LEDC_TIMER_0,
.freq_hz = 50,
.clk_cfg = LEDC_AUTO_CLK,
};
ledc_timer_config(&timer);
ledc_channel_config_t ch_throttle = {
.gpio_num = 1, .channel = LEDC_CHANNEL_0,
.timer_sel = LEDC_TIMER_0, .duty = US_TO_DUTY(1500),
};
ledc_channel_config(&ch_throttle);
ledc_channel_config_t ch_steering = {
.gpio_num = 2, .channel = LEDC_CHANNEL_1,
.timer_sel = LEDC_TIMER_0, .duty = US_TO_DUTY(1500),
};
ledc_channel_config(&ch_steering);设置脉宽与 ESC 解锁:
c
static void set_pulse(ledc_channel_t ch, uint32_t pulse_us)
{
ledc_set_duty(LEDC_LOW_SPEED_MODE, ch, US_TO_DUTY(pulse_us));
ledc_update_duty(LEDC_LOW_SPEED_MODE, ch);
}
// ESC 解锁:中立位保持 2 秒
set_pulse(CH_THROTTLE, 1500);
set_pulse(CH_STEERING, 1500);
vTaskDelay(pdMS_TO_TICKS(2000));3.5 课程总结
本章掌握了 RC PWM 协议的原理和 LEDC 14-bit 精度配置,实现了 ESC 解锁和舵机扫描。US_TO_DUTY() 宏将物理脉宽直接映射为寄存器值,是后续 PID 控制输出的基础接口。