aboutsummaryrefslogtreecommitdiffstats
path: root/java/src/com/android/inputmethod/latin
diff options
context:
space:
mode:
Diffstat (limited to 'java/src/com/android/inputmethod/latin')
-rw-r--r--java/src/com/android/inputmethod/latin/BinaryDictionary.java53
-rw-r--r--java/src/com/android/inputmethod/latin/CandidateView.java14
-rw-r--r--java/src/com/android/inputmethod/latin/DebugSettings.java10
-rw-r--r--java/src/com/android/inputmethod/latin/LatinIME.java36
-rw-r--r--java/src/com/android/inputmethod/latin/Settings.java4
-rw-r--r--java/src/com/android/inputmethod/latin/SubtypeSwitcher.java17
-rw-r--r--java/src/com/android/inputmethod/latin/Suggest.java53
-rw-r--r--java/src/com/android/inputmethod/latin/UserDictionary.java2
-rw-r--r--java/src/com/android/inputmethod/latin/Utils.java13
9 files changed, 132 insertions, 70 deletions
diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionary.java b/java/src/com/android/inputmethod/latin/BinaryDictionary.java
index 813f7d32f..a7e95a080 100644
--- a/java/src/com/android/inputmethod/latin/BinaryDictionary.java
+++ b/java/src/com/android/inputmethod/latin/BinaryDictionary.java
@@ -20,6 +20,7 @@ import android.content.Context;
import android.content.res.AssetFileDescriptor;
import android.util.Log;
+import java.io.File;
import java.util.Arrays;
/**
@@ -72,9 +73,40 @@ public class BinaryDictionary extends Dictionary {
public static BinaryDictionary initDictionary(Context context, int resId, int dicTypeId) {
synchronized (sInstance) {
sInstance.closeInternal();
- if (resId != 0) {
- sInstance.loadDictionary(context, resId);
+ try {
+ final AssetFileDescriptor afd = context.getResources().openRawResourceFd(resId);
+ if (afd == null) {
+ Log.e(TAG, "Found the resource but it is compressed. resId=" + resId);
+ return null;
+ }
+ final String sourceDir = context.getApplicationInfo().sourceDir;
+ final File packagePath = new File(sourceDir);
+ // TODO: Come up with a way to handle a directory.
+ if (!packagePath.isFile()) {
+ Log.e(TAG, "sourceDir is not a file: " + sourceDir);
+ return null;
+ }
+ sInstance.loadDictionary(sourceDir, afd.getStartOffset(), afd.getLength());
sInstance.mDicTypeId = dicTypeId;
+ } catch (android.content.res.Resources.NotFoundException e) {
+ Log.e(TAG, "Could not find the resource. resId=" + resId);
+ return null;
+ }
+ }
+ return sInstance;
+ }
+
+ // For unit test
+ /* package */ static BinaryDictionary initDictionary(File dictionary, long startOffset,
+ long length, int dicTypeId) {
+ synchronized (sInstance) {
+ sInstance.closeInternal();
+ if (dictionary.isFile()) {
+ sInstance.loadDictionary(dictionary.getAbsolutePath(), startOffset, length);
+ sInstance.mDicTypeId = dicTypeId;
+ } else {
+ Log.e(TAG, "Could not find the file. path=" + dictionary.getAbsolutePath());
+ return null;
}
}
return sInstance;
@@ -92,22 +124,11 @@ public class BinaryDictionary extends Dictionary {
int[] inputCodes, int inputCodesLength, char[] outputChars, int[] frequencies,
int maxWordLength, int maxBigrams, int maxAlternatives);
- private final void loadDictionary(Context context, int resId) {
- try {
- final AssetFileDescriptor afd = context.getResources().openRawResourceFd(resId);
- if (afd == null) {
- Log.e(TAG, "Found the resource but it is compressed. resId=" + resId);
- return;
- }
- mNativeDict = openNative(context.getApplicationInfo().sourceDir,
- afd.getStartOffset(), afd.getLength(),
+ private final void loadDictionary(String path, long startOffset, long length) {
+ mNativeDict = openNative(path, startOffset, length,
TYPED_LETTER_MULTIPLIER, FULL_WORD_FREQ_MULTIPLIER,
MAX_WORD_LENGTH, MAX_WORDS, MAX_ALTERNATIVES);
- mDictLength = afd.getLength();
- } catch (android.content.res.Resources.NotFoundException e) {
- Log.e(TAG, "Could not find the resource. resId=" + resId);
- return;
- }
+ mDictLength = length;
}
@Override
diff --git a/java/src/com/android/inputmethod/latin/CandidateView.java b/java/src/com/android/inputmethod/latin/CandidateView.java
index fc45c7c75..9699ad136 100644
--- a/java/src/com/android/inputmethod/latin/CandidateView.java
+++ b/java/src/com/android/inputmethod/latin/CandidateView.java
@@ -54,7 +54,7 @@ public class CandidateView extends LinearLayout implements OnClickListener, OnLo
private static final CharacterStyle UNDERLINE_SPAN = new UnderlineSpan();
private static final int MAX_SUGGESTIONS = 16;
- private static boolean DBG = LatinImeLogger.sDBG;
+ private static final boolean DBG = LatinImeLogger.sDBG;
private final ArrayList<View> mWords = new ArrayList<View>();
private final boolean mConfigCandidateHighlightFontColorEnabled;
@@ -226,10 +226,14 @@ public class CandidateView extends LinearLayout implements OnClickListener, OnLo
}
final String debugString = info.getDebugString();
if (DBG) {
- if (!TextUtils.isEmpty(debugString)) {
+ if (TextUtils.isEmpty(debugString)) {
+ dv.setVisibility(GONE);
+ } else {
dv.setText(debugString);
dv.setVisibility(VISIBLE);
}
+ } else {
+ dv.setVisibility(GONE);
}
} else {
dv.setVisibility(GONE);
@@ -249,8 +253,10 @@ public class CandidateView extends LinearLayout implements OnClickListener, OnLo
final TextView tv = (TextView)mWords.get(1).findViewById(R.id.candidate_word);
final Spannable word = new SpannableString(autoCorrectedWord);
final int wordLength = word.length();
- word.setSpan(mInvertedBackgroundColorSpan, 0, wordLength, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
- word.setSpan(mInvertedForegroundColorSpan, 0, wordLength, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
+ word.setSpan(mInvertedBackgroundColorSpan, 0, wordLength,
+ Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
+ word.setSpan(mInvertedForegroundColorSpan, 0, wordLength,
+ Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
tv.setText(word);
mShowingAutoCorrectionInverted = true;
}
diff --git a/java/src/com/android/inputmethod/latin/DebugSettings.java b/java/src/com/android/inputmethod/latin/DebugSettings.java
index 03211f36b..2f1e7c2b8 100644
--- a/java/src/com/android/inputmethod/latin/DebugSettings.java
+++ b/java/src/com/android/inputmethod/latin/DebugSettings.java
@@ -20,6 +20,7 @@ import android.content.SharedPreferences;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager.NameNotFoundException;
import android.os.Bundle;
+import android.os.Process;
import android.preference.CheckBoxPreference;
import android.preference.PreferenceActivity;
import android.util.Log;
@@ -30,6 +31,7 @@ public class DebugSettings extends PreferenceActivity
private static final String TAG = "DebugSettings";
private static final String DEBUG_MODE_KEY = "debug_mode";
+ private boolean mServiceNeedsRestart = false;
private CheckBoxPreference mDebugMode;
@Override
@@ -39,16 +41,24 @@ public class DebugSettings extends PreferenceActivity
SharedPreferences prefs = getPreferenceManager().getSharedPreferences();
prefs.registerOnSharedPreferenceChangeListener(this);
+ mServiceNeedsRestart = false;
mDebugMode = (CheckBoxPreference) findPreference(DEBUG_MODE_KEY);
updateDebugMode();
}
@Override
+ protected void onStop() {
+ super.onStop();
+ if (mServiceNeedsRestart) Process.killProcess(Process.myPid());
+ }
+
+ @Override
public void onSharedPreferenceChanged(SharedPreferences prefs, String key) {
if (key.equals(DEBUG_MODE_KEY)) {
if (mDebugMode != null) {
mDebugMode.setChecked(prefs.getBoolean(DEBUG_MODE_KEY, false));
updateDebugMode();
+ mServiceNeedsRestart = true;
}
}
}
diff --git a/java/src/com/android/inputmethod/latin/LatinIME.java b/java/src/com/android/inputmethod/latin/LatinIME.java
index 5ce1b7e95..cb1ff41dd 100644
--- a/java/src/com/android/inputmethod/latin/LatinIME.java
+++ b/java/src/com/android/inputmethod/latin/LatinIME.java
@@ -81,8 +81,7 @@ import java.util.Locale;
/**
* Input method implementation for Qwerty'ish keyboard.
*/
-public class LatinIME extends InputMethodService implements KeyboardActionListener,
- SharedPreferences.OnSharedPreferenceChangeListener {
+public class LatinIME extends InputMethodService implements KeyboardActionListener {
private static final String TAG = "LatinIME";
private static final boolean PERF_DEBUG = false;
private static final boolean TRACE = false;
@@ -186,7 +185,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
// Keeps track of most recently inserted text (multi-character key) for reverting
private CharSequence mEnteredText;
- private boolean mRefreshKeyboardRequired;
private final ArrayList<WordAlternatives> mWordHistory = new ArrayList<WordAlternatives>();
@@ -359,9 +357,9 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
// but always use the default setting defined in the resources.
if (res.getBoolean(R.bool.config_enable_show_recorrection_option)) {
mReCorrectionEnabled = prefs.getBoolean(Settings.PREF_RECORRECTION_ENABLED,
- res.getBoolean(R.bool.default_recorrection_enabled));
+ res.getBoolean(R.bool.config_default_recorrection_enabled));
} else {
- mReCorrectionEnabled = res.getBoolean(R.bool.default_recorrection_enabled);
+ mReCorrectionEnabled = res.getBoolean(R.bool.config_default_recorrection_enabled);
}
mConfigEnableShowSubtypeSettings = res.getBoolean(
@@ -395,7 +393,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
registerReceiver(mReceiver, filter);
mVoiceConnector = VoiceIMEConnector.init(this, prefs, mHandler);
- prefs.registerOnSharedPreferenceChangeListener(this);
}
/**
@@ -523,11 +520,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
mSubtypeSwitcher.updateParametersOnStartInputView();
- if (mRefreshKeyboardRequired) {
- mRefreshKeyboardRequired = false;
- onRefreshKeyboard();
- }
-
TextEntryState.newSession(this);
// Most such things we decide below in initializeInputAttributesAndGetMode, but we need to
@@ -1942,19 +1934,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
}
@Override
- public void onSharedPreferenceChanged(SharedPreferences sharedPreferences,
- String key) {
- mSubtypeSwitcher.onSharedPreferenceChanged(sharedPreferences, key);
- if (Settings.PREF_SELECTED_LANGUAGES.equals(key)) {
- mRefreshKeyboardRequired = true;
- } else if (Settings.PREF_RECORRECTION_ENABLED.equals(key)) {
- mReCorrectionEnabled = sharedPreferences.getBoolean(
- Settings.PREF_RECORRECTION_ENABLED,
- mResources.getBoolean(R.bool.default_recorrection_enabled));
- }
- }
-
- @Override
public void onSwipeDown() {
if (mConfigSwipeDownDismissKeyboardEnabled)
handleClose();
@@ -2082,7 +2061,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
private void updateAutoTextEnabled() {
if (mSuggest == null) return;
- mSuggest.setAutoTextEnabled(mQuickFixes
+ mSuggest.setQuickFixesEnabled(mQuickFixes
&& SubtypeSwitcher.getInstance().isSystemLanguageSameAsInputLanguage());
}
@@ -2121,7 +2100,8 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
Vibrator vibrator = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE);
mVibrateOn = vibrator != null && vibrator.hasVibrator()
&& prefs.getBoolean(Settings.PREF_VIBRATE_ON, false);
- mSoundOn = prefs.getBoolean(Settings.PREF_SOUND_ON, false);
+ mSoundOn = prefs.getBoolean(Settings.PREF_SOUND_ON,
+ mResources.getBoolean(R.bool.config_default_sound_enabled));
mPopupOn = isPopupEnabled(prefs);
mAutoCap = prefs.getBoolean(Settings.PREF_AUTO_CAP, true);
@@ -2272,10 +2252,10 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
di.dismiss();
switch (position) {
case 0:
- launchSettings();
+ mImm.showInputMethodPicker();
break;
case 1:
- mImm.showInputMethodPicker();
+ launchSettings();
break;
}
}
diff --git a/java/src/com/android/inputmethod/latin/Settings.java b/java/src/com/android/inputmethod/latin/Settings.java
index 12338ce61..341d5add0 100644
--- a/java/src/com/android/inputmethod/latin/Settings.java
+++ b/java/src/com/android/inputmethod/latin/Settings.java
@@ -225,7 +225,9 @@ public class Settings extends PreferenceActivity
final String action;
if (android.os.Build.VERSION.SDK_INT
>= /* android.os.Build.VERSION_CODES.HONEYCOMB */ 11) {
- action = "android.settings.INPUT_METHOD_AND_SUBTYPE_ENABLER";
+ // Refer to android.provider.Settings.ACTION_INPUT_METHOD_SUBTYPE_SETTINGS
+ // TODO: Can this be a constant instead of literal String constant?
+ action = "android.settings.INPUT_METHOD_SUBTYPE_SETTINGS";
} else {
action = "com.android.inputmethod.latin.INPUT_LANGUAGE_SELECTION";
}
diff --git a/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java b/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java
index f4262cc99..dee3da425 100644
--- a/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java
+++ b/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java
@@ -426,8 +426,15 @@ public class SubtypeSwitcher {
if (mConfigUseSpacebarLanguageSwitcher) {
return mLanguageSwitcher.getEnabledLanguages();
} else {
+ int enabledLanguageCount = mEnabledLanguagesOfCurrentInputMethod.size();
+ // Workaround for explicitly specifying the voice language
+ if (enabledLanguageCount == 1) {
+ mEnabledLanguagesOfCurrentInputMethod.add(
+ mEnabledLanguagesOfCurrentInputMethod.get(0));
+ ++enabledLanguageCount;
+ }
return mEnabledLanguagesOfCurrentInputMethod.toArray(
- new String[mEnabledLanguagesOfCurrentInputMethod.size()]);
+ new String[enabledLanguageCount]);
}
}
@@ -465,14 +472,6 @@ public class SubtypeSwitcher {
}
}
- public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {
- if (mConfigUseSpacebarLanguageSwitcher) {
- if (Settings.PREF_SELECTED_LANGUAGES.equals(key)) {
- mLanguageSwitcher.loadLocales(sharedPreferences);
- }
- }
- }
-
/**
* Change system locale for this application
* @param newLocale
diff --git a/java/src/com/android/inputmethod/latin/Suggest.java b/java/src/com/android/inputmethod/latin/Suggest.java
index ced355bb2..c9e57d0a5 100644
--- a/java/src/com/android/inputmethod/latin/Suggest.java
+++ b/java/src/com/android/inputmethod/latin/Suggest.java
@@ -22,6 +22,7 @@ import android.text.TextUtils;
import android.util.Log;
import android.view.View;
+import java.io.File;
import java.util.ArrayList;
import java.util.Arrays;
@@ -64,7 +65,7 @@ public class Suggest implements Dictionary.WordCallback {
static final int LARGE_DICTIONARY_THRESHOLD = 200 * 1000;
- private static boolean DBG = LatinImeLogger.sDBG;
+ private static final boolean DBG = LatinImeLogger.sDBG;
private BinaryDictionary mMainDict;
@@ -80,7 +81,7 @@ public class Suggest implements Dictionary.WordCallback {
private static final int PREF_MAX_BIGRAMS = 60;
- private boolean mAutoTextEnabled;
+ private boolean mQuickFixesEnabled;
private double mAutoCorrectionThreshold;
private int[] mPriorities = new int[mPrefMaxSuggestions];
@@ -109,6 +110,12 @@ public class Suggest implements Dictionary.WordCallback {
initPool();
}
+ // For unit test
+ /* package */ Suggest(File dictionary, long startOffset, long length) {
+ mMainDict = BinaryDictionary.initDictionary(dictionary, startOffset, length, DIC_MAIN);
+ initPool();
+ }
+
private void initPool() {
for (int i = 0; i < mPrefMaxSuggestions; i++) {
StringBuilder sb = new StringBuilder(getApproxMaxWordLength());
@@ -116,8 +123,8 @@ public class Suggest implements Dictionary.WordCallback {
}
}
- public void setAutoTextEnabled(boolean enabled) {
- mAutoTextEnabled = enabled;
+ public void setQuickFixesEnabled(boolean enabled) {
+ mQuickFixesEnabled = enabled;
}
public int getCorrectionMode() {
@@ -224,6 +231,7 @@ public class Suggest implements Dictionary.WordCallback {
mLowerOriginalWord = "";
}
+ double normalizedScore = Integer.MIN_VALUE;
if (wordComposer.size() == 1 && (mCorrectionMode == CORRECTION_FULL_BIGRAM
|| mCorrectionMode == CORRECTION_BASIC)) {
// At first character typed, search only the bigrams
@@ -290,9 +298,9 @@ public class Suggest implements Dictionary.WordCallback {
&& mSuggestions.size() > 0 && mPriorities.length > 0) {
// TODO: when the normalized score of the first suggestion is nearly equals to
// the normalized score of the second suggestion, behave less aggressive.
- final double normalizedScore = Utils.calcNormalizedScore(
+ normalizedScore = Utils.calcNormalizedScore(
typedWord, mSuggestions.get(0), mPriorities[0]);
- if (LatinImeLogger.sDBG) {
+ if (DBG) {
Log.d(TAG, "Normalized " + typedWord + "," + mSuggestions.get(0) + ","
+ mPriorities[0] + ", " + normalizedScore
+ "(" + mAutoCorrectionThreshold + ")");
@@ -308,7 +316,7 @@ public class Suggest implements Dictionary.WordCallback {
if (typedWord != null) {
mSuggestions.add(0, typedWord.toString());
}
- if (mAutoTextEnabled) {
+ if (mQuickFixesEnabled) {
int i = 0;
int max = 6;
// Don't autotext the suggestions from the dictionaries
@@ -354,7 +362,30 @@ public class Suggest implements Dictionary.WordCallback {
}
}
removeDupes();
- return new SuggestedWords.Builder().addWords(mSuggestions, null);
+ if (DBG) {
+ ArrayList<SuggestedWords.SuggestedWordInfo> frequencyInfoList =
+ new ArrayList<SuggestedWords.SuggestedWordInfo>();
+ frequencyInfoList.add(new SuggestedWords.SuggestedWordInfo("+", false));
+ final int priorityLength = mPriorities.length;
+ for (int i = 0; i < priorityLength; ++i) {
+ if (normalizedScore > 0) {
+ final String priorityThreshold = Integer.toString(mPriorities[i]) + " (" +
+ normalizedScore + ")";
+ frequencyInfoList.add(
+ new SuggestedWords.SuggestedWordInfo(priorityThreshold, false));
+ normalizedScore = 0.0;
+ } else {
+ final String priority = Integer.toString(mPriorities[i]);
+ frequencyInfoList.add(new SuggestedWords.SuggestedWordInfo(priority, false));
+ }
+ }
+ for (int i = priorityLength; i < mSuggestions.size(); ++i) {
+ frequencyInfoList.add(new SuggestedWords.SuggestedWordInfo("--", false));
+ }
+ return new SuggestedWords.Builder().addWords(mSuggestions, frequencyInfoList);
+ } else {
+ return new SuggestedWords.Builder().addWords(mSuggestions, null);
+ }
}
public int[] getNextLettersFrequencies() {
@@ -392,12 +423,12 @@ public class Suggest implements Dictionary.WordCallback {
return mHasAutoCorrection;
}
- private boolean compareCaseInsensitive(final String mLowerOriginalWord,
+ private static boolean compareCaseInsensitive(final String lowerOriginalWord,
final char[] word, final int offset, final int length) {
- final int originalLength = mLowerOriginalWord.length();
+ final int originalLength = lowerOriginalWord.length();
if (originalLength == length && Character.isUpperCase(word[offset])) {
for (int i = 0; i < originalLength; i++) {
- if (mLowerOriginalWord.charAt(i) != Character.toLowerCase(word[offset+i])) {
+ if (lowerOriginalWord.charAt(i) != Character.toLowerCase(word[offset+i])) {
return false;
}
}
diff --git a/java/src/com/android/inputmethod/latin/UserDictionary.java b/java/src/com/android/inputmethod/latin/UserDictionary.java
index 56ee5b9e7..db5d9244f 100644
--- a/java/src/com/android/inputmethod/latin/UserDictionary.java
+++ b/java/src/com/android/inputmethod/latin/UserDictionary.java
@@ -138,7 +138,7 @@ public class UserDictionary extends ExpandableDictionary {
private void addWords(Cursor cursor) {
clearDictionary();
-
+ if (cursor == null) return;
final int maxWordLength = getMaxWordLength();
if (cursor.moveToFirst()) {
final int indexWord = cursor.getColumnIndex(Words.WORD);
diff --git a/java/src/com/android/inputmethod/latin/Utils.java b/java/src/com/android/inputmethod/latin/Utils.java
index e980d3a30..aafafbf2f 100644
--- a/java/src/com/android/inputmethod/latin/Utils.java
+++ b/java/src/com/android/inputmethod/latin/Utils.java
@@ -261,6 +261,19 @@ public class Utils {
return dp[sl][tl];
}
+ // Get the current stack trace
+ public static String getStackTrace() {
+ StringBuilder sb = new StringBuilder();
+ try {
+ throw new RuntimeException();
+ } catch (RuntimeException e) {
+ StackTraceElement[] frames = e.getStackTrace();
+ // Start at 1 because the first frame is here and we don't care about it
+ for (int j = 1; j < frames.length; ++j) sb.append(frames[j].toString() + "\n");
+ }
+ return sb.toString();
+ }
+
// In dictionary.cpp, getSuggestion() method,
// suggestion scores are computed using the below formula.
// original score (called 'frequency')