野火STM32_HAL库版课程笔记-TB6612FNG驱动有刷电机

本节虽然使用电机模块, 但是主要使用到的就是定时器的 PWM 来驱动.

像舵机一样, 有刷电机同样需要 PWM 来驱动, 只不过不想舵机一样有硬性要求, 需要达到多少频率, 多少占空比才能够进行工作.

有刷电机是一种更加灵活的, 可以控制的电机类型.

前置介绍

实验目的与模块介绍
实验引脚
TB6612FNG 驱动模块

AO1 和 AO2 就可以连接一个直流电机 进行控制

BO1 和 BO2 也可以连接一个直流电机 进行控制

VM 电机驱动电压输入引脚, 即该电源是给电机的.

PWMA / B: A / B 通道 PWM 输入引脚, 即需通过 STM32 输入 PWM 到引脚中, 才能够驱动电机. (电机转速则由 PWM 占空比决定)

AIN1 和 AIN2 即逻辑输入引脚, 输入不同的电平来控制电机的正反转.

BIN1 和 BIN2 同理, 输入不同的电平来控制电机的正反转.

首先 AO1 和 AO2 是电源, 电机的输出引脚, 不需要配置

GND 需要进行接地.

还有连接芯片的 VCC 和 GND. 用来供给驱动芯片工作.

而 电机的驱动电源 VM 需要连接 5V 的供电引脚.

STM32 要使用的引脚用 PWM 引脚连接 PWMA,

然后再用两个 GPIO 连接 AIN2 和 AIN1 来控制电机的方向.

同时, 还可以用一个 GPIO 引脚来连接 STBY (待机引脚), 控制芯片的工作.

即总共需要用到 STM32 的 4 个引脚

|----|--------|--------|-------|------|
| 状态 | 导通的开关 | 截止的开关 | 电流方向 | 电机动作 |
| 正转 | Q1, Q4 | Q2, Q3 | 左 → 右 | 正向旋转 |
| 反转 | Q2, Q3 | Q1, Q4 | 右 → 左 | 反向旋转 |

关键提示:

  • 严禁直通(Shoot-through): 在同一个侧臂(例如Q1和Q2,或者Q3和Q4)不能同时导通。如果Q1和Q2同时导通,电源VM会直接短路到地,导致电路烧毁。

PWM 配置的极性是高电平, 占空比越大, 电机转速越高, 反之, 极性是低电平, 占空比越大, 电机转速越低.

项目配置

TIM3

先点击 PB0, 选择 TIM3_CH3, 然后在 TIM3 中, 将 Channel3 改为 PWM Generation CH3

PSC : 72-1

ARR : 100-1

auto-reload preload : Enabel

其余默认即可

GPIO

(GPIO_Output) AIN1 , AIN2 控制方向的引脚 : PA4, PA5

(GPIO_Output) STBY 控制工作模式 : PA7

(GPIO_Input) 按键引脚 : PA0, PA13

按照图中红框处, 将两个按键输入引脚的标签改为 KEY1 和 KEY2, 并设置 下拉模式 (pull-down)

其他引脚的标签改为图中对应的引脚功能名称

代码部分

复制代码
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */

// 建议使用 20% 到 80% 的占空比, 如果过高或者过低, 可能会出现其他问题. 
#define SPEED_LOW 20  // 低速, 占空比 20%
#define SPEED_HIGH 80 // 高速, 占空比 80%

/* USER CODE END PD */

/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */

/* USER CODE END PM */

/* Private variables ---------------------------------------------------------*/

/* USER CODE BEGIN PV */

uint8_t speed_mode = 0;     // 0=慢速, 1=快速
uint8_t direction_mode = 0; // 0=正转, 1=反转

/* USER CODE END PV */

/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
/* USER CODE BEGIN PFP */

/* USER CODE END PFP */

/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */

/**
  * @brief  设置电机的转向和转速
  * @param  direction: 方向控制: 0 为正转, 1 为反转
  * @param  speed: PWM 占空比 (范围 0~100), 值越大转速越快 (PWM极性为High的情况下)
  * @retval 无
  * @note   使用 TIM3 通道 3 输出 PWM 控制转速, AIN1 / AIN2 控制方向
  */
