C51单片机利用LCD1602设计时钟

这篇博客介绍了如何使用C51单片机结合LCD1602显示器设计一个时钟,包括设计思路、LCD1602接口知识、编程代码实现以及遇到的问题和总结。在设计中,时钟上电即开始计时,通过按键K2控制计时和设置,K1用于60秒倒计时,K3和K4实现加减功能。文章还讨论了LCD1602的操作、初始化设置和常见错误处理。
摘要由CSDN通过智能技术生成

-设计思路
-知识积累
-编写代码
-总结

1. 设计思路
第一行显示年月日,第二行显示时间
上电之后计时开始,K2控制分秒设置,按第一次计时停止秒针闪烁,按第二次分针闪烁,按第三次计时继续,K3,K4分别控制加减(只有在按键K2按下后生效),在计时过程中可以实现整分报时,K1转换成60秒倒计时

2. 知识积累

  1. LCD1602

(1)LCD1602接口信号说明

VSS:电源地信号引脚;
VDD:电源信号引脚;
VEE:液晶对比度调节引脚,接0~5V以调节液晶的显示对比度;
RS:寄存器选择引脚:
RS = 1时为数据寄存器;
RS = 0时为指令寄存器;
RW:读写选择引脚:
RW = 1时,选择读操作;
RW = 0时,选择写操作;
E:读写操作选择引脚,下降沿时,数据被写入1602液晶,E= 1时,对1602液晶进行读数据操作;
D0~D7:数据总线引脚;
LEDA:背光电源引脚;
LEDK:背光电源地引脚;

(2)LCD1602的基本操作分为四种:

1)读状态:输入RS=0,RW=1,E=高脉冲。输出:D0—D7为状态字。
2)读数据:输入RS=1,RW=1,E=高脉冲。输出:D0—D7为数据。
3)写命令:输入RS=0,RW=0,E=高脉冲。输出:无。<

以下是使用C51单片机LCD1602显示屏实现的电子时钟代码: ```c #include <reg52.h> #include <intrins.h> #define uchar unsigned char #define uint unsigned int sbit RS = P2^6; sbit EN = P2^5; uchar code table[]={ 0x38, 0x0c, 0x01, 0x06, 0x0f, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x80, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x0c, 0x18, 0x30, 0x60, 0xc0, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; uchar time[] = {0x00,0x00,0x00,0x00,0x00,0x00}; //时分秒 void delayms(uint x) { uint i, j; for(i=x; i>0; i--) { for(j=112; j>0; j--); } } void write_com(uchar com) { RS = 0; P0 = com; delayms(5); EN = 1; delayms(5); EN = 0; } void write_data(uchar dat) { RS = 1; P0 = dat; delayms(5); EN = 1; delayms(5); EN = 0; } void init_lcd() { uchar i; write_com(0x38); //设置16*2显示,5×7点阵,8位数据接口 write_com(0x0c); //显示开,关光标,不闪烁 write_com(0x06); //数据写入后,光标自动加1 write_com(0x01); //清除光标位置的字符 delayms(20); for(i=0; i<128; i++) { write_data(table[i]); //初始化显示数据 } } void display_time() { uchar i; uchar display_hour, display_minute, display_second; //要显示的时分秒 uchar display_year, display_month, display_day; //要显示 uchar tmp; //调整时间格式 if(time[0] < 10) { display_hour = time[0]; } else { display_hour = time[0] - 10; display_hour |= 0x80; //设置高位是1 } if(time[1] < 10) { display_minute = time[1]; } else { display_minute = time[1] - 10; display_minute |= 0x80; //设置高位是1 } if(time[2] < 10) { display_second = time[2]; } else { display_second = time[2] - 10; display_second |= 0x80; //设置高位是1 } //显示,这里只显示份的后两位 display_year = time[3] % 100; //取百位和十位 display_month = time[4]; display_day = time[5]; //设置光标位置 write_com(0x80+0x40); //显示时分秒 write_data(display_hour); write_data(':'); write_data(display_minute); write_data(':'); write_data(display_second); //设置光标位置 write_com(0x80); //显示 if(display_year < 10) { write_data('0'); } tmp = display_year / 10; write_data(tmp + '0'); tmp = display_year % 10; write_data(tmp + '0'); write_data('/'); if(display_month < 10) { write_data('0'); } tmp = display_month / 10; write_data(tmp + '0'); tmp = display_month % 10; write_data(tmp + '0'); write_data('/'); if(display_day < 10) { write_data('0'); } tmp = display_day / 10; write_data(tmp + '0'); tmp = display_day % 10; write_data(tmp + '0'); } void get_time() { uchar i; uchar second, minute, hour, day, month, year; second = minute = hour = day = month = year = 0; //读取DS1302芯片中的时间数据 write_com(0x8e); //写入读操作命令 for(i=0; i<7; i++) { P0 = 0x81 + i * 2; delayms(5); EN = 1; delayms(5); EN = 0; P0 = 0x80 + i * 2; delayms(5); EN = 1; delayms(5); time[i] = P0 >> 4; time[i] = (time[i] << 4) + (P0 & 0x0f); EN = 0; //转换BCD码为十进制数 if(i == 0) { second = time[i] & 0x7f; second = (second >> 4) * 10 + (second & 0x0f); } else if(i == 1) { minute = time[i] & 0x7f; minute = (minute >> 4) * 10 + (minute & 0x0f); } else if(i == 2) { hour = time[i] & 0x3f; hour = (hour >> 4) * 10 + (hour & 0x0f); } else if(i == 3) { day = time[i] & 0x3f; day = (day >> 4) * 10 + (day & 0x0f); } else if(i == 4) { month = time[i] & 0x1f; month = (month >> 4) * 10 + (month & 0x0f); } else if(i == 6) { year = time[i]; year = (year >> 4) * 10 + (year & 0x0f); } } //调整时间,将DS1302取到的时间转换为标准格式 time[0] = hour; time[1] = minute; time[2] = second; time[3] = year; time[4] = month; time[5] = day; } void main() { init_lcd(); while(1) { get_time(); display_time(); } } ``` 这段代码中使用了DS1302时钟芯片来获取当前时间,并将时间显示LCD1602显示屏上。需要注意的是,这里只显示份的后两位,如果需要显示完整的份,可以将相应的代码进行修改。同时,如果使用的是其他型号的LCD显示屏,需要对应修改初始化和显示的命令。
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值