目录
事件传递
1、事件传递
1、iOS 检测到手指触摸,打包成一个UIEvent对象
2、springBoard
3、通过端口传递给当前进程
4、触发sorce1回调
5、soruce0回调
6、放入当前活动Application的事件队列
7、UIApplication 会从事件队列中取出触摸事件并传递给单例的 UIWindow 来处理
8、UIWindow 对象首先会使用 hitTest:withEvent:方法
9、方法内部调用pointInside来判断触点是否在自身上
如果在返回YES
如果有子view调用子view的hitTest,不断向下递归,寻找响应者
如果没有子view,返回自身,自身就是响应者
如果不在返回NO
返回nil,响应者不是自身或子view
响应者链
一、找到响应者之后事件是如何响应的
view(First Responser) –> 父View–>VC->The Window –> The Application –> nil(丢弃)
响应者链过程
1、调用响应者的touchBegain方法,此方法的默认实现将消息向上转发到响应程序链。
如果在不调用super(一种常用模式)的情况下重写此方法,则必须重写用于处理触摸事件的其他方法,即使您的实现什么也不做。
2、如果重写了touchBegain来处理事件,响应链会中断。
要想继续响应者链,可调用了 父类 的touchBegain,事件会被传递到父view.
注意父类和父view的区别。
3、如果响应者添加了手势,手势回调处理完成后,会调用响应者的touchesCancelled。
二、无法响应的情况
1.Alpha=0、hidden=YES、子视图超出父视图的情况、userInteractionEnabled=NO 视图会被忽略,不会调用hitTest
2.父视图被忽略后其所有子视图也会被忽略,所以View3上的button不会有点击反应
3.出现视图无法响应的情况,可以考虑上诉情况来排查问题
三、应用示例
限定点击区域
给定一个显示为圆形的视图,实现只有在点击区域在圆形里面才视为有效。
我们可以重写View的pointInside方法来判断点击的点是否在圆内,也就是判断点击的点到圆心的距离是否小于等于半径就可以。
行者常至,为者常成!