diff options
| author | 2024-10-29 19:02:21 +0000 | |
|---|---|---|
| committer | 2024-10-29 19:02:21 +0000 | |
| commit | cff23ddfd236b82e55f9c30b9df9e7df48b4af7b (patch) | |
| tree | 3a017af7af0aa666b90488ef624de28efd4cb30b | |
| parent | bbf2463510122c448aadea8549abb2dab7454ed9 (diff) | |
| parent | 213dd25ea8c14ce16a32dc9eb6581a9bc2ea09d1 (diff) | |
Merge "Set view bounds in parent by diff'ing the bounds in screen with parent." into main
| -rw-r--r-- | core/java/android/view/View.java | 45 |
1 files changed, 41 insertions, 4 deletions
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java index d9092ee737ce..d5fc26281fc6 100644 --- a/core/java/android/view/View.java +++ b/core/java/android/view/View.java @@ -40,6 +40,7 @@ import static android.view.displayhash.DisplayHashResultCallback.EXTRA_DISPLAY_H import static android.view.flags.Flags.FLAG_SENSITIVE_CONTENT_APP_PROTECTION_API; import static android.view.flags.Flags.FLAG_TOOLKIT_SET_FRAME_RATE_READ_ONLY; import static android.view.flags.Flags.FLAG_VIEW_VELOCITY_API; +import static android.view.flags.Flags.calculateBoundsInParentFromBoundsInScreen; import static android.view.flags.Flags.enableUseMeasureCacheDuringForceLayout; import static android.view.flags.Flags.sensitiveContentAppProtection; import static android.view.flags.Flags.toolkitFrameRateAnimationBugfix25q1; @@ -967,6 +968,13 @@ public class View implements Drawable.Callback, KeyEvent.Callback, private static boolean sAlwaysRemeasureExactly = false; /** + * When true calculates the bounds in parent from bounds in screen relative to its parents. + * This addresses the deprecated API (setBoundsInParent) in Compose, which causes empty + * getBoundsInParent call for Compose apps. + */ + private static boolean sCalculateBoundsInParentFromBoundsInScreenFlagValue = false; + + /** * When true makes it possible to use onMeasure caches also when the force layout flag is * enabled. This helps avoiding multiple measures in the same frame with the same dimensions. */ @@ -2556,6 +2564,8 @@ public class View implements Drawable.Callback, KeyEvent.Callback, sToolkitSetFrameRateReadOnlyFlagValue = toolkitSetFrameRateReadOnly(); sToolkitMetricsForFrameRateDecisionFlagValue = toolkitMetricsForFrameRateDecision(); + sCalculateBoundsInParentFromBoundsInScreenFlagValue = + calculateBoundsInParentFromBoundsInScreen(); sUseMeasureCacheDuringForceLayoutFlagValue = enableUseMeasureCacheDuringForceLayout(); } @@ -9776,7 +9786,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, structure.setChildCount(1); final ViewStructure root = structure.newChild(0); if (info != null) { - populateVirtualStructure(root, provider, info, forAutofill); + populateVirtualStructure(root, provider, info, null, forAutofill); info.recycle(); } else { Log.w(AUTOFILL_LOG_TAG, "AccessibilityNodeInfo is null."); @@ -11075,11 +11085,19 @@ public class View implements Drawable.Callback, KeyEvent.Callback, private void populateVirtualStructure(ViewStructure structure, AccessibilityNodeProvider provider, AccessibilityNodeInfo info, - boolean forAutofill) { + @Nullable AccessibilityNodeInfo parentInfo, boolean forAutofill) { structure.setId(AccessibilityNodeInfo.getVirtualDescendantId(info.getSourceNodeId()), null, null, info.getViewIdResourceName()); Rect rect = structure.getTempRect(); - info.getBoundsInParent(rect); + // The bounds in parent for Jetpack Compose views aren't set as setBoundsInParent is + // deprecated, and only setBoundsInScreen is called. + // The bounds in parent can be calculated by diff'ing the child view's bounds in screen with + // the parent's. + if (sCalculateBoundsInParentFromBoundsInScreenFlagValue) { + getBoundsInParent(info, parentInfo, rect); + } else { + info.getBoundsInParent(rect); + } structure.setDimens(rect.left, rect.top, 0, 0, rect.width(), rect.height()); structure.setVisibility(VISIBLE); structure.setEnabled(info.isEnabled()); @@ -11163,13 +11181,32 @@ public class View implements Drawable.Callback, KeyEvent.Callback, AccessibilityNodeInfo.getVirtualDescendantId(info.getChildId(i))); if (cinfo != null) { ViewStructure child = structure.newChild(i); - populateVirtualStructure(child, provider, cinfo, forAutofill); + populateVirtualStructure(child, provider, cinfo, info, forAutofill); cinfo.recycle(); } } } } + private void getBoundsInParent(@NonNull AccessibilityNodeInfo info, + @Nullable AccessibilityNodeInfo parentInfo, @NonNull Rect rect) { + info.getBoundsInParent(rect); + // Fallback to calculate bounds in parent by diffing the bounds in + // screen if it's all 0. + if ((rect.left | rect.top | rect.right | rect.bottom) == 0) { + if (parentInfo != null) { + Rect parentBoundsInScreen = parentInfo.getBoundsInScreen(); + Rect boundsInScreen = info.getBoundsInScreen(); + rect.set(boundsInScreen.left - parentBoundsInScreen.left, + boundsInScreen.top - parentBoundsInScreen.top, + boundsInScreen.right - parentBoundsInScreen.left, + boundsInScreen.bottom - parentBoundsInScreen.top); + } else { + info.getBoundsInScreen(rect); + } + } + } + /** * Dispatch creation of {@link ViewStructure} down the hierarchy. The default * implementation calls {@link #onProvideStructure} and |