How to reliably find correct view for UIGestureRecognizer?

Viewed 16211

I have a bunch of UIViews like in the image below. The red/pink (semi-transparent) view is on top of the others.

  • Red has a UISwipeGestureRecognizer.
  • Green has as a UITapGestureRecognizer.
  • Blue has no recognizer.

enter image description here

A tap on the visible (bottom-left) part of Green trigger its recognizer.

A tap on the hidden parts of Green does not trigger its recognizer (Red blocks it).

That's the problem: I want Green to trigger. How can I do this?

In practice, the views may be in any order, any number and be subviews of each others etc. But the problem is the same:

How can I reliably find the uppermost view that can handle the gesture (tap or swipe)?


I tried with the code below. It neatly traverses all views, but it fails since it cannot know if the event is part of a swipe or a tap. So the method always returns the red view. If I remove the swipe-recognizer from Red, the code works correctly.

- (UIView*)hitTest:(CGPoint)point withEvent:(UIEvent *)event 
{
    UIView *hitView = [super hitTest:point withEvent:event];
    if (hitView == self)
    {
        if (self.hasASwipeRecognizer)
            return self;  // What if this was a tap?
        if (self.hasATapRecognizer)
            return self; 
        else
            return nil;
    }
    else
         return hitView;
 }
3 Answers
Related