轉兩個stm32定時器的使用代碼
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Enable;
TIM_OCInitStructure.TIM_Pulse = Pluse;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OCInitStructure.TIM_OCNPolarity = TIM_OCNPolarity_High;
TIM_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Set;
TIM_OCInitStructure.TIM_OCNIdleState = TIM_OCNIdleState_Set;
TIM_OC1Init(BLDC_TIMER_NUM, &TIM_OCInitStructure);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2;
Pluse = MotorA.TimerPeriod - Pluse;
TIM_OCInitStructure.TIM_Pulse = Pluse;
TIM_OC2Init(BLDC_TIMER_NUM, &TIM_OCInitStructure);
#define Fsys 72000000ul // system freq 72MHz
#define Fpwm 20000 // PWM freq 20K
void ConfigTimer(void)
{
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB1PeriphClockCmd( RCC_APB1Periph_TIM4,ENABLE);
RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOB,ENABLE);
TIM_DeInit(TIM4);
TIM_TimeBaseStructure.TIM_Prescaler = 0;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_CenterAligned1;
TIM_TimeBaseStructure.TIM_Period = (Fsys/2) / Fpwm;
TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseStructure.TIM_RepetitionCounter = 0;
TIM_TimeBaseInit(TIM4,&TIM_TimeBaseStructure);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_OutputNState = TIM_OutputState_Disable;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OCInitStructure.TIM_OCNPolarity = TIM_OCNPolarity_Low;
TIM_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Reset;
TIM_OCInitStructure.TIM_OCNIdleState = TIM_OCIdleState_Reset;
TIM_OCInitStructure.TIM_Pulse = (((Fsys/2) / Fpwm) * 20) / 100;
TIM_OC3Init(TIM4,&TIM_OCInitStructure);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2;
TIM_OCInitStructure.TIM_Pulse = (((Fsys/2) / Fpwm) * (100-20)) / 100;
TIM_OC4Init(TIM4,&TIM_OCInitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_9;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
TIM_CtrlPWMOutputs(TIM4, ENABLE);
TIM_Cmd(TIM4,ENABLE);
}
基本設置如下:
1)配置定時器的計數(shù)器為中間對齊計數(shù),即先向上計數(shù)再向下計數(shù)。
2)在該定時器上選擇2個通道,并分別配置為輸出比較模式,并配置在比較成功時翻轉對應的引腳輸出。
3)配置自動重裝載寄存器TIMx_ARR為要求輸出頻率的一半。
4)假定CC1為第一個輸出信號的通道,再假定第一個信號的正脈沖寬度對應為W1,則配置TIMx_CCR1為TIMx_ARR-W1/2。
5) 同4),假定CC2為第二個輸出信號的通道,正脈沖寬度對應為W2,配置TIMx_CCR2為W2/2。
----------------------------------------------
下面以一個例子說明:
假設要求輸出的信號頻率為10kHz,占空比為1:3。
再假設定時器的輸入時鐘為72MHz。
輸出信號的頻率10kHz,換算為計數(shù)器的數(shù)值為7200。
按照上述3),設置TIMx_ARR=3600
輸出信號1的高電平時間W1,換算為計數(shù)器的數(shù)值為W1=7200/4=1800
按照上述4),設置TIMx_CC1=3600 - W1/2=2700
輸出信號2的高電平時間W2,換算為計數(shù)器的數(shù)值為W2=7200/4=1800
按照上述5),設置TIMx_CC2=2/2=450
參照下圖,圖中紅線表示計數(shù)器的數(shù)值變化:
①當計數(shù)器的數(shù)值從0向上計數(shù),達到TIMx_CC1時,CC1匹配成功,CC1的輸出電平翻轉;
②計數(shù)器繼續(xù)向上計數(shù),達到TIMx_ARR時開始調頭向下計數(shù);當計數(shù)器的數(shù)值下降到TIMx_CC1時,CC1再次匹配成功,CC1的輸出電平再次翻轉;
③計數(shù)器繼續(xù)向下計數(shù),達到到TIMx_CC2時,CC2匹配成功,CC2的輸出電平翻轉;
④計數(shù)器繼續(xù)向下計數(shù),減到0時開始調頭向上計數(shù);當計數(shù)器的數(shù)值上升到TIMx_CC2時,CC2再次匹配成功,CC2的輸出電平再次翻轉;
如此循環(huán),得到連續(xù)的相位互為180度的兩路輸出波形。
注意:上述描述是一個原理性的說明,但能夠輸出要求的波形并且占空比可調,實際編程計算中需要可能需要對某些數(shù)值加1或者減1,以達到準確地輸出。
評論