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

Commit 7f9f126d authored by Hyunyoung Song's avatar Hyunyoung Song Committed by Android (Google) Code Review
Browse files

Merge "Add passive callback for system-run insets animation" into tm-qpr-dev

parents f02444f0 03110e20
Loading
Loading
Loading
Loading
+24 −2
Original line number Diff line number Diff line
@@ -314,6 +314,9 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
            (int) (startValue.right + fraction * (endValue.right - startValue.right)),
            (int) (startValue.bottom + fraction * (endValue.bottom - startValue.bottom)));

    /** Logging listener. */
    private WindowInsetsAnimationControlListener mLoggingListener;

    /**
     * The default implementation of listener, to be used by InsetsController and InsetsPolicy to
     * animate insets.
@@ -330,6 +333,7 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
        private final long mDurationMs;
        private final boolean mDisable;
        private final int mFloatingImeBottomInset;
        private final WindowInsetsAnimationControlListener mLoggingListener;

        private final ThreadLocal<AnimationHandler> mSfAnimationHandlerThreadLocal =
                new ThreadLocal<AnimationHandler>() {
@@ -343,7 +347,7 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation

        public InternalAnimationControlListener(boolean show, boolean hasAnimationCallbacks,
                @InsetsType int requestedTypes, @Behavior int behavior, boolean disable,
                int floatingImeBottomInset) {
                int floatingImeBottomInset, WindowInsetsAnimationControlListener loggingListener) {
            mShow = show;
            mHasAnimationCallbacks = hasAnimationCallbacks;
            mRequestedTypes = requestedTypes;
@@ -351,12 +355,16 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
            mDurationMs = calculateDurationMs();
            mDisable = disable;
            mFloatingImeBottomInset = floatingImeBottomInset;
            mLoggingListener = loggingListener;
        }

        @Override
        public void onReady(WindowInsetsAnimationController controller, int types) {
            mController = controller;
            if (DEBUG) Log.d(TAG, "default animation onReady types: " + types);
            if (mLoggingListener != null) {
                mLoggingListener.onReady(controller, types);
            }

            if (mDisable) {
                onAnimationFinish();
@@ -410,6 +418,9 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
        public void onFinished(WindowInsetsAnimationController controller) {
            if (DEBUG) Log.d(TAG, "InternalAnimationControlListener onFinished types:"
                    + Type.toString(mRequestedTypes));
            if (mLoggingListener != null) {
                mLoggingListener.onFinished(controller);
            }
        }

        @Override
@@ -420,6 +431,9 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
            }
            if (DEBUG) Log.d(TAG, "InternalAnimationControlListener onCancelled types:"
                    + mRequestedTypes);
            if (mLoggingListener != null) {
                mLoggingListener.onCancelled(controller);
            }
        }

        protected Interpolator getInsetsInterpolator() {
@@ -1147,6 +1161,13 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
        updateRequestedVisibilities();
    }

    // TODO(b/242962223): Make this setter restrictive.
    @Override
    public void setSystemDrivenInsetsAnimationLoggingListener(
            @Nullable WindowInsetsAnimationControlListener listener) {
        mLoggingListener = listener;
    }

    /**
     * @return Pair of (types ready to animate, IME ready to animate).
     */
@@ -1460,7 +1481,8 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
        boolean hasAnimationCallbacks = mHost.hasAnimationCallbacks();
        final InternalAnimationControlListener listener = new InternalAnimationControlListener(
                show, hasAnimationCallbacks, types, mHost.getSystemBarsBehavior(),
                skipAnim || mAnimationsDisabled, mHost.dipToPx(FLOATING_IME_BOTTOM_INSET_DP));
                skipAnim || mAnimationsDisabled, mHost.dipToPx(FLOATING_IME_BOTTOM_INSET_DP),
                mLoggingListener);

        // We are about to playing the default animation (show/hide). Passing a null frame indicates
        // the controlled types should be animated regardless of the frame.
