stm32 PWM控制舵机
- 项目: stm32 PWM控制舵机
- 代码
- Servo.c
123456789101112131415
#include "stm32f10x.h"
#include "PWM.h"
//舵机初始化
void
Servo_Init(
void
)
{
PWM_Init();
}
//舵机角度设定
void
Servo_SetAngle(
float
Angle)
{
PWM_SetCompare1(Angle / 180 * 2000 + 500);
//Angle=0, PWM_SetCompare1(500)对应舵机0°角
//Angle=180,PWM_SetCompare1(2500)对应舵机180°角
}
- Servo.h
1234567
#ifndef __SERVO_H
#define __SERVO_H
void
Servo_Init(
void
);
void
Servo_SetAngle(
float
Angle);
#endif
- main.c
12345678910111213141516171819202122232425262728293031
#include "stm32f10x.h"
#include "Delay.h"
#include "OLED.h"
#include "Servo.h"
#include "Key.h"
uint8_t KeyNum;
float
Angle;
int
main(
void
)
{
OLED_Init();
Servo_Init();
Key_Init();
OLED_ShowString(1, 1,
"Angle:"
);
while
(1)
{
KeyNum = Key_GetNum();
if
(KeyNum == 1)
{
Angle += 30;
if
(Angle > 180)
{
Angle = 0;
}
}
Servo_SetAngle(Angle);
OLED_ShowNum(1, 7, Angle, 3);
}
}
- PWM.c
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647
#include "stm32f10x.h"
void
PWM_Init(
void
)
{
//PB0默认TIM3_CH3通道
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
//配置PB0为复用推挽输出
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
//复用推挽输出,中断控制来自片上外设(TIM3_CH3),而非输出数据寄存器
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
//设置TIM3定时器内部时钟源
TIM_InternalClockConfig(TIM3);
//频率为1kHz, 占空比为50%,分辨率为1%
TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
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(TIM3, &TIM_TimeBaseInitStructure);
//清除更新标志位
TIM_ClearFlag(TIM3, TIM_FLAG_Update);
TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);
//TIM3中断配置使能
TIM_OCInitTypeDef TIM_OCInitStructure;
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_OC1Init(TIM3, &TIM_OCInitStructure);
//打开TIM3定时器外设
TIM_Cmd(TIM3, ENABLE);
}
//PWM占空比的函数
void
PWM_SetCompare1(uint16_t Compare1)
{
TIM_SetCompare1(TIM3, Compare1);
}
- PWM.h
123456
#ifndef __PWM_H
#define __PWM_H
void
PWM_Init(
void
);
void
PWM_SetCompare1(uint16_t Compare1);
#endif
- Key.c
1234567891011121314151617181920212223242526
#include "stm32f10x.h"
#include "delay.h"
void
Key_Init(
void
)
{
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
//上拉输入
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
}
uint8_t Key_GetNum(
void
)
{
uint8_t KeyNum = 0;
if
(GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_0) == 1)
//判断GPIOA Pin_0口高低
{
Delay_ms(20);
while
(GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_0) == 1);
Delay_ms(20);
KeyNum =1;
}
return
KeyNum;
}
- Key.h
1234567
#ifndef __KEY_H
#define __KEY_H
void
Key_Init(
void
);
uint8_t Key_GetNum(
void
);
#endif
- Delay.c
1234567891011121314151617181920212223242526272829303132333435363738394041
#include "stm32f10x.h"
/**
* @brief 微秒级延时
* @param xus 延时时长,范围:0~233015
* @retval 无
*/
void
Delay_us(uint32_t xus)
{
SysTick->LOAD = 72 * xus;
//设置定时器重装值
SysTick->VAL = 0x00;
//清空当前计数值
SysTick->CTRL = 0x00000005;
//设置时钟源为HCLK,启动定时器
while
(!(SysTick->CTRL & 0x00010000));
//等待计数到0
SysTick->CTRL = 0x00000004;
//关闭定时器
}
/**
* @brief 毫秒级延时
* @param xms 延时时长,范围:0~4294967295
* @retval 无
*/
void
Delay_ms(uint32_t xms)
{
while
(xms--)
{
Delay_us(1000);
}
}
/**
* @brief 秒级延时
* @param xs 延时时长,范围:0~4294967295
* @retval 无
*/
void
Delay_s(uint32_t xs)
{
while
(xs--)
{
Delay_ms(1000);
}
}
- Delay.h
123456789
#ifndef __DELAY_H
#define __DELAY_H
void
Delay_us(uint32_t us);
void
Delay_ms(uint32_t ms);
void
Delay_s(uint32_t s);
#endif
- Servo.c
- 参考资料
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· DeepSeek “源神”启动!「GitHub 热点速览」
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· C# 集成 DeepSeek 模型实现 AI 私有化(本地部署与 API 调用教程)
· DeepSeek R1 简明指南:架构、训练、本地部署及硬件要求
· 2 本地部署DeepSeek模型构建本地知识库+联网搜索详细步骤