事件的传递与产生

2016-09-01  本文已影响15人  Mario_ZJ

如何寻找最合适的View

底层实现代码:
-(UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event{
   // 1.查看自己能不能接收事件
    if(self.userInteractionEnabled == NO || self.hidden == YES || self.alpha <= 0.01)
    {        
          return nil;
    }
  // 2.判断当前的点在不在自己身上.
    if(![self pointInside:point withEvent:event])
    {        
          return nil;
    }
  // 查看自己是不是最适合的view
  // 从后往前遍历自己的子控制器.
    int count = (int)self.subviews.count;
    for (int i = count - 1; i >=0; i--) {
       //取出子控件.
        UIView *childView = self.subviews[i];
       //要把当前的点转换成子控件上的坐标点.
        CGPoint childP =  [self convertPoint:point toView:childView];
        UIView *view = [childView hitTest:childP withEvent:event];
        //如果有值,直接返回,返回的就是最适合的View.
        if (view) {
            return view;     
         }
    }
    //没有找到比自己更适合的View.自己就是最适合的View 
    return self;
}

实现代码:

1.实现点击添加子控制器
 -(IBAction)chatBtnClick:(id)sender {  
     UIButton *btn = [UIButton buttonWithType:UIButtonTypeCustom];  
    [btn setImage:[UIImage imageNamed:@"对话框"] forState:UIControlStateNormal];        
    [btn setImage:[UIImage imageNamed:@"小孩"] forState:UIControlStateHighlighted];    
    btn.frame = CGRectMake(self.chatBtn.bounds.size.width * 0.5, -80, 100, 80);
    self.chatBtn.btn = btn;   
    [self.chatBtn addSubview:btn];   
}
2.自定义按钮,实现拖动按钮
让按钮跟着手指移动而移动.
-(void)touchesMoved:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{
    获取当前手指对象
    UITouch *touch =   [touches anyObject];
    获取当前手指所在的点
    CGPoint curP =  [touch locationInView:self];
    获取上一个手指所在的点
    CGPoint preP =  [touch previousLocationInView:self];   
    X轴的偏移量
    CGFloat offsetX = curP.x - preP.x;
    Y轴的偏移量
    CGFloat offsetY = curP.y - preP.y;
    移动
    self.transform = CGAffineTransformTranslate(self.transform, offsetX, offsetY);   
}
3.拦截hitTest方法
-(UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event{
    判断当前的点在不在上面的按钮上.
    先把点转换成上面按钮上面的点
   CGPoint btnP = [self convertPoint:point toView:self.btn];
    判断点在不在按钮上.
    if ([self.btn pointInside:btnP withEvent:event]) {
        让按钮点击响应事件
        return self.btn;
    }else{
        保持系统默认做法
        return [super hitTest:point withEvent:event];    }
}

注意:hitTest方法的返回值的问题
hitTest方法中最后返回的self和hitTest练习中最后返回[super hitTest]的原因

上一篇 下一篇

猜你喜欢

热点阅读