一、背景

最近开发了一个空鼠遥控器的外设产品,采用Nordic51822 MCU芯片,基于BLE4.0标准,与OTT盒子连接,同时具有遥控器、空鼠、游戏手柄的功能。其中在按键的设计这块我们走了一些弯路,现总结一下经验教训,以供开发类似产品时参考。

二、初始设计

1、结构设计

最初按键在结构设计上采用类似路由器按键的方式,比较简单,在PCB按键位置放置一个波仔片,然后上面加一个橡胶的按键,按下橡胶时,其内部的触点压下波仔片,波仔片把电路连通,从而实现一次按键动作,属于机械式按键方式。

如图:

2、硬件设计

在按键的硬件设计上,我们采用MCU的GPIO来检测,通过把MCU的GPIO引脚连接到按键上,MCU内部把这个GPIO上拉,然后再把按键接地,形成回路。当按键没有按下时,回路断开为高电平,当按键按下后,回路接通为低电平(低有效)。软件通过检测这个GPIO从高到低的电平变化,即可检测出按键是否被按下。

如图:

3、软件设计

由于产品要支持游戏手柄,所以存在多个按键同时按下的情况,并且每个按键都需要各自独立检测按下弹起状态。软件实现上,把每个按键相连的GPIO设置成输入模式,并检测从高到低的电平变化,当按键按下时,电平被拉低,这个电平变化被检测到之后,触发一个中断。接下来的处理有两个特别的设计考量:

1)软件接收到按键中断后,把这个中断事件放入按键对应的中断事件队列,然后起一个50ms的定时器,定时器超时后就从各个按键对应的中断事件队列各取一个事件,然后通过BLE上报OTT盒子。这样设计的原因是因为有需要多个按键同时按下的情况,而实际上人即便同时按下多个按键,肯定也是有先后的,所以需要有一个延时上报来允许在一定时间内先后按下的键被认为是同时按下的。延时上报定时器每50ms超时一次就处理上报一次,只要还有一个按键的事件队列里还有事件未被处理,这个定时器就不停止。

2)同时每个按键的事件队列长度只设计为3个位置,按下或者弹起各作为一个事件入队,中断检测到事件后从队尾入队,定时器超时后从队头取事件,当某个按键的队列满了后,假如又来了第4个事件,就把队列第3个位置的事件删掉,同时抛弃掉第4个事件。因为每个按键的按下和弹起事件是交替出现的,所以这样做就相当于删除了一对按下和弹起事件。这样设计的原因是用户有可能十分快速的按键,但我们起的延时上报定时器是50ms上报一次按键事件,每个键一次取一个事件上报,如果当队列有积压时而又没有删除事件的设计,就可能出现用户密集按键停止后,按键还陆续向OTT盒子上报,这样的用户体验是不行的。

三、改进设计

1、结构改进

产品第一版出来后,因为采用的波仔片机械式按键,所以每次按下都有一个塔塔声,经过试用大家普遍反映按键很硬,手感不好,需要改进。最初我们以为问题的原因在于采用了机械式按键设计,如果要手感好可能就要采用电容式按键设计。电容式按键的原理是当手按下按键时,按键里的触点往下压,造成跟PCB板上的触点距离改变,从而带来两者间的容值发生改变,检测并计算这个容值的改变,就可以转换成检测到的按键事件,但经过了解这种方式,会引入软件算法的复杂度,我们在此之前没有经验。

我们经过研究其他厂商的手柄发现,大多数游戏手柄并没有采用电容式按键,而是在PCB板上采用手指交叉状的触点,然后上面覆盖一层软胶,软胶内部有一块导电橡胶,软胶上是硬塑料的按键。这样当硬塑料按键被按下时,压下软胶,软胶内的导电橡胶向下压在PCB板的触点上,由于导电橡胶的导电性把触点的正负极连通,同时导电橡胶的柔软度使得其更容易与触点结合紧密,手指交叉状的触点也加大了正负极连通的容易度,这样就实现了一次按键动作。

如图:

2、硬件改进

在电路上,很多游戏手柄采用的是正交矩阵的电路设计方式,这样能够节省GPIO的用量,在GPIO不够用的MCU芯片上,是一种好的选择。但如果用这种方式,软件上就不能采用中断式的检测了,而要采用扫描式的检测,需要定时去扫描横轴和众轴的GPIO,当检测到某个横轴和众轴的GPIO为低电平时,就能确定其交叉的那个点所对应的按键被按下了。在我们的MCU上GPIO数量是够的,所以为了软件实现的简单起见,还是维持原有的每个按键对应一个GPIO,每个GPIO接地的方式。

矩阵式电路如图:

3、软件改进

软件开发完成后,测试时发现一个问题,就是当按键按下时,正常情况MCU只会上报一个按下的中断事件,但有时MCU会上报3个中断事件,分别是按下、弹起、按下。这种情况可能是GPIO电路信号有毛刺或者MCU内部中断缓存处理有问题造成的。要解决这个问题,需要加一个防抖定时器,在获取到一个按键中断事件之后起一个定时器,在这个定时器超时前,如果再有中断事件上报,就直接丢弃,当定时器超时后,再收到中断事件,就可以继续正常处理,同时重新启动这个定时器,从而形成防抖处理机制。

