From 0b05f9e49dc6e2a418479f432e8728346ebaaf54 Mon Sep 17 00:00:00 2001 From: lumark Date: Mon, 26 Nov 2018 15:09:06 +0800 Subject: Add IMMS#showInputMethodPickerFromSystem. Since the NavBar will be supported for multi-display, for single session IME, it will be possible that IME switcher icon will shown on external display. Add IMMS#showInputMethodPickerFromSystem for system modules (i.e. Settings or SystemUI) to pass displayId for creating right display context, so that IME switcher dialog can shown on the display correctly. Also Add a TODO item for ACTION_SHOW_INPUT_METHOD_PICKER notification that currently only support showing IME picker for default display, this should support per display after supporting status bar per display. Bug: 119933861 Fix: 120050928 Test: manual, verify IME switcher dialog can shown on external display when tapping IME switcher icon on external navbar. Test: atest InputMethodManagerTest#testShowInputMethodPicker Change-Id: Ic7d7c5a7ad8005a3fbd9d1c1b73e3c5a39a07001 --- core/java/android/app/ActivityThread.java | 9 +++++ core/java/android/app/ContextImpl.java | 16 +++++++-- .../view/inputmethod/InputMethodManager.java | 8 +++-- .../android/internal/view/IInputMethodManager.aidl | 2 ++ .../com/android/keyguard/KeyguardPasswordView.java | 3 +- .../statusbar/phone/NavigationBarView.java | 4 +-- .../inputmethod/InputMethodManagerService.java | 42 ++++++++++++++-------- .../MultiClientInputMethodManagerService.java | 7 ++++ 8 files changed, 68 insertions(+), 23 deletions(-) diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java index 41166dd40e56..c1c9fd6a1e79 100644 --- a/core/java/android/app/ActivityThread.java +++ b/core/java/android/app/ActivityThread.java @@ -2282,6 +2282,15 @@ public final class ActivityThread extends ClientTransactionHandler { } } + /** + * Create the context instance base on system resources & display information which used for UI. + * @param displayId The ID of the display where the UI is shown. + * @see ContextImpl#createSystemUiContext(ContextImpl, int) + */ + public ContextImpl createSystemUiContext(int displayId) { + return ContextImpl.createSystemUiContext(getSystemUiContext(), displayId); + } + public void installSystemApplicationInfo(ApplicationInfo info, ClassLoader classLoader) { synchronized (this) { getSystemContext().installSystemApplicationInfo(info, classLoader); diff --git a/core/java/android/app/ContextImpl.java b/core/java/android/app/ContextImpl.java index 6f0b6c8687db..a29a8aeff00b 100644 --- a/core/java/android/app/ContextImpl.java +++ b/core/java/android/app/ContextImpl.java @@ -2404,16 +2404,28 @@ class ContextImpl extends Context { /** * System Context to be used for UI. This Context has resources that can be themed. * Make sure that the created system UI context shares the same LoadedApk as the system context. + * @param systemContext The system context which created by + * {@link #createSystemContext(ActivityThread)}. + * @param displayId The ID of the display where the UI is shown. */ - static ContextImpl createSystemUiContext(ContextImpl systemContext) { + static ContextImpl createSystemUiContext(ContextImpl systemContext, int displayId) { final LoadedApk packageInfo = systemContext.mPackageInfo; ContextImpl context = new ContextImpl(null, systemContext.mMainThread, packageInfo, null, null, null, 0, null); - context.setResources(createResources(null, packageInfo, null, Display.DEFAULT_DISPLAY, null, + context.setResources(createResources(null, packageInfo, null, displayId, null, packageInfo.getCompatibilityInfo())); + context.updateDisplay(displayId); return context; } + /** + * The overloaded method of {@link #createSystemUiContext(ContextImpl, int)}. + * Uses {@Code Display.DEFAULT_DISPLAY} as the target display. + */ + static ContextImpl createSystemUiContext(ContextImpl systemContext) { + return createSystemUiContext(systemContext, Display.DEFAULT_DISPLAY); + } + @UnsupportedAppUsage static ContextImpl createAppContext(ActivityThread mainThread, LoadedApk packageInfo) { if (packageInfo == null) throw new IllegalArgumentException("packageInfo"); diff --git a/core/java/android/view/inputmethod/InputMethodManager.java b/core/java/android/view/inputmethod/InputMethodManager.java index 13409554da28..be0ff03eb108 100644 --- a/core/java/android/view/inputmethod/InputMethodManager.java +++ b/core/java/android/view/inputmethod/InputMethodManager.java @@ -2354,17 +2354,19 @@ public final class InputMethodManager { } /** - * Shows the input method chooser dialog. + * Shows the input method chooser dialog from system. * * @param showAuxiliarySubtypes Set true to show auxiliary input methods. + * @param displayId The ID of the display where the chooser dialog should be shown. * @hide */ - public void showInputMethodPicker(boolean showAuxiliarySubtypes) { + @RequiresPermission(WRITE_SECURE_SETTINGS) + public void showInputMethodPickerFromSystem(boolean showAuxiliarySubtypes, int displayId) { final int mode = showAuxiliarySubtypes ? SHOW_IM_PICKER_MODE_INCLUDE_AUXILIARY_SUBTYPES : SHOW_IM_PICKER_MODE_EXCLUDE_AUXILIARY_SUBTYPES; try { - mService.showInputMethodPickerFromClient(mClient, mode); + mService.showInputMethodPickerFromSystem(mClient, mode, displayId); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } diff --git a/core/java/com/android/internal/view/IInputMethodManager.aidl b/core/java/com/android/internal/view/IInputMethodManager.aidl index 1e71bd171eea..a82027c44cb4 100644 --- a/core/java/com/android/internal/view/IInputMethodManager.aidl +++ b/core/java/com/android/internal/view/IInputMethodManager.aidl @@ -64,6 +64,8 @@ interface IInputMethodManager { void showInputMethodPickerFromClient(in IInputMethodClient client, int auxiliarySubtypeMode); + void showInputMethodPickerFromSystem(in IInputMethodClient client, int auxiliarySubtypeMode, + int displayId); void showInputMethodAndSubtypeEnablerFromClient(in IInputMethodClient client, String topId); boolean isInputMethodPickerShownForTest(); // TODO(Bug 114488811): this can be removed once we deprecate special null token rule. diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardPasswordView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardPasswordView.java index 6b24ad56d01c..41afa9a21128 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardPasswordView.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardPasswordView.java @@ -193,7 +193,8 @@ public class KeyguardPasswordView extends KeyguardAbsKeyInputView public void onClick(View v) { mCallback.userActivity(); // Leave the screen on a bit longer // Do not show auxiliary subtypes in password lock screen. - mImm.showInputMethodPicker(false /* showAuxiliarySubtypes */); + mImm.showInputMethodPickerFromSystem(false /* showAuxiliarySubtypes */, + getContext().getDisplayId()); } }); diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java index cd6e1d794428..edc1b6d7e874 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java @@ -212,8 +212,8 @@ public class NavigationBarView extends FrameLayout implements PluginListener