Loading services/core/java/com/android/server/wm/DisplayContent.java +10 −0 Original line number Diff line number Diff line Loading @@ -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) { Loading services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java +26 −0 Original line number Diff line number Diff line Loading @@ -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; Loading Loading @@ -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, Loading Loading
services/core/java/com/android/server/wm/DisplayContent.java +10 −0 Original line number Diff line number Diff line Loading @@ -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) { Loading
services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java +26 −0 Original line number Diff line number Diff line Loading @@ -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; Loading Loading @@ -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, Loading