单片机按键程序

 

目录

(1)源代码(摘自战舰程序)

(2)代码解释

(3)改进代码


(1)源代码(摘自战舰程序)

#include <REG51.H>

#define	key_up      1  
#define key_right   2
#define key_left    3
#define key_down    4

#define U8  unsigned  char   
sbit key0=P1^0;
sbit key1=P1^1 ;
sbit key2=P1^2 ;
sbit key3=P1^3 ;
bit  key_state;
sbit LED0=P2^1;
sbit LED1=P2^2;
void delay(unsigned char z)  //延时0.n  ms
    {
	 U8 a,b;
	 for(a=0;a<z;a++)
	 	  for(b=0;b<110;b++);
		    }

U8 key_scan(U8 mode)   //mode==1  连续按键   mode==0  不支持连续按键
{
 	static key_state =1;
	if(mode) key_state=1;
	if(key_state&&(key0==0||key1==0||key2==0||key3==0))
	{
	 delay(100);
	 key_state=0;
	 if(key0==0) return key_up;
	 else if (key1==0) return key_right;
	 else if (key2==0) return key_left;	
	 else if (key3==0) return key_down;
	}else if(key0==1&&key1==1&&key2==1&&key3==1) key_state=1; 	    
 	return 0;
}

void main (void )
{
	U8 key_return;
 	while(1)
	{
	  key_return=key_scan(0);
			if(key_return)
		{						   
			switch(key_return)
			{				 
				case key_up:	LED0=!LED0;	 break;				
				case key_left:	LED0=!LED0;	 break;				
				case key_down:	LED1=!LED1;	 break;
				case key_right:	LED1=!LED1;	 break;	
			}
		}else delay(100); 	
	}
}

(2)代码解释

上面是按键扫描程序,通过mode 来修改按键是否可以长按

static key_state =1;
1,短按下KEY0时,每按一次,数字加1
2,当按下KEY0不放时,数字每隔10ms加1

static key_state  这句话是程序初始化的时候,只执行一次赋值,在每次执行该key_scan()时候,key_state 类似于全局变量能够保存上次的值,这样(和全局变量的区别)限定了key_state 使用只能在该函数内使用。

有按键按下的时候key_state是0,当函数再次进入按键扫描函数的时候(此时按键还是按下的),key_state的值为零。key_state&&(key0==0||key1==0||key2==0||key3==0  这条语句进去不去, key0==1&&key1==1&&key2==1&&key3==1   这个判断也进不去, 所以他会返回一个return 0 。表示没有按键按下。

这样就表示了按键只有按下一次,就是只有一个返回值返回。这样比起原先用的while(key==0){;} 这种语句相比,在动态扫描的时候不会让扫描出现错误。

当mode为一的时候每次进入扫描函数都会给key_state进行赋值为一,这样就像当于在一直按下某个键的时候,每隔delay(100) 的时候,按键执行一次,比如这个按键是加一的话,这样长按就是delay(100)个时间的加一,实现了这个功能。

(3)改进代码

在实际中,delay(100),会使得CPU停止在这个状态10ms,会对其它操作产生影响(如按键按下时,刚好需要通讯,则通讯会有10ms延迟)。可改用时间轮询法,采用时基改进程序。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值