51单片机秒表、定时器大作业

#include 

//定义段选数组
unsigned char code seg[] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90}; //数码管显示
char a[10][6]; //记录的数据
char b[6]; //各个位的预设值

//定义全局变量
char choice, sec, min, secs;
char key_1, key_2, key_3, key_4,key_5,key_6,key_7;
char Mode,num=0,flag1=0,i=0,full,flag3,flag2,i,j;
/*********************************************************
 choice:选位
 sec,min,secs:分 秒 毫秒
 key_x:按键相应情况
 Mode:选择的功能
 num:记录的数据编号
 flagx:标记功能完成情况
 full:查询是否完成倒计时录入情况
 i:查询哪一位
**********************************************************/

//定义按键
sbit key1 = P3 ^ 0; //开始
sbit key2 = P3 ^ 1; //暂停
sbit key3 = P3 ^ 4; //归零
sbit key4 = P3 ^ 5; //记录
sbit key5 = P3 ^ 6;  //上一条
sbit key6 = P3 ^ 7;  //下一条
sbit fm = P3 ^ 3;    //蜂鸣器



//定义延迟函数
void delay(unsigned int x)
{
    while (x--);
}

//初始化函数
void start()
{
    //总控
    EA = 1;
    //分控
    ET0 = 1;
    EX0 = 1;
    IT0 = 1;
    //设置TMOD
    TMOD = 0x01;
    //填充初始值
    TH0 = 0xd8;
    TL0 = 0xf0;
    //启动
    TR0 = 1;
	fm=0;
}

//定义按键函数
void key()
{
    //启动
    if (key1 == 0)
    {
        //消抖
        delay(500);
        if (key1 == 0) key_1 = 1;
    }
    //如果按键曾经按下过并且现在抬起了
    if (key1 == 1 && key_1 == 1)
    {
        key_1 = 0;      
        Mode = 1;
    }

    //暂停
    if (key2 == 0)
    {
        delay(500);
        if (key2 == 0) key_2 = 1;
    }
    if (key2 == 1 && key_2 == 1)
    {
        key_2 = 0;
        Mode = 2;
    }

    //清零
    if (key3 == 0)
    {
        delay(500);
        if (key3 == 0) key_3 = 1;
    }
    if (key3 == 1 && key_3 == 1)
    {
        key_3 = 0;
        //清零时暂停秒表
        Mode = 3;
        secs = 0;
        sec = 0;
        min = 0;
			for(j=0;jnum){
            i=0;
        }
        key_5=0;
    }
    //查询上一条
    if(key_6 ==0){
        delay(500);
        if(key6==0) key_6=1;
    }
    if(key6==1&&key_6==1){
        Mode=5;
        i--;
        if(i<0){
            i=num;
        }
        key_6=0;
    }

}



//显示函数
void display()
{
    //清屏
    P0 = 0xff;
    switch (choice)
    {
	    case 0:
	        P0 = seg[secs % 10];
	        P2 = 0x01;
	        break;
	    case 1:
	        P0 = seg[secs / 10];
	        P2 = 0x02;
	        break;
	    case 2:
	        P0 = seg[sec % 10] & (0x7f);
	        P2 = 0x04;
	        break;
	    case 3:
	        P0 = seg[sec / 10];
	        P2 = 0x08;
	        break;
	    case 4:
	        P0 = seg[min % 10] & (0x7f);
	        P2 = 0x10;
	        break;
	    case 5:
	        P0 = seg[min / 10];
	        P2 = 0x20;
	        break;
    }
    choice++;
    if (choice >= 6)
        choice = 0;
}

