【Android工场】Android(安卓)Input System介绍
【Android工场】Android Input System介绍
主要模块
Android Input System主要涉及到EventHub,InputReader,InputDispatcher和InputTransport相关。
EventHub 主要监听/dev/input/event*事件上报,同时监听device的Add和Remove事件,封装成RawEvent
InputReader 根据RawEvent事件来源的device类型做对应的处理
InputDispatcher 判断事件是否丢弃,负责事件的分发
InputTransport 封装成了lib库,包括publiser和consumer两个模块,server端负责publish,APP的client端负责consume
Native对象
InputManager持有和管理InputReader和InputDispatcher两个对象以及两个对象所运行在的线程。
InputManager又被NativeInputManager持有,NativeInputManager为InputManagerService的Native对象,其地址被InputManagerService的成员变量mPtr保存。
NativeInputManager继承了InputDispatcherPolicyInterface和InputReaderPolicyInterface,因此Reader和Dispatcher中的mPolicy都指向它,policy的回调也会回调到它。
InputReader
Input Reader中维护了InputDevice向量,InputDevice中包含负责对应处理的InputMapper
Input Reader通过EventHub的getEvents获取Event
根据Event来源device的不同,选取对应的Input Mapper执行process(例如mt touch事件识别virtualkey并做处理,合成手写笔信息等)
InputListener
InputReader通过Input Listener调用InputDispatcher。
InputListener中维护一个NotifyArgs队列,对于不同的事件类型,使用不同的NotifyArgs。
InputReader解析出NotifyArgs对象,push进队列。Input Reader全部解析完后,调用InputListener flush方法,调用各个NotifyArgs的notify方法,回调InputDispatcher中的各个dispatch。
InputDispatcher
notifyMotion
此时会将motion event加入InputBoundQueue,同时会调用policy的interceptMotionBeforeQueueing和filterInputEvent。
interceptMotionBeforeQueueing给上层提供了分发前的拦截机会,回调会修改policyFlag,对后续分发产生影响。
filterInputEvent为上层提供filter功能的实现,如果event直接在filter中被处理了,直接跳过该事件的分发。
Drop reason
消息在分发阶段可能被drop掉,Dispatcher确定了集中drop原因,比如DROP_REASON_APP_SWITCH:APP切换时有一定保护延时,不接受按键信息 DROP_REASON_DISABLED:上层策略通知不接受信息。
Dispatcher还有种Frozen状态,该状态下事件会不处理,但是不会被drop。
findTouchedWindowTargetsLocked
窗口增改删除时,WindowManagerService会将窗口信息保存在InputDispatcher的mWindowHandles中。 FindTouchedWindowTargetsLocked会根据触摸事件的位置及窗口信息来确定将事件发送到哪个窗口。
CommandQueue
InputDispatcherThread维护了一个CommandQueue,除了正常接收、处理和分发消息外,其他的操作通过push Command到队列里,在下次循环时执行。例如doNotifyANRLockedInterruptible(通知ANR), doNotifyConfigurationChangedInterruptible(通知配置的变化), doInterceptKeyBeforeDispatchingLockedInterruptible(分发前拦截)等都是这个方式执行。
InputTransport
APP启动的时候调用addWindow注册InputChannel
InputConsumer和InputPublisher分别被APP和InputSystem所持有,Consumer中封装了socket的client端,Publisher封装了server端
APP端通过InputConsumer来接收处理event和发送finishSignal
InputSystem通过InputPublisher来发送event
Event Consume
APP进程监听到System通过socket发送过来的事件后会做对应的处理
- 非Move事件,立刻上报给APP,回调APP的事件监听函数
- Move事件
- 第一次接收到Move事件,通知FWK层打开app vsync监听,并且schedule vsync到来时的回调函数
- 后来监听到的Move事件会保存在mBatch对象中,不上报给APP
vsync到来时,consume Move事件的batch,生成MOVE事件上报给APP
Resample
插点算法出现的背景
由于Touch上报的频率和VSYNC不一致,会导致每次报点之间的距离不相同,导致滑动不平滑
插点算法介绍
- vsync到来时判断
如果RESAMPLE_LATENCY之内有MOVE point B上报,根据point B和之前的point A计算出虚拟上报点(绿点) - 下次vsync到来时
根据上次遗留的point B和本周期内上报的point C预测出虚拟上报点(黄点) - 因此每次vsync到来,consumeBatch时过滤掉RESAMPLE_LATENCY(默认5ms)内的点
更多相关文章
- GridView的简单使用,带有点击事件
- 解决CardView无点击效果,实现水波纹效果
- 详解Android(安卓)触摸事件处理和传递过程的来龙去脉
- Android退出程序(三)——Android事件总线
- 详解Android(安卓)触摸事件处理和传递过程的来龙去脉
- android事件处理
- 丰富多彩的Android(安卓)onTouch事件
- android使用CheckedTextView搭配listview完成选择列表
- android使用CheckedTextView搭配listview完成选择列表