基于stm32f103的舵机角度控制程序

#include "stm32f10x.h"

void servo_set_pulse(uint32_t pulse_width, uint16_t delay_time = 0);
void servo_set_angle(uint8_t angle, uint16_t delay_time = 0);
void servo_init(uint16_t pwm_frequency = 50);

int main(void)
{
    servo_init(50);  // 初始化舵机,默认PWM频率为50Hz

    while(1) {
        servo_set_angle(90, 1000);  // 使舵机旋转到90度,等待1秒钟
        servo_set_pulse(1500, 1000); // 设置脉冲宽度为1.5ms,等待1秒钟
        servo_set_angle(0, 1000);   // 使舵机旋转到0度,等待1秒钟
        servo_set_pulse(1000, 1000); // 设置脉冲宽度为1ms,等待1秒钟
    }
}

void servo_init(uint16_t pwm_frequency)
{
    GPIO_InitTypeDef GPIO_InitStructure;
    TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStruct;
    TIM_OCInitTypeDef TIM_OCInitStructure;

    // 使能GPIOA、AFIO和TIM3的时钟
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO | RCC_APB1Periph_TIM3, ENABLE);

    // 将PA1配置为复用推挽输出
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOA, &GPIO_InitStructure);

    // 使能TIM3的时钟
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);

    // 配置TIM3
    TIM_TimeBaseInitStruct.TIM_Prescaler = 72 - 1;  // 72MHz/72 = 1MHz
    TIM_TimeBaseInitStruct.TIM_CounterMode = TIM_CounterMode_Up;
    TIM_TimeBaseInitStruct.TIM_Period = 20000 - 1;  // 1MHz/20,000 = 50Hz或20ms周期
    TIM_TimeBaseInitStruct.TIM_ClockDivision = 0;
    TIM_TimeBaseInitStruct.TIM_RepetitionCounter = 0;
    TIM_TimeBaseInit(TIM3, &TIM_TimeBaseInitStruct);

    // 将TIM3通道1配置为PWM输出
    TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
    TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
    TIM_OCInitStructure.TIM_Pulse = 1500;  // 配置90度时的1.5ms脉冲宽度
    TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
    TIM_OC1Init(TIM3, &TIM_OCInitStructure);
    TIM_OC1PreloadConfig(TIM3, TIM_OCPreload_Enable);

    // 启动TIM3
    TIM_Cmd(TIM3, ENABLE);
}

void servo_set_angle(uint8_t angle, uint16_t delay_time)
{
    if(angle < 0) angle = 0;
    if(angle > 180) angle = 180;
    uint32_t pulse_width = (angle * 11) + 500;  // 将角度转换为脉冲宽度
    servo_set_pulse(pulse_width, delay_time);
}

void servo_set_pulse(uint32_t pulse_width, uint16_t delay_time)
{
    TIM3->CCR1 = pulse_width;  // 设置PWM脉冲宽度
    
    if(delay_time > 0) {
        delay_ms(delay_time);  // 等待指定的时间
    }
}

这个程序中使用的定时器脉冲频率是1MHz,即72MHz的时钟频率除以72,将TIM3的预分频器设置为72-1。然后,每20ms产生一个PWM周期,将TIM3的重装载值设置为20000-1。所以定时器的输出频率是1MHz/20000,也就是50Hz。

