91欧美超碰AV自拍|国产成年人性爱视频免费看|亚洲 日韩 欧美一厂二区入|人人看人人爽人人操aV|丝袜美腿视频一区二区在线看|人人操人人爽人人爱|婷婷五月天超碰|97色色欧美亚州A√|另类A√无码精品一级av|欧美特级日韩特级

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

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

倩倩 ? 來源:電子開發(fā)網(wǎng) ? 2020-09-18 16:55 ? 次閱讀
加入交流群
微信小助手二維碼

掃碼添加小助手

加入工程師交流群

共用體除非必要,否則我們不推薦使用,枚舉的用法比較簡(jiǎn)單,在本書 19 章的項(xiàng)目實(shí)踐中有很好的示例,這節(jié)課我們先來練習(xí)一下結(jié)構(gòu)體的使用。下邊這個(gè)程序的功能是一個(gè)帶日期的電子鐘,相當(dāng)于一個(gè)簡(jiǎn)易萬(wàn)年歷了,并且加入了按鍵調(diào)時(shí)功能。學(xué)有余力的同學(xué)看到這里,不妨先不看我們提供的代碼,自己寫寫試試。如果能夠獨(dú)立寫一個(gè)按鍵可調(diào)的萬(wàn)年歷程序,單片機(jī)可以說基本入門了。如果自己還不能夠獨(dú)立完成這個(gè)程序,那么還是老規(guī)矩,先抄并且理解,而后自己獨(dú)立默寫出來,并且要邊默寫邊理解。

本例直接忽略了星期這項(xiàng)內(nèi)容,通過上、下、左、右、回車、ESC 這 6 個(gè)按鍵可以調(diào)整時(shí)間。這也是一個(gè)具有綜合練習(xí)性質(zhì)的實(shí)例,雖然在功能實(shí)現(xiàn)上沒有多少難度,但要進(jìn)行的操作卻比較多而且煩瑣,同學(xué)們可以從中體會(huì)到把繁雜的功能實(shí)現(xiàn)分解為一步步函數(shù)操作的必要性以及方便靈活性。簡(jiǎn)單說一下這個(gè)程序的幾個(gè)要點(diǎn),方便大家閱讀理解程序。

把 DS1302 的底層操作封裝為一個(gè) DS1302.c 文件,對(duì)上層應(yīng)用提供基本的實(shí)時(shí)時(shí)間的操作接口,這個(gè)文件也是我們的又一個(gè)功能模塊了,我們的積累也越來越多了。

定義一個(gè)結(jié)構(gòu)體類型 sTime 用來封裝日期時(shí)間的各個(gè)元素,又用該結(jié)構(gòu)體定義了一個(gè)時(shí)間緩沖區(qū)變量 bufTime 來暫存從 DS1302 讀出的時(shí)間和設(shè)置時(shí)間時(shí)的設(shè)定值。需要注意的是在其它文件中要使用這個(gè)結(jié)構(gòu)體變量時(shí),必須首先再聲明一次 sTime 類型;

定義一個(gè)變量 setIndex 來控制當(dāng)前是否處于設(shè)置時(shí)間的狀態(tài),以及設(shè)置時(shí)間的哪一位,該值為 0 就表示正常運(yùn)行,1~12 分別代表可以修改日期時(shí)間的 12 個(gè)位;

由于這節(jié)課的程序功能要進(jìn)行時(shí)間調(diào)整,用到了 1602 液晶的光標(biāo)功能,添加了設(shè)置光標(biāo)的函數(shù),我們要改變哪一位的數(shù)字,就在 1602 對(duì)應(yīng)位置上進(jìn)行光標(biāo)閃爍,所以 Lcd1602.c在之前文件的基礎(chǔ)上添加了兩個(gè)控制光標(biāo)的函數(shù);

時(shí)間的顯示、增減、設(shè)置移位等上層功能函數(shù)都放在 main.c 中來實(shí)現(xiàn),當(dāng)按鍵需要這些函數(shù)時(shí)則在按鍵文件中做外部聲明,這樣做是為了避免一組功能函數(shù)分散在不同的文件內(nèi)而使程序顯得凌亂。

/***************************DS1302.c 文件程序源代碼*****************************/

#include 《reg52.h》

sbit DS1302_CE = P1^7;

sbit DS1302_CK = P3^5;

sbit DS1302_IO = P3^4;

