【单片机】含有闹钟的时钟设计

2019-04-15 18:22发布

#include
#define uchar unsigned char
#define uint  unsigned int
sbit key1 = P3^2; //手动控制数码管1,2位
sbit key2 = P3^3;   //手动控制数码管4,5位
sbit key3 = P3^4; //手动控制数码管7,8位
sbit key5 = P1^6;   //手动切换数码管显示(可显示三种情况:时钟,日期,闹钟时间)
sbit key6 = P1^7;   //停止闹钟音乐
sbit alarm = P1^4;  //闹钟
uchar count,hour,minute,second;      // 时钟时间 时分秒
uchar i;                             
uchar h,s,m;                         //闹钟时间  时分秒
uchar pattern=0;                     //工作模式 (0:时钟模式 1;日期模式 2:闹钟模式)
uint year,month,day;                    //日期时间 年月日 
uchar code led[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};//数码管段码
uchar num;
uchar code SONG[] ={ //祝你平安
0x26,0x20,0x20,0x20,0x20,0x20,0x26,0x10,0x20,0x10,0x20,0x80,0x26,0x20,0x30,0x20,
0x30,0x20,0x39,0x10,0x30,0x10,0x30,0x80,0x26,0x20,0x20,0x20,0x20,0x20,0x1c,0x20,
0x20,0x80,0x2b,0x20,0x26,0x20,0x20,0x20,0x2b,0x10,0x26,0x10,0x2b,0x80,0x26,0x20,
0x30,0x20,0x30,0x20,0x39,0x10,0x26,0x10,0x26,0x60,0x40,0x10,0x39,0x10,0x26,0x20,
0x30,0x20,0x30,0x20,0x39,0x10,0x26,0x10,0x26,0x80,0x26,0x20,0x2b,0x10,0x2b,0x10,
0x2b,0x20,0x30,0x10,0x39,0x10,0x26,0x10,0x2b,0x10,0x2b,0x20,0x2b,0x40,0x40,0x20,
0x20,0x10,0x20,0x10,0x2b,0x10,0x26,0x30,0x30,0x80,0x18,0x20,0x18,0x20,0x26,0x20,
0x20,0x20,0x20,0x40,0x26,0x20,0x2b,0x20,0x30,0x20,0x30,0x20,0x1c,0x20,0x20,0x20,
0x20,0x80,0x1c,0x20,0x1c,0x20,0x1c,0x20,0x30,0x20,0x30,0x60,0x39,0x10,0x30,0x10,
0x20,0x20,0x2b,0x10,0x26,0x10,0x2b,0x10,0x26,0x10,0x26,0x10,0x2b,0x10,0x2b,0x80,
0x18,0x20,0x18,0x20,0x26,0x20,0x20,0x20,0x20,0x60,0x26,0x10,0x2b,0x20,0x30,0x20,
0x30,0x20,0x1c,0x20,0x20,0x20,0x20,0x80,0x26,0x20,0x30,0x10,0x30,0x10,0x30,0x20,
0x39,0x20,0x26,0x10,0x2b,0x10,0x2b,0x20,0x2b,0x40,0x40,0x10,0x40,0x10,0x20,0x10,
0x20,0x10,0x2b,0x10,0x26,0x30,0x30,0x80,0x00};
/*定时器1中断:用于闹钟音乐播放*/
void Time0_Int() interrupt 3  
{
TH1= 0xD8;
TL1= 0xEF;     //计入初值,10毫秒定时
num++; //长度加1
}
/*功能:1MS延时子程序*/
void Delay_xMs(uint x) //音乐播放所需延时
{
unsigned int i,j;
for( i =0;i < x;i++ )
{
for( j =0;j<3;j++ );
}
}
/* 延时子程序:时钟显示所需*/
void delay(uint time) //延时
{
uchar j=5;
for(; time>0 ; time--)
for(;j>0;j--);
}
void wait(uchar n) //延时
{
for(i=0 ; i    delay(100); 
}
/*功能:闹钟歌曲播放子程序*/
void Play_Song()
{
unsigned char Temp1,Temp2;
unsigned int Addr;
num = 0; //中断计数器清0
Addr = 0;   //SONG下标
while(1)
{
Temp1 = SONG[Addr++];
if(key6!=1)   //判断key6键按下
{
     delay(100);   //硬件防抖
if(key6!=1)
{
   Temp1=0x00;
   }
 }
 if ( Temp1 == 0x00 ) //歌曲结束符
{
return;
}
else
{
Temp2 = SONG[Addr++];
TR1 = 1;
while(1)
{
alarm= ~alarm;
Delay_xMs(Temp1);
if ( Temp2 == num )
{
num = 0;
break;
}
}
}
}
}
void INT_T() interrupt 1    //中断子程序,时间,日期自动进位
{
TH0=0x3c;
TL0=0xb0;  
count++;
if(count==20)
    {
count=0;
second++;                      //秒自增
if(second==60)
{
second=0;    
    minute++;                 //分自增
if(minute==60)
{
minute=0;
hour++;                 // 时自增
    if(hour==24)

    hour=0;
day++;            //  日自增
                    if(((month==1||month==3||month==5||month==7||month==8||month==10||month==12)&&day==32)||
                   ((month==4||month==6||month==9||month==11)&&day==31)||
                   ((month==2&&(year%400==0||(year%100!=0&&year%4==0)))&&day==30)||
                   ((month==2&&year%4!=0)&&day==29) )
    {
day=1;
    month++;
if(month==13)

    month=1;
year++;
if(year==100)
                      year=0; 
}
    }
        }
}
    }
    }
}
void main()                //主函数
{
TMOD=0X11;           //定时器1方式1;定时器0方式1
TH0=0x3c;
TL0=0xb0;                  //计入初值,定时50毫秒
EA=1;                     //总中断允许
ET0=1;                   //定时器中断允许
ET1=1;
TR0=1;                    //允许计数
hour=0;
minute=0;
second=0;                   //时钟初值
year=2017;
month=12;
day=12;                       //日期初值
h=8;
m=0;
s=0;                //闹钟初值
while(1)
{
          alarm=0;                //闹钟关闭
if(pattern==0) //pattern=0,时钟显示
{
P2=0x7f;
P0=led[hour/10];
    wait(1);
P2=0xbf;
P0=led[hour%10];
wait(1);
P2=0xdf;
P0=0x40;
wait(1);
P2=0xef;
P0=led[minute/10];
wait(1);
P2=0xf7;
P0=led[minute%10];
wait(1);
        P2=0xfb;
P0=0x40;
      wait(1);
P2=0xfd;
P0=led[second/10];
wait(1);
    P2=0xfe;
P0=led[second%10];
wait(1);             //各位赋值
if(key1!=1)    //按键1,时+1
{
delay(100);        //硬件防抖
if(key1!=1)
hour++;
delay(100);
while(key1==0);
}
if(key2!=1) //按键2,分+1
    {
delay(100);
if(key2!=1)
minute++;   
delay(100);
while(key2==0);
}
if(key3!=1)   //按键3,秒+1
{
delay(100);
if(key3!=1)
second++;    
delay(100);
while(key3==0);
}
if(key5!=1) //按键5,切换工作模式
{
delay(100);
if(key5!=1)
pattern++;
if(pattern==3)
pattern=0;
delay(100);
while(key5==0);
}
}
if (hour==h && minute==m && second==s) //到达闹钟时间点
{
Play_Song();

}    
if(pattern==1)    //pattern=1,日期显示
{
P2=0x7f;
P0=led[year/1000];
wait(1);
P2=0xbf;
P0=led[year%1000/100];
    wait(1);
P2=0xdf;
P0=led[year%100/10];
wait(1);
    P2=0xef;
P0=led[year%10];
wait(1);
P2=0xf7;
P0=led[month/10];
wait(1);
P2=0xfb;
P0=led[month%10];
        wait(1);
P2=0xfd;
P0=led[day/10];
    wait(1);
P2=0xfe;
P0=led[day%10];
    wait(1);
if(key1!=1)         //年+1

delay(100);    
if(key1!=1)
year++;
delay(100);
while(key1==0);
}
if(key2!=1)        //月+1
{
delay(100);
        if(key2!=1)
month++;   
delay(100);
while(key2==0);
         }
  if(key3!=1)     //日+1  
  {
delay(100);
if(key3!=1)
day++;    
delay(100);
while(key3==0);
  }
  if(key5!=1)     //切换工作模式
  {
delay(100);
         if(key5!=1)
         pattern++;
if(pattern==3)
              pattern=0;
delay(100);
while(key5==0);
}
if (hour==h && minute==m && second==s)
{

Play_Song();
}  
}
if(pattern==2)    //pattern=2,闹钟显示
{
    P2=0x7f;
P0=led[h/10];
   wait(1);
P2=0xbf;
P0=led[h%10];
wait(1);
P2=0xdf;
P0=0x40;
wait(1);
P2=0xef;
P0=led[m/10];
wait(1);
P2=0xf7;
P0=led[m%10];
wait(1);
P2=0xfb;
P0=0x40;
wait(1);
P2=0xfd;
P0=led[s/10];
wait(1);
P2=0xfe;
P0=led[s%10];
wait(1);
if(key1!=1)     //小时+1
{
delay(100);   //进位规则 时
if(key1!=1)
h++;
if(h==24)
h=0;
delay(100);
while(key1==0);
}
if(key2!=1)
    {                               //分
delay(100);
if(key2!=1)
m++;
if(m==60)
{
  m=0;
  h++;
}   
delay(100);
    while(key2==0);
}
if(key3!=1)                   //秒
{
delay(100);
if(key3!=1)
    s++;
if(s==60)
{
s=0;
m++;
}    
    delay(100);
  while(key3==0);
}
if (hour==h && minute==m && second==s)
{
Play_Song();
}
if(key5!=1)         //切换
       {
delay(100);
if(key5!=1)
pattern++;
if(pattern==3)
              pattern=0;
delay(100);
    while(key5==0);
   }
        }  




if(hour==24) hour=0; //手动更改时间时期时进位规则
if(minute==60)
{
hour++;
minute=0;
}
if(second==60)
{
minute++;
second=0;
}
if(year==100) year=0;
if(month==13)
{
    year++;  
      month=1;


if(((month==1||month==3||month==5||month==7||month==8||month==10||month==12)&&day==32)||
  ((month==4||month==6||month==9||month==11)&&day==31)||
  ((month==2&&(year%400==0||(year%100!=0&&year%4==0)))&&day==30)||
  ((month==2&&year%4!=0)&&day==29))
{
day=1;
month++;
}


    }
}