打印
[单片机类]

【一个小小的个人经验分享】【四】按键+数码管

[复制链接]
8391|7
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
enderman1|  楼主 | 2019-2-10 20:25 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
说在前面的话:亲戚这可算走完了,不知道小伙伴们过年忙完没有啊?
说起按键,总会让人头疼,它似乎是一个非常玄学的东西;也是历年来蓝桥杯单片机比赛的一个重难点。

对于蓝桥杯开发板而言,按键分为矩阵按键独立按键两种,矩阵按键比独立按键难自然不多说,而一般情况下省赛期间补考矩阵按键但是还是能难倒一大批人;其主要原因在于一个按键可以有不同的功能,如果想要增加难度的话比赛也可以出长短按键也说不定;总之按键这个东西想出难可以使整个题目瞬间上升一个难度,但是其归根结底无非是对IO口状态的读取,但是却能灵活的运用到各个地方,因此平常的多多练习是必不可少的。

好了,言归正传,对于独立按键与其它外设的结合,我总结了几种方法:

1、传统方案——软件消抖or松手检测


//软件消抖一般实现方法
优点:可以大概实现按键消抖的效果
缺点:使用软件延时浪费CPU时间、而且长按不丢的话可能影响数码管显示

//松手检测一般实现方法
sbit key1=P3^0;
if(key1==0){
      num++;
}while(!key1);
优点:按着不丢的时候数据不会一直增加(如果是题目有要求的话另当别论)
缺点:按着不丢的时候动态扫描数码管不正常显示

当然也有第三种写法,就是软件消抖和松手检测写在一起的写法,但是似乎都解决不了手一直按着的问题(要么数据一直快速自加、要么数码管不正常显示);


因此我自己想了一个办法,谈不上多好,但是可以有效的解决这个问题,至少在实现效果来说是可以的。


2、改进方案

//改进方法
sbit key1=P3^0;
if(key1==0){
    delay_ms(5);
if(key1==0){
    num++;
}
}while(!key1){display();}


没错,就是在原有while(!key1)的里面添加了display();也就是数码管显示的函数;这可能有点操作系统的思想(开玩笑的了,比不上),也就是说,按键按下的时候,while是一直在循环的,也就是说CPU算是一直干等着,什么也没有干,因此你的动态扫描数码管显示当然无法正常显示了,所以基于这个的缺陷,while里面不能干等;在等的同时也要维持数码管的显示,这就保证了按下不丢的时候你的显示效果不受影响,说不定验分的时候这个实现效果也是一个添分项   你说是不是。。。但是,要知道,仅仅是维持数码管的显示,数据当然也就停止了(外设犹如DS1302什么的不会受影响的了~)

至于矩阵按键也是同样的道理,以下是矩阵按键的程序(直接复制我当年写的吧),谈不上多好,但是可以用。。

3、矩阵按键

其实对于矩阵按键,网上的方法层出不穷,有心的话一搜就能搜出一大堆教程+例程,所以我也在此不多费**,比较我也是用的人家的方法嘛。。。

unsigned char keyscan(){
        unsigned char key_value;
        unsigned char key_num;

        P3=0x7f;
        P44=0;P42=1;
        key_value=P3;
        key_value&=0x0f;
        if(key_value!=0x0f){        
                key_value=P3;
                switch(key_value){
                        case 0x7e:key_num=1;break;
                        case 0x7d:key_num=2;break;
                        case 0x7b:key_num=3;break;
                        case 0x77:key_num=4;break;
                        default:key_num=0x00;
                }
        }
        //====================================
        P3=0xbf;
        P44=1;P42=0;
        key_value=P3;
        key_value&=0x0f;
        if(key_value!=0x0f){        
                key_value=P3;
                switch(key_value){
                        case 0xbe:key_num=5;break;
                        case 0xbd:key_num=6;break;
                        case 0xbb:key_num=7;break;
                        case 0xb7:key_num=8;break;
                        default:key_num=0x00;
                }
        }
        //====================================
        P3=0xdf;
        P44=1;P42=1;
        key_value=P3;
        key_value&=0x0f;
        if(key_value!=0x0f){        
                key_value=P3;
                switch(key_value){
                        case 0xde:key_num=9;break;
                        case 0xdd:key_num=10;break;
                        case 0xdb:key_num=11;break;
                        case 0xd7:key_num=12;break;
                        default:key_num=0x00;
                }
        }
        //====================================
        P3=0xef;
        P44=1;P42=1;
        key_value=P3;
        key_value&=0x0f;
        if(key_value!=0x0f){        
                key_value=P3;
                switch(key_value){
                        case 0xee:key_num=13;break;
                        case 0xed:key_num=14;break;
                        case 0xeb:key_num=15;break;
                        case 0xe7:key_num=16;break;
                        default:key_num=0x00;
                }
        }

        return key_num;
}


采用的是比较传统的方式,如果想写成上方的改进版也是可以的,原理都是一样的;至于P44 和  P42  在完整电路分析的时候我似乎已经提到,它们分别代替了传统单片机的P37   和  P36



那么今天的内容就到这里的,下次见。。。。



相关帖子

沙发
xyz549040622| | 2019-2-10 20:29 | 只看该作者
支持下,谢谢分享!从刚开始入门的时候使用状态机,是个很好的习惯。

使用特权

评论回复
评论
enderman1 2019-2-10 20:50 回复TA
一看评论就知道肯定是老江湖了,哈哈,多谢支持 
板凳
换专业的娃| | 2019-3-22 11:09 | 只看该作者
支持支持

使用特权

评论回复
地板
lihui567| | 2019-5-31 23:36 | 只看该作者
新手来说入门学习很好,采用按键扫描,后续可以写成按键驱动

使用特权

评论回复
5
妄言之半!| | 2020-1-13 12:57 | 只看该作者
while(!key1)什么意思啊,while 语句不是条件为真才会执行下面的语句吗,当按键按下的时候,条件为真,然后取反不就是条件为假了吗,怎么还会执行下面的语句啊?

使用特权

评论回复
评论
enderman1 2020-1-29 17:33 回复TA
按键另一端是接地的,按下的时候是0,取反之后是1 
6
思难忘| | 2020-4-6 11:27 | 只看该作者
学习了

使用特权

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

本版积分规则

11

主题

71

帖子

12

粉丝