struct sTime { //日期時(shí)間結(jié)構(gòu)體定義

unsigned int year; //年

unsigned char mon; //月

unsigned char day; //日

unsigned char hour; //時(shí)

unsigned char min; //分

unsigned char sec; //秒

unsigned char week; //星期

};

/* 發(fā)送一個(gè)字節(jié)到 DS1302 通信總線上 */

void DS1302ByteWrite(unsigned char dat){

unsigned char mask;

for (mask=0x01; mask!=0; mask《《=1){ //低位在前,逐位移出

if ((mask&dat) != 0){ //首先輸出該位數(shù)據(jù)

DS1302_IO = 1;

}else{

DS1302_IO = 0;

}

DS1302_CK = 1; //然后拉高時(shí)鐘

DS1302_CK = 0; //再拉低時(shí)鐘,完成一個(gè)位的操作

}

DS1302_IO = 1; //最后確保釋放 IO 引腳

}

/* 由 DS1302 通信總線上讀取一個(gè)字節(jié) */

unsigned char DS1302ByteRead(){

unsigned char mask;

unsigned char dat = 0;

for (mask=0x01; mask!=0; mask《《=1){ //低位在前,逐位讀取

if (DS1302_IO != 0){ //首先讀取此時(shí)的 IO 引腳,并設(shè)置 dat 中的對(duì)應(yīng)位

dat |= mask;

}

DS1302_CK = 1; //然后拉高時(shí)鐘

DS1302_CK = 0; //再拉低時(shí)鐘,完成一個(gè)位的操作

}

return dat; //最后返回讀到的字節(jié)數(shù)據(jù)

}

/* 用單次寫操作向某一寄存器寫入一個(gè)字節(jié),reg-寄存器地址,dat-待寫入字節(jié) */

void DS1302SingleWrite(unsigned char reg, unsigned char dat){

DS1302_CE = 1; //使能片選信號(hào)

DS1302ByteWrite((reg《《1)|0x80); //發(fā)送寫寄存器指令

DS1302ByteWrite(dat); //寫入字節(jié)數(shù)據(jù)

DS1302_CE = 0; //除能片選信號(hào)

}

/* 用單次讀操作從某一寄存器讀取一個(gè)字節(jié),reg-寄存器地址,返回值-讀到的字節(jié) */

unsigned char DS1302SingleRead(unsigned char reg){

unsigned char dat;

DS1302_CE = 1; //使能片選信號(hào)

DS1302ByteWrite((reg《《1)|0x81); //發(fā)送讀寄存器指令

dat = DS1302ByteRead(); //讀取字節(jié)數(shù)據(jù)

DS1302_CE = 0; //除能片選信號(hào)

return dat;

}

/* 用突發(fā)模式連續(xù)寫入 8 個(gè)寄存器數(shù)據(jù),dat-待寫入數(shù)據(jù)指針 */

void DS1302BurstWrite(unsigned char *dat){

unsigned char i;

DS1302_CE = 1;

DS1302ByteWrite(0xBE); //發(fā)送突發(fā)寫寄存器指令

for (i=0; i《8; i++){ //連續(xù)寫入 8 字節(jié)數(shù)據(jù)

DS1302ByteWrite(dat[i]);

}

DS1302_CE = 0;

}

/* 用突發(fā)模式連續(xù)讀取 8 個(gè)寄存器的數(shù)據(jù),dat-讀取數(shù)據(jù)的接收指針 */

void DS1302BurstRead(unsigned char *dat){

unsigned char i;

DS1302_CE = 1;

DS1302ByteWrite(0xBF); //發(fā)送突發(fā)讀寄存器指令

for (i=0; i《8; i++){ //連續(xù)讀取 8 個(gè)字節(jié)

dat[i] = DS1302ByteRead();

}

DS1302_CE = 0;

}

/* 獲取實(shí)時(shí)時(shí)間,即讀取 DS1302 當(dāng)前時(shí)間并轉(zhuǎn)換為時(shí)間結(jié)構(gòu)體格式 */

void GetRealTime(struct sTime *time){

unsigned char buf[8];

DS1302BurstRead(buf);

time-》year = buf[6] + 0x2000;

time-》mon = buf[4];

time-》day = buf[3];

time-》hour = buf[2];

time-》min = buf[1];

time-》sec = buf[0];

time-》week = buf[5];

}

