How to cancel UIGestureRecognizer if subview's button pressed

后端 未结 4 609
说谎
说谎 2021-02-04 03:27

I am struggling to get the behaviour I would like from the gesture recognisers, specifically cancelling certain gestures if others have fired.

I have a scrollView set to

相关标签:
4条回答
  • 2021-02-04 03:40

    Apple documentation shows the answer:

    - (void)viewDidLoad {
          [super viewDidLoad];
          // Add the delegate to the tap gesture recognizer
          self.tapGestureRecognizer.delegate = self;
    }
    
    // Implement the UIGestureRecognizerDelegate method
    -(BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:    (UITouch *)touch {
          // Determine if the touch is inside the custom subview
         if ([touch view] == self.customSubview){
             // If it is, prevent all of the delegate's gesture recognizers
             // from receiving the touch
            return NO;
         }
         return YES;
    }
    

    Of course in this case customSubview would be subview on the page that has buttons in it (or even the buttons on it)

    0 讨论(0)
  • 2021-02-04 03:41

    You can subclass UIView and overwrite the -touchesBegan selector, or you can play with the opaque property of the subviews to make them "invisible" to the touches (if view.opaque = NO, the view ignores touch events).

    0 讨论(0)
  • 2021-02-04 03:51

    The solution that worked the best for me in the end was to use the hitTest to determine if there were any buttons underneath the location of the tap gesture. If there are then just ignore the rest of the gesture code.

    Seems to work well. Would like to know if there are any gotchas with what I have done.

    - (void) tapGestureHandler:(UIGestureRecognizer *) gestureRecognizer {
        const CGFloat kTapMargin = 180;
    
        // Get the position of the point tapped in the window co-ordinate system
        CGPoint tapPoint = [gestureRecognizer locationInView:nil];
    
        // If there are no buttons beneath this tap then move to the next page if near the page edge
        UIView *viewAtBottomOfHeirachy = [self.window hitTest:tapPoint withEvent:nil];
        if (![viewAtBottomOfHeirachy isKindOfClass:[UIButton class]]) {
    
            // If the tap point is to the left of the page then go back a page
            if (tapPoint.x > (self.bounds.size.width - kTapMargin)) [self scrollRectToVisible:pageViewRightFrame animated:YES];
    
            // If the tap point is to the right of the page then go forward a page
            else if (tapPoint.x < kTapMargin) [self scrollRectToVisible:pageViewLeftFrame animated:YES];
        }   
    }
    
    0 讨论(0)
  • 2021-02-04 03:54

    Swift 3

    Set UITapGestureRecognizer

    let tap = UITapGestureRecognizer(target: self, action: #selector(Class.didTap))
    tap.delegate = self
    

    UITapGestureRecognizer delegate method:

    func gestureRecognizer(_ gestureRecognizer: UIGestureRecognizer, shouldReceive touch: UITouch) -> Bool {
        return touch.view != buttonThatShouldCancelTapGesture
    }
    
    0 讨论(0)
提交回复
热议问题