• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2014 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 com.android.tv.settings.system;
18 
19 import com.android.tv.settings.ActionBehavior;
20 import com.android.tv.settings.ActionKey;
21 import com.android.tv.settings.BaseSettingsActivity;
22 import com.android.tv.settings.R;
23 import com.android.tv.settings.dialog.old.Action;
24 import com.android.tv.settings.dialog.old.ActionAdapter;
25 
26 import android.app.ActivityManagerNative;
27 import android.content.Intent;
28 import android.content.pm.PackageManager;
29 import android.os.Bundle;
30 import android.os.RemoteException;
31 import android.os.UserHandle;
32 import android.provider.Settings;
33 import android.text.TextUtils;
34 import android.util.Log;
35 import android.view.inputmethod.InputMethodInfo;
36 import android.view.inputmethod.InputMethodManager;
37 
38 import java.util.ArrayList;
39 import java.util.Iterator;
40 import java.util.List;
41 
42 public class KeyboardActivity extends BaseSettingsActivity implements ActionAdapter.Listener {
43 
44     private static final String TAG = "KeyboardActivity";
45     private static final boolean DEBUG = false;
46 
47     private static final String INPUT_METHOD_SEPARATOR = ":";
48     private InputMethodManager mInputMan;
49 
50     @Override
onCreate(Bundle savedInstanceState)51     public void onCreate(Bundle savedInstanceState) {
52         mInputMan = (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE);
53         // enable all available input methods
54         enableAllInputMethods();
55 
56         super.onCreate(savedInstanceState);
57     }
58 
59     @Override
onActionClicked(Action action)60     public void onActionClicked(Action action) {
61         /*
62          * For list preferences
63          */
64         String key = action.getKey();
65         switch ((ActionType) mState) {
66             case KEYBOARD_OVERVIEW_CURRENT_KEYBOARD:
67                 setInputMethod(key);
68                 goBack();
69                 return;
70             default:
71                 break;
72         }
73 
74         /*
75          * For regular states
76          */
77         ActionKey<ActionType, ActionBehavior> actionKey = new ActionKey<ActionType, ActionBehavior>(
78                 ActionType.class, ActionBehavior.class, action.getKey());
79         final ActionType type = actionKey.getType();
80         switch (type) {
81             case KEYBOARD_OVERVIEW_CONFIGURE:
82                 InputMethodInfo currentInputMethodInfo = getCurrentInputMethodInfo();
83                 if (currentInputMethodInfo != null &&
84                         currentInputMethodInfo.getSettingsActivity() != null) {
85                     startActivity(getInputMethodSettingsIntent(currentInputMethodInfo));
86                 }
87                 return;
88             default:
89         }
90 
91         final ActionBehavior behavior = actionKey.getBehavior();
92         if (behavior == null) {
93             return;
94         }
95         switch (behavior) {
96             case INIT:
97                 setState(type, true);
98                 break;
99             case ON:
100                 setProperty(true);
101                 break;
102             case OFF:
103                 setProperty(false);
104                 break;
105             default:
106         }
107     }
108 
109     @Override
getInitialState()110     protected Object getInitialState() {
111         return ActionType.KEYBOARD_OVERVIEW;
112     }
113 
114     @Override
refreshActionList()115     protected void refreshActionList() {
116         mActions.clear();
117         InputMethodInfo currentInputMethodInfo = getCurrentInputMethodInfo();
118         switch ((ActionType) mState) {
119             case KEYBOARD_OVERVIEW:
120                 String name = getDefaultInputMethodName();
121                 mActions.add(ActionType.KEYBOARD_OVERVIEW_CURRENT_KEYBOARD
122                         .toAction(mResources, TextUtils.isEmpty(name) ? "" : name));
123 
124                 if (currentInputMethodInfo != null
125                         && currentInputMethodInfo.getSettingsActivity() != null) {
126                     mActions.add(ActionType.KEYBOARD_OVERVIEW_CONFIGURE.toAction(mResources));
127                 }
128                 break;
129             case KEYBOARD_OVERVIEW_CURRENT_KEYBOARD:
130                 mActions = Action.createActionsFromArrays(getInputMethodIds(),
131                         getInputMethodNames());
132                 for (Action action : mActions) {
133                     action.setChecked(currentInputMethodInfo != null &&
134                             action.getKey().equals(currentInputMethodInfo.getId()));
135                 }
136                 break;
137             default:
138                 break;
139         }
140     }
141 
142     @Override
updateView()143     protected void updateView() {
144         refreshActionList();
145         switch ((ActionType) mState) {
146             case KEYBOARD_OVERVIEW:
147                 setView(R.string.system_keyboard, R.string.settings_app_name, 0,
148                         R.drawable.ic_settings_keyboard);
149                 break;
150             case KEYBOARD_OVERVIEW_CURRENT_KEYBOARD:
151                 setView(R.string.title_current_keyboard, R.string.system_keyboard, 0,
152                         R.drawable.ic_settings_keyboard);
153                 break;
154             default:
155                 break;
156         }
157     }
158 
159     @Override
setProperty(boolean enable)160     protected void setProperty(boolean enable) {
161     }
162 
getDefaultInputMethodId()163     private String getDefaultInputMethodId() {
164         return Settings.Secure.getString(getContentResolver(),
165                 Settings.Secure.DEFAULT_INPUT_METHOD);
166     }
167 
getDefaultInputMethodName()168     private String getDefaultInputMethodName() {
169         String defaultInputMethodInfo = getDefaultInputMethodId();
170 
171         List<InputMethodInfo> enabledInputMethodInfos = getEnabledSystemInputMethodList();
172         for (InputMethodInfo info : enabledInputMethodInfos) {
173             if (defaultInputMethodInfo.equals(info.getId())) {
174                 return info.loadLabel(getPackageManager()).toString();
175             }
176         }
177         return null;
178     }
179 
getCurrentInputMethodInfo()180     private InputMethodInfo getCurrentInputMethodInfo() {
181         String defaultInputMethodInfo = getDefaultInputMethodId();
182 
183         List<InputMethodInfo> enabledInputMethodInfos = getEnabledSystemInputMethodList();
184         for (InputMethodInfo info : enabledInputMethodInfos) {
185             if (defaultInputMethodInfo.equals(info.getId())) {
186                 return info;
187             }
188         }
189         return null;
190     }
191 
getInputMethodNames()192     private String[] getInputMethodNames() {
193         List<InputMethodInfo> enabledInputMethodInfos = getEnabledSystemInputMethodList();
194         int totalInputMethods = enabledInputMethodInfos.size();
195         String[] inputMethodNames = new String[totalInputMethods];
196         for (int i = 0; i < totalInputMethods; i++) {
197             inputMethodNames[i] = enabledInputMethodInfos.get(i)
198                     .loadLabel(getPackageManager()).toString();
199         }
200         return inputMethodNames;
201     }
202 
getInputMethodIds()203     private String[] getInputMethodIds() {
204         List<InputMethodInfo> enabledInputMethodInfos = getEnabledSystemInputMethodList();
205         int totalInputMethods = enabledInputMethodInfos.size();
206         String[] inputMethodIds = new String[totalInputMethods];
207         for (int i = 0; i < totalInputMethods; i++) {
208             inputMethodIds[i] = enabledInputMethodInfos.get(i).getId();
209         }
210         return inputMethodIds;
211     }
212 
getEnabledSystemInputMethodList()213     private List<InputMethodInfo> getEnabledSystemInputMethodList() {
214         List<InputMethodInfo> enabledInputMethodInfos =
215                 new ArrayList<>(mInputMan.getEnabledInputMethodList());
216         // Filter auxiliary keyboards out
217         for (Iterator<InputMethodInfo> it = enabledInputMethodInfos.iterator(); it.hasNext();) {
218             if (it.next().isAuxiliaryIme()) {
219                 it.remove();
220             }
221         }
222         return enabledInputMethodInfos;
223     }
224 
setInputMethod(String imid)225     private void setInputMethod(String imid) {
226         if (imid == null) {
227             throw new IllegalArgumentException("Unknown id: " + imid);
228         }
229 
230         int userId;
231         try {
232             userId = ActivityManagerNative.getDefault().getCurrentUser().id;
233             Settings.Secure.putStringForUser(getContentResolver(),
234                     Settings.Secure.DEFAULT_INPUT_METHOD, imid, userId);
235 
236             if (ActivityManagerNative.isSystemReady()) {
237                 Intent intent = new Intent(Intent.ACTION_INPUT_METHOD_CHANGED);
238                 intent.addFlags(Intent.FLAG_RECEIVER_REPLACE_PENDING);
239                 intent.putExtra("input_method_id", imid);
240                 sendBroadcastAsUser(intent, UserHandle.CURRENT);
241             }
242         } catch (RemoteException e) {
243             Log.d(TAG, "set default input method remote exception");
244         }
245     }
246 
enableAllInputMethods()247     private void enableAllInputMethods() {
248         List<InputMethodInfo> allInputMethodInfos =
249                 new ArrayList<InputMethodInfo>(mInputMan.getInputMethodList());
250         boolean needAppendSeparator = false;
251         StringBuilder builder = new StringBuilder();
252         for (InputMethodInfo imi : allInputMethodInfos) {
253             if (needAppendSeparator) {
254                 builder.append(INPUT_METHOD_SEPARATOR);
255             } else {
256                 needAppendSeparator = true;
257             }
258             builder.append(imi.getId());
259         }
260         Settings.Secure.putString(getContentResolver(), Settings.Secure.ENABLED_INPUT_METHODS,
261                 builder.toString());
262     }
263 
getInputMethodSettingsIntent(InputMethodInfo imi)264     private Intent getInputMethodSettingsIntent(InputMethodInfo imi) {
265         final PackageManager pm = getPackageManager();
266         final CharSequence label = imi.loadLabel(pm);// IME settings
267         final Intent intent;
268         final String settingsActivity = imi.getSettingsActivity();
269         if (!TextUtils.isEmpty(settingsActivity)) {
270             intent = new Intent(Intent.ACTION_MAIN);
271             intent.setClassName(imi.getPackageName(), settingsActivity);
272         } else {
273             intent = null;
274         }
275         return intent;
276     }
277 }
278