diff options
| -rw-r--r-- | services/core/java/com/android/server/wm/DisplayContent.java | 10 | ||||
| -rw-r--r-- | services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java | 26 |
2 files changed, 36 insertions, 0 deletions
diff --git a/services/core/java/com/android/server/wm/DisplayContent.java b/services/core/java/com/android/server/wm/DisplayContent.java index 735fae3391a2..d6bf46119cb1 100644 --- a/services/core/java/com/android/server/wm/DisplayContent.java +++ b/services/core/java/com/android/server/wm/DisplayContent.java @@ -724,6 +724,16 @@ class DisplayContent extends RootDisplayArea implements WindowManagerPolicy.Disp return false; } + // When switching the app task, we keep the IME window visibility for better + // transitioning experiences. + // However, in case IME created a child window without dismissing during the task + // switching to keep the window focus because IME window has higher window hierarchy, + // we don't give it focus if the next IME layering target doesn't request IME visible. + if (w.mIsImWindow && w.isChildWindow() && (mImeLayeringTarget == null + || !mImeLayeringTarget.getRequestedVisibility(ITYPE_IME))) { + return false; + } + final ActivityRecord activity = w.mActivityRecord; if (focusedApp == null) { diff --git a/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java b/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java index 6d4454bd964a..9cd604cb4120 100644 --- a/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java +++ b/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java @@ -31,6 +31,7 @@ import static android.view.Display.DEFAULT_DISPLAY; import static android.view.Display.FLAG_PRIVATE; import static android.view.DisplayCutout.BOUNDS_POSITION_TOP; import static android.view.DisplayCutout.fromBoundingRect; +import static android.view.InsetsState.ITYPE_IME; import static android.view.InsetsState.ITYPE_NAVIGATION_BAR; import static android.view.InsetsState.ITYPE_STATUS_BAR; import static android.view.Surface.ROTATION_0; @@ -2139,6 +2140,31 @@ public class DisplayContentTests extends WindowTestsBase { ACTIVITY_TYPE_STANDARD)); } + @UseTestDisplay(addWindows = W_INPUT_METHOD) + @Test + public void testImeChildWindowFocusWhenImeLayeringTargetChanges() { + final WindowState imeChildWindow = + createWindow(mImeWindow, TYPE_APPLICATION_ATTACHED_DIALOG, "imeChildWindow"); + makeWindowVisibleAndDrawn(imeChildWindow, mImeWindow); + assertTrue(imeChildWindow.canReceiveKeys()); + mDisplayContent.setInputMethodWindowLocked(mImeWindow); + + // Verify imeChildWindow can be focused window if the next IME target requests IME visible. + final WindowState imeAppTarget = + createWindow(null, TYPE_BASE_APPLICATION, mDisplayContent, "imeAppTarget"); + mDisplayContent.setImeLayeringTarget(imeAppTarget); + spyOn(imeAppTarget); + doReturn(true).when(imeAppTarget).getRequestedVisibility(ITYPE_IME); + assertEquals(imeChildWindow, mDisplayContent.findFocusedWindow()); + + // Verify imeChildWindow doesn't be focused window if the next IME target does not + // request IME visible. + final WindowState nextImeAppTarget = + createWindow(null, TYPE_BASE_APPLICATION, mDisplayContent, "nextImeAppTarget"); + mDisplayContent.setImeLayeringTarget(nextImeAppTarget); + assertNotEquals(imeChildWindow, mDisplayContent.findFocusedWindow()); + } + private void removeRootTaskTests(Runnable runnable) { final TaskDisplayArea taskDisplayArea = mRootWindowContainer.getDefaultTaskDisplayArea(); final Task rootTask1 = taskDisplayArea.createRootTask(WINDOWING_MODE_FULLSCREEN, |