<acronym id="xonnx"></acronym>
      <td id="xonnx"></td>
    1. <pre id="xonnx"></pre>

      1. 專注電子技術學習與研究
        當前位置:單片機教程網 >> MCU設計實例 >> 瀏覽文章

        DS1302用1602顯示加按鍵調時

        作者:我行天下   來源:本站原創   點擊數:  更新時間:2014年03月31日   【字體:


        #include <reg51.h>
        #include <intrins.h>
        /*********************************端口定義**********************************/
        sbit sclk = P3^4;
        sbit io= P3^3;
        sbit rst= P3^5;
        sbit rs=P1^0;
        sbit en=P1^2;
        sbit rw=P1^1;
        sbit GND=P2^4;
        sbit key=P2^0;
        sbit K1=P2^1;
        sbit K2=P2^2;
        #define uchar unsigned char
        #define uint  unsigned int
        uchar S1num,flag,second,minute,hour,week,day,month,year;//秒、分、時、星期、日、月、年
        bit keyflag=0;

        void delay(uint z) //延時子程序
        {
          uint x,y;
          for(x=z;x>0;x--)
             for(y=110;y>0;y--);
        }
        void delayus()
        {
        _nop_();
        _nop_();
        _nop_();
        _nop_();
        }

        void write_1602dat(uchar dat)//定義一個帶參數的寫數據子程序
        {
         rs=1; //1602的rs為0時,接收命令,為1時接收數據
         P0=dat;//把void write_shu(uchar shu)中的COM中的數據給P0口
         delay(5);
         en=1;
         delay(5);
         en=0;
         delay(5);
        }
         
         

        void write_1602com(uchar com)//定義一個帶參數的寫命令子程序
        {
         rs=0; //1602的rs為0時,接收命令,為1時接收數據
         P0=com;//把void write_com(uchar com)中的COM中的數據給P0口
         delay(5);
         en=1;
         delay(5);
         en=0;
         delay(5);
        }
        void Write1602(uchar add,uchar dat)
        {
         write_1602com(add);
         write_1602dat(dat);
        }
        void init1602()//定義一個初始化子程序
        {
         en=0;
         rw=0;
        write_1602com(0x38);//調用 write_com子程序并把0x38賦給P0口,顯示模式打開
        write_1602com(0x0e);//調用 write_com子程序并把“開顯示,顯示光標,光標閃爍”指令碼賦給P0口
        write_1602com(0x06);//調用 write_com子程序并把“地址指針加1,整屏不移動”指令碼賦給P0口
         //write_com(0x80+0x10);//數據指針初始化,讓指針指向可顯示的最右端
        write_1602com(0x80);//數據指針初始化,讓指針指向最左端,顯示從第一行開始
        write_1602com(0x01);//調用 write_com子程序并把"清零指"令碼賦給P0口
        Write1602(0x80,'2');
        Write1602(0x81,'0');
        Write1602(0x80+4,'-');
        Write1602(0x80+7,'-');
        Write1602(0x80+0x40+5,':');
        Write1602(0x80+0x40+8,':');
         }
        /********************寫一個字節**************/
        void write_1302byte(dat)
        {
        uchar i;
        sclk=0;
        delayus();
        for(i=8;i>0;i--)
          {
           io=dat&0x01;//只要是從低位取數,向高位一定要和0X01與
           delayus();
           sclk=1;//為寫數據制造上升沿。
           delayus();
           sclk=0;//為下一次上升沿寫下一個字節做準備
           dat>>=1;//將數據向左移一位,準備寫入下一個數據
          }
        }

        /********************讀一個字節***************/
        uchar read_1302byte()
        {
        uchar i,dat;
        delayus();
        for(i=8;i>0;i--)
          {
           dat>>=1;
           if(io==1)
           {
             dat|=0x80;//將1取出,寫在dat的最高位。
           }
         
           sclk=1;//把sclk拉高,為讀一個字節的下降沿做準備
           delayus();//稍等制造一個高電平
           sclk=0;//為讀一個字節制造下降沿
           delayus();
          }
        return dat;
        }

        /*************寫入一個時間位*****************/
        void write_1302(uchar add,uchar dat)
        {
         rst=0;
        delayus();
        sclk=0;
        delayus();
        rst=1;
        write_1302byte(add);
        delayus();
        write_1302byte(dat);
        delayus();
        rst=0;
        }
        /****************讀1302的地址******************/
        uchar read_1302add(uchar add)
        {
        uchar timedat;
        rst=0;
        _nop_();
        sclk=0;
        _nop_();
        rst=1;
        write_1302byte(add);//寫入要讀的地址
        timedat=read_1302byte();//將上面地址中的數據賦給timedat
        sclk=1;
        _nop_();
        rst=0;
        return timedat;
        }
        /****************初始化1302*********************/
        void init_1302()
        {
         
          flag=read_1302add(0x81);//讀秒寄存器的最高位,讀出時鐘狀態
          if(flag&0x80)//判斷時鐘是否關閉,若內部關閉,則初始,若沒關閉,不初始化,還在走
         
           {
           write_1302(0x8e,0x00);//去除寫保護
           write_1302(0x80,((55/10)<<4|(55%10)));//寫秒寄存器,并寫入初值55
           write_1302(0x82,((59/10)<<4|(59%10)));//寫分寄存器,并寫入初值59
           write_1302(0x84,((22/10)<<4|(22%10)));//寫小時寄存器,并寫入初值23
           write_1302(0x86,((24/10)<<4|(24%10)));//寫日寄存器,并寫入初值18
           write_1302(0x88,((2/10)<<4|(2%10)));//寫月寄存器,并寫入初值2
           write_1302(0x8a,((5/10)<<4|(5%10)));//寫周寄存器,并寫入初值5
           write_1302(0x8c,((12/10)<<4|(12%10)));//寫年寄存器,并寫入初值12,不能寫2012年
            write_1302(0x90,0xa5);//寫充電方式
            write_1302(0x8e,0x80);//加上寫保護
           }
        }
        /*****************讀出秒的十進制數***************************/

        uchar readsecond()
        {
        uchar dat;
        dat=read_1302add(0x81);
        second=((dat&0x70)>>4)*10+(dat&0x0f);
        return second;
        }

        /*****************讀出分的十進制數***************************/

        uchar readminute()
        {
        uchar dat;
        dat=read_1302add(0x83);
        minute=((dat&0x70)>>4)*10+(dat&0x0f);
        return minute;
        }

        /*****************讀出小時的十進制數***************************/

        uchar readhour()
        {
        uchar dat;
        dat=read_1302add(0x85);
        hour=((dat&0x70)>>4)*10+(dat&0x0f);
        return hour;
        }
        /*****************讀出天的十進制數***************************/

        uchar readday()
        {
        uchar dat;
        dat=read_1302add(0x87);
        day=((dat&0x70)>>4)*10+(dat&0x0f);
        return day;
        }

        /*****************讀出月的十進制數***************************/

        uchar readmonth()
        {
        uchar dat;
        dat=read_1302add(0x89);
        month=((dat&0x70)>>4)*10+(dat&0x0f);
        return month;
        }
        /*****************讀出周的十進制數***************************/

        uchar readweek()
        {
        uchar dat;
        dat=read_1302add(0x8b);
        week=((dat&0x70)>>4)*10+(dat&0x0f);
        return week;
        }

        /*****************讀出年的十進制數***************************/

        uchar readyear()
        {
        uchar dat;
        dat=read_1302add(0x8d);
        year=((dat&0xf0)>>4)*10+(dat&0x0f);
        return year;
        }
         
        /************************讀出所有時間**********************/
        readtime()
        {
        readsecond();
        readminute();
        readhour();
        readday();
        readmonth();
        readweek();
        readyear();
        }
        /*********************向1602寫入時間****************************/
        void write_second()
        {
        uchar shi,ge;
        shi=second/10;
        ge=second%10;
        Write1602(0x80+0x40+9,0x30+shi);
        Write1602(0x80+0x40+10,0x30+ge);
        }
        void write_minute()
        {
        uchar shi,ge;
        shi=minute/10;
        ge=minute%10;
        Write1602(0x80+0x40+6,0x30+shi);
        Write1602(0x80+0x40+7,0x30+ge);
        }
        void write_hour()
        {
        uchar shi,ge;
        shi=hour/10;
        ge=hour%10;
        Write1602(0x80+0x40+3,0x30+shi);
        Write1602(0x80+0x40+4,0x30+ge);
        }

        void write_day()
        {
        uchar shi,ge;
        shi=day/10;
        ge=day%10;
        Write1602(0x80+8,0x30+shi);
        Write1602(0x80+9,0x30+ge);
        }
        void write_month()
        {
        uchar shi,ge;
        shi=month/10;
        ge=month%10;
        Write1602(0x80+5,0x30+shi);
        Write1602(0x80+6,0x30+ge);
        }
        void write_year()
        {
        uchar shi,ge;
        shi=year/10;
        ge=year%10;
        Write1602(0x80+2,0x30+shi);
        Write1602(0x80+3,0x30+ge);
        }
        void write_week()
        {
        Write1602(0x80+12,0x30+week);
        //uchar week;
        switch(week)
          {
           case 1: Write1602(0x80+12,'M');
                Write1602(0x80+13,'O');
             Write1602(0x80+14,'N');
             break;
            case 2:Write1602(0x80+12,'T');
                Write1602(0x80+13,'U');
             Write1602(0x80+14,'E');
             break;
            case 3:Write1602(0x80+12,'W');
                Write1602(0x80+13,'E');
             Write1602(0x80+14,'N');
             break;
            case 4:Write1602(0x80+12,'T');
                Write1602(0x80+13,'H');
             Write1602(0x80+14,'U');
             break;
         case 5:Write1602(0x80+12,'F');
                Write1602(0x80+13,'R');
             Write1602(0x80+14,'I');
             break;
            case 6:Write1602(0x80+12,'S');
                Write1602(0x80+13,'A');
             Write1602(0x80+14,'T');
             break;
         case 7:Write1602(0x80+12,'S');
                Write1602(0x80+13,'U');
             Write1602(0x80+14,'N');
             break;
          }
        }
        /*********************鍵盤掃描****************************/
        void keyscan()
        {
          if(key==0)
          {
            delay(5);
             if(key==0);//防止誤動作
          {
           
             S1num++;
             while(!key);
             switch(S1num)
             {
              case 1:
                keyflag=1;
                write_1302(0x8e,0x00);//去除寫保護
             write_1302(0x80,0x80);//時鐘停下
             write_1602com(0x80+0x40+10);
             write_1602com(0x0f);
             break;
              case 2:
                write_1602com(0x80+0x40+7);
                break;
              case 3:
                write_1602com(0x80+0x40+4);
                break;
              case 4:
                write_1602com(0x80+9);
                break;
              case 5:
                write_1602com(0x80+6);
                break;
              case 6:
                write_1602com(0x80+3);
                break;
              case 7:
                write_1602com(0x80+12);
                break;
              case 8:
                S1num=0;
             keyflag=0;
           
                         write_1602com(0x0c);//不顯示光標                           
                          write_1302(0x80,0x00);//禁止寫保護
                 write_1302(0x80,(second/10)<<4|second%10);//將調節后的秒寫入DS1302
                          write_1302(0x82,(minute/10)<<4|minute%10);//將調節后的分寫入DS1302
                          write_1302(0x84,(hour/10)<<4|hour%10);//將調節后的時寫入DS1302
                 write_1302(0x8a,(week/10)<<4|week%10);//將調節后的星期寫入DS1302
                          write_1302(0x86,(day/10)<<4|day%10);//將調節后的日寫入DS1302
                          write_1302(0x88,(month/10)<<4|month%10);//將調節后的月寫入DS1302
                 write_1302(0x8c,(year/10)<<4|year%10);//
                //write_1302(0x80,0x00);//時鐘繼續走這一句不能加在這,否則每次調 完時后秒會歸O
             write_1302(0x8e,0x80);//寫保護關
             //write_1602com(0x0c);
                break;
           }
          }
          }
          if(S1num!=0)
          {
            if(K1==0)
            {
             delay(5);
          while(!K1);
          switch(S1num)
          {
           case 1:
            second++;
            if(second==60)second=0;
            //write_1302(0x8e,0x00);//去除寫保護
            write_second();
            write_1602com(0x80+0x40+10);
            break;
           case 2:
            minute++;
            if(minute==60)minute=0;
            write_minute();
            write_1602com(0x80+0x40+7);
            break;
           case 3:
            hour++;
            if(hour==24)hour=0;
            write_hour();
            write_1602com(0x80+0x40+4);
            break;
           case 4:
            day++;
            write_day();
            write_1602com(0x80+9);
            break;
             case 5:
            month++;
            write_month();
            write_1602com(0x80+6);
            break;
             case 6:
            year++;
            write_year();
            write_1602com(0x80+3);
            break;
             case 7:
            week++;
            write_week();
            write_1602com(0x80+12);
            break;
            // default:break;
             }
            }
            if(K2==0)
            {
             delay(5);
          while(!K2);
          switch(S1num)
          {
           case 1:
            second--;
            if(second<0)second=59;
            write_second();
            write_1602com(0x80+0x40+10);
            break;
           case 2:
            minute--;
            if(minute<0)minute=59;
            write_minute();
            write_1602com(0x80+0x40+7);
            break;
           case 3:
            hour--;
            if(hour<0)hour=23;
            write_hour();
            write_1602com(0x80+0x40+4);
            break;
           case 4:
            day--;
            write_day();
            write_1602com(0x80+9);
            break;
             case 5:
            month--;
            write_month();
            write_1602com(0x80+6);
            break;
             case 6:
            year--;
            write_year();
            write_1602com(0x80+3);
            break;
             case 7:
            week--;
            write_week();
            write_1602com(0x80+12);
            break;
           //  default:break;
          }
            }
          }
        }

         void main()
        {
          GND=0;
          delay(100);
          init1602();
          init_1302();
          while(1)
            {
          keyscan();
          if(keyflag==0)
          {
          readtime();
          write_second();
          write_minute();
          write_hour();
          write_day();
          write_month();
          write_year();
          write_week();
          }
         }
        }
         

        關閉窗口

        相關文章

        欧美性色欧美精品视频,99热这里只有精品mp4,日韩高清亚洲日韩精品一区二区,2020国自产拍精品高潮