From da8ed6b6252fd53a83f14ab6da7e9b467f12ffe1 Mon Sep 17 00:00:00 2001 From: Joshua Gross Date: Thu, 4 Mar 2021 10:33:17 -0800 Subject: [PATCH] Disable setRemoveClippedSubviews in ReactHorizontalScrollContainerView.java in RTL mode Summary: setRemoveClippedSubviews in ReactHorizontalScrollContainerView.java in RTL mode is overzealous and unexpectedly clips out views in a way that is not desirable. It seems like what is actually happening is that the computed rect for the view is "0,0" and so contents are assumed to always be outside of this rect. For now I've disabled this feature. We can investigate as a followup. Changelog: [Android][Changed] Clipping subviews has been temporarily disabled in HorizontalScrollView in RTL mode. Minor/negligible perf impact. Reviewed By: sammy-SC Differential Revision: D26808937 fbshipit-source-id: 85af9c3fb542db9ca3aae03413a475695cd53391 --- .../ReactHorizontalScrollContainerView.java | 22 +++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java index 15aa7bfb7acdf7..0445fbdf36cf4a 100644 --- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java +++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java @@ -27,8 +27,30 @@ public ReactHorizontalScrollContainerView(Context context) { mCurrentWidth = 0; } + @Override + public void setRemoveClippedSubviews(boolean removeClippedSubviews) { + // Clipping doesn't work well for horizontal scroll views in RTL mode - in both + // Fabric and non-Fabric - especially with TextInputs. The behavior you could see + // is TextInputs being blurred immediately after being focused. So, for now, + // it's easier to just disable this for these specific RTL views. + // TODO T86027499: support `setRemoveClippedSubviews` in RTL mode + if (mLayoutDirection == LAYOUT_DIRECTION_RTL) { + super.setRemoveClippedSubviews(false); + return; + } + + super.setRemoveClippedSubviews(removeClippedSubviews); + } + @Override protected void onLayout(boolean changed, int left, int top, int right, int bottom) { + /** + * Note: in RTL mode, *when layout width changes*, we adjust the scroll position. Practically, + * this means that on the first (meaningful) layout we will go from position 0 to position + * (right - screenWidth). In theory this means if the width of the view ever changes during + * layout again, scrolling could jump. Which shouldn't happen in theory, but... if you find a + * weird product bug that looks related, keep this in mind. + */ if (mLayoutDirection == LAYOUT_DIRECTION_RTL) { // When the layout direction is RTL, we expect Yoga to give us a layout // that extends off the screen to the left so we re-center it with left=0