硬件系統(tǒng)方案設(shè)計 圖2.1為電話撥號報警器的系統(tǒng)構(gòu)成方框圖,由單片機控制器、鍵盤輸入、數(shù)碼管顯示、觸發(fā)電路、撥號電路及電源等6部分組成。 單片機控制器是整個系統(tǒng)的核心,負責(zé)控制檢測輸入/輸出顯示、模擬摘機、撥號摘機、撥號報警、掛機等一系列的程序動作。這里使用了小引腳、高性能、低價位的AT89S2052。 鍵盤輸入電路負責(zé)輸入電片機中一系列工作參數(shù)及功能設(shè)定。 發(fā)光二極管數(shù)碼管顯示器在整個系統(tǒng)工作過程中充當(dāng)一個簡單的人機界面,用以顯示工作狀況及輸入/輸出的數(shù)據(jù)等。 電話撥號防盜報警器的觸發(fā)電路用磁性開關(guān)(門磁開關(guān)),簡單可靠,也可用紅外探測器或無線門磁,以實現(xiàn)全方位遠距離監(jiān)測。報警器應(yīng)采用隱蔽安裝,防止小偷發(fā)現(xiàn)。 撥號及報警電路用來完成模擬摘機、撥號、發(fā)出報警音、掛機等工作過程,它的工作由單片機控制。 電源部分負責(zé)對整個系統(tǒng)供電。平時由電話線上取得工作電流并對后備電池充電,撥號報警時轉(zhuǎn)由后備電池供電。 圖2.1 電話撥號防盜報警器方框圖 2.1.2脈沖撥號原理 脈沖撥號是目前電話機兩種撥號方式中的一種,另一種為雙音多頻撥號方式。 脈沖撥號就是指在電話機上撥入的電話號碼以脈沖個數(shù)的形式發(fā)出,也就是說,在已經(jīng)通以直流電流的回路上,利用撥號盤及發(fā)號電路將回路斷開、再接通而形成的脈沖信號,來完成輸入電話號碼的發(fā)送。在操作中,若用戶撥1,則送出1個脈沖,回路中斷一次、接通一次;撥2,則發(fā)出2個脈沖,回路斷一次、接通一次、再斷一次;……;而撥0時,則發(fā)出10個脈沖,回路斷、接通輪流10次。圖2.2為電話號碼“32”的脈沖波形。 圖2.2 電話號碼“32”的脈沖波形
正常撥號時,電路電流中斷的時間一般在58~65ms之間,視斷續(xù)比的不同而不同。快速撥號時,只要取一半時間即可。電路電流接通的時間(即在同一位號碼中的2個斷脈沖之間的接通電流時間)約在32~42ms之間,視斷續(xù)比的不同而不同。快速撥號時,只要取一半時間即可。顯然脈沖周期等于脈沖中斷時間和脈沖接通時間之和,每一個周期的時間為100ms左右。快速撥號時,在50ms左右。2位號碼(即2組脈沖串)之間的最小時間間隔,通常為800ms左右;而快速撥號時,其值減半,為400ms左右。 我國目前采用的電話脈沖撥號的速率是10PPS(每秒的脈沖數(shù)),即每秒發(fā)出10個脈沖,因此上述各參數(shù)不存在快速撥號時的值。 為了提高撥號的可靠性及穩(wěn)定性,這里設(shè)計時選定更低的脈沖撥號速率:1個脈沖代表播出1,2個脈沖代表撥出2,……,10個脈沖代表撥出0,每個脈沖的寬度和間隔為100ms。工作時首先進行模擬摘機,然后開始脈沖撥號,撥出1位號碼后停頓500ms(保持接通)再撥下一位,直至全部撥完后再發(fā)報警音,……,最后掛機。
2.1.3 脈沖撥號實現(xiàn)過程 圖2.3為脈沖撥號的實現(xiàn)電路。平時電話線上的電壓約為50~60V左右。未撥號時電片機的P3.0、P3.1 均輸出低電平。 撥號過程如下: ①單片機的P3.0輸出高電平,使TR1導(dǎo)通,由于電話線路上接入了負載R1,這樣電話線的電壓下降,模擬摘機。 ②單片機的P3.0開始輸出撥號脈沖,使電話線的電壓(電平)也呈高、低變化。1個脈沖代表撥出1,2個脈沖代表撥出2,……,10個脈沖代表撥出0,每個脈沖的寬度和間隔均為100ms。撥出1位號碼后停頓500ms(保持P3.0高電平)再撥下一位,直至全部撥完。 ③P3.0 保持高電平(保持電話線路接通),P3.1輸出1KHz的報警音脈沖驅(qū)動TR2,以2Hz進行調(diào)制(即接通1kHz信號0.5s、斷開1kHz信號0.5s),這樣從接聽方的電話中就會聽到“嘟、嘟……”的報警聲。報警音的時間根據(jù)設(shè)計為60s。 ④60后,P3.1輸出低電平,TR2 截止,停止報警。隨后P3.0也輸出低電平,模擬掛機。完成一次報警過程。
電路原理如圖所示,共有4個按鍵,即rst、ok、up、set。 rst:系統(tǒng)復(fù)位鍵。 ok:輸入數(shù)據(jù)確認鍵。 up:顯示的數(shù)字增加鍵。 set:工作模式設(shè)定鍵,可設(shè)定管機、工作、輸入時間t1、輸入時間t2及輸入電話號碼5種模式。 磁性開關(guān)即為裝于門或窗口的防盜感應(yīng)開關(guān),門關(guān)閉時常開,門打開時閉合接通。當(dāng)然也可改用其他的感應(yīng)器件,如激光探測、超聲波感應(yīng)、熱釋電感應(yīng)、主動紅外線探測或無線門磁等,以實現(xiàn)全方位遠距離檢測。為了防止磁性開關(guān)離控制器較遠而產(chǎn)生引入干擾,使用了光耦作信號傳遞,效果良好。LED數(shù)碼管用于工作狀態(tài)指示或輸入數(shù)據(jù)指示。L1、L2接電話線,ZND為擊穿電壓120V的壓敏二極管,防止電路受雷電干擾。平時系統(tǒng)處于低功耗待機狀態(tài)(此時耗電僅2mA左右),由電話線上取電工作,并對3.6V/60mA鎳鉻電池充電,當(dāng)輸入數(shù)據(jù)進行設(shè)定或進行撥號報警時,耗電會達到10mA,這時主要由鎳鉻電池供電。由于有鎳鉻電池后備供電,即使電話線斷電也不會使已輸入的數(shù)據(jù)丟失。該機除用于防盜報警外,若對軟件進行一些修改,也可通過電話線進行遠程數(shù)據(jù)傳遞。三極管T1、T2及電阻R1、R2構(gòu)成撥號及報警電路,其工作原理前面已作詳細介紹。 4.1.2時鐘計時器的硬件電路設(shè)計描述 時鐘計時器的硬件電路,采用AT89S52單片機最小化應(yīng)用設(shè)計,顯示采用共陽七段LED顯示器,P0口輸出段數(shù)碼數(shù)據(jù),P2.0~P2.5口作列掃描輸出,P1.0,P1.1和P1.2口接三個按鈕開關(guān)用以實現(xiàn)調(diào)時,調(diào)分功能.為了提供共陽LED數(shù)碼管的驅(qū)動電壓,用三極管8550作電源驅(qū)動輸出。采用12MHZ晶振有利于提高秒計時的精確性。硬件電路圖如圖3.2示。
三系統(tǒng)的軟件設(shè)計 3.1電話撥號防盜報警器程序設(shè)計 3.1.1主程序設(shè)計 主程序的工作過程為:先進行初始化工作,隨后根據(jù)輸入的鍵值分別散轉(zhuǎn)輸入的鍵值分別散轉(zhuǎn)至對應(yīng)的子程序(管機、警戒工作、輸入時間t1、輸入時間t2、輸入電話號碼)循環(huán)工作。T0為100ms定時中斷服務(wù)子程序,它實現(xiàn)精確的撥號脈沖時序。INT0外中斷服務(wù)子函數(shù)用于實現(xiàn)功能選擇;而INT1外中斷服務(wù)子函數(shù)則檢測防盜觸發(fā)開關(guān)的狀態(tài)。 主程序狀態(tài)流程圖如圖3.6所示。INT0外中斷服務(wù)子函數(shù)狀態(tài)流程圖及INT1外中斷服務(wù)子函數(shù)的狀態(tài)流程圖分別如圖3.7、圖3.8所示。 - 1 -
3.2 時鐘顯示程序設(shè)計 3.2.1主函數(shù) 本設(shè)計中計時采用定時器T0中斷完成,其余狀態(tài)循環(huán)調(diào)用顯示子函數(shù)及鍵掃描子函數(shù),當(dāng)端口開關(guān)按下時,轉(zhuǎn)入相應(yīng)調(diào)時功能。其主函數(shù)執(zhí)行流程如圖3.3所示。
3.2.2 LED顯示子函數(shù) 數(shù)碼管顯示的數(shù)據(jù)存放在內(nèi)存單元dis[0]~dis[5]中,其中dis[0]~dis[1]存放秒數(shù)據(jù),dis[2]~dis[3]存放分?jǐn)?shù)據(jù),dis[4]~dis[5]存放時數(shù)據(jù),每一單元內(nèi)均為十進制BCD碼。由于采用軟件動態(tài)掃描實現(xiàn)數(shù)據(jù)顯示功能,顯示用的十進制BCD碼數(shù)據(jù)的對應(yīng)段碼存放在ROM表(dis7[11])中,顯示時,先取出dis[0]~dis[5]中的某一數(shù)據(jù),然后查得對應(yīng)得顯示段碼從P0口輸出,P2口將對應(yīng)得數(shù)碼管選中供電,就能顯示該地址單元的數(shù)據(jù)值。 3.2.3定時器T0中斷函數(shù) 定時器T0用于時間計時。定時溢出中斷周期可設(shè)為50ms,中斷進入后先判斷,中斷計時累計20次(即1ms)時對妙計數(shù)單元進行加1操作。時鐘計數(shù)單元在 義的6個單元(timedata[6])中。timedata[0]~timedata[1]存放秒數(shù)據(jù),timedata[2]~timedata[3]存放分?jǐn)?shù)據(jù),timedata[4]~timedata[5]存放時數(shù)據(jù)。最大計時值為23小時59分59秒。在計數(shù)單元中采用十進制BCD碼計數(shù),秒,分、時之間滿60進位。T0中斷服務(wù)程序執(zhí)行流程如圖3.4所示。
3.2.4中斷函數(shù) T1中斷服務(wù)程序用于指示調(diào)整數(shù)字單元的亮閃,在時間調(diào)整狀態(tài)下,每過0.4s,將對應(yīng)單元的顯示數(shù)據(jù)換成“熄滅符”數(shù)據(jù)(0x0a)。這樣,在調(diào)整時間時,對應(yīng)調(diào)整單元的顯示數(shù)據(jù)會間隔閃亮。 3.2.5功能函數(shù) 調(diào)時功能函數(shù)的設(shè)計方法是:按下T0鍵,進入調(diào)分狀態(tài),時鐘停止走動;按T1或T2鍵可進行加1或減1操作 ;繼續(xù)按T0鍵可分別進行分十位、時個位和時十位調(diào)整;最后按T0建將退出調(diào)整狀態(tài),時鐘開始計時運行。
四系統(tǒng)的調(diào)試部分 4.1 時鐘系統(tǒng)的調(diào)試 4.1.1時鐘系統(tǒng)的硬件調(diào)試 硬件調(diào)試時可先檢查印制板及焊接的質(zhì)量情況,在檢查無誤后可通電檢查LED顯示器的點亮狀況。若亮度不理想,可以調(diào)整P0口的電阻大小,一般情況下取200歐姆電阻即可獲得滿意的亮度效果。 4.1.2時鐘系統(tǒng)的軟件調(diào)試 軟件調(diào)試Keil C51編譯器,源程序編譯及仿真調(diào)試應(yīng)分段或以子函數(shù)為單位一個個地進行,最后可結(jié)合硬件實時運行調(diào)試。 4.1.3性能分析 按照設(shè)計程序分析,LED顯示器動態(tài)掃描頻率約為167Hz,實際使用觀察時完全沒有閃爍,實際計時時精度較高,可滿足一般場合的應(yīng)用需要。
4.2撥號報警器功能調(diào)試 通電前應(yīng)檢查焊接質(zhì)量,確認無短路、虛焊等故障。將撥碼開關(guān)J2指向下側(cè),即斷開3.6V鎳鉻電池與系統(tǒng)的連接。將外部直流可調(diào)穩(wěn)壓電源調(diào)整為3.6V。接入系統(tǒng)的Vcc與地。如果系統(tǒng)耗電小于15mA為正常,否則應(yīng)檢查是否有短路、元器件不良或錯焊現(xiàn)象存在。隨后取下外接直流穩(wěn)壓電源,恢復(fù)3.6V鎳鉻電池與系統(tǒng)的連接,進行軟、硬件統(tǒng)調(diào)測試。 由于AT89S52的I/O引腳有限,故數(shù)碼管只設(shè)一位,因此輸入數(shù)字時只能分階段一位一位輸入。 假設(shè)需輸入t1=061,t2=025,電話號碼=12345678,在此詳述如下: 地1步:接上電話線(也即接上電源)后,數(shù)碼管顯示“E”,意為數(shù)據(jù)錯誤,因為此時我們尚未輸入任何數(shù)據(jù)。 第2步: ①點按一下set鍵,鍵值加1,即此時set=1.這時數(shù)碼管最下的一橫點亮,顯示“_”,意為可輸入時間t1,點按ok鍵確認(小數(shù)點被同時點亮)。然后數(shù)碼管顯示數(shù)字“0”。 ②按下up鍵后,數(shù)字開始從0~9循環(huán)遞增,調(diào)至0后松開up鍵,點按ok鍵確認(小數(shù)點被同時點亮)。此時百位數(shù)字“0”存入內(nèi)存。 ③按下up鍵后,數(shù)字開始循環(huán)遞增,調(diào)至1后松開up鍵,點按ok鍵確認(小數(shù)點被同時點亮)。此時十位數(shù)字“6”存入內(nèi)存。 ④按下up鍵后,數(shù)字開始循環(huán)遞增,調(diào)至1后松開up鍵,點按ok鍵確認(小數(shù)點被同時點亮)。此時個位數(shù)字“6”存入內(nèi)存。 這樣就完成了將061(代表t1=61s)存入內(nèi)存的過程。同時數(shù)碼管又恢復(fù)顯示“_” 。 第3步: ①點按一下set鍵,鍵值加1,即此時set=2。這時數(shù)碼管下面的二橫點亮,顯示“二”,意為可輸入時間t2,點按ok鍵確認(小數(shù)點被同時點亮)。然后數(shù)碼管顯示數(shù)字“0”。 ②按下up鍵后,數(shù)字開始從從0~9循環(huán)遞增,調(diào)至0后松開up鍵,點按ok鍵確認(小數(shù)點被同時點亮)。此時百位數(shù)字“0”存入內(nèi)存。 ③按下up鍵后,數(shù)字開始循環(huán)遞增,調(diào)至2后松開up鍵,點按ok鍵確認(小數(shù)點被同時點亮)。此時十位數(shù)字“2”存入內(nèi)存。 ④按下up鍵后,數(shù)字開始循環(huán)遞增,調(diào)至5后松開up鍵,點按ok鍵確認(小數(shù)點被同時點亮)。此時個位數(shù)字“5”存入內(nèi)存。 這樣就完成了將025(代表t1=25s)存入內(nèi)存的過程。同時數(shù)碼管又恢復(fù)顯示“二” 以后的調(diào)試同前面的方法相同。
(1) 電話撥號報警程序
程序設(shè)計時需要設(shè)立3個數(shù)組DATA[20]、X[3]、Y[3]。DATA[20]用于存放電話號碼(最長20位),X[3]用于存放時間t1(000~999s),Y[3]用于存放時間t2(000~999s)。
另外還要設(shè)立3個軟件計數(shù)器data_flag、t1_flag、t2_flag。Data_flag用于統(tǒng)計輸入的電話號碼位長,t1_flag用于統(tǒng)計輸入的時間t1位長,t2位長。
- uchar DATA[20]; /*存放電話號碼的數(shù)組*/
- uchar X[3]; /*存放時間t1數(shù)組*/
- uchar Y[3]; /*存放時間t2數(shù)組*/
- uchar flag; /*RAM區(qū)防干擾標(biāo)志*/
- uchar data_flag=0; /*輸入電話號碼計數(shù)器(最長20位)*/
- uchar set=0; /*功能鍵值*/
- uchar m=0; //全局變量
- uchar n=0;
- uint f;
- uchar t1_flag=0; /*輸入時間t1計數(shù)器(最長3位)*/
- uchar t2_flag=0; /*輸入時間t2計數(shù)器(最長3位)*/
- uchar cnt_1=0; /*時間t1單元數(shù)學(xué)運算后暫存單元*/
- uchar cnt_2=0; /*時間t2單元數(shù)學(xué)運算后暫存單元*/
- /*定時器T0初始化*/
- viod init_timer()
- {
- TMOD=0x01; //定時器T0方式1
- TH0=-(50000/256); //裝載100ms定時初值
- TL0=-(50000%256);
- IE=0x82; //開中斷
- }
- 啟動報警器子程序模塊
-
- /*---啟動報警器進入警戒---*/
- void work()
- {uchar h;
- p1=0xdf; /*數(shù)碼管左上角顯示“1”*/
- delay(1);
- if(set==1) /*進入時間1循環(huán)*/
- {while(cnt<=x[0]*100+X[1]*10+X[2])
- {
- delay(1000);
- cnt_1++; /*計數(shù)器cnt_1累加*/
- if(set!=1){EX1=0;cnt_1=0;break;}
- } /*如按下Set鍵,則推出此循環(huán)*/
- }
- else {EX1=1;PCON=0x00;}
- if(set==1)
- {if(cnt_1>=X[0]*100+X[1]*10+X[2])
- {EX1=1;cnt_1=0;} /*時間1到,打開外中斷1,計數(shù)器歸零*/
- /*進入待機。若有1s以上開關(guān)動作,退出待機*/
- while(1)
- {PCON=0x01;if(f>=5{PCON=0x00;break;})
- }
- /*-----------------------------------------------------------*/
- EX1=0; /*關(guān)閉外中斷1*/
- if(set==1) /*進入時間2循環(huán)*/
- {while(cnt_2<=Y[0]*100+Y[1]*10+Y[2])
- {
- delay(1000);
- cnt_2++; /*計時器cnt_2累加*/
- if(set!=1){cnt_2=0;break;}
- } /*如按下Set鍵,則退出此循環(huán)*/
- }
- if(set==1)
- {
- bh(); /*時間2到,調(diào)用撥號子程序*/
- delay(3000);
- p3_7=0; //控制輸出端為低,可驅(qū)動蜂鳴器等
- for(h=0;h<60;h++) /*發(fā)出60s警音*/
- { for(f=0;f<500;f++)
- {f++;
- P3_1=! P3_1;P1=0x5f;
- delay(1);
- }
- P3_1=0;P1=0x7f;delay(500);
- }
- P3_7=1;//控制輸出端恢復(fù)高
- cnt_1=0;cnt_2=0; /*有關(guān)計數(shù)器、端口回到初始狀態(tài)*/
- P3_0=0;P3_1=0;P1_7=1;
- for(f=0;f<3;f++)delay(60000); /*關(guān)閉3min,讓接警人進行手機或電話座機報警*/
- }
- }
-
- 撥號脈沖子程序模塊
-
- /*---撥號---*/
- void bh()
- {data_flag=0; /*電話號碼計數(shù)器(20位)歸零*/
- P3_0=1; /*接通線路*/
- p1_7=0; /*數(shù)碼管小數(shù)點亮*/
- delay(1000);
- while (DATA[data_flag]<10) /*號碼小于10進入循環(huán)撥號狀態(tài)*/
-
- {
- if(DATA[data_flag]==0) /*若號碼為0*/
- {TR0=1; /*啟動T0定時器*/
- if(n==20){data_flag++; /*進行20次中斷,產(chǎn)生10個脈沖*/
- n=0;TR0=0;
- P3_0=1;P1_7=0;
- delay(500);
- }
- }
- if(DATA[data_flag]>0) /*若號碼〉0但<10*/
- {TR=1; /*啟動T0定時器*/
- if(n==((DATA[data_flag]*2)) /*進行號碼x2次中斷,產(chǎn)生號碼個脈沖*/
- {data_flag++;
- n=0;TR0=0;
- P3_0=1;P1_7=0;
- delay(500);
- }
- }
- }
- TR0=0;
- }
-
- 關(guān)機子程序模塊
-
- void stop() //*關(guān)機子程序
- {if(flag==0x55)P1=0xfb; //*若標(biāo)志為55H,說明內(nèi)存區(qū)未受干擾,數(shù)碼
- //管右下角顯示“1”
- else P1=0x86; //否則數(shù)碼管顯示“E”
- delay(1); //延時1ms再判
- if(flag==0x55)PCON=0x01; //進入低耗節(jié)電待機狀態(tài)
- delay(1); //延時1ms
- }
-
- 完整代碼
-
- #include<AT89x052.H> //器件配置文件
- #define uchar unsigned char //變量類型的宏定義
- #define uint unsigned int
- uchar code DATA_7SEG[10]={0xC0,0xF9,0xA4,0xB0,0x99
- 0x92,0x82,0xF8,0x80,0x90,}; /*0~9數(shù)碼管段碼*/
- uchar DATA[20]; /*存放電話號碼的數(shù)組*/
- uchar x[3]; /*存放時間t2數(shù)組*/
- uchar flag; /*RAM區(qū)防干擾標(biāo)志*/
- uchar data_flag=0; /*輸入電話號碼計數(shù)器(最長20位)*/
- uchar set=0; /* 功能鍵值*/
- uchar m=0; //全局變量
- uchar n=0;
- uint f;
- uchar t1_flag=0; /*輸入時間1計數(shù)器(最長3位)*/
- uchar t2_flag=0; /*輸入時間2 計數(shù)器(最長3位)*/
- uchar cnt_1=0; /*時間t1單元數(shù)學(xué)運算后暫存單元*/
- uchar cnt_2=0; /*時間t2單元數(shù)學(xué)運算后暫存單元*/
- /*************************************************/
- void delay(uint k); /*延時子函數(shù)聲明*/
- void stop(); /*關(guān)機子函數(shù)聲明*/
- void bh(); /*撥號子函數(shù)聲明*/
- /*************************************************/
- /*定時器T0初始化*/
- void init_timer()
- {
- TMOD=0x01;
- TH0=-(50000/256);
- TL0=-(50000%256);
- IE=0x82;
- }
- /***********************************************************/
- /*100ms定時中斷服務(wù)子函數(shù)*/
- void zd0()interrupt 1
- {
- P3_0=! P3_0; //P3.0每100ms取反一次,送出脈沖
- P1_7=! P1_7; //數(shù)碼管小數(shù)點同步閃爍
- n++;
- TH0=-(50000/256);
- TL0=-(50000%256);
- }
- /********************************************************/
- /*100ms定時中斷服務(wù)子函數(shù)*/
- void zd0()interrupt 1
- {
- p3_0=!P3_0; //P3.0每100ms取反一次,送出脈沖
- P1_7=!P1_7; //數(shù)碼管小數(shù)點同步閃爍
- n++;
- TH0=-(50000/256);
- TL0=-(50000%256);
- }
- /*********************************************/
- /*INT0中斷服務(wù)子函數(shù)*/
- viod zd_int0()interrupt 0
- {
- delay(10);
- if(P3_2==0)set++; //功能鍵值遞增
- if(set>=5)set=0; //鍵值的范圍0~4
- if(set==1)flag=0x55; //向RAM區(qū)的標(biāo)志flag寫入55H
- PCON=0x00;f=8;
- again:if(P3_2==0)goto again; //若按鍵未釋放,則等待
- }
- /*****************************************/
- /*INT1中斷服務(wù)子函數(shù)*/
- void zd_int1()interrupt 2
- {uchar h;
- f=0;
- for(h=0;h<10;h++) /*檢查磁性開關(guān)(P3_3狀態(tài))10次,共1s*/
- {
- delay(100)
- if(P3_3==0)f++;
- }
- }
- /********************************************************************/
- /*---關(guān)機---*/
- void stop()
- {if(flag==0x55)P1=0xfb;
- elsep1=0x86; //數(shù)碼管右下角顯示“1”。
- delay(1);
- if(flag==0x55)PCON=0x01; /*進入節(jié)電待機狀態(tài)*/
- delay(1);
- }
- /*********************************************************************/
- /*延時1ms*K子函數(shù)*/
- void delay(uint k)
- {
- uint i,j;
- for(i=1;j<k;i++){
- for(j=0;j<60;j++)
- {;}}
- }
- /*********************************************************************/
- /*----輸入時間t1----*/
- viod in_time1()
- {
- P1=0xf7;delay(1); /*數(shù)碼管顯示“—”*/
- if(P3_5==0)
- {
- delay(10); /*按下OK鍵確認并點亮小數(shù)點*/
- if(P3_5==0){P1=0x7f;m=0;t1_flag=0;delay(500);}
- while(t1_flag<3)
- {
- if(P3_4==0)
- {delay(10);if(P3_4==0) /*按下UP鍵數(shù)碼管作0~9遞增顯示*/
- {m++;if(m==10)m=0;P1=DATA_7SEG[m];delay(300);}
- }
- P1=DATA_7SEG[m];delay(1); /*若不按下UP鍵數(shù)碼管也作0~9顯示*/
- if(P3_5==0)
- {delay(10);if(P3_5==0) /*按下OK鍵顯示的數(shù)據(jù)存入數(shù)組X中*/
- {X[t1_flag]=m;t1_flag++;P1=0x7f;delay(500);}
- }
- }
- }
- if(t1_flag>=3)t1_flag=0; /*時間1計數(shù)器>=3時歸零*/
- }
- /**********************************************************************
- /
- /*-----輸入時間t2-----*/
- viod in_time2()
- {
- P1=0xb7;delay(1); /*數(shù)碼管顯示“二”*/
- if(P3_5==0)
- {
- delay(10); /*按下OK鍵確認并點亮小數(shù)點*/
- if(P3_5==0){P1=0X7f;m=0;t2_flag=0;delay(500);}
- while(t2_flag<3)
- {
- if(P3_4==0)
- {delay(10);if(P3_4==0) /*按下UP鍵數(shù)碼管作0~9遞增顯示*/
- {m++;if(m==10)m=0;P1=DATA_7SEG[m];delay(300);}
- }
- P1=DATA_7SEG[m];delay(1); /*若不按UP鍵數(shù)碼管也作0~9顯示*/
- if(P3_5==0)
- {delay(10);if(P3_5==0) /*按下OK鍵顯示的數(shù)據(jù)存入數(shù)組Y中*/
- {Y[t2_flag=m;t2_flag++;P1=0x7f;delay(500);}
-
- }
- }
- }
- if(t2_flag>=3)t2_flag=0; /*時間2計數(shù)器>=3時歸零*/
- }
- /***********************************************************************
- /
- /*----輸入電話號碼----*/
- vioa in_data()
- {uchar g;
- P1=0xb6;delay(1); /*數(shù)碼管顯示三*/
- if(P3_5==0)
- {delay(10);if(P3_5==0)
- {p1=0x7f;m=0;data_flag=0; /*按下OK鍵確認并點亮小數(shù)點*/
- for(g=0;g<20;g++){DATA[g]=10;}
- delay(500); /*同時DATA數(shù)組中全部寫入10*/
- while(1)
- {
- if(P3_4==0){delay(10); /*按下UP鍵數(shù)碼管作0~9遞增顯示*/
- if(P3_4==0);{m++;if(m==10)m=0;P1=DATA_7SEG[m];delay(300);}
- }
- P1=DATA_7SEG[m];delay(1); /*若不按UP鍵數(shù)碼管也作0~9顯示*/
- if(P3_5==0)
- {delay(10);
- if(P3_5==0) /*按下OK鍵顯示的數(shù)據(jù)(號碼)存入數(shù)組DATA中*/
- {DATA[data_flag]=m;data_flag++;P1=0x7f;delay(500);}
- } /按下OK鍵超過2s則退出向數(shù)組DATA送入號碼*/
- if(P3_5==0){delay(2000);if(P3_5==0)break;}
- }
- }
- }
- F1:if(P3_5==0){delay(10);if(P3_5==0){P1=0xb6;delay(1);goto F1;}}
-
-
- /********************************************************************/
- /*--主函數(shù)--*/
- void main()
- {
- int_timer(); /*定時器T0初始化*/
- EA=1;EX0=1; /*開總中斷,開外中斷0*/
- p3_0=0; /*關(guān)閉線路(掛機)*/
- p3_1=0;
- while(1) /*無限循環(huán)*/
- {
- switch(set) /*根據(jù)Set標(biāo)志散轉(zhuǎn)*/
- {
- case 0:stop();break; /*關(guān)機*/
- case 1:work();break; /*警戒工作*/
- case 3:in_time2();break; /*輸入時間t1*/
- case 4:in_data();break;
- }
- if(flag!=0x55)
- {p1=0x86;delay(1);}
- }
- }
-
-
- (2) 時鐘計時器程序
- /**************************************************************/
- // 采用6位LED動態(tài)掃描時鐘演示程序
- // 使用Keil C51
- // 2004.03.31
- /*************************************************************/
- /*使用AT89S52單片機,12MHZ晶振,P0口輸出段碼,P2口作列掃描,用共陽LED數(shù)碼管*/
- //key0為調(diào)時位選用,key1為加1鍵,key2為減1鍵
- #include "reg51.h"
- #define char unsigned char
- //
- char code dis_7[11]={0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0x80,0x90,0xff};
- /*共陽LED段碼表"0" "1" "2" "3" "4" "5" "6" "7" "8" "9" "不亮"*/
- char code scan_con[8]={0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f}; //列掃描控制字
- char data timedata[6]={0x00,0x00,0x00,0x00,0x00,0x00}; //計時單元數(shù)據(jù)初值,共6個
- char data dis[8]={0x00,0x00,0x00,0x00,0x00,0x00,0x0a,0x00,}; //顯示單元數(shù)據(jù),共6個數(shù)據(jù)
- char data con1s=0x00,con04s=0x00,con=0x00; //秒定時用
- sbit key0=P1^0;
- sbit key1=P1^1;
- sbit key2=P1^2;
- //
- /************/
- //1ms延時函數(shù)//
- /***********/
- dalaylms(int t)
- {
- int i,j;
- for(i=0;i<t;i++)
- for(j=0;j<120;j++)
- ;
- }
- /*************/
- //鍵掃描子函數(shù)//
- keyscan()
- {
- EA=0;
- if(key0==0)
- {
- delaylms(10);
- while(key0==0);
- if(dis[con]==10)
- {dis[7]=dis[con];dis[con]=dis[6];dis[6]=dis[7];}
- con++;TR0=0;ET0=0;TR1=1;ET1=1;
- if(con >=6)
- {con=0;TR1=0;ET1=0;TR0=1;ET0=1;}
- }
- //
- if(con!=0)
- {
- if(key1==0)
- {
- delaylms(10);
- while(key1==0);
- timedata[con]++
- if(timedata[con]>=10)
- {timedata[con]=0;}
- dis[con]=timedata[con];dis[6]=0x0a;
-
- }
- }
- //
- if(con!=0)
- {
- if(key2==0)
- {
- delaylms(10);
- while(key2==0);
- if(timedata[con]==0)
- {timedata[con]=0x90;}
- else{timedata[con]--;}
- dis[con]=timedata[con];dis[6]=0x0a;
-
- }
- }
- EA=1;
- }
- //
- /***********/
- //顯示函數(shù)//
- /***********/
- scan()
- {
- char k;
- for(k=0;k<6;k++)
- {
- p0=dis_7[dis[k]];p2=scan_con[k];delaylms(1);p2=0xff;
- }
- }
- /*************/
- //初始化函數(shù)//
- /*************/
- clearmen()
- {
- int i;
- for(i=0;i<6;i++)
- {
- dis[i]=timedata[i];}
- TH0=0x3C;TL0=0xB0; //50ms定時初值(T0計時用)
- TH1=0x3C;TL1=0xB0; //50ms定時初值(T1計時用)
- TMOD=0X11;ET0=1;ET1=1;TR1=0;TR0=1;EA=1;
- }
- /**********/
- //主函數(shù)//
- /*********/
- main()
- {
- clearmen();
- while(1)
- {
- scan();
- keyscan();
- }
- }
- /********************/
- //1s中斷處理函數(shù)//
- /*******************/
- viod time_intt0(viod) interrupt 1
- {
- ET0=0;TR0=0;TH0=0x3C;TL0=0xB0;TR0=1;
- con1s++;
- if(con1s==20)
- {
- con1s=0x00;
- timedata[0]++;
- if(timedata[0]>=10)
- {
- timedata[0]=0;timedata[1]++;
- if(timedata[1]>=6)
- {
- timedata[1]=0;timedata[2]++;
- if(timedata[2]>=10)
- {
- timedata[2]=0;timedata[3]++;
- if(timedata[3]>=6)
- {
- timedata[3]=0;timedata[4]++;
- if(timedata[4]>=10)
- {
- timedata[4]=0;timedata[5]++;
- }
- if(timedata[5]==2)
- {
- if(timedata[4]==4)
- {
- timedata[4]=0;timedata[5]=0;
- }
- }
- }
- }
- }
- }
- dis[0]=timedata[0];dis[1]=timedata[1];dis[2]=timedata[2];
- dis[3]=timedata[3];dis[4]=timedata[4];dis[5]=timedata[5];
- }
- ET0=1;
- }
- /********************/
- //0.4S閃爍中斷函數(shù)//
- /*******************/
- viod time_intt1(viod) interrupt3
- {
- EA=0;TR1=0;TH1=0x3C;TL1=0xB0;TR1=1;
- con04s++;
- if(con04s==8)
- {
- con04s=0x00;
- dis[7]=dis[con];dis[con]=dis[6];dis[6]=dis[7];
- }
- EA=1;
- }
復(fù)制代碼
以上的Word格式文檔51黑下載地址:
文檔.doc
(255.5 KB, 下載次數(shù): 15)
2020-11-29 04:38 上傳
點擊文件名下載附件
|