InputManager 简介

1.1. 模块
按照进程空间,我大概把整个事件输入系统分为三个部分:

kernel 收集事件上报,InputManager 读取事件并分发, InputQueue 接收事件。之间进程通信用的读写设备文件,以及共享内
存等。
1.2. 类关系
本文主要介绍 InputManager 相关,其他模块不做过多讨论。
InputManager 相关的主要类关系图:

WindowManager 往上的还没有去看,先写写 c++ 层的部分。
整个 InputManager 是通过 NativeInputManager 提供给java层的 WindowManagerService 使用的。java 层通过 JNI 构造
NativeInputManager,并向下注册通道,最后等待底层上报的事件通过通道分发上来。
InputManager 主要有两大部件:
InputReader
InputDispatcher
分别负责事件的读取和分发,各自内部有一个线程负责循环。
被处理的事件类型有:
Switch
Keyboard
Cursor
Touch(MultiTouch, SingleTouch)
Joystick
这里我只关注了Keyboard,其他流程都是类似的,更多精彩内容等待大家挖掘

2. 处理流程

整个事件处理流程简单理解就是:
InputReader 线程不断的从底层读取事件,并提交给 InputDispatcher 列队
InputDispatcher 线程把队列里的事件通过通道上报给 WindowManagerService
2.1. 输入事件的读取
InputReaderThread负责输入事件的读取,流程大致如下(dia功能有限,生命线将就了):

1. InputReaderThread 每次循环,会调用 InputReader 的 loopOnce() 方法
2. InputReader::loopOnce() 方法会依次执行:
I. EventHub::getEvents() , 这个方法会通过 epoll_wait 获取 kernel 上报的事件, ( 按键事件) 通过
KeyLayoutMap.mapKey() 映射扫描码和键值

II. processEventsLocked() ⇒ processEventsForDevicesLocked() , 获取到事件后,就开始处理事件
a. InputDevice::process() , 交给设备处理
α. KeyboardInputMapper::process() ⇒ processKey() ,交给对应的mapper处理,这里介绍键盘
输入事件。 这里会根据orientationAware属性判断是否调用rotateKeyCode()旋转一些键值
α. QueuedInputListener::notifyKey(),最后把事件加入到一个队列
III. QueuedInputListener::flush() , 之后, 调用这个函数把之前加入队列的事件刷新( 其实是把事件从
QueuedInputListener报告给InputDispatcher)
a. InputDispatcher 会把InputReader 送过来的事件,先 intercept 给 java 层的 PhoneWindowManager 做
一些预处理(比如 截屏快捷键问题 里的处理),最后加入一个队列,等着 InputDispatcherThread 来
分发
事件的读取部分到此结束,后面事件的分发是由 InputDispatcherThread 进行的。
2.2. 输入事件的分发
InputDispatcherThread 把 InputReader 提交的事件分发给 InputQueue,然后一层层上报。过程大致如下:

期间用到了 epoll,信号量 等同步方法, 和共享内存等通信方式。。。越看越庞大,先止步于此吧。
可能有疑问的地方是, Channel B怎么来的?
其实在每个Activity的ViewRoot把窗口交给WindowManagerService的时候,WMS会打开一对通道。WMS把Channel A注册到
InputManager,ViewRoot端则把 Channel B注册到 InputQueue:

2.2.1. 事件的重复
mKeyRepeatState 维护了最后一个分发的事件的重复状态。
3. 其它
3.1. NavigationBar的处理

