找回密碼
 立即注冊(cè)

QQ登錄

只需一步,快速開始

搜索
查看: 1886|回復(fù): 0
打印 上一主題 下一主題
收起左側(cè)

單片機(jī)電子時(shí)鐘設(shè)計(jì)

[復(fù)制鏈接]
跳轉(zhuǎn)到指定樓層
樓主


一、設(shè)計(jì)內(nèi)容
內(nèi)容:用單片機(jī)控制實(shí)現(xiàn)基本數(shù)字電子鐘的設(shè)計(jì),擴(kuò)展了4X4鍵盤和4位LED數(shù)碼顯示器,可用于顯示和按鍵控制。

功能:能夠顯示時(shí)和分;可通過按鍵設(shè)置鬧鐘功能;可進(jìn)行整點(diǎn)報(bào)時(shí);可通過按鍵設(shè)置分校時(shí)。

二、總體方案設(shè)計(jì)
2.1 功能分析
數(shù)字電子鐘系統(tǒng)可以分為主控制單元、復(fù)位電路、鍵盤電路、顯示電路等。



2.2 各模塊功能說明
晶振電路的功能:每個(gè)單片機(jī)系統(tǒng)里都有晶振,全程是叫晶體震蕩器,在單片機(jī)系統(tǒng)里晶振的作用非常大,他結(jié)合單片機(jī)內(nèi)部的電路,產(chǎn)生單片機(jī)所必須的時(shí)鐘頻率,單片機(jī)的一切指令的執(zhí)行都是建立在這個(gè)基礎(chǔ)上的,晶振的提供的時(shí)鐘頻率越高,那單片機(jī)的運(yùn)行速度也就越快。晶振用一種能把電能和機(jī)械能相互轉(zhuǎn)化的晶體在共振的狀態(tài)下工作,以提供穩(wěn)定,精確的單頻振蕩。

復(fù)位電路的功能:把電路初始化到一個(gè)確定的狀態(tài),一般來說,單片機(jī)復(fù)位電路作用是把一個(gè)例如狀態(tài)機(jī)初始化到空狀態(tài),而在單片機(jī)內(nèi)部,復(fù)位的時(shí)候單片機(jī)是把一些寄存器以及存儲(chǔ)設(shè)備裝入廠商預(yù)設(shè)的一個(gè)值。

鍵盤電路:根據(jù)4×4矩陣鍵盤,它是用四條I/O線作為行線,四條I/O線作為列線組成的鍵盤。在行線和列線的每個(gè)交叉點(diǎn)上設(shè)置一個(gè)按鍵。這樣鍵盤上按鍵的個(gè)數(shù)就為4×4個(gè)。這種行列式鍵盤結(jié)構(gòu)能有效地提高單片機(jī)系統(tǒng)中I/O口的利用率。實(shí)現(xiàn)按鍵控制鬧鐘,設(shè)置時(shí)間的功能。

顯示電路的功能:采用4位共陰極數(shù)碼管驅(qū)動(dòng)方式P2口相應(yīng)的位置0  即選擇要顯示的數(shù)碼管位,P0口相應(yīng)的位置1即可顯示相應(yīng)的數(shù)碼管段。負(fù)責(zé)顯示時(shí)鐘的時(shí)和分。

三、硬件系統(tǒng)設(shè)計(jì)
    使用了Produce軟件進(jìn)行硬件原理圖的仿真設(shè)計(jì)。

    部分電路如圖所示:

  a. 主控電路: 80C51單片機(jī)

        

   b. 晶振電路:89C51單片機(jī)內(nèi)部的振蕩電路是一個(gè)高增益反相放大器,引線XTAL1和XTAL2分別            為反相振蕩放大器的輸入及內(nèi)部時(shí)鐘工作電路的輸入和來自反相振蕩器的輸出,該反相放大             器可以配置為片內(nèi)振蕩器。

         

       c. 復(fù)位電路:采用上電復(fù)位,上電后,由于電容充電,使RST持續(xù)一段時(shí)間的高電平,從而實(shí)                現(xiàn)上電復(fù)位操作。這不僅能使單片機(jī)復(fù)位,還能是單片機(jī)的外圍設(shè)備同時(shí)復(fù)位,當(dāng)程序出              現(xiàn)錯(cuò)誤時(shí),可以隨時(shí)使電路復(fù)位。

           

        d. 鍵盤電路:當(dāng)按鍵被按下時(shí),相應(yīng)的引腳被拉低,經(jīng)掃描后,獲得鍵值,并執(zhí)行鍵功能程                   序,因此通過按下同一個(gè)鍵,將執(zhí)行不同的功能程序。

           

        e. 顯示電路:主要是數(shù)碼管顯示數(shù)字電子鐘的時(shí)和分。  

      