四、总结

项目过程中,从结构、硬件到软件都走了一些弯路,一方面也是之前没有类似产品经验造成的,在经过研究分析和参考了他人的设计之后,这些问题也陆续得到解决。在这里把这个过程记录下来,后续有人碰到类似问题时,可以做一个参考。

(完)

关于游戏手柄按键的设计相关推荐

  1. Verilog设计实例(8)按键防抖设计之软件防抖

    博文目录 写在前面 正文 背景介绍及回顾 单个按键 单按键的其他设计版本 多个按键 写在最后 参考资料 交个朋友 写在前面 个人微信公众号: FPGA LAB 个人博客首页 注:学习交流使用! 正文 ...

  2. 单片机按键软硬件设计技巧!

    在单片机系统里,按键是常见的输入设备,在本文将介绍几种按键硬件.软件设计方面的技巧. 一般在按键的设计上,一般有四种方案. 一是GPIO口直接检测单个按键,如图1.1所示; 二是按键较多则使用矩阵键盘 ...

  3. android 按键点击触摸有水印效果_“100例”—优秀产品设计按键细节设计美图

    品索设计,让设计考研 \ 就业 \ 留学更简单欢迎关注「品索设计」按键是产品设计中非常重要的一个细节,它是一个产品中与人零距离接触次数最多的一个地方.设计可不是单单有创意就可以的,要想把创意展现得好, ...

  4. 游戏手柄按键遥杆值检测

    前言 本章讲述游戏手柄按键遥感值检测 1 环境 as 4.1.* 2 代码 MainActivity.java package com.example.testthooth1;import andro ...

  5. Android 模拟游戏手柄按键(跨进程 KeyEvent 事件)实践方案

    Android 模拟游戏手柄按键(跨进程 KeyEvent 事件)实践方案

  6. 有限状态机的嵌入式Linux按键驱动设计(转载)

    本文转载自边缘之火<有限状态机的嵌入式Linux按键驱动设计(转载)> 原文链接:  http://www.eccn.com/design_2010052509381340.htm 秦国栋 ...

  7. linux 薄膜键盘驱动,有限状态机的嵌入式Linux按键驱动设计

    0  引言 一般的按键驱动程序通常非常简单.在程序中一旦检测到按键输入口为低电平时,就采用软件延时10 ms后再次检测按键输入口.如果仍然是低电平则表示有按键按下,便转入执行按键处理程序:否则,当按键 ...

  8. Android 小米盒子游戏手柄按键捕获 - 能获取到的 home 键依然是个痛

    Android 小米盒子游戏手柄按键捕获 太阳火神的美丽人生 (http://blog.csdn.net/opengl_es) 本文遵循"署名-非商业用途-保持一致"创作公用协议 ...

  9. linux按键驱动设计(V3S开发板)

    1.前言 本文描述了基于全志V3S开发板的按键驱动程序和测试应用程序的设计流程. 本次设计系统内核是基于linux3.4. 2.设计流程概述 本次设计的步骤是: 步骤一.编写一个driver_butt ...

最新文章

  1. 反转!BAT编程吸金榜来了,AI程序员刷爆了......
  2. CTOR对比Gavin提出的交易排序规则
  3. Mybatis映射文件(3)
  4. android 分区layout以及虚拟内存布局-小结
  5. 理解分布式一致性:Paxos协议之Cheap Paxos Fast Paxos
  6. elasticsearch Insert 插入数据和delete 删除数据(Java)
  7. 动态卷积效率低?UCSD微软用矩阵分解的方法解决了这个问题,性能还更高!(ICLR2021)...
  8. @EqualsAndHashCode
  9. 俯瞰大雾弥漫下的鄱阳湖二桥
  10. scrapy爬取某网站,模拟登陆过程中遇到的那些坑
  11. 19muduo_base库源码分析(十)
  12. Matlab函数——wgn
  13. Atitit 高并发设计实践 艾提拉著 目录 1. 并发的实现俩中模式 并发角度来看 基于事件触发vs线程的 1 2. 负载均衡 1 2.1. 云服务模型paas caas faas+http
  14. 【Unity3D】地形Terrain
  15. 汇编语言工具(DosBox、debug)下载与安装教程
  16. java gzip解压请求_使用 gzip 压缩请求正文
  17. 质量管理体系和行业标准
  18. 英语对于软件开发者来说到底有多重要?
  19. 静态代理和动态代理的区别和联系
  20. h3c交换机端口加入vlan命令_7.2.2 H3C交换机VLAN接口基本属性配置

热门文章

  1. STM32-SWD仿真时PB3,PB4,PA15使用问题
  2. 深度学习目标检测方法汇总
  3. 产品| 产品经理学习路径及职业规划
  4. 评价RA滑膜炎的综合评分系统的计量学特点: 来自一项随机、前瞻、多中心研究的结果...
  5. 给宝宝补钙的健康新钙念
  6. 数据中台建设(三):数据中台架构介绍
  7. Java中两数交换引发的值传递问题及解决方案
  8. empty() 是 (boolean) var 的反义词 is_null() 是 is_set() 的反义词!
  9. 【UEFI基础】EFI_HANDLE
  10. 八、CPython语法改动实验:增加“非”与“前缀自增”