基于51的1602时钟显示

来源:互联网 发布:匕首cad图纸数据 编辑:程序博客网 时间:2024/06/06 02:35
#include<reg52.h>
#define uchar unsigned char//宏定义
#define uint unsigned int//宏定义
sbit dula=P2^6;//控制数码管
sbit wela=P2^7;
sbit rs=P3^5;//控制液晶数据名命令选择
sbit lcden=P3^4;//液晶写数据控制
sbit s1=P3^0;//控制矩阵键盘的S9
sbit s2=P3^1;//控制矩阵键盘的S13
sbit s3=P3^2;//控制矩阵键盘的S17
sbit rd=P3^7;//申明RD的位
uchar count,date,shi,fen,miao,s1num;
uchar code table[]=" 2017-10-17 MON";//初始化显示日期
uchar code table1[]="    19:28:20";//初始化显示时间
void delay(uint z)
{
    uint x,y;
     for(x=z;x>0;x--)
          for(y=110;y>0;y--);
}
void write_com(uchar com)//写指令函数
{
     rs=0;//数据置低
     lcden=0;//lcden拉低
     P0=com;
     delay(5);
     lcden=1;//拉高
     delay(5);//稳定五毫秒
     lcden=0;//拉低
         
}
void write_date(uchar date)//写指数据函数
{
     rs=1;//数据置高
     lcden=0;//lcden拉低
     P0=date;
     delay(5);
     lcden=1;//拉高
     delay(5);//稳定五毫秒
     lcden=0;//拉低
         
}


void init()
{
     uchar num;
     dula=0;//关闭数码管
     wela=0;
     lcden=0;//通过1602的资料显示lcden初始为低


/*  一定注意这里的赋值与程序开头的自定义赋值,当二者赋值一致的时候才会正常走动,不也一样时就会出现错误,原因未知*/
     fen=28;
     miao=20;
     shi=19;
/***************************************************/
     write_com(0x38);//设置16X2显示,5X7点阵,8位数据接口
     delay(5);
     write_com(0x0c);//00001100开显示,不显示光标
     write_com(0x06);//00000110,读入一个字符后指针和光标都加一,整屏不移动
     write_com(0x01);//清零,不清零会显示出错
     write_com(0x80);//指针赋值,写入地址,表示从第一行开始写
    for(num=0;num<15;num++)//第一行共需要15个显示位,显示位数一定要一一对应
        {
            write_date(table[num]);//写数据进去
            delay(5);
        }
    write_com(0x80+0x40);//写入第二行的地址
    for(num=0;num<12;num++)//第二行共需要11个显示位,显示位数一定要一一对应,
        {
            write_date(table1[num]);//写数据进去
            delay(5);
        }
     TMOD=0x01;//采用定时器0的方式1
     TH0=(65536-50000)/256;//装初值
     TL0=(65536-50000)%256;
     EA=1;//开总中断
     ET0=1;//打开T0中断
     TR0=1;//启动定时器0
    
  



void write_sfm(uchar add,uchar date)//写动态数据到时分秒表中
{
   uchar shi,ge;//时、分、秒、都由两个数字表示,分离开
   shi=date/10;//分离出数据的十位
   ge=date%10;//分离个位
   write_com(0x80+0x40+add); //写动态到第二行中
   write_date(0x30+shi);//通过1602的字符手册,让十位显示0(0x30),送数据到第二行
   write_date(0x30+ge);//通过1602的字符手册,让个位显示0(0x30),送数据到第二行
     


}
void keyscan()//编写按键控制时钟函数
{//5
   rd=0;//让RD接地,要控制那一列就让那一列接地,通过矩阵键盘原理图判断    
   if(s1==0)//检测s1是否按下
    {//4
        s1num++;//每按下一次s1就加一
        delay(5);//延时消抖
        if(s1==0)//判断s1确实被按下
          {
            
             while(!s1);//检测是否松手 
             if(s1num==1)//按下第一次让秒闪烁
                   {
                  TR0=0;//关闭定时器,禁止时钟继续走动
                  write_com(0x80+0x40+11);//控制第二行的第几位
                  write_com(0x0f);//显示光标,并让光标闪烁,0x0f来源于1602的原理图
                   }
             if(s1num==2)//按下第二次让分闪烁
                  {
                  TR0=0;//关闭定时器,禁止时钟继续走动
                  write_com(0x80+0x40+8);//控制第二行的第几位
                  write_com(0x0f);//显示光标,并让光标闪烁,0x0f来源于1602的原理图
                  }
             if(s1num==3)//按下第三次让时闪烁
                  {
                   TR0=0;//关闭定时器,禁止时钟继续走动
                   write_com(0x80+0x40+5);//控制第二行的第几位
                   write_com(0x0f);//显示光标,并让光标闪烁,0x0f来源于1602的原理图
                  }
             if(s1num==4)//第四次按下,清零,让光标不闪烁
                 {
                  s1num=0;//清零
                  write_com(0x0c);//光标停止闪烁
                  TR0=1;//开启定时器,时钟重新开始走动
                 }


          }


  
    }//4
    
       if(s1num!=0)//确认s1键被按下
          {//3
            if(s2==0)//检测s2被按下
              {//2
                  delay(5);
                  if(s2==0)//确定s2被按下
                    {//1
                         while(!s2);
                         if(s1num==1)//确定让秒加一
                           {
                             miao++;
                                if(miao==60)
                                     miao=0;
                             write_sfm(10,miao);
                             write_com(0x80+0x40+10);
                             
                           }    
                         if(s1num==2)//确定让分加一
                           {
                             fen++;
                             if(fen==60)
                                     fen=0;
                             write_sfm(7,fen);
                             write_com(0x80+0x40+7);
                            
                           }  
                         if(s1num==3)//确定让时加一
                           {
                             shi++;
                              if(shi==24)
                                  shi=0;
                              write_sfm(4,shi);
                             write_com(0x80+0x40+4);
                             
                           }  
                    }//1 
      
              }//2
           if(s3==0)//检测s3被按下
              {//2
                  delay(5);
                  if(s3==0)//确定s2被按下
                    {//1
                         while(!s3);
                         if(s1num==1)//确定让秒加一
                           {
                             miao--;
                                if(miao==0)
                                     miao=60;
                             write_sfm(10,miao);
                             write_com(0x80+0x40+10);
                             
                           }    
                         if(s1num==2)//确定让分加一
                           {
                             fen++;
                             if(fen==0)
                                     fen=60;
                             write_sfm(7,fen);
                             write_com(0x80+0x40+7);
                            
                           }  
                         if(s1num==3)//确定让时加一
                           {
                             shi++;
                              if(shi==0)
                                  shi=24;
                              write_sfm(4,shi);
                             write_com(0x80+0x40+4);
                             
                           }  
                    }//1 
      
              }//2  
          } //3     
            
}//5


void main()
{
     init();
      
     while(1)
    { 
         keyscan();
         if(count==20)//判断是否到了1秒
         {
            count=0;
            miao++; 
              if(miao==60)//判断是否到了一分钟
                   {
                   miao=0;
                   fen++;
                   if(fen==60)
                      {
                         fen=0;
                         shi++;
                         if(shi==24)
                            {
                               shi=0;
                               
                            }
                         write_sfm(4,shi); 
                       }
                    write_sfm(7,fen); 
                   } 
             write_sfm(10,miao);//10表示table1[]中的秒位正好在第十个字符位后面
         }
    }
     


}




void timer0() interrupt 1//选择中断源
{
      TH0=(65536-50000)/256;//装初值
      TL0=(65536-50000)%256;
     count++;


}
原创粉丝点击