根据手册可以知道我们
只要控制AIN和BIN就能控制小车是向前走还是向后走,向左转还是向右转
控制PWMA和PWMB就能控制车子的转速
通过下面的表我们可以得出
方向 AIN1 AIN2 BIN1 BIN2
前 0 1 0 1
后 1 0 1 0
左 1 0 0 1
右 0 1 1 0
通过原理图我们可以见到
AIN1对应PB13
AIN2对应PB12
BIN1对应PB1
BIN2对应PB0
PWMA对应PA11
PWMB对应PA8
所以我们新建一个文件名为TB6612.c用于存放TB6612 GPIO的初始化和PWM的初始化
查看手册能找到PWM的脚在PA8和PA11分别对应TIM1_CH1和TIM1_CH4
我们可以先在头文件里面定义相关的宏定义
#define AIN1 PBout(13)// PB13
#define AIN2 PBout(12)// PB12
#define BIN1 PBout(1)// PB1
#define BIN2 PBout(0)// PB0
配置GPIO
void TB6612_GPIO_Init(void)
{
//开启GPIOB的时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
//配置端口 AIN1 AIN2 BIN1 BIN2 对应 PB13 PB12 PB1 PB0
GPIO_InitTypeDef GPIO_Structure;
GPIO_Structure.GPIO_Mode = GPIO_Mode_Out_PP; //推挽输出
GPIO_Structure.GPIO_Pin = GPIO_Pin_13 | GPIO_Pin_12 | GPIO_Pin_1 | GPIO_Pin_0 ;
GPIO_Structure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB,&GPIO_Structure);
GPIO_SetBits(GPIOB,GPIO_Pin_13 | GPIO_Pin_12 | GPIO_Pin_1 | GPIO_Pin_0); //将端口设置成高电平
}
配置PWM
void TB6612_TIM_PWM_Init(u16 arr,u16 psc)
{
//开启TIM1的时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1,ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO,ENABLE); //PWM脚在GPIOA上,并开启AFIO复用
//配置端口
//开启AFIO复用后, Pin8 和 pin11 对应 TIM1 的 CH1 和 CH4
GPIO_InitTypeDef GPIO_Structure;
GPIO_Structure.GPIO_Mode = GPIO_Mode_AF_PP; //复用推挽输出
GPIO_Structure.GPIO_Pin = GPIO_Pin_11; //TIM1_CH1 | TIM1_CH4
GPIO_Structure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA,&GPIO_Structure);
GPIO_Structure.GPIO_Mode = GPIO_Mode_AF_PP; //复用推挽输出
GPIO_Structure.GPIO_Pin = GPIO_Pin_8; //TIM1_CH1 | TIM1_CH4
GPIO_Structure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA,&GPIO_Structure);
//初始化TIM1
TIM_TimeBaseInitTypeDef TIM1_Structure;
TIM1_Structure.TIM_Period = arr; //设置在下一个更新事件装入活动的自动重装载寄存器周期的值
TIM1_Structure.TIM_Prescaler = psc; //设置用来作为TIMx时钟频率除数的预分频值
TIM1_Structure.TIM_ClockDivision = 0; //设置时钟分割:TDTS = Tck_tim
TIM1_Structure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上计数
TIM_TimeBaseInit(TIM1,&TIM1_Structure);
//初始化TIM1_CH1 PWM模式
TIM_OCInitTypeDef TIM_OC_Structure;
TIM_OC_Structure.TIM_OCMode = TIM_OCMode_PWM2; //选择定时器模式:TIM脉冲宽度调制模式2
TIM_OC_Structure.TIM_OutputState = TIM_OutputState_Enable; //比较输出使能
TIM_OC_Structure.TIM_OCPolarity = TIM_OCPolarity_High; //输出极性:TIM输出比较极性高
TIM_OC1Init(TIM1,&TIM_OC_Structure);
TIM_OC1PreloadConfig(TIM1,TIM_OCPreload_Enable); //使能TIM1在CCR2上的预装载寄存器
//初始化TIM1_CH4 PWM模式
TIM_OC_Structure.TIM_OCMode = TIM_OCMode_PWM2; //选择定时器模式:TIM脉冲宽度调制模式2
TIM_OC_Structure.TIM_OutputState = TIM_OutputState_Enable; //比较输出使能
TIM_OC_Structure.TIM_OCPolarity = TIM_OCPolarity_High; //输出极性:TIM输出比较极性高
TIM_OC4Init(TIM1,&TIM_OC_Structure);
TIM_OC4PreloadConfig(TIM1,TIM_OCPreload_Enable); //使能TIM1在CCR2上的预装载寄存器
//时钟上电
TIM_Cmd(TIM1,ENABLE);
//MOE 主输出使能,高级定时器必须开启
TIM_CtrlPWMOutputs(TIM1,ENABLE);
}
main.c调用
//初始化TB6612的GPIO
TB6612_GPIO_Init();
//控制PWM的占空比来达到控制小车速度的效果
//数字越大越慢,实测发现调到2000电机已经不动了
TB6612_TIM_PWM_Init(1999,359);
TIM_SetCompare1(TIM1,1700);
TIM_SetCompare4(TIM1,1700);
前进方向的封装
//通过控制AIN BIN来控制小车的前进方向
#include "stm32f10x.h"
#include "TB6612.h"
#include "Ward.h"
uint16_t speed = 1700;
void Forward(void)
{
AIN1 = 0; //PB13
AIN2 = 1; //PB12
BIN1 = 0; //PB1
BIN2 = 1; //PB0
TIM_SetCompare1(TIM1,speed); //PA8 PWMB
TIM_SetCompare4(TIM1,speed); //PA11 PWMA
}
void Backward(void)
{
AIN1 = 1; //PB13
AIN2 = 0; //PB12
BIN1 = 1; //PB1
BIN2 = 0; //PB0
TIM_SetCompare1(TIM1,speed); //PA8 PWMB
TIM_SetCompare4(TIM1,speed); //PA11 PWMA
}
void Rightward(void)
{
AIN1 = 0; //PB13
AIN2 = 1; //PB12
BIN1 = 1; //PB1
BIN2 = 0; //PB0
TIM_SetCompare1(TIM1,speed); //PA8 PWMB
TIM_SetCompare4(TIM1,speed); //PA11 PWMA
}
void Leftward(void)
{
AIN1 = 1; //PB13
AIN2 = 0; //PB12
BIN1 = 0; //PB1
BIN2 = 1; //PB0
TIM_SetCompare1(TIM1,speed); //PA8 PWMB
TIM_SetCompare4(TIM1,speed); //PA11 PWMA
}
这样一来我们就能直接调用方向函数进行方向的控制了