当前位置:文档之家› 单片机课程设计--篮球记分牌

单片机课程设计--篮球记分牌

单片机课程设计报告题目篮球记分牌学院自动化与电气工程学院专业自动化班级自动化103学号学生姓名指导教师完成日期2012年12月15日篮球记分牌一.设计要求:1、比赛开始,比分能够全部清零,数码管前2位、末2位做记分用,当中2位做24秒倒计时用。

2、24秒倒计时时间到,蜂鸣器响、指示灯亮,重新开始倒计时,蜂鸣器停止鸣叫、指示灯灭。

3、比分进行增加后,倒计时从24秒重新开始倒计时。

任意时刻24秒可以重新开始倒计时。

必要时候能够关闭倒计时。

4、利用AT24C02或者单片机内部资源保存比分,支持复位保存,掉电保存功能。

5、其他附加功能。

二.原理图:三.实验流程图:四.实验程序:Main.c文件:/****************************************************************************** ***************函数名:篮球记分牌说明:比赛开始,比分能够全部清零,数码管前2位、末2位做记分用,当中2位做24秒倒计时用。

24秒倒计时时间到,蜂鸣器响、指示灯亮,重新开始倒计时,蜂鸣器停止鸣叫、指示灯灭。

比分进行增加后,倒计时从24秒重新开始倒计时。

任意时刻24秒可以重新开始倒计时。

必要时候能够关闭倒计时。

作者:完成日期:2012.12.2/****************************************************************************** ****************/#include<stc12c5a60s2.h>#include <intrins.h>#include"eeprom.h"#define uchar unsigned char#define uint unsigned int/***********端口定义*************//*数码管段选用P0口,位选用P2口*//******指示灯******/sbit LED=P3^4;/********蜂鸣器*********/sbit FMQ=P3^5;/******数组定义*******/uchar codetable[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x07f,0x6f};//0,1,2,3,4,5,6,7, 8,9uchar password[6]; //掉电保存6位数组/***********变量定义*************/uchar fen1; //甲队初始得分uchar fen2; //乙队初始得分uchar fen3; //甲乙两队上下半场换分uchar SJ; //时间变量值uchar cxjs=1; //重新计时标志位uchar key; //矩阵键盘按键值uchar temp; //矩阵键盘P1口寄存变量uchar time; //中断计数器/***********************************************************函数名称:delay函数功能:基本延时程序入口参数:无出口参数:无备注:无***********************************************************/void delay(uchar x){ uchar j;while((x--)!=0){ for(j=0;j<125;j++){;}}}/*********************************************************** 函数名称:display函数功能:数码管显示程序入口参数:fen1,fen2,SJ出口参数:无备注:无***********************************************************/ void display(void){uchar m;for(m=6;m>0;m--){delay(2);if(m==6){P2 = 0XFE;P0 = table[fen1/10];}if(m==5){P2 = 0XFD;P0 = table[fen1%10];}if(m==4){P2 = 0XFB;P0 = table[SJ/10];}if(m==3){P2 = 0XF7;P0 = table[SJ%10];}if(m==2){P2 = 0XEF;P0 = table[fen2/10];}if(m==1){P2 = 0XDF;P0 = table[fen2%10];}}}/*********************************************************** 函数名称:keyscan函数功能:4X4矩阵键盘扫描程序入口参数:无出口参数:无备注:读取的键值赋给了key***********************************************************/ void keyscan(void){temp=P1;if(temp!=0xf0){delay(120);if(temp!=0xf0){P1=0xfe;temp=P1;delay(120);switch(temp){case(0xee):key=0;break;case(0xde):key=1;break;case(0xbe):key=2;break;case(0x7e):key=3;break;}P1=0xfd;temp=P1;delay(120);switch(temp){case(0xed):key=4;break;case(0xdd):key=5;break;case(0xbd):key=6;break;case(0x7d):key=7;break;}P1=0xfb;temp=P1;delay(120);switch(temp){case(0xeb):key=8;break;case(0xdb):key=9;break;case(0xbb):key=10;break;case(0x7b):key=11;break;}P1=0xf7;temp=P1;delay(120);switch(temp){case(0xe7):key=12;break;case(0xd7):key=13;break;case(0xb7):key=14;break;case(0x77):key=15;break;}}}}/*********************************************************** 函数名称:keydown函数功能:4X4矩阵键盘判断程序入口参数:无出口参数:无备注:判断是否有按键按下***********************************************************/ void keydown(void){P1=0xF0;if(P1!=0xF0){delay(150); //消抖if(P1!=0xF0){ keyscan();}}}/*********************************************************** 函数名称:timer0init函数功能:定时器初始化部分程序入口参数:无出口参数:无备注:设置定时器0工作方式***********************************************************/ void timer0init(){TMOD &= 0xf0; //定时器0工作方式1TMOD |= 0x01;}/*********************************************************** 函数名称:timer0函数功能:中断服务程序入口参数:无出口参数:无备注:此程序无调用***********************************************************/void timer0 (void) interrupt 1 using 0{TH0=0x15;TL0=0xa0;time=time+1;if(time==20){time=0;SJ=SJ-1;if(SJ==0){SJ=0;EA=0;FMQ=0;LED=0;}}}/***********************************************************函数名称:setpassword函数功能:掉电保存程序入口参数:无出口参数:无备注:此程序调用eeprom_eares擦除扇区程序,eeprom_write字节编程程序***********************************************************/void setpassword(){eeprom_eares(0x0000);eeprom_write(0x0000,fen1/10);eeprom_write(0x0001,fen1%10);eeprom_write(0x0002,SJ/10);eeprom_write(0x0003,SJ%10);eeprom_write(0x0004,fen2/10);eeprom_write(0x0005,fen2%10);}/***********************************************************函数名称:getpassword函数功能:读出eeprom内存储值入口参数:无出口参数:无备注:无***********************************************************/void getpassword(){uchar i;for(i=0;i<6;i++)password[i]=eeprom_read(i);}/***********************************************************函数名称:main函数功能:主程序入口参数:无出口参数:无备注:实现功能:通过按键开始/停止,暂停/继续计时和对甲乙两队的加分***********************************************************/void main(){LED=1;FMQ=1;P2=0xFF;P1=0xF0;SJ=24;fen1=0;fen2=0;key=16;/*定时器设置*/timer0init();ET0=1;TR0=1;while(1){display();keydown();if(key==0) //开始按键{EA=1;}if(key==1) //甲队加分按键{fen1=fen1+1;cxjs=0;}if(key==2) //乙队加分按键{fen2=fen2+1;cxjs=0;}if(key==3) //暂停计时{EA=0;}if(key==4) //停止按键{fen1=0;fen2=0;SJ=24;EA=0;FMQ=1;LED=1;}if(key==5) //上下半场换分{fen3=fen1;fen1=fen2;fen2=fen3;}if(cxjs==0) //重新计时{SJ=24;cxjs=1;}if(key==6) //保存当前值{setpassword();}if(key==7) //调用前次记录{getpassword();fen1=password[0]*10+password[1];SJ=password[2]*10+password[3];fen2=password[4]*10+password[5];EA=0;}key=16; //此处赋值key,否则key将一直保留按键后的值 }}Eeprom.c文件:#define eeprom#include"eeprom.h"//-------------------------------------------------------------------------------------------------------//EEPROM操作//------------------------------------------------------------------------------------------------------//定义Flash 操作等待时间及允许IAP/ISP/EEPROM 操作的常数//#define ENABLE_ISP 0x80 //系统工作时钟<30MHz 时,对IAP_CONTR 寄存器设置此值//#define ENABLE_ISP 0x81 //系统工作时钟<24MHz 时,对IAP_CONTR 寄存器设置此值#define ENABLE_ISP 0x82 //系统工作时钟<20MHz 时,对IAP_CONTR 寄存器设置此值//#define ENABLE_ISP 0x83 //系统工作时钟<12MHz 时,对IAP_CONTR 寄存器设置此值//#define ENABLE_ISP 0x84 //系统工作时钟<6MHz 时,对IAP_CONTR 寄存器设置此值//#define ENABLE_ISP 0x85 //系统工作时钟<3MHz 时,对IAP_CONTR 寄存器设置此值//#define ENABLE_ISP 0x86 //系统工作时钟<2MHz 时,对IAP_CONTR 寄存器设置此值//#define ENABLE_ISP 0x87 //系统工作时钟<1MHz 时,对IAP_CONTR 寄存器设置此值union union_temp16{unsigned int un_temp16;unsigned char un_temp8[2];}my_unTemp16;unsigned char eeprom_read(unsigned int add); //读一字节,调用前需打开IAP 功能void eeprom_write(unsigned int add, unsigned char ch); //字节编程,调用前需打开IAP 功能void eeprom_eares(unsigned int add); //擦除扇区void IAP_Disable(); //关闭IAP 功能void IAP_Disable(){//关闭IAP 功能, 清相关的特殊功能寄存器,使CPU 处于安全状态,//一次连续的IAP 操作完成之后建议关闭IAP 功能,不需要每次都关IAP_CONTR = 0; //关闭IAP 功能IAP_CMD = 0; //清命令寄存器,使命令寄存器无命令,此句可不用IAP_TRIG = 0; //清命令触发寄存器,使命令触发寄存器无触发,此句可不用IAP_ADDRH = 0;IAP_ADDRL = 0;}//读一字节,调用前需打开IAP 功能,入口:DPTR = 字节地址,返回:A = 读出字节unsigned char eeprom_read(unsigned int add){IAP_DATA = 0x00;IAP_CONTR = ENABLE_ISP; //打开IAP 功能, 设置Flash 操作等待时间IAP_CMD = 0x01; //IAP/ISP/EEPROM 字节读命令my_unTemp16.un_temp16 = add;IAP_ADDRH = my_unTemp16.un_temp8[0]; //设置目标单元地址的高8 位地址IAP_ADDRL = my_unTemp16.un_temp8[1]; //设置目标单元地址的低8 位地址//EA = 0;IAP_TRIG = 0x5A; //先送 5Ah,再送A5h 到ISP/IAP 触发寄存器,每次都需如此IAP_TRIG = 0xA5; //送完A5h 后,ISP/IAP 命令立即被触发起动_nop_();//EA = 1;IAP_Disable(); //关闭IAP 功能, 清相关的特殊功能寄存器,使CPU 处于安全状态, //一次连续的IAP 操作完成之后建议关闭IAP 功能,不需要每次都关return (IAP_DATA);}//字节编程,调用前需打开IAP 功能,入口:DPTR = 字节地址, A= 须编程字节的数据void eeprom_write(unsigned int add, unsigned char ch){IAP_CONTR = ENABLE_ISP; //打开 IAP 功能, 设置Flash 操作等待时间IAP_CMD = 0x02; //IAP/ISP/EEPROM 字节编程命令my_unTemp16.un_temp16 = add;IAP_ADDRH = my_unTemp16.un_temp8[0]; //设置目标单元地址的高8 位地址IAP_ADDRL = my_unTemp16.un_temp8[1]; //设置目标单元地址的低8 位地址IAP_DATA = ch; //要编程的数据先送进IAP_DATA 寄存器//EA = 0;IAP_TRIG = 0x5A; //先送 5Ah,再送A5h 到ISP/IAP 触发寄存器,每次都需如此IAP_TRIG = 0xA5; //送完A5h 后,ISP/IAP 命令立即被触发起动_nop_();//EA = 1;IAP_Disable(); //关闭IAP 功能, 清相关的特殊功能寄存器,使CPU 处于安全状态, //一次连续的IAP 操作完成之后建议关闭IAP 功能,不需要每次都关}//擦除扇区, 入口:DPTR = 扇区地址void eeprom_eares(unsigned int add){IAP_CONTR = ENABLE_ISP; //打开IAP 功能, 设置Flash 操作等待时间IAP_CMD = 0x03; //IAP/ISP/EEPROM 扇区擦除命令my_unTemp16.un_temp16 = add;IAP_ADDRH = my_unTemp16.un_temp8[0]; //设置目标单元地址的高8 位地址IAP_ADDRL = my_unTemp16.un_temp8[1]; //设置目标单元地址的低8 位地址//EA = 0;IAP_TRIG = 0x5A; //先送 5Ah,再送A5h 到ISP/IAP 触发寄存器,每次都需如此IAP_TRIG = 0xA5; //送完A5h 后,ISP/IAP 命令立即被触发起动_nop_();//EA = 1;IAP_Disable(); //关闭IAP 功能, 清相关的特殊功能寄存器,使CPU 处于安全状态, //一次连续的IAP 操作完成之后建议关闭IAP 功能,不需要每次都关}//-------------------------------------------------------------------------------------------------------Eeprom.h文件:#ifndef _eeprom_h_#define _eeprom_h_#ifdef eeprom#include<stc12c5a60s2.h>#include"intrins.h"#define EXET#else#define EXET extern#endif//typedef unsigned char INT8U;//typedef unsigned int INT16U;EXET unsigned char eeprom_read(unsigned int add); //读一字节,调用前需打开IAP 功能EXET void eeprom_write(unsigned int add, unsigned char ch); //字节编程,调用前需打开IAP 功能EXET void eeprom_eares(unsigned int add); //擦除扇区#endif五.实验仿真:六.实验实物图:七.实验总结:通过这次单片机课程设计,我学到了很多东西。

相关主题