/* 設(shè)定實(shí)時(shí)時(shí)間,時(shí)間結(jié)構(gòu)體格式的設(shè)定時(shí)間轉(zhuǎn)換為數(shù)組并寫入 DS1302 */

void SetRealTime(struct sTime *time){

unsigned char buf[8];

buf[7] = 0;

buf[6] = time-》year;

buf[5] = time-》week;

buf[4] = time-》mon;

buf[3] = time-》day;

buf[2] = time-》hour;

buf[1] = time-》min;

buf[0] = time-》sec;

DS1302BurstWrite(buf);

}

/* DS1302 初始化,如發(fā)生掉電則重新設(shè)置初始時(shí)間 */

void InitDS1302(){

unsigned char dat;

struct sTime code InitTime[] = { //2013 年 10 月 8 日 12:30:00 星期二

0x2013,0x10,0x08, 0x12,0x30,0x00, 0x02

};

DS1302_CE = 0; //初始化 DS1302 通信引腳

DS1302_CK = 0;

dat = DS1302SingleRead(0); //讀取秒寄存器

if ((dat & 0x80) != 0){ //由秒寄存器最高位 CH 的值判斷 DS1302 是否已停止

DS1302SingleWrite(7, 0x00); //撤銷寫保護(hù)以允許寫入數(shù)據(jù)

SetRealTime(&InitTime); //設(shè)置 DS1302 為默認(rèn)的初始時(shí)間

}

}

DS1302.c 最終向外提供出與具體時(shí)鐘芯片寄存器位置無(wú)關(guān)的、由時(shí)間結(jié)構(gòu)類型 sTime 作為接口的實(shí)時(shí)時(shí)間的讀取和設(shè)置函數(shù),如此處理體現(xiàn)了我們前面提到過的層次化編程的思想。應(yīng)用層可以不關(guān)心底層實(shí)現(xiàn)細(xì)節(jié),底層實(shí)現(xiàn)的改變也不會(huì)對(duì)應(yīng)用層造成影響,比如說日后你可能需要換一款時(shí)鐘芯片,而它與 DS1302 的操作和時(shí)間寄存器順序是不同的,那么你需要做的也僅是針對(duì)這款新的時(shí)鐘芯片設(shè)計(jì)出底層操作函數(shù),最終提供出同樣的以 sTime 為接口的操作函數(shù)即可,應(yīng)用層無(wú)需做任何的改動(dòng)。

/***************************Lcd1602.c 文件程序源代碼*****************************/

#include 《reg52.h》

#define LCD1602_DB P0

sbit LCD1602_RS = P1^0;

sbit LCD1602_RW = P1^1;

sbit LCD1602_E = P1^5;

/* 等待液晶準(zhǔn)備好 */

void LcdWaitReady(){

unsigned char sta;

LCD1602_DB = 0xFF;

LCD1602_RS = 0;

LCD1602_RW = 1;

do {

LCD1602_E = 1;

sta = LCD1602_DB; //讀取狀態(tài)字

LCD1602_E = 0;

} while (sta & 0x80); //bit7 等于 1 表示液晶正忙,重復(fù)檢測(cè)直到其等于 0 為止

}

/* 向 LCD1602 液晶寫入一字節(jié)命令,cmd-待寫入命令值 */

void LcdWriteCmd(unsigned char cmd){

LcdWaitReady();

LCD1602_RS = 0;

LCD1602_RW = 0;

LCD1602_DB = cmd;

LCD1602_E = 1;

LCD1602_E = 0;

}

/* 向 LCD1602 液晶寫入一字節(jié)數(shù)據(jù),dat-待寫入數(shù)據(jù)值 */

void LcdWriteDat(unsigned char dat){

LcdWaitReady();

LCD1602_RS = 1;

LCD1602_RW = 0;

LCD1602_DB = dat;

LCD1602_E = 1;

LCD1602_E = 0;

}

/* 設(shè)置顯示 RAM 起始地址,亦即光標(biāo)位置,(x,y)-對(duì)應(yīng)屏幕上的字符坐標(biāo) */

void LcdSetCursor(unsigned char x, unsigned char y){

unsigned char addr;

if (y == 0){ //由輸入的屏幕坐標(biāo)計(jì)算顯示 RAM 的地址

addr = 0x00 + x; //第一行字符地址從 0x00 起始

}else{

addr = 0x40 + x; //第二行字符地址從 0x40 起始

}

LcdWriteCmd(addr | 0x80); //設(shè)置 RAM 地址

}