+15 −1
Original line number Diff line number Diff line
@@ -44,6 +44,7 @@ public class PendingInsetsController implements WindowInsetsController {
    private ArrayList<OnControllableInsetsChangedListener> mControllableInsetsChangedListeners
            = new ArrayList<>();
    private int mCaptionInsetsHeight = 0;
    private WindowInsetsAnimationControlListener mLoggingListener;

    @Override
    public void show(int types) {
@@ -176,6 +177,9 @@ public class PendingInsetsController implements WindowInsetsController {
            controller.addOnControllableInsetsChangedListener(
                    mControllableInsetsChangedListeners.get(i));
        }
        if (mLoggingListener != null) {
            controller.setSystemDrivenInsetsAnimationLoggingListener(mLoggingListener);
        }

        // Reset all state so it doesn't get applied twice just in case
        mRequests.clear();
@@ -184,7 +188,7 @@ public class PendingInsetsController implements WindowInsetsController {
        mAppearance = 0;
        mAppearanceMask = 0;
        mAnimationsDisabled = false;

        mLoggingListener = null;
        // After replaying, we forward everything directly to the replayed instance.
        mReplayedInsetsController = controller;
    }
@@ -197,6 +201,16 @@ public class PendingInsetsController implements WindowInsetsController {
        mReplayedInsetsController = null;
    }

    @Override
    public void setSystemDrivenInsetsAnimationLoggingListener(
            @Nullable WindowInsetsAnimationControlListener listener) {
        if (mReplayedInsetsController != null) {
            mReplayedInsetsController.setSystemDrivenInsetsAnimationLoggingListener(listener);
        } else {
            mLoggingListener = listener;
        }
    }

    @Override
    public void controlWindowInsetsAnimation(@InsetsType int types, long durationMillis,
            @Nullable Interpolator interpolator,
+15 −0
Original line number Diff line number Diff line
@@ -200,6 +200,21 @@ public interface WindowInsetsController {
            @Nullable CancellationSignal cancellationSignal,
            @NonNull WindowInsetsAnimationControlListener listener);

    /**
     * Lets the application add non-controllable listener object that can be called back
     * when animation is invoked by the system by host calling methods such as {@link #show} or
     * {@link #hide}.
     *
     * The listener is supposed to be used for logging only, using the control or
     * relying on the timing of the callback in any other way is not supported.
     *
     * @param listener The {@link WindowInsetsAnimationControlListener} that gets called when
     *                 the animation is driven by the system and not the host
     * @hide
     */
    void setSystemDrivenInsetsAnimationLoggingListener(
            @Nullable WindowInsetsAnimationControlListener listener);

    /**
     * Controls the appearance of system bars.
     * <p>
+15 −0
Original line number Diff line number Diff line
@@ -235,6 +235,21 @@ public class InsetsControllerTest {
        verify(controlListener, never()).onReady(any(), anyInt());
    }

    @Test
    public void testSystemDrivenInsetsAnimationLoggingListener_onReady() {
        prepareControls();
        // only the original thread that created view hierarchy can touch its views
        InstrumentationRegistry.getInstrumentation().runOnMainSync(() -> {
            WindowInsetsAnimationControlListener loggingListener =
                    mock(WindowInsetsAnimationControlListener.class);
            mController.setSystemDrivenInsetsAnimationLoggingListener(loggingListener);
            mController.getSourceConsumer(ITYPE_IME).onWindowFocusGained(true);
            // since there is no focused view, forcefully make IME visible.
            mController.show(Type.ime(), true /* fromIme */);
            verify(loggingListener).onReady(notNull(), anyInt());
        });
    }

    @Test
    public void testAnimationEndState() {
        InsetsSourceControl[] controls = prepareControls();
+19 −0
Original line number Diff line number Diff line
@@ -212,6 +212,25 @@ public class PendingInsetsControllerTest {
        verifyZeroInteractions(secondController);
    }

    @Test
    public void testSystemDrivenInsetsAnimationLoggingListener() {
        WindowInsetsAnimationControlListener listener =
                mock(WindowInsetsAnimationControlListener.class);
        mPendingInsetsController.setSystemDrivenInsetsAnimationLoggingListener(listener);
        mPendingInsetsController.replayAndAttach(mReplayedController);
        verify(mReplayedController).setSystemDrivenInsetsAnimationLoggingListener(eq(listener));
    }

    @Test
    public void testSystemDrivenInsetsAnimationLoggingListener_direct() {
        mPendingInsetsController.replayAndAttach(mReplayedController);
        WindowInsetsAnimationControlListener listener =
                mock(WindowInsetsAnimationControlListener.class);
        mPendingInsetsController.setSystemDrivenInsetsAnimationLoggingListener(listener);
        verify(mReplayedController).setSystemDrivenInsetsAnimationLoggingListener(
                eq(listener));
    }

    @Test
    public void testDetachReattach() {
        mPendingInsetsController.show(systemBars());
Loading