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

Commit 9d42c332 authored by Ming-Shin Lu's avatar Ming-Shin Lu
Browse files

Initialize ImsConfigurationTracker when IME#onCreate

To parse InputMethod_configChanges locally without waiting system
callback with initializeInternal, in case IME#mInputView may not
able to call resetStateForNewConfiguration in time before
IME#initializeInternal when it's required.

Fix: 260198823
Test: atest InputMethodServiceTest
Change-Id: I0268360f1b60ebc1f2676d3edab1910a9ce0f050
parent f9ca7a2f
Loading
Loading
Loading
Loading
+38 −1
Original line number Diff line number Diff line
@@ -70,11 +70,14 @@ import android.app.compat.CompatChanges;
import android.compat.annotation.ChangeId;
import android.compat.annotation.EnabledSince;
import android.compat.annotation.UnsupportedAppUsage;
import android.content.ComponentName;
import android.content.Context;
import android.content.pm.PackageManager;
import android.content.pm.ServiceInfo;
import android.content.res.Configuration;
import android.content.res.Resources;
import android.content.res.TypedArray;
import android.content.res.XmlResourceParser;
import android.database.ContentObserver;
import android.graphics.Rect;
import android.graphics.Region;
@@ -98,6 +101,7 @@ import android.text.method.MovementMethod;
import android.util.Log;
import android.util.PrintWriterPrinter;
import android.util.Printer;
import android.util.Xml;
import android.util.proto.ProtoOutputStream;
import android.view.BatchedInputEventReceiver.SimpleBatchedInputEventReceiver;
import android.view.Choreographer;
@@ -158,6 +162,8 @@ import com.android.internal.inputmethod.InputMethodPrivilegedOperationsRegistry;
import com.android.internal.inputmethod.SoftInputShowHideReason;
import com.android.internal.util.RingBuffer;

import org.xmlpull.v1.XmlPullParserException;

import java.io.FileDescriptor;
import java.io.PrintWriter;
import java.lang.annotation.Retention;
@@ -730,7 +736,6 @@ public class InputMethodService extends AbstractInputMethodService {
        @Override
        public final void initializeInternal(@NonNull IInputMethod.InitParams params) {
            Trace.traceBegin(TRACE_TAG_WINDOW_MANAGER, "IMS.initializeInternal");
            mConfigTracker.onInitialize(params.configChanges);
            mPrivOps.set(params.privilegedOperations);
            InputMethodPrivilegedOperationsRegistry.put(params.token, mPrivOps);
            mNavigationBarController.onNavButtonFlagsChanged(params.navigationBarFlags);
@@ -1601,6 +1606,8 @@ public class InputMethodService extends AbstractInputMethodService {
        mHideNavBarForKeyboard = getApplicationContext().getResources().getBoolean(
                com.android.internal.R.bool.config_hideNavBarForKeyboard);

        initConfigurationTracker();

        // TODO(b/111364446) Need to address context lifecycle issue if need to re-create
        // for update resources & configuration correctly when show soft input
        // in non-default display.
@@ -1656,6 +1663,36 @@ public class InputMethodService extends AbstractInputMethodService {
        Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER);
    }

    private void initConfigurationTracker() {
        final int flags = PackageManager.GET_META_DATA
                | PackageManager.MATCH_DISABLED_UNTIL_USED_COMPONENTS;
        final ComponentName imeComponent = new ComponentName(
                getPackageName(), getClass().getName());
        final String imeId = imeComponent.flattenToShortString();
        final ServiceInfo si;
        try {
            si = getPackageManager().getServiceInfo(imeComponent,
                    PackageManager.ComponentInfoFlags.of(flags));
        } catch (PackageManager.NameNotFoundException e) {
            Log.wtf(TAG, "Unable to find input method " + imeId, e);
            return;
        }
        try (XmlResourceParser parser = si.loadXmlMetaData(getPackageManager(),
                InputMethod.SERVICE_META_DATA);
             TypedArray sa = getResources().obtainAttributes(Xml.asAttributeSet(parser),
                     com.android.internal.R.styleable.InputMethod)) {
            if (parser == null) {
                throw new XmlPullParserException(
                        "No " + InputMethod.SERVICE_META_DATA + " meta-data");
            }
            final int handledConfigChanges = sa.getInt(
                    com.android.internal.R.styleable.InputMethod_configChanges, 0);
            mConfigTracker.onInitialize(handledConfigChanges);
        } catch (Exception e) {
            Log.wtf(TAG, "Unable to load input method " + imeId, e);
        }
    }

    /**
     * This is a hook that subclasses can use to perform initialization of
     * their interface.  It is called for you prior to any of your UI objects
+0 −1
Original line number Diff line number Diff line
@@ -40,7 +40,6 @@ oneway interface IInputMethod {
    parcelable InitParams {
        IBinder token;
        IInputMethodPrivilegedOperations privilegedOperations;
        int configChanges;
        int navigationBarFlags;
    }

+1 −2
Original line number Diff line number Diff line
@@ -110,11 +110,10 @@ final class IInputMethodInvoker {

    @AnyThread
    void initializeInternal(IBinder token, IInputMethodPrivilegedOperations privilegedOperations,
            int configChanges, @InputMethodNavButtonFlags int navigationBarFlags) {
            @InputMethodNavButtonFlags int navigationBarFlags) {
        final IInputMethod.InitParams params = new IInputMethod.InitParams();
        params.token = token;
        params.privilegedOperations = privilegedOperations;
        params.configChanges = configChanges;
        params.navigationBarFlags = navigationBarFlags;
        try {
            mTarget.initializeInternal(params);
+1 −1
Original line number Diff line number Diff line
@@ -279,7 +279,7 @@ final class InputMethodBindingController {
                    if (DEBUG) Slog.v(TAG, "Initiating attach with token: " + mCurToken);
                    final InputMethodInfo info = mMethodMap.get(mSelectedMethodId);
                    mSupportsStylusHw = info.supportsStylusHandwriting();
                    mService.initializeImeLocked(mCurMethod, mCurToken, info.getConfigChanges());
                    mService.initializeImeLocked(mCurMethod, mCurToken);
                    mService.scheduleNotifyImeUidToAudioService(mCurMethodUid);
                    mService.reRequestCurrentClientSessionLocked();
                    mService.performOnCreateInlineSuggestionsRequestLocked();
+2 −3
Original line number Diff line number Diff line
@@ -2692,14 +2692,13 @@ public final class InputMethodManagerService extends IInputMethodManager.Stub
    }

    @GuardedBy("ImfLock.class")
    void initializeImeLocked(@NonNull IInputMethodInvoker inputMethod, @NonNull IBinder token,
            @android.content.pm.ActivityInfo.Config int configChanges) {
    void initializeImeLocked(@NonNull IInputMethodInvoker inputMethod, @NonNull IBinder token) {
        if (DEBUG) {
            Slog.v(TAG, "Sending attach of token: " + token + " for display: "
                    + mCurTokenDisplayId);
        }
        inputMethod.initializeInternal(token, new InputMethodPrivilegedOperationsImpl(this, token),
                configChanges, getInputMethodNavButtonFlagsLocked());
                getInputMethodNavButtonFlagsLocked());
    }

    @AnyThread