事件
事件包括有三类:Touch Motion Remote 本篇主要介绍touch事件
Touch事件
事件产生->事件分发->事件响应
每产生一个时间都会产生一个UIEvent对象,该对象记录了事件、类型、触点等信息
@interface UIEvent:NSObject
属性有 type,subType
方法:-(nullable NSSet<UITouch*>*)allTouches//说明UIEvent持有UITouch,也能用以判断是几个点的触控
@interface UITouch:NSObject
属性 phase,tapCount,gestureRecgnizers
UIView中有方法-(UIView*)hitTest:(CGPoint)point withEvent:(UIEvent*)event//用以判断当前的touch是点在了那个View上
hitTest方法从UIWindow开始父类传到子类,subViews按照逆顺序遍历
事件分发从UIAppliction一直到hitTestView
-(void)sendEvent:(UIEvent*)event;
touch响应事件
-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent*)event
-(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent*)event
-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent*)event
-(void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent*)event
Responder Chain从子类到父类传递 一直到AppDelegate如果都没有响应就丢弃
实例 加大按钮的点击区域
方法1
-(UIView*)hitTest:(CGPoint)point withEvent:(UIEvent*)event{
//使用cgrectInset作用是 改变目标frame的inset
CGRect targetRect=CGRectInset(_button.frame, -ExtraPadding, -ExtraPadding);
//重点 查看点击区域在targetRect中吗
if(CGRectContainsPoint(targetRect,point)){
//把这一区域设置为button的点击区域
return _button;
}
else
return [super hitTest:pointwithEvent:event];
}
方法二: 调用hitTest会先调用ponitInside
创建button类 重写
-(BOOL)pointInside:(CGPoint)point withEvent:(UIEvent*)event{
CGRecttargetRect=CGRectInset(self.bounds,-20, -20);
//如果想使用frame 因为frame是父view的坐标系 所以需要转化
//CGPoint convertPoint=[self convertPoint:point toView:self.superview];
//CGRect targetRectFrame=CGRectInset(self.frame, -20, -20);
//此时下方的point应该使用convertPoint
if(CGRectContainsPoint(targetRect, point)){
return YES;
}
else
return [super pointInside:pointwithEvent:event];
子View超过了父View的范围
方法修改父View的pointInside
-(BOOL)pointInside:(CGPoint)point withEvent:(UIEvent*)event
{
//ponit应该是button的坐标系中 而此时point是view的 因此需要转化
if([_button pointInside:[self convertPoint:point toView:_button] withEvent:event])
{
return YES;
}
else
return [super pointInside:pointwithEvent:event];
}