本文主要是介绍长短键识别,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
功能实现
MSP-EXP430G2 开发板上 P1.3 接了一个按键,P1.0 和 P1.6 接了 LED(用跳线帽连接),要求短按 P1.3 控制 LED1 的亮灭,长按P1.3 控制 LED2 的亮灭。
状态机
代码
#include "MSP430G2553.h" //-----对状态机进行宏定义-----
#define IDLE 0
#define SHORT 1
#define LONG 2
#define COUNTER_THRESHOLD 50 /*长键判别门限*/
//-----全局变量-----
unsigned char WDT_Counter=0; /*用于对按键按下时间进行计数*/
//-----在main函数前提前声明函数-----
void GPIO_init();
void WDT_init();
void Key_SM();
unsigned char LongClick_Dect();
void P13_OnShortRelease();
void P13_OnLongClick(); void main(void) { WDTCTL = WDTPW + WDTHOLD; //关狗 GPIO_init(); WDT_init(); _EINT(); //开总中断 LPM3; //LPM3休眠
}/****************************************************************************************************** * 名 称:GPIO_init() * 功 能:设定按键和LED控制IO的方向,启用按键IO的上拉电阻 * 入口参数:无 * 出口参数:无 * 说 明:无 * 范 例:无
******************************************************************************************************/
void GPIO_init()
{ //-----设定P1.0和P1.6的输出初始值----- P1DIR |= BIT0+BIT6; //设定P1.0和P1.6为输出 P1OUT |= BIT0; //设定P1.0初值 P1OUT &= ~BIT6; //设定P1.6初值 //-----配合机械按键,启用内部上拉电阻----- P1REN |= BIT3; //启用P1.3内部上下拉电阻 P1OUT |= BIT3; //将电阻设置为上拉
} /****************************************************************************************************** * 名 称:WDT_init() * 功 能:设定WDT定时中断为16ms,开启WDT定时中断使能 * 入口参数:无 * 出口参数:无 * 说 明:WDT定时中断的时钟源选择ACLK,可以用LPM3休眠。 * 范 例:无
******************************************************************************************************/
void WDT_init()
{ //-----设定WDT为----- WDTCTL=WDT_ADLY_16; //-----WDT中断使能----- IE1|=WDTIE;
} /****************************************************************************************************** * 名 称:WDT_ISR() * 功 能:响应WDT定时中断服务 * 入口参数:无 * 出口参数:无 * 说 明:不能直接判断事件,需启用状态机 * 范 例:无
******************************************************************************************************/
#pragma vector=WDT_VECTOR
__interrupt void WDT_ISR(void)
{ //-----启用按键状态机----- Key_SM();
} /****************************************************************************************************** * 名 称:Key_SM() * 功 能:判断出长短键 * 入口参数:无 * 出口参数:无 * 说 明:本状态机为Mealy型状态机,在Switch(State)中需要判断事件 * 范 例:无
******************************************************************************************************/
void Key_SM()
{ static unsigned char State=0; //状态机的状态变量 static unsigned char Key_Now=0; //记录按键的当前电平 unsigned char Key_Past=0; //记录按键的前一次电平 unsigned char Key_Dect=0; //按键状态值 Key_Past=Key_Now; //-----查询IO的输入寄存器----- if(P1IN&BIT3) Key_Now=1; else Key_Now=0; //-----电平前高后低,表明按下----- if((Key_Past==1)&&(Key_Now==0)) Key_Dect=1; //-----电平前低后高,表明弹起----- if((Key_Past==0)&&(Key_Now==1)) Key_Dect=2 ; switch(State) //该状态机靠扫描的按键值Key_Dect跳转状态 { case IDLE: WDT_Counter=0; //空闲状态对计数清零 if(Key_Dect==1) State=SHORT; //路径1 break; case SHORT: if(Key_Dect==2) //路径2 { State=IDLE; P13_OnShortRelease(); //短按事件处理函数 break;} if(LongClick_Dect()) //路径3 { State=LONG; P13_OnLongClick(); //长按事件处理函数 } break; case LONG: WDT_Counter=0; //长按状态对计数清零 if(Key_Dect==2) State=IDLE; //路径4 break; default: State=IDLE; break; }
} /****************************************************************************************************** * 名 称:LongClick_Dect() * 功 能:对WDT中断计时,计满清零并返回”长键“信息 * 入口参数:无 * 出口参数:1:长按键;0:非长按键 * 说 明:无 * 范 例:无
******************************************************************************************************/
unsigned char LongClick_Dect()
{ WDT_Counter++; if (WDT_Counter==COUNTER_THRESHOLD) { WDT_Counter=0; return(1); } else return(0);
} /****************************************************************************************************** * 名 称:P13_OnShortRelease() * 功 能:P1.3的短按事件处理函数,即当P1.3键被”短按“后,下一步干什么 * 入口参数:无 * 出口参数:无 * 说 明:使用事件处理函数的形式,可以增强代码的移植性和可读性 * 范 例:无
******************************************************************************************************/
void P13_OnShortRelease() //P1.3的事件处理函数
{ //----翻转P1.3IO电平----- P1OUT ^= BIT0;
}
/****************************************************************************************************** * 名 称:P13_OnLongClick() * 功 能:P1.3的长按事件处理函数,即当P1.3键被”长按“后,下一步干什么 * 入口参数:无 * 出口参数:无 * 说 明:使用事件处理函数的形式,可以增强代码的移植性和可读性 * 范 例:无 ******************************************************************************************************/
void P13_OnLongClick() //P1.3的事件处理函数
{ //----翻转P1.6IO电平----- P1OUT ^= BIT6;
}
这篇关于长短键识别的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!