项目介绍
基于电位器的模拟调速系统:使用一个摇杆电位器作为输入,实时无级地控制电机的速度和方向。
硬件介绍
本项目基于以下核心硬件构建了一个直观的模拟调速控制系统:
主控平台:NXP FRDM-MCXA153开发板
核心为MCXA153系列微控制器,基于高效的Arm® Cortex®-M33内核。
板载Arduino R3兼容接口,便于扩展。
集成USB调试与供电接口,内置CMSIS-DAP调试器,开发便捷。
驱动模块:Adafruit Motor Shield V2
采用TB6612 MOSFET驱动芯片,支持双路直流电机。
通过I2C接口(默认地址0x60)与主控板通信,节省I/O资源。
提供稳定的电机电源管理及保护。
输入设备:旋转电位器(10kΩ)
作为模拟输入设备,将旋转角度转换为连续的电压信号。
连接到开发板的模拟输入引脚,实现无级调速。
功能概览
系统利用摇杆电位器作为速度与方向指令的输入源。通过实时读取电位器输出的模拟电压值,将其映射为电机的控制参数,最终实现对单个直流电机的无级调速与正反转控制。整个系统运行平滑,响应迅速,直观地演示了模拟信号采集、数据处理与电机驱动控制的完整流程。
设计思路
设计核心在于将连续的模拟输入映射为离散的电机控制命令,关键思路如下:
信号采集:利用MCXA153内部的ADC(模数转换器)模块,将电位器输出的0-3.3V模拟电压转换为数字值(例如0-1023)。
控制策略:
速度控制:ADC采样值直接对应PWM(脉宽调制)的占空比。采样值越大,占空比越高,电机转速越快。
方向控制:在ADC量程中间设置一个“死区”。当采样值高于死区上限时,电机正转;低于死区下限时,电机反转;位于死区内时,电机停止。这有效避免了因电位器微小抖动导致的误动作。
电机驱动:通过I2C协议将计算出的PWM占空比与方向指令发送给Adafruit Motor Shield,由其内部的TB6612芯片执行安全、高效的电机驱动。
功能实现软件流程图

硬件连接:
1. 电位器两端分别接3.3V与GND,中间引脚接MCXA153的A0(ADC0_A8)引脚。
2. Motor Shield堆叠在MCXA153的Arduino接口上。
3. 直流电机连接至Motor Shield的M4端口。
4. 外部电源(如7-12V)接入Motor Shield的电源端子,为电机供电。

核心代码逻辑(关键步骤):
// 1. 初始化ADC,与ADC中断处理函数
/**
* @brief LPADC中断处理函数
* @details 当ADC转换完成并将结果放入FIFO时,会触发此中断
*/
void DEMO_LPADC_IRQ_HANDLER_FUNC(void) {
// 中断计数器加1,记录中断发生次数
g_LpadcInterruptCounter++;
// 当LPADC只有1个FIFO时,直接获取结果
if (LPADC_GetConvResult(ADC0, &g_LpadcResultConfigStruct)) {
// 设置转换完成标志,通知主循环可以处理结果
g_LpadcConversionCompletedFlag = true;
}
// SDK中断退出屏障,确保中断处理完成
SDK_ISR_EXIT_BARRIER;
}
// 2. 主循环
while(1) {
// 等待转换完成
if (g_LpadcConversionCompletedFlag){
// 打印ADC转换结果和中断计数
if(g_FreeTurnState) { // 自由调节状态,根据中位值计算方向和速度
int16_t adcValue = (g_LpadcResultConfigStruct.convValue) >> g_LpadcResultShift;
uint8_t adcSpeed = map(adcValue, 0, g_LpadcFullRange, 0, 255);
uint8_t midValue = 176; // 中位值,根据实际情况调整
// 计算速度与中位值的差值,大于0表示顺时钟转,小于0表示逆时钟转,等于0表示停止。正负10以内表示停止
uint8_t diffValue = 0;
uint8_t speed = 0;
if (adcSpeed > (midValue + 10)) {
// 逆时钟转
diffValue = adcSpeed - (midValue + 10);
speed = map(diffValue, 0, (255 - midValue - 10), 50, 255);
g_MotorRunningState = true;
task2(MOTOR_DIR_BACKWARD, speed);
} else if (adcSpeed < (midValue - 10)) {
// 顺时钟转
diffValue = (midValue - 10) - adcSpeed;
speed = map(diffValue, 0, (midValue - 10), 50, 255);
g_MotorRunningState = true;
task2(MOTOR_DIR_FORWARD, speed);
} else if (g_MotorRunningState) {
// 停止
g_MotorRunningState = false;
task2(MOTOR_DIR_RELEASE, 0);
}
}
// 重置转换完成标志
g_LpadcConversionCompletedFlag = false;
// 触发软件转换(1U是触发0的掩码)
LPADC_DoSoftwareTrigger(ADC0, 1U);
}
}关键点:map函数实现了输入到输出的线性映射;死区的设置提高了控制稳定性。
功能展示
系统上电后,操作直观:
正向加速
向前缓慢推动摇杆电位器。当推动过中间停止点(有明显阻力感)后,电机开始正转。随着继续推动摇杆,电机转速平滑、线性地增加,直至最高速。

反向加速
向后缓慢推动摇杆电位器。同样经过中间停止点后,电机反转,转速随旋转角度增大而平滑增加。

精确停止
松开摇杆电位器时,摇杆自动回到机械中点附近时,电机可靠停止,无明显抖动或蠕动,得益于软件死区的设置。

实时响应
摇杆电位器的任何角度变化,电机转速都能在毫秒级内做出对应调整,实现了真正的实时无级调速。

演示视频
总结
本项目成功构建了一个基于模拟输入的直流电机调速系统。它充分运用了 NXP FRDM-MCXA153 的模拟信号采集能力、Adafruit Motor Shield V2的集成驱动优势以及电位器的直观交互特性,实现了稳定、平滑、双向的电机速度控制。
技术要点总结:
模拟信号处理:掌握了MCU ADC模块的使用,实现了连续模拟量到数字量的精准转换。
控制算法设计:通过“死区”和线性映射策略,将单一模拟输入优雅地解耦为速度与方向两个控制维度,提升了系统鲁棒性。
硬件协作:熟练运用I2C总线控制外围驱动模块,体现了模块化开发的高效性。
本系统作为一个基础平台,可轻松扩展,例如增加第二个电位器控制另一台电机实现差速转向,或移植到更复杂的机器人底盘控制中,具有很好的实践教学价值与工程参考意义。
传送门
【2025 Let's do 第4期】基于单片机的直流电机控制开箱帖
【2025 Let's do 第4期】基于单片机的直流电机控制过程贴
参考资料
https://www.nxp.com.cn/document/guide/getting-started-with-frdm-mcxa153:GS-FRDM-MCXAXX
https://akizukidenshi.com/goodsaffix/FRDM-MCXA153_User Manual.pdf
https://learn.adafruit.com/adafruit-motor-shield-v2-for-arduino
我要赚赏金