四、軟件系統(tǒng)設(shè)計(jì)
  4.1 程序總體流程圖
       主函數(shù)的流程框圖:先進(jìn)行初始化設(shè)定初值,然后相關(guān)子程序的調(diào)用

            
  4.2 主要模塊程序流程

       1.調(diào)用中斷服務(wù)子程序,循環(huán)次數(shù)++,因?yàn)槎〞r(shí)時(shí)長(zhǎng)為50ms,所以循環(huán)次數(shù)為20時(shí),循環(huán)次數(shù)清0,秒++;秒為60時(shí)分加++,秒清0;分為60時(shí),時(shí)++,分清0;時(shí)為24時(shí),時(shí)清0,中斷返回。

                     

         2.先確認(rèn)彈簧消抖是否有鍵按下,之后判斷掃描按鍵,不同的按鍵觸發(fā)不同功能。

                  

五、源代碼
部分代碼展示:

#include<reg51.h>
#define tl 0xba;  //宏定義 tl賦初值
#define th 0x3c;   //宏定義 th賦初值

sbit speaker=P3^5;             //鬧鐘輸出    蜂鳴器               

unsigned char code led[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};  //數(shù)碼管顯示的數(shù)字0-9的編碼
unsigned char count0,second,minit,hour;    //時(shí)間時(shí)分秒
unsigned int second1,minit1,hour1;//鬧鐘時(shí)分秒

//timenum1是調(diào)節(jié)時(shí)間的按鍵按下的次數(shù)
//timenum2是調(diào)節(jié)鬧鐘的按鍵按下的次數(shù)
//f1是否在設(shè)置鬧鐘
//f2是否在設(shè)置時(shí)間
unsigned char timenum1,timenum2,f1,f2;   
unsigned int dsflg;
unsigned char temp;

//延時(shí)子程序  代碼燒路軟件自動(dòng)生成的
void delay(void)
{
    unsigned int i;
    for(i=0;i<100;i++);
}
//50ms
//數(shù)碼管顯示
void display(void)
{
   
    P0=led[hour/10]; //p0口送數(shù)據(jù) 拆數(shù)顯示,時(shí)的十位  
    P2=0xFE;         //片選    P2.0
    delay();          //延時(shí)
    P2=0xFF;          //片選關(guān)
   
    P0=led[hour%10];   //p0口送數(shù)據(jù) 拆數(shù)顯示,時(shí)的個(gè)位
    P2=0xFD;    //P2.1
    delay();
    P2=0xFF;
   
    P0=led[minit/10];   //p0口送數(shù)據(jù) 拆數(shù)顯示,分的十位
    P2=0xFB;  //P2.2
    delay();
    P2=0xFF;
   
    P0=led[minit%10];   //p0口送數(shù)據(jù) 拆數(shù)顯示,分的個(gè)位
    P2=0xF7;  //P2.3
    delay();
    P2=0xFF;
}

