是一按键程序?我想了好久,看代码是没有问题的,可问题还是有好多? 第一点:没有按键是,自退出设置状态(SetupFlag为设置标志),可现在没有退出(重要) 第二点:按键锁键后,没有办法开锁(重要) 第三点:红色代码部分只能放在那个位置,如果放在程序的最后,按键就不工作了
以上3点,各位看官能不能帮小弟解答下,小弟感激涕零啊!!!!!!
和个变量说明: SetupFlag 设置标志 KEY_DoFlag 按键是否执行 KEY_NUM 现在的键码 KEY_BUF 备份键 KEY_JSQ 按键计时器 KEY_LA_DL 连按延时 KEY_CJ_DL 长按延时 LockedFlag 锁键标志
这个按键子程序10MS调用一次....
新版论坛开张后,重要的第一帖////////////,祝新版论坛蒸蒸日上
void Key_Function (void) {
KEY_NUM = KeyScan(); if(!LockedFlag) { //获取按键码,实际可以使用其它键盘扫描程序 if((KEY_NUM!=0)&&(KEY_NUM == KEY_BUF)) //如果按键有效,不是空键而且和上次相同 { NOKEY_JSQ=0; Fah_JSQ=0; if(!KEY_DoFlag) //如果按键没有进行处理 { KEY_JSQ++; if(SetupFlag) { if(!KEY_LaFlag) //如果还没有开始处理循环长按 { if(KEY_JSQ>=KEY_LA_DL) KEY_LaFlag = 1; //如果延时大于循环处理其实条件 } if(KEY_LaFlag) //如果已经是循环处理 { DoubleHitFlash=1; if(KEY_JSQ>=KEY_LA_DL) //而且延时大于循环处理延时(时间越小处理愉快) { switch(KEY_NUM) { case 3:{ switch(SetCounter) { case 1: Timer.Hou =Set_HouUp(Timer.Hou); break; case 2: Timer.Min =Set_MinUp(Timer.Min); break; } KEY_JSQ = 0; //计数器清零 } break; case 4:{ switch(SetCounter) { case 1: Timer.Hou =Set_HouDon(Timer.Hou); break; case 2: Timer.Min =Set_MinDon(Timer.Min); break; } KEY_JSQ=0; } break; } } } } else if(KEY_JSQ>=KEY_CJ_DL) //当大于设定长击时间时判断为长击按键类型,在这种状态下,没有进入设置状态。,进行的长按 { switch(KEY_NUM) { case 5:{ //这里长按是可以正常锁键的 LockedFlag=1; //锁键 KEY_DoFlag=1; KEY_JSQ=0; SetupFlag=0; SetCounter=0; Sp_Mode=3; EN_SpeakerFlag=1; } break; } } KEY_BUF=KEY_NUM; //记录新键码 } } else //如果按键已经松开或者按键无效(前后不相同) { if((!KEY_DoFlag)&&(KEY_JSQ >= KEY_XD_DL)&&((!KEY_LaFlag)||(KEY_JSQ<KEY_CJ_DL))&&(!LockedFlag)) //按键没有处理,并且延时满足,而且没有进入循环按键处理 { if(SetupFlag) //表明已进入设置状态 { switch(KEY_BUF) { case 5:{ Do_Set(); KEY_DoFlag=1; Sp_Mode=3; EN_SpeakerFlag=1; KEY_JSQ=0; } break; } KEY_LaFlag = 0; //循环处理标志清零 允许处理如果一真为1则不允许处理 KEY_JSQ = 0; //计数器清零 } else{ if(!SetupFlag) //不是设置状态,且不是长击 { switch(KEY_BUF) { case 5:{ SetupFlag=1; GetTimeFlag=0; SetCounter=1; Display_Mode=2; EN_SpeakerFlag=1; Sp_Mode=3; KEY_DoFlag=1; KEY_JSQ=0; } break; } } } } KEY_BUF=KEY_NUM; //更新当前键值(即有按键更新为按键键值,无按键更新为0) KEY_DoFlag=0; KEY_LaFlag=0; KEY_JSQ=0; } } else { if((KEY_NUM==1)||(KEY_NUM==2)||(KEY_NUM==3)||(KEY_NUM==4)||(KEY_NUM==5)||(KEY_NUM==6)) //如果是锁键状态,那么按12346键显示状态4 { Display_Mode=4; //这个地方理论来说,如果按住5号键,长按时,就会解锁键盘,可实际情况没有解锁 if(KEY_NUM==5){ if(!KEY_DoFlag) { KEY_JSQ++; if(KEY_JSQ>KEY_CJ_DL) { LockedFlag=0; //解锁 KEY_DoFlag=1; Display_Mode=1; //一旦解锁,显示状态1,并将计时器清零 // KEY_JSQ=0; EN_SpeakerFlag=1; Sp_Mode=3; SetupFlag=0; } KEY_BUF=KEY_NUM; KEY_DoFlag=0; } } } } //在这个位置按理说,是没有按键时执行的代码,如果没有锁键,NOKEY_JSQ是继续加 如是在设置状态且NOKEY_JSQ>1000后,就会自动退出设置态,过一会,就会自动锁键,可现在要命的是,没有按键且在设置态时,不会自动退出,也不会锁键 if(!LockedFlag) NOKEY_JSQ++; //这里应当做好,在按键锁状态 else NOKEY_JSQ=0; Fah_JSQ++; if(Fah_JSQ>=50) { Fah_JSQ=0; DoubleHitFlash=0; } //如果在500MS内没有按键则闪,如果有则不闪 if(SetupFlag&&(NOKEY_JSQ>=1000)) //如果在显示模式2,10秒无按键,回到显示模式1 然后在经过30秒锁键 { Display_Mode=1; SetupFlag=0; SetCounter=0; GetTimeFlag=1; Sp_Mode=2; EN_SpeakerFlag=1; } else if(NOKEY_JSQ>3000) //无按键30秒锁 { LockedFlag=1; Sp_Mode=2; //按键锁后长鸣一声 EN_SpeakerFlag=1; NOKEY_JSQ=0; } } |