一、接线
二、实验实现
动手让 SG90 每秒转动一下,0° -> 20° -> 40° -> 100° -> 180° 如此循环。
舵机接A6
复制18-呼吸灯,重命名24-sg90舵机
把PWM重命名sg90
打开项目文件
在魔术棒和品上把PWM都去掉,加载sg90文件夹
加载之后把文件中含有pwm.h字样的换成sg90
编译
使用定时器3通道1(产品手册18页)
在代码中把相应数据改掉
三、舵机实现0-180°,180-0°
main.c
#include "sys.h"
#include "delay.h"
#include "led.h"
#include "sg90.h"
int main(void)
{
HAL_Init(); /* 初始化HAL库 */
stm32_clock_init(RCC_PLL_MUL9); /* 设置时钟, 72Mhz */
led_init();//初始化led灯
sg90_init();
uint16_t i = 0;
while(1)
{
//舵机
for(i = 5;i<=25;i++)
{
tim3_compare_set(i);
delay_ms(100);
}
for(i = 5;i<=25;i++)
{
tim3_compare_set(30 - i);
delay_ms(100);
}
}
}
sg90.c
#include "sg90.h"
TIM_HandleTypeDef tim3_handle ={0};
//init函数
void tim3_init(void)//固定20ms周期
{
TIM_OC_InitTypeDef pwm_config = {0};
tim3_handle.Instance = TIM3; //寄存器时基地址
tim3_handle.Init.Prescaler = 7200 - 1; //psc
tim3_handle.Init.Period = 200 - 1; //arr
tim3_handle.Init.CounterMode = TIM_COUNTERMODE_UP; //计数器模式:向上计数
HAL_TIM_PWM_Init(&tim3_handle);
pwm_config.OCMode = TIM_OCMODE_PWM1; //定时模式:模式1
pwm_config.Pulse = 100;//CCR(比较寄存器)的值 :随意指定,因为值还要改 ;指定PWM信号的脉冲宽度
pwm_config.OCPolarity = TIM_OCPOLARITY_HIGH;//舵机看占空比,有效电平:高电平
HAL_TIM_PWM_ConfigChannel(&tim3_handle,&pwm_config,TIM_CHANNEL_1);//句柄,pwm配置,通道1
HAL_TIM_PWM_Start(&tim3_handle,TIM_CHANNEL_1);
}
//msp函数
void HAL_TIM_PWM_MspInit(TIM_HandleTypeDef *htim)
{
if(htim->Instance == TIM3)
{
GPIO_InitTypeDef gpio_initstruct;//定义一个结构体gpio_initstruct
//打开时钟
__HAL_RCC_GPIOA_CLK_ENABLE();
__HAL_RCC_TIM3_CLK_ENABLE();
//调用GPIO初始化函数
gpio_initstruct.Mode = GPIO_MODE_AF_PP;//复式推挽输出
gpio_initstruct.Pin = GPIO_PIN_6;//LED1对应的引脚
gpio_initstruct.Pull = GPIO_PULLUP;//上拉
gpio_initstruct.Speed = GPIO_SPEED_FREQ_HIGH;//速度:高速
HAL_GPIO_Init(GPIOA,&gpio_initstruct);
//使用中断的时候才使用NVIC
// HAL_NVIC_SetPendingIRQ(TIM3_IRQn);
// HAL_NVIC_EnableIRQ(TIM3_IRQn);
}
}
//修改CCR值的函数
void tim3_compare_set(uint16_t val)
{
__HAL_TIM_SET_COMPARE(&tim3_handle,TIM_CHANNEL_1,val);//句柄,通道,值
}
void sg90_init(void)
{
tim3_init();
}
sg90.h
#ifndef __SG90_H__
#define __SG90_H__
#include "sys.h"
void sg90_init(void);
void tim3_compare_set(uint16_t val);
#endif
四、实现输入一个角度,舵机旋转到指定角度
main.c
#include "sys.h"
#include "delay.h"
#include "led.h"
#include "sg90.h"
int main(void)
{
HAL_Init(); /* 初始化HAL库 */
stm32_clock_init(RCC_PLL_MUL9); /* 设置时钟, 72Mhz */
led_init();//初始化led灯
sg90_init();
//uint16_t i = 0;
while(1)
{
sg90_angle_set(0);//度数
delay_ms(1000);
sg90_angle_set(20);
delay_ms(1000);
sg90_angle_set(40);
delay_ms(1000);
sg90_angle_set(90);
delay_ms(1000);
sg90_angle_set(180);
delay_ms(1000);
// //舵机
// for(i = 5;i<=25;i++)
// {
// tim3_compare_set(i);
// delay_ms(100);
// }
// for(i = 5;i<=25;i++)
// {
// tim3_compare_set(30 - i);
// delay_ms(100);
// }
}
}
sg90.c
#include "sg90.h"
TIM_HandleTypeDef tim3_handle ={0};
//init函数
void tim3_init(void)//固定20ms周期
{
TIM_OC_InitTypeDef pwm_config = {0};
tim3_handle.Instance = TIM3; //寄存器时基地址
tim3_handle.Init.Prescaler = 7200 - 1; //psc
tim3_handle.Init.Period = 200 - 1; //arr
tim3_handle.Init.CounterMode = TIM_COUNTERMODE_UP; //计数器模式:向上计数
HAL_TIM_PWM_Init(&tim3_handle);
pwm_config.OCMode = TIM_OCMODE_PWM1; //定时模式:模式1
pwm_config.Pulse = 100;//CCR(比较寄存器)的值 :随意指定,因为值还要改 ;指定PWM信号的脉冲宽度
pwm_config.OCPolarity = TIM_OCPOLARITY_HIGH;//舵机看占空比,有效电平:高电平
HAL_TIM_PWM_ConfigChannel(&tim3_handle,&pwm_config,TIM_CHANNEL_1);//句柄,pwm配置,通道1
HAL_TIM_PWM_Start(&tim3_handle,TIM_CHANNEL_1);
}
//msp函数
void HAL_TIM_PWM_MspInit(TIM_HandleTypeDef *htim)
{
if(htim->Instance == TIM3)
{
GPIO_InitTypeDef gpio_initstruct;//定义一个结构体gpio_initstruct
//打开时钟
__HAL_RCC_GPIOA_CLK_ENABLE();
__HAL_RCC_TIM3_CLK_ENABLE();
//调用GPIO初始化函数
gpio_initstruct.Mode = GPIO_MODE_AF_PP;//复式推挽输出
gpio_initstruct.Pin = GPIO_PIN_6;//LED1对应的引脚
gpio_initstruct.Pull = GPIO_PULLUP;//上拉
gpio_initstruct.Speed = GPIO_SPEED_FREQ_HIGH;//速度:高速
HAL_GPIO_Init(GPIOA,&gpio_initstruct);
//使用中断的时候才使用NVIC
// HAL_NVIC_SetPendingIRQ(TIM3_IRQn);
// HAL_NVIC_EnableIRQ(TIM3_IRQn);
}
}
//修改CCR值的函数
void tim3_compare_set(uint16_t val)
{
__HAL_TIM_SET_COMPARE(&tim3_handle,TIM_CHANNEL_1,val);//句柄,通道,值
}
void sg90_init(void)
{
tim3_init();
}
void sg90_angle_set(uint16_t angle)
{
uint16_t CCRx = (1.0/9.0) * angle + 5.0;
tim3_compare_set(CCRx);
}
sg90.h
#ifndef __SG90_H__
#define __SG90_H__
#include "sys.h"
void sg90_init(void);
void sg90_angle_set(uint16_t angle);
#endif