目录
一、stm32定时器
1、定时器简介
2、定时器分类
3、通用定时器介绍
二、PWM相关介绍
1、工作原理
2、PWM的一般步骤
三、定时器控制LED亮灭
1、工程创建
2、代码编写
3、实现效果
四、采用PWM模式,实现呼吸灯效果
1、工程创建
2、代码编写
3、实现效果
一、stm32定时器
1、定时器简介
定时器就是用来定时的机器,是存在于STM32单片机中的一个外设。其本质就是计数器,只不过 计数器 记录的是STM32的外部情况,所接收的也是外部脉冲,而 定时器 则是由STM32自身提供的一个非常稳定的计数器,这个稳定的计数器就是STM32上连接的晶振部件。
定时器主要功能如下:
2、定时器分类
STM32总共有8个定时器,分别是2个高级定时器(TIM1、TIM8),4个通用定时器(TIM2、TIM3、TIM4、TIM5)和2个基本定时器(TIM5、TIM6 )
三种定时器的主要区别如下:
3、通用定时器介绍
STM32的众多定时器中我们使用最多的是高级定时器和通用定时器,而高级定时器一般也是用作通用定时器的功能,下面我们就以通用定时器为例进行讲解,其功能和特点包括:
位于低速的APB1总线上(APB1)
16 位向上、向下、向上/向下(中心对齐)计数模式,自动装载计数器(TIMx_CNT)。
16 位可编程(可以实时修改)预分频器(TIMx_PSC),计数器时钟频率的分频系数 为 1~65535 之间的任意数值。
4 个独立通道(TIMx_CH1~4),这些通道可以用来作为:
① 输入捕获
② 输出比较
③ PWM 生成(边缘或中间对齐模式)
④ 单脉冲模式输出
可使用外部信号(TIMx_ETR)控制定时器和定时器互连(可以用 1 个定时器控制另外一个定时器)的同步电路。
如下事件发生时产生中断/DMA(6个独立的IRQ/DMA请求生成器):
①更新:计数器向上溢出/向下溢出,计数器初始化(通过软件或者内部/外部触发)
②触发事件(计数器启动、停止、初始化或者由内部/外部触发计数)
③输入捕获
④输出比较
⑤支持针对定位的增量(正交)编码器和霍尔传感器电路
⑥触发输入作为外部时钟或者按周期的电流管理
STM32 的通用定时器可以被用于:测量输入信号的脉冲长度(输入捕获)或者产生输出波形(输出比较和 PWM)等。
使用定时器预分频器和 RCC 时钟控制器预分频器,脉冲长度和波形周期可以在几个微秒到几个毫秒间调整。STM32 的每个通用定时器都是完全独立的,没有互相共享的任何资源。
二、PWM相关介绍
PWM(Pulse Width Modulation,脉冲宽度调制)是一种利用脉冲宽度即占空比实现对模拟信号进行控制的技术,即是对模拟信号电平进行数字表示的方法。
占空比(Duty Cycle),是指在一个周期内,高电平时间占整个信号周期的百分比,即高电平时间与周期的比值: 占空比=Tp/T。
1、工作原理
(1)STM32的定时器除了TIM6和TIM7,其他定时器都可以用来产生PWM输出;
(2)高级定时器TIM1和TIM8可以同时产生多达7路的PWM输出;
(3)通用定时器能同时产生多达4路的PWM输出; STM32中每个定时器有4个输入通道:TIMx_CH1~TIMx_CH4;
(4)每个通道对应1个捕获/比较寄存器TIMx_CRRx,将寄存器值和计数器值相比较,通过比较结果输出高低电平,从而得到PWM信号;
(5)脉冲宽度调制模式可以产生一个由TIMx_ARR寄存器确定频率、由TIMx_CCRx寄存器确定占空比的信号。
如上图所示:在PWM的一个周期内,定时器从0开始向上计数,在0-t1时间段,定时器计数器TIMx_CNT值小于TIMx_CCRx值,输出低电平; 在t1-t2时间段,定时器计数器TIMx_CNT值大于TIMx_CCRx值,输出高电平; 当定时器计数器的值TIMx_CNT达到ARR时,定时器溢出,重新从0开始向上计数,如此循环。
2、PWM的一般步骤
使能定时器和相关IO口时钟。调用函数:RCC_APB1PeriphClockCmd()
RCC_APB2PeriphClockCmd();
初始化IO口为复用功能输出。调用函数:GPIO_Init();
这里是要把PB5用作定时器的PWM输出引脚,所以要重映射配置,所以需要开- 启AFIO时钟,同时设置重映射;调用函数:RCC_APB2PeriphClockCmd();GPIO_PinRemapConfig();
初始化定时器。调用函数:ARR,PSC等:TIM_TimeBaseInit();
初始化输出比较参数。调用函数:TIM_OC2Init();
使能预装载寄存器。调用函数:TIM_OC2PreloadConfig();
使能定时器。调用函数:TIM_Cmd();
不断改变比较值CCRx,达到不同的占空比效果;调用函TIM_SetCompare2()
三、定时器控制LED亮灭
1、工程创建
打开外部时钟,点击 System Core,选择RCC,在右侧弹出的菜单栏中选择Crystal/Ceramic Resonator
选择调试接口,点击 System Core,选择SYS,在右侧弹出的菜单栏中选 Serial Wire
配置IO口,选择 PB7 作为 LED 灯的阴极输入,将其设置为 GPIO-Output,并改名为LED
配置定时器,选择定时器2来实现定时的功能。选中 TIM2,将定时器2的时钟源设置为内部时钟;设置分频系数为71,向上计数模式,计数周期为50000。
这里将分频系数设置为71,系统处理的时候会自动加1,所以此处进行的是72分频。由于时钟设置为为72MHZ,所以72分频后得到1MHZ的时钟;1MHZ的时钟,计数50000次,得到时间50000/1000000=0.05秒;每隔0.05秒,定时器2产生一次定时中断。这里要设置灯周期性的亮灭,周期为两秒,即亮一秒,灭一秒,则中断产生20次后,改变led的引脚电平。
配置中断,允许定时器2的中断
配置时钟,将HCLK修改为 72MHz
最后就可生成项目
2、代码编写
在main主函数里面添加定时器启动代码
HAL_TIM_Base_Start_IT(&htim2);
在main主函数后面添加定时器回调中断函数
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
//这里灯亮一秒,灭一秒,则中断产生20次改变一次电平
static uint32_t time_cnt =0; //记录中断次数
if(htim->Instance == TIM2)
{
if(++time_cnt >= 20) //判断是否已经达到一秒
{
time_cnt =0; //点灯用的中断次数归零
HAL_GPIO_TogglePin(GPIOB,GPIO_PIN_7); //改变LED所接引脚的电平
}
}
}
3、实现效果
点亮LED
四、采用PWM模式,实现呼吸灯效果
1、工程创建
打开外部时钟,点击 System Core,选择RCC,在右侧弹出的菜单栏中选择Crystal/Ceramic Resonator
选择调试接口,点击 System Core,选择SYS,在右侧弹出的菜单栏中选 Serial Wire
配置TIM2
clock source选择internal clock
将 Channel2 设置为 PWM Generation CH2(PWM输出通道2)
Prtscaler (定时器分频系数) 设置为71,即72分频——1MHz
Counter Mode(计数模式)设置为Up(向上计数模式)
Counter Period(自动重装载值) 设置为500,计数器从0向上计数(递增)到自动装载值,然后再次回到0开始计数,并产生一个计数溢出事件.
CKD(时钟分频因子) 设置为No Division (不分频 )
配置USART
配置时钟,将 HCLK 设置为 72MHz
然后就可生成项目
2、代码编写
在 main.c 文件中定义一个变量来记录 pwm 波形的占空比
uint16_t pwm=10;
在main主函数中添加如下代码
HAL_TIM_PWM_Start(&htim2,TIM_CHANNEL_2);
在主函数 while 循环里加入如下代码
while(pwm<500)
{
pwm = pwm + 10;
__HAL_TIM_SetCompare(&htim2,TIM_CHANNEL_2,pwm);
HAL_Delay(20);//延时20毫秒
}
while(pwm>0)
{
pwm = pwm - 10;
__HAL_TIM_SetCompare(&htim2,TIM_CHANNEL_2,pwm);
HAL_Delay(20);
}
3、实现效果
呼吸灯
总结
定时器的学习,让我更加深入的了解到stm32的工作原理,同时实现呼吸灯的效果也感觉很有趣。
参考链接:
定时器&PWM应用编程-CSDN博客