欢迎来到三一文库! | 帮助中心 三一文库31doc.com 一个上传文档投稿赚钱的网站
三一文库
全部分类
  • 研究报告>
  • 工作总结>
  • 合同范本>
  • 心得体会>
  • 工作报告>
  • 党团相关>
  • 幼儿/小学教育>
  • 高等教育>
  • 经济/贸易/财会>
  • 建筑/环境>
  • 金融/证券>
  • 医学/心理学>
  • ImageVerifierCode 换一换
    首页 三一文库 > 资源分类 > DOC文档下载
     

    单片机中按键消抖程序.doc

    • 资源ID:3398170       资源大小:24.50KB        全文页数:5页
    • 资源格式: DOC        下载积分:2
    快捷下载 游客一键下载
    会员登录下载
    微信登录下载
    三方登录下载: 微信开放平台登录 QQ登录   微博登录  
    二维码
    微信扫一扫登录
    下载资源需要2
    邮箱/手机:
    温馨提示:
    用户名和密码都是您填写的邮箱或者手机号,方便查询和重复下载(系统自动生成)
    支付方式: 支付宝    微信支付   
    验证码:   换一换

    加入VIP免费专享
     
    账号:
    密码:
    验证码:   换一换
      忘记密码?
        
    友情提示
    2、PDF文件下载后,可能会被浏览器默认打开,此种情况可以点击浏览器菜单,保存网页到桌面,就可以正常下载了。
    3、本站不支持迅雷下载,请使用电脑自带的IE浏览器,或者360浏览器、谷歌浏览器下载即可。
    4、本站资源下载后的文档和图纸-无水印,预览文档经过压缩,下载后原文更清晰。
    5、试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。

    单片机中按键消抖程序.doc

    单片机中按键消抖程序写在前面:按键去抖:由上图可以看出理想波形与实际波形之间是有区别的,实际波形在按下和释放的瞬间都有抖动的现象,抖动时间的长短和按键的机械特性有关,一般为510ms。通常我们手动按键然后释放,这个动作中稳定闭合的时间超过了20ms。因此单片机在检测键盘是否按下时都要加上去抖动操作,有专用的去抖动电路,也有专门的去抖动芯片,但通常我们采用软件延时的方法就可以解决抖动问题。1、单片机中按键消抖程序1.1  单片机中,比如STM32中,一般的方法(最简单的方法)软件消抖程序:if(GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_14)=1)                                delay_ms(20);/延时20ms再去检测按键值          if(GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_14)=0) / 相当于下降沿KEY1 = 1;  /表示KEY1被按下1.2 比较全面的按键消抖程序及按键状态检测程序第一步:初始化全局时间戳的定时器,一般采用SysTick定时器来产生,每ms一次tick即可。第二步:初始化按键对应的IO,复用为边沿触发的外部中断。第三步:在外部中断函数中添加按键事件处理函数。代码部分:typedef struct _Key_t    u32 last_time;  enum    May_Press,  Release,  private_state;  enum    No_Press,  Short_Press,  Long_Press,  state;  Key_t;  #define Is_ShortPress_Threshold  1500  简单定义一个按键状态的结构体,用于管理每个按键的状态。顺便再定义一个长短按的识别阈值,用于区分按键的长短按。if(key_state.private_state=Release)            if(KEY=0)    key_state.private_state=May_Press;  key_state.last_time=course_ms();      else if(key_state.private_state=May_Press)    if(KEY=1)    if(course_ms()-key_state.last_time>10)">  key_state.state=Short_Press;  key_state.private_state=Release;    else if(course_ms()-key_state.last_time>Is_ShortPress_Threshold)    key_state.state=Long_Press;  key_state.private_state=Release;    else  key_state.private_state=Release;      以上为需要添加到中断处理函数的按键事件处理函数,算法的核心是一个状态机。在本例中,按键被默认上拉,按下接地。course_ms()为获取全局时间戳的函数。思路解释如下:按键状态结构体有一个用于识别的状态位,默认处于Release,也就是释放的状态。一旦按键被按下,中断触发,此时检查是否是Relase状态,如果是就检查按键是否被拉低,如果是,此时进入May_Press状态,也就是可能是按下的,并且记录此时的时间戳,这一步是消抖的关键。当按键被释放,由于是边沿触发,会再次进行处理,此时检查和上一次触发之间的时间戳之差,如果小于10ms我们就认为是抖动,此时不会对按键输出状态进行修改,而是直接将按键状态置回Relase状态,反之检查差值和长短按阈值之间的关系,将state置位为对应的状态。消抖的核心在于记录时间戳,而这只是一个简单的赋值操作,并不耗费时间。效率上来说,延时消抖花费时间在无意义延时上,而相对较好的定时轮询还是不可避免的在轮询,而现在这种方式完全是中断性质的。唯一多出的开销(全局时间戳)并不是只可以用于按键消抖,另外在HAL库中存在直接获取tick的函数,这样实现就更方便了。经实际测试,消抖效果可以达到其他两种消抖算法的水平。2、FPGA按键消抖程序首先,做两个假定,以方便后面的描述:假定按键的默认状态为0,被按下后为1假定按键抖动时长小于20ms,也即使用20ms的消抖时间核心:方案最容易想到的方案在按键电平稳定的情况下,当第一次检测到键位电平变化,开始20ms计时,计时时间到后将按键电平更新为当前电平。或许这才是最容易想的方案在20ms计时的过程中,有任何的电平变化都立即复位计时消除按键反应延时抖方案在有电平变化时立即改变按键输出电平,并开始20ms计时,忽略这其中抖动测试平台设计(修改代码以仿真的1us代替实际1ms)无抖动 上升沿抖动5毫秒下降沿抖动15毫秒上升和下降沿均抖动19毫秒附加测试(可以不通过)抖动25毫秒代码方案1module debounce(    input wire clk, nrst,    input wire key_in,    output reg key_out    );    / 20ms parameter/    localparam TIME_20MS = 1_000_000; localparam TIME_20MS = 1_000; / just for test    / variable reg 20:0 cnt;    reg key_cnt;        / debounce time passed, refresh key state always (posedge clk or negedge nrst) begin if(nrst = 0)            key_out ait reset repeat(3) (negedge clk);                / no bounce        / key down key_in = 1;        / last 60ms repeat(3000) (negedge clk);        / key up key_in = 0;        / wait 50ms repeat(2500) (negedge clk);        / down 5ms, up 15ms        / key down, bounce 5ms repeat(251) (negedge clk) key_in = key_in;        / last 60ms repeat(3000) (negedge clk);        / key up, bounce 15ms repeat(751) (negedge clk) key_in = key_in;        / wait 50ms repeat(2500) (negedge clk);        / down 19ms, up 19ms        / key down, bounce 19ms repeat(951) (negedge clk) key_in = key_in;        / last 60ms repeat(3000) (negedge clk);        / key up, bounce 19ms repeat(951) (negedge clk) key_in = key_in;        / wait 50ms repeat(2500) (negedge clk);                / additional, this situation shoud not ever happen        / down 25ms, up 25ms        / key down, bounce 25ms repeat(1251) (negedge clk) key_in = key_in;        / last 60ms repeat(3000) (negedge clk);        / key up, bounce 25ms repeat(1251) (negedge clk) key_in = key_in;        / wait 50ms repeat(2500) (negedge clk);        / stop        $stop;    endendmodule放在最后的,并不一定是最不重要的对于上面的三种方案,我比较喜欢第三种方案,它更贴合实际的按键状态,以上的代码我都做过modelsim仿真,但还没有在实际的项目中验证。在整理准备这个博客的时候,我又想到了一个感觉是更巧妙的方案,具体是这样的:在第三个方案的基础上,因为按键输入有变化的第一时刻,输出就已经改变了,在这种情况下,我可以把计时的时长改为一个很小的值,该值只要比抖动中的最长高低电平变化时间长即可。但想想也没这个必要,且这个抖动的高低电平变化时长我也很难去给它界定一个值。

    注意事项

    本文(单片机中按键消抖程序.doc)为本站会员(白大夫)主动上传,三一文库仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知三一文库(点击联系客服),我们立即给予删除!

    温馨提示:如果因为网速或其他原因下载失败请重新下载,重复下载不扣分。




    经营许可证编号:宁ICP备18001539号-1

    三一文库
    收起
    展开