如何自定义一个UIButton,并阻止父视图手势触发

关于手势和响应链这篇文章,我觉得已经讲的很不错了
https://www.jianshu.com/p/53e03e558cbd
但是里面有一个问题,当我们自己写一个继承于UIControl的自定义Button控件时,假设功能只是响应单击,可以这样写

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
    [super touchesBegan:touches withEvent:event];
    [self sendActionsForControlEvents:UIControlEventTouchUpInside];
}

会发现当我们单击时,自定义的Button控件触发了事件,父视图手势也触发了事件。但是如果继承UIButton,就不会有这样的事情发生。
补全touche的四个个方法

 (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
{
    [super touchesMoved:touches withEvent:event];
    NSLog(@"%s", __FUNCTION__);
}

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
{
    [super touchesEnded:touches withEvent:event];
    NSLog(@"%s", __FUNCTION__);
}

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event
{
    [super touchesCancelled:touches withEvent:event];
    NSLog(@"%s", __FUNCTION__);
}

最后发现,如果是继承UIButton,事件并没有被cancel掉,如果直接继承UIControl,事件其实还是被父视图的手势给Cancel了。所以才会出现这种和UIButton完全不同的现象。
其实在UIView有一个分类方法

// called when the recognizer attempts to transition out of UIGestureRecognizerStatePossible if a touch hit-tested to this view will be cancelled as a result of gesture recognition
// returns YES by default. return NO to cause the gesture recognizer to transition to UIGestureRecognizerStateFailed
// subclasses may override to prevent recognition of particular gestures. for example, UISlider prevents swipes parallel to the slider that start in the thumb
- (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer NS_AVAILABLE_IOS(6_0);

在自定义的Button中,重写这个方法,返回NO,就可以表现出和UIButton一模一样的行为了。

你可能感兴趣的:(如何自定义一个UIButton,并阻止父视图手势触发)