//掃描按鍵
void keyscan()
{
     unsigned char temp;
      P1=0xfe;     // 給P1.0賦低電平
      temp=P1;
      temp=temp&0xf0;     //判斷P1.0那一列是否有鍵按下
      if(temp!=0xf0)// 確定有鍵按下的時(shí)候
      {
            delay1(10);   //延時(shí)子程序進(jìn)行消抖
        temp=P1;
        temp=temp&0xf0; //再次判斷p1.0那一列是否有鍵按下
        if(temp!=0xf0)      //確定有鍵按下
        {
              temp=P1;     //將P1的值給temp
            switch(temp)
              {
                case 0xee:    //p1.4口
                    timenum1++;          //標(biāo)記++
                    TR1=0;     //不啟動(dòng)T1 ,關(guān)閉蜂鳴器
                    f2=0;     //進(jìn)入調(diào)時(shí)間的狀態(tài)
                    if(timenum1==1||timenum2==1)     //如果timenum1==1 調(diào)時(shí)
                    {
                        dsflg=0;    //正在調(diào)時(shí)間
                    }
                    if(timenum1==3)     如果timenum1==4 退出         
                    {   
                        TR1=1;     //啟動(dòng)T1
                        timenum1=0;      //將按鍵次數(shù)歸零
                        dsflg=1;      //退出調(diào)時(shí)間
                        f2=1;     //退出調(diào)節(jié)時(shí)間
                    }
                    break;
                        
                case 0xde:  //p1.5口
                    //調(diào)時(shí)間
                    if(timenum1==1)     //如果timenum1==1 調(diào)時(shí)
                    {
                        hour++;        //小時(shí)++
                     }
                    if(timenum1==2)     //如果timenum1==2 調(diào)分
                    {
                           minit++;
                      }
                  //調(diào)鬧鐘
                    if(timenum2==1)     //如果timenum2==1 調(diào)時(shí)     鬧鐘
                      {
                        hour1++;        //小時(shí)++
                      }
                    if(timenum2==2)     //如果timenum2==2 調(diào)分    鬧鐘
                      {
                           minit1++;
                      }
                     break;
                     
                case 0xbe:     //p1.6口
                      speaker=1;  //蜂鳴器處于不響狀態(tài)在設(shè)置時(shí)間的時(shí)候
                    if(timenum1==1)     //如果timenum1==1 調(diào)時(shí)
                      {
                        hour--;        //小時(shí)--
                      }
                    if(timenum1==2)     //如果timenum1==2 調(diào)分
                      {
                           minit--;    //分鐘--
                      }
                     //調(diào)鬧鐘
                    if(timenum2==1)     //如果timenum2==1 調(diào)時(shí)     鬧鐘
                      {
                        hour1--;        //小時(shí)--
                      }
                    if(timenum2==2)     //如果timenum2==2 調(diào)分    鬧鐘
                      {
                           minit1--;
                      }
                     break;
                     
                case 0x7e://p1.7
                    timenum2++;      //標(biāo)記++
                    f1=0;    //進(jìn)入設(shè)置鬧鐘
                    if(timenum2==1||timenum2==2)    //如果timenum2=1設(shè)定腦鐘的小時(shí)
                    {
                        dsflg=0;   //正在調(diào)時(shí)間
                     }
                    if(timenum2==3)    //如果timenum2=3退出
                    {
                        timenum2=0;     //將按鍵次數(shù)歸零
                        dsflg=1;  //退出調(diào)時(shí)間
                        f1=1;     // 退出設(shè)置鬧鐘
                    }
                     break;
              }
              
              while(temp!=0xf0)    //判斷按鍵是否彈起
              {
                temp=P1;
                temp=temp&0xf0;
              }
        }
      }
}

//按鍵控制 時(shí)間設(shè)置
void Keykonzhi()
{
    if(timenum1==1)     //如果timenum1==1 調(diào)時(shí)
    {
        if(hour>23)      //限位
        {
            hour=0;
        }
        
        P0=led[hour/10];    //顯示小時(shí)
        P2=0xFE;     //小時(shí)十位 p2.0
        delay();
        P2=0xFF;     
        
        P0=led[hour%10]; //顯示小時(shí)
        P2=0xFD;     //小時(shí)個(gè)位  p2.1
        delay();
        P2=0xFF;
    }
   
    if(timenum1==2)     如果timenum1==2 調(diào)分  //以下也是和調(diào)時(shí)一樣的方法
        
    {
        if(minit>59)
        {   
            minit=0;
        }
        
        P0=led[minit/10];
        P2=0xFB;   //分鐘十位  p2.2
        delay();
        P2=0xFF;
        
        P0=led[minit%10];
        P2=0xF7;   //分鐘個(gè)位   p2.3
        delay();
        P2=0xFF;
    }
}

