基于AT89C51单片机的电子表设计.docx
- 文档编号:6392775
- 上传时间:2023-01-06
- 格式:DOCX
- 页数:13
- 大小:99.65KB
基于AT89C51单片机的电子表设计.docx
《基于AT89C51单片机的电子表设计.docx》由会员分享,可在线阅读,更多相关《基于AT89C51单片机的电子表设计.docx(13页珍藏版)》请在冰豆网上搜索。
基于AT89C51单片机的电子表设计
基于AT89C51单片机的电子表设计
黄河科技学院课程设计任务书
工学院机械系机械设计制造及其自动化专业11级3班
学号1101110035姓名席世琦指导教师朱煜钰
题目:
基于AT89C51单片机的电子表设计
课程:
单片机应用技术课程设计
课程设计时间2014年10月27日至2014年11月10日共2周
课程设计工作内容与基本要求(设计要求、设计任务、工作计划、所需相关资料)(纸张不够可加页)
1.设计要求
利用AT89C51单片机作为微控制器,在数码管通过一个控制键转换来显示相应的时间和日期,能通过多个控制键用来实现时间和日期的调节。
2.设计任务与要求
2.1系统硬件电路设计
根据该系统设计的功能要求选择所用元器件,设计硬件电路。
要求用Proteus绘制整个系统电路原理图。
2.2软件设计
根据该系统要求的功能进行软件设计,绘制整个系统的软件流程图;根据流程图编写程序并汇编调试通过;列出软件清单,软件清单要求逐条加以注释。
2.3Proteus仿真
用Proteus对系统软硬件进行仿真调试并通过。
2.4编写设计说明书
内容包括任务书、设计方案分析、硬件部分设计、软件部分设计、调试结果整理分析、设计调试的心得体会等,字数不少于5000字;硬件部分设计要绘制整个系统电路原理图,对各部分电路设计原理做出说明;软件设计部分要(用visio2003画图软件)绘制整个系统及各部分的软件流程图,列出程序清单,逐条加以注释,并注明各程序功能块的功能。
3.工作计划
序号
设计内容
所用时间
1
布置任务及调研
4天
3
制作与调试
8天
4
撰写设计报告书
2天
合计
14天
4.主要参考资料
单片机课程设计指导书皮大能北京理工大学出版社2012.7
8051单片机实践与应用吴金戎清华大学出版社2003.8
单片机技术基础教程与实践夏路易电子工业出版社 2008.1
单片机原理及应用张毅刚高等教育出版社2012.11
基于Proteus的单片机系统设计与仿真实例蒋辉平机械工业出版社
2007.7
…
指导老师签字:
日期:
一、电子表
1.1电子表简介
1957年,Ventura发明了世界上第一个电子表,从而奠定了电子表的基础,电子表开始迅速发展起来。
现代的电子表是基于单片机的一种计时工具,采用延时程序产生一定的时间中断,用于一秒的定义,通过计数方式进行满六十秒分钟进一,满六十分小时进一,满二十四小时小时清零。
从而达到计时的功能,是人民日常生活补课缺少的工具。
1.2电子表的原理
该电子表由AT89C51,74LS373,BUTTON,数码管等构成,采用晶振电路作为驱动电路,由延时程序和循环程序产生的一秒定时,达到时分秒的计时,六十秒为一分钟,六十分钟为一小时,满二十四小时为一天,满三十天(闰年二月满二十九天,平年二月满二十八天)为一个月,满十二个月为一年。
电路中的键控1实现“年”和“分”的调节,键控2实现“月”和“时”的调节,键控3实现“日”和“分”的调节。
每按一次就加一。
二、控制系统的硬件设计
2.1单片机型号的选择
通过对多种单片机性能的分析,最终认为89C51是最理想的电子时钟开发芯片。
89C51是一种带4K字节闪烁可编程可擦除只读存储器的低电压,高性能CMOS8位微处理器,器件采用ATMEL高密度非易失存储器制造技术制造,与工业标准的MCS-51指令集和输出管脚相兼容。
由于将多功能8位CPU和闪烁存储器组合在单个芯片中,ATMEL的89C51是一种高效微控制器,而且它与MCS-51兼容,且具有4K字节可编程闪烁存储器和1000写/擦循环,数据保留时间为10年等特点,是最好的选择。
2.2数码管显示工作原理
数码管是一种把多个LED(7SEG-MP*8-CA-BLUE)显示段集成在一起的显示设备。
有两种类型,一种是共阳型,一种是共阴型。
共阳型就是把多个LED显示段的阳极接在一起,又称为公共端。
共阴型就是把多个LED显示段的阴极接在一起,即为公共商。
阳极即为二极管的正极,又称为正极,阴极即为二极管的负极,又称为负极。
通常的数码管又分为8段,即8个LED显示段,这是为工程应用方便如设计的,分别为A、B、C、D、E、F、G、DP,其中DP是小数点位段。
而多位数码管,除某一位的公共端会连接在一起,不同位的数码管的相同端也会连接在一起。
即,所有的A段都会连在一起,其它的段也是如此,这是实际最常用的用法。
数码管显示方法可分为静态显示和动态显示两种。
静态显示就是数码管的8段输入及其公共端电平一直有效。
动态显示的原理是,各个数码管的相同段连接在一起,共同占用8位段引管线;每位数码管的阳极连在一起组成公共端。
利用人眼的视觉暂留性,依次给出各个数码管公共端加有效信号,在此同时给出该数码管加有效的数据信号,当全段扫描速度大于视觉暂留速度时,显示就会清晰显示出来。
共阴数码管
2.374LS373介绍:
373为三态输出的八D透明锁存器,373的输出端O0~O7可直接与总线相连。
当三态允许控制端OE为低电平时,O0~O7为正常逻辑状态,可用来驱动负载或总 线。
当OE为高电平时,O0~O7呈高阻态,即不驱动总线,也不为总线的负载,锁存器内部的逻辑操作不受影响。
当锁存允许端LE为高电平时,O随数据D而变。
当LE为低电平时,O被锁存在已建立的数据电平。
当LE端施密特触发器的输入滞后作用,使交流和直流噪声抗扰度被改善400mV。
引出端符号:
D0~D7数据输入端;OE三态允许控制端(低电平有效;LE锁存允许端;O0~O7输出端
图374LS373
2.4系统硬件电路设计
三、控制系统的软件设计
3.1软件设计
程序清单
#include
#include
sbitP20=P2^0;/****定义端口****/
sbitkhour=P3^0;
sbitkmin=P3^1;
sbitknian=P3^2;
sbittiaonian=P3^3;
sbitspeaker=P3^7;
intj=-1;/*****定义变量,j用以控制扫描********/
bitflag=0,leap=0;/*****定义flag控制时分秒和年月日的显示,leap判断是否为闰年***/
charsecshi=0,secge=0,minshi=0,minge=0,hourshi=0,hourge=0;
chardayshi=0,dayge=0,monthshi=0,monthge=0,yearshi=0,yearge=0;
unsignedintnum=0,sec=0,min=0,hour=0;/****设置初始时间为00时0分0秒****/
unsignedintday=1,month=1,year=10;/****设置初始日期为2010年1月1日****/
charsaomiao[8]={0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80};
/****扫描数组,控制位选******/
charshijian[10]={0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90};
/*******共阴数码管的0,1,2,3,4,5,6,7,8,9********/
voiddelay(unsignedintz)/*******延时子程序******/
{unsignedintx,y;
for(x=z;x>0;x--)
for(y=10;y>0;y--);
}
voidtimer()interrupt1/*********定时器中断0********/
{
TH0=(65535-5000)/256;/******重新装入初值*****/
TL0=(65535-5000)%256;
num++;
j++;
if((year%4==0&&year%100!
=0)||(year%400==0))/*******判断是否为闰年******/
leap=1;/*******闰年,使leap=1******/
else
leap=0;/*******平年,使leap=0******/
if(num==150)/*****实验微调得num=150时大概为1s******/
{num=0;
sec++;/****秒自动加1*****/
}
if(sec==60)
{
sec=0;
min++;/****60s时,分自动加1,秒归0*****/
}
if(min==60)
{
min=0;
hour++;/****60分时,小时自动加1,分归0*****/
}
if(hour==24)
{
hour=0;
min=0;
sec=0;
day++;/****24时,天自动加1,时分秒归0*****/
}
/*************************************************************************************************************************************************************************月份的判断,平年时的2月和闰年时的2月,以及30天和31天的判断**************************************************************************************************************************************************************/
if((leap==1&&month==2&&day==30)||(leap==0&&month==2&&day==29))
{
day=1;
month++;/*****2月28天或29天时月自加1*****/
}
if(month==1||month==3||month==5||month==7||month==8||month==10||month==12)
{
if(day==32)
{
day=1;
month++;/*****月为31天达到时月自动加1*****/
}
}
if(month==4||month==6||month==9||month==11)
{
if(day==31)
{
day=1;
month++;/*****月为30天达到时月自动加1*****/
}
}
if(month==13)
{
year++;
month=1;/*********新的一年的开始**********/
}
secge=sec%10;
secshi=sec/10;
minge=min%10;
minshi=min/10;
hourge=hour%10;
hourshi=hour/10;
dayge=day%10;
dayshi=day/10;
monthge=month%10;
monthshi=month/10;
yearge=year%10;
yearshi=year/10;
P1=saomiao[j];/*******数码管的位选设置*********/
if(flag==1)/*******flag=1,显示年月日*******/
{
if(P1==0x80)P2=shijian[dayge];
if(P1==0x40)P2=shijian[dayshi];
if(P1==0x20)P2=0xbf;/******年与月之间的分隔符"-"的显示*****/
if(P1==0x10)P2=shijian[monthge];
if(P1==0x08)P2=shijian[monthshi];
if(P1==0x04)P2=0xbf;/******月与天之间的分隔符"-"的显示*****/
if(P1==0x02)P2=shijian[yearge];
if(P1==0x01)P2=shijian[yearshi];
}
else/*******flag=0,显示时分秒*******/
{
if(P1==0x80)P2=shijian[secge];
if(P1==0x40)P2=shijian[secshi];
if(P1==0x20)P2=0xbf;
if(P1==0x10)P2=shijian[minge];//xianshi
if(P1==0x08)P2=shijian[minshi];
if(P1==0x04)P2=0xbf;
if(P1==0x02&&hour<24)P2=shijian[hourge];/*****显示小时0~23*****/
if(P1==0x01&&hour<24)P2=shijian[hourshi];
}
if(j==7)
{
j=-1;
}
}
voidtimer1()interrupt0
/*************************************************************************************************************************************************************外部中断0,设置标志flag,按键未按下,flag=0,显示时分秒,按键按下,flag=1,显示年月日*************************************************************************************************************************************************************/
{
flag=!
flag;/******按下knian按钮****flag=1,x显示年月日*******/
}
voidcontrol()/*******时分的调整子程序********/
{
if(flag==0)/****显示时分秒的情况下做时分的调整******/
{if(kmin==0)
{
min++;
while(kmin==0);
if(min==60)
min=0;
}
if(khour==0)
{
hour++;
//sec=0xc0;
while(khour==0);
if(hour>23)
hour=0;
}
}
if(flag==1)/********显示年月日的情况下做年月日的调整**********/
{
if(kmin==0)
{
day++;
while(kmin==0);
}
if(khour==0)
{
month++;
while(khour==0);
if(month>12)
month=1;
}
if(tiaonian==0&&speaker==1)
{
year++;
while(tiaonian==0);
}
}
}
voidbaoshi()/******整点报时子程序********/
{
if(min==0&&sec<10)/*****整点闹钟响,响10秒*****/
{
speaker=0;
delay
(1);
speaker=1;
}
else
speaker=1;
}
voidalarm()/******闹钟子程序*******/
{
bitring=1;
charxx=10;
if(tiaonian==0)
{
ring=0;
delay(100);
while(tiaonian==0);/******关闭正在叫的闹钟*****/
}
if(hour==6&&min==xx&&ring==1)/*******闹钟按时鸣叫1分钟******/
{
speaker=0;
delay
(1);
speaker=1;
}
if(hour==6&&min==xx+1)/*****1分钟后闹钟停止鸣叫*******/
{
speaker=1;
}
}
voidmain()
{
TMOD=0x01;/*******设置工作方式******/
TR0=1;
P2=0;
TH0=(65535-5000)/256;/******装入计时初值*****/
TL0=(65535-5000)%256;
IE=0x82;
IP=0x00;/*******设置中断优先级*****/
EA=1;
EX0=1;/****开外部中断0******/
while
(1)
{
control();
alarm();
baoshi();
}
}
3.2Proteus仿真
图5.a时间仿真图(此时时间为2点8分31秒)
图5.b日期仿真图(此时日期为2010年9月3日)
四、心得
进过不懈的努力,我们顺利完成了这次单片机课程设计课题中的个性化电子表设计,
本次仿真总的来说是实现了预期的效果,但是喇叭把的效果不是很好。
功能还不够完善,设计还比较简单。
不过通过此次设计我们还是学会了不少东西。
首先,学会了keil和proteus软件。
然后,由于此次程序是用C语言编写的,以前的C语言知识的到了巩固。
同时,我们还领悟到了团队精神的真谛。
通过这次的设计使我认识到本人对单片机方面的知识知道的太少了,对于书本上的很多知识还不能灵活运用,尤其是对程序设计语句的理解和运用,不能够充分理解每个语句的具体含义
总的来说,本次的设计使我从中学到了最重要的东西,那就是如何从理论到实践的转化,怎样将我所学到的知识运用到我以后的工作中去。
在大学的课堂的学习只是在给我们灌输专业知识,而我们应把所学的用到我们现实的生活中去,此次的电子时钟设计给我奠定了一个实践基础,我会在以后的学习、生活中磨练自己,使自己适应于以后的竞争,同时在查找资料的过程中我也学到了许多新的知识,在和同学协作过程中增进同学间的友谊,使我对团队精神的积极性和重要性有了更加充分的理解。
最后,我觉得应该感谢朱煜钰老师在平时课堂上的启发。
使得我们在课程设计过程中,巩固和学习了单片机知识。
相信这对我以后的课程设计和毕业设计将会有很大的帮助!
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 基于 AT89C51 单片机 电子表 设计