按键状态机消抖(下)

该博客介绍了一种使用状态机实现的按键检测函数,适用于检测按键的按下、弹起以及持续按下事件。通过定时运行该函数,可以实现对按键的实时监控,并根据按键状态执行相应操作。同时,函数还包括了持续响应模式,允许用户设置按键持续按下的响应间隔。
摘要由CSDN通过智能技术生成

        我们在使用按键时,可能会碰到按下检测,弹起检测以及一直按下实现特定功能(如:一直按下,使值间隔自增)。

        下面是使用状态机的键值检测函数,只需将函数放入while中大概20ms运行一次即可,使用时先判断对应标志位是否为1,在判断具体键值,例如:

 if (m4x4_press_flag == 1)
    {
        switch (m4x4_press_value)
        {
        case matrix_4x4_key_s1:······;break;

        case matrix_4x4_key_s2:······;break;

         ·······

        }

     }//要注意的是用完后要标志位要清0,因为键值是不变的也是不能软件该变的,否则会出错。

//获取参数定义
//按键键值获取
unsigned char m4x4_now_value = 0xff;       //按键实时值
unsigned char m4x4_press_value = 0xff;     //按键按下响应值
unsigned char m4x4_upspring_value = 0xff;  //按键弹起响应值
unsigned char m4x4_continued_value = 0xff; //按键持续响应值
unsigned char m4x4_press_flag = 1;         //按键按下标志
unsigned char m4x4_upspring_flag = 1;      //按键弹起标志
unsigned char m4x4_continued_flag = 1;     //按键持续标志
unsigned char m4x4_continued_mode = 0;     //持续响应模式(为0是按下就响应一次,x为1是等待一定间隔后响应))
unsigned char m4x4_continued_xms = 50;     //按键持续响应的间隔(大小为key_continued_xms*key_readtimexms ms)

//按键键值获取
void read_matrix_4x4_val()
{
#define _have_press_start 1  //按下状态
#define _no_press_start 0    //非按下状态
#define continued_delay 1    //等待一定间隔后响应状态
#define continued_no_delay 0 //按下就响应状态

    static unsigned char matrix_last_key_value = matrix_4x4_key_no, _press_flag = 0, _count = 0, first = 0; //_count是一个间接计数器,为持续响应提供间隔时钟,可替换为其他计数器
    m4x4_now_value = read_matrix_4x4();

    if (matrix_last_key_value != m4x4_now_value) //按下检测
    {
        m4x4_press_value = m4x4_now_value;
        m4x4_press_flag = 1;             //按键按下标志置1表示有按键按下
        m4x4_upspring_flag = 0;          //清除按键弹起标志
        m4x4_continued_flag = 0;         //清除按键持续标志
        _press_flag = _have_press_start; //按下标志位置为按下状态
        _count = 0;                      //间接计数器清0
        first = 0;
    }

    if ((m4x4_now_value == matrix_4x4_key_no) && (_press_flag == _have_press_start)) //弹起检测
    {
        m4x4_upspring_value = matrix_last_key_value;
        m4x4_press_flag = 0;           //清除按键按下标志
        m4x4_upspring_flag = 1;        //按键弹起标志置1表示有按键正弹起
        m4x4_continued_flag = 0;       //清除按键持续标志
        _press_flag = _no_press_start; //按下标志位置为非按下状态
    }

    if ((_press_flag == 1) && (matrix_last_key_value == m4x4_now_value)) //处于按下状态且键值未变(变了会在进函数进入第一条判断语句)
    {

        if (m4x4_continued_mode == continued_no_delay) //持续按下且按下就响应状态
        {
            if (first == 0) //第一次按下
            {
                m4x4_continued_value = matrix_last_key_value;
                _count = 0;
            }
            else if (_count == m4x4_continued_xms)
            {
                m4x4_continued_value = matrix_last_key_value;
                _count = 0; //间接计数器清0
            }
        }

        else //持续按下且等待一定间隔后响应状态
        {

            if (_count == m4x4_continued_xms)
            {
                m4x4_continued_value = matrix_last_key_value;
                _count = 0;
            }
        }
        _count++; //计数值自加
    }

    matrix_last_key_value = m4x4_now_value;
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值