/* 在液晶上顯示字符串,(x,y)-對(duì)應(yīng)屏幕上的起始坐標(biāo),str-字符串指針 */

void LcdShowStr(unsigned char x, unsigned char y, unsigned char *str){

LcdSetCursor(x, y); //設(shè)置起始地址

while (*str != ‘\0’){ //連續(xù)寫入字符串?dāng)?shù)據(jù),直到檢測(cè)到結(jié)束符

LcdWriteDat(*str++);

}

}

/* 打開光標(biāo)的閃爍效果 */

void LcdOpenCursor(){

LcdWriteCmd(0x0F);

}

/* 關(guān)閉光標(biāo)顯示 */

void LcdCloseCursor(){

LcdWriteCmd(0x0C);

}

/* 初始化 1602 液晶 */

void InitLcd1602(){

LcdWriteCmd(0x38); //16*2 顯示,5*7 點(diǎn)陣,8 位數(shù)據(jù)接口

LcdWriteCmd(0x0C); //顯示器開,光標(biāo)關(guān)閉

LcdWriteCmd(0x06); //文字不動(dòng),地址自動(dòng)+1

LcdWriteCmd(0x01); //清屏

}

為了本例的具體需求,在之前文件的基礎(chǔ)上添加兩個(gè)控制光標(biāo)效果打開和關(guān)閉的函數(shù),雖然函數(shù)都很簡(jiǎn)單,但為了保持程序整體上良好的模塊化和層次化,還是應(yīng)該在液晶驅(qū)動(dòng)文件內(nèi)以函數(shù)的形式提供,而不是由應(yīng)用層代碼直接來調(diào)用具體的液晶寫命令操作。

/***************************keyboard.c 文件程序源代碼****************************/

(此處省略,可參考之前章節(jié)的代碼)

/*****************************main.c 文件程序源代碼******************************/

#include 《reg52.h》

struct sTime { //日期時(shí)間結(jié)構(gòu)體定義

unsigned int year;

unsigned char mon;

unsigned char day;

unsigned char hour;

unsigned char min;

unsigned char sec;

unsigned char week;

};

bit flag200ms = 1; //200ms 定時(shí)標(biāo)志

struct sTime bufTime; //日期時(shí)間緩沖區(qū)

unsigned char setIndex = 0; //時(shí)間設(shè)置索引

unsigned char T0RH = 0; //T0 重載值的高字節(jié)

unsigned char T0RL = 0; //T0 重載值的低字節(jié)

void ConfigTimer0(unsigned int ms);

void RefreshTimeShow();

extern void InitDS1302();

extern void GetRealTime(struct sTime *time);

extern void SetRealTime(struct sTime *time);

extern void KeyScan();

extern void KeyDriver();

extern void InitLcd1602();

extern void LcdShowStr(unsigned char x, unsigned char y, unsigned char *str);

extern void LcdSetCursor(unsigned char x, unsigned char y);

extern void LcdOpenCursor();

extern void LcdCloseCursor();

void main(){

unsigned char psec=0xAA; //秒備份,初值 AA 確保首次讀取時(shí)間后會(huì)刷新顯示

EA = 1; //開總中斷

ConfigTimer0(1); //T0 定時(shí) 1ms

InitDS1302(); //初始化實(shí)時(shí)時(shí)鐘

InitLcd1602(); //初始化液晶

//初始化屏幕上固定不變的內(nèi)容

LcdShowStr(3, 0, “20 - - ”);

LcdShowStr(4, 1, “ : : ”);

while (1){

KeyDriver(); //調(diào)用按鍵驅(qū)動(dòng)

if (flag200ms && (setIndex == 0)){ //每隔 200ms 且未處于設(shè)置狀態(tài)時(shí),

flag200ms = 0;

GetRealTime(&bufTime); //獲取當(dāng)前時(shí)間

if (psec != bufTime.sec){ //檢測(cè)到時(shí)間有變化時(shí)刷新顯示

RefreshTimeShow();

psec = bufTime.sec; //用當(dāng)前值更新上次秒數(shù)

}

}

}

}

/* 將一個(gè) BCD 碼字節(jié)顯示到屏幕上,(x,y)-屏幕起始坐標(biāo),bcd-待顯示 BCD 碼 */

