一、独立按键检测 长按 短按

//长按开关机,短按切换功能

//开机状态下,短接按才有效

//长按时间到,不需松手就动作,便开观察开关机,短按松手动作

//按键去抖动

//关机状态下,5S内自动睡眠,按键唤醒

bit B_1ms=0;
u16 T_5s=0;


#define Const_Key_Jitter  40 //抖动计数
#define Const_Key_Long   1000 //长按1秒
u16 INT1_Cnt=0;
bit Short_Click=0;
bit Long_Click=0;
bit INT1_Lock=0;

bit Power_On=0;

/*******************************************************
	当短按有效时,继续计数,满足长按条件自锁
	松手解锁
	短按为松手后判断
	长按不需要松手就有效	
*******************************************************/
void Key_Scan()
{	 
	if(INT1==1)
	{
		INT1_Cnt=0;	 //按下计数清0
		if(INT1_Lock==1)  //长按锁标志
		{
			INT1_Lock=0;	
		}
		else if (Short_Click==1&&(Power_On==1))	//短按标志且电源开启
		{
			Short_Click=0;
			BLUE=~BLUE;	
		}	 	       
		
	}
	else if(INT1_Lock==0) //有键按下,且自锁标志为0,即第一次按下
	{
		INT1_Cnt++;
		if(INT1_Cnt>=Const_Key_Jitter)
		{
			Short_Click=1;			  //短按有效标志
		
		}
		if(INT1_Cnt>=Const_Key_Long)	  //说明是长按,开自锁
		{
			INT1_Lock=1;			  //长按锁住
			//INT1_Cnt=0;
			Short_Click=0;
			Power_On=~Power_On;
			RED=~RED;
		}
	}
}
void main( )
{	 

	delay_ms(10);
	GPIO_Inilize();
	Timer0_Inilize();
	Exti_Inilize();
	TR0=1;
	EA=1;
	while(1)
	{
		if(B_1ms==1)
		{
			B_1ms=0;
			if(++T_5s>=5000)
			{
				T_5s=0;
				if(INT1&&(Power_On==0))
				{
					
					TR0=0;
					BLUE=0;
					RED=0;
					INT1_Clear();  //清标志IE1=0
					INT1_Enable(); //使能按键中断EX1=1,用于唤醒
					MCU_POWER_DOWN(); //进入睡眠
					NOP7();
				}
			}
			Key_Scan();
		}
		
	}
}

/********************* Timer0中断函数定时1ms************************/
void timer0_int (void) interrupt TIMER0_VECTOR
{
	TF0=0;
	B_1ms=1;
}

void Ext_INT1 (void) interrupt INT1_VECTOR		//进中断时已经清除标志
{
	INT1_Disable();  //关闭按键中断使能
	TR0=1;

}

  

posted @ 2021-06-17 18:43  来去勿扰  阅读(644)  评论(0)    收藏  举报