//設(shè)置鬧鐘
void almset()
{
    timenum1=0;
    if(timenum2==1)    //如果timenum2==1設(shè)定鬧鐘的小時(shí)
    {
        if(hour1>23)   //限位
        {
            hour1=0;
        }
        
        P0=led[hour1/10];//小時(shí)顯示  十位
        P2=0xFE;//p2.0
        delay();
        P2=0xFF;
        
        P0=led[hour1%10];
        P2=0xFD;//p2.1    小時(shí)個(gè)位 顯示
        delay();
        P2=0xFF;
    }
   
    if(timenum2==2)       //如果timenum2==2設(shè)定鬧鐘的分鐘  和上面小時(shí)一樣
    {
        if(minit1>59)
        {
            minit1=0;
        }
        
        P0=led[minit1/10];//顯示分鐘十位
        P2=0xFB; //  p2.2
        delay();
        P2=0xFF;
        
        P0=led[minit1%10];//顯示分鐘個(gè)位
        P2=0xF7;// p2.3
        delay();
        P2=0xFF;
    }
}

//控制鬧鐘 (鬧鐘到了設(shè)定時(shí)間就會(huì)響)
void almkozi()
{
    if((hour1==hour)&&(minit1==minit)&&(second<4))
    {
        speaker=0;      //鬧鐘時(shí)間到,蜂鳴器響
     }
    if(minit==0&&second<4)   
    {
        //整點(diǎn)報(bào)時(shí),蜂鳴器響
        speaker=0;
    }
   
    if(second>4) //控制蜂鳴器響的時(shí)長(zhǎng)
    {
          speaker=1;   //關(guān)閉蜂鳴器
    }
}

六、測(cè)試結(jié)果展示
      1. 時(shí)鐘顯示:最開始設(shè)置時(shí)間為12:59。
      2 . 鬧鐘調(diào)時(shí):手動(dòng)按鍵調(diào)整時(shí)鐘的時(shí)。
      3. 鬧鐘調(diào)分:手動(dòng)按鍵調(diào)整時(shí)鐘的分。
      4. 整點(diǎn)報(bào)時(shí):時(shí)鐘到整點(diǎn)蜂鳴器就會(huì)響,達(dá)到報(bào)時(shí)的效果。

          在做設(shè)計(jì)的過程中,我進(jìn)一步認(rèn)識(shí)到全面專業(yè)知識(shí)以及邏輯思考方式對(duì)研究問題的重要性,同時(shí)我也更加具體的掌握了設(shè)計(jì)的基本方法。經(jīng)過不斷的努力,我終于完成了這次設(shè)計(jì),總的來說,我學(xué)到了不少的東西,知道了理論聯(lián)系實(shí)際的重要性。在設(shè)計(jì)過程中我遇到了很多的困難,但沒放棄,查閱了許多相關(guān)的書籍,自己獨(dú)立思考和借鑒了前人的許多優(yōu)秀成果,并與所學(xué)的知識(shí)緊密的結(jié)合了起來。我相信這過程對(duì)我今后的學(xué)習(xí)和工作有著積極的影響,并搭好了平臺(tái)。通過這次設(shè)計(jì),我對(duì)這門課有了更好的理解,尤其結(jié)合了這幾年學(xué)的相關(guān)的專業(yè)知識(shí),對(duì)各門課都有了一個(gè)較全面的理解。這必將對(duì)我以后的學(xué)習(xí)和工作有很大的幫助。本次設(shè)計(jì)的定時(shí)鬧鐘電路,可以滿足人們的基本要求,但因?yàn)橹R(shí)水平有限,此電路中存在一定的問題,雖可以通過增加電路解決,但過于復(fù)雜和現(xiàn)有水平有限,本次設(shè)計(jì)就未深入涉及,想要更好的改進(jìn)電路,需要進(jìn)一步的努力,如果有好的意見,希望
分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏1 分享淘帖 頂 踩
回復(fù)

使用道具 舉報(bào)

本版積分規(guī)則

手機(jī)版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術(shù)交流QQ群281945664

Powered by 單片機(jī)教程網(wǎng)

快速回復(fù) 返回頂部 返回列表