STM8单片机课程设计报告(闹钟+定时器)_第1页
STM8单片机课程设计报告(闹钟+定时器)_第2页
STM8单片机课程设计报告(闹钟+定时器)_第3页
STM8单片机课程设计报告(闹钟+定时器)_第4页
STM8单片机课程设计报告(闹钟+定时器)_第5页
已阅读5页,还剩11页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、课程设计内容与要求课程设计目的:1、巩固和加深对单片机原理知识的理解和运用。2、进一步提高学生综合运用所学知识的能力。3、培养学生综合分析问题、发现问题和解决问题的能力基本要求:1) 显示时间和日期2) 可设置多个闹钟3) 可以调整时间扩展功能:1) 按键复用 共有六个按键,每个按键在不同模式下有不同的功能。2) 秒表功能 进入秒表界面后,再按一下就秒表开始计时,再按一下秒表停止。3) 省电模式 在每天00:00会自动进入省电模式,8个数码管会自动关闭,到5:00时会自动退出省电模式;也可以手动进入和退出省电模式。4) 查看/删除闹钟 查看闹钟时间为五秒,五秒内按键无动作则自动退出。器件介绍本

2、次设计主要用到的硬件有:1、51实验板1块2、stm8s105c6开发板1快51实验板:主要用到实验板上的硬件有:1) 两个四位一体的共阴LED数码管,电路图如下:2)两个74HC573的锁存芯片:3)8个独立按键,用了其中6个5) 一个蜂鸣器:Stm8s105c6开发板:总共有48个引脚,本设计共用引脚20个引脚。PB0PB7和PE6PE7用于数码管显示控制,PD0PD5用于键盘输入,PD6、 PE0、PE3用于LED指示灯控制。PD7用于蜂鸣器控制。设计方案本次设计采用51实验板和stm8s105c6开发板来完成,没有做实物。显示电路采用8个共阳数码管显示;控制按键采用六个独立按键,每一个

3、按键都有复用功能;闹钟提醒采用蜂鸣器;外加四个不同颜色的LED发光二极管,当进入相应功能模式时对应的指示灯就会亮。1、键盘设计:在键盘电路中,使用的是6个独立键盘。键盘在源程序中的功能安排如下:1)当扫描到有键盘按下时,设置相应标志位,然后延时一定时间消抖。2)键盘的设置键盘表面如图:OkEsc其中各键设置为:(待机状态:正常的时间显示模式)待机状态下是“设置闹钟”,在其他模式下是“递增功能”待机状态下是“调整时间”,在其他模式下是“递减功能”。 待机状态下是“秒表功能”,在其他模式下是“左移功能”。 待机状态下是“查看/删除闹钟”,在其他模式下是“右移功能”OK 待机状态下是“切换显示”,在

4、省电模式下是“退出功能”,在其他模式下是“确认功能”Esc 待机状态下是“省电模式”,在查看/删除闹钟模式下是“删除功能”,在其他模式下是“退出功能”2、数码管显示:采用按位扫描的动态显示方式。3、其他设计:定时器使用stm8s105c6中的Tim2定时器,每1ms产生一次溢出中断。闹铃响的时间为15秒。查看/删除闹钟模式下,5s内键盘无动作则自动退出。每次按键按下后,会延时240ms,此时间内不会再对键盘进行扫描。在每天00:00会自动进入省电模式,8个数码管会自动关闭,到5:00时会自动退出省电模式;也可以手动进入和退出省电模式。4、设计思路:开始初始化引脚和Tim2定时器调用时间处理函数

5、闹铃响闹钟时间? 是 否扫描键盘闹钟设置位=1?是时间调整位=1? 否 是调用相应功能函数 否秒表功能位=1? 是 否查看闹钟位=1? 是 否显示切换位=1?显示日期 是 是 否显示时间5、以下是部分程序:/*标志位*/_Bool off;/省电模式_Bool tab;/切换显示模式_Bool run;/控制秒表_Bool left;/左移_Bool right;/右移_Bool set;/设置闹钟_Bool adjust;/调整时间_Bool ok;/确定_Bool esc;/取消或删除_Bool duan PE_ODR:7; /PE6作为段锁存_Bool wei PE_ODR:6; /PE

6、7作为位锁存_Bool set_c PE_ODR:3;_Bool adjust_t PE_ODR:0;_Bool check_clock PD_ODR:6;_Bool c_alarm PD_ODR:7;/*相关变量*/unsigned char month_day=31,28,31,30,31,30,31,31,30,31,30,31;unsigned char wei_ma=0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f;/显示位码unsigned char duan_ma=0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7

