STM32学习记录——L298N电机驱动

文章目录


前言

        之前做了一个很普通的蓝牙小车,其实很早就想做,但是一直拖着,最大的原因就是电机驱动的问题。由于一直不清楚电机驱动的用法以及一些细节,加上网上的资料五花八门,导致作为新手,学习起来很困难,后来也是经过漫长的摸索和学长的讲解,终于初窥门径,在这里记录一下。


一、学习目的

       我的学习目的就是通过电机驱动模块,驱动电机并且控制电机的转速和正转反转,最终同时驱动两个电机,完成小车的轮子部分。

二、模块介绍

                                    

        今天要介绍的是很常见的L298N电机驱动模块,它有三种工作方式,由于我只记录我的学习,所以我直接讲我使用的工作方式,也是比较好用的一种。首先看看它各个位置的功能:

1、我们先看看电机驱动如何供电:

        我们只需要在12V供电处接上7-12V电压,供电GND处与单片机共地即可,5V供电处会输出一个5V的电压,可以用于给单片机供电,做小车时最常用的就是这种方式。使用这种方式时,板载5V使能不用管。

2、输出A输出B:

        顾名思义,输出A和输出B是可以给电机输出电压的,将电机的两端分别接上输出A或者输出B即可。所以这个电机驱动可以同时驱动两个电机。

3、通道使能:
PWM调速
        如果你想用PWM调速,那就把通道使能脚(通道使能引脚是下面那个引脚,上面的引脚就是固定的高电平引脚)接入单片机的PWM波输出脚。ENA控制输出A,ENB控制输出B。

非PWM调速
        不用PWM调速,就单纯想让电机转动,就给使能脚一个高电平即可,可以通过跳线帽将其与高电平输出脚相连,如果给使能脚低电平的话,电机将无法转动。

4、逻辑输入:

        逻辑输入一共有4个引脚:IN1、IN2、IN3、IN4,这四个引脚是用来控制电机状态的(正转、反转以及制动)其中IN1IN2是控制输出A的,IN3IN4是控制输出B的,接线方面直接将四个逻辑输入引脚接上单片机的IO口即可。

        可以根据下面的表格设置四个逻辑输入引脚来确定电机状态。

逻辑输入控制电机状态
ENA和ENBIN1(或IN3)IN2(或IN4)电机状态
PWM输出或0XX停止
PWM输出或100制动
PWM输出或101正转
PWM输出或110反转
PWM输出或111制动

5、接线:

如果只驱动一个电机,接线方面如下:

输出AOUT1OUT2   ——>     电机的两端

            12V供电             ——>      7-12V电源

           供电GND            ——>      GND      (与单片机共地)

                ENA               ——>      单片机IO口    (可自己定义,需要具备PWM功能的IO口)

            IN1、IN2           ——>      单片机IO口    (可自己定义)

如果要驱动两个电机,同理即可

三、代码记录

以下是驱动两个电机的代码

l298n.h

头文件定义逻辑输入的引脚对应的IO口,以及电机驱动函数、PWM控制占空比调速的相关函数

#ifndef __L1298N_H
#define __L1298N_H
#include "sys.h"
	 
#define Ina PAout(0)
#define Inb PAout(1)
#define Inc PAout(4)
#define Ind PAout(5)	 
	 
void qianjin(void);
void houtui(void);
void stop(void);
void TIM3_PWM_Init(u16 arr,u16 psc);

#endif

l298n.c

这个代码的转速是通过PWM控制的

#include "timer.h"
#include "l298n.h"
#include "stm32f10x_tim.h"
#include "stm32f10x_rcc.h"
 
void TIM3_PWM_Init(u16 arr,u16 psc)
{
	GPIO_InitTypeDef GPIO_InitStructure;
	TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
	TIM_OCInitTypeDef  TIM_OCInitStructure;
 
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
 	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);
	
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;  
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOA, &GPIO_InitStructure);
	
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6; 
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;  
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOA, &GPIO_InitStructure);
	
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;			
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; 		
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;		
	GPIO_Init(GPIOA, &GPIO_InitStructure);					 
	GPIO_ResetBits(GPIOA,GPIO_Pin_0);					
	
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; 				
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;		 
	GPIO_Init(GPIOA, &GPIO_InitStructure);				
	GPIO_ResetBits(GPIOA,GPIO_Pin_1);						
	
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4;				 
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; 		
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;		 
	GPIO_Init(GPIOA, &GPIO_InitStructure);					 
	GPIO_ResetBits(GPIOA,GPIO_Pin_4);						
	
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;				
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; 		
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;		 
	GPIO_Init(GPIOA, &GPIO_InitStructure);					 
	GPIO_ResetBits(GPIOA,GPIO_Pin_5);						
 
	TIM_TimeBaseStructure.TIM_Period = arr; 
	TIM_TimeBaseStructure.TIM_Prescaler =psc; 
	TIM_TimeBaseStructure.TIM_ClockDivision = 0; 
	TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;  
	TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);
		
	TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; 
 	TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; 
	TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; 
	TIM_OC2Init(TIM3, &TIM_OCInitStructure);  
 
	TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; 
 	TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; 
	TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; 
	TIM_OC1Init(TIM3, &TIM_OCInitStructure);  
 
    TIM_OC2PreloadConfig(TIM3, TIM_OCPreload_Enable);
    TIM_OC1PreloadConfig(TIM3, TIM_OCPreload_Enable);
	TIM_Cmd(TIM3, ENABLE);  
 
}

void qianjin()
{
	Ina=1;
	Inb=0;	
	Inc=1;
	Ind=0;
	TIM_SetCompare2(TIM3,1);   //PWM调速,值越小,速度越大
	TIM_SetCompare1(TIM3,1);   //PWM调速,值越小,速度越大
	
}
void houtui()
{

	Ina=0;
	Inb=1;
	Inc=0;
	Ind=1;
	TIM_SetCompare2(TIM3,1);   //PWM调速,值越小,速度越大
	TIM_SetCompare1(TIM3,1);   //PWM调速,值越小,速度越大

}

void stop(void)
{
	Ina=0;
	Inb=0;
	Inc=0;
	Ind=0;
}

main.c

#include "delay.h"
#include "usart.h"
#include "l298n.h"

 int main(void)
 {		
	delay_init();	   
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); 	
	uart_init(115200);	
 	
	TIM3_PWM_Init(999,0);  
   	while(1)
	{
 		qianjin(); 
		delay_ms(3000);
	    
        houtui(); 
		delay_ms(3000);
	}	 
 }


  • 74
    点赞
  • 553
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 23
    评论
评论 23
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

KAIs32

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值