ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

L298N电机驱动模块接线与代码实战:Arduino/树莓派/STM32全平台驱动指南

L298N电机驱动模块接线与代码实战:Arduino/树莓派/STM32全平台驱动指南 说个真事我见过不少玩智能车的新手第一次拿到 L298N 电机驱动模块第一反应都是“这板子怎么这么多针脚”然后照着网上的教程一顿接线结果上电之后电机纹丝不动于是开始怀疑人生。其实 L298N 电机驱动模块远没有想象中复杂它核心就三件事电源怎么给、控制信号怎么接、电机怎么输出。这篇文章我就围绕 L298N 的接线使用与代码实现把从零到一调通两个直流减速电机的全过程写清楚同时附上我在 Arduino、树莓派、STM32 三种平台上的实测代码以及踩坑之后总结出来的排查方法。1. 项目概述与方案定位L298N 到底解决了什么问题1.1 一个模块完成正反转与调速两件事L298N 电机驱动模块核心是一颗 ST 公司生产的 L298 双 H 桥驱动芯片。所谓双 H 桥你可以粗暴地理解为内部有两组“四开关电路”每组都能独立控制一个直流电机的正转、反转和停止。模块上还额外集成了续流二极管、5V 稳压电路和两个使能跳线帽所以用户拿到手之后不用再搭外围电路直接把电机和控制板接上去就能用。它最典型的应用场景是驱动两个直流减速电机也就是我们常说的“坦克式”双电机小车底盘。一个电机接左边轮一个电机接右边轮依靠两轮的速度差就能实现前进、后退、转弯、原地旋转。也正因为控制方式简单直接——给高电平就全速转给 PWM 就变速转——所以它是很多创客教育、智能车竞赛入门的首选模块。1.2 为什么新手期建议优先选 L298N 而不是 TB6612看到热词里有 TB6612 电机驱动模块这里顺便对比一下帮大家做选型判断。L298N 和 TB6612 是目前市面上最常见的两款驱动模块但它们的定位差异非常大。我自己在入门阶段用的就是 L298N原因很简单它皮实、容错率高、接线直观。L298N 的工作电压范围宽模块上有明显的接线端子还有一排指示灯接错线时至少能通过电压、发热、灯亮等情况推断问题。而 TB6612 虽然效率更高、体积更小、PWM 频率响应更好但它是贴片模块引脚细密对新手接线不太友好而且耐压范围窄电源接反时更容易烧芯片。从驱动能力看L298N 的最大驱动电流可以到 2A 每通道对于常见的 TT 马达、370/540 电机、乃至一些小型 12V 减速电机都够用。当然它也有缺点饱和压降大芯片本身功耗高PWM 频率过高时发热明显。所以如果你做的是电池供电的平衡小车或者追求续航的巡线小车那后期换 TB6612 是合理升级但如果只是学习原理、调通逻辑、验证项目L298N 完全够用而且能让你把“电机控制”这件事理解得更扎实。1.3 项目场景与适用人群这个项目的适用人群非常广。一方面是想做智能小车、循迹小车、遥控小车的大学生或电子爱好者另一方面是刚刚接触单片机、还不清楚怎么用 GPIO 控制外部大功率设备的入门玩家。只要你手里有一块 Arduino UNO、树莓派、STM32、ESP32 或者其他任意支持输出高低电平的控制器都可以通过 L298N 来驱动直流电机。从扩展角度讲它的能力不止于“小车”。我做过的项目中就用 L298N 驱动过直流减速电机组成的云台、传送带模型、卷帘门机构、以及用两路输出组合驱动的四线步进电机。换句话说你掌握这个模块之后很多需要“双向可控”的中小型电机项目都能直接套用同样的思路。2. 硬件解析引脚定义、H 桥原理与供电逻辑2.1 模块引脚逐一说明拿到 L298N 模块先别急着接线我建议先把每个端子认清楚。常见模块的引脚布局大致如下12V 电源端子VMS/VIN接电机电源正极实际允许范围通常是 5V 到 35V 左右但具体要看模块上的电容耐压和你所使用电机的额定电压。GND 端子电机电源地也是整个系统的公共地。5V 输出/输入端子VSS/VS这个比较特殊当它跳线帽插着的时候是模块用内部稳压电路从电机电源那里取电输出 5V 供自身逻辑电路使用当跳线帽拔掉时这个端子可以当作外部 5V 输入口使用。ENA、ENB 使能端分别控制 A 路和 B 路的输出。默认跳线帽插着的时候通道一直处于使能状态电机只要 IN 有信号就转拔掉跳线帽后ENA/ENB 需要外部输入高电平或 PWM 信号这时才能用 PWM 调速。IN1、IN2控制 A 路电机的方向和状态。IN3、IN4控制 B 路电机的方向和状态。OUT1、OUT2接 A 路电机的两个接线端。OUT3、OUT4接 B 路电机的两个接线端。2.2 电源选择与 5V 跳线帽最容易炸的地方这里我要把 5V 跳线帽单独拎出来说因为这是我见过新手烧模块最多的地方。模块上那个小跳线帽默认是插在 5V 使能位置上的意思是让电路板从电机电源端子取电经过降压后给 L298 芯片的逻辑部分供电。这个设计本身没问题但有个前提电机电源电压不能太高一般建议不要超过 12V否则板载稳压芯片会严重发热甚至直接烧毁。更稳妥的做法是如果你的控制器比如 Arduino已经能提供稳定的 5V那就把跳线帽拔掉然后从控制器的 5V 引脚引一根线到模块的 5V 端子给逻辑电路单独供电。这样电机电源可以放心接 12V 甚至更高也不用担心稳压芯片过热。当然要注意如果从 Arduino 的 5V 取电给 L298N 逻辑部分那这个 5V 电的负载并不大只是逻辑电流几十毫安级别不会对 Arduino 造成什么压力。另外无论哪种供电方式都必须保证电机电源、模块控制逻辑、单片机三者共地。也就是说电机电源的 GND 必须和单片机的 GND 连在一起。没有共地控制信号就没有参考电平L298N 收到的 IN 信号就是悬空的电机自然不动。2.3 H 桥工作原理与 PWM 调速的关系为什么要用 H 桥而不是直接用一个三极管去开关电机因为直流电机需要双向控制你要让它正转、反转就需要改变电机两端电压的极性。H 桥的四个开关管刚好可以做到这一点打开左上和右下的开关电流从左边流向右边电机正转打开右上和左下的开关电流变成从右向左电机反转四个开关全关电机惯性滑行四个开关全开或者同侧两个同时打开相当于短路电机制动。实际模块上这些开关管都是集成在 L298 芯片内部的我们只需要通过 IN1、IN2 的高低电平组合去控制它。IN1 高、IN2 低电机正转IN1 低、IN2 高电机反转IN1、IN2 同为高或同为低电机停止。这里有个容易搞混的点为什么 IN1、IN2 都是高电平时不是正转因为 H 桥左右两侧同时打开会导致上下桥臂直通短路芯片内部逻辑会把它处理成停止状态所以在驱动直流电机时不要把两个 IN 同时置高。调速则通过 ENA 端口的 PWM 信号实现。PWM 的占空比决定了单位时间内电机两端有效电压的平均值。占空比越高平均电压越高电机转速越快。理论上PWM 频率越高电流越平滑但 L298N 内部的三极管开关特性决定了它不适合过高频率一般建议 1kHz 到 10kHz 之间。频率太高芯片发热严重频率太低会听到明显的“嘶嘶”声。3. 接线实操从 Arduino 到树莓派再到 STM323.1 Arduino UNO 平台接线最标准的入门方案如果你手头有 Arduino我建议从这里开始第一次实验。硬件准备如下L298N 模块一块直流减速电机两个带轮子的那种更好方便看见效果12V 电源一组如果电机是 12V 的Arduino UNO 一块杜邦线若干接线分四步。第一步把电机接到 OUT1、OUT2 和 OUT3、OUT4不需要管正负因为后面可以用代码翻转方向。第二步把电机电源接到模块的 12V 端子和 GND 端子。第三步用杜邦线把 Arduino 的 GND 接到模块的 GND这一步就是共地。第四步控制信号线Arduino D5 接 ENAD6 接 IN1D7 接 IN2D8 接 IN3D9 接 IN4D10 接 ENB。如果你的电机额定电压是 5V 或者 6V也可以不接外部电源直接从 Arduino 的 5V 和 GND 给模块供电前提是电机电流不要太大否则会拖垮 Arduino 板载稳压。我通常建议准备一个独立电源因为电机启动瞬间的电流经常能达到额定电流的 3 到 5 倍如果借用控制板电源很容易造成单片机复位。3.2 树莓派平台接线注意逻辑电平这个坑树莓派和 Arduino 最大的不同是它的 GPIO 输出高电平是 3.3V而 L298N 模块的逻辑高电平阈值一般接近 5V 的 TTL 电平。理论上 3.3V 也能被识别为高电平因为 TTL 高电平门槛大约在 2V 左右但实测中不同批次的模块表现不一致有的能正常驱动有的会偶尔抖动失效。为了稳妥起见我建议在树莓派和 L298N 之间加一个电平转换模块或者使用自带电平转换的驱动扩展板。如果你手头没有电平转换还有一个“土办法”把 L298N 的 VS 逻辑端子接到一个 5V 电源并且把 5V 电源的 GND 和树莓派的 GND 连在一起然后用 IN 引脚直接驱动试试。我的实测经验是大部分模块在这种情况下都能工作但如果你要跑正式项目还是别省这几十块钱。接线方面树莓派的树莓派 GPIO 编号方式有两种BOARD 和 BCM。建议统一用 BCM 编号因为 Python 代码里默认就是这种。我用的接法是树莓派 GPIO17 接 IN1GPIO18 接 IN2GPIO22 接 IN3GPIO23 接 IN4GPIO27 接 ENAGPIO24 接 ENB其中 GPIO18 是硬件 PWM 引脚但是 PWM 配置会涉及不同内核版本的问题我用的是软件 PWM后面代码部分再细说。3.3 STM32 平台接线从 CubeMX 到推挽输出STM32 接线逻辑和 Arduino 类似但有几个细节需要注意。首先是 GPIO 模式IN1 到 IN4 这些方向控制引脚要配置成推挽输出模式速度可以选低速就够了因为方向切换不是高频操作。ENA、ENB 如果没有用到硬件 PWM可以当作普通 GPIO 输出写高电平即可。如果要用硬件 PWM 调速那就需要把 ENA、ENB 接到 STM32 定时器的 PWM 输出通道。STM32 的不同定时器和引脚复用关系差异很大以 F103 系列为例TIM2 的 CH1 对应 PA0CH2 对应 PA1CH3 对应 PA2CH4 对应 PA3。你用 CubeMX 配置时直接在图形界面上选中对应引脚下拉菜单选 TIM2_CH1然后设置预分频和重载值频率和占空比就都出来了。电源方面STM32 开发板上的 5V 引脚可以为 L298N 的逻辑电路供电但同时要注意如果 L298N 驱动的电机电流较大开发板上 5V 的压降会非常明显甚至导致 STM32 自己复位。我建议电机电源独立逻辑 5V 也从开发板取电但前提是电机电源和逻辑电源的 GND 必须连在一起。你想想如果两个电源的负极不连那控制信号的高低电平就完全没有参考点就像两个人说中文和鸟语谁也听不懂谁。3.4 四线步进电机的接法扩展除了直流电机L298N 还可以驱动四线两相步进电机。接线方式是步进电机的 A、A- 接到 OUT1、OUT2B、B- 接到 OUT3、OUT4然后把 IN1、IN2、IN3、IN4 分别接到单片机的四个 GPIOEN 接入高电平。控制步进电机比直流电机复杂因为它不是简单地给 PWM 调速而是要按节拍给四个绕组通电产生旋转磁场。这样可以让电机精确地转过一定角度比如 1.8 度一步。不过说实话如果是专门做 3D 打印机或者 CNC 项目我更推荐用 A4988 或 TMC2209 这类专门驱动步进电机的模块它们内部集成了电流斩波和细分功能精度和噪音表现都好得多。但作为学习 H 桥和电机控制原理用 L298N 驱动步进电机是一种很好的“练手”方式。4. 代码实现三种主流平台的完整驱动示例4.1 Arduino 平台digitalWrite 控制方向analogWrite 控制速度Arduino 代码是所有平台里最容易上手的适合第一次接触电机控制的人。原理很简单IN1 和 IN2 组合决定方向ENA 的模拟值决定速度。模拟值范围 0 到 255对应 PWM 占空比 0% 到 100%。// L298N 电机驱动 - Arduino 示例代码 // 引脚定义 const int ENA 5; const int IN1 6; const int IN2 7; const int IN3 8; const int IN4 9; const int ENB 10; void setup() { pinMode(ENA, OUTPUT); pinMode(ENB, OUTPUT); pinMode(IN1, OUTPUT); pinMode(IN2, OUTPUT); pinMode(IN3, OUTPUT); pinMode(IN4, OUTPUT); } void motorA(int speed, bool forward) { digitalWrite(IN1, forward ? HIGH : LOW); digitalWrite(IN2, forward ? LOW : HIGH); analogWrite(ENA, speed); } void motorB(int speed, bool forward) { digitalWrite(IN3, forward ? HIGH : LOW); digitalWrite(IN4, forward ? LOW : HIGH); analogWrite(ENB, speed); } void loop() { motorA(200, true); // A 电机正转速度约 78% motorB(200, true); // B 电机正转 delay(3000); motorA(0, true); // 停止 motorB(0, true); delay(1000); motorA(150, false); // A 电机反转 motorB(150, false); delay(3000); motorA(150, true); // 左转A 正转B 反转 motorB(150, false); delay(2000); }我在这里特意用了一个函数封装而不是直接在 loop 里堆 digitalWrite因为封装之后形参 speed 和 forward 的意图非常清楚后续扩展成循迹小车时只需要把 sensor 的判断结果传给 motorA 和 motorB 就可以了。有一点要提醒Arduino 的 analogWrite 默认 PWM 频率是 980Hz 左右对于大部分直流减速电机来说是可以工作的但有些电机在低速时会出现明显的顿挫声。如果你想提高 PWM 频率可以通过修改定时器寄存器来实现但新手阶段不建议折腾先用默认频率把逻辑跑通再说。4.2 树莓派平台Python 脚本实现软加速与遥控控制树莓派上最常用的 Python 库是 RPi.GPIO 和 rpi_softpwm。我习惯用 RPi.GPIO 的 PWM 类因为它自带 start、ChangeDutyCycle、stop 这些方法控制起来非常顺滑。import RPi.GPIO as GPIO import time # BCM 编号模式 ENA 27 IN1 17 IN2 18 IN3 22 IN4 23 ENB 24 GPIO.setmode(GPIO.BCM) GPIO.setup(ENA, GPIO.OUT) GPIO.setup(ENB, GPIO.OUT) GPIO.setup(IN1, GPIO.OUT) GPIO.setup(IN2, GPIO.OUT) GPIO.setup(IN3, GPIO.OUT) GPIO.setup(IN4, GPIO.OUT) pwm_a GPIO.PWM(ENA, 1000) # PWM 频率 1kHz pwm_b GPIO.PWM(ENB, 1000) pwm_a.start(0) pwm_b.start(0) def motor_forward(speed): GPIO.output(IN1, GPIO.HIGH) GPIO.output(IN2, GPIO.LOW) GPIO.output(IN3, GPIO.HIGH) GPIO.output(IN4, GPIO.LOW) pwm_a.ChangeDutyCycle(speed) pwm_b.ChangeDutyCycle(speed) def motor_backward(speed): GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.HIGH) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.HIGH) pwm_a.ChangeDutyCycle(speed) pwm_b.ChangeDutyCycle(speed) def motor_stop(): GPIO.output(IN1, GPIO.LOW) GPIO.output(IN2, GPIO.LOW) GPIO.output(IN3, GPIO.LOW) GPIO.output(IN4, GPIO.LOW) pwm_a.ChangeDutyCycle(0) pwm_b.ChangeDutyCycle(0) try: while True: motor_forward(60) time.sleep(2) motor_stop() time.sleep(1) motor_backward(40) time.sleep(2) motor_stop() time.sleep(1) except KeyboardInterrupt: pass finally: pwm_a.stop() pwm_b.stop() GPIO.cleanup()这段代码中 PWM 频率设成了 1000Hz也就是 1kHz这个频率下 L298N 的发热和噪音相对均衡。你在实际运行时会发现树莓派上的软件 PWM 有一个特点占空比改变时电机的响应有一点延迟并且在 CPU 负载高时可能出现抖动。如果项目对实时性要求高建议改用树莓派的硬件 PWM也就是使用 12、13、18、19 这几个带硬件 PWM 功能的引脚配合 Device Tree 配置。我个人的习惯是在开发阶段先用软件 PWM 验证逻辑等到项目基本定型以后再切换到硬件 PWM 或者直接换一块 STM32 作为下位机树莓派只负责视觉和决策。4.3 STM32 平台HAL 库配置 PWM 与方向控制STM32 的代码结构相对复杂但核心逻辑和 Arduino 是一样的方向引脚控制高低电平PWM 输出控制速度。这里我给出一个基于 HAL 库的简化版假设你用 CubeMX 配置好了定时器 PWM。先说一下 CubeMX 的关键配置。假设用 TIM2 的 CH1 和 CH2 输出 PWM分别接 ENA 和 ENB那么初始化时要把 CH1、CH2 的模式选为 PWM Generation CH1、CH2然后设置 Prescaler 和 Period。例如你希望得到 1kHz 的 PWM系统时钟是 72MHz那么可以设 Prescaler 为 71Period 为 999这样 PWM 频率就是 72MHz /711/9991 1000Hz。// main.c 中关键代码片段 TIM_HandleTypeDef htim2; // 方向控制函数 void Motor_SetDirection(uint8_t forward) { if (forward) { HAL_GPIO_WritePin(IN1_GPIO_Port, IN1_Pin, GPIO_PIN_SET); HAL_GPIO_WritePin(IN2_GPIO_Port, IN2_Pin, GPIO_PIN_RESET); HAL_GPIO_WritePin(IN3_GPIO_Port, IN3_Pin, GPIO_PIN_SET); HAL_GPIO_WritePin(IN4_GPIO_Port, IN4_Pin, GPIO_PIN_RESET); } else { HAL_GPIO_WritePin(IN1_GPIO_Port, IN1_Pin, GPIO_PIN_RESET); HAL_GPIO_WritePin(IN2_GPIO_Port, IN2_Pin, GPIO_PIN_SET); HAL_GPIO_WritePin(IN3_GPIO_Port, IN3_Pin, GPIO_PIN_RESET); HAL_GPIO_WritePin(IN4_GPIO_Port, IN4_Pin, GPIO_PIN_SET); } } // 速度控制speed 范围 0~1000 void Motor_SetSpeed(uint16_t speed_a, uint16_t speed_b) { __HAL_TIM_SET_COMPARE(htim2, TIM_CHANNEL_1, speed_a); __HAL_TIM_SET_COMPARE(htim2, TIM_CHANNEL_2, speed_b); } // 主函数里先启动 PWM HAL_TIM_PWM_Start(htim2, TIM_CHANNEL_1); HAL_TIM_PWM_Start(htim2, TIM_CHANNEL_2); while (1) { Motor_SetDirection(1); Motor_SetSpeed(700, 700); HAL_Delay(3000); Motor_SetSpeed(0, 0); HAL_Delay(1000); Motor_SetDirection(0); Motor_SetSpeed(500, 500); HAL_Delay(3000); }这里有个细节我用 __HAL_TIM_SET_COMPARE 来设置比较寄存器比较值除以上一轮 Period 就得到占空比。如果你想要一个更平滑的调速过程可以在循环里逐渐增加比较值比如每隔 10 毫秒加 10这样电机就不会从静止猛地跳到全速对机械结构和电流冲击都更友好。4.4 通用小技巧软启动函数实现斜坡加速说到平稳调速我这里插入一个很实用的通用函数。无论你用哪个平台直接把电机从占空比 0 拉到 100%轮子都会瞬间打滑或者产生很大的电流冲击。更合理的做法是让速度以一个固定斜率逐步上升。// Arduino 风格的软启动函数 void softStart(int targetSpeed, unsigned long rampMs) { int currentSpeed 0; unsigned long stepDelay rampMs / targetSpeed; while (currentSpeed targetSpeed) { currentSpeed; analogWrite(ENA, currentSpeed); analogWrite(ENB, currentSpeed); delay(stepDelay); } }这个函数的思路简单粗暴把目标速度拆成很多小台阶每个台阶加 1然后延迟一小段时间。如果你用树莓派只要把 analogWrite 换成 pwm.ChangeDutyCycle 即可。我在实际调试中发现斜坡启动不仅能减少电流冲击还能让小车起步的方向更直因为两个轮子的启动时间差变小了。如果你的项目有“起步跑偏”的问题先别怀疑电机不对称多半是缺了软启动。5. 常见问题与排查技巧实录5.1 一台电机完全不转另一台正常这个问题的排查顺序是先看 OUT 端有没有接错、电机线是否松动然后看对应路的 ENA 跳线帽或者 PWM 信号是否正常最后再把两个电机的接线互换如果故障跟着电机走那就是电机本身坏了如果故障留在原来的输出口那就是模块那一路损坏。我踩过的坑是有一个客户拿来的模块A 路电机正常工作B 路怎么调都不转最后发现是 B 路的 OUT3 和 OUT4 插反了导致两个输出端被二极管钳位电机接收到的是很小的压差。所以接线时除了看颜色还要确认接线端子是否完全插紧。5.2 电机只能转一个方向反方向没反应如果电机正转正常、反转没反应优先检查 IN1 和 IN2 是否接反或者代码里 forward 参数是否传反了。还有一种情况是 IN1 和 IN2 都接到了同一个 GPIO 引脚上导致电平永远相同H 桥无法换向。你可以用万用表量一下两个引脚的电平正转时应该是一高一低如果两个都是高那就是接线问题。再有就是 L298N 模块上的 IN1 和 IN2 是否和通道 A 对应。有些模块的丝印不太清楚IN1、IN2 在左边OUT1、OUT2 在右边中间隔着芯片一不小心就接错通道。所以我每次接线后会先用代码做一次“左右互换测试”确认两个电机都能正反转再往下写业务逻辑。5.3 模块发热严重甚至冒烟模块发热的原因主要有这几个第一电机电源电压超过板载稳压电路的耐压也就是跳线帽还在的情况下接了 24V 甚至更高第二PWM 频率设置太高L298N 内部的开关管频繁切换损耗增加第三输出过载电机堵转时电流可能达到好几安培超过模块的极限。解决方法是逻辑 5V 用外接方式或拔掉跳线帽使用外部 5VPWM 频率控制在 1kHz 到 5kHz电机堵转检测加超时处理不要让电机长时间堵转。另外给模块加一个小的散热片也有效但治标不治本关键还是要控制电流。5.4 一启动电机单片机就死机或者复位这是最经典的问题原因几乎都是电源容量不足。电机启动的瞬时电流远大于额定电流如果你的电源同时给单片机和电机供电电压会被瞬间拉低到单片机的工作阈值以下于是单片机复位。处理思路有两个第一电机电源和单片机电源分开用独立电源给电机供电共用 GND。第二在电机电源输入端并联一个大容量电解电容比如 470uF 或 1000uF形成一个小的“蓄水池”在电机启动瞬间补充电流。我一般在模块的电源端放一个 470uF 的电解电容和一个 0.1uF 的瓷片电容一个吸收低频波动一个滤除高频噪声效果很稳定。5.5 PWM 调速没有效果电机要么全速要么停如果你发现电机的转速不受 PWM 占空比影响一上电就是全速那十有八九是 ENA 或者 ENB 跳线帽还在插着PWM 信号根本没进到模块的使能端通道被跳线帽强制置成使能状态。这种情况下IN 引脚的高低电平只负责方向电机要么全速转要么停完全不会调速。解决方法是拔掉 ENA 和 ENB 的跳线帽并把对应引脚的 PWM 信号接进去。还有一种情况是 PWM 信号接到了 IN 引脚而不是 ENA这样虽然也能部分调速但因为 IN 引脚内部逻辑同时控制方向和开关导致电机在低占空比时频繁启停声音难听转速也不稳。方向控制走 IN速度控制走 ENA尽量不要混用。5.6 快速排查速查表我把常见问题整理成一张表方便你调试的时候对照。现象可能原因处理方式电源灯亮但电机全不转公共地未连接检查所有 GND 是否相连单路不转该路 OUT 端子接触不良或 ENA 跳线帽没插重插电机线检查跳线帽只能正转不能反转IN1/IN2 接线或代码逻辑问题万用表检查两个 IN 电平是否一高一低无法调速只能全速或停止ENA/ENB 未接 PWM跳线帽未拔拔掉跳线帽输入 PWM 信号电机启动时单片机复位电源容量不足或共地不良独立电源加电解电容模块严重发热电压过高、PWM 频率过高、堵转过久外接逻辑电源降低频率加超时保护电机转但有明显异响PWM 频率过低把 PWM 频率提升到 1kHz 以上两个电机转速不一致左右电机负载不同或电源压降不同用软启动和闭环速度控制先检查机械阻力5.7 个人调试习惯分享最后分享一个我自己的调试习惯第一次拿到一套 L298N 和电机时我不会直接连单片机而是先用一节 9V 电池或者可调电源手动给 IN 引脚灌一个高电平看电机能不能转。这样能把“模块故障”和“代码故障”两个变量彻底分开。确认模块本身没问题之后再连单片机、跑程序。这个习惯看起来多了一步其实能省下大量排查时间。另外我会在连接控制线之前先给模块上电再把控制器的 GND 接到模块的 GND最后才插控制信号线。如果你拿着杜邦线在带电状态下乱插不小心碰到 12V 和 5V 引脚很容易烧掉控制器的 IO 口。顺序很反直觉但真的能保命。踩过几次坑之后我现在每个项目的电机控制代码里都会保留一个“自检模式”上电后先低速正转 1 秒、停止、反转 1 秒、停止确认每个通道都正常再进入正式工作流程。这样即使硬件出了问题也能在 5 秒内判断出是电机、模块、还是控制信号的问题。你把这个自检函数写到项目里后续调试会轻松很多。
返回列表