From e7f096753e0e8310dda514808cced420c402628b Mon Sep 17 00:00:00 2001 From: Genki Kondo Date: Mon, 27 Mar 2023 10:12:36 -0700 Subject: [PATCH] Trigger pointer leave when active controller switched Summary: For VR, JSPointerDispatcher skips calculating the delta of hit targets (which happens in onMove) on the frame in which the active controller is switched because the motion event is a DOWN event, not a MOVE event in that specific frame. This diff fixes the issue by just calling onMove in addition to onDown for DOWN motion events. Unfortunately we do not have separate pointer IDs for each controller. This won't change the behavior for non-hoverable pointers. For hoverable pointers, it will dispatch an extra pointer_enter if the hit path has changed between the last move event and the down event. Changelog: [Internal][Fixed] - Trigger pointer leave when active controller switched Reviewed By: lunaleaps, javache Differential Revision: D44377324 fbshipit-source-id: 0942e3262598b3ce92b5fca736ab3a913ebdbfed --- .../com/facebook/react/uimanager/JSPointerDispatcher.java | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/uimanager/JSPointerDispatcher.java b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/uimanager/JSPointerDispatcher.java index 8f4a992f85383a..c93537fbae35ef 100644 --- a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/uimanager/JSPointerDispatcher.java +++ b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/uimanager/JSPointerDispatcher.java @@ -158,6 +158,10 @@ private void onDown( motionEvent, enterViewTargets, eventDispatcher); + } else { + // There are cases when the pointer may have moved in the same frame as the down event. + // Dispatch the move event before the down event. + onMove(activeTargetTag, eventState, motionEvent, eventDispatcher); } boolean listeningForDown = @@ -384,11 +388,10 @@ private void onMove( int activePointerId = eventState.getActivePointerId(); List activeHitPath = eventState.getHitPathByPointerId().get(activePointerId); - List lastHitPath = mLastHitPathByPointerId != null && mLastHitPathByPointerId.containsKey(activePointerId) ? mLastHitPathByPointerId.get(activePointerId) - : new ArrayList(); + : new ArrayList<>(); // hitState is list ordered from inner child -> parent tag // Traverse hitState back-to-front to find the first divergence with lastHitPath