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

Commit e75d6ad1 authored by Johannes Gallmann's avatar Johannes Gallmann
Browse files

Remove notifyImeHidden call in ImeBackAnimationController

Calling notifyImeHidden had two purposes:
 1. Triggering the regular IME hide animation. This can be replaced with
    InsetsController#hide where applicable.
 2. Triggering the back callback unregistration by the
    InputMethodService. This is not required anymore since we are using
    ImeOnBackInvokedDispatcher#preliminaryClear to do so instead.

Bug: 417738140
Test: ImeBackAnimationControllerTest
Test: Manual, i.e. verified IME back navigation in multiple setups:
      predictive back enabled vs disabled, splitscreen, folded and
      unfolded screen, quick double back swipes, quick input field
      refocus
Flag: EXEMPT bugfix
Change-Id: I01278c31b5a98e66d0eee7aea6927b79828e06f4
parent 2e27b9f5
Loading
Loading
Loading
Loading
+5 −17
Original line number Diff line number Diff line
@@ -21,6 +21,7 @@ import static android.view.InsetsController.ANIMATION_DURATION_UNSYNC_IME_MS;
import static android.view.InsetsController.ANIMATION_TYPE_USER;
import static android.view.InsetsController.FAST_OUT_LINEAR_IN_INTERPOLATOR;
import static android.view.InsetsController.SYNC_IME_INTERPOLATOR;
import static android.view.WindowInsets.Type.IME;
import static android.view.WindowInsets.Type.ime;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE;
@@ -54,7 +55,6 @@ import java.io.PrintWriter;
public class ImeBackAnimationController implements OnBackAnimationCallback {

    private static final String TAG = "ImeBackAnimationController";
    private static final int POST_COMMIT_DURATION_MS = 200;
    private static final int POST_COMMIT_CANCEL_DURATION_MS = 50;
    private static final float PEEK_FRACTION = 0.1f;
    private static final Interpolator BACK_GESTURE = new BackGestureInterpolator();
@@ -144,7 +144,10 @@ public class ImeBackAnimationController implements OnBackAnimationCallback {
            // play regular hide animation if predictive back-animation is not allowed or if insets
            // control has been cancelled by the system. This can happen in multi-window mode for
            // example (i.e. split-screen or activity-embedding)
            notifyHideIme();
            ImeTracker.Token statsToken = ImeTracker.forLogging().onStart(ImeTracker.TYPE_HIDE,
                    ImeTracker.ORIGIN_CLIENT,
                    SoftInputShowHideReason.HIDE_SOFT_INPUT_REQUEST_HIDE_WITH_CONTROL, true);
            mInsetsController.hide(IME, /*fromIme*/ false, statsToken);
        } else {
            startPostCommitAnim(/*hideIme*/ true);
        }
@@ -225,27 +228,12 @@ public class ImeBackAnimationController implements OnBackAnimationCallback {
        mPostCommitAnimator.start();
        if (triggerBack) {
            mInsetsController.setPredictiveBackImeHideAnimInProgress(true);
            notifyHideIme();
            // requesting IME as invisible during post-commit
            mInsetsController.setRequestedVisibleTypes(0, ime());
            mInsetsController.onAnimationStateChanged(ime(), /*running*/ true);
        }
    }

    private void notifyHideIme() {
        ImeTracker.Token statsToken = ImeTracker.forLogging().onStart(ImeTracker.TYPE_HIDE,
                ImeTracker.ORIGIN_CLIENT,
                SoftInputShowHideReason.HIDE_SOFT_INPUT_REQUEST_HIDE_WITH_CONTROL, true);
        // This notifies the IME that it is being hidden. In response, the IME will unregister the
        // animation callback, such that new back gestures happening during the post-commit phase of
        // the hide animation can already dispatch to a new callback.
        // Note that the IME will call hide() in InsetsController. InsetsController will not animate
        // that hide request if it sees that ImeBackAnimationController is already animating
        // the IME away
        mInsetsController.getHost().getInputMethodManager()
                .notifyImeHidden(mInsetsController.getHost().getWindowToken(), statsToken);
    }

    private void reset() {
        mWindowInsetsAnimationController = null;
        resetPostCommitAnimator();
+1 −1
Original line number Diff line number Diff line
@@ -1250,7 +1250,7 @@ public class InsetsController implements WindowInsetsController, InsetsAnimation
        hide(types, false /* fromIme */, null /* statsToken */);
    }

    @VisibleForTesting
    @VisibleForTesting(visibility = PACKAGE)
    public void hide(@InsetsType int types, boolean fromIme,
            @Nullable ImeTracker.Token statsToken) {
        if ((types & ime()) != 0) {
+9 −9
Original line number Diff line number Diff line
@@ -159,9 +159,9 @@ public class ImeBackAnimationControllerTest {
        mBackAnimationController.onBackProgressed(new BackEvent(100f, 0f, 0.5f, EDGE_LEFT));
        // commit back gesture
        mBackAnimationController.onBackInvoked();
        // verify that InputMethodManager#notifyImeHidden is called (which is the case whenever
        // getInputMethodManager is called from ImeBackAnimationController)
        verify(mViewRootInsetsControllerHost, times(2)).getInputMethodManager();
        // verify that ImeOnBackInvokedDispatcher#preliminaryClear is called (which is the case
        // whenever getInputMethodManager is called from ImeBackAnimationController)
        verify(mViewRootInsetsControllerHost, times(1)).getInputMethodManager();
        // verify that ImeBackAnimationController does not take control over IME insets
        verify(mInsetsController, never()).controlWindowInsetsAnimation(anyInt(), any(), any(),
                anyBoolean(), anyLong(), any(), anyInt(), anyBoolean());
@@ -178,9 +178,9 @@ public class ImeBackAnimationControllerTest {
        mBackAnimationController.onBackProgressed(new BackEvent(100f, 0f, 0.5f, EDGE_LEFT));
        // commit back gesture
        mBackAnimationController.onBackInvoked();
        // verify that InputMethodManager#notifyImeHidden is called (which is the case whenever
        // getInputMethodManager is called from ImeBackAnimationController)
        verify(mViewRootInsetsControllerHost, times(2)).getInputMethodManager();
        // verify that ImeOnBackInvokedDispatcher#preliminaryClear is called (which is the case
        // whenever getInputMethodManager is called from ImeBackAnimationController)
        verify(mViewRootInsetsControllerHost, times(1)).getInputMethodManager();
        // verify that ImeBackAnimationController does not take control over IME insets
        verify(mInsetsController, never()).controlWindowInsetsAnimation(anyInt(), any(), any(),
                anyBoolean(), anyLong(), any(), anyInt(), anyBoolean());
@@ -298,9 +298,9 @@ public class ImeBackAnimationControllerTest {

            // commit back gesture
            mBackAnimationController.onBackInvoked();
            // verify that InputMethodManager#notifyImeHidden is called (which is the case whenever
            // getInputMethodManager is called from ImeBackAnimationController)
            verify(mViewRootInsetsControllerHost, times(2)).getInputMethodManager();
            // verify that ImeOnBackInvokedDispatcher#preliminaryClear is called (which is the case
            // whenever getInputMethodManager is called from ImeBackAnimationController)
            verify(mViewRootInsetsControllerHost, times(1)).getInputMethodManager();
        });
    }