void ShowBcdByte(unsigned char x, unsigned char y, unsigned char bcd){

unsigned char str[4];

str[0] = (bcd 》》 4) + ‘0’;

str[1] = (bcd&0x0F) + ‘0’;

str[2] = ‘\0’;

LcdShowStr(x, y, str);

}

/* 刷新日期時(shí)間的顯示 */

void RefreshTimeShow(){

ShowBcdByte(5, 0, bufTime.year);

ShowBcdByte(8, 0, bufTime.mon);

ShowBcdByte(11, 0, bufTime.day);

ShowBcdByte(4, 1, bufTime.hour);

ShowBcdByte(7, 1, bufTime.min);

ShowBcdByte(10, 1, bufTime.sec);

}

/* 刷新當(dāng)前設(shè)置位的光標(biāo)指示 */

void RefreshSetShow(){

switch (setIndex){

case 1: LcdSetCursor(5, 0); break;

case 2: LcdSetCursor(6, 0); break;

case 3: LcdSetCursor(8, 0); break;

case 4: LcdSetCursor(9, 0); break;

case 5: LcdSetCursor(11, 0); break;

case 6: LcdSetCursor(12, 0); break;

case 7: LcdSetCursor(4, 1); break;

case 8: LcdSetCursor(5, 1); break;

case 9: LcdSetCursor(7, 1); break;

case 10: LcdSetCursor(8, 1); break;

case 11: LcdSetCursor(10, 1); break;

case 12: LcdSetCursor(11, 1); break;

default: break;

}

}

/* 遞增一個(gè) BCD 碼的高位 */

unsigned char IncBcdHigh(unsigned char bcd){

if ((bcd&0xF0) 《 0x90){

bcd += 0x10;

}else{

bcd &= 0x0F;

}

return bcd;

}

/* 遞增一個(gè) BCD 碼的低位 */

unsigned char IncBcdLow(unsigned char bcd){

if ((bcd&0x0F) 《 0x09){

bcd += 0x01;

}else{

bcd &= 0xF0;

}

return bcd;

}

/* 遞減一個(gè) BCD 碼的高位 */

unsigned char DecBcdHigh(unsigned char bcd){

if ((bcd&0xF0) 》 0x00){

bcd -= 0x10;

}else{

bcd |= 0x90;

}

return bcd;

}

/* 遞減一個(gè) BCD 碼的低位 */

unsigned char DecBcdLow(unsigned char bcd){

if ((bcd&0x0F) 》 0x00){

bcd -= 0x01;

}else{

bcd |= 0x09;

}

return bcd;

}

/* 遞增時(shí)間當(dāng)前設(shè)置位的值 */

void IncSetTime(){

switch (setIndex){

case 1: bufTime.year = IncBcdHigh(bufTime.year); break;

case 2: bufTime.year = IncBcdLow(bufTime.year); break;

case 3: bufTime.mon = IncBcdHigh(bufTime.mon); break;

case 4: bufTime.mon = IncBcdLow(bufTime.mon); break;

case 5: bufTime.day = IncBcdHigh(bufTime.day); break;

case 6: bufTime.day = IncBcdLow(bufTime.day); break;

case 7: bufTime.hour = IncBcdHigh(bufTime.hour); break;

case 8: bufTime.hour = IncBcdLow(bufTime.hour); break;

case 9: bufTime.min = IncBcdHigh(bufTime.min); break;

case 10: bufTime.min = IncBcdLow(bufTime.min); break;

case 11: bufTime.sec = IncBcdHigh(bufTime.sec); break;

case 12: bufTime.sec = IncBcdLow(bufTime.sec); break;

default: break;

}

RefreshTimeShow();

RefreshSetShow();

}

/* 遞減時(shí)間當(dāng)前設(shè)置位的值 */

void DecSetTime(){

switch (setIndex){

case 1: bufTime.year = DecBcdHigh(bufTime.year); break;

case 2: bufTime.year = DecBcdLow(bufTime.year); break;

case 3: bufTime.mon = DecBcdHigh(bufTime.mon); break;

case 4: bufTime.mon = DecBcdLow(bufTime.mon); break;

case 5: bufTime.day = DecBcdHigh(bufTime.day); break;

case 6: bufTime.day = DecBcdLow(bufTime.day); break;

case 7: bufTime.hour = DecBcdHigh(bufTime.hour); break;

case 8: bufTime.hour = DecBcdLow(bufTime.hour); break;

case 9: bufTime.min = DecBcdHigh(bufTime.min); break;

case 10: bufTime.min = DecBcdLow(bufTime.min); break;

case 11: bufTime.sec = DecBcdHigh(bufTime.sec); break;

case 12: bufTime.sec = DecBcdLow(bufTime.sec);

default: break;

}

RefreshTimeShow();

RefreshSetShow();

}

