iOS事件处理机制

事件类型

iOS的事件可以分为三类:触摸事件,加速计事件,远程控制事件

iOS中不是任何对象都能处理对象,只有继承了UIResponder的对象才能接收并处理事件. ---->响应者对象

typedef NS_ENUM(NSInteger, UIEventType) {
    UIEventTypeTouches,
    UIEventTypeMotion,
    UIEventTypeRemoteControl,
};

//事件类型
@property(nonatomic,readonly) UIEventType     type 
@property(nonatomic,readonly) UIEventSubtype  subtype 
//事件产生的时间
@property(nonatomic,readonly) NSTimeInterval  timestamp;

事件的传递

  • 系统把事件加入到一个由UIApplication管理的事件队列中
    之所以加入队列而不是栈是因为队列先进先出,意味着先产生的事件,先处理

  • 然后,事件会按照UIApplication -> UIWindow -> SuperView -> SubView的顺序不断的检测

  • 而检测就是靠两个方法hitTest与pointInside

事件与runloop

当我们触发了事件(触摸/锁屏/摇晃等)后,

  • IOKit.framework生成一个 IOHIDEvent事件

  • IOKit是苹果的硬件驱动框架

  • 由它进行底层接口的抽象封装与系统进行交互传递硬件感应的事件

  • 它专门处理用户交互设备,由IOHIDServicesIOHIDDisplays两部分组成

  • 其中IOHIDServices是专门处理用户交互的,它会将事件封装成IOHIDEvents对象,详细请看这里

  • 然后这些事件又由SpringBoard接收,它只接收收按键(锁屏/静音等),触摸,加速,接近传感器等几种 Event

  • 接着用mach port转发给需要的App进程

  • Source1 接收IOHIDEvent,之后再回调__IOHIDEventSystemClientQueueCallback()内触发的Source0

  • Source0再触发的 __dispatchPreprocessEventFromEventQueue()

  • __dispatchPreprocessEventFromEventQueue()IOHIDEvent处理包装成UIEvent进行处理分发,我们平时的UIGesture/处理屏幕旋转/发送给 UIWindow/UIButton 点击、touchesBegin/Move/End/Cancel这些事件,都是在这个回调中完成。

iOS事件处理机制_第1张图片
image.png
0 - [AView touchesBegan:withEvent
1 - [UIWindow _sendTouchesForEvent]
2 - [UIWindow sendEvent]           
3 - [UIApplication sendEvent]      
4 __dispatchPreprocessEventFromEventQueue
5 __handleEventQueueInternal
6 _CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE0_PERFORM_FUNCTION_
7 _CFRunLOOPDoSource0
8 _CFRunLOOPDoSources1
9 _CFRunLoopRun
10 _CFRunLoopRunSpecific
11 GSEventRunModal
12 UIApplication
13 main
14 start

手势识别

  • 当上面的 __dispatchPreprocessEventFromEventQueue() 识别了一个手势时,其首先会调用 Cancel 将当前的 touchesBegin/Move/End 系列回调打断。随后系统将对应的 UIGestureRecognizer 标记为待处理。

  • 苹果注册了一个 Observer 监测 BeforeWaiting (Loop即将进入休眠) 事件,这个Observer的回调函数是 _UIGestureRecognizerUpdateObserver(),其内部会获取所有刚被标记为待处理的 GestureRecognizer,并执行GestureRecognizer的回调。

  • 当有 UIGestureRecognizer 的变化(创建/销毁/状态改变)时,这个回调都会进行相应处理。

你可能感兴趣的:(iOS事件处理机制)