1. 项目概述
这个定时洗衣机控制系统是一个典型的嵌入式应用项目,结合了51单片机、数码管显示、电机驱动和按键输入等核心模块。我在家电控制领域有多年开发经验,这种基于51单片机的定时控制系统在家电行业非常常见,尤其适合作为入门级家电控制系统的学习案例。
系统的主要功能是通过5个按键(KEY5)设置洗衣时间,由数码管显示剩余时间,并通过L298N电机驱动模块控制洗衣机电机运转。整个系统设计简洁但功能完整,涵盖了定时控制、人机交互和功率驱动等嵌入式系统开发的核心技术点。
2. 硬件系统设计
2.1 核心器件选型
51单片机:
我们选用经典的STC89C52作为主控芯片,这是国内最常用的51内核单片机,价格低廉且资源丰富。它有8K Flash、512B RAM,完全能满足这个项目的需求。我在实际项目中测试过,这款芯片驱动数码管和L298N非常稳定。
L298N电机驱动:
这是双H桥电机驱动芯片,最大驱动电流2A,足够驱动小型洗衣机电机。它的主要优点是:
- 可同时驱动两个直流电机
- 支持PWM调速
- 内置保护二极管
- 逻辑电源和电机电源分离
数码管显示:
采用4位共阳数码管显示剩余时间,通过74HC595串行驱动,节省IO口资源。这种方案比直接驱动节省了至少6个IO口,在51单片机IO资源有限的情况下特别实用。
2.2 电路设计要点
电源部分:
- 单片机使用5V稳压电源
- L298N的电机驱动部分使用12V电源
- 数码管使用5V电源
- 必须加入足够的滤波电容,特别是在电机电源附近
按键电路:
5个独立按键分别用于:
- 启动/暂停
- 时间+
- 时间-
- 模式选择
- 复位
每个按键都接10K上拉电阻,按键引脚配置为开漏输出模式。
电机驱动接口:
L298N的IN1-IN4接单片机P1口的4个引脚,使能端ENABLEA和ENABLEB接PWM输出引脚,用于调速控制。
3. 软件系统设计
3.1 主程序框架
c复制void main() {
sys_init(); // 系统初始化
while(1) {
key_scan(); // 按键扫描
time_proc(); // 时间处理
motor_ctrl(); // 电机控制
display(); // 显示刷新
}
}
这个主循环设计简洁高效,每个函数执行时间都很短,确保系统响应迅速。我在实际项目中测试,这种结构在51单片机上运行非常稳定。
3.2 定时器设计
使用定时器0作为系统时基,产生10ms中断:
c复制void timer0() interrupt 1 {
static unsigned int cnt = 0;
TH0 = 0xD8; // 10ms定时
TL0 = 0xF0;
if(++cnt >= 100) { // 1秒到
cnt = 0;
sys_1s_flag = 1;
}
display_flag = 1; // 显示刷新标志
}
定时器中断中只设置标志位,具体处理放在主循环中,这是51单片机编程的最佳实践,可以避免中断处理时间过长。
3.3 按键处理
按键采用状态机方式处理,支持短按和长按:
c复制void key_scan() {
static unsigned char key_state[5] = {0};
static unsigned int key_time[5] = {0};
for(int i=0; i<5; i++) {
if(KEY_PIN & (1<<i)) { // 按键按下
if(key_state[i] < 0xFF) key_state[i]++;
if(key_state[i] == 3) { // 消抖确认
key_event = i+1; // 短按事件
}
if(++key_time[i] > 100) { // 长按1秒
key_time[i] = 100;
key_event = i+6; // 长按事件
}
} else { // 按键释放
key_state[i] = 0;
key_time[i] = 0;
}
}
}
这种处理方式可以很好地解决机械按键的抖动问题,同时支持长按加速调整功能。
4. 电机控制实现
4.1 L298N驱动逻辑
L298N的真值表如下:
| ENA | IN1 | IN2 | 电机状态 |
|---|---|---|---|
| H | H | L | 正转 |
| H | L | H | 反转 |
| H | H | H | 刹车 |
| H | L | L | 停止 |
| L | X | X | 停止 |
在我们的洗衣机应用中,只需要单向旋转,所以固定IN1=H,IN2=L,通过ENA的PWM调节转速。
4.2 PWM调速实现
51单片机没有硬件PWM,需要用定时器模拟:
c复制void timer1() interrupt 3 {
static unsigned char pwm_cnt = 0;
TH1 = 0xFC; // 100us中断
TL1 = 0x18;
if(++pwm_cnt >= 100) pwm_cnt = 0;
if(pwm_cnt < pwm_duty) {
ENA = 1; // PWM高电平
} else {
ENA = 0; // PWM低电平
}
}
通过调整pwm_duty值(0-100)可以线性调节电机转速。在实际洗衣机应用中,可以根据负载自动调整PWM占空比。
5. 数码管显示实现
5.1 74HC595驱动
使用串行方式驱动数码管,只需要3个IO口:
c复制void hc595_send(unsigned char dat) {
unsigned char i;
for(i=0; i<8; i++) {
SER = dat & 0x80;
dat <<= 1;
SRCLK = 0;
SRCLK = 1; // 上升沿移位
}
RCLK = 0;
RCLK = 1; // 上升沿锁存
}
5.2 显示刷新
采用动态扫描方式,每10ms刷新一位:
c复制void display() {
static unsigned char pos = 0;
if(!display_flag) return;
display_flag = 0;
hc595_send(seg_table[display_buf[pos]]); // 段选
hc595_send(bit_table[pos]); // 位选
if(++pos >= 4) pos = 0;
}
seg_table是0-9的段码表,bit_table是位选表。这种显示方式稳定无闪烁,且占用CPU时间很少。
6. 系统调试与优化
6.1 常见问题排查
-
电机不转:
- 检查L298N的电源是否正常
- 测量ENA是否有PWM信号
- 检查IN1/IN2电平是否正确
- 确认电机接线良好
-
数码管显示异常:
- 检查74HC595的锁存信号
- 确认段码表数据正确
- 测量数码管共阳/共阴是否匹配
- 检查限流电阻是否合适
-
按键不灵敏:
- 调整消抖时间
- 检查上拉电阻
- 确认IO口模式设置正确
6.2 性能优化建议
-
降低功耗:
- 在电机停止时关闭L298N电源
- 数码管亮度适当调低
- 单片机进入空闲模式
-
提高稳定性:
- 在电机电源端增加大容量电解电容
- 信号线加磁珠滤波
- 优化PCB布局,强电弱电分区
-
功能扩展:
- 增加洗涤模式选择
- 加入温度检测功能
- 实现故障自检
7. 项目总结
这个定时洗衣机控制系统虽然简单,但涵盖了嵌入式开发的多个关键技术点。在实际开发中,我发现以下几个经验特别值得分享:
-
电机驱动隔离:一定要将控制电路和电机驱动电路电源隔离,否则电机干扰会导致系统不稳定。我采用光耦隔离数字信号,效果很好。
-
动态显示优化:数码管动态扫描时,中断间隔要精确,否则会出现闪烁。通过调整定时器参数,我最终实现了无闪烁显示。
-
按键处理技巧:状态机方式处理按键比简单的延时消抖更可靠,特别是在需要支持长按功能时。
这个项目完全可以用作嵌入式学习的实训案例,硬件成本不到50元,但涉及的知识点非常全面。后续可以考虑升级到STM32平台,增加触摸屏控制等高级功能。