void Motor_Set(uint8_t direction, uint16_t speed)
{
  __HAL_TIM_SET_COMPARE(&htim3, TIM_CHANNEL_3, speed);  // 设置占空比

  if (direction == 0) // 正转
  {
    HAL_GPIO_WritePin(AIN1_GPIO_Port, AIN1_Pin, GPIO_PIN_SET);    // AIN1 高电平
    HAL_GPIO_WritePin(AIN2_GPIO_Port, AIN2_Pin, GPIO_PIN_RESET);  // AIN2 低电平
  }
  else  // 反转
  {
    HAL_GPIO_WritePin(AIN1_GPIO_Port, AIN1_Pin, GPIO_PIN_RESET);  // AIN1 低电平
    HAL_GPIO_WritePin(AIN2_GPIO_Port, AIN2_Pin, GPIO_PIN_SET);    // AIN2 高电平
  }
  
}

/* USER CODE END 0 */

/**
  * @brief  The application entry point.
  * @retval int
  */
int main(void)
{

  /* USER CODE BEGIN 1 */

  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  MX_TIM3_Init();
  /* USER CODE BEGIN 2 */
  
  HAL_TIM_PWM_Start(&htim3, TIM_CHANNEL_3); // 开启 PWM 输出 (PB0-TIM3-CH3)
  HAL_GPIO_WritePin(STBY_GPIO_Port, STBY_Pin, GPIO_PIN_SET); // STBY 拉高使能电机驱动芯片

  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
    // 初始情况 PWM 为 0, AIN1 和 AIN2 也为 0 , 电机是停止状态
    // 只有当按下按键(KEY1 或者 KEY2), 才能够设置电机的转速和方向, 电机才会被驱动. 
    if (HAL_GPIO_ReadPin(KEY1_GPIO_Port, KEY1_Pin) == GPIO_PIN_SET) // KEY1 切换速度模式
    {
      // 切换速度模式 (0: 低速, 1: 高速)
      speed_mode = !speed_mode;

      // 根据当前速度模式选择对应占空比
      uint16_t speed = (speed_mode == 0) ? SPEED_LOW : SPEED_HIGH;

      // 设置电机转向和速度
      Motor_Set(direction_mode, speed);

      while(HAL_GPIO_ReadPin(KEY1_GPIO_Port, KEY1_Pin) == GPIO_PIN_SET); // 等待松手
    }

    if (HAL_GPIO_ReadPin(KEY2_GPIO_Port, KEY2_Pin) == GPIO_PIN_SET) // KEY2 切换方向模式
    {
      // 切换方向模式 (0: 正转, 1: 反转)
      direction_mode = !direction_mode;

      // 根据当前速度模式选择对应占空比 
      uint16_t speed = (speed_mode == 0) ? SPEED_LOW : SPEED_HIGH;

      // 设置电机转向和速度
      Motor_Set(direction_mode, speed);
      while(HAL_GPIO_ReadPin(KEY2_GPIO_Port, KEY2_Pin) == GPIO_PIN_SET); // 等待松手
    }

    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  }

程序现象

参考接线:

通过按键 KEY1 切换速度, 按键 KEY2 切换旋转方向.

分别对应

正转-慢速

正转-快速

反转-慢速

相关推荐
恶魔泡泡糖7 小时前
stm32F103C8T6标准库反射(反射式红外)传感器触发蜂鸣器
stm32·单片机·嵌入式硬件
fengxin_rou7 小时前
JVM 核心笔记:对象创建、生命周期与类加载器详解
java·jvm·笔记
weixin_704266057 小时前
Spring Cloud Gateway 完整版笔记
笔记
华清远见IT开放实验室7 小时前
STM32+Linux双体系,零基础玩转嵌入式
linux·stm32·嵌入式硬件
LCG元7 小时前
STM32实战:基于FreeRTOS的智能小车多任务调度(循迹+避障+通信)
stm32·单片机·嵌入式硬件
qeen877 小时前
【算法笔记】二分查找与二分答案
c语言·c++·笔记·学习·算法·二分
脆皮炸鸡7557 小时前
进程的程序替换
linux·经验分享·笔记·vim·学习方法
萌新小码农‍8 小时前
机器学习概述 学习笔记day2
笔记·学习·机器学习
daanpdf8 小时前
大一《中国近代史纲要》题库及答案PDF知识点整理笔记
笔记·pdf
曦月逸霜8 小时前
区块链技术与应用学习笔记(持续更新中)
笔记·学习·区块链