//矩阵键盘函数
void KKEY()		
{	
		char a=0;
        char sum=0;					
		P1=0x0f;				//开始列扫描,从高位到底位
		if(P1!=0x0f&&flag3==0)		//是有按键被按下,
		{
				delay(1000);//消抖
				if(P1!=0x0f&&flag3==0)
				{
                        flag2=1;
						switch(P1)//对应列高电平变为低电平
						{
							case 0x07:sum=0;break;
							case 0x0b:sum=1;break;
							case 0x0d:sum=2;break;
							case 0x0e:sum=3;break;
						}
						P1=0xf0;	//列扫描完毕,现在开始行扫描
						switch(P1)//按照顺序,被按下的引脚会变成低电平,依次来判断哪一行被按下。
						{
							case 0x70:sum=sum;b[full]=sum;full++;flag3=1;break; 
							case 0xb0:sum=sum+4;b[full]=sum;full++;flag3=1;break;
							case 0xd0:sum=sum+8;b[full]=sum;full++;flag3=1;break;
							case 0xe0:sum=sum;b[full]=sum;full++;flag3=1;break;
						}
				}
		}
        //flag2表示被按下,当被按下,并且抬起来。,
        if(flag2==1&&P1==0x0f){
            flag2=0;
            flag3=0;             //其中flag3==1表示按下,flag3表示已经抬起来
        }
		
}



//设置时间中断函数
void time() interrupt 1
{
    //填充初始值
    TH0 = 0xd8; //10ms
    TL0 = 0xf0;
    if(Mode==1) //1正计时
    secs++;
    if(Mode==7) //7倒计时
    secs--;
}

void ex0() interrupt 0{
	fm=0;//蜂鸣器初始化
    Mode=7;
  
    secs=0;
    sec=0;
    min=0;
    full=0;
    b[0]=0;
    b[1]=0;
    b[2]=0;
    b[3]=0;
    b[4]=0;
    b[5]=0;
    while(1){
        //录入char b[6]
            KKEY();
            //显示数字
            P0 = 0xff;
	          P0 = seg[b[0]];
	          P2 = 0x01;
		        delay(1000);     //延长显示时间
						P0 = 0xff;
						P0 = seg[b[1]];
						P2 = 0x02; 
						delay(1000);
						P0 = 0xff;
						P0 = seg[b[2]]& (0x7f);
						P2 = 0x04;
						delay(1000);
            P0 = 0xff;
						P0 =seg[b[3]];
            P2 = 0x08;
  	        delay(1000);
						P0 = 0xff;		
						P0 = seg[b[4]]& (0x7f);
            P2 = 0x10;
            delay(1000);
						P0 = 0xff;	  
						P0 = seg[b[5]];
						P2 = 0x20;
						delay(1000);
						if(full==6){
								secs=b[1]*10+b[0];
								if(b[3]<6) sec=b[3]*10+b[2];
								else sec=(b[3]%6)*10+b[2];
								if(b[3]<6) min=b[5]*10+b[4];
								else min=b[5]*10+b[4]+1;
								break;		
						}
    }
		
}

//主函数
void main()
{
    //调用初始化函数
    start();
    while (1)
    {
        //调用按键函数
        key();
        if(Mode==1){
            display();
            
            if (secs > 99)
            { 
                secs = 0;
                sec++;
            }
            if (sec > 59)
            {
                sec = 0;
                min++;
            }
            if (min > 99)
                min = 0;
        }
        if(Mode==2){
            display();
        }
        if(Mode==3){
            secs = 0;
            sec = 0;
            min = 0;
            display();
        }
        //查询
        if(Mode==5){
            	P0 = 0xff;
	            P0 = seg[a[i][0]];
	            P2 = 0x01;
							delay(1000);

							P0 = 0xff;
	            P0 = seg[a[i][1]];
							P2 = 0x02; 
							delay(1000);
        
							P0 = 0xff;
	            P0 = seg[a[i][2]]& (0x7f);
							P2 = 0x04;
							delay(1000);
	   
	            P0 = 0xff;
							P0 =seg[a[i][3]];
              P2 = 0x08;
	  	        delay(1000);

	            P0 = 0xff;		
							P0 = seg[a[i][4]]& (0x7f);
              P2 = 0x10;
	            delay(1000);

							P0 = 0xff;	  
							P0 = seg[a[i][5]];
	            P2 = 0x20;
	            delay(1000);
        }
        //倒计时
        if(Mode==7){
            display();
            if(secs<0){
                secs=99;
                sec--;
            }
            if(sec<0){
                sec=59;
                min--;
            }
            if(min<0){
                secs=0;
                sec=0;
                min=0;
                fm=1;
				i=500;
				while(i--){
					delay(110);				
				}
                fm=0;
                Mode=3;
            }
        }
    }
}

proteus如下

51单片机秒表、定时器大作业_第1张图片

 

你可能感兴趣的:(51单片机,单片机,c语言)