7、f,0x6f; /共阴极显示段码unsigned char sec_duan_ma=0xbf,0x86,0xdb,0xcf,0xe6,0xed,0xfd,0x87,0xff,0xef;unsigned char hour_5,minute_5,second_5=1,2,3,4,5;/用于秒表unsigned char sec_time8;/用于秒表unsigned char clocks58;/可存5个闹钟信息unsigned char times8;/存放当前时间unsigned char days8;/存放当前日期unsigned int T1=1000;/200x10ms=1s秒计算un

8、signed int T2=0;/20x10ms=200msunsigned char c=0;/用于记录闹钟个数unsigned char hour=8,minute=55,second;unsigned char month=12,day=12;int year=2011;unsigned char *ud;/ud加减指针unsigned char lr;/记录指针所指位char A,B,C,D,E,F,G,H,I,J,K,L;int T3=0,T4=0;/其他定时,闹钟显示和蜂鸣器int sec1,sec2;/用于秒表的变量/*函数声明*/unsigned char leapyear(i

9、nt b);/闰年判断void TIM2_initial(void);/初始化定时器void GPIO_initial(void);/初始化I/O引脚void display(unsigned char x8);/时间显示函数void time_process(void);/时间处理函数void times_bi_duan_ma(unsigned char,unsigned char,unsigned char);void days_bi_duan_ma(int,unsigned char,unsigned char);void keyscan(void);/键盘扫描函数void set_cl

10、ock(void);/设置闹钟void adjust_times(void);/void clock_display(void);/闹钟显示函数void alarm(void);void second_clock(void);/*主函数*/main()GPIO_initial();TIM2_initial();leapyear(year);while(1)time_process();alarm();if(T2=0)/消抖,延时100mskeyscan();if(hour=0&minute=0&second=0)off=1;if(hour=5&minute=0&

11、second=0)off=0;if(set=0&adjust=0&left=0&right=0&ok=0&off=1) PB_ODR=0xff;/不显示时间,省电模式wei=1;wei=0;else if(set=1&adjust=0)/设置闹钟模式 set_c=0;set_clock(); else if(set=0&adjust=1)/调整时间模式 adjust_t=0;adjust_times();else if(left=1)/秒表模式second_clock();else if(right=1)/查看/删除闹钟模式check_c

12、lock=0; clock_display();else if(tab=0) times_bi_duan_ma(hour,minute,second); display(times);/时间显示 else if(tab=1)days_bi_duan_ma(year,month,day); display(days); /*秒表函数*/void second_clock(void)if(sec1=999)sec1=999;sec_time0=0x00; sec_time1=0x00; sec_time2=0x00; sec_time3=duan_masec1/100; sec_time4=dua

13、n_masec1%100/10; sec_time5=sec_duan_masec1%10; sec_time6=duan_masec2/10;/小数位 sec_time7=duan_masec2%10;/小数位display(sec_time);if(esc=1) left=0;run=0;sec1=0; sec2=0;esc=0;/*闹钟设置*/void set_clock(void)unsigned char i,j; display(times);if(lr=0)ud=&G;/指针指向Gif(lr=1)ud=&H;if(lr=3)ud=&I;if(lr=4)ud

14、=&J;if(lr=6)ud=&K;if(lr=7)ud=&L;timeslr=duan_ma*ud;/*ud即是ud所指变量的当前值if(ok=1)hour_c=G*10+H;minute_c=I*10+J;second_c=K*10+L;if(c=4)c=0;else c+;set=0;ud=0;lr=0;right=0;left=0;ok=0;set_c=1;/*校时函数*/void adjust_times(void)if(ok=0)display(days);if(lr=0)ud=&A;if(lr=1)ud=&B;if(lr=3)ud=&

15、;C;if(lr=4)ud=&D;if(lr=6)ud=&E;if(lr=7)ud=&F;dayslr=duan_ma*ud;if(ok=1)display(times);if(lr=0)ud=&G;if(lr=1)ud=&H;if(lr=3)ud=&I;if(lr=4)ud=&J;if(lr=6)ud=&K;if(lr=7)ud=&L;timeslr=duan_ma*ud;if(esc=1&ok=1)year=2000+A*10+B;month=C*10+D;day=E*10+F;hour=G*10+H;minu

16、te=I*10+J;second=K*10+L;ok=0;esc=0;lr=0;ud=0;adjust=0;T1=100;adjust_t=1;/*时间处理函数*/void time_process(void) if(second>=60) /秒到60,分钟加1 second=0; minute+; if(minute>=60)/分钟到60,小时加1 minute=0; hour+; if(hour>=24)/小时到24,回零 hour=0; leapyear(year);/闰、平年计算if(day>=month_daymonth-1)/是否到了每月的最后一天 day=

