线反转法扫描矩阵程序
uchar key(void){
uchar key,key1,key2,k;
P1=0XF0;
k=0xff;
if((P1&0XF0)!=0XF0)
{
delay();
if((P1&0XF0)!=0XF0)
key1=P1&0XF0;
P1=0X0F;
if((P1&0X0F)!=0X0F)
{
delay();
if((P1&0X0F)!=0X0F)
{
key2=P1&0X0F;
key=key1|key2;
if(key!=0xff)
{
switch(key)
{
case 0xee: k=0;break;
case 0xed: k=1;break;
case 0xeb: k=2;break;
case 0xe7: k=3; break;
case 0xde: k=4;break;
case 0xdd: k=5;break;
case 0xdb: k=6;break;
case 0xd7: k=7; break;
case 0xbe: k=8;break;
case 0xbd: k=9;break;
case 0xbb: k=10;break;
case 0xb7: k=11; break;
case 0x7e: k=12;break;
case 0x7d: k=13;break;
case 0x7b: k=14;break;
case 0x77: k=15; break;
}
}
}
}
}
return(k);
}
只做了键盘扫描程序,说明问题, 代码太多没必要,刚在另一帖子里回的,顺手复制过来吧, 假定4X4,使用P1口反转扫描法:
unsigned char keystatus;
//键扫描,大家真正关心的部分
keystatus = 0;
P1 = 0xF0; keystatus |= (P1&0x0F);
P1 = 0x0F; keystatus |= (P1&0xF0);
//以下是键处理,这部分与键扫描无关了.
switch(keystatus){
case 16种排列组合:~ *
}
键扫描为红色部分,就这么几行而已. mark mark 学习下 mark mark mark 经典啊,学习了 强 mark DING! 支持.学习了 是应该这么简短的,行扫描法其实也是不错的 学习 看看 mark!!! 收下 mark mark 呵呵,都是高手。 mark 按键扫描 学习中 思路很好 mark 一下 cool 标记 mark 高~ 膜拜二楼 回复【1楼】rainyss
-----------------------------------------------------------------------
这个貌似有错误,当两个IO口短接时,是把电平变低,就是说P01是1,P05是0.那么按键按下后应该是P01,P05都为0.按照你所说,那么KEYSTATUE一直是0X00,应该
P1 = 0xF0; keystatus |= (P1&0xF0);
P1 = 0x0F; keystatus |= (P1&0x0F); 关注一下,./emotion/em025.gif mark mark 回复【30楼】wj78681969
回复【1楼】rainyss
-----------------------------------------------------------------------
这个貌似有错误,当两个io口短接时,是把电平变低,就是说p01是1,p05是0.那么按键按下后应该是p01,p05都为0.按照你所说,那么keystatue一直是0x00,应该
p1 = 0xf0; keystatus |= (p1&0xf0);
p1 = 0x0f; keystatus |= (p1&0x0f);
-----------------------------------------------------------------------
正解!得到keystatus后可以转换编码变成0-15的形式用switch 。。。case m k 这个必须mark 回复【1楼】rainyss
代码太多没必要,刚在另一帖子里回的,顺手复制过来吧, 假定4x4,使用p1口反转扫描法:
unsigned char keystatus;
//键扫描,大家真正关心的部分
keystatus = 0;
p1 = 0xf0; keystatus |= (p1&0x0f);
p1 = 0x0f; keystatus |= (p1&0xf0);
//以下是键处理,这部分与键扫描无关了.
switch(keystatus){
case 16种排列组合:~ *
}
键扫描为红色部分,就这么几行而已.
-----------------------------------------------------------------------
mark,马克,马可,马科,吗可 这个精简版本需要mark 嘛 mark MARK 非常好的反转法,学习了! 回复【1楼】rainyss
-----------------------------------------------------------------------
牛 马克 扫描法呢 给个代码看看 MARK 回复【1楼】rainyss
-----------------------------------------------------------------------
不太明白 MARK 二楼经典啊,mark 顶下二楼 二楼的用法好像用过,嗯,不错。 mark 回复【48楼】dawmoon
-----------------------------------------------------------------------
扫描法 是逐行扫描查询 假如按键很多按下的键位于最后1列时 那么要扫描到最后一列才能知道按键位置
反转法 无论按下是第一列 还是最后1列,只需要2步便可获得按键位置
所以反转法更加方便实用 回复【48楼】dawmoon
-----------------------------------------------------------------------
扫描法 代码更多
unsigned int keyboar() //键盘检测函数,返回键值
{
P2=0xfe;
temp=P2;
temp=temp&0xf0;
if(temp!=0xf0)
{
delay1ms(10);
temp=P2;
switch(temp)
{
case 0xee:
key=0;
break;
case 0xde:
key=1;
break;
case 0xbe:
key=2;
break;
case 0x7e:
key=3;
break;
}
while(temp!=0xf0)
{
temp=P2;
temp=temp&0xf0;
}
}
P2=0xfd;
temp=P2;
temp=temp&0xf0;
if(temp!=0xf0)
{
delay1ms(10);
temp=P2;
switch(temp)
{
case 0xed:
key=4;
break;
case 0xdd:
key=5;
break;
case 0xbd:
key=6;
break;
case 0x7d:
key=7;
break;
}
while(temp!=0xf0)
{
temp=P2;
temp=temp&0xf0;
}
}
P2=0xfb;
temp=P2;
temp=temp&0xf0;
if(temp!=0xf0)
{
delay1ms(10);
temp=P2;
switch(temp)
{
case 0xeb:
key=8;
break;
case 0xdb:
key=9;
break;
case 0xbb:
key=10;
break;
case 0x7b:
key=11;
break;
}
while(temp!=0xf0)
{
temp=P2;
temp=temp&0xf0;
}
}
P2=0xf7;
temp=P2;
temp=temp&0xf0;
if(temp!=0xf0)
{
delay1ms(10);
temp=P2;
switch(temp)
{
case 0xe7:
key=12;
break;
case 0xd7:
key=13;
break;
case 0xb7:
key=14;
break;
case 0x77:
key=15;
break;
}
while(temp!=0xf0)
{
temp=P2;
temp=temp&0xf0;
}
}
return key;
} 回复【58楼】yao1
-----------------------------------------------------------------------
代码太长 重新简化
int keyscan()
{
unsigned char k k_temp;
P1=0xf0; //低位置0,准备查询按键
k=P1; //取得当前P1口状态
if(k!=0xf0) //如果有变化则表示有按键按下
{
delay(10); //延迟 消抖
k_temp=p1;
if(k==k_temp)//确实有键按下
{
k=0xfe;
do //循环扫描每一行
{
p1=k;
if(k!=p1)
{
switch(P1)//判断按键 并返回键值
{
//第1行
case 0x7e:{return 0;break;}
case 0xbe:{return 0;break;}
case 0xde:{return 0;break;}
case 0xee:{return 0;break;}
//第2行
case 0x7d:{return 0;break;}
case 0xbd:{return 0;break;}
case 0xdd:{return 0;break;}
case 0xed:{return 0;break;}
//第3行
case 0x7b:{return 0;break;}
case 0xbb:{return 0;break;}
case 0xdb:{return 0;break;}
case 0xeb:{return 0;break;}
//第4行
case 0x77:{return 0;break;}
case 0xb7:{return 0;break;}
case 0xd7:{return 0;break;}
case 0xe7:{return 0;break;}
}
}
k=_crol_(k,1); //移位 进入下一行扫描
}
while(k!=0xef); //超过列范围 退出扫描
}
}
} 回复【59楼】yao1
-----------------------------------------------------------------------
修正return 数
//第1行
case 0x7e:{return 0; break;}
case 0xbe:{return 1; break;}
case 0xde:{return 2; break;}
case 0xee:{return 3; break;}
//第2行
case 0x7d:{return 4; break;}
case 0xbd:{return 5; break;}
case 0xdd:{return 6; break;}
case 0xed:{return 7; break;}
//第3行
case 0x7b:{return 8; break;}
case 0xbb:{return 9; break;}
case 0xdb:{return 10;break;}
case 0xeb:{return 11;break;}
//第4行
case 0x77:{return 12;break;}
case 0xb7:{return 13;break;}
case 0xd7:{return 14;break;}
case 0xe7:{return 15;break;} 回复【楼主位】GOOOOL
-----------------------------------------------------------------------
多谢分享 太精典了 不错,不错,高手如云! MARK! 30楼说的应该是正确的,模拟可以,方法也如1楼所说,比较简洁了~~!! 学习 嗯,不错的,但是线转发没有松手检测啊,这样的键盘程序你是没用的啊,实际一起中要是没有松手检测一般都会出问题的 mark,马克,马可,马科,吗可 mark 4x4 key 貌似很强大的说。~ 4x4矩阵键盘,mark mark mark,学无止境 mark...... 按键扫描 MARK..... OK!OK!OK!OK!OK!OK!OK!OK!OK!OK!OK!OK!
页:
[1]