Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5c57f3be authored by Galia Peycheva's avatar Galia Peycheva Committed by Android (Google) Code Review
Browse files

Merge changes from topic "keep_clear_areas"

* changes:
  Add keep clear rects API
  Add WMS support for keep-clear areas
parents 62414500 4e2adbd3
Loading
Loading
Loading
Loading
+5 −0
Original line number Diff line number Diff line
@@ -1135,6 +1135,7 @@ package android {
    field public static final int popupWindowStyle = 16842870; // 0x1010076
    field public static final int port = 16842793; // 0x1010029
    field public static final int positiveButtonText = 16843253; // 0x10101f5
    field public static final int preferKeepClear;
    field public static final int preferMinimalPostProcessing = 16844300; // 0x101060c
    field public static final int preferenceCategoryStyle = 16842892; // 0x101008c
    field public static final int preferenceFragmentStyle = 16844038; // 0x1010506
@@ -50270,6 +50271,7 @@ package android.view {
    method public float getPivotX();
    method public float getPivotY();
    method public android.view.PointerIcon getPointerIcon();
    method @NonNull public final java.util.List<android.graphics.Rect> getPreferKeepClearRects();
    method @Nullable public String[] getReceiveContentMimeTypes();
    method public android.content.res.Resources getResources();
    method public final boolean getRevealOnFocusHint();
@@ -50387,6 +50389,7 @@ package android.view {
    method protected boolean isPaddingOffsetRequired();
    method public boolean isPaddingRelative();
    method public boolean isPivotSet();
    method public final boolean isPreferKeepClear();
    method public boolean isPressed();
    method public boolean isSaveEnabled();
    method public boolean isSaveFromParentEnabled();
@@ -50629,6 +50632,8 @@ package android.view {
    method public void setPivotX(float);
    method public void setPivotY(float);
    method public void setPointerIcon(android.view.PointerIcon);
    method public final void setPreferKeepClear(boolean);
    method public final void setPreferKeepClearRects(@NonNull java.util.List<android.graphics.Rect>);
    method public void setPressed(boolean);
    method public void setRenderEffect(@Nullable android.graphics.RenderEffect);
    method public final void setRevealOnFocusHint(boolean);
+8 −0
Original line number Diff line number Diff line
@@ -16,8 +16,11 @@

package android.view;

import android.graphics.Rect;
import android.content.res.Configuration;

import java.util.List;

/**
 * Interface to listen for changes to display window-containers.
 *
@@ -56,4 +59,9 @@ oneway interface IDisplayWindowListener {
     * Called when the previous fixed rotation on a display is finished.
     */
    void onFixedRotationFinished(int displayId);

    /**
     * Called when the keep clear ares on a display have changed.
     */
    void onKeepClearAreasChanged(int displayId, in List<Rect> keepClearAreas);
}
+5 −0
Original line number Diff line number Diff line
@@ -289,6 +289,11 @@ interface IWindowSession {
     */
    oneway void reportSystemGestureExclusionChanged(IWindow window, in List<Rect> exclusionRects);

    /**
     * Called when the keep-clear areas for this window have changed.
     */
    oneway void reportKeepClearAreasChanged(IWindow window, in List<Rect> keepClearRects);

    /**
    * Request the server to call setInputWindowInfo on a given Surface, and return
    * an input channel where the client can receive input.
+132 −10
Original line number Diff line number Diff line
@@ -4734,15 +4734,18 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
        WindowInsetsAnimation.Callback mWindowInsetsAnimationCallback;
        /**
         * This lives here since it's only valid for interactive views. This list is null until the
         * first use.
         * This lives here since it's only valid for interactive views. This list is null
         * until its first use.
         */
        private List<Rect> mSystemGestureExclusionRects = null;
        private List<Rect> mKeepClearRects = null;
        private boolean mPreferKeepClear = false;
        /**
         * Used to track {@link #mSystemGestureExclusionRects}
         * Used to track {@link #mSystemGestureExclusionRects} and {@link #mKeepClearRects}
         */
        public RenderNode.PositionUpdateListener mPositionUpdateListener;
        private Runnable mPositionChangedUpdate;
        /**
         * Allows the application to implement custom scroll capture support.
@@ -6028,6 +6031,9 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
                case R.styleable.View_clipToOutline:
                    setClipToOutline(a.getBoolean(attr, false));
                    break;
                case R.styleable.View_preferKeepClear:
                    setPreferKeepClear(a.getBoolean(attr, false));
                    break;
            }
        }
@@ -11665,37 +11671,49 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
        } else {
            info.mSystemGestureExclusionRects = new ArrayList<>(rects);
        }
        if (rects.isEmpty()) {
        updatePositionUpdateListener();
        postUpdate(this::updateSystemGestureExclusionRects);
    }
    private void updatePositionUpdateListener() {
        final ListenerInfo info = getListenerInfo();
        if (getSystemGestureExclusionRects().isEmpty()
                && collectPreferKeepClearRects().isEmpty()) {
            if (info.mPositionUpdateListener != null) {
                mRenderNode.removePositionUpdateListener(info.mPositionUpdateListener);
                info.mPositionChangedUpdate = null;
            }
        } else {
            if (info.mPositionUpdateListener == null) {
                info.mPositionChangedUpdate = () -> {
                    updateSystemGestureExclusionRects();
                    updateKeepClearRects();
                };
                info.mPositionUpdateListener = new RenderNode.PositionUpdateListener() {
                    @Override
                    public void positionChanged(long n, int l, int t, int r, int b) {
                        postUpdateSystemGestureExclusionRects();
                        postUpdate(info.mPositionChangedUpdate);
                    }
                    @Override
                    public void positionLost(long frameNumber) {
                        postUpdateSystemGestureExclusionRects();
                        postUpdate(info.mPositionChangedUpdate);
                    }
                };
                mRenderNode.addPositionUpdateListener(info.mPositionUpdateListener);
            }
        }
        postUpdateSystemGestureExclusionRects();
    }
    /**
     * WARNING: this can be called by a hwui worker thread, not just the UI thread!
     */
    void postUpdateSystemGestureExclusionRects() {
    private void postUpdate(Runnable r) {
        // Potentially racey from a background thread. It's ok if it's not perfect.
        final Handler h = getHandler();
        if (h != null) {
            h.postAtFrontOfQueue(this::updateSystemGestureExclusionRects);
            h.postAtFrontOfQueue(r);
        }
    }
@@ -11726,6 +11744,106 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
        return Collections.emptyList();
    }
    /**
     * Set a preference to keep the bounds of this view clear from floating windows above this
     * view's window. This informs the system that the view is considered a vital area for the
     * user and that ideally it should not be covered. Setting this is only appropriate for UI
     * where the user would likely take action to uncover it.
     * <p>
     * The system will try to respect this, but when not possible will ignore it.
     * <p>
     * @see #setPreferKeepClearRects
     * @see #isPreferKeepClear
     * @attr ref android.R.styleable#View_preferKeepClear
     */
    public final void setPreferKeepClear(boolean preferKeepClear) {
        getListenerInfo().mPreferKeepClear = preferKeepClear;
        updatePositionUpdateListener();
        postUpdate(this::updateKeepClearRects);
    }
    /**
     * Retrieve the preference for this view to be kept clear. This is set either by
     * {@link #setPreferKeepClear} or via the attribute android.R.styleable#View_preferKeepClear.
     * <p>
     * If this is {@code true}, the system will ignore the Rects set by
     * {@link #setPreferKeepClearRects} and try to keep the whole view clear.
     * <p>
     * @see #setPreferKeepClear
     * @attr ref android.R.styleable#View_preferKeepClear
     */
    public final boolean isPreferKeepClear() {
        return mListenerInfo != null && mListenerInfo.mPreferKeepClear;
    }
    /**
     * Set a preference to keep the provided rects clear from floating windows above this
     * view's window. This informs the system that these rects are considered vital areas for the
     * user and that ideally they should not be covered. Setting this is only appropriate for UI
     * where the user would likely take action to uncover it.
     * <p>
     * If the whole view is preferred to be clear ({@link #isPreferKeepClear}), the rects set here
     * will be ignored.
     * <p>
     * The system will try to respect this preference, but when not possible will ignore it.
     * <p>
     * @see #setPreferKeepClear
     * @see #getPreferKeepClearRects
     */
    public final void setPreferKeepClearRects(@NonNull List<Rect> rects) {
        final ListenerInfo info = getListenerInfo();
        if (info.mKeepClearRects != null) {
            info.mKeepClearRects.clear();
            info.mKeepClearRects.addAll(rects);
        } else {
            info.mKeepClearRects = new ArrayList<>(rects);
        }
        updatePositionUpdateListener();
        postUpdate(this::updateKeepClearRects);
    }
    /**
     * @return the list of rects, set by {@link #setPreferKeepClearRects}.
     *
     * @see #setPreferKeepClearRects
     */
    @NonNull
    public final List<Rect> getPreferKeepClearRects() {
        final ListenerInfo info = mListenerInfo;
        if (info != null && info.mKeepClearRects != null) {
            return new ArrayList(info.mKeepClearRects);
        }
        return Collections.emptyList();
    }
    void updateKeepClearRects() {
        final AttachInfo ai = mAttachInfo;
        if (ai != null) {
            ai.mViewRootImpl.updateKeepClearRectsForView(this);
        }
    }
    /**
     * Retrieve the list of areas within this view's post-layout coordinate space which the
     * system will try to not cover with other floating elements, like the pip window.
     */
    @NonNull
    List<Rect> collectPreferKeepClearRects() {
        final ListenerInfo info = mListenerInfo;
        if (info != null) {
            final List<Rect> list = new ArrayList();
            if (info.mPreferKeepClear) {
                list.add(new Rect(0, 0, getWidth(), getHeight()));
            } else if (info.mKeepClearRects != null) {
                list.addAll(info.mKeepClearRects);
            }
            return list;
        }
        return Collections.emptyList();
    }
    /**
     * Compute the view's coordinate within the surface.
     *
@@ -15120,7 +15238,11 @@ public class View implements Drawable.Callback, KeyEvent.Callback,
            notifyAppearedOrDisappearedForContentCaptureIfNeeded(isVisible);
            if (!getSystemGestureExclusionRects().isEmpty()) {
                postUpdateSystemGestureExclusionRects();
                postUpdate(this::updateSystemGestureExclusionRects);
            }
            if (!collectPreferKeepClearRects().isEmpty()) {
                postUpdate(this::updateKeepClearRects);
            }
        }
    }
+32 −4
Original line number Diff line number Diff line
@@ -749,7 +749,10 @@ public final class ViewRootImpl implements ViewParent,
        return mImeFocusController;
    }

    private final GestureExclusionTracker mGestureExclusionTracker = new GestureExclusionTracker();
    private final ViewRootRectTracker mGestureExclusionTracker =
            new ViewRootRectTracker(v -> v.getSystemGestureExclusionRects());
    private final ViewRootRectTracker mKeepClearRectsTracker =
            new ViewRootRectTracker(v -> v.collectPreferKeepClearRects());

    private IAccessibilityEmbeddedConnection mAccessibilityEmbeddedConnection;

@@ -4767,7 +4770,7 @@ public final class ViewRootImpl implements ViewParent,
     * the root's view hierarchy.
     */
    public void setRootSystemGestureExclusionRects(@NonNull List<Rect> rects) {
        mGestureExclusionTracker.setRootSystemGestureExclusionRects(rects);
        mGestureExclusionTracker.setRootRects(rects);
        mHandler.sendEmptyMessage(MSG_SYSTEM_GESTURE_EXCLUSION_CHANGED);
    }

@@ -4777,7 +4780,26 @@ public final class ViewRootImpl implements ViewParent,
     */
    @NonNull
    public List<Rect> getRootSystemGestureExclusionRects() {
        return mGestureExclusionTracker.getRootSystemGestureExclusionRects();
        return mGestureExclusionTracker.getRootRects();
    }

    /**
     * Called from View when the position listener is triggered
     */
    void updateKeepClearRectsForView(View view) {
        mKeepClearRectsTracker.updateRectsForView(view);
        mHandler.sendEmptyMessage(MSG_KEEP_CLEAR_RECTS_CHANGED);
    }

    void keepClearRectsChanged() {
        final List<Rect> rectsForWindowManager = mKeepClearRectsTracker.computeChangedRects();
        if (rectsForWindowManager != null && mView != null) {
            try {
                mWindowSession.reportKeepClearAreasChanged(mWindow, rectsForWindowManager);
            } catch (RemoteException e) {
                throw e.rethrowFromSystemServer();
            }
        }
    }

    /**
@@ -5273,6 +5295,7 @@ public final class ViewRootImpl implements ViewParent,
    private static final int MSG_HIDE_INSETS = 35;
    private static final int MSG_REQUEST_SCROLL_CAPTURE = 36;
    private static final int MSG_WINDOW_TOUCH_MODE_CHANGED = 37;
    private static final int MSG_KEEP_CLEAR_RECTS_CHANGED = 38;


    final class ViewRootHandler extends Handler {
@@ -5341,6 +5364,8 @@ public final class ViewRootImpl implements ViewParent,
                    return "MSG_HIDE_INSETS";
                case MSG_WINDOW_TOUCH_MODE_CHANGED:
                    return "MSG_WINDOW_TOUCH_MODE_CHANGED";
                case MSG_KEEP_CLEAR_RECTS_CHANGED:
                    return "MSG_KEEP_CLEAR_RECTS_CHANGED";
            }
            return super.getMessageName(message);
        }
@@ -5565,6 +5590,9 @@ public final class ViewRootImpl implements ViewParent,
                case MSG_SYSTEM_GESTURE_EXCLUSION_CHANGED: {
                    systemGestureExclusionChanged();
                }   break;
                case MSG_KEEP_CLEAR_RECTS_CHANGED: {
                    keepClearRectsChanged();
                }   break;
                case MSG_REQUEST_SCROLL_CAPTURE:
                    handleScrollCaptureRequest((IScrollCaptureResponseListener) msg.obj);
                    break;
Loading