4.x之后,如果手机上有虚拟按键(MENU,HOME,SEARCH,BACK等),用户点击的时候,底层驱动直接发送的是
KeyEvent 给 WindowManager,处理流程和前文提到的一样。如果手机没有虚拟按键,则会显示一个NavigationBar,里面放
置几个KeyButtonView模拟成虚拟按键用于导航。
这几个按键的事件处理有点特别。可以说是结合了MotionEvent和KeyEvent进行的处理。这里简单说一下它的实现方式。
1. 由于NavigationBar是显示在屏幕上的,所以它接收的是MotionEvent。
2. 然后交给KeyButtonView处理,在点击事件中,KeyButtonView会根据它自身的属性(在navigation_bar.xml里指定),
如果发现自己有keyCode(systemui:keyCode),在响应事件的时候,就会往 InputManager (的Dispatcher里)注入
一个 KeyEvent。如果没有keyCode,就按普通的点击事件处理,回调各个 onClickListener 等等。。。
3. 再然后 InputManager 分发这个 KeyEvent 之前,让 WindowManager 拦截(interceptKeyBeforeDispatching)一次,
这样就走到跟有虚拟按键一样的流程。
其中,BACK ,HOME 以及 MENU 默认都指定了 一个 keyCode,所以走到第三步。而 RECENTAPP 默认则没有keyCode,
是在onClickListener里做的处理。如果需要把RECENTAPP也模拟成虚拟按键的方式处理,就需要增加一个键值,并在
navigation_bar.xml里指定给对应的KeyButtonView。

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: Unity InputManager是Unity引擎中的一个组件,用于管理游戏中的输入设备,例如键盘、鼠标、手柄等。通过InputManager,开发者可以轻松地获取玩家的输入,并将其应用于游戏中的角色控制、UI交互等方面。同时,InputManager还提供了一些常用的输入设置,例如灵敏度、反转轴等,方便开发者进行游戏调试和优化。 ### 回答2: Unity InputManager是Unity游戏引擎的一个功能强大的模块,允许用户从多个输入源(比如键盘、鼠标、控制器等)中捕捉输入。用于操作游戏角色、快速移动相机、进入不同的游戏模式等。通过使用Unity InputManager,用户能够创建响应灵敏和良好输入交互的游戏。Unity InputManager是一种非常适合初学者的输入管理器,因为它很容易上手,并且可以快速设置和调试输入,使得游戏玩家体验到更加愉快的游戏过程。 Unity InputManager不仅仅是一个单纯的按键输入功能,它还提供了丰富的输入选项和配置选项。其中包括对多年轻玩家的支持、可配置的按键重复等。同时还可以对输入源进行映射,使得在不同的平台下都能够兼容游戏的输入方式。Unity Input Manager还支持事件和响应式编程模式。事件模式中,可以设置一系列事件,以响应特定的用户输入。而响应式编程模式则允许用户编写自定义脚本,处理用户输入并响应游戏行为,从而实现更加灵活和定制化的游戏场景。 总之,Unity InputManager是一个在Unity中广泛使用和高度可定制的输入管理器。无论您是初学者或专业游戏设计师,都可以使用Unity InputManager轻松地实现高质量的用户输入交互。 ### 回答3: Unity InputManager是一个可以通过核心脚本来访问输入数据的工具,它可以使得我们在游戏中使用键盘、鼠标、手柄等各种输入设备。Unity InputManager可以简化游戏中输入控制的开发,提供一种方法来方便的获取并配置用户输入数据,使得游戏控制更加方便与灵活,提升了用户游戏体验。 Unity InputManager提供了多种输入类型,如:Keyboard、Mouse、Joystick、Touch Screen等。根据不同的输入类型,我们可以在Unity InputManager中对键位进行配置,比如指定按键的名称、部件和轴等。配置完成后,我们可以通过脚本来访问Unity InputManager并接收输入数据。 Unity InputManager还提供了一份默认的输入映射,它已经包含了常见输入设备的配置,比如:鼠标左键、右键、中键,键盘的wasd、上、下、左、右等。当我们的项目中需要使用这些输入类型时,就可以直接使用Unity InputManager中的默认映射而无需重新配置。 Unity InputManager需要注意的一点是,当我们在脚本中访问输入数据时,最好使用Input.GetAxis和Input.GetButton等通用方法来获取数据,而不是通过KeyCode或if语句等来获取,因为InputManager可以帮助我们自动处理输入设备的不同和用户的个性化设置。这样不仅避免了代码冗长,也使得整体的代码更加简洁易读。 总之,Unity InputManager是Unity中一个非常实用的工具,可大大简化游戏中输入控制的开发工作,提升用户游戏体验,如果您想要更深入学习Unity InputManager,可以在Unity官网上找到更多关于该工具的学习资源。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值