是一按键程序?我想了好久,看代码是没有问题的,可问题还是有好多?
第一点:没有按键是,自退出设置状态(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;
}
} |