一个很好的单片机按键处理子程序
时间:11-30
来源:互联网
点击:
这是一个用于实际产品的stc单片机按键处理程序头文件和原理图可从原帖下载:http://www.51hei.com/bbs/dpj-19294-1.html
#include "STC12C5620AD.H"#include "Key_Scan.H"#include "Key_Handle.H"#include "DS1302.H"#include "Radio.H"#include "Channel_Handle.H"#include "Volume_Handle.H"/********************** 声明外部变量**************************/extern uchar Volume; //Volume_Handle.cextern uint PLL; //From Radio.cextern bit Flag_40ms; //From Main.cextern uchar Work_Mode; //From Main.cextern uchar data Sec; //From DS1302.cextern uchar data Min; //From DS1302.cextern uchar data Hour; //From DS1302.cextern uchar data Date; //From DS1302.cextern uchar data Month; //From DS1302.cextern uchar data Day; //From DS1302.cextern uchar data Year; //From DS1302.cextern uchar Display_Channel[]; //From Main.c/********************** 定义变量**************************/uchar Radio_Index; //预置电台切换计数,0-15,8用于记录最后一次的电台uchar Key_Flag=0x00; //按键计时,有按键时清零,无按键10S左右使Woke_Mode=0;/********************** 按键处理**************************/void Key_Handle(){uchar Time_Write_Temp; //调整用的缓存uchar Key_Value;Radio_Index=EEPROM_Get_Index(); //获取频道序号Display_Channel[3]=(Radio_Index/10)|0x30; Display_Channel[4]=(Radio_Index%10)|0x30; //显示频道序号if(Flag_40ms){Key_Value=Key_Scan(); //40ms进行一次扫描Flag_40ms=0;Key_Flag++;if(Key_Flag>=250){Key_Flag=250;LCD_BLK=0;Work_Mode=0; //无按键10s后,自动回到模式0}elseLCD_BLK=1;}switch (Key_Value){case 0x0e: //按下MENUswitch (Work_Mode){case 0:Work_Mode=1; //进入电台搜索break;case 1:Work_Mode=2; //进入调节年份break;case 2:Work_Mode=3; //进入调节月份break;case 3:Work_Mode=4; //进入调节日break;case 4:Work_Mode=5; //进入调节星期break;case 5:Work_Mode=6; //进入调节时break;case 6:Work_Mode=7; //进入调节分break;case 7:DS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x80,0x00); //秒置0DS1302_Write_Data(0x8e,0x80); // 开启写保护Work_Mode=0; //回到正常显示break;default:break;}Key_Flag=0; //清除按键计时break;case 0x0d: //按下|>4)*10+(Year&0x0f); //装换成十进制数if(Time_Write_Temp==0){Time_Write_Temp=99;}else{Time_Write_Temp--;}Year=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x8c,Year); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 3: //月减少 Time_Write_Temp=(Month>>4)*10+(Month&0x0f); //装换成十进制数if(Time_Write_Temp==1){Time_Write_Temp=12;}else{Time_Write_Temp--;}Month=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x88,Month); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 4: //日减少 Time_Write_Temp=(Date>>4)*10+(Date&0x0f); //装换成十进制数if(Time_Write_Temp==1){Time_Write_Temp=31;}else{Time_Write_Temp--;}Date=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x86,Date); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 5: //星期减少 Time_Write_Temp=(Day>>4)*10+(Day&0x0f); //装换成十进制数if(Time_Write_Temp==1){Time_Write_Temp=7;}else{Time_Write_Temp--;}Day=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x8a,Day); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 6: //时减少 Time_Write_Temp=(Hour>>4)*10+(Hour&0x0f); //装换成十进制数if(Time_Write_Temp==0){Time_Write_Temp=23;}else{Time_Write_Temp--;}Hour=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x84,Hour); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 7: //分减少 Time_Write_Temp=(Min>>4)*10+(Min&0x0f); //装换成十进制数if(Time_Write_Temp==0){Time_Write_Temp=59;}else{Time_Write_Temp--;}Min=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x82,Min); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 8: //音量调节Volume+=5; //音量减小5dBif(Volume>=35)Volume=35;Volume_Write(Volume); //写入声音参数break;default:break;}Key_Flag=0; //清除按键计时break;case 0x0b: //按下>>|switch (Work_Mode){case 0: //正常状态Radio_Index++; //下一个预置电台if(Radio_Index==16)Radio_Index=1;EEPROM_Write_Index(Radio_Index); //更新新电台序号PLL=EEPROM_Get_PLL(Radio_Index); //更新新电台PLLTEA5767_Update_PLL(); //写入PLLbreak;case 1:TEA5767_User_Search(1); //向上手动搜索break;case 2: //年增加 Time_Write_Temp=(Year>>4)*10+(Year&0x0f); //装换成十进制数if(Time_Write_Temp==99){Time_Write_Temp=0;}else{Time_Write_Temp++;}Year=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x8c,Year); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 3: //月增加 Time_Write_Temp=(Month>>4)*10+(Month&0x0f); //装换成十进制数if(Time_Write_Temp==12){Time_Write_Temp=1;}else{Time_Write_Temp++;}Month=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x88,Month); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 4: //日增加 Time_Write_Temp=(Date>>4)*10+(Date&0x0f); //装换成十进制数if(Time_Write_Temp==31){Time_Write_Temp=1;}else{Time_Write_Temp++;}Date=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x86,Date); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 5: //星期增加 Time_Write_Temp=(Day>>4)*10+(Day&0x0f); //装换成十进制数if(Time_Write_Temp==7){Time_Write_Temp=1;}else{Time_Write_Temp++;}Day=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x8a,Day); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 6: //时增加 Time_Write_Temp=(Hour>>4)*10+(Hour&0x0f); //装换成十进制数if(Time_Write_Temp==23){Time_Write_Temp=0;}else{Time_Write_Temp++;}Hour=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x84,Hour); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 7: //分增加 Time_Write_Temp=(Min>>4)*10+(Min&0x0f); //装换成十进制数if(Time_Write_Temp==59){Time_Write_Temp=0;}else{Time_Write_Temp++;}Min=(Time_Write_Temp/10)<4|(Time_Write_Temp%10); //装换成BCDDS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x82,Min); //写入DS1302_Write_Data(0x8e,0x80); // 开启写保护break;case 8: //音量调节if(Volume<=0)Volume=0; elseVolume-=5; //音量增加5dBVolume_Write(Volume); //写入声音参数break;default:break;}Key_Flag=0; //清除按键计时break;case 0x07: //按下SET{ switch (Work_Mode){case 0: //正常状态Work_Mode=8; //转到音量调节状态break;case 1: //电台搜索EEPROM_Save_PLL(Radio_Index,PLL); //存入新收到的电台Work_Mode=0;break;case 8: //音量调节状态Work_Mode=0; //转到正常状态break;default:DS1302_Write_Data(0x8e,0x00); // 禁止写保护DS1302_Write_Data(0x80,0x00); //置秒为00,并启动时钟DS1302_Write_Data(0x8e,0x80); // 开启写保护Work_Mode=0;break;} }Key_Flag=0; //清除按键计时break;default:break;} }
单片机按键处理子程 相关文章:
- Windows CE 进程、线程和内存管理(11-09)
- RedHatLinux新手入门教程(5)(11-12)
- uClinux介绍(11-09)
- openwebmailV1.60安装教学(11-12)
- Linux嵌入式系统开发平台选型探讨(11-09)
- Windows CE 进程、线程和内存管理(二)(11-09)