关于PWM脉冲宽度调制的点滴总结


基本原理

PWM的全称是脉冲宽度调制Pulse-width modulation),是通过将有效的电信号分散成离散形式从而来降低电信号所传递的平均功率的一种方式;

所以根据面积等效法则,可以通过对改变脉冲的时间宽度,来等效的获得所需要合成的相应幅值频率的波形;

具体如下图所示;

由上图可知,脉冲宽度调制使用一个脉冲宽度会被调制的方波,并且波型的平均值会有所变化。

如果我们考虑一个周期为 T {\displaystyle T} T 的脉冲波 f ( t ) {\displaystyle f(t)} f(t) ,低值 y min {\displaystyle y_{\text{min}}} ymin,高值为 y max {\displaystyle y_{\text{max}}} ymax ,跟占空比 D D D(duty cycle),此波的平均值为:
y ˉ = 1 T ∫ 0 T f ( t )   d t {\displaystyle {\bar {y}}={\frac {1}{T}}\int _{0}^{T}f(t)\,dt} yˉ=T10Tf(t)dt
f ( t ) {\displaystyle f(t)} f(t) 是一个脉冲波,它的值在 0 < t < D ⋅ T {\displaystyle 0<t<D\cdot T} 0<t<DT y max {\displaystyle y_{\text{max}}} ymax 而在 D ⋅ T < t < T {\displaystyle D\cdot T<t<T} DT<t<T y min {\displaystyle y_{\text{min}}} ymin

上式的描述可以变为:
y ˉ = 1 T ( ∫ 0 D T y max   d t + ∫ D T T y min   d t ) = 1 T ( D ⋅ T ⋅ y max + T ( 1 − D ) y min ) = D ⋅ y max + ( 1 − D ) y min {\displaystyle {\begin{aligned}{\bar {y}}&={\frac {1}{T}}\left(\int _{0}^{DT}y_{\text{max}}\,dt+\int _{DT}^{T}y_{\text{min}}\,dt\right)\\&={\frac {1}{T}}\left(D\cdot T\cdot y_{\text{max}}+T\left(1-D\right)y_{\text{min}}\right)\\&=D\cdot y_{\text{max}}+\left(1-D\right)y_{\text{min}}\end{aligned}}} yˉ=T1(0DTymaxdt+DTTymindt)=T1(DTymax+T(1D)ymin)=Dymax+(1D)ymin
以上公式可以在很多状况下被简化,当 y min = 0 {\displaystyle y_{\text{min}}=0} ymin=0 y ˉ = D ⋅ y max {\displaystyle {\bar {y}}=D\cdot y_{\text{max}}} yˉ=Dymax

从这里可以看出,波型的平均值非常明显地直接与占空比 D D D 有关。

占空比

图中存在三种占空比状态,25%50%75%占空比状态,不难发现,假设占空比为D,则满足:

D = T o n T D = \cfrac{T_{on}}{T} D=TTon

其中 T T T是PWM的周期,通常和载波的周期相同;

PWM是如何实现?

PWM实现的原理是通过锯齿波/三角波(载波)所需要合成的波形(调制波)进行比较,然后确定PWM所需要输出的极性,通常是ON或者是OFF,因为一般都是作用到开关元器件上;如下图所示;

振荡器和比较器

振荡器输出的锯齿波和参考值 V T H V_{TH} VTH 进行比较,然后就可以输出PWM波形了;

matlabsimulink中搭建了一下仿真,具体如下图所示;

simulink

最终输出波形如下:

50%占空比

这里简单说明一下:

  • 锯齿波(图中橙色波形)最大为10,然后我希望输出平均为5的波形(图1中红色的水平直线);
  • 那么通过比较,当锯齿波小于5时;PWM输出低电平,即为OFF
  • 当锯齿波大于5时,PWM输出高电平,即为ON

所以再换一个思路,如果我希望输出一个电压逐渐升高的波形呢,该如何设计呢?

其实很简单,只要把需要调制的波形设置为斜坡输出的波形就可以了,具体如下图所示;

占空比逐渐增大

可以看到,最终占空比逐渐从0%增大到100%

然后我们继续想,能不能调制出其他的波形,比如调制一个正弦波sin wave,那也就是我们常说的SPWM,其实是可以的,具体如下图所示;

SPWM

分类

参考STM32中PWM的配置,根据载波波形的形状,假设三角波最大值是10,那么它的变化过程可能存在以下两种情况:

  • 完整周期包括两个过程,先递增,再递减: 0 → 增 加 5 → 增 加 10 → 减 少 5 → 减 少 0 0\xrightarrow{增加}5\xrightarrow{增加}10\xrightarrow{减少}5\xrightarrow{减少}0 0 5 10 5 0,这种也叫中央对齐PWM;
  • 完整周期只有递增过程: 0 → 增 加 5 → 增 加 10 0\xrightarrow{增加}5\xrightarrow{增加}10 0 5 10

中央对齐PWM

脉冲波的中心将会被固定在时间窗格的中心,同时脉冲波的两边可以移动,使得波的宽度被延伸或压缩,具体如下图所示;

中央对齐PWM

另一种类型的PWM脉冲波形如下图所示;

程序实现

现在的MCU大部分都自带硬件PWM发生器,即配置好相应的寄存器,就能直接产生PWM,下面的例子基于NUCLEO-F767ZI,通过cubemx配置了三路PWM输出,然后实现了呼吸灯的效果;

int main(void)
{

	HAL_Init();

	MX_GPIO_Init();
	MX_TIM4_Init();
	MX_TIM3_Init();
	MX_TIM12_Init();

	int32_t time_stamp = 0;
	int32_t time_stamp_old = 0;
	int32_t ccr_val = 0;
	uint8_t add_flag = 1;
	HAL_TIM_PWM_Start(&htim4, TIM_CHANNEL_2);
	HAL_TIM_PWM_Start(&htim12, TIM_CHANNEL_1);
	HAL_TIM_PWM_Start(&htim3, TIM_CHANNEL_3);	
	while (1)
	{
		time_stamp = HAL_GetTick();
		if(time_stamp - time_stamp_old > 5){
		time_stamp_old = time_stamp;
		if(add_flag){
			ccr_val+=25;
			if(ccr_val >= 0xFFFF){
			ccr_val = 0xFFFF;
			add_flag = 0;
		}
		}else{
			ccr_val-=25;
			if(ccr_val <= 0){
				add_flag = 1;
				ccr_val = 0;
			}
		}
		TIM4->CCR2 = ccr_val;
		TIM12->CCR1 = ccr_val;
		TIM3->CCR3 = ccr_val;
		}
	}
}

整体效果如下:

呼吸灯

通过示波器看其中的一路PWM输出的占空比也是随时间变化;

PWM变化情况

总结

本文简单介绍了PWM的原理,以及如何产生PWM,可以通过锯齿波作为载波和调制波经过比较强,产生相应的PWM输出波形,最后结合STM32实现了一个呼吸灯的简单程序。

小麦大叔 CSDN认证博客专家 CSDN签约作者 有梦想的咸鱼
更多干货,欢迎关注公众号:[小麦大叔]
一个热衷技术的工程师的原创分享,
涉及内容包括但不限于嵌入式、物联网、单片机、编程技术、PCB、硬件设计等等。
来交个朋友?
已标记关键词 清除标记
©️2020 CSDN 皮肤主题: 数字20 设计师:CSDN官方博客 返回首页