Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 43 additions & 15 deletions ios/RNSScreenStack.mm
Original file line number Diff line number Diff line change
Expand Up @@ -600,27 +600,22 @@ - (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer
{
RNSScreenView *topScreen = (RNSScreenView *)_controller.viewControllers.lastObject.view;

if (![topScreen isKindOfClass:[RNSScreenView class]] || !topScreen.gestureEnabled ||
_controller.viewControllers.count < 2) {
return NO;
}

#if TARGET_OS_TV
[self cancelTouchesInParent];
return YES;
#else
if (topScreen.fullScreenSwipeEnabled) {
// we want only `RNSPanGestureRecognizer` to be able to recognize when
// `fullScreenSwipeEnabled` is set, and we are in the bounds set by user
if ([gestureRecognizer isKindOfClass:[RNSPanGestureRecognizer class]] &&
[self isInGestureResponseDistance:gestureRecognizer topScreen:topScreen]) {
// RNSPanGestureRecognizer will receive events iff topScreen.fullScreenSwipeEnabled == YES;
// Events are filtered in gestureRecognizer:shouldReceiveEvent: method
if ([gestureRecognizer isKindOfClass:[RNSPanGestureRecognizer class]]) {
if ([self isInGestureResponseDistance:gestureRecognizer topScreen:topScreen]) {
_isFullWidthSwiping = YES;
[self cancelTouchesInParent];
return YES;
}
return NO;
}

// Now we're dealing with RNSScreenEdgeGestureRecognizer (or _UIParallaxTransitionPanGestureRecognizer)
if (topScreen.customAnimationOnSwipe && [RNSScreenStackAnimator isCustomAnimation:topScreen.stackAnimation]) {
if ([gestureRecognizer isKindOfClass:[RNSScreenEdgeGestureRecognizer class]]) {
// if we do not set any explicit `semanticContentAttribute`, it is `UISemanticContentAttributeUnspecified` instead
Expand All @@ -639,10 +634,8 @@ - (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer
if ([gestureRecognizer isKindOfClass:[RNSScreenEdgeGestureRecognizer class]]) {
// it should only recognize with `customAnimationOnSwipe` set
return NO;
} else if ([gestureRecognizer isKindOfClass:[RNSPanGestureRecognizer class]]) {
// it should only recognize with `fullScreenSwipeEnabled` set
return NO;
}
// _UIParallaxTransitionPanGestureRecognizer (other...)
[self cancelTouchesInParent];
return YES;
}
Expand Down Expand Up @@ -819,16 +812,51 @@ - (BOOL)isScrollViewPanGestureRecognizer:(UIGestureRecognizer *)gestureRecognize
return scrollView.panGestureRecognizer == gestureRecognizer;
}

// RNSScreenStackView is a UIGestureRecognizerDelegate for three types of gesture recognizers:
// RNSPanGestureRecognizer, RNSScreenEdgeGestureRecognizer, _UIParallaxTransitionPanGestureRecognizer
// Be careful when adding another type of gesture recognizer.
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveEvent:(UIEvent *)event
{
RNSScreenView *topScreen = (RNSScreenView *)_controller.viewControllers.lastObject.view;

if (![topScreen isKindOfClass:[RNSScreenView class]] || !topScreen.gestureEnabled ||
_controller.viewControllers.count < 2) {
return NO;
}

// We want to pass events to RNSPanGestureRecognizer iff full screen swipe is enabled.
if ([gestureRecognizer isKindOfClass:[RNSPanGestureRecognizer class]]) {
return topScreen.fullScreenSwipeEnabled;
}

// RNSScreenEdgeGestureRecognizer || _UIParallaxTransitionPanGestureRecognizer
return YES;
}

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer
shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
{
return [self isScrollViewPanGestureRecognizer:otherGestureRecognizer];
if ([gestureRecognizer isKindOfClass:[RNSPanGestureRecognizer class]] &&
[self isScrollViewPanGestureRecognizer:otherGestureRecognizer]) {
RNSPanGestureRecognizer *panGestureRecognizer = (RNSPanGestureRecognizer *)gestureRecognizer;
BOOL isBackGesture = [panGestureRecognizer translationInView:panGestureRecognizer.view].x > 0 &&
_controller.viewControllers.count > 1;

if (gestureRecognizer.state == UIGestureRecognizerStateBegan || isBackGesture) {
return NO;
}

return YES;
}
return NO;
}

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer
shouldBeRequiredToFailByGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
{
return [self isScrollViewPanGestureRecognizer:otherGestureRecognizer];
return (
[gestureRecognizer isKindOfClass:[UIScreenEdgePanGestureRecognizer class]] &&
[self isScrollViewPanGestureRecognizer:otherGestureRecognizer]);
}

- (void)insertReactSubview:(RNSScreenView *)subview atIndex:(NSInteger)atIndex
Expand Down