From bb40322347812614d44131945edda3defe6ddd1e Mon Sep 17 00:00:00 2001 From: Ming-Shin Lu Date: Fri, 12 Aug 2022 21:03:24 +0800 Subject: [PATCH] Fix toggleSoftInput can't hide IME when the app in multi-window mode CL[1] changed toggleSoftInput behavior with checking the last IME requested visibility by using ImeInsetsSourceConsumer#mRequestedVisible to toggle IME. However, ImeInsetsSourceConsumer#mRequestedVisible will be updated only when: 1) The IME insets is controllable for the app. 2) The caller uses WindowsInsetsController#{show, hide} Since by design when the app is in multi-window mode, SystemUI will take over the insets control for synchronizing task resizing / IME animation concern, so it ends up making the app unable to receive IME insets control then affects toggling IME visiblity. Even though toggleSoftInput has been deprecated since Android S, we still requires to support its functionality for old apps run in some platforms by default in multi-window mode (e.g. ARC++ in freeform windowing mode). To fix the issue, replace the check logic with getRootWindowInests().isVisible(ime()) to check the last IME visiblity from the root window the served view. [1]: I390dc029e7bcc30c200926a9bfbbbd0268a1f714 Bug: 240886131 Test: atest KeyboardVisibilityControlTest#testToggleSoftInput in ARC++ Change-Id: Iaf7ccc17a7c02711000983db0d65ad095fe9f8fa --- core/java/android/view/inputmethod/InputMethodManager.java | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/core/java/android/view/inputmethod/InputMethodManager.java b/core/java/android/view/inputmethod/InputMethodManager.java index a0a3b4f9c5202..a5326c96bfc06 100644 --- a/core/java/android/view/inputmethod/InputMethodManager.java +++ b/core/java/android/view/inputmethod/InputMethodManager.java @@ -89,6 +89,7 @@ import android.view.InputEventSender; import android.view.KeyEvent; import android.view.View; import android.view.ViewRootImpl; +import android.view.WindowInsets; import android.view.WindowManager.LayoutParams.SoftInputModeFlags; import android.view.autofill.AutofillManager; import android.window.ImeOnBackInvokedDispatcher; @@ -2122,8 +2123,9 @@ public final class InputMethodManager { null /* icProto */); synchronized (mH) { final View view = getServedViewLocked(); - if (mImeInsetsConsumer != null && view != null) { - if (mImeInsetsConsumer.isRequestedVisible()) { + if (view != null) { + final WindowInsets rootInsets = view.getRootWindowInsets(); + if (rootInsets != null && rootInsets.isVisible(WindowInsets.Type.ime())) { hideSoftInputFromWindow(view.getWindowToken(), hideFlags, null, SoftInputShowHideReason.HIDE_TOGGLE_SOFT_INPUT); } else {