1 /*
2  * Copyright (C) 2017 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.inputmethodservice.cts.ime;
18 
19 import android.content.BroadcastReceiver;
20 import android.content.Context;
21 import android.content.Intent;
22 import android.content.IntentFilter;
23 import android.inputmethodservice.InputMethodService;
24 import android.inputmethodservice.cts.common.ImeCommandConstants;
25 import android.inputmethodservice.cts.ime.ImeCommandReceiver.ImeCommandCallbacks;
26 import android.util.Log;
27 
28 /**
29  * {@link ImeCommandConstants#ACTION_IME_COMMAND} intent receiver.
30  */
31 final class ImeCommandReceiver<T extends InputMethodService & ImeCommandCallbacks>
32         extends BroadcastReceiver {
33 
34     private static final boolean DEBUG = false;
35 
36     interface ImeCommandCallbacks {
37         /**
38          * Callback method for {@link ImeCommandConstants#COMMAND_COMMIT_TEXT} intent.
39          *
40          * @param text text to be committed via {@link android.view.inputmethod.InputConnection}.
41          * @param newCursorPosition new cursor position after commit.
42          */
commandCommitText(CharSequence text, int newCursorPosition)43         void commandCommitText(CharSequence text, int newCursorPosition);
44 
45         /**
46          * Callback method for {@link ImeCommandConstants#COMMAND_SWITCH_INPUT_METHOD} intent.
47          *
48          * @param imeId IME id to switch.
49          */
commandSwitchInputMethod(String imeId)50         void commandSwitchInputMethod(String imeId);
51 
52         /**
53          * Callback method for {@link ImeCommandConstants#COMMAND_REQUEST_HIDE_SELF} intent.
54          */
commandRequestHideSelf(int flags)55         void commandRequestHideSelf(int flags);
56     }
57 
58     private T mIme;
59 
register(T ime)60     void register(T ime) {
61         mIme = ime;
62         ime.registerReceiver(this, new IntentFilter(ImeCommandConstants.ACTION_IME_COMMAND));
63     }
64 
65     @Override
onReceive(Context context, Intent intent)66     public void onReceive(Context context, Intent intent) {
67         final String command = intent.getStringExtra(ImeCommandConstants.EXTRA_COMMAND);
68         if (DEBUG) {
69             Log.d(mIme.getClass().getSimpleName(), "onReceive: command=" + command);
70         }
71 
72         switch (command) {
73             case ImeCommandConstants.COMMAND_COMMIT_TEXT: {
74                 final CharSequence text = getCharSequence1(intent);
75                 final int newCursorPosition = getInt1(intent);
76                 mIme.commandCommitText(text, newCursorPosition);
77                 return;
78             }
79             case ImeCommandConstants.COMMAND_SWITCH_INPUT_METHOD: {
80                 final String imeId = getString1(intent);
81                 mIme.commandSwitchInputMethod(imeId);
82                 return;
83             }
84             case ImeCommandConstants.COMMAND_REQUEST_HIDE_SELF: {
85                 final int flags = getInt1(intent);
86                 mIme.commandRequestHideSelf(flags);
87                 return;
88             }
89             case ImeCommandConstants.COMMAND_SWITCH_INPUT_METHOD_WITH_SUBTYPE: {
90                 final String imeId = getString1(intent);
91                 // we don't support mock imes with subtypes yet.
92                 mIme.switchInputMethod(imeId, null /* subtype*/);
93                 return;
94             }
95             case ImeCommandConstants.COMMAND_SWITCH_TO_NEXT_INPUT: {
96                 mIme.switchToNextInputMethod(false);
97                 return;
98             }
99             case ImeCommandConstants.COMMAND_SWITCH_TO_PREVIOUS_INPUT: {
100                 mIme.switchToPreviousInputMethod();
101                 return;
102             }
103             default: {
104                 throw new UnsupportedOperationException("Unknown IME command: " + command);
105             }
106         }
107     }
108 
getCharSequence1(Intent intent)109     private static CharSequence getCharSequence1(Intent intent) {
110         return intent.getCharSequenceExtra(ImeCommandConstants.EXTRA_ARG_CHARSEQUENCE1);
111     }
112 
getString1(Intent intent)113     private static String getString1(Intent intent) {
114         return intent.getStringExtra(ImeCommandConstants.EXTRA_ARG_STRING1);
115     }
116 
getInt1(Intent intent)117     private static int getInt1(Intent intent) {
118         if (intent.hasExtra(ImeCommandConstants.EXTRA_ARG_INT1)) {
119             return intent.getIntExtra(ImeCommandConstants.EXTRA_ARG_INT1, 0);
120         }
121         throw new IllegalArgumentException(
122                 "Needs " + ImeCommandConstants.EXTRA_ARG_INT1 + " in " + intent);
123     }
124 }
125