打印

4*4键盘扫描卡死问题

[复制链接]
2181|10
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
本帖最后由 青石向晚 于 2010-5-23 15:56 编辑

#include<reg51.h>
#define uchar  unsigned char
#define uint   unsigned int

#define rowkey()  (~P1)&0x0f

unsigned char i=0;                        //扫描值的当前个数
unsigned char  dis[15] = {0};      //扫描值存放的数组

void debouncer(void)        //消抖函数
{
        uint i;
        for(i=0;i<240;i++);  //延迟约2ms
}

void scanner (void)         //扫描程序
{
            uint col,row;          //变量声明,当前扫描的行和列
            char scan,keyin;  //扫描信号,列按键值
            scan=0xef;
            for(col=0;col<4;col++)
           {
                P1=scan;
                keyin=rowkey();
                if(keyin!=0)
                {
                        for(row=0;row<4;row++)
                        {
                                if(keyin==(0x01<<row))
                                {        
                                         dis=keycode(row+4*col); //返回键盘值
                                         i++;        
                                         while(rowkey()!=0);    //等待按键放开
                                         debouncer();                //消抖
                                }
                        }
                        
                 }
                 scan=(scan<<1)|0x01;        //左移1位扫描信号        
        }
}

void main(void)
{
        while(dis[i-1]!=15)       //约定当键盘扫描值为15时扫描结束
             scanner();
}
通过protuse仿真,按键后会出现单片机卡死的情况,即P1(键盘连接口)的电平不再变化,怪异的是按第一排的键的时候并不会出现卡死,请各位高手分析分析看,是不是程序有什么缺陷~~~

相关帖子

沙发
NE5532| | 2010-5-23 16:14 | 只看该作者
打断点跟踪,看有没有无法执行到的语句

使用特权

评论回复
板凳
青石向晚|  楼主 | 2010-5-24 12:40 | 只看该作者
while(rowkey()!=0);  //等待按键放开,打断点的过程中有时候这一句根本不执行,按键没有放开,它也不管,直接跳过这句话,执行下面的语句了,请问这是怎么回事啊?[b] 2# NE5532

使用特权

评论回复
地板
青石向晚|  楼主 | 2010-5-24 12:55 | 只看该作者
而且发现很怪异的是 while(rowkey()!=0)这句话在P1.0口等于零时会执行(这时候(~P1)&0x0f的值为1),除此之外其他全部无视[b] 2# NE5532

使用特权

评论回复
5
NE5532| | 2010-5-24 14:14 | 只看该作者
跟踪这句话的入口条件,程序就是这样,你设计的条件都满足了,他就运行,有一个不对,就不运行,你就把所有入口都挨着看一遍,就知道了。

使用特权

评论回复
6
原野之狼| | 2010-5-24 14:39 | 只看该作者
while(rowkey()!=0);    //等待按键放开
这种做法不大好 要是不放开按键程序岂不是假死了

使用特权

评论回复
7
青石向晚|  楼主 | 2010-5-24 18:10 | 只看该作者
那请问有没有更好一点的办法,希望前辈指点 6# 原野之狼

使用特权

评论回复
8
青石向晚|  楼主 | 2010-5-24 19:12 | 只看该作者
把while(rowkey()!=0);改成while(rowkey());程序就通过,不知道这该怎么解释啊~~ 5# NE5532

使用特权

评论回复
9
周华堂| | 2013-8-17 10:14 | 只看该作者
顶楼上。。。。。。

使用特权

评论回复
10
liang7143| | 2013-8-17 18:32 | 只看该作者
本帖最后由 liang7143 于 2013-8-17 18:35 编辑
青石向晚 发表于 2010-5-24 19:12
把while(rowkey()!=0);改成while(rowkey());程序就通过,不知道这该怎么解释啊~~ 5# NE5532  ...

LZ啊,你为什么不打一个括号。
优先级的问题在你自己都不清楚的情况下,就打括号吧,不要想当然

rowkey()!=0 宏替换是

(~P1)&0x0f!=0
这里 != 比 &优先级要 高
实际等价于
(~P1)&(0x0f!=0)

使用特权

评论回复
11
青石向晚|  楼主 | 2015-6-8 19:48 | 只看该作者
liang7143 发表于 2013-8-17 18:32
LZ啊,你为什么不打一个括号。
优先级的问题在你自己都不清楚的情况下,就打括号吧,不要想当然

多谢指点,确实宏定义的问题

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

13

主题

41

帖子

0

粉丝