一文讲透PWM,超级详细!!!

立芯嵌入式 2025-07-21 12:19

PWM,全称脉宽调制,听起来高大上,但其实就是通过控制信号高低电平的时间比例来实现模拟量输出。无论是搞个小风扇转速控制,还是弄个炫酷的RGB灯效,PWM都是绕不过去的坎儿。


什么是PWM的占空比?

先来说说PWM的核心概念:占空比。简单点讲,占空比就是在一个周期内,信号处于有效状态(通常是高电平)的时间占比,用百分比表示。比如一个方波,高电平和低电平时间各占一半,那占空比就是50%。这就像你家空调遥控器,50%功率时,压缩机可能一半时间在干活,一半时间在偷懒。

举个例子,假设一个信号周期是10个时间单位,其中高电平持续3个单位,那么占空比就是 (3 ÷ 10) × 100 = 30%。如果信号是低电平有效,那占空比就是70%。这在实际开发中很常见,比如控制LED亮度时,低电平有效可能意味着LED点亮的时间更长。


PWM定时器的工作原理

PWM定时器的工作方式有点像一个精准的节拍器。它的核心是一个计数器,从0开始计数,数到某个设定值(称为模数)后清零,循环往复。这个模数决定了PWM信号的周期,而另一个关键寄存器——宽度寄存器,则控制了高电平的持续时间,也就是脉宽

举个栗子,假设模数设为9,计数器会从0数到9,总共10个状态,构成一个完整的周期。宽度寄存器设为2,那么计数器从0到2时输出高电平,之后变低电平,直到计数器溢出归零,信号重新拉高。这样就形成了一个占空比为 (2 ÷ 10) × 100 = 20%的PWM信号。想改变脉宽?简单,随时改宽度寄存器的值就行,动态调整,灵活得像在调试串口波特率。

PWM定时器通常还有个预分频器,用来把主时钟频率降低,方便控制计数器的速度。多个PWM通道可以共享同一个周期计数器,但每个通道有独立的宽度寄存器,所以脉宽可以各不相同。这在多路电机控制或LED调光中特别有用。


PWM在电机控制中的使用

PWM最常见的应用场景之一就是电机控制。无论是直流电机还是舵机,PWM都能玩得转。大家应该都折腾过小四轴无人机或者机器人项目,里面电机转速的控制基本都靠PWM。

以直流电机为例,PWM信号通常送到一个电机驱动芯片,控制电机的转速和方向。比如占空比50%时,电机可能处于静止状态;占空比大于50%,电机顺时针转,扭矩跟占空比的增量成正比;小于50%,电机逆时针转。这就像你开车,油门踩得越深,车速越快,PWM的占空比就像油门踏板的深度。

再来看看舵机,这东西在机器人和航模里特别常见。普通舵机通过脉宽控制轴的角度,比如1.5毫秒的脉宽对应0度,1毫秒到-90度,2毫秒到+90度。而我最近在折腾一个连续旋转舵机,它的脉宽控制方式更直接:周期固定为20毫秒,脉宽1.5毫秒时电机不动,脉宽大于1.5毫秒逆时针加速,小于1.5毫秒顺时针加速。这就像给舵机发了个微信,告诉它该往哪边转、转多快。


用PWM调LED亮度

除了电机,PWM调光也是个经典应用。很多智能家居项目,比如调光灯或者RGB氛围灯,基本都靠PWM来实现。原理很简单:通过快速开关LED,控制点亮时间的长短,人眼感知到的就是亮度的变化,而不是闪烁。就像你在抖音刷短视频,切换快到一定程度,感觉就像连续的画面。

比如,占空比10%时,LED点亮时间短,看起来暗;占空比90%时,点亮时间长,灯就亮得晃眼。实际电路中,PWM信号通常直接接到LED驱动电路,低电平点亮LED,高电平熄灭。速度快到人眼察觉不到闪烁,效果就像模拟调光。


PWM定时器的参数设置

拿一个实际案例来说,假设我们需要控制前面提到的连续旋转舵机,需求如下:

  • PWM周期:20毫秒
  • 电机静止脉宽:1.5毫秒
  • 最大顺时针速度脉宽:1毫秒
  • 最大逆时针速度脉宽:2毫秒

硬件条件是:

  • 主时钟频率:24 MHz
  • 预分频器可选:1、2、4、8、16、32、64、128
  • 周期计数器和宽度寄存器:16位,最大65536计数

第一步:选预分频器

我们需要让计数器的输入频率(fPC)能满足20毫秒的周期。假设用60000次计数来达到20毫秒:

fPC = (0.02 ÷ 60000)^-1 = 3 MHz

主时钟是24 MHz,预分频值P = 24 MHz ÷ 3 MHz = 8。完美!用8分频,计数器模数设为59999(从0计数到59999正好60000次),就能得到20毫秒的周期。此时计数器的时钟周期是1 ÷ 3 MHz ≈ 0.333微秒,这也是PWM信号的时间分辨率

第二步:算脉宽寄存器的值

脉宽时间tW = W × 0.333微秒,W是宽度寄存器的值。计算如下:

  • 电机静止:1.5毫秒 ÷ 0.333微秒 ≈ 4500
  • 最大顺时针速度:1毫秒 ÷ 0.333微秒 ≈ 3000
  • 最大逆时针速度:2毫秒 ÷ 0.333微秒 ≈ 6000

所以,宽度寄存器值从3000变到6000,就能实现从全速顺时针到全速逆时针的控制。实际开发中,舵机精度可能有点飘,建议用示波器测一下实际脉宽,再微调这些值,就像调收音机频率,得找准那个点。

第三步:检查分辨率

从静止(4500)到全速(3000或6000),有1500个计数步进,分辨率是1 ÷ 1500 ≈ 0.067%。这对于低端舵机来说已经够细腻了,相当于你开车时油门能精确到0.1%的力度,够用了吧!


中断:让PWM更精准

有时候,PWM信号和软件逻辑需要紧密配合,这时候中断就派上用场了。PWM定时器通常支持两种中断:计数器溢出(周期结束)和脉宽匹配(脉宽结束)。如果是多通道PWM,中断服务函数得去读寄存器,搞清楚是哪个通道触发了中断。这就像你家有好几个门铃,得看是哪个门在响。

用中断可以实现精准的动态调整,比如在电机控制中,实时更新脉宽以响应传感器数据。


声明:内容取材于网络,仅代表作者观点,如有内容违规问题,请联系处理。 
Copyright © 2025 成都区角科技有限公司
蜀ICP备2025143415号-1
  
川公网安备51015602001305号