/* 右移時(shí)間設(shè)置位 */

void RightShiftTimeSet(){

if (setIndex != 0){

if (setIndex 《 12){

setIndex++;

}else{

setIndex = 1;

}

RefreshSetShow();

}

}

/* 左移時(shí)間設(shè)置位 */

void LeftShiftTimeSet(){

if (setIndex != 0){

if (setIndex 》 1){

setIndex--;

}else{

setIndex = 12;

}

RefreshSetShow();

}

}

/* 進(jìn)入時(shí)間設(shè)置狀態(tài) */

void EnterTimeSet(){

setIndex = 2; //把設(shè)置索引設(shè)置為 2,即可進(jìn)入設(shè)置狀態(tài)

LeftShiftTimeSet(); //再利用現(xiàn)成的左移操作移到位置 1 并完成顯示刷新

LcdOpenCursor(); //打開光標(biāo)閃爍效果

}

/* 退出時(shí)間設(shè)置狀態(tài),save-是否保存當(dāng)前設(shè)置的時(shí)間值 */

void ExitTimeSet(bit save){

setIndex = 0; //把設(shè)置索引設(shè)置為 0,即可退出設(shè)置狀態(tài)

if (save){ //需保存時(shí)即把當(dāng)前設(shè)置時(shí)間寫入 DS1302

SetRealTime(&bufTime);

}

LcdCloseCursor(); //關(guān)閉光標(biāo)顯示

}

/* 按鍵動(dòng)作函數(shù),根據(jù)鍵碼執(zhí)行相應(yīng)的操作,keycode-按鍵鍵碼 */

void KeyAction(unsigned char keycode){

if ((keycode》=‘0’) && (keycode《=‘9’)){ //本例中不響應(yīng)字符鍵

}else if (keycode == 0x26){ //向上鍵,遞增當(dāng)前設(shè)置位的值

IncSetTime();

}else if (keycode == 0x28){ //向下鍵,遞減當(dāng)前設(shè)置位的值

DecSetTime();

}else if (keycode == 0x25){ //向左鍵,向左切換設(shè)置位

LeftShiftTimeSet();

}else if (keycode == 0x27){ //向右鍵,向右切換設(shè)置位

RightShiftTimeSet();

}else if (keycode == 0x0D){ //回車鍵,進(jìn)入設(shè)置模式/啟用當(dāng)前設(shè)置值

if (setIndex == 0){ //不處于設(shè)置狀態(tài)時(shí),進(jìn)入設(shè)置狀態(tài)

EnterTimeSet();

}else{ //已處于設(shè)置狀態(tài)時(shí),保存時(shí)間并退出設(shè)置狀態(tài)

ExitTimeSet(1);

}

}else if (keycode == 0x1B){ //Esc 鍵,取消當(dāng)前設(shè)置

ExitTimeSet(0);

}

}

/* 配置并啟動(dòng) T0,ms-T0 定時(shí)時(shí)間 */

void ConfigTimer0(unsigned int ms){

unsigned long tmp; //臨時(shí)變量

tmp = 11059200 / 12; //定時(shí)器計(jì)數(shù)頻率

tmp = (tmp * ms) / 1000; //計(jì)算所需的計(jì)數(shù)值

tmp = 65536 - tmp; //計(jì)算定時(shí)器重載值

tmp = tmp + 28; //補(bǔ)償中斷響應(yīng)延時(shí)造成的誤差

T0RH = (unsigned char)(tmp》》8); //定時(shí)器重載值拆分為高低字節(jié)

T0RL = (unsigned char)tmp;

TMOD &= 0xF0; //清零 T0 的控制位

TMOD |= 0x01; //配置 T0 為模式 1

TH0 = T0RH; //加載 T0 重載值

TL0 = T0RL;

ET0 = 1; //使能 T0 中斷

TR0 = 1; //啟動(dòng) T0

}

/* T0 中斷服務(wù)函數(shù),執(zhí)行按鍵掃描和 200ms 定時(shí) */

