macoscocoansscrollviewnsrespondertrackpad

Nested NSScrollViews that can be scrolled with different gestures?


I've got an app with an NSScrollView nested inside another NSScrollView. I'd like the user to be able to scroll the inner scrollview using two-finger swipe, and to scroll the outer scrollview using three fingers.

I imagine I'll need to somehow configure each scrollview to reject touches with the wrong numbers of fingers, but I'm not sure how to do this.


Solution

  • I figured it out! The trick is to subclass the inner ScrollView and force it to reject gestures that have a certain number of touches, forwarding them to the parent scrollview:

    - (void)scrollWheel:(NSEvent *)event {
        if (_forwardScrollToParent) {
            // [self.enclosingScrollView scrollWheel:event];
        } else {
            [super scrollWheel:event];
            [self recordInteractionWithThisTab];
        }
    }
    
    - (void)touchesBeganWithEvent:(NSEvent *)event {
        [super touchesBeganWithEvent:event];
        NSInteger nTouches = [event touchesMatchingPhase:NSTouchPhaseTouching inView:self].count;
        if (nTouches == 3) {
            _forwardScrollToParent = YES;
        } else {
            _forwardScrollToParent = NO;
        }
    }