[STM32F1] STM32学习笔记-PWM波形输出

[复制链接]
1027|4
 楼主| IversonCar 发表于 2015-9-27 09:55 | 显示全部楼层 |阅读模式
调试芯片:STM32F103C8T6
外部晶振:8MHz
功能介绍:使用Timer3实现两路(可四路)PWM波形的输出
代码如下:
    初始化:系统时钟初始化,GPIO端口初始化,Timer初始化
系统时钟初始化:
  1. /* 配置系统时钟为72M */
  2. SystemInit();
GPIO端口初始化:
  1.     /****************************************************************
  2.      * 函数名:void GPIO_Config(void)
  3.      * 描述  :配置复用输出PWM时用到的I/O
  4.      * 输入  :无
  5.      * 输出  :无
  6.      * 调用  :main()调用
  7.      ***************************************************************/
  8.     void GPIO_Config(void)  
  9.     {
  10.       GPIO_InitTypeDef GPIO_InitStructure;
  11.      
  12.       /* GPIOA and GPIOB clock enable */
  13.       RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);  
  14.      
  15.       /*GPIOA Configuration: TIM3 channel 1 and 2 as alternate function push-pull */
  16.       GPIO_InitStructure.GPIO_Pin =  GPIO_Pin_6 | GPIO_Pin_7;
  17.       GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;           // 复用推挽输出
  18.       GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
  19.       GPIO_Init(GPIOA, &GPIO_InitStructure);
  20.     }


 楼主| IversonCar 发表于 2015-9-27 09:56 | 显示全部楼层
Timer初始化:
  1.     /****************************************************************
  2.      * 函数名:void TIM3_Config(void)  
  3.      * 描述  :配置TIM3输出的PWM信号的模式
  4.      *      CH1:输出 T=2.5ms(f=1/2.5ms=400Hz)  D=0.6的PWM波(高电平在前,低电平在后)
  5.      *      CH2:输出 T=2.5ms(f=1/2.5ms=400Hz)  D=0.4的PWM波(高电平在后,低电平在前)
  6.      *      步骤一:通过T和TIMxCLK的时钟源确定TIM_Period和TIM_Prescaler  
  7.      *          T=(TIM_Period+1)*(TIM_Prescaler+1)/TIMxCLK=2.5ms  
  8.      *          因为 TIM_Period<65535,所以 TIM_Prescaler>1,即 TIM_Prescaler=2
  9.      *          所以 TIM_Period=59999=0xEA5F
  10.      *      步骤二:根据TIM_Period的值,高低电平的先后D,确定CCR和TIM_OCPolarity
  11.      *          CH1:因为D=0.6,先高后低;
  12.      *              所以CCR1=(TIM_Period+1)* D=36000;TIM_OCPolarity=TIM_OCPolarity_High
  13.      *          CH2:因为D=0.4,先高后低;
  14.      *              所以CCR1=(TIM_Period+1)* (1-D)=36000;TIM_OCPolarity=TIM_OCPolarity_Low
  15.      *      步骤三:基础寄存器初始化
  16.      *      步骤四:通道寄存器初始化
  17.      *      步骤五:使能TIM3重载寄存器ARR
  18.      *      步骤六:使能TIM3  
  19.      * 输入  :无  
  20.      * 输出  :无  
  21.      * 调用  :main()调用  
  22.      ***************************************************************/  
  23.     void TIM3_Config(void)  
  24.     {  
  25.         TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;  
  26.         TIM_OCInitTypeDef  TIM_OCInitStructure;  
  27.         /* PWM信号电平跳变值 */  
  28.         u16 CCR1= 36000;         
  29.         u16 CCR2= 36000;  
  30.         /*PCLK1经过2倍频后作为TIM3的时钟源等于72MHz*/  
  31.         RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);  
  32.         /* Time base configuration */                                            
  33.         TIM_TimeBaseStructure.TIM_Period =0xEA5F;  
  34.         TIM_TimeBaseStructure.TIM_Prescaler = 2;                                    //设置预分频:预分频=2,即为72/3=24MHz  
  35.         TIM_TimeBaseStructure.TIM_ClockDivision = 0;                                //设置时钟分频系数:不分频  
  36.         TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;                 //向上计数溢出模式  
  37.         TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);  
  38.         /* PWM1 Mode configuration: Channel1 */  
  39.         TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;                           //配置为PWM模式1  
  40.         TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;               
  41.         TIM_OCInitStructure.TIM_Pulse = CCR1;                                       //设置跳变值,当计数器计数到这个值时,电平发生跳变  
  42.         TIM_OCInitStructure.TIM_OCPolarity =TIM_OCPolarity_High;                    //当定时器计数值小于CCR1时为高电平  
  43.         TIM_OC1Init(TIM3, &TIM_OCInitStructure);                                    //使能通道1      
  44.         TIM_OC1PreloadConfig(TIM3, TIM_OCPreload_Enable);  
  45.         /* PWM1 Mode configuration: Channel2 */  
  46.         TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;  
  47.         TIM_OCInitStructure.TIM_Pulse = CCR2;                                       //设置通道2的电平跳变值,输出另外一个占空比的PWM  
  48.         TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_Low;                    //当定时器计数值小于CCR2时为低电平
  49.         TIM_OC2Init(TIM3, &TIM_OCInitStructure);                                    //使能通道2  
  50.         TIM_OC2PreloadConfig(TIM3, TIM_OCPreload_Enable);  
  51.         TIM_ARRPreloadConfig(TIM3, ENABLE);                                         //使能TIM3重载寄存器ARR  
  52.         /* TIM3 enable counter */  
  53.         TIM_Cmd(TIM3, ENABLE);                                                      //使能TIM3   
  54.     }

主函数代码:
  1.     /***************************************************************
  2.      * 函数名:main
  3.      * 描述  :主函数
  4.      * 输入  :无
  5.      * 输出  :无
  6.      ***************************************************************/
  7.     int main(void)
  8.     {
  9.         SystemInit();
  10.         GPIO_Config();
  11.         TIM3_Config();
  12.         while (1)
  13.         {
  14.          
  15.         }
  16.     }
 楼主| IversonCar 发表于 2015-9-27 09:56 | 显示全部楼层
最后上结果图:

     疑问:虽然不影响用,但是为什么第一个周期不正确,正确的波形是从第二个周期开始输出的?

734774645 发表于 2015-9-27 14:51 来自手机 | 显示全部楼层
第一个周期是初始化时候造成的吧
wuliangtianzu 发表于 2016-3-13 19:09 | 显示全部楼层
楼主编写的程序里,主函数里面的while(){}l里面写的程序是什么呢,可以共享一下吗,谢谢了
您需要登录后才可以回帖 登录 | 注册

本版积分规则

50

主题

344

帖子

0

粉丝
快速回复 在线客服 返回列表 返回顶部