void InterruptTimer0() interrupt 1{

static unsigned char tmr200ms = 0;

TH0 = T0RH; //重新加載重載值

TL0 = T0RL;

KeyScan(); //按鍵掃描

tmr200ms++;

if (tmr200ms 》= 200){ //定時(shí) 200ms

tmr200ms = 0;

flag200ms = 1;

}

}

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • 模塊
    +關(guān)注

    關(guān)注

    7

    文章

    2838

    瀏覽量

    53322
  • 函數(shù)
    +關(guān)注

    關(guān)注

    3

    文章

    4418

    瀏覽量

    67597
  • 源代碼
    +關(guān)注

    關(guān)注

    96

    文章

    2953

    瀏覽量

    70397
收藏 人收藏
加入交流群
微信小助手二維碼

掃碼添加小助手

加入工程師交流群

    評(píng)論

    相關(guān)推薦
    熱點(diǎn)推薦

    嵌入式電子時(shí)鐘硬核進(jìn)化史:從單片機(jī)到網(wǎng)絡(luò)對(duì)時(shí)

    在現(xiàn)代科技生活中,電子時(shí)鐘似乎是最不起眼的存在。然而,對(duì)于嵌入式工程師和極客而言,嵌入式電子時(shí)鐘不僅是一個(gè)計(jì)時(shí)工具,更是硬件控制、低功耗設(shè)計(jì)與軟件算法的集大成者。從早年單純的單片機(jī)計(jì)數(shù),到如今支持NTP網(wǎng)絡(luò)對(duì)時(shí)的高精度設(shè)備,這塊
    的頭像 發(fā)表于 03-10 11:31 ?125次閱讀
    嵌入式<b class='flag-5'>電子時(shí)鐘</b>硬核進(jìn)化史:從<b class='flag-5'>單片機(jī)</b>到網(wǎng)絡(luò)對(duì)時(shí)

    請(qǐng)問單片機(jī)開發(fā)的程序設(shè)計(jì)語(yǔ)言主要有哪幾種?

    單片機(jī)開發(fā)的程序設(shè)計(jì)語(yǔ)言主要有哪幾種?
    發(fā)表于 01-14 08:29

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

    的 12 個(gè)位; 4. 由于這節(jié)課的程序功能要進(jìn)行時(shí)間調(diào)整,用到了 1602 液晶的光標(biāo)功能,添加了設(shè)置光標(biāo)的函數(shù),我們要改變哪一位的數(shù)字,就在 1602 對(duì)應(yīng)位置上進(jìn)行光標(biāo)閃爍,所以 Lcd1602.c在
    發(fā)表于 01-05 06:21

    【EASY EAI Nano-TB(RV1126B)開發(fā)板試用】+電子時(shí)鐘計(jì)時(shí)效果的實(shí)現(xiàn)

    在實(shí)現(xiàn)串行數(shù)碼管顯示模塊驅(qū)動(dòng)的情況下,通過與延時(shí)函數(shù)的配合即可實(shí)現(xiàn)電子時(shí)鐘計(jì)時(shí)效果。 其程序內(nèi)容為: 運(yùn)行腳本程序的方法如圖1所示,其運(yùn)行效果見圖2所示。 圖1 運(yùn)行方法 圖2 運(yùn)行效果 演示視頻:
    發(fā)表于 12-24 19:17

    編寫簡(jiǎn)單高效單片機(jī)匯編程序

    1、使用模塊化結(jié)構(gòu):分解功能塊 模塊化編程讓代碼更清晰,并能提高代碼的復(fù)用性。 例如,對(duì)于電子時(shí)鐘程序,可以將代碼分為顯示模塊、按鍵處理模塊、計(jì)時(shí)模塊、定時(shí)器中斷服務(wù)程序等。 每個(gè)模塊處理相對(duì)
    發(fā)表于 11-24 07:00

    NTP電子時(shí)鐘系統(tǒng):安徽京準(zhǔn)提升醫(yī)院高效運(yùn)行

    NTP電子時(shí)鐘系統(tǒng):安徽京準(zhǔn)提升醫(yī)院高效運(yùn)行
    的頭像 發(fā)表于 10-31 14:11 ?424次閱讀
    NTP<b class='flag-5'>電子時(shí)鐘</b>系統(tǒng):安徽京準(zhǔn)提升醫(yī)院高效運(yùn)行

    單片機(jī)電路設(shè)計(jì)必讀:電容選用的五大關(guān)鍵原則

    表現(xiàn)。電容在單片機(jī)電路中的核心作用單片機(jī)的穩(wěn)定運(yùn)行離不開電容的保駕護(hù)航。去耦電容用于消除電源噪聲,耦合電容負(fù)責(zé)信號(hào)傳輸,起振電容確保時(shí)鐘精準(zhǔn),復(fù)位電容保障系統(tǒng)啟動(dòng)可靠。這些看似簡(jiǎn)單的
    的頭像 發(fā)表于 10-23 15:40 ?626次閱讀
    <b class='flag-5'>單片機(jī)電</b>路設(shè)計(jì)必讀:電容選用的五大關(guān)鍵原則

    【RA4M2-SENSOR】+RTC與電子時(shí)鐘

    , .tm_wday = 5, }; 在配有串口通訊功能的情況下,實(shí)現(xiàn)電子時(shí)鐘效果的主程序為: void hal_entry(void) { err = R_SCI_UART_Open(&
    發(fā)表于 09-03 12:08

    怎么測(cè)單片機(jī)系統(tǒng)頻率

    單片機(jī)系統(tǒng)頻率是指單片機(jī)工作時(shí)的時(shí)鐘頻率,它直接影響單片機(jī)的運(yùn)行速度和處理能力,準(zhǔn)確測(cè)量系統(tǒng)頻率對(duì)單片機(jī)應(yīng)用開發(fā)、
    的頭像 發(fā)表于 07-25 11:39 ?841次閱讀

    【RA-Eco-RA6M4開發(fā)板評(píng)測(cè)】+電子時(shí)鐘的實(shí)現(xiàn)

    ; } OLED_ShowChar(x+(size2/2)*t,y,temp+\'0\',size2); } } 隨后,在主程序中搭建一個(gè)計(jì)時(shí)進(jìn)制處理便可實(shí)現(xiàn)電子時(shí)鐘的功效,其主程序的內(nèi)容為: void
    發(fā)表于 07-23 21:03

    單片機(jī)怎么燒程序

    單片機(jī)程序是將編寫好的程序代碼寫入單片機(jī)內(nèi)部存儲(chǔ)單元,讓單片機(jī)按照預(yù)設(shè)邏輯工作的過程,是單片機(jī)
    的頭像 發(fā)表于 07-23 11:47 ?1418次閱讀

    STC單片機(jī)范例程序

    電子發(fā)燒友網(wǎng)站提供《STC單片機(jī)范例程序.zip》資料免費(fèi)下載
    發(fā)表于 06-04 16:27 ?10次下載

    4G無(wú)線電子時(shí)鐘助力智慧城市建設(shè)

    4G無(wú)線電子時(shí)鐘是一種通過4G網(wǎng)絡(luò)實(shí)現(xiàn)時(shí)間同步和數(shù)據(jù)傳輸?shù)闹悄?b class='flag-5'>時(shí)鐘設(shè)備,具有實(shí)時(shí)精準(zhǔn)、遠(yuǎn)程管理、多功能集成等特點(diǎn),其應(yīng)用場(chǎng)景廣泛,涵蓋多個(gè)領(lǐng)域,以下是具體介紹: 一、公共服務(wù)與市政設(shè)施場(chǎng)景 1.城市
    的頭像 發(fā)表于 05-26 15:50 ?743次閱讀

    電子時(shí)鐘#

    電子時(shí)鐘
    jf_63683381
    發(fā)布于 :2025年05月08日 17:25:18

    時(shí)空刻度:LED電子時(shí)鐘系統(tǒng)如何重塑現(xiàn)代節(jié)奏

    ?高鐵站臺(tái)的安全倒計(jì)時(shí)在暴雨中清晰閃爍,體育場(chǎng)館的24秒進(jìn)攻時(shí)鐘與裁判哨聲嚴(yán)絲合縫,跨國(guó)企業(yè)總部的大樓立面時(shí)鐘同步切換三大時(shí)區(qū)——這些精準(zhǔn)的視覺化時(shí)間表達(dá),由LED電子時(shí)鐘系統(tǒng)在毫秒維度構(gòu)建的時(shí)空坐標(biāo)系支撐。
    的頭像 發(fā)表于 03-16 17:25 ?962次閱讀
    時(shí)空刻度:LED<b class='flag-5'>電子時(shí)鐘</b>系統(tǒng)如何重塑現(xiàn)代節(jié)奏