一个基本的舵机角度控制代码,如有不足希望大家指正,

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
#include "stm32f10x.h" #include "GPIOLIKE51.h" #define uint unsigned int #define uchar unsigned char #define CLOCK 72/8 //时钟=72M //函数声明 void GPIO_Configuration(void); /**************************************************************************** * 名 称:delay_us(u32 nus) * 功 能:微秒延时函数 * 入口参数:u32 us * 出口参数:无 * 说 明: * 调用方法:无 ****************************************************************************/ //void delay_us(u32 us) //{ // u32 temp; // SysTick->LOAD = 9*us; // SysTick->VAL=0X00;//清空计数器 // SysTick->CTRL=0X01;//使能,减到零是无动作,采用外部时钟源 // do // { // temp=SysTick->CTRL;//读取当前倒计数值 // }while((temp&0x01;)&&(!(temp&(1<CTRL=0x00; //关闭计数器 // SysTick->VAL =0X00; //清空计数器 //} /**************************************************************************** * 名 称:delay_ms(u16 ms) * 功 能:毫秒延时函数 * 入口参数:u16 nms * 出口参数:无 * 说 明: * 调用方法:无 ****************************************************************************/ void delay_ms(u16 ms) { u32 temp; SysTick->LOAD = 9000*ms; SysTick->VAL=0X00;//清空计数器 SysTick->CTRL=0X01;//使能,减到零是无动作,采用外部时钟源 do { temp=SysTick->CTRL;//读取当前倒计数值 }while((temp&0x01;)&&(!(temp&(1<CTRL=0x00; //关闭计数器 SysTick->VAL =0X00; //清空计数器 } //============================================================================= //文件名称:main //功能概要:主函数 //参数说明:无 //函数返回:int //============================================================================= int main(void) { GPIO_Configuration(); while (1) { // GPIO_SetBits(GPIOB,GPIO_Pin_9); // delay_ms(500);// 100=0.1S GPIO_ResetBits(GPIOB,GPIO_Pin_9); delay_ms(500); } } //============================================================================= //文件名称:GPIO_Configuration //功能概要:GPIO初始化 //参数说明:无 //函数返回:无 //============================================================================= void GPIO_Configuration(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE&#4
### 回答1: 基于stm32f103的蓝牙摇控程序一个用于控制蓝牙设备的程序,通过连接蓝牙模块和stm32f103开发板,可以实现远程控制。 首先,我们需要确定硬件连接。将蓝牙模块的TX引脚连接到stm32f103的RX引脚,将蓝牙模块的RX引脚连接到stm32f103的TX引脚,同时连接蓝牙模块的VCC和GND引脚到stm32f103。 接下来,我们需要编写程序。首先,在main函数初始化stm32f103的串口功能,设定波特率和其他相关设置。然后,创建一个用于接收蓝牙数据的缓冲区。 接着,我们需要编写一个循环函数,不断接收蓝牙发来的数据。在每次接收到数据时,可以根据数据的不同进行相应的处理。例如,如果接收到的数据是"forward",则可以调用相应的函数实现前进动作;如果接收到的数据是"backward",则可以调用相应的函数实现后退动作。通过按照预定的规则来解析和处理蓝牙数据,我们就可以实现根据接收到的指令来控制各种设备或执行各种动作。 最后,我们可以根据需要添加一些辅助功能,如LED指示灯的控制,用于显示当前设备的状态或连接状态。 总的来说,基于stm32f103的蓝牙摇控程序是通过连接蓝牙模块和stm32f103开发板,实现接收蓝牙数据并根据数据来控制各种设备或执行各种动作的程序。这种程序可以在无线远程控制方面有着广泛的应用,可用于遥控车辆、智能家居等领域。 ### 回答2: 基于STM32F103的蓝牙摇控程序是一种通过蓝牙技术来控制摇控设备的方案。该程序主要通过STM32F103单片机与蓝牙模块之间的串口通信实现。 首先,需要连接STM32F103单片机和蓝牙模块。通过串口连接,将蓝牙模块的TX接口连接到STM32F103单片机的RX引脚,将蓝牙模块的RX接口连接到STM32F103单片机的TX引脚。同时,还需要为STM32F103单片机编写相应的程序代码。 在STM32F103单片机上,首先需要初始化串口功能,设置波特率等参数。然后,通过接收蓝牙模块发送的数据来判断用户的控制指令。常见的控制指令可以包括前进、后退、左转、右转等。 接收到指令后,STM32F103单片机需要将相应的指令转化为PWM信号,通过控制电机或舵机转动来实现相应的动作。例如,将前进指令转化为电机正转的PWM信号,将后退指令转化为电机反转的PWM信号。 除了控制指令的处理,还可以在程序加入一些保护机制,例如限制最大速度、避免意外碰撞等。可以通过调整控制指令与PWM信号的对应关系,来实现不同速度的控制。 最后,在程序的循环,需要不断接收来自蓝牙模块的指令,并执行相应的动作。通过这样的方式,就可以实现基于STM32F103的蓝牙摇控程序

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值