这个代码是参考了某站一位UP的
单击代码如下,用的是10ms的定时中断,这个是单击加双击加长按的代码
struct key{
uint8_t key_stage;//第几阶段阶段
uint8_t key_state;//按键的状态
uint8_t key_short_flag;//短按标志位
uint8_t key_long_flag;//长按标志位
uint8_t time_Count;//时间计数
uint8_t double_count_EN;//双击按键使能计数标志位
uint8_t double_count;//双击时间计数
uint8_t double_flag;//双击标志位
};
struct key Key[4]={0,0,0};
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
```
if(htim->Instance==TIM1)
{
Key[0].key_state=HAL_GPIO_ReadPin(B1_GPIO_Port,B1_Pin);
Key[1].key_state=HAL_GPIO_ReadPin(B2_GPIO_Port,B2_Pin);
Key[2].key_state=HAL_GPIO_ReadPin(B3_GPIO_Port,B3_Pin);
Key[3].key_state=HAL_GPIO_ReadPin(B4_GPIO_Port,B4_Pin);
for(uint8_t i=0;i<4;i++)
{
switch(Key[i].key_stage)
{
case 0:{
if(Key[i].key_state==0)
{
Key[i].key_stage=1;
}
}break;
case 1:{
if(Key[i].key_state==0)//消抖
{
Key[i].key_stage=2;
}
else{
Key[i].key_stage=0;
}
}break;
case 2:{
if(Key[i].key_state==1)
{
if(Key[i].time_Count<70)//一次单次按键
{
if(Key[i].double_count_EN==0)//第一次按下,开启双击计数按键
{
Key[i].double_count_EN=1;//使能双击计时
}
else{//第二次已经被按下也就是Key[i].double_count_EN==1的情况
Key[i].double_flag=1;//标志位置1
Key[i].double_count_EN=0;//结束双击计数,不然在抬起后会执行短击
}
}
Key[i].time_Count=0;//长按计数器清零
Key[i].key_stage=0;//返回第一阶段
}
else{
Key[i].time_Count++;
if(Key[i].time_Count>70)//长按
{
Key[i].key_long_flag=1;
Key[i].double_count_EN=0;//结束双击计数,不然在抬起后会执行短击
}
}
}break;
}
if(Key[i].double_count_EN==1)
{
Key[i].double_count++;
if(Key[i].double_count>30)//一个按键已经被按下被隔离了300ms没有被按下,所以判断是单击
{
Key[i].key_short_flag=1;//短按标志位置1
Key[i].double_count=0;//双击计数清零
Key[i].double_count_EN=0;//关闭双击使能
}
}
}
}
```
}
这个是单击加双击的代码
struct key{
uint8_t key_stage;//第几阶段阶段
uint8_t key_state;//按键的状态
uint8_t key_short_flag;//短按标志位
uint8_t double_count_EN;//双击按键使能计数标志位
uint8_t double_count;//双击时间计数
uint8_t double_flag;//双击标志位
};
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
HAL_GPIO_WritePin(GPIOD,GPIO_PIN_2,1);
HAL_GPIO_TogglePin(LD1_GPIO_Port,LD1_Pin);
HAL_GPIO_WritePin(GPIOD,GPIO_PIN_2,0);
if(htim->Instance==TIM1)
{
Key[0].key_state=HAL_GPIO_ReadPin(B1_GPIO_Port,B1_Pin);
Key[1].key_state=HAL_GPIO_ReadPin(B2_GPIO_Port,B2_Pin);
Key[2].key_state=HAL_GPIO_ReadPin(B3_GPIO_Port,B3_Pin);
Key[3].key_state=HAL_GPIO_ReadPin(B4_GPIO_Port,B4_Pin);
for(uint8_t i=0;i<4;i++)
{
switch(Key[i].key_stage)
{
case 0:{
if(Key[i].key_state==0)
{
Key[i].key_stage=1;
}
}break;
case 1:{
if(Key[i].key_state==0)
{
Key[i].key_stage=2;
}
else{
Key[i].key_stage=0;
}
```
}break;
case 2:{
if(Key[i].key_state==1)//到这里说明被按下去
{
if(Key[i].double_count_EN==0)//第一次按下
{
Key[i].double_count_EN=1;
Key[i].key_short_temp=1;//短按已经被按下
}
else{//第二次被按下
Key[i].double_flag=1;
Key[i].double_count_EN=0;
Key[i].double_count=0;
}
Key[i].key_stage=0;
}
}break;
}
if(Key[i].double_count_EN==1)
{
Key[i].double_count++;
if(Key[i].double_count>30&&Key[i].key_short_temp!=0)//短按
{
Key[i].key_short_flag=1;
Key[i].double_count=0;
Key[i].double_count_EN=0;
}
}
}
}
```
}
这个是单击加长按的代码
```
struct key{
uint8_t key_stage;
uint8_t key_state;
uint8_t key_time_count;
uint8_t key_short_flag;
uint8_t key_long_flag;
};
struct key Key[4]={0,0,0};
```
```
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)//10MS进一次中断
{
if(htim->Instance==TIM1)
{
Key[0].key_state=HAL_GPIO_ReadPin(B1_GPIO_Port,B1_Pin);
Key[1].key_state=HAL_GPIO_ReadPin(B2_GPIO_Port,B2_Pin);
Key[2].key_state=HAL_GPIO_ReadPin(B3_GPIO_Port,B3_Pin);
Key[3].key_state=HAL_GPIO_ReadPin(B4_GPIO_Port,B4_Pin);//获取按键状态
for(int i=0;i<4;i++)
{
switch(Key[i].key_stage)//阶段判断
{
case 0:{//第0阶段也就是第一次按下
if(Key[i].key_state==0)
Key[i].key_stage=1;
}break;
case 1:{//第1阶段也就是消抖与第0阶段隔了10MS0到1阶段相当于消抖
if(Key[i].key_state==0)
{
Key[i].key_stage=2;
}
else
{
Key[i].key_stage=0;
}
}break;
case 2:{
if(Key[i].key_state==1)
{
Key[i].key_stage=0;
if(Key[i].time_Count<70)
{
Key[i].key_short_flag=1;
}
Key[i].time_Count=0;
}
else
{
Key[i].time_Count++;
if(Key[i].time_Count>70)
{
Key[i].key_long_flag=1;
}
// Key[i].key_stage=0;//如果在这里只返回第零阶段那么会卡住因为Key[i].time_Count没有能够清零
//如果在这里返回第零阶段并且把Key[i].time_Count清零那么会是一次按键重新的开始,就会触发Key[i].key_short_flag置1
}
}break;
}
}
}
}
```
这个是按键单击
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)//10MS进一次中断
{
if(htim->Instance==TIM1)
{
Key[0].key_state=HAL_GPIO_ReadPin(B1_GPIO_Port,B1_Pin);
Key[1].key_state=HAL_GPIO_ReadPin(B2_GPIO_Port,B2_Pin);
Key[2].key_state=HAL_GPIO_ReadPin(B3_GPIO_Port,B3_Pin);
Key[3].key_state=HAL_GPIO_ReadPin(B4_GPIO_Port,B4_Pin);//获取按键状态
for(int i=0;i<4;i++)
{
switch(Key[i].key_stage)//阶段判断
{
case 0:{//第0阶段也就是第一次按下
if(Key[i].key_state==0)
Key[i].key_stage=1;
}break;
case 1:{//第1阶段也就是消抖与第0阶段隔了10MS
if(Key[i].key_state==0)
{
Key[i].key_stage=2;
}
else
Key[i].key_stage=0;
}break;
case 2:{
if(Key[i].key_state==1)
{
Key[i].key_short_flag=1;
Key[i].key_stage=0;
}
}break;
}
}
}
}