diff --git a/core/java/android/view/ViewRootImpl.java b/core/java/android/view/ViewRootImpl.java index fbb86ff3a55a8..e648d804f4897 100644 --- a/core/java/android/view/ViewRootImpl.java +++ b/core/java/android/view/ViewRootImpl.java @@ -321,6 +321,11 @@ public final class ViewRootImpl implements ViewParent, private static final int UNSET_SYNC_ID = -1; + /** + * Minimum time to wait before reporting changes to keep clear areas. + */ + private static final int KEEP_CLEAR_AREA_REPORT_RATE_MILLIS = 100; + @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) static final ThreadLocal sRunQueues = new ThreadLocal(); @@ -796,6 +801,8 @@ public final class ViewRootImpl implements ViewParent, new ViewRootRectTracker(v -> v.collectPreferKeepClearRects()); private final ViewRootRectTracker mUnrestrictedKeepClearRectsTracker = new ViewRootRectTracker(v -> v.collectUnrestrictedPreferKeepClearRects()); + private List mPendingKeepClearAreas; + private List mPendingUnrestrictedKeepClearAreas; private IAccessibilityEmbeddedConnection mAccessibilityEmbeddedConnection; @@ -4824,15 +4831,42 @@ public final class ViewRootImpl implements ViewParent, unrestrictedKeepClearRects = Collections.emptyList(); } - try { - mWindowSession.reportKeepClearAreasChanged(mWindow, restrictedKeepClearRects, - unrestrictedKeepClearRects); - } catch (RemoteException e) { - throw e.rethrowFromSystemServer(); + if (mHandler.hasMessages(MSG_REPORT_KEEP_CLEAR_RECTS)) { + // Keep clear areas have been reported recently, wait before reporting new set + // of keep clear areas + mPendingKeepClearAreas = restrictedKeepClearRects; + mPendingUnrestrictedKeepClearAreas = unrestrictedKeepClearRects; + } else { + mHandler.sendEmptyMessageDelayed(MSG_REPORT_KEEP_CLEAR_RECTS, + KEEP_CLEAR_AREA_REPORT_RATE_MILLIS); + try { + mWindowSession.reportKeepClearAreasChanged(mWindow, restrictedKeepClearRects, + unrestrictedKeepClearRects); + } catch (RemoteException e) { + throw e.rethrowFromSystemServer(); + } } } } + void reportKeepClearAreasChanged() { + final List restrictedKeepClearRects = mPendingKeepClearAreas; + final List unrestrictedKeepClearRects = mPendingUnrestrictedKeepClearAreas; + if (restrictedKeepClearRects == null && unrestrictedKeepClearRects == null) { + return; + } + + mPendingKeepClearAreas = null; + mPendingUnrestrictedKeepClearAreas = null; + + try { + mWindowSession.reportKeepClearAreasChanged(mWindow, restrictedKeepClearRects, + unrestrictedKeepClearRects); + } catch (RemoteException e) { + throw e.rethrowFromSystemServer(); + } + } + /** * Requests that the root render node is invalidated next time we perform a draw, such that * {@link WindowCallbacks#onPostDraw} gets called. @@ -5325,6 +5359,7 @@ public final class ViewRootImpl implements ViewParent, private static final int MSG_REQUEST_SCROLL_CAPTURE = 33; private static final int MSG_WINDOW_TOUCH_MODE_CHANGED = 34; private static final int MSG_KEEP_CLEAR_RECTS_CHANGED = 35; + private static final int MSG_REPORT_KEEP_CLEAR_RECTS = 36; final class ViewRootHandler extends Handler { @@ -5601,6 +5636,9 @@ public final class ViewRootImpl implements ViewParent, case MSG_KEEP_CLEAR_RECTS_CHANGED: { keepClearRectsChanged(); } break; + case MSG_REPORT_KEEP_CLEAR_RECTS: { + reportKeepClearAreasChanged(); + } break; case MSG_REQUEST_SCROLL_CAPTURE: handleScrollCaptureRequest((IScrollCaptureResponseListener) msg.obj); break;