介绍
想要通过stm32单片机控制舵机,如SG90舵机、MG996R舵机等,那就得给舵机一定周期得脉冲信号。而stm32上的定时器的PWM模式能够满足我们的需求。
舵机控制原理
舵机的控制一般需要一个20ms左右的时基脉冲,该脉冲的高电平部分一般为0.5ms-2.5ms范围内的角度控制脉冲部分,总间隔为2ms。以180度角度伺服为例,那么对应的控制关系是这样的:
0.5ms--------------0度;
1.0ms------------45度;
1.5ms------------90度;
2.0ms-----------135度;
2.5ms-----------180度;
所以,如果我们想要让舵机转动指定的角度,就需要按照上面的关系计算出高电平的时间。
代码实现
利用stm32f103c8t6上的TIM2通用定时器的通道2,对应的引脚是PA2(可通过单片机的参考文档查找)来输出PWM信号。
下面是参考代码:
void PWM_Init(void)
{
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
GPIO_InitTypeDef GPIO_InitStructure2; //配置PA2为复用推挽输出模式
GPIO_InitStructure2.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure2.GPIO_Pin = GPIO_Pin_1;
GPIO_InitStructure2.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure2);
TIM_InternalClockConfig(TIM2);
TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure; //配置定时器2
TIM_TimeBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInitStructure.TIM_Period = 20000 - 1; //ARR
TIM_TimeBaseInitStructure.TIM_Prescaler = 72 - 1; //PSC
TIM_TimeBaseInitStructure.TIM_RepetitionCounter = 0;
TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStructure);
TIM_OCInitTypeDef TIM_OCInitStructure; //配置PWM1输出模式
TIM_OCStructInit(&TIM_OCInitStructure);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0; //CCR
TIM_OC2Init(TIM2, &TIM_OCInitStructure);
TIM_Cmd(TIM2, ENABLE);
}
上面是初始化函数,再通过修改定时器的占空比来控制舵机的角度
void PWM_SetCompare2(uint16_t Compare) //这里有个占空比的计算关系 Angle / 180 * 2000 + 500
{
TIM_SetCompare2(TIM2, Compare);
}
mian函数:
int main(void)
{
PWM_Init();
while (1)
{
PWM_SetCompare2( 60 / 180 * 2000 + 500) ;
}
}
希望以上分享能对大家有所帮助!
如有问题,恳请斧正~