Skip to content

Commit

Permalink
Make RootViewGestureHandler handler cancel awaiting gestures (#2900)
Browse files Browse the repository at this point in the history
## Description

Gesture Handler is handling calls to
`requestDisallowInterceptTouchEvent` by canceling all gestures:
https://github.com/software-mansion/react-native-gesture-handler/blob/5523506c7b64ac5a8a78f5d73dc96adfb13962ba/android/src/main/java/com/swmansion/gesturehandler/react/RNGestureHandlerRootHelper.kt#L90-L94

This is done by activating a root handler that should, in turn, cancel
other gestures:
https://github.com/software-mansion/react-native-gesture-handler/blob/5523506c7b64ac5a8a78f5d73dc96adfb13962ba/android/src/main/java/com/swmansion/gesturehandler/react/RNGestureHandlerRootHelper.kt#L109-L114

There is a case where this doesn't currently work: when gesture A waits
for gesture B and root view is activated, gesture B gets canceled but
gesture A is not due to this check:
https://github.com/software-mansion/react-native-gesture-handler/blob/5523506c7b64ac5a8a78f5d73dc96adfb13962ba/android/src/main/java/com/swmansion/gesturehandler/core/GestureHandlerOrchestrator.kt#L692-L698

Since handler A is awaiting, it doesn't get canceled. Gesture B does get
canceled, which in turn causes gesture A to activate, effectively making
it ignore the cancellation.

This happens because of this method:
https://github.com/software-mansion/react-native-gesture-handler/blob/5523506c7b64ac5a8a78f5d73dc96adfb13962ba/android/src/main/java/com/swmansion/gesturehandler/react/RNGestureHandlerInteractionManager.kt#L52-L58
which will always return false if the activating gesture is root view.

This PR makes it so that if the activating gesture is the root handler,
`shouldHandlerBeCancelledBy` will always return `true`, canceling the
waiting gesture.

Fixes
#2870

## Test plan

Tested on the example app and the reproducer from the issue
  • Loading branch information
j-piasecki authored May 9, 2024
1 parent 5523506 commit 030cf73
Show file tree
Hide file tree
Showing 2 changed files with 5 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,10 @@ class RNGestureHandlerInteractionManager : GestureHandlerInteractionController {
return otherHandler.disallowInterruption
}

if (otherHandler is RNGestureHandlerRootHelper.RootViewGestureHandler) {
return true
}

return false
}
override fun shouldRecognizeSimultaneously(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ class RNGestureHandlerRootHelper(private val context: ReactContext, wrappedView:
}
}

private inner class RootViewGestureHandler : GestureHandler<RootViewGestureHandler>() {
internal inner class RootViewGestureHandler : GestureHandler<RootViewGestureHandler>() {
override fun onHandle(event: MotionEvent, sourceEvent: MotionEvent) {
val currentState = state
// we shouldn't stop intercepting events when there is an active handler already, which could happen when
Expand Down

0 comments on commit 030cf73

Please sign in to comment.