17、1;if(month>=12) month=1; year+; else month+;else day+; /*时间数据的转换*/void times_bi_duan_ma(unsigned char hour,unsigned char minute,unsigned char second)G=hour/10;H=hour%10;I=minute/10;J=minute%10;K=second/10;L=second%10; times0=duan_maG; /时/数据的转换,因我们采用数码管09的显示,将数据分开 times1=duan_maH; times2=0x40; /加入

18、"-" times3=duan_maI;/分 times4=duan_maJ; times5=0x40; times6=duan_maK;/秒 times7=duan_maL; /*日期数据的转换*/ void days_bi_duan_ma(int year,unsigned char month,unsigned char day) A=(year%100)/10);B=(year%100)%10); C=month/10;D=month%10; E=day/10;F=day%10; days0=duan_maA;/年 days1=duan_maB; days2=0x4

19、0; days3=duan_maC;/月 days4=duan_maD; days5=0x40; days6=duan_maE;/日 days7=duan_maF; /*时间显示函数*/void display(unsigned char time8)unsigned char a=0,i;while(a<8)PB_ODR=0x00;/确保清除之前的数据,防止重影duan=1;duan=0;if(set=1|adjust=1)&a=lr&T1<=50)PB_ODR=0xff;/指针所指的位闪烁elsePB_ODR=wei_maa;wei=1;wei=0; PB_OD

20、R=timea+; duan=1; duan=0; for(i=100;i>0;i-);/延时a=0;/*查看/删除闹钟函数*/void clock_display(void)unsigned char a=0,i;times_bi_duan_ma(hour_lr,minute_lr,second_lr);display(times);if(esc=1)esc=0;for(i=0;i<8;i+)hour_lr=0; minute_lr=0; second_lr=lr+1; if(T3=0)right=0;/5s内键盘无输入,切换到原来的显示模式/*键盘扫描函数*/void keys

21、can(void)T2=241;/延时241ms,消抖if(PD_IDR&0x01)=0x00)/加或设置闹钟按键if(set=1|adjust=1)/闹钟或校时模式下if(*ud=9)*ud=0;else(*ud)+;/ud所指的变量加1else /正常显示模式下 set=1; esc=0;ok=0; else if(PD_IDR&0x02)=0x00)/减或调整时间if(set=1|adjust=1)/闹钟或校时模式下if(*ud=0)*ud=9;else(*ud)-;/ud所指的变量减1else /正常显示模式下 adjust=1;esc=0;ok=0;else if(P

22、D_IDR&0x04)=0x00)/左移/查看闹钟if(set=1|adjust=1)/闹钟或校时模式下lr-;if(lr=255)lr=7; else if(lr=5)lr=4;/跳过第3和6个数码管 else if(lr=2)lr=1;else if(right=1)/查看闹钟模式下T3=5000; if(lr=0)lr=4;else lr-;else if(left=1)run=run1;/为1时秒表开始计时else left=1;esc=0;ok=0;else if(PD_IDR&0x08)=0x00)/右移/查看闹钟if(set=1|adjust=1)/闹钟或校时模式

23、下lr+;if(lr=8)lr=0;/跳过第3和6个数码管 else if(lr=2)lr=3;else if(lr=5)lr=6;else if(right=1)/查看闹钟模式下T3=5000; if(lr=4)lr=0;else lr+;else right=1;T3=5000;esc=0;ok=0;else if(PD_IDR&0x10)=0x00)/确定off=0;/退出省电模式 tab=tab1;if(ok=0)ok=1;else if(ok=1&adjust=1)esc=1;else if(PD_IDR&0x20)=0x00)/取消删除或进入省电模式if(a

24、djust=1|set=1)set=0; ok=0; lr=0; ud=0; adjust=0;set_c=1; adjust_t=1; check_clock=1; else if(set=0&adjust=0&left=0&right=0) off=1;ok=0;else esc=1;else 1;调试过程因为此次程序比较大,实现的功能比较多,所以从一开始我便一个功能一个功能的做,边做边调试,做完一个功能之后才做下一个。第一次做数码管显示的时候就出现问题,8个数码管一直显示乱码。当时我就把程序用原来的动态显示改为静态显示,可是还是不行。于是我就再把8个数码管同时显示改为一个数码管显示,这下就可以了。然后我又再把显示的位数慢慢增加,当增加到第5位的时候发现,乱码又来了,之后我又改用其他引脚,发现原来之前写的程序时没有错的,是因为芯片的一个引脚出问题了,不知道为什么,那个引脚总是高电平。所以才导致了之前的乱码一直出来。数码管调试好之后,其他的程序调试起来就顺利多了,在用到蜂鸣器的时候还遇到了一个问题。因为之前课程设计做蜂鸣器电路的时候都是做

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论