diff options
117 files changed, 1180 insertions, 735 deletions
diff --git a/common/Android.mk b/common/Android.mk index 085543f75..132a22358 100644 --- a/common/Android.mk +++ b/common/Android.mk @@ -12,7 +12,7 @@ # See the License for the specific language governing permissions and # limitations under the License. -LOCAL_PATH:= $(call my-dir) +LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) LOCAL_MODULE := latinime-common LOCAL_SRC_FILES := $(call all-java-files-under, src) diff --git a/java/src/com/android/inputmethod/latin/utils/CollectionUtils.java b/common/src/com/android/inputmethod/latin/common/CollectionUtils.java index 01f5e1079..f7ba693af 100644 --- a/java/src/com/android/inputmethod/latin/utils/CollectionUtils.java +++ b/common/src/com/android/inputmethod/latin/common/CollectionUtils.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package com.android.inputmethod.latin.utils; +package com.android.inputmethod.latin.common; import java.util.ArrayList; import java.util.Collection; diff --git a/java/src/com/android/inputmethod/latin/utils/CoordinateUtils.java b/common/src/com/android/inputmethod/latin/common/CoordinateUtils.java index 3a9705904..031662411 100644 --- a/java/src/com/android/inputmethod/latin/utils/CoordinateUtils.java +++ b/common/src/com/android/inputmethod/latin/common/CoordinateUtils.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package com.android.inputmethod.latin.utils; +package com.android.inputmethod.latin.common; import javax.annotation.Nonnull; diff --git a/java/src/com/android/inputmethod/latin/utils/FileUtils.java b/common/src/com/android/inputmethod/latin/common/FileUtils.java index f1106a6c6..676845842 100644 --- a/java/src/com/android/inputmethod/latin/utils/FileUtils.java +++ b/common/src/com/android/inputmethod/latin/common/FileUtils.java @@ -14,7 +14,7 @@ * the License. */ -package com.android.inputmethod.latin.utils; +package com.android.inputmethod.latin.common; import java.io.File; import java.io.FilenameFilter; diff --git a/java/src/com/android/inputmethod/dictionarypack/LocaleUtils.java b/common/src/com/android/inputmethod/latin/common/LocaleUtils.java index 4f0805c5c..14b3d220d 100644 --- a/java/src/com/android/inputmethod/dictionarypack/LocaleUtils.java +++ b/common/src/com/android/inputmethod/latin/common/LocaleUtils.java @@ -14,11 +14,7 @@ * the License. */ -package com.android.inputmethod.dictionarypack; - -import android.content.res.Configuration; -import android.content.res.Resources; -import android.text.TextUtils; +package com.android.inputmethod.latin.common; import java.util.HashMap; import java.util.Locale; @@ -105,8 +101,8 @@ public final class LocaleUtils { * @return a constant that measures how well the tested locale matches the reference locale. */ public static int getMatchLevel(final String referenceLocale, final String testedLocale) { - if (TextUtils.isEmpty(referenceLocale)) { - return TextUtils.isEmpty(testedLocale) ? LOCALE_FULL_MATCH : LOCALE_ANY_MATCH; + if (StringUtils.isEmpty(referenceLocale)) { + return StringUtils.isEmpty(testedLocale) ? LOCALE_FULL_MATCH : LOCALE_ANY_MATCH; } if (null == testedLocale) return LOCALE_NO_MATCH; final String[] referenceParams = referenceLocale.split("_", 3); @@ -160,21 +156,6 @@ public final class LocaleUtils { return LOCALE_MATCH <= level; } - /** - * Sets the system locale for this process. - * - * @param res the resources to use. Pass current resources. - * @param newLocale the locale to change to. - * @return the old locale. - */ - public static Locale setSystemLocale(final Resources res, final Locale newLocale) { - final Configuration conf = res.getConfiguration(); - final Locale saveLocale = conf.locale; - conf.locale = newLocale; - res.updateConfiguration(conf, res.getDisplayMetrics()); - return saveLocale; - } - private static final HashMap<String, Locale> sLocaleCache = new HashMap<>(); /** diff --git a/java/src/com/android/inputmethod/latin/settings/NativeSuggestOptions.java b/common/src/com/android/inputmethod/latin/common/NativeSuggestOptions.java index 7603dbba5..7ef741cc2 100644 --- a/java/src/com/android/inputmethod/latin/settings/NativeSuggestOptions.java +++ b/common/src/com/android/inputmethod/latin/common/NativeSuggestOptions.java @@ -14,7 +14,7 @@ * limitations under the License. */ -package com.android.inputmethod.latin.settings; +package com.android.inputmethod.latin.common; public class NativeSuggestOptions { // Need to update suggest_options.h when you add, remove or reorder options. @@ -25,8 +25,11 @@ public class NativeSuggestOptions { private static final int WEIGHT_FOR_LOCALE_IN_THOUSANDS = 4; private static final int OPTIONS_SIZE = 5; - private final int[] mOptions = new int[OPTIONS_SIZE - + AdditionalFeaturesSettingUtils.ADDITIONAL_FEATURES_SETTINGS_SIZE]; + private final int[] mOptions; + + public NativeSuggestOptions(final int additionalFeaturesSettingsSize) { + mOptions = new int[OPTIONS_SIZE + additionalFeaturesSettingsSize]; + } public void setIsGesture(final boolean value) { setBooleanOption(IS_GESTURE, value); diff --git a/java-overridable/src/com/android/inputmethod/latin/settings/AdditionalFeaturesSettingUtils.java b/java-overridable/src/com/android/inputmethod/latin/settings/AdditionalFeaturesSettingUtils.java index bd54238f8..4e8a10b1f 100644 --- a/java-overridable/src/com/android/inputmethod/latin/settings/AdditionalFeaturesSettingUtils.java +++ b/java-overridable/src/com/android/inputmethod/latin/settings/AdditionalFeaturesSettingUtils.java @@ -47,6 +47,7 @@ public class AdditionalFeaturesSettingUtils { // do nothing. } + @Nonnull public static RichInputMethodSubtype createRichInputMethodSubtype( @Nonnull final RichInputMethodManager imm, @Nonnull final InputMethodSubtype subtype, diff --git a/java/Android.mk b/java/Android.mk index a2c5697d3..b84b3471e 100644 --- a/java/Android.mk +++ b/java/Android.mk @@ -12,7 +12,7 @@ # See the License for the specific language governing permissions and # limitations under the License. -LOCAL_PATH:= $(call my-dir) +LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) LOCAL_MODULE_TAGS := optional diff --git a/java/res/values-af/strings-emoji-descriptions.xml b/java/res/values-af/strings-emoji-descriptions.xml index 26bfc5f08..5ed066a87 100644 --- a/java/res/values-af/strings-emoji-descriptions.xml +++ b/java/res/values-af/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Koekie"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Staaf sjokolade"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Lekkergoed"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Suiglekker"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Vla"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Heuningpot"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Broskoek"</string> diff --git a/java/res/values-ar/strings-emoji-descriptions.xml b/java/res/values-ar/strings-emoji-descriptions.xml index 875f626c2..c1decd303 100644 --- a/java/res/values-ar/strings-emoji-descriptions.xml +++ b/java/res/values-ar/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"كعكة"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"بار شيكولاتة"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"حلوى"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"مصاصة"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"كاسترد"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"جرة عسل"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"كعكة بسمن وسكر"</string> diff --git a/java/res/values-bn-rBD/strings-emoji-descriptions.xml b/java/res/values-bn-rBD/strings-emoji-descriptions.xml index 4c661661d..3c58621f4 100644 --- a/java/res/values-bn-rBD/strings-emoji-descriptions.xml +++ b/java/res/values-bn-rBD/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"কুকি"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"চকোলেট বার"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"ক্যান্ডি"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"ললিপপ"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"কাস্টার্ড"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"মধুর পাত্র"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"শর্টকেক"</string> diff --git a/java/res/values-cs/strings-emoji-descriptions.xml b/java/res/values-cs/strings-emoji-descriptions.xml index b66420247..b7f359c55 100644 --- a/java/res/values-cs/strings-emoji-descriptions.xml +++ b/java/res/values-cs/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Sušenka"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Tabulka čokolády"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Bonbon"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lízátko"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Pudink"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Hrnek medu"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Dort"</string> diff --git a/java/res/values-el/strings-emoji-descriptions.xml b/java/res/values-el/strings-emoji-descriptions.xml index aa8966e97..a15d0fdba 100644 --- a/java/res/values-el/strings-emoji-descriptions.xml +++ b/java/res/values-el/strings-emoji-descriptions.xml @@ -269,7 +269,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Κούκι"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Σοκολάτα"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Γλυκά"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Γλειφιτζούρι"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Κρέμα"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Βάζο με μέλι"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Μπισκότο"</string> diff --git a/java/res/values-fa/strings-emoji-descriptions.xml b/java/res/values-fa/strings-emoji-descriptions.xml index cc670eef9..8adb530be 100644 --- a/java/res/values-fa/strings-emoji-descriptions.xml +++ b/java/res/values-fa/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"کلوچه"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"تخته شکلات"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"آبنبات"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"آبنبات چوبی"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"آبنبات چوبی"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"کاستارد"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"ظرف عسل"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"کیک روغنی"</string> diff --git a/java/res/values-fa/strings.xml b/java/res/values-fa/strings.xml index 2461da5af..16a6f8767 100644 --- a/java/res/values-fa/strings.xml +++ b/java/res/values-fa/strings.xml @@ -84,7 +84,7 @@ <string name="hint_add_to_dictionary_without_word" msgid="3040385779511255101">"برای ذخیره اینجا را لمس کنید"</string> <string name="has_dictionary" msgid="6071847973466625007">"دیکشنری موجود است"</string> <string name="keyboard_layout" msgid="8451164783510487501">"طرح زمینه صفحهکلید"</string> - <string name="switch_accounts" msgid="3321216593719006162">"جابجایی بین حسابها"</string> + <string name="switch_accounts" msgid="3321216593719006162">"جابهجایی بین حسابها"</string> <string name="no_accounts_selected" msgid="2073821619103904330">"هیچ حسابی انتخاب نشده است"</string> <string name="account_selected" msgid="2846876462199625974">"در حال حاضر در حال استفاده از <xliff:g id="EMAIL_ADDRESS">%1$s</xliff:g>"</string> <string name="account_select_ok" msgid="9141195141763227797">"تأیید"</string> diff --git a/java/res/values-fi/strings-emoji-descriptions.xml b/java/res/values-fi/strings-emoji-descriptions.xml index 72af3c229..7d6a9f957 100644 --- a/java/res/values-fi/strings-emoji-descriptions.xml +++ b/java/res/values-fi/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Pikkuleipä"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Suklaapatukka"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Karamelli"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Tikkari"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Vanukas"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Hunajapurkki"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Kakkuviipale"</string> diff --git a/java/res/values-fr/strings-emoji-descriptions.xml b/java/res/values-fr/strings-emoji-descriptions.xml index b7ad706fc..1f99ee3bc 100644 --- a/java/res/values-fr/strings-emoji-descriptions.xml +++ b/java/res/values-fr/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Biscuit"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Barre de chocolat"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Bonbon"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Sucette"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Crème anglaise"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Pot de miel"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Sablé"</string> diff --git a/java/res/values-gl-rES/strings-emoji-descriptions.xml b/java/res/values-gl-rES/strings-emoji-descriptions.xml index 31eb89bb2..cdb67fa45 100644 --- a/java/res/values-gl-rES/strings-emoji-descriptions.xml +++ b/java/res/values-gl-rES/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Galleta"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Barra de chocolate"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Caramelo"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Chupa-chupa"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Crema"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Tarro de mel"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Pastel"</string> diff --git a/java/res/values-hi/strings-emoji-descriptions.xml b/java/res/values-hi/strings-emoji-descriptions.xml index df5fa1e13..1f18e6add 100644 --- a/java/res/values-hi/strings-emoji-descriptions.xml +++ b/java/res/values-hi/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"कुकी"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"चॉकलेट बार"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"कैंडी"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"लॉलीपॉप"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"दही"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"शहद का बर्तन"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"शॉर्टकेक"</string> diff --git a/java/res/values-hu/strings-emoji-descriptions.xml b/java/res/values-hu/strings-emoji-descriptions.xml index 4f3d01c86..b72f29853 100644 --- a/java/res/values-hu/strings-emoji-descriptions.xml +++ b/java/res/values-hu/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Sütemény"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Csokoládé"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Cukorka"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Nyalóka"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Sodó"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Mézesbödön"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Tortaszelet"</string> diff --git a/java/res/values-hy-rAM/strings-emoji-descriptions.xml b/java/res/values-hy-rAM/strings-emoji-descriptions.xml index f41f2fc96..dcc718e22 100644 --- a/java/res/values-hy-rAM/strings-emoji-descriptions.xml +++ b/java/res/values-hy-rAM/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Թխվածքաբլիթ"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Շոկոլադի սալիկ"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Կոնֆետ"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Սառնաշաքար կոնֆետ"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Շաքարաքլոր"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Եփովի կրեմ"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Մեղրանոթ"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Տորթի կտոր"</string> diff --git a/java/res/values-iw/strings-emoji-descriptions.xml b/java/res/values-iw/strings-emoji-descriptions.xml index ab31403aa..fc4435a14 100644 --- a/java/res/values-iw/strings-emoji-descriptions.xml +++ b/java/res/values-iw/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"עוגייה"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"חפיסת שוקולד"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"סוכרייה"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"סוכרייה על מקל"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"רפרפת"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"סיר דבש"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"עוגת פירות"</string> diff --git a/java/res/values-km-rKH/strings-emoji-descriptions.xml b/java/res/values-km-rKH/strings-emoji-descriptions.xml index 757df50e7..e9b8780a5 100644 --- a/java/res/values-km-rKH/strings-emoji-descriptions.xml +++ b/java/res/values-km-rKH/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"ខូគី"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"សូកូឡា"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"ស្ករគ្រាប់"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"ស្ករគ្រាប់មានដងកាន់"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"សង់ខ្យា"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"ថូ"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"នំខេក"</string> diff --git a/java/res/values-kn-rIN/strings-emoji-descriptions.xml b/java/res/values-kn-rIN/strings-emoji-descriptions.xml index 4e6d5ced5..a013c2755 100644 --- a/java/res/values-kn-rIN/strings-emoji-descriptions.xml +++ b/java/res/values-kn-rIN/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"ಕುಕಿ"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"ಚಾಕೊಲೇಟ್ ಬಾರ್"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"ಕ್ಯಾಂಡಿ"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"ಲಾಲಿಪಪ್"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"ಕಸ್ಟರ್ಡ್"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"ಜೇನಿನ ಮಡಕೆ"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"ಶಾರ್ಟ್ಕೇಕ್"</string> diff --git a/java/res/values-ml-rIN/strings-emoji-descriptions.xml b/java/res/values-ml-rIN/strings-emoji-descriptions.xml index ab6509756..a846f31a5 100644 --- a/java/res/values-ml-rIN/strings-emoji-descriptions.xml +++ b/java/res/values-ml-rIN/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"കുക്കി"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"ചോക്കലേറ്റ് ബാർ"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"മിഠായി"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"ലോലിപോപ്പ്"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"കസ്റ്റാർഡ്"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"തേൻ കുടം"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"ഷോർട്ട്കേക്ക്"</string> diff --git a/java/res/values-nb/strings-emoji-descriptions.xml b/java/res/values-nb/strings-emoji-descriptions.xml index fa655f12f..681118833 100644 --- a/java/res/values-nb/strings-emoji-descriptions.xml +++ b/java/res/values-nb/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Kjeks"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Sjokoladeplate"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Godteri"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Kjærlighet på pinne"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Pudding"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Honningkrukke"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Kakestykke"</string> diff --git a/java/res/values-nl/strings-emoji-descriptions.xml b/java/res/values-nl/strings-emoji-descriptions.xml index a02c21fa0..3b298900b 100644 --- a/java/res/values-nl/strings-emoji-descriptions.xml +++ b/java/res/values-nl/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Cookie"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Chocoladereep"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Snoep"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lolly"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Vla"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Honingpot"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Cake"</string> diff --git a/java/res/values-pt/strings.xml b/java/res/values-pt/strings.xml index 2e0cd3b55..2cc86e12f 100644 --- a/java/res/values-pt/strings.xml +++ b/java/res/values-pt/strings.xml @@ -102,8 +102,7 @@ <string name="subtype_with_layout_hi_ZZ" msgid="6827402953860547044">"Híndi-inglês (<xliff:g id="KEYBOARD_LAYOUT">%s</xliff:g>)"</string> <string name="subtype_with_layout_sr_ZZ" msgid="2859024772719772407">"Sérvio (<xliff:g id="KEYBOARD_LAYOUT">%s</xliff:g>)"</string> <string name="subtype_generic_traditional" msgid="8584594350973800586">"<xliff:g id="LANGUAGE_NAME">%s</xliff:g> (tradicional)"</string> - <!-- no translation found for subtype_generic_compact (3353673321203202922) --> - <skip /> + <string name="subtype_generic_compact" msgid="3353673321203202922">"<xliff:g id="LANGUAGE_NAME">%s</xliff:g> (compacto)"</string> <string name="subtype_no_language" msgid="7137390094240139495">"Nenhum idioma (alfabeto)"</string> <string name="subtype_no_language_qwerty" msgid="244337630616742604">"Alfabeto (QWERTY)"</string> <string name="subtype_no_language_qwertz" msgid="443066912507547976">"Alfabeto (QWERTZ)"</string> diff --git a/java/res/values-ro/strings-emoji-descriptions.xml b/java/res/values-ro/strings-emoji-descriptions.xml index f44a0b974..2ac84e5a0 100644 --- a/java/res/values-ro/strings-emoji-descriptions.xml +++ b/java/res/values-ro/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Biscuit"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Ciocolată"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Bomboane"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Acadea"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Budincă"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Oală de miere"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Prăjitură"</string> diff --git a/java/res/values-sw/strings-emoji-descriptions.xml b/java/res/values-sw/strings-emoji-descriptions.xml index 57163878e..329bf398a 100644 --- a/java/res/values-sw/strings-emoji-descriptions.xml +++ b/java/res/values-sw/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Biskuti"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Mchi wa chokoleti"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Peremende"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Peremende ya kijiti"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Faluda au Kastadi"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Emoji ya chungu cha asali"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Keki tamu yenye vitandamlo inayofanana na biskuti"</string> diff --git a/java/res/values-th/strings-emoji-descriptions.xml b/java/res/values-th/strings-emoji-descriptions.xml index e5ef9b89d..86ab2c08e 100644 --- a/java/res/values-th/strings-emoji-descriptions.xml +++ b/java/res/values-th/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"คุกกี้"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"ช็อกโกแลตแท่ง"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"ลูกกวาด"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"อมยิ้ม"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"คัสตาร์ด"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"โถน้ำผึ้ง"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"ชอร์ตเค้ก"</string> diff --git a/java/res/values-ur-rPK/strings-emoji-descriptions.xml b/java/res/values-ur-rPK/strings-emoji-descriptions.xml index d5bcf2f94..e6bbdcf49 100644 --- a/java/res/values-ur-rPK/strings-emoji-descriptions.xml +++ b/java/res/values-ur-rPK/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"کوکی"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"چاکلیٹ بار"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"قندی"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"لالی پاپ"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"کسٹرڈ"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"شہد کا برتن"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"کیک کا ٹکڑا"</string> diff --git a/java/res/values-vi/strings-emoji-descriptions.xml b/java/res/values-vi/strings-emoji-descriptions.xml index 8b44dcfbf..492c726d1 100644 --- a/java/res/values-vi/strings-emoji-descriptions.xml +++ b/java/res/values-vi/strings-emoji-descriptions.xml @@ -267,7 +267,7 @@ <string name="spoken_emoji_1F36A" msgid="2726271795913042295">"Bánh quy"</string> <string name="spoken_emoji_1F36B" msgid="6342163604299875931">"Thanh sôcôla"</string> <string name="spoken_emoji_1F36C" msgid="2168934753998218790">"Kẹo"</string> - <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Kẹo que"</string> + <string name="spoken_emoji_1F36D" msgid="3671507903799975792">"Lollipop"</string> <string name="spoken_emoji_1F36E" msgid="4630541402785165902">"Món sữa trứng"</string> <string name="spoken_emoji_1F36F" msgid="5577915387425169439">"Mắt ong"</string> <string name="spoken_emoji_1F370" msgid="7243244547866114951">"Bánh bơ giòn"</string> diff --git a/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java b/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java index 7fc1e9d8a..2de71cec9 100644 --- a/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java +++ b/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java @@ -31,9 +31,9 @@ import android.view.inputmethod.EditorInfo; import com.android.inputmethod.keyboard.Key; import com.android.inputmethod.keyboard.Keyboard; import com.android.inputmethod.keyboard.KeyboardView; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.settings.Settings; import com.android.inputmethod.latin.settings.SettingsValues; -import com.android.inputmethod.latin.utils.CoordinateUtils; import java.util.List; diff --git a/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java b/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java index d3e24e342..be0744393 100644 --- a/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java +++ b/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java @@ -27,8 +27,8 @@ import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.latin.SuggestedWords; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.SuggestionSpanPickedNotificationReceiver; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.define.DebugFlags; -import com.android.inputmethod.latin.utils.LocaleUtils; import java.lang.reflect.Field; import java.util.ArrayList; diff --git a/java/src/com/android/inputmethod/dictionarypack/DictionaryProvider.java b/java/src/com/android/inputmethod/dictionarypack/DictionaryProvider.java index 37fa76be7..659fe5c51 100644 --- a/java/src/com/android/inputmethod/dictionarypack/DictionaryProvider.java +++ b/java/src/com/android/inputmethod/dictionarypack/DictionaryProvider.java @@ -31,6 +31,7 @@ import android.text.TextUtils; import android.util.Log; import com.android.inputmethod.latin.R; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.utils.DebugLogUtils; import java.io.File; diff --git a/java/src/com/android/inputmethod/dictionarypack/DictionaryService.java b/java/src/com/android/inputmethod/dictionarypack/DictionaryService.java index e9b634eec..e6acb8f36 100644 --- a/java/src/com/android/inputmethod/dictionarypack/DictionaryService.java +++ b/java/src/com/android/inputmethod/dictionarypack/DictionaryService.java @@ -25,6 +25,7 @@ import android.os.IBinder; import android.widget.Toast; import com.android.inputmethod.latin.R; +import com.android.inputmethod.latin.common.LocaleUtils; import java.util.Locale; import java.util.Random; diff --git a/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java b/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java index c2dc87900..14e005007 100644 --- a/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java +++ b/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java @@ -16,6 +16,8 @@ package com.android.inputmethod.dictionarypack; +import com.android.inputmethod.latin.common.LocaleUtils; + import android.app.Activity; import android.content.BroadcastReceiver; import android.content.ContentResolver; diff --git a/java/src/com/android/inputmethod/dictionarypack/DownloadOverMeteredDialog.java b/java/src/com/android/inputmethod/dictionarypack/DownloadOverMeteredDialog.java index f1633ff28..50b3c72f3 100644 --- a/java/src/com/android/inputmethod/dictionarypack/DownloadOverMeteredDialog.java +++ b/java/src/com/android/inputmethod/dictionarypack/DownloadOverMeteredDialog.java @@ -26,6 +26,7 @@ import android.widget.TextView; import com.android.inputmethod.annotations.ExternallyReferenced; import com.android.inputmethod.latin.R; +import com.android.inputmethod.latin.common.LocaleUtils; import java.util.Locale; diff --git a/java/src/com/android/inputmethod/dictionarypack/UpdateHandler.java b/java/src/com/android/inputmethod/dictionarypack/UpdateHandler.java index d59b7a545..bd6152119 100644 --- a/java/src/com/android/inputmethod/dictionarypack/UpdateHandler.java +++ b/java/src/com/android/inputmethod/dictionarypack/UpdateHandler.java @@ -39,6 +39,7 @@ import com.android.inputmethod.compat.ConnectivityManagerCompatUtils; import com.android.inputmethod.compat.DownloadManagerCompatUtils; import com.android.inputmethod.compat.NotificationCompatUtils; import com.android.inputmethod.latin.R; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.utils.ApplicationUtils; import com.android.inputmethod.latin.utils.DebugLogUtils; diff --git a/java/src/com/android/inputmethod/keyboard/Keyboard.java b/java/src/com/android/inputmethod/keyboard/Keyboard.java index 3c90a04db..619b801f4 100644 --- a/java/src/com/android/inputmethod/keyboard/Keyboard.java +++ b/java/src/com/android/inputmethod/keyboard/Keyboard.java @@ -22,7 +22,7 @@ import com.android.inputmethod.keyboard.internal.KeyVisualAttributes; import com.android.inputmethod.keyboard.internal.KeyboardIconsSet; import com.android.inputmethod.keyboard.internal.KeyboardParams; import com.android.inputmethod.latin.common.Constants; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; import java.util.ArrayList; import java.util.Collections; diff --git a/java/src/com/android/inputmethod/keyboard/KeyboardLayoutSet.java b/java/src/com/android/inputmethod/keyboard/KeyboardLayoutSet.java index 1637ed9f6..51f37fdc6 100644 --- a/java/src/com/android/inputmethod/keyboard/KeyboardLayoutSet.java +++ b/java/src/com/android/inputmethod/keyboard/KeyboardLayoutSet.java @@ -51,6 +51,9 @@ import java.io.IOException; import java.lang.ref.SoftReference; import java.util.HashMap; +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + /** * This class represents a set of keyboard layouts. Each of them represents a different keyboard * specific to a keyboard state, such as alphabet, symbols, and so on. Layouts in the same @@ -82,6 +85,8 @@ public final class KeyboardLayoutSet { private static final HashMap<KeyboardId, SoftReference<Keyboard>> sKeyboardCache = new HashMap<>(); private static final KeysCache sKeysCache = new KeysCache(); + private final static HashMap<InputMethodSubtype, Integer> sScriptIdsForSubtypes = + new HashMap<>(); @SuppressWarnings("serial") public static final class KeyboardLayoutSetException extends RuntimeException { @@ -140,6 +145,16 @@ public final class KeyboardLayoutSet { sKeysCache.clear(); } + public static int getScriptId(final Resources resources, final InputMethodSubtype subtype) { + final Integer value = sScriptIdsForSubtypes.get(subtype); + if (null == value) { + final int scriptId = Builder.readScriptId(resources, subtype); + sScriptIdsForSubtypes.put(subtype, scriptId); + return scriptId; + } + return value; + } + KeyboardLayoutSet(final Context context, final Params params) { mContext = context; mParams = params; @@ -244,7 +259,7 @@ public final class KeyboardLayoutSet { private static final EditorInfo EMPTY_EDITOR_INFO = new EditorInfo(); - public Builder(final Context context, final EditorInfo ei) { + public Builder(final Context context, @Nullable final EditorInfo ei) { mContext = context; mPackageName = context.getPackageName(); mResources = context.getResources(); @@ -265,7 +280,7 @@ public final class KeyboardLayoutSet { return this; } - public Builder setSubtype(final RichInputMethodSubtype subtype) { + public Builder setSubtype(@Nonnull final RichInputMethodSubtype subtype) { final boolean asciiCapable = InputMethodSubtypeCompatUtils.isAsciiCapable(subtype); // TODO: Consolidate with {@link InputAttributes}. @SuppressWarnings("deprecation") @@ -303,31 +318,13 @@ public final class KeyboardLayoutSet { return this; } - public Builder setScriptId(final int scriptId) { - mParams.mScriptId = scriptId; - return this; - } - public Builder setSplitLayoutEnabledByUser(final boolean enabled) { mParams.mIsSplitLayoutEnabledByUser = enabled; return this; } - private final static HashMap<InputMethodSubtype, Integer> sScriptIdsForSubtypes = - new HashMap<>(); - public static int getScriptId(final Resources resources, final InputMethodSubtype subtype) { - final Integer value = sScriptIdsForSubtypes.get(subtype); - if (null == value) { - final int scriptId = readScriptId(resources, subtype); - sScriptIdsForSubtypes.put(subtype, scriptId); - return scriptId; - } - return value; - } - // Super redux version of reading the script ID for some subtype from Xml. - private static int readScriptId(final Resources resources, - final InputMethodSubtype subtype) { + static int readScriptId(final Resources resources, final InputMethodSubtype subtype) { final String layoutSetName = KEYBOARD_LAYOUT_SET_RESOURCE_PREFIX + SubtypeLocaleUtils.getKeyboardLayoutSetName(subtype); final int xmlId = getXmlId(resources, layoutSetName); @@ -414,7 +411,7 @@ public final class KeyboardLayoutSet { if (TAG_ELEMENT.equals(tag)) { parseKeyboardLayoutSetElement(parser); } else if (TAG_FEATURE.equals(tag)) { - parseKeyboardLayoutSetFeature(parser); + mParams.mScriptId = readScriptIdFromTagFeature(mResources, parser); } else { throw new XmlParseUtils.IllegalStartTag(parser, tag, TAG_KEYBOARD_SET); } @@ -459,12 +456,6 @@ public final class KeyboardLayoutSet { } } - private void parseKeyboardLayoutSetFeature(final XmlPullParser parser) - throws XmlPullParserException, IOException { - final int scriptId = readScriptIdFromTagFeature(mResources, parser); - setScriptId(scriptId); - } - private static int getKeyboardMode(final EditorInfo editorInfo) { final int inputType = editorInfo.inputType; final int variation = inputType & InputType.TYPE_MASK_VARIATION; diff --git a/java/src/com/android/inputmethod/keyboard/KeyboardSwitcher.java b/java/src/com/android/inputmethod/keyboard/KeyboardSwitcher.java index c2862f59d..5e3a5f17c 100644 --- a/java/src/com/android/inputmethod/keyboard/KeyboardSwitcher.java +++ b/java/src/com/android/inputmethod/keyboard/KeyboardSwitcher.java @@ -114,7 +114,7 @@ public final class KeyboardSwitcher implements KeyboardState.SwitchActions { final int keyboardWidth = ResourceUtils.getDefaultKeyboardWidth(res); final int keyboardHeight = ResourceUtils.getKeyboardHeight(res, settingsValues); builder.setKeyboardGeometry(keyboardWidth, keyboardHeight); - builder.setSubtype(mSubtypeSwitcher.getCurrentSubtype()); + builder.setSubtype(RichInputMethodManager.getInstance().getCurrentSubtype()); builder.setVoiceInputKeyEnabled(settingsValues.mShowsVoiceInputKey); builder.setLanguageSwitchKeyEnabled(mLatinIME.shouldShowLanguageSwitchKey()); builder.setSplitLayoutEnabledByUser(ProductionFlags.IS_SPLIT_KEYBOARD_SUPPORTED @@ -123,7 +123,8 @@ public final class KeyboardSwitcher implements KeyboardState.SwitchActions { try { mState.onLoadKeyboard(currentAutoCapsState, currentRecapitalizeState); // TODO: revisit this for multi-lingual input - mKeyboardTextsSet.setLocale(mSubtypeSwitcher.getCurrentSubtypeLocales()[0], + mKeyboardTextsSet.setLocale( + RichInputMethodManager.getInstance().getCurrentSubtypeLocales()[0], mThemeContext); } catch (KeyboardLayoutSetException e) { Log.w(TAG, "loading keyboard failed: " + e.mKeyboardId, e.getCause()); @@ -163,7 +164,7 @@ public final class KeyboardSwitcher implements KeyboardState.SwitchActions { currentSettingsValues.mKeyPreviewDismissEndXScale, currentSettingsValues.mKeyPreviewDismissEndYScale, currentSettingsValues.mKeyPreviewDismissDuration); - keyboardView.updateShortcutKey(mSubtypeSwitcher.isShortcutImeReady()); + keyboardView.updateShortcutKey(RichInputMethodManager.getInstance().isShortcutImeReady()); final boolean subtypeChanged = (oldKeyboard == null) || !keyboard.mId.mSubtype.equals(oldKeyboard.mId.mSubtype); final int languageOnSpacebarFormatType = mSubtypeSwitcher.getLanguageOnSpacebarFormatType( @@ -414,9 +415,10 @@ public final class KeyboardSwitcher implements KeyboardState.SwitchActions { } public void onNetworkStateChanged() { - if (mKeyboardView != null) { - mKeyboardView.updateShortcutKey(mSubtypeSwitcher.isShortcutImeReady()); + if (mKeyboardView == null) { + return; } + mKeyboardView.updateShortcutKey(RichInputMethodManager.getInstance().isShortcutImeReady()); } public int getKeyboardShiftMode() { diff --git a/java/src/com/android/inputmethod/keyboard/MainKeyboardView.java b/java/src/com/android/inputmethod/keyboard/MainKeyboardView.java index 1bad7cbb6..cba7ff2a2 100644 --- a/java/src/com/android/inputmethod/keyboard/MainKeyboardView.java +++ b/java/src/com/android/inputmethod/keyboard/MainKeyboardView.java @@ -56,9 +56,9 @@ import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.RichInputMethodSubtype; import com.android.inputmethod.latin.SuggestedWords; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.common.StringUtils; import com.android.inputmethod.latin.settings.DebugSettings; -import com.android.inputmethod.latin.utils.CoordinateUtils; import com.android.inputmethod.latin.utils.TypefaceUtils; import java.util.Locale; diff --git a/java/src/com/android/inputmethod/keyboard/MoreKeysKeyboardView.java b/java/src/com/android/inputmethod/keyboard/MoreKeysKeyboardView.java index 01522536f..3acc11b59 100644 --- a/java/src/com/android/inputmethod/keyboard/MoreKeysKeyboardView.java +++ b/java/src/com/android/inputmethod/keyboard/MoreKeysKeyboardView.java @@ -31,7 +31,7 @@ import com.android.inputmethod.accessibility.MoreKeysKeyboardAccessibilityDelega import com.android.inputmethod.keyboard.internal.KeyDrawParams; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.common.Constants; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; /** * A view that renders a virtual {@link MoreKeysKeyboard}. It handles rendering of keys and diff --git a/java/src/com/android/inputmethod/keyboard/PointerTracker.java b/java/src/com/android/inputmethod/keyboard/PointerTracker.java index 41eb87f81..7902ce852 100644 --- a/java/src/com/android/inputmethod/keyboard/PointerTracker.java +++ b/java/src/com/android/inputmethod/keyboard/PointerTracker.java @@ -35,10 +35,10 @@ import com.android.inputmethod.keyboard.internal.TimerProxy; import com.android.inputmethod.keyboard.internal.TypingTimeRecorder; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.common.InputPointers; import com.android.inputmethod.latin.define.DebugFlags; import com.android.inputmethod.latin.settings.Settings; -import com.android.inputmethod.latin.utils.CoordinateUtils; import com.android.inputmethod.latin.utils.ResourceUtils; import java.util.ArrayList; diff --git a/java/src/com/android/inputmethod/keyboard/internal/DrawingPreviewPlacerView.java b/java/src/com/android/inputmethod/keyboard/internal/DrawingPreviewPlacerView.java index a5d47adb3..9c0d7436b 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/DrawingPreviewPlacerView.java +++ b/java/src/com/android/inputmethod/keyboard/internal/DrawingPreviewPlacerView.java @@ -24,7 +24,7 @@ import android.graphics.PorterDuffXfermode; import android.util.AttributeSet; import android.widget.RelativeLayout; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; import java.util.ArrayList; diff --git a/java/src/com/android/inputmethod/keyboard/internal/GestureFloatingTextDrawingPreview.java b/java/src/com/android/inputmethod/keyboard/internal/GestureFloatingTextDrawingPreview.java index 330ec52f0..5443c2a8c 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/GestureFloatingTextDrawingPreview.java +++ b/java/src/com/android/inputmethod/keyboard/internal/GestureFloatingTextDrawingPreview.java @@ -27,7 +27,7 @@ import android.text.TextUtils; import com.android.inputmethod.keyboard.PointerTracker; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.SuggestedWords; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; import javax.annotation.Nonnull; diff --git a/java/src/com/android/inputmethod/keyboard/internal/KeyPreviewChoreographer.java b/java/src/com/android/inputmethod/keyboard/internal/KeyPreviewChoreographer.java index d3764877c..448f1b4b1 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/KeyPreviewChoreographer.java +++ b/java/src/com/android/inputmethod/keyboard/internal/KeyPreviewChoreographer.java @@ -23,7 +23,7 @@ import android.view.View; import android.view.ViewGroup; import com.android.inputmethod.keyboard.Key; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.utils.ViewLayoutUtils; import java.util.ArrayDeque; diff --git a/java/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelper.java b/java/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelper.java index 21eaed950..2a70ef51a 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelper.java +++ b/java/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelper.java @@ -25,6 +25,8 @@ import java.util.Collections; import java.util.List; import java.util.Locale; +import javax.annotation.Nonnull; + /** * This class determines that the language name on the spacebar should be displayed in what format. */ @@ -37,7 +39,7 @@ public final class LanguageOnSpacebarHelper { private List<InputMethodSubtype> mEnabledSubtypes = Collections.emptyList(); private boolean mIsSystemLanguageSameAsInputLanguage; - public int getLanguageOnSpacebarFormatType(final RichInputMethodSubtype subtype) { + public int getLanguageOnSpacebarFormatType(@Nonnull final RichInputMethodSubtype subtype) { if (subtype.isNoLanguage()) { return FORMAT_TYPE_FULL_LOCALE; } @@ -65,11 +67,30 @@ public final class LanguageOnSpacebarHelper { : FORMAT_TYPE_LANGUAGE_ONLY; } - public void updateEnabledSubtypes(final List<InputMethodSubtype> enabledSubtypes) { + public void onUpdateEnabledSubtypes(@Nonnull final List<InputMethodSubtype> enabledSubtypes) { mEnabledSubtypes = enabledSubtypes; } - public void updateIsSystemLanguageSameAsInputLanguage(final boolean isSame) { - mIsSystemLanguageSameAsInputLanguage = isSame; + public void onSubtypeChanged(@Nonnull final RichInputMethodSubtype subtype, + final boolean implicitlyEnabledSubtype, @Nonnull final Locale systemLocale) { + final Locale[] newLocales = subtype.getLocales(); + if (newLocales.length > 1) { + // In multi-locales mode, the system language is never the same as the input language + // because there is no single input language. + mIsSystemLanguageSameAsInputLanguage = false; + return; + } + final Locale newLocale = newLocales[0]; + if (systemLocale.equals(newLocale)) { + mIsSystemLanguageSameAsInputLanguage = true; + return; + } + if (!systemLocale.getLanguage().equals(newLocale.getLanguage())) { + mIsSystemLanguageSameAsInputLanguage = false; + return; + } + // If the subtype is enabled explicitly, the language name should be displayed even when + // the keyboard language and the system language are equal. + mIsSystemLanguageSameAsInputLanguage = implicitlyEnabledSubtype; } } diff --git a/java/src/com/android/inputmethod/keyboard/internal/MoreKeySpec.java b/java/src/com/android/inputmethod/keyboard/internal/MoreKeySpec.java index a0bb406aa..b1a3887d8 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/MoreKeySpec.java +++ b/java/src/com/android/inputmethod/keyboard/internal/MoreKeySpec.java @@ -21,10 +21,10 @@ import android.util.SparseIntArray; import com.android.inputmethod.compat.CharacterCompat; import com.android.inputmethod.keyboard.Key; +import com.android.inputmethod.latin.common.CollectionUtils; import com.android.inputmethod.latin.common.Constants; import com.android.inputmethod.latin.common.StringUtils; import com.android.inputmethod.latin.define.DebugFlags; -import com.android.inputmethod.latin.utils.CollectionUtils; import java.util.ArrayList; import java.util.Arrays; diff --git a/java/src/com/android/inputmethod/keyboard/internal/NonDistinctMultitouchHelper.java b/java/src/com/android/inputmethod/keyboard/internal/NonDistinctMultitouchHelper.java index 3a9aa81a3..8a375c620 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/NonDistinctMultitouchHelper.java +++ b/java/src/com/android/inputmethod/keyboard/internal/NonDistinctMultitouchHelper.java @@ -22,7 +22,7 @@ import android.view.MotionEvent; import com.android.inputmethod.keyboard.Key; import com.android.inputmethod.keyboard.KeyDetector; import com.android.inputmethod.keyboard.PointerTracker; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; public final class NonDistinctMultitouchHelper { private static final String TAG = NonDistinctMultitouchHelper.class.getSimpleName(); diff --git a/java/src/com/android/inputmethod/keyboard/internal/SlidingKeyInputDrawingPreview.java b/java/src/com/android/inputmethod/keyboard/internal/SlidingKeyInputDrawingPreview.java index ef4c74d61..73a6f9516 100644 --- a/java/src/com/android/inputmethod/keyboard/internal/SlidingKeyInputDrawingPreview.java +++ b/java/src/com/android/inputmethod/keyboard/internal/SlidingKeyInputDrawingPreview.java @@ -23,7 +23,7 @@ import android.graphics.Path; import com.android.inputmethod.keyboard.PointerTracker; import com.android.inputmethod.latin.R; -import com.android.inputmethod.latin.utils.CoordinateUtils; +import com.android.inputmethod.latin.common.CoordinateUtils; /** * Draw rubber band preview graphics during sliding key input. diff --git a/java/src/com/android/inputmethod/latin/AssetFileAddress.java b/java/src/com/android/inputmethod/latin/AssetFileAddress.java index fd6c24dfe..923f43cbe 100644 --- a/java/src/com/android/inputmethod/latin/AssetFileAddress.java +++ b/java/src/com/android/inputmethod/latin/AssetFileAddress.java @@ -16,7 +16,7 @@ package com.android.inputmethod.latin; -import com.android.inputmethod.latin.utils.FileUtils; +import com.android.inputmethod.latin.common.FileUtils; import java.io.File; diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionary.java b/java/src/com/android/inputmethod/latin/BinaryDictionary.java index b5d0b446f..46cd3b8b2 100644 --- a/java/src/com/android/inputmethod/latin/BinaryDictionary.java +++ b/java/src/com/android/inputmethod/latin/BinaryDictionary.java @@ -24,6 +24,7 @@ import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.common.ComposedData; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.FileUtils; import com.android.inputmethod.latin.common.InputPointers; import com.android.inputmethod.latin.common.StringUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; @@ -33,7 +34,6 @@ import com.android.inputmethod.latin.makedict.UnsupportedFormatException; import com.android.inputmethod.latin.makedict.WordProperty; import com.android.inputmethod.latin.settings.SettingsValuesForSuggestion; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; -import com.android.inputmethod.latin.utils.FileUtils; import com.android.inputmethod.latin.utils.JniUtils; import com.android.inputmethod.latin.utils.WordInputEventForPersonalization; diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java b/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java index 1570bdae0..46c8d5562 100644 --- a/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java +++ b/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java @@ -21,11 +21,11 @@ import android.content.SharedPreferences; import android.content.res.AssetFileDescriptor; import android.util.Log; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; import com.android.inputmethod.latin.makedict.UnsupportedFormatException; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; import com.android.inputmethod.latin.utils.DictionaryInfoUtils; -import com.android.inputmethod.latin.utils.LocaleUtils; import java.io.File; import java.io.IOException; diff --git a/java/src/com/android/inputmethod/latin/DicTraverseSession.java b/java/src/com/android/inputmethod/latin/DicTraverseSession.java index 95390aa9f..aefefd305 100644 --- a/java/src/com/android/inputmethod/latin/DicTraverseSession.java +++ b/java/src/com/android/inputmethod/latin/DicTraverseSession.java @@ -17,7 +17,8 @@ package com.android.inputmethod.latin; import com.android.inputmethod.latin.common.Constants; -import com.android.inputmethod.latin.settings.NativeSuggestOptions; +import com.android.inputmethod.latin.common.NativeSuggestOptions; +import com.android.inputmethod.latin.settings.AdditionalFeaturesSettingUtils; import com.android.inputmethod.latin.utils.JniUtils; import java.util.Locale; @@ -43,7 +44,8 @@ public final class DicTraverseSession { public final int[] mOutputAutoCommitFirstWordConfidence = new int[1]; public final float[] mInputOutputWeightOfLangModelVsSpatialModel = new float[1]; - public final NativeSuggestOptions mNativeSuggestOptions = new NativeSuggestOptions(); + public final NativeSuggestOptions mNativeSuggestOptions = new NativeSuggestOptions( + AdditionalFeaturesSettingUtils.ADDITIONAL_FEATURES_SETTINGS_SIZE); private static native long setDicTraverseSessionNative(String locale, long dictSize); private static native void initDicTraverseSessionNative(long nativeDicTraverseSession, diff --git a/java/src/com/android/inputmethod/latin/ExpandableBinaryDictionary.java b/java/src/com/android/inputmethod/latin/ExpandableBinaryDictionary.java index b47eaa9bb..d9d22e0fc 100644 --- a/java/src/com/android/inputmethod/latin/ExpandableBinaryDictionary.java +++ b/java/src/com/android/inputmethod/latin/ExpandableBinaryDictionary.java @@ -23,6 +23,7 @@ import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.common.ComposedData; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.FileUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; import com.android.inputmethod.latin.makedict.FormatSpec; import com.android.inputmethod.latin.makedict.UnsupportedFormatException; @@ -32,7 +33,6 @@ import com.android.inputmethod.latin.utils.AsyncResultHolder; import com.android.inputmethod.latin.utils.CombinedFormatUtils; import com.android.inputmethod.latin.utils.DistracterFilter; import com.android.inputmethod.latin.utils.ExecutorUtils; -import com.android.inputmethod.latin.utils.FileUtils; import com.android.inputmethod.latin.utils.WordInputEventForPersonalization; import java.io.File; diff --git a/java/src/com/android/inputmethod/latin/LatinIME.java b/java/src/com/android/inputmethod/latin/LatinIME.java index eb0037e8c..719656b07 100644 --- a/java/src/com/android/inputmethod/latin/LatinIME.java +++ b/java/src/com/android/inputmethod/latin/LatinIME.java @@ -77,6 +77,7 @@ import com.android.inputmethod.keyboard.TextDecoratorUi; import com.android.inputmethod.latin.Suggest.OnGetSuggestedWordsCallback; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.common.InputPointers; import com.android.inputmethod.latin.define.DebugFlags; import com.android.inputmethod.latin.define.ProductionFlags; @@ -93,7 +94,6 @@ import com.android.inputmethod.latin.suggestions.SuggestionStripViewAccessor; import com.android.inputmethod.latin.touchinputconsumer.GestureConsumer; import com.android.inputmethod.latin.utils.ApplicationUtils; import com.android.inputmethod.latin.utils.CapsModeUtils; -import com.android.inputmethod.latin.utils.CoordinateUtils; import com.android.inputmethod.latin.utils.CursorAnchorInfoUtils; import com.android.inputmethod.latin.utils.DialogUtils; import com.android.inputmethod.latin.utils.ImportantNoticeUtils; @@ -603,7 +603,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen // Has to be package-visible for unit tests @UsedForTesting void loadSettings() { - final Locale[] locales = mSubtypeSwitcher.getCurrentSubtypeLocales(); + final Locale[] locales = mRichImm.getCurrentSubtypeLocales(); final EditorInfo editorInfo = getCurrentInputEditorInfo(); final InputAttributes inputAttributes = new InputAttributes( editorInfo, isFullscreenMode(), getPackageName()); @@ -657,7 +657,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen } void resetDictionaryFacilitatorIfNecessary() { - final Locale[] subtypeSwitcherLocales = mSubtypeSwitcher.getCurrentSubtypeLocales(); + final Locale[] subtypeSwitcherLocales = mRichImm.getCurrentSubtypeLocales(); if (mDictionaryFacilitator.isForLocales(subtypeSwitcherLocales)) { return; } @@ -909,7 +909,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen // Update to a gesture consumer with the current editor and IME state. mGestureConsumer = GestureConsumer.newInstance(editorInfo, mInputLogic.getPrivateCommandPerformer(), - Arrays.asList(mSubtypeSwitcher.getCurrentSubtypeLocales()), + Arrays.asList(mRichImm.getCurrentSubtypeLocales()), switcher.getKeyboard()); // Forward this event to the accessibility utilities, if enabled. @@ -947,7 +947,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen // span, so we should reset our state unconditionally, even if restarting is true. // We also tell the input logic about the combining rules for the current subtype, so // it can adjust its combiners if needed. - mInputLogic.startInput(mSubtypeSwitcher.getCombiningRulesExtraValueOfCurrentSubtype(), + mInputLogic.startInput(mRichImm.getCombiningRulesExtraValueOfCurrentSubtype(), currentSettingsValues); resetDictionaryFacilitatorIfNecessary(); @@ -1424,7 +1424,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen // completely replace #onCodeInput. public void onEvent(@Nonnull final Event event) { if (Constants.CODE_SHORTCUT == event.mKeyCode) { - mSubtypeSwitcher.switchToShortcutIME(this); + mRichImm.switchToShortcutIME(this); } final InputTransaction completeInputTransaction = mInputLogic.onCodeInput(mSettings.getCurrent(), event, @@ -1468,7 +1468,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen public void onStartBatchInput() { mInputLogic.onStartBatchInput(mSettings.getCurrent(), mKeyboardSwitcher, mHandler); mGestureConsumer.onGestureStarted( - Arrays.asList(mSubtypeSwitcher.getCurrentSubtypeLocales()), + Arrays.asList(mRichImm.getCurrentSubtypeLocales()), mKeyboardSwitcher.getKeyboard()); } @@ -1590,7 +1590,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen // We should clear the contextual strip if there is no suggestion from dictionaries. || noSuggestionsFromDictionaries) { mSuggestionStripView.setSuggestions(suggestedWords, - mSubtypeSwitcher.getCurrentSubtype().isRtlSubtype()); + mRichImm.getCurrentSubtype().isRtlSubtype()); } } @@ -1811,7 +1811,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen public void onReceive(final Context context, final Intent intent) { final String action = intent.getAction(); if (action.equals(ConnectivityManager.CONNECTIVITY_ACTION)) { - mSubtypeSwitcher.onNetworkStateChanged(intent); + mRichImm.onNetworkStateChanged(intent); } else if (action.equals(AudioManager.RINGER_MODE_CHANGED_ACTION)) { AudioAndHapticFeedbackManager.getInstance().onRingerModeChanged(); } diff --git a/java/src/com/android/inputmethod/latin/RichInputMethodManager.java b/java/src/com/android/inputmethod/latin/RichInputMethodManager.java index a53837a59..a1ac55a20 100644 --- a/java/src/com/android/inputmethod/latin/RichInputMethodManager.java +++ b/java/src/com/android/inputmethod/latin/RichInputMethodManager.java @@ -17,9 +17,15 @@ package com.android.inputmethod.latin; import static com.android.inputmethod.latin.common.Constants.Subtype.KEYBOARD_MODE; +import static com.android.inputmethod.latin.common.Constants.Subtype.ExtraValue.REQ_NETWORK_CONNECTIVITY; import android.content.Context; +import android.content.Intent; import android.content.SharedPreferences; +import android.inputmethodservice.InputMethodService; +import android.net.ConnectivityManager; +import android.net.NetworkInfo; +import android.os.AsyncTask; import android.os.Build; import android.os.IBinder; import android.preference.PreferenceManager; @@ -28,9 +34,9 @@ import android.view.inputmethod.InputMethodInfo; import android.view.inputmethod.InputMethodManager; import android.view.inputmethod.InputMethodSubtype; +import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.compat.InputMethodManagerCompatWrapper; -import com.android.inputmethod.compat.InputMethodSubtypeCompatUtils; -import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.keyboard.KeyboardSwitcher; import com.android.inputmethod.latin.settings.AdditionalFeaturesSettingUtils; import com.android.inputmethod.latin.settings.Settings; import com.android.inputmethod.latin.utils.AdditionalSubtypeUtils; @@ -41,6 +47,7 @@ import java.util.HashMap; import java.util.HashSet; import java.util.List; import java.util.Locale; +import java.util.Map; import java.util.Set; import javax.annotation.Nonnull; @@ -51,6 +58,7 @@ import javax.annotation.Nonnull; // non final for easy mocking. public class RichInputMethodManager { private static final String TAG = RichInputMethodManager.class.getSimpleName(); + private static final boolean DEBUG = false; private RichInputMethodManager() { // This utility class is not publicly instantiable. @@ -61,6 +69,10 @@ public class RichInputMethodManager { private Context mContext; private InputMethodManagerCompatWrapper mImmWrapper; private InputMethodInfoCache mInputMethodInfoCache; + private RichInputMethodSubtype mCurrentRichInputMethodSubtype; + private InputMethodInfo mShortcutInputMethodInfo; + private InputMethodSubtype mShortcutSubtype; + private boolean mIsNetworkConnected; final HashMap<InputMethodInfo, List<InputMethodSubtype>> mSubtypeListCacheWithImplicitlySelectedSubtypes = new HashMap<>(); final HashMap<InputMethodInfo, List<InputMethodSubtype>> @@ -100,6 +112,11 @@ public class RichInputMethodManager { SubtypeLocaleUtils.init(context); final InputMethodSubtype[] additionalSubtypes = getAdditionalSubtypes(context); setAdditionalInputMethodSubtypes(additionalSubtypes); + + final ConnectivityManager connectivityManager = + (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); + final NetworkInfo info = connectivityManager.getActiveNetworkInfo(); + mIsNetworkConnected = (info != null && info.isConnected()); } public InputMethodSubtype[] getAdditionalSubtypes(final Context context) { @@ -309,10 +326,47 @@ public class RichInputMethodManager { } @Nonnull + public RichInputMethodSubtype onSubtypeChanged(@Nonnull final InputMethodSubtype newSubtype) { + final RichInputMethodSubtype richSubtype = createCurrentRichInputMethodSubtype(newSubtype); + if (DEBUG) { + Log.w(TAG, "onSubtypeChanged: " + richSubtype.getNameForLogging()); + } + mCurrentRichInputMethodSubtype = richSubtype; + return richSubtype; + } + + private static RichInputMethodSubtype sForcedSubtypeForTesting = null; + + @UsedForTesting + static void forceSubtype(final InputMethodSubtype subtype) { + sForcedSubtypeForTesting = new RichInputMethodSubtype(subtype); + } + + public Locale[] getCurrentSubtypeLocales() { + if (null != sForcedSubtypeForTesting) { + return sForcedSubtypeForTesting.getLocales(); + } + return getCurrentSubtype().getLocales(); + } + + public RichInputMethodSubtype getCurrentSubtype() { + if (null != sForcedSubtypeForTesting) { + return sForcedSubtypeForTesting; + } + return mCurrentRichInputMethodSubtype; + } + + + public String getCombiningRulesExtraValueOfCurrentSubtype() { + return SubtypeLocaleUtils.getCombiningRulesExtraValue(getCurrentSubtype().getRawSubtype()); + } + + @Nonnull public InputMethodSubtype getCurrentRawSubtype() { return mImmWrapper.mImm.getCurrentInputMethodSubtype(); } + @Nonnull public RichInputMethodSubtype createCurrentRichInputMethodSubtype( @Nonnull final InputMethodSubtype rawSubtype) { return AdditionalFeaturesSettingUtils.createRichInputMethodSubtype(this, rawSubtype, @@ -462,4 +516,96 @@ public class RichInputMethodManager { } return true; } + + // TODO: Make this private + void updateShortcutIME() { + if (DEBUG) { + Log.d(TAG, "Update shortcut IME from : " + + (mShortcutInputMethodInfo == null + ? "<null>" : mShortcutInputMethodInfo.getId()) + ", " + + (mShortcutSubtype == null ? "<null>" : ( + mShortcutSubtype.getLocale() + ", " + mShortcutSubtype.getMode()))); + } + // TODO: Update an icon for shortcut IME + final Map<InputMethodInfo, List<InputMethodSubtype>> shortcuts = + getInputMethodManager().getShortcutInputMethodsAndSubtypes(); + mShortcutInputMethodInfo = null; + mShortcutSubtype = null; + for (final InputMethodInfo imi : shortcuts.keySet()) { + final List<InputMethodSubtype> subtypes = shortcuts.get(imi); + // TODO: Returns the first found IMI for now. Should handle all shortcuts as + // appropriate. + mShortcutInputMethodInfo = imi; + // TODO: Pick up the first found subtype for now. Should handle all subtypes + // as appropriate. + mShortcutSubtype = subtypes.size() > 0 ? subtypes.get(0) : null; + break; + } + if (DEBUG) { + Log.d(TAG, "Update shortcut IME to : " + + (mShortcutInputMethodInfo == null + ? "<null>" : mShortcutInputMethodInfo.getId()) + ", " + + (mShortcutSubtype == null ? "<null>" : ( + mShortcutSubtype.getLocale() + ", " + mShortcutSubtype.getMode()))); + } + } + + public void switchToShortcutIME(final InputMethodService context) { + if (mShortcutInputMethodInfo == null) { + return; + } + + final String imiId = mShortcutInputMethodInfo.getId(); + switchToTargetIME(imiId, mShortcutSubtype, context); + } + + private void switchToTargetIME(final String imiId, final InputMethodSubtype subtype, + final InputMethodService context) { + final IBinder token = context.getWindow().getWindow().getAttributes().token; + if (token == null) { + return; + } + final InputMethodManager imm = getInputMethodManager(); + new AsyncTask<Void, Void, Void>() { + @Override + protected Void doInBackground(Void... params) { + imm.setInputMethodAndSubtype(token, imiId, subtype); + return null; + } + }.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR); + } + + public boolean isShortcutImeEnabled() { + updateShortcutIME(); + if (mShortcutInputMethodInfo == null) { + return false; + } + if (mShortcutSubtype == null) { + return true; + } + return checkIfSubtypeBelongsToImeAndEnabled( + mShortcutInputMethodInfo, mShortcutSubtype); + } + + public boolean isShortcutImeReady() { + updateShortcutIME(); + if (mShortcutInputMethodInfo == null) { + return false; + } + if (mShortcutSubtype == null) { + return true; + } + if (mShortcutSubtype.containsExtraValueKey(REQ_NETWORK_CONNECTIVITY)) { + return mIsNetworkConnected; + } + return true; + } + + public void onNetworkStateChanged(final Intent intent) { + final boolean noConnection = intent.getBooleanExtra( + ConnectivityManager.EXTRA_NO_CONNECTIVITY, false); + mIsNetworkConnected = !noConnection; + + KeyboardSwitcher.getInstance().onNetworkStateChanged(); + } } diff --git a/java/src/com/android/inputmethod/latin/RichInputMethodSubtype.java b/java/src/com/android/inputmethod/latin/RichInputMethodSubtype.java index 1a6c6ba06..03f6d60ab 100644 --- a/java/src/com/android/inputmethod/latin/RichInputMethodSubtype.java +++ b/java/src/com/android/inputmethod/latin/RichInputMethodSubtype.java @@ -23,7 +23,7 @@ import android.view.inputmethod.InputMethodSubtype; import com.android.inputmethod.compat.InputMethodSubtypeCompatUtils; import com.android.inputmethod.latin.common.Constants; -import com.android.inputmethod.latin.utils.LocaleUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.utils.SubtypeLocaleUtils; import java.util.Arrays; diff --git a/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java b/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java index 306ccf0d0..23e348bff 100644 --- a/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java +++ b/java/src/com/android/inputmethod/latin/SubtypeSwitcher.java @@ -16,37 +16,18 @@ package com.android.inputmethod.latin; -import static com.android.inputmethod.latin.common.Constants.Subtype.ExtraValue.REQ_NETWORK_CONNECTIVITY; - import android.content.Context; -import android.content.Intent; import android.content.res.Resources; -import android.inputmethodservice.InputMethodService; -import android.net.ConnectivityManager; -import android.net.NetworkInfo; -import android.os.AsyncTask; -import android.os.IBinder; -import android.util.Log; -import android.view.inputmethod.InputMethodInfo; -import android.view.inputmethod.InputMethodManager; import android.view.inputmethod.InputMethodSubtype; -import com.android.inputmethod.annotations.UsedForTesting; -import com.android.inputmethod.keyboard.KeyboardSwitcher; import com.android.inputmethod.keyboard.internal.LanguageOnSpacebarHelper; -import com.android.inputmethod.latin.define.DebugFlags; import com.android.inputmethod.latin.utils.SubtypeLocaleUtils; import java.util.List; -import java.util.Locale; -import java.util.Map; import javax.annotation.Nonnull; public final class SubtypeSwitcher { - private static boolean DBG = DebugFlags.DEBUG_ENABLED; - private static final String TAG = SubtypeSwitcher.class.getSimpleName(); - private static final SubtypeSwitcher sInstance = new SubtypeSwitcher(); private /* final */ RichInputMethodManager mRichImm; @@ -54,10 +35,6 @@ public final class SubtypeSwitcher { private final LanguageOnSpacebarHelper mLanguageOnSpacebarHelper = new LanguageOnSpacebarHelper(); - private InputMethodInfo mShortcutInputMethodInfo; - private InputMethodSubtype mShortcutSubtype; - private RichInputMethodSubtype mCurrentRichInputMethodSubtype; - private boolean mIsNetworkConnected; public static SubtypeSwitcher getInstance() { return sInstance; @@ -79,11 +56,6 @@ public final class SubtypeSwitcher { } mResources = context.getResources(); mRichImm = RichInputMethodManager.getInstance(); - ConnectivityManager connectivityManager = (ConnectivityManager) context.getSystemService( - Context.CONNECTIVITY_SERVICE); - - final NetworkInfo info = connectivityManager.getActiveNetworkInfo(); - mIsNetworkConnected = (info != null && info.isConnected()); onSubtypeChanged(mRichImm.getCurrentRawSubtype()); updateParametersOnStartInputView(); @@ -96,161 +68,21 @@ public final class SubtypeSwitcher { public void updateParametersOnStartInputView() { final List<InputMethodSubtype> enabledSubtypesOfThisIme = mRichImm.getMyEnabledInputMethodSubtypeList(true); - mLanguageOnSpacebarHelper.updateEnabledSubtypes(enabledSubtypesOfThisIme); - updateShortcutIME(); - } - - private void updateShortcutIME() { - if (DBG) { - Log.d(TAG, "Update shortcut IME from : " - + (mShortcutInputMethodInfo == null - ? "<null>" : mShortcutInputMethodInfo.getId()) + ", " - + (mShortcutSubtype == null ? "<null>" : ( - mShortcutSubtype.getLocale() + ", " + mShortcutSubtype.getMode()))); - } - // TODO: Update an icon for shortcut IME - final Map<InputMethodInfo, List<InputMethodSubtype>> shortcuts = - mRichImm.getInputMethodManager().getShortcutInputMethodsAndSubtypes(); - mShortcutInputMethodInfo = null; - mShortcutSubtype = null; - for (final InputMethodInfo imi : shortcuts.keySet()) { - final List<InputMethodSubtype> subtypes = shortcuts.get(imi); - // TODO: Returns the first found IMI for now. Should handle all shortcuts as - // appropriate. - mShortcutInputMethodInfo = imi; - // TODO: Pick up the first found subtype for now. Should handle all subtypes - // as appropriate. - mShortcutSubtype = subtypes.size() > 0 ? subtypes.get(0) : null; - break; - } - if (DBG) { - Log.d(TAG, "Update shortcut IME to : " - + (mShortcutInputMethodInfo == null - ? "<null>" : mShortcutInputMethodInfo.getId()) + ", " - + (mShortcutSubtype == null ? "<null>" : ( - mShortcutSubtype.getLocale() + ", " + mShortcutSubtype.getMode()))); - } + mLanguageOnSpacebarHelper.onUpdateEnabledSubtypes(enabledSubtypesOfThisIme); + mRichImm.updateShortcutIME(); } // Update the current subtype. LatinIME.onCurrentInputMethodSubtypeChanged calls this function. public void onSubtypeChanged(@Nonnull final InputMethodSubtype newSubtype) { - final RichInputMethodSubtype richSubtype = - mRichImm.createCurrentRichInputMethodSubtype(newSubtype); - if (DBG) { - Log.w(TAG, "onSubtypeChanged: " + richSubtype.getNameForLogging()); - } - mCurrentRichInputMethodSubtype = richSubtype; - final Locale[] newLocales = richSubtype.getLocales(); - if (newLocales.length > 1) { - // In multi-locales mode, the system language is never the same as the input language - // because there is no single input language. - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(false); - } else { - final Locale newLocale = newLocales[0]; - final Locale systemLocale = mResources.getConfiguration().locale; - final boolean sameLocale = systemLocale.equals(newLocale); - final boolean sameLanguage = systemLocale.getLanguage().equals(newLocale.getLanguage()); - final boolean implicitlyEnabled = mRichImm - .checkIfSubtypeBelongsToThisImeAndImplicitlyEnabled(newSubtype); - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage( - sameLocale || (sameLanguage && implicitlyEnabled)); - } - updateShortcutIME(); - } - - //////////////////////////// - // Shortcut IME functions // - //////////////////////////// - - public void switchToShortcutIME(final InputMethodService context) { - if (mShortcutInputMethodInfo == null) { - return; - } - - final String imiId = mShortcutInputMethodInfo.getId(); - switchToTargetIME(imiId, mShortcutSubtype, context); - } - - private void switchToTargetIME(final String imiId, final InputMethodSubtype subtype, - final InputMethodService context) { - final IBinder token = context.getWindow().getWindow().getAttributes().token; - if (token == null) { - return; - } - final InputMethodManager imm = mRichImm.getInputMethodManager(); - new AsyncTask<Void, Void, Void>() { - @Override - protected Void doInBackground(Void... params) { - imm.setInputMethodAndSubtype(token, imiId, subtype); - return null; - } - }.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR); - } - - public boolean isShortcutImeEnabled() { - updateShortcutIME(); - if (mShortcutInputMethodInfo == null) { - return false; - } - if (mShortcutSubtype == null) { - return true; - } - return mRichImm.checkIfSubtypeBelongsToImeAndEnabled( - mShortcutInputMethodInfo, mShortcutSubtype); + final RichInputMethodSubtype richSubtype = mRichImm.onSubtypeChanged(newSubtype); + final boolean implicitlyEnabledSubtype = mRichImm + .checkIfSubtypeBelongsToThisImeAndImplicitlyEnabled(newSubtype); + mLanguageOnSpacebarHelper.onSubtypeChanged( + richSubtype, implicitlyEnabledSubtype, mResources.getConfiguration().locale); + mRichImm.updateShortcutIME(); } - public boolean isShortcutImeReady() { - updateShortcutIME(); - if (mShortcutInputMethodInfo == null) { - return false; - } - if (mShortcutSubtype == null) { - return true; - } - if (mShortcutSubtype.containsExtraValueKey(REQ_NETWORK_CONNECTIVITY)) { - return mIsNetworkConnected; - } - return true; - } - - public void onNetworkStateChanged(final Intent intent) { - final boolean noConnection = intent.getBooleanExtra( - ConnectivityManager.EXTRA_NO_CONNECTIVITY, false); - mIsNetworkConnected = !noConnection; - - KeyboardSwitcher.getInstance().onNetworkStateChanged(); - } - - ////////////////////////////////// - // Subtype Switching functions // - ////////////////////////////////// - public int getLanguageOnSpacebarFormatType(final RichInputMethodSubtype subtype) { return mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(subtype); } - - private static RichInputMethodSubtype sForcedSubtypeForTesting = null; - - @UsedForTesting - static void forceSubtype(final InputMethodSubtype subtype) { - sForcedSubtypeForTesting = new RichInputMethodSubtype(subtype); - } - - public Locale[] getCurrentSubtypeLocales() { - if (null != sForcedSubtypeForTesting) { - return sForcedSubtypeForTesting.getLocales(); - } - return getCurrentSubtype().getLocales(); - } - - public RichInputMethodSubtype getCurrentSubtype() { - if (null != sForcedSubtypeForTesting) { - return sForcedSubtypeForTesting; - } - return mCurrentRichInputMethodSubtype; - } - - public String getCombiningRulesExtraValueOfCurrentSubtype() { - return SubtypeLocaleUtils.getCombiningRulesExtraValue(getCurrentSubtype().getRawSubtype()); - } } diff --git a/java/src/com/android/inputmethod/latin/Suggest.java b/java/src/com/android/inputmethod/latin/Suggest.java index 9b4619d35..ee8d3f8cb 100644 --- a/java/src/com/android/inputmethod/latin/Suggest.java +++ b/java/src/com/android/inputmethod/latin/Suggest.java @@ -230,7 +230,7 @@ public final class Suggest { inputStyle = inputStyleIfNotPrediction; } callback.onGetSuggestedWords(new SuggestedWords(suggestionsList, - suggestionResults.mRawSuggestions, + suggestionResults.mRawSuggestions, typedWord, // TODO: this first argument is lying. If this is a whitelisted word which is an // actual word, it says typedWordValid = false, which looks wrong. We should either // rename the attribute or change the value. @@ -286,8 +286,12 @@ public final class Suggest { // (typedWordValid=true), not as an "auto correct word" (willAutoCorrect=false). // Note that because this method is never used to get predictions, there is no need to // modify inputType such in getSuggestedWordsForNonBatchInput. + final String pseudoTypedWord = suggestionsContainer.isEmpty() ? null + : suggestionsContainer.get(0).mWord; + callback.onGetSuggestedWords(new SuggestedWords(suggestionsContainer, suggestionResults.mRawSuggestions, + pseudoTypedWord, true /* typedWordValid */, false /* willAutoCorrect */, false /* isObsoleteSuggestions */, diff --git a/java/src/com/android/inputmethod/latin/SuggestedWords.java b/java/src/com/android/inputmethod/latin/SuggestedWords.java index c51e20f21..bddeac495 100644 --- a/java/src/com/android/inputmethod/latin/SuggestedWords.java +++ b/java/src/com/android/inputmethod/latin/SuggestedWords.java @@ -73,21 +73,11 @@ public class SuggestedWords { final boolean willAutoCorrect, final boolean isObsoleteSuggestions, final int inputStyle) { - this(suggestedWordInfoList, rawSuggestions, typedWordValid, willAutoCorrect, - isObsoleteSuggestions, inputStyle, NOT_A_SEQUENCE_NUMBER); - } - - public SuggestedWords(final ArrayList<SuggestedWordInfo> suggestedWordInfoList, - final ArrayList<SuggestedWordInfo> rawSuggestions, - final boolean typedWordValid, - final boolean willAutoCorrect, - final boolean isObsoleteSuggestions, - final int inputStyle, - final int sequenceNumber) { this(suggestedWordInfoList, rawSuggestions, (suggestedWordInfoList.isEmpty() || isPrediction(inputStyle)) ? null : suggestedWordInfoList.get(INDEX_OF_TYPED_WORD).mWord, - typedWordValid, willAutoCorrect, isObsoleteSuggestions, inputStyle, sequenceNumber); + typedWordValid, willAutoCorrect, + isObsoleteSuggestions, inputStyle, NOT_A_SEQUENCE_NUMBER); } public SuggestedWords(final ArrayList<SuggestedWordInfo> suggestedWordInfoList, diff --git a/java/src/com/android/inputmethod/latin/WordComposer.java b/java/src/com/android/inputmethod/latin/WordComposer.java index fa55319d2..78860d87d 100644 --- a/java/src/com/android/inputmethod/latin/WordComposer.java +++ b/java/src/com/android/inputmethod/latin/WordComposer.java @@ -21,10 +21,10 @@ import com.android.inputmethod.event.Event; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.common.ComposedData; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.common.InputPointers; import com.android.inputmethod.latin.common.StringUtils; import com.android.inputmethod.latin.define.DebugFlags; -import com.android.inputmethod.latin.utils.CoordinateUtils; import java.util.ArrayList; import java.util.Collections; diff --git a/java/src/com/android/inputmethod/latin/debug/ExternalDictionaryGetterForDebug.java b/java/src/com/android/inputmethod/latin/debug/ExternalDictionaryGetterForDebug.java index d4be0e397..78bfd2b52 100644 --- a/java/src/com/android/inputmethod/latin/debug/ExternalDictionaryGetterForDebug.java +++ b/java/src/com/android/inputmethod/latin/debug/ExternalDictionaryGetterForDebug.java @@ -26,10 +26,10 @@ import android.os.Environment; import com.android.inputmethod.latin.BinaryDictionaryFileDumper; import com.android.inputmethod.latin.BinaryDictionaryGetter; import com.android.inputmethod.latin.R; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; import com.android.inputmethod.latin.utils.DialogUtils; import com.android.inputmethod.latin.utils.DictionaryInfoUtils; -import com.android.inputmethod.latin.utils.LocaleUtils; import java.io.BufferedInputStream; import java.io.BufferedOutputStream; diff --git a/java/src/com/android/inputmethod/latin/personalization/PersonalizationHelper.java b/java/src/com/android/inputmethod/latin/personalization/PersonalizationHelper.java index 331f85e0e..ac2fc07c2 100644 --- a/java/src/com/android/inputmethod/latin/personalization/PersonalizationHelper.java +++ b/java/src/com/android/inputmethod/latin/personalization/PersonalizationHelper.java @@ -19,7 +19,7 @@ package com.android.inputmethod.latin.personalization; import android.content.Context; import android.util.Log; -import com.android.inputmethod.latin.utils.FileUtils; +import com.android.inputmethod.latin.common.FileUtils; import java.io.File; import java.io.FilenameFilter; diff --git a/java/src/com/android/inputmethod/latin/settings/PreferencesSettingsFragment.java b/java/src/com/android/inputmethod/latin/settings/PreferencesSettingsFragment.java index 49db2bdc0..c0ceb8857 100644 --- a/java/src/com/android/inputmethod/latin/settings/PreferencesSettingsFragment.java +++ b/java/src/com/android/inputmethod/latin/settings/PreferencesSettingsFragment.java @@ -24,7 +24,7 @@ import android.preference.Preference; import com.android.inputmethod.latin.AudioAndHapticFeedbackManager; import com.android.inputmethod.latin.R; -import com.android.inputmethod.latin.SubtypeSwitcher; +import com.android.inputmethod.latin.RichInputMethodManager; /** * "Preferences" settings sub screen. @@ -49,7 +49,7 @@ public final class PreferencesSettingsFragment extends SubScreenFragment { // When we are called from the Settings application but we are not already running, some // singleton and utility classes may not have been initialized. We have to call // initialization method of these classes here. See {@link LatinIME#onCreate()}. - SubtypeSwitcher.init(context); + RichInputMethodManager.init(context); final boolean showVoiceKeyOption = res.getBoolean( R.bool.config_enable_show_voice_key_option); @@ -71,7 +71,7 @@ public final class PreferencesSettingsFragment extends SubScreenFragment { super.onResume(); final Preference voiceInputKeyOption = findPreference(Settings.PREF_VOICE_INPUT_KEY); if (voiceInputKeyOption != null) { - final boolean isShortcutImeEnabled = SubtypeSwitcher.getInstance() + final boolean isShortcutImeEnabled = RichInputMethodManager.getInstance() .isShortcutImeEnabled(); voiceInputKeyOption.setEnabled(isShortcutImeEnabled); voiceInputKeyOption.setSummary( diff --git a/java/src/com/android/inputmethod/latin/settings/SettingsValues.java b/java/src/com/android/inputmethod/latin/settings/SettingsValues.java index 509b41fd3..26415e7d4 100644 --- a/java/src/com/android/inputmethod/latin/settings/SettingsValues.java +++ b/java/src/com/android/inputmethod/latin/settings/SettingsValues.java @@ -28,7 +28,6 @@ import com.android.inputmethod.compat.AppWorkaroundsUtils; import com.android.inputmethod.latin.InputAttributes; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.RichInputMethodManager; -import com.android.inputmethod.latin.SubtypeSwitcher; import com.android.inputmethod.latin.utils.AsyncResultHolder; import com.android.inputmethod.latin.utils.ResourceUtils; import com.android.inputmethod.latin.utils.TargetPackageInfoGetterTask; @@ -140,7 +139,7 @@ public class SettingsValues { DebugSettings.PREF_SLIDING_KEY_INPUT_PREVIEW, true); mShowsVoiceInputKey = needsToShowVoiceInputKey(prefs, res) && mInputAttributes.mShouldShowVoiceInputKey - && SubtypeSwitcher.getInstance().isShortcutImeEnabled(); + && RichInputMethodManager.getInstance().isShortcutImeEnabled(); final String autoCorrectionThresholdRawValue = prefs.getString( Settings.PREF_AUTO_CORRECTION_THRESHOLD, res.getString(R.string.auto_correction_threshold_mode_index_modest)); diff --git a/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java b/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java index 3ad8fb910..c90e8a3cf 100644 --- a/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java +++ b/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java @@ -34,10 +34,10 @@ import com.android.inputmethod.latin.NgramContext; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.WordComposer; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.CoordinateUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.common.StringUtils; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; -import com.android.inputmethod.latin.utils.CoordinateUtils; -import com.android.inputmethod.latin.utils.LocaleUtils; import com.android.inputmethod.latin.utils.ScriptUtils; import com.android.inputmethod.latin.utils.SuggestionResults; diff --git a/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryAddWordContents.java b/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryAddWordContents.java index eda81940f..22fc35a42 100644 --- a/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryAddWordContents.java +++ b/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryAddWordContents.java @@ -28,7 +28,7 @@ import android.widget.EditText; import com.android.inputmethod.compat.UserDictionaryCompatUtils; import com.android.inputmethod.latin.R; -import com.android.inputmethod.latin.utils.LocaleUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import java.util.ArrayList; import java.util.Locale; diff --git a/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryList.java b/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryList.java index 90e4faafd..b9ed35375 100644 --- a/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryList.java +++ b/java/src/com/android/inputmethod/latin/userdictionary/UserDictionaryList.java @@ -31,7 +31,7 @@ import android.view.inputmethod.InputMethodManager; import android.view.inputmethod.InputMethodSubtype; import com.android.inputmethod.latin.R; -import com.android.inputmethod.latin.utils.LocaleUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import java.util.List; import java.util.Locale; diff --git a/java/src/com/android/inputmethod/latin/userdictionary/UserDictionarySettingsUtils.java b/java/src/com/android/inputmethod/latin/userdictionary/UserDictionarySettingsUtils.java index e58727ec4..c0a946e42 100644 --- a/java/src/com/android/inputmethod/latin/userdictionary/UserDictionarySettingsUtils.java +++ b/java/src/com/android/inputmethod/latin/userdictionary/UserDictionarySettingsUtils.java @@ -17,7 +17,7 @@ package com.android.inputmethod.latin.userdictionary; import com.android.inputmethod.latin.R; -import com.android.inputmethod.latin.utils.LocaleUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import android.content.Context; import android.text.TextUtils; diff --git a/java/src/com/android/inputmethod/latin/utils/DictionaryInfoUtils.java b/java/src/com/android/inputmethod/latin/utils/DictionaryInfoUtils.java index 24025b272..81c3e3c61 100644 --- a/java/src/com/android/inputmethod/latin/utils/DictionaryInfoUtils.java +++ b/java/src/com/android/inputmethod/latin/utils/DictionaryInfoUtils.java @@ -28,6 +28,7 @@ import com.android.inputmethod.latin.AssetFileAddress; import com.android.inputmethod.latin.BinaryDictionaryGetter; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; import com.android.inputmethod.latin.makedict.UnsupportedFormatException; import com.android.inputmethod.latin.settings.SpacingAndPunctuations; diff --git a/java/src/com/android/inputmethod/latin/utils/LocaleUtils.java b/java/src/com/android/inputmethod/latin/utils/LocaleUtils.java deleted file mode 100644 index 4bab497ba..000000000 --- a/java/src/com/android/inputmethod/latin/utils/LocaleUtils.java +++ /dev/null @@ -1,195 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.inputmethod.latin.utils; - -import android.text.TextUtils; - -import java.util.HashMap; -import java.util.Locale; - -import javax.annotation.Nullable; - -/** - * A class to help with handling Locales in string form. - * - * This file has the same meaning and features (and shares all of its code) with - * the one in the dictionary pack. They need to be kept synchronized; for any - * update/bugfix to this file, consider also updating/fixing the version in the - * dictionary pack. - */ -public final class LocaleUtils { - private LocaleUtils() { - // Intentional empty constructor for utility class. - } - - // Locale match level constants. - // A higher level of match is guaranteed to have a higher numerical value. - // Some room is left within constants to add match cases that may arise necessary - // in the future, for example differentiating between the case where the countries - // are both present and different, and the case where one of the locales does not - // specify the countries. This difference is not needed now. - - // Nothing matches. - public static final int LOCALE_NO_MATCH = 0; - // The languages matches, but the country are different. Or, the reference locale requires a - // country and the tested locale does not have one. - public static final int LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER = 3; - // The languages and country match, but the variants are different. Or, the reference locale - // requires a variant and the tested locale does not have one. - public static final int LOCALE_LANGUAGE_AND_COUNTRY_MATCH_VARIANT_DIFFER = 6; - // The required locale is null or empty so it will accept anything, and the tested locale - // is non-null and non-empty. - public static final int LOCALE_ANY_MATCH = 10; - // The language matches, and the tested locale specifies a country but the reference locale - // does not require one. - public static final int LOCALE_LANGUAGE_MATCH = 15; - // The language and the country match, and the tested locale specifies a variant but the - // reference locale does not require one. - public static final int LOCALE_LANGUAGE_AND_COUNTRY_MATCH = 20; - // The compared locales are fully identical. This is the best match level. - public static final int LOCALE_FULL_MATCH = 30; - - // The level at which a match is "normally" considered a locale match with standard algorithms. - // Don't use this directly, use #isMatch to test. - private static final int LOCALE_MATCH = LOCALE_ANY_MATCH; - - // Make this match the maximum match level. If this evolves to have more than 2 digits - // when written in base 10, also adjust the getMatchLevelSortedString method. - private static final int MATCH_LEVEL_MAX = 30; - - /** - * Return how well a tested locale matches a reference locale. - * - * This will check the tested locale against the reference locale and return a measure of how - * a well it matches the reference. The general idea is that the tested locale has to match - * every specified part of the required locale. A full match occur when they are equal, a - * partial match when the tested locale agrees with the reference locale but is more specific, - * and a difference when the tested locale does not comply with all requirements from the - * reference locale. - * In more detail, if the reference locale specifies at least a language and the testedLocale - * does not specify one, or specifies a different one, LOCALE_NO_MATCH is returned. If the - * reference locale is empty or null, it will match anything - in the form of LOCALE_FULL_MATCH - * if the tested locale is empty or null, and LOCALE_ANY_MATCH otherwise. If the reference and - * tested locale agree on the language, but not on the country, - * LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER is returned if the reference locale specifies a country, - * and LOCALE_LANGUAGE_MATCH otherwise. - * If they agree on both the language and the country, but not on the variant, - * LOCALE_LANGUAGE_AND_COUNTRY_MATCH_VARIANT_DIFFER is returned if the reference locale - * specifies a variant, and LOCALE_LANGUAGE_AND_COUNTRY_MATCH otherwise. If everything matches, - * LOCALE_FULL_MATCH is returned. - * Examples: - * en <=> en_US => LOCALE_LANGUAGE_MATCH - * en_US <=> en => LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER - * en_US_POSIX <=> en_US_Android => LOCALE_LANGUAGE_AND_COUNTRY_MATCH_VARIANT_DIFFER - * en_US <=> en_US_Android => LOCALE_LANGUAGE_AND_COUNTRY_MATCH - * sp_US <=> en_US => LOCALE_NO_MATCH - * de <=> de => LOCALE_FULL_MATCH - * en_US <=> en_US => LOCALE_FULL_MATCH - * "" <=> en_US => LOCALE_ANY_MATCH - * - * @param referenceLocale the reference locale to test against. - * @param testedLocale the locale to test. - * @return a constant that measures how well the tested locale matches the reference locale. - */ - public static int getMatchLevel(String referenceLocale, String testedLocale) { - if (TextUtils.isEmpty(referenceLocale)) { - return TextUtils.isEmpty(testedLocale) ? LOCALE_FULL_MATCH : LOCALE_ANY_MATCH; - } - if (null == testedLocale) return LOCALE_NO_MATCH; - String[] referenceParams = referenceLocale.split("_", 3); - String[] testedParams = testedLocale.split("_", 3); - // By spec of String#split, [0] cannot be null and length cannot be 0. - if (!referenceParams[0].equals(testedParams[0])) return LOCALE_NO_MATCH; - switch (referenceParams.length) { - case 1: - return 1 == testedParams.length ? LOCALE_FULL_MATCH : LOCALE_LANGUAGE_MATCH; - case 2: - if (1 == testedParams.length) return LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER; - if (!referenceParams[1].equals(testedParams[1])) - return LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER; - if (3 == testedParams.length) return LOCALE_LANGUAGE_AND_COUNTRY_MATCH; - return LOCALE_FULL_MATCH; - case 3: - if (1 == testedParams.length) return LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER; - if (!referenceParams[1].equals(testedParams[1])) - return LOCALE_LANGUAGE_MATCH_COUNTRY_DIFFER; - if (2 == testedParams.length) return LOCALE_LANGUAGE_AND_COUNTRY_MATCH_VARIANT_DIFFER; - if (!referenceParams[2].equals(testedParams[2])) - return LOCALE_LANGUAGE_AND_COUNTRY_MATCH_VARIANT_DIFFER; - return LOCALE_FULL_MATCH; - } - // It should be impossible to come here - return LOCALE_NO_MATCH; - } - - /** - * Return a string that represents this match level, with better matches first. - * - * The strings are sorted in lexicographic order: a better match will always be less than - * a worse match when compared together. - */ - public static String getMatchLevelSortedString(int matchLevel) { - // This works because the match levels are 0~99 (actually 0~30) - // Ideally this should use a number of digits equals to the 1og10 of the greater matchLevel - return String.format(Locale.ROOT, "%02d", MATCH_LEVEL_MAX - matchLevel); - } - - /** - * Find out whether a match level should be considered a match. - * - * This method takes a match level as returned by the #getMatchLevel method, and returns whether - * it should be considered a match in the usual sense with standard Locale functions. - * - * @param level the match level, as returned by getMatchLevel. - * @return whether this is a match or not. - */ - public static boolean isMatch(int level) { - return LOCALE_MATCH <= level; - } - - private static final HashMap<String, Locale> sLocaleCache = new HashMap<>(); - - /** - * Creates a locale from a string specification. - */ - @Nullable - public static Locale constructLocaleFromString(@Nullable final String localeStr) { - if (localeStr == null) { - // TODO: Should this be Locale.ROOT? - return null; - } - synchronized (sLocaleCache) { - Locale retval = sLocaleCache.get(localeStr); - if (retval != null) { - return retval; - } - final String[] localeParams = localeStr.split("_", 3); - if (localeParams.length == 1) { - retval = new Locale(localeParams[0]); - } else if (localeParams.length == 2) { - retval = new Locale(localeParams[0], localeParams[1]); - } else if (localeParams.length == 3) { - retval = new Locale(localeParams[0], localeParams[1], localeParams[2]); - } - if (retval != null) { - sLocaleCache.put(localeStr, retval); - } - // TODO: Should return Locale.ROOT instead of null? - return retval; - } - } -} diff --git a/java/src/com/android/inputmethod/latin/utils/SubtypeLocaleUtils.java b/java/src/com/android/inputmethod/latin/utils/SubtypeLocaleUtils.java index e4a8ee2a6..b36168b6c 100644 --- a/java/src/com/android/inputmethod/latin/utils/SubtypeLocaleUtils.java +++ b/java/src/com/android/inputmethod/latin/utils/SubtypeLocaleUtils.java @@ -28,6 +28,7 @@ import android.view.inputmethod.InputMethodSubtype; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.RichInputMethodSubtype; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.common.StringUtils; import java.util.Arrays; diff --git a/native/dicttoolkit/NativeFileList.mk b/native/dicttoolkit/NativeFileList.mk index b6be9c541..925ec458b 100644 --- a/native/dicttoolkit/NativeFileList.mk +++ b/native/dicttoolkit/NativeFileList.mk @@ -15,7 +15,15 @@ LATIN_IME_DICT_TOOLKIT_MAIN_SRC_FILES := \ dict_toolkit_main.cpp -LATIN_IME_DICT_TOOLKIT_SRC_FILES := +LATIN_IME_DICT_TOOLKIT_SRC_FILES := \ + $(addprefix command_executors/, \ + diff_executor.cpp \ + header_executor.cpp \ + help_executor.cpp \ + info_executor.cpp \ + makedict_executor.cpp) \ + utils/command_utils.cpp LATIN_IME_DICT_TOOLKIT_TEST_FILES := \ - dict_toolkit_defines_test.cpp + dict_toolkit_defines_test.cpp \ + utils/command_utils_test.cpp diff --git a/native/dicttoolkit/UnitTests.mk b/native/dicttoolkit/UnitTests.mk index d568db44a..96e28730e 100644 --- a/native/dicttoolkit/UnitTests.mk +++ b/native/dicttoolkit/UnitTests.mk @@ -46,6 +46,7 @@ include $(BUILD_HOST_STATIC_LIBRARY) include $(CLEAR_VARS) # TODO: Remove -std=c++11 once it is set by default on host build. +LOCAL_ADDRESS_SANITIZER := true LOCAL_CFLAGS += -std=c++11 -Wno-unused-parameter -Wno-unused-function LOCAL_CLANG := true LOCAL_CXX_STL := libc++ diff --git a/native/dicttoolkit/dict_toolkit_main.cpp b/native/dicttoolkit/dict_toolkit_main.cpp index d71b50eb4..53cc5e915 100644 --- a/native/dicttoolkit/dict_toolkit_main.cpp +++ b/native/dicttoolkit/dict_toolkit_main.cpp @@ -16,8 +16,24 @@ #include <cstdio> +#include "dict_toolkit_defines.h" +#include "utils/command_utils.h" + +void usage(int argc, char **argv) { + fprintf(stderr, "Usage: %s <command> [arguments]\n", argc > 0 ? argv[0] : "dicttoolkit"); +} + int main(int argc, char **argv) { - // TODO: Implement. - printf("%s\n", argv[0]); - return 0; + if (argc < MIN_ARG_COUNT) { + usage(argc, argv); + return 1; + } + using namespace latinime::dicttoolkit; + const CommandType commandType = CommandUtils::getCommandType(argv[1]); + if (commandType == CommandType::Unknown) { + CommandUtils::printCommandUnknownMessage(argv[0], argv[1]); + return 1; + } + const auto executor = CommandUtils::getCommandExecutor(commandType); + return executor(argc - 1, argv + 1); } diff --git a/native/dicttoolkit/src/command_executors/diff_executor.cpp b/native/dicttoolkit/src/command_executors/diff_executor.cpp new file mode 100644 index 000000000..077a40090 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/diff_executor.cpp @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "command_executors/diff_executor.h" + +#include <cstdio> + +namespace latinime { +namespace dicttoolkit { + +const char *const DiffExecutor::COMMAND_NAME = "diff"; + +/* static */ int DiffExecutor::run(const int argc, char **argv) { + fprintf(stderr, "Command '%s' has not been implemented yet.\n", COMMAND_NAME); + return 0; +} + +/* static */ void DiffExecutor::printUsage() { + printf("*** %s\n", COMMAND_NAME); + printf("Usage: %s\n", COMMAND_NAME); + printf("Shows differences between two dictionaries.\n\n"); +} + +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/dicttoolkit/src/command_executors/diff_executor.h b/native/dicttoolkit/src/command_executors/diff_executor.h new file mode 100644 index 000000000..fc8dc0d8f --- /dev/null +++ b/native/dicttoolkit/src/command_executors/diff_executor.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_DICT_TOOLKIT_DIFF_EXECUTOR_H +#define LATINIME_DICT_TOOLKIT_DIFF_EXECUTOR_H + +#include "dict_toolkit_defines.h" + +namespace latinime { +namespace dicttoolkit { + +class DiffExecutor final { + public: + static const char *const COMMAND_NAME; + + static int run(const int argc, char **argv); + static void printUsage(); + + private: + DISALLOW_IMPLICIT_CONSTRUCTORS(DiffExecutor); +}; + +} // namespace dicttoolkit +} // namepsace latinime +#endif // LATINIME_DICT_TOOLKIT_DIFF_EXECUTOR_H diff --git a/native/dicttoolkit/src/command_executors/header_executor.cpp b/native/dicttoolkit/src/command_executors/header_executor.cpp new file mode 100644 index 000000000..068a62c31 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/header_executor.cpp @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "command_executors/header_executor.h" + +#include <cstdio> + +namespace latinime { +namespace dicttoolkit { + +const char *const HeaderExecutor::COMMAND_NAME = "header"; + +/* static */ int HeaderExecutor::run(const int argc, char **argv) { + fprintf(stderr, "Command '%s' has not been implemented yet.\n", COMMAND_NAME); + return 0; +} + +/* static */ void HeaderExecutor::printUsage() { + printf("*** %s\n", COMMAND_NAME); + printf("Usage: %s\n", COMMAND_NAME); + printf("Prints the header contents of a dictionary file.\n\n"); +} + +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/dicttoolkit/src/command_executors/header_executor.h b/native/dicttoolkit/src/command_executors/header_executor.h new file mode 100644 index 000000000..4cdeb1a99 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/header_executor.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_DICT_TOOLKIT_HEADER_EXECUTOR_H +#define LATINIME_DICT_TOOLKIT_HEADER_EXECUTOR_H + +#include "dict_toolkit_defines.h" + +namespace latinime { +namespace dicttoolkit { + +class HeaderExecutor final { + public: + static const char *const COMMAND_NAME; + + static int run(const int argc, char **argv); + static void printUsage(); + + private: + DISALLOW_IMPLICIT_CONSTRUCTORS(HeaderExecutor); +}; + +} // namespace dicttoolkit +} // namepsace latinime +#endif // LATINIME_DICT_TOOLKIT_HEADER_EXECUTOR_H diff --git a/native/dicttoolkit/src/command_executors/help_executor.cpp b/native/dicttoolkit/src/command_executors/help_executor.cpp new file mode 100644 index 000000000..bd29a5b16 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/help_executor.cpp @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "command_executors/help_executor.h" + +#include <cstdio> +#include <functional> +#include <vector> + +#include "command_executors/diff_executor.h" +#include "command_executors/header_executor.h" +#include "command_executors/info_executor.h" +#include "command_executors/makedict_executor.h" +#include "utils/command_utils.h" + +namespace latinime { +namespace dicttoolkit { + +const char *const HelpExecutor::COMMAND_NAME = "help"; + +/* static */ int HelpExecutor::run(const int argc, char **argv) { + printf("Available commands:\n\n"); + const std::vector<std::function<void(void)>> printUsageMethods = {DiffExecutor::printUsage, + HeaderExecutor::printUsage, InfoExecutor::printUsage, MakedictExecutor::printUsage, + printUsage}; + for (const auto &printUsageMethod : printUsageMethods) { + printUsageMethod(); + } + return 0; +} + +/* static */ void HelpExecutor::printUsage() { + printf("*** %s\n", COMMAND_NAME); + printf("Usage: %s\n", COMMAND_NAME); + printf("Show this help list.\n\n"); +} + +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/dicttoolkit/src/command_executors/help_executor.h b/native/dicttoolkit/src/command_executors/help_executor.h new file mode 100644 index 000000000..280610eb9 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/help_executor.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_DICT_TOOLKIT_HELP_EXECUTOR_H +#define LATINIME_DICT_TOOLKIT_HELP_EXECUTOR_H + +#include "dict_toolkit_defines.h" + +namespace latinime { +namespace dicttoolkit { + +class HelpExecutor final { + public: + static const char *const COMMAND_NAME; + + static int run(const int argc, char **argv); + static void printUsage(); + + private: + DISALLOW_IMPLICIT_CONSTRUCTORS(HelpExecutor); +}; + +} // namespace dicttoolkit +} // namepsace latinime +#endif // LATINIME_DICT_TOOLKIT_HELP_EXECUTOR_H diff --git a/native/dicttoolkit/src/command_executors/info_executor.cpp b/native/dicttoolkit/src/command_executors/info_executor.cpp new file mode 100644 index 000000000..c4d84cab3 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/info_executor.cpp @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "command_executors/info_executor.h" + +#include <cstdio> + +namespace latinime { +namespace dicttoolkit { + +const char *const InfoExecutor::COMMAND_NAME = "info"; + +/* static */ int InfoExecutor::run(const int argc, char **argv) { + fprintf(stderr, "Command '%s' has not been implemented yet.\n", COMMAND_NAME); + return 0; +} + +/* static */ void InfoExecutor::printUsage() { + printf("*** %s\n", COMMAND_NAME); + printf("Usage: %s\n", COMMAND_NAME); + printf("Prints various information about a dictionary file.\n\n"); +} + +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/dicttoolkit/src/command_executors/info_executor.h b/native/dicttoolkit/src/command_executors/info_executor.h new file mode 100644 index 000000000..4ffa74fb0 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/info_executor.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_DICT_TOOLKIT_INFO_EXECUTOR_H +#define LATINIME_DICT_TOOLKIT_INFO_EXECUTOR_H + +#include "dict_toolkit_defines.h" + +namespace latinime { +namespace dicttoolkit { + +class InfoExecutor final { + public: + static const char *const COMMAND_NAME; + + static int run(const int argc, char **argv); + static void printUsage(); + + private: + DISALLOW_IMPLICIT_CONSTRUCTORS(InfoExecutor); +}; + +} // namepsace dicttoolkit +} // namespace latinime +#endif // LATINIME_DICT_TOOLKIT_INFO_EXECUTOR_H diff --git a/native/dicttoolkit/src/command_executors/makedict_executor.cpp b/native/dicttoolkit/src/command_executors/makedict_executor.cpp new file mode 100644 index 000000000..ea62e3c37 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/makedict_executor.cpp @@ -0,0 +1,40 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "command_executors/makedict_executor.h" + +#include <cstdio> + +namespace latinime { +namespace dicttoolkit { + +const char *const MakedictExecutor::COMMAND_NAME = "makedict"; + +/* static */ int MakedictExecutor::run(const int argc, char **argv) { + fprintf(stderr, "Command '%s' has not been implemented yet.\n", COMMAND_NAME); + return 0; +} + +/* static */ void MakedictExecutor::printUsage() { + printf("*** %s\n", COMMAND_NAME); + printf("Usage: %s\n", COMMAND_NAME); + printf("Converts a source dictionary file to one or several outputs.\n" + "Source can be a binary dictionary file or a combined format file.\n" + "Binary version 2 (Jelly Bean), 4, and combined format outputs are supported.\n\n"); +} + +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/dicttoolkit/src/command_executors/makedict_executor.h b/native/dicttoolkit/src/command_executors/makedict_executor.h new file mode 100644 index 000000000..ae1309f60 --- /dev/null +++ b/native/dicttoolkit/src/command_executors/makedict_executor.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_DICT_TOOLKIT_MAKEDICT_EXECUTOR_H +#define LATINIME_DICT_TOOLKIT_MAKEDICT_EXECUTOR_H + +#include "dict_toolkit_defines.h" + +namespace latinime { +namespace dicttoolkit { + +class MakedictExecutor final { + public: + static const char *const COMMAND_NAME; + + static int run(const int argc, char **argv); + static void printUsage(); + + private: + DISALLOW_IMPLICIT_CONSTRUCTORS(MakedictExecutor); +}; + +} // namespace dicttoolkit +} // namepsace latinime +#endif // LATINIME_DICT_TOOLKIT_MAKEDICT_EXECUTOR_H diff --git a/native/dicttoolkit/src/dict_toolkit_defines.h b/native/dicttoolkit/src/dict_toolkit_defines.h index 2a2104e26..dbaae0ca0 100644 --- a/native/dicttoolkit/src/dict_toolkit_defines.h +++ b/native/dicttoolkit/src/dict_toolkit_defines.h @@ -19,4 +19,6 @@ #include "defines.h" +#define MIN_ARG_COUNT 2 + #endif // LATINIME_DICT_TOOLKIT_DEFINES_H diff --git a/native/dicttoolkit/src/utils/command_utils.cpp b/native/dicttoolkit/src/utils/command_utils.cpp new file mode 100644 index 000000000..34196425e --- /dev/null +++ b/native/dicttoolkit/src/utils/command_utils.cpp @@ -0,0 +1,74 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "utils/command_utils.h" + +#include <cstdio> + +#include "command_executors/diff_executor.h" +#include "command_executors/header_executor.h" +#include "command_executors/help_executor.h" +#include "command_executors/info_executor.h" +#include "command_executors/makedict_executor.h" + +namespace latinime { +namespace dicttoolkit { + +/* static */ CommandType CommandUtils::getCommandType(const std::string &commandName) { + if (commandName == InfoExecutor::COMMAND_NAME) { + return CommandType::Info; + } else if (commandName == DiffExecutor::COMMAND_NAME) { + return CommandType::Diff; + } else if (commandName == MakedictExecutor::COMMAND_NAME) { + return CommandType::Makedict; + } else if (commandName == HeaderExecutor::COMMAND_NAME) { + return CommandType::Header; + } else if (commandName == HelpExecutor::COMMAND_NAME) { + return CommandType::Help; + } else { + return CommandType::Unknown; + } +} + +/* static */ void CommandUtils::printCommandUnknownMessage(const std::string &programName, + const std::string &commandName) { + fprintf(stderr, "Command '%s' is unknown. Try '%s %s' for more information.\n", + commandName.c_str(), programName.c_str(), HelpExecutor::COMMAND_NAME); +} + +/* static */ std::function<int(int, char **)> CommandUtils::getCommandExecutor( + const CommandType commandType) { + switch (commandType) { + case CommandType::Info: + return InfoExecutor::run; + case CommandType::Diff: + return DiffExecutor::run; + case CommandType::Makedict: + return MakedictExecutor::run; + case CommandType::Header: + return HeaderExecutor::run; + case CommandType::Help: + return HelpExecutor::run; + default: + return [] (int, char **) -> int { + printf("Command executor not found."); + return 1; + }; + } +} + +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/dicttoolkit/src/utils/command_utils.h b/native/dicttoolkit/src/utils/command_utils.h new file mode 100644 index 000000000..4a181f194 --- /dev/null +++ b/native/dicttoolkit/src/utils/command_utils.h @@ -0,0 +1,50 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_DICT_TOOLKIT_COMMAND_UTILS_H +#define LATINIME_DICT_TOOLKIT_COMMAND_UTILS_H + +#include <functional> +#include <memory> +#include <string> + +#include "dict_toolkit_defines.h" + +namespace latinime { +namespace dicttoolkit { + +enum class CommandType : int { + Info, + Diff, + Makedict, + Header, + Help, + Unknown +}; + +class CommandUtils { +public: + static CommandType getCommandType(const std::string &commandName); + static void printCommandUnknownMessage(const std::string &programName, + const std::string &commandName); + static std::function<int(int, char **)> getCommandExecutor(const CommandType commandType); + +private: + DISALLOW_IMPLICIT_CONSTRUCTORS(CommandUtils); +}; +} // namespace dicttoolkit +} // namespace latinime +#endif // LATINIME_DICT_TOOLKIT_COMMAND_UTILS_H diff --git a/native/dicttoolkit/tests/utils/command_utils_test.cpp b/native/dicttoolkit/tests/utils/command_utils_test.cpp new file mode 100644 index 000000000..9d79c9dd9 --- /dev/null +++ b/native/dicttoolkit/tests/utils/command_utils_test.cpp @@ -0,0 +1,37 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "utils/command_utils.h" + +#include <gtest/gtest.h> + +namespace latinime { +namespace dicttoolkit { +namespace { + +TEST(CommandUtilsTests, TestGetCommandType) { + EXPECT_EQ(CommandUtils::getCommandType(""), CommandType::Unknown); + EXPECT_EQ(CommandUtils::getCommandType("abc"), CommandType::Unknown); + EXPECT_EQ(CommandUtils::getCommandType("info"), CommandType::Info); + EXPECT_EQ(CommandUtils::getCommandType("diff"), CommandType::Diff); + EXPECT_EQ(CommandUtils::getCommandType("makedict"), CommandType::Makedict); + EXPECT_EQ(CommandUtils::getCommandType("header"), CommandType::Header); + EXPECT_EQ(CommandUtils::getCommandType("help"), CommandType::Help); +} + +} // namespace +} // namespace dicttoolkit +} // namespace latinime diff --git a/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp b/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp index 118f600bb..9c065e0d1 100644 --- a/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp +++ b/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp @@ -35,6 +35,7 @@ #include "utils/int_array_view.h" #include "utils/jni_data_utils.h" #include "utils/log_utils.h" +#include "utils/profiler.h" #include "utils/time_keeper.h" namespace latinime { @@ -43,8 +44,8 @@ class ProximityInfo; static jlong latinime_BinaryDictionary_open(JNIEnv *env, jclass clazz, jstring sourceDir, jlong dictOffset, jlong dictSize, jboolean isUpdatable) { - PROF_OPEN; - PROF_START(66); + PROF_INIT; + PROF_TIMER_START(66); const jsize sourceDirUtf8Length = env->GetStringUTFLength(sourceDir); if (sourceDirUtf8Length <= 0) { AKLOGE("DICT: Can't get sourceDir string"); @@ -63,8 +64,7 @@ static jlong latinime_BinaryDictionary_open(JNIEnv *env, jclass clazz, jstring s Dictionary *const dictionary = new Dictionary(env, std::move(dictionaryStructureWithBufferPolicy)); - PROF_END(66); - PROF_CLOSE; + PROF_TIMER_END(66); return reinterpret_cast<jlong>(dictionary); } @@ -586,7 +586,7 @@ static bool latinime_BinaryDictionary_migrateNative(JNIEnv *env, jclass clazz, j } if (!dictionaryStructureWithBufferPolicy->addUnigramEntry( CodePointArrayView(wordCodePoints, wordCodePointCount), - wordProperty.getUnigramProperty())) { + &wordProperty.getUnigramProperty())) { LogUtils::logToJava(env, "Cannot add unigram to the new dict."); return false; } @@ -605,7 +605,7 @@ static bool latinime_BinaryDictionary_migrateNative(JNIEnv *env, jclass clazz, j return false; } } - for (const NgramProperty &ngramProperty : *wordProperty.getNgramProperties()) { + for (const NgramProperty &ngramProperty : wordProperty.getNgramProperties()) { if (!dictionaryStructureWithBufferPolicy->addNgramEntry(&ngramProperty)) { LogUtils::logToJava(env, "Cannot add ngram to the new dict."); return false; diff --git a/native/jni/src/defines.h b/native/jni/src/defines.h index 885118524..0e67b4d5a 100644 --- a/native/jni/src/defines.h +++ b/native/jni/src/defines.h @@ -23,10 +23,10 @@ #define AK_FORCE_INLINE inline #endif // __GNUC__ -#if defined(FLAG_DO_PROFILE) || defined(FLAG_DBG) +#if defined(FLAG_DBG) #undef AK_FORCE_INLINE #define AK_FORCE_INLINE inline -#endif // defined(FLAG_DO_PROFILE) || defined(FLAG_DBG) +#endif // defined(FLAG_DBG) // Must be equal to Constants.Dictionary.MAX_WORD_LENGTH in Java #define MAX_WORD_LENGTH 48 @@ -172,69 +172,6 @@ static inline void showStackTrace() { #define INTS_TO_CHARS(input, length, output) #endif // defined(FLAG_DO_PROFILE) || defined(FLAG_DBG) -#ifdef FLAG_DO_PROFILE -// Profiler -#include <time.h> - -#define PROF_BUF_SIZE 100 -static float profile_buf[PROF_BUF_SIZE]; -static float profile_old[PROF_BUF_SIZE]; -static unsigned int profile_counter[PROF_BUF_SIZE]; - -#define PROF_RESET prof_reset() -#define PROF_COUNT(prof_buf_id) ++profile_counter[prof_buf_id] -#define PROF_OPEN do { PROF_RESET; PROF_START(PROF_BUF_SIZE - 1); } while (0) -#define PROF_START(prof_buf_id) do { \ - PROF_COUNT(prof_buf_id); profile_old[prof_buf_id] = (clock()); } while (0) -#define PROF_CLOSE do { PROF_END(PROF_BUF_SIZE - 1); PROF_OUTALL; } while (0) -#define PROF_END(prof_buf_id) profile_buf[prof_buf_id] += ((clock()) - profile_old[prof_buf_id]) -#define PROF_CLOCKOUT(prof_buf_id) \ - AKLOGI("%s : clock is %f", __FUNCTION__, (clock() - profile_old[prof_buf_id])) -#define PROF_OUTALL do { AKLOGI("--- %s ---", __FUNCTION__); prof_out(); } while (0) - -static inline void prof_reset(void) { - for (int i = 0; i < PROF_BUF_SIZE; ++i) { - profile_buf[i] = 0; - profile_old[i] = 0; - profile_counter[i] = 0; - } -} - -static inline void prof_out(void) { - if (profile_counter[PROF_BUF_SIZE - 1] != 1) { - AKLOGI("Error: You must call PROF_OPEN before PROF_CLOSE."); - } - AKLOGI("Total time is %6.3f ms.", - profile_buf[PROF_BUF_SIZE - 1] * 1000.0f / static_cast<float>(CLOCKS_PER_SEC)); - float all = 0.0f; - for (int i = 0; i < PROF_BUF_SIZE - 1; ++i) { - all += profile_buf[i]; - } - if (all < 1.0f) all = 1.0f; - for (int i = 0; i < PROF_BUF_SIZE - 1; ++i) { - if (profile_buf[i] > 0.0f) { - AKLOGI("(%d): Used %4.2f%%, %8.4f ms. Called %d times.", - i, (profile_buf[i] * 100.0f / all), - profile_buf[i] * 1000.0f / static_cast<float>(CLOCKS_PER_SEC), - profile_counter[i]); - } - } -} - -#else // FLAG_DO_PROFILE -#define PROF_BUF_SIZE 0 -#define PROF_RESET -#define PROF_COUNT(prof_buf_id) -#define PROF_OPEN -#define PROF_START(prof_buf_id) -#define PROF_CLOSE -#define PROF_END(prof_buf_id) -#define PROF_CLOCK_OUT(prof_buf_id) -#define PROF_CLOCKOUT(prof_buf_id) -#define PROF_OUTALL - -#endif // FLAG_DO_PROFILE - #ifdef FLAG_DBG #define DEBUG_DICT true #define DEBUG_DICT_FULL false diff --git a/native/jni/src/suggest/core/dictionary/property/word_property.h b/native/jni/src/suggest/core/dictionary/property/word_property.h index b5314faaa..d4db3f09f 100644 --- a/native/jni/src/suggest/core/dictionary/property/word_property.h +++ b/native/jni/src/suggest/core/dictionary/property/word_property.h @@ -23,6 +23,7 @@ #include "jni.h" #include "suggest/core/dictionary/property/ngram_property.h" #include "suggest/core/dictionary/property/unigram_property.h" +#include "utils/int_array_view.h" namespace latinime { @@ -33,10 +34,10 @@ class WordProperty { WordProperty() : mCodePoints(), mUnigramProperty(), mNgrams() {} - WordProperty(const std::vector<int> &&codePoints, const UnigramProperty *const unigramProperty, - const std::vector<NgramProperty> *const ngrams) - : mCodePoints(std::move(codePoints)), mUnigramProperty(*unigramProperty), - mNgrams(*ngrams) {} + WordProperty(const std::vector<int> &&codePoints, const UnigramProperty &unigramProperty, + const std::vector<NgramProperty> &ngrams) + : mCodePoints(std::move(codePoints)), mUnigramProperty(unigramProperty), + mNgrams(ngrams) {} void outputProperties(JNIEnv *const env, jintArray outCodePoints, jbooleanArray outFlags, jintArray outProbabilityInfo, jobject outNgramPrevWordsArray, @@ -44,12 +45,16 @@ class WordProperty { jobject outNgramProbabilities, jobject outShortcutTargets, jobject outShortcutProbabilities) const; - const UnigramProperty *getUnigramProperty() const { - return &mUnigramProperty; + const CodePointArrayView getCodePoints() const { + return CodePointArrayView(mCodePoints); } - const std::vector<NgramProperty> *getNgramProperties() const { - return &mNgrams; + const UnigramProperty &getUnigramProperty() const { + return mUnigramProperty; + } + + const std::vector<NgramProperty> &getNgramProperties() const { + return mNgrams; } private: diff --git a/native/jni/src/suggest/core/suggest.cpp b/native/jni/src/suggest/core/suggest.cpp index c372d668b..e5e9b46bf 100644 --- a/native/jni/src/suggest/core/suggest.cpp +++ b/native/jni/src/suggest/core/suggest.cpp @@ -29,6 +29,7 @@ #include "suggest/core/result/suggestions_output_utils.h" #include "suggest/core/session/dic_traverse_session.h" #include "suggest/core/suggest_options.h" +#include "utils/profiler.h" namespace latinime { @@ -48,8 +49,8 @@ void Suggest::getSuggestions(ProximityInfo *pInfo, void *traverseSession, int *inputXs, int *inputYs, int *times, int *pointerIds, int *inputCodePoints, int inputSize, const float weightOfLangModelVsSpatialModel, SuggestionResults *const outSuggestionResults) const { - PROF_OPEN; - PROF_START(0); + PROF_INIT; + PROF_TIMER_START(0); const float maxSpatialDistance = TRAVERSAL->getMaxSpatialDistance(); DicTraverseSession *tSession = static_cast<DicTraverseSession *>(traverseSession); tSession->setupForGetSuggestions(pInfo, inputCodePoints, inputSize, inputXs, inputYs, times, @@ -57,8 +58,8 @@ void Suggest::getSuggestions(ProximityInfo *pInfo, void *traverseSession, // TODO: Add the way to evaluate cache initializeSearch(tSession); - PROF_END(0); - PROF_START(1); + PROF_TIMER_END(0); + PROF_TIMER_START(1); // keep expanding search dicNodes until all have terminated. while (tSession->getDicTraverseCache()->activeSize() > 0) { @@ -66,12 +67,11 @@ void Suggest::getSuggestions(ProximityInfo *pInfo, void *traverseSession, tSession->getDicTraverseCache()->advanceActiveDicNodes(); tSession->getDicTraverseCache()->advanceInputIndex(inputSize); } - PROF_END(1); - PROF_START(2); + PROF_TIMER_END(1); + PROF_TIMER_START(2); SuggestionsOutputUtils::outputSuggestions( SCORING, tSession, weightOfLangModelVsSpatialModel, outSuggestionResults); - PROF_END(2); - PROF_CLOSE; + PROF_TIMER_END(2); } /** diff --git a/native/jni/src/suggest/policyimpl/dictionary/structure/backward/v402/ver4_patricia_trie_policy.cpp b/native/jni/src/suggest/policyimpl/dictionary/structure/backward/v402/ver4_patricia_trie_policy.cpp index 9455222dd..ca7d93b0e 100644 --- a/native/jni/src/suggest/policyimpl/dictionary/structure/backward/v402/ver4_patricia_trie_policy.cpp +++ b/native/jni/src/suggest/policyimpl/dictionary/structure/backward/v402/ver4_patricia_trie_policy.cpp @@ -614,7 +614,7 @@ const WordProperty Ver4PatriciaTriePolicy::getWordProperty( const UnigramProperty unigramProperty(ptNodeParams.representsBeginningOfSentence(), ptNodeParams.isNotAWord(), ptNodeParams.isPossiblyOffensive(), ptNodeParams.getProbability(), *historicalInfo, std::move(shortcuts)); - return WordProperty(wordCodePoints.toVector(), &unigramProperty, &ngrams); + return WordProperty(wordCodePoints.toVector(), unigramProperty, ngrams); } int Ver4PatriciaTriePolicy::getNextWordAndNextToken(const int token, int *const outCodePoints, diff --git a/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp b/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp index 59873612a..1a51acad5 100644 --- a/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp +++ b/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp @@ -478,7 +478,7 @@ const WordProperty PatriciaTriePolicy::getWordProperty( const UnigramProperty unigramProperty(ptNodeParams.representsBeginningOfSentence(), ptNodeParams.isNotAWord(), ptNodeParams.isPossiblyOffensive(), ptNodeParams.getProbability(), HistoricalInfo(), std::move(shortcuts)); - return WordProperty(wordCodePoints.toVector(), &unigramProperty, &ngrams); + return WordProperty(wordCodePoints.toVector(), unigramProperty, ngrams); } int PatriciaTriePolicy::getNextWordAndNextToken(const int token, int *const outCodePoints, diff --git a/native/jni/src/suggest/policyimpl/dictionary/structure/v4/ver4_patricia_trie_policy.cpp b/native/jni/src/suggest/policyimpl/dictionary/structure/v4/ver4_patricia_trie_policy.cpp index 1992d4a5a..7449cd02b 100644 --- a/native/jni/src/suggest/policyimpl/dictionary/structure/v4/ver4_patricia_trie_policy.cpp +++ b/native/jni/src/suggest/policyimpl/dictionary/structure/v4/ver4_patricia_trie_policy.cpp @@ -560,7 +560,7 @@ const WordProperty Ver4PatriciaTriePolicy::getWordProperty( wordAttributes.isNotAWord(), wordAttributes.isBlacklisted(), wordAttributes.isPossiblyOffensive(), wordAttributes.getProbability(), *historicalInfo, std::move(shortcuts)); - return WordProperty(wordCodePoints.toVector(), &unigramProperty, &ngrams); + return WordProperty(wordCodePoints.toVector(), unigramProperty, ngrams); } int Ver4PatriciaTriePolicy::getNextWordAndNextToken(const int token, int *const outCodePoints, diff --git a/native/jni/src/utils/profiler.h b/native/jni/src/utils/profiler.h new file mode 100644 index 000000000..5f107fed3 --- /dev/null +++ b/native/jni/src/utils/profiler.h @@ -0,0 +1,86 @@ +/* + * Copyright (C) 2014, The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LATINIME_PROFILER_H +#define LATINIME_PROFILER_H + +#ifdef FLAG_DO_PROFILE + +#include "defines.h" + +#include <ctime> +#include <unordered_map> + +namespace latinime { + +class Profiler final { + public: + Profiler(const clockid_t clockId) + : mClockId(clockId), mStartTime(getTimeInMicroSec()), mStartTimes(), mTimes(), + mCounters() {} + + ~Profiler() { + const float totalTime = + static_cast<float>(getTimeInMicroSec() - mStartTime) / 1000.f; + AKLOGI("Total time is %6.3f ms.", totalTime); + for (const auto &time : mTimes) { + AKLOGI("(%d): Used %4.2f%%, %8.4f ms. Called %d times.", time.first, + time.second / totalTime * 100.0f, time.second, mCounters[time.first]); + } + } + + void startTimer(const int id) { + mStartTimes[id] = getTimeInMicroSec(); + } + + void endTimer(const int id) { + mTimes[id] += static_cast<float>(getTimeInMicroSec() - mStartTimes[id]) / 1000.0f; + mCounters[id]++; + } + + operator bool() const { return false; } + + private: + DISALLOW_IMPLICIT_CONSTRUCTORS(Profiler); + + const clockid_t mClockId; + int64_t mStartTime; + std::unordered_map<int, int64_t> mStartTimes; + std::unordered_map<int, float> mTimes; + std::unordered_map<int, int> mCounters; + + int64_t getTimeInMicroSec() { + timespec time; + clock_gettime(mClockId, &time); + return static_cast<int64_t>(time.tv_sec) * 1000000 + + static_cast<int64_t>(time.tv_nsec) / 1000; + } +}; +} // namespace latinime + +#define PROF_INIT Profiler __LATINIME__PROFILER__(CLOCK_THREAD_CPUTIME_ID) +#define PROF_TIMER_START(timer_id) __LATINIME__PROFILER__.startTimer(timer_id) +#define PROF_TIMER_END(timer_id) __LATINIME__PROFILER__.endTimer(timer_id) + +#else // FLAG_DO_PROFILE + +#define PROF_INIT +#define PROF_TIMER_START(timer_id) +#define PROF_TIMER_END(timer_id) + +#endif // FLAG_DO_PROFILE + +#endif /* LATINIME_PROFILER_H */ diff --git a/tests/Android.mk b/tests/Android.mk index 7cdabf249..0b5449143 100644 --- a/tests/Android.mk +++ b/tests/Android.mk @@ -12,7 +12,7 @@ # See the License for the specific language governing permissions and # limitations under the License. -LOCAL_PATH:= $(call my-dir) +LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) # We only want this apk build for tests. diff --git a/tests/src/com/android/inputmethod/keyboard/action/ActionTestsBase.java b/tests/src/com/android/inputmethod/keyboard/action/ActionTestsBase.java index 94caf51ed..1ea68e471 100644 --- a/tests/src/com/android/inputmethod/keyboard/action/ActionTestsBase.java +++ b/tests/src/com/android/inputmethod/keyboard/action/ActionTestsBase.java @@ -30,7 +30,7 @@ import com.android.inputmethod.keyboard.KeyboardLayoutSetTestsBase; import com.android.inputmethod.keyboard.internal.KeyboardIconsSet; import com.android.inputmethod.keyboard.layout.expected.ExpectedKeyVisual; import com.android.inputmethod.latin.common.Constants; -import com.android.inputmethod.latin.utils.LocaleUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.utils.RunInLocale; import com.android.inputmethod.latin.utils.SubtypeLocaleUtils; diff --git a/tests/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelperTests.java b/tests/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelperTests.java index e6198015a..6bb255b01 100644 --- a/tests/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelperTests.java +++ b/tests/src/com/android/inputmethod/keyboard/internal/LanguageOnSpacebarHelperTests.java @@ -30,10 +30,11 @@ import com.android.inputmethod.latin.RichInputMethodSubtype; import com.android.inputmethod.latin.utils.AdditionalSubtypeUtils; import com.android.inputmethod.latin.utils.SubtypeLocaleUtils; -import java.util.Arrays; -import java.util.List; +import java.util.ArrayList; import java.util.Locale; +import javax.annotation.Nonnull; + @SmallTest public class LanguageOnSpacebarHelperTests extends AndroidTestCase { private final LanguageOnSpacebarHelper mLanguageOnSpacebarHelper = @@ -48,6 +49,7 @@ public class LanguageOnSpacebarHelperTests extends AndroidTestCase { RichInputMethodSubtype FR_CH_SWISS; RichInputMethodSubtype FR_CH_QWERTY; RichInputMethodSubtype FR_CH_QWERTZ; + RichInputMethodSubtype IW_HEBREW; RichInputMethodSubtype ZZ_QWERTY; @Override @@ -56,116 +58,160 @@ public class LanguageOnSpacebarHelperTests extends AndroidTestCase { final Context context = getContext(); RichInputMethodManager.init(context); mRichImm = RichInputMethodManager.getInstance(); - SubtypeLocaleUtils.init(context); - - EN_US_QWERTY = new RichInputMethodSubtype(mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( - Locale.US.toString(), "qwerty")); - EN_GB_QWERTY = new RichInputMethodSubtype(mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( - Locale.UK.toString(), "qwerty")); - FR_AZERTY = new RichInputMethodSubtype(mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( - Locale.FRENCH.toString(), "azerty")); - FR_CA_QWERTY = new RichInputMethodSubtype(mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( - Locale.CANADA_FRENCH.toString(), "qwerty")); - FR_CH_SWISS = new RichInputMethodSubtype(mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( - "fr_CH", "swiss")); + + EN_US_QWERTY = findSubtypeOf(Locale.US.toString(), "qwerty"); + EN_GB_QWERTY = findSubtypeOf(Locale.UK.toString(), "qwerty"); + FR_AZERTY = findSubtypeOf(Locale.FRENCH.toString(), "azerty"); + FR_CA_QWERTY = findSubtypeOf(Locale.CANADA_FRENCH.toString(), "qwerty"); + FR_CH_SWISS = findSubtypeOf("fr_CH", "swiss"); FR_CH_QWERTZ = new RichInputMethodSubtype( AdditionalSubtypeUtils.createAsciiEmojiCapableAdditionalSubtype("fr_CH", "qwertz")); FR_CH_QWERTY = new RichInputMethodSubtype( AdditionalSubtypeUtils.createAsciiEmojiCapableAdditionalSubtype("fr_CH", "qwerty")); - ZZ_QWERTY = new RichInputMethodSubtype(mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( - SubtypeLocaleUtils.NO_LANGUAGE, "qwerty")); + IW_HEBREW = findSubtypeOf("iw", "hebrew"); + ZZ_QWERTY = findSubtypeOf(SubtypeLocaleUtils.NO_LANGUAGE, "qwerty"); + } + + @Nonnull + private RichInputMethodSubtype findSubtypeOf(final String localeString, + final String keyboardLayoutSetName) { + final InputMethodSubtype subtype = mRichImm.findSubtypeByLocaleAndKeyboardLayoutSet( + localeString, keyboardLayoutSetName); + if (subtype == null) { + throw new RuntimeException("Can't find subtype of " + localeString + " with " + + keyboardLayoutSetName); + } + return new RichInputMethodSubtype(subtype); + } + + private void enableSubtypes(final RichInputMethodSubtype ... subtypes) { + final ArrayList<InputMethodSubtype> enabledSubtypes = new ArrayList<>(); + for (final RichInputMethodSubtype subtype : subtypes) { + enabledSubtypes.add(subtype.getRawSubtype()); + } + mLanguageOnSpacebarHelper.onUpdateEnabledSubtypes(enabledSubtypes); + } + + private void assertFormatType(final RichInputMethodSubtype subtype, + final boolean implicitlyEnabledSubtype, final Locale systemLocale, + final int expectedFormat) { + mLanguageOnSpacebarHelper.onSubtypeChanged(subtype, implicitlyEnabledSubtype, systemLocale); + assertEquals(subtype.getLocales()[0] + " implicitly=" + implicitlyEnabledSubtype + + " in " + systemLocale, expectedFormat, + mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(subtype)); + } + + public void testOneSubtypeImplicitlyEnabled() { + enableSubtypes(EN_US_QWERTY); + assertFormatType(EN_US_QWERTY, true, Locale.US, FORMAT_TYPE_NONE); + + enableSubtypes(EN_GB_QWERTY); + assertFormatType(EN_GB_QWERTY, true, Locale.UK, FORMAT_TYPE_NONE); + + enableSubtypes(FR_AZERTY); + assertFormatType(FR_AZERTY, true, Locale.FRANCE, FORMAT_TYPE_NONE); + + enableSubtypes(FR_CA_QWERTY); + assertFormatType(FR_CA_QWERTY, true, Locale.CANADA_FRENCH, FORMAT_TYPE_NONE); + } + + public void testOneSubtypeExplicitlyEnabled() { + enableSubtypes(EN_US_QWERTY); + assertFormatType(EN_US_QWERTY, false, Locale.UK, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(EN_US_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + + enableSubtypes(EN_GB_QWERTY); + assertFormatType(EN_GB_QWERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(EN_GB_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + + enableSubtypes(FR_AZERTY); + assertFormatType(FR_AZERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_AZERTY, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + + enableSubtypes(FR_CA_QWERTY); + assertFormatType(FR_CA_QWERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); } - private static List<InputMethodSubtype> asList(final InputMethodSubtype ... subtypes) { - return Arrays.asList(subtypes); + public void testOneSubtypeImplicitlyEnabledWithNoLanguageSubtype() { + final Locale Locale_IW = new Locale("iw"); + enableSubtypes(IW_HEBREW, ZZ_QWERTY); + // TODO: Should this be FORMAT_TYPE_NONE? + assertFormatType(IW_HEBREW, true, Locale_IW, FORMAT_TYPE_LANGUAGE_ONLY); + // TODO: Should this be FORMAT_TYPE_NONE? + assertFormatType(ZZ_QWERTY, true, Locale_IW, FORMAT_TYPE_FULL_LOCALE); } - public void testOneSubtype() { - mLanguageOnSpacebarHelper.updateEnabledSubtypes(asList(EN_US_QWERTY.getRawSubtype())); - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(true /* isSame */); - assertEquals("one same English (US)", FORMAT_TYPE_NONE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_US_QWERTY)); - assertEquals("one same NoLanguage", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(ZZ_QWERTY)); - - mLanguageOnSpacebarHelper.updateEnabledSubtypes(asList(FR_AZERTY.getRawSubtype())); - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(false /* isSame */); - assertEquals("one diff English (US)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_US_QWERTY)); - assertEquals("one diff NoLanguage", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(ZZ_QWERTY)); + public void testTwoSubtypesExplicitlyEnabled() { + enableSubtypes(EN_US_QWERTY, FR_AZERTY); + assertFormatType(EN_US_QWERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_AZERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(EN_US_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_AZERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(EN_US_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_AZERTY, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + + enableSubtypes(EN_US_QWERTY, ZZ_QWERTY); + assertFormatType(EN_US_QWERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(ZZ_QWERTY, false, Locale.US, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(EN_US_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(ZZ_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_FULL_LOCALE); + } - public void testTwoSubtypes() { - mLanguageOnSpacebarHelper.updateEnabledSubtypes(asList(EN_US_QWERTY.getRawSubtype(), - FR_AZERTY.getRawSubtype())); - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(true /* isSame */); - assertEquals("two same English (US)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_US_QWERTY)); - assertEquals("two same French)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_AZERTY)); - assertEquals("two same NoLanguage", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(ZZ_QWERTY)); - - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(false /* isSame */); - assertEquals("two diff English (US)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_US_QWERTY)); - assertEquals("two diff French", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_AZERTY)); - assertEquals("two diff NoLanguage", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(ZZ_QWERTY)); + public void testMultiSubtypeWithSameLanuageAndSameLayout() { + // Explicitly enable en_US, en_GB, fr_FR, and no language keyboards. + enableSubtypes(EN_US_QWERTY, EN_GB_QWERTY, FR_CA_QWERTY, ZZ_QWERTY); + + assertFormatType(EN_US_QWERTY, false, Locale.US, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(EN_GB_QWERTY, false, Locale.US, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CA_QWERTY, false, Locale.US, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(ZZ_QWERTY, false, Locale.US, FORMAT_TYPE_FULL_LOCALE); + + assertFormatType(EN_US_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(EN_GB_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CA_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(ZZ_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_FULL_LOCALE); } - public void testSameLanuageSubtypes() { - mLanguageOnSpacebarHelper.updateEnabledSubtypes( - asList(EN_US_QWERTY.getRawSubtype(), EN_GB_QWERTY.getRawSubtype(), - FR_AZERTY.getRawSubtype(), ZZ_QWERTY.getRawSubtype())); - - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(true /* isSame */); - assertEquals("two same English (US)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_US_QWERTY)); - assertEquals("two same English (UK)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_GB_QWERTY)); - assertEquals("two same NoLanguage", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(ZZ_QWERTY)); - - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(false /* isSame */); - assertEquals("two diff English (US)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_US_QWERTY)); - assertEquals("two diff English (UK)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(EN_GB_QWERTY)); - assertEquals("two diff NoLanguage", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(ZZ_QWERTY)); + public void testMultiSubtypesWithSameLanguageButHaveDifferentLayout() { + enableSubtypes(FR_AZERTY, FR_CA_QWERTY, FR_CH_SWISS, FR_CH_QWERTZ); + + assertFormatType(FR_AZERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_SWISS, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_QWERTZ, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + + assertFormatType(FR_AZERTY, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_SWISS, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_QWERTZ, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + + assertFormatType(FR_AZERTY, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_SWISS, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_QWERTZ, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); } - public void testMultiSameLanuageSubtypes() { - mLanguageOnSpacebarHelper.updateEnabledSubtypes( - asList(FR_AZERTY.getRawSubtype(), FR_CA_QWERTY.getRawSubtype(), - FR_CH_SWISS.getRawSubtype(), FR_CH_QWERTY.getRawSubtype(), - FR_CH_QWERTZ.getRawSubtype())); - - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(true /* isSame */); - assertEquals("multi same French", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_AZERTY)); - assertEquals("multi same French (CA)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CA_QWERTY)); - assertEquals("multi same French (CH)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CH_SWISS)); - assertEquals("multi same French (CH) (QWERTY)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CH_QWERTY)); - assertEquals("multi same French (CH) (QWERTZ)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CH_QWERTZ)); - - mLanguageOnSpacebarHelper.updateIsSystemLanguageSameAsInputLanguage(false /* isSame */); - assertEquals("multi diff French", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_AZERTY)); - assertEquals("multi diff French (CA)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CA_QWERTY)); - assertEquals("multi diff French (CH)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CH_SWISS)); - assertEquals("multi diff French (CH) (QWERTY)", FORMAT_TYPE_FULL_LOCALE, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CH_QWERTY)); - assertEquals("multi diff French (CH) (QWERTZ)", FORMAT_TYPE_LANGUAGE_ONLY, - mLanguageOnSpacebarHelper.getLanguageOnSpacebarFormatType(FR_CH_QWERTZ)); + public void testMultiSubtypesWithSameLanguageAndMayHaveSameLayout() { + enableSubtypes(FR_AZERTY, FR_CA_QWERTY, FR_CH_SWISS, FR_CH_QWERTY, FR_CH_QWERTZ); + + assertFormatType(FR_AZERTY, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CH_SWISS, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_QWERTY, false, Locale.FRANCE, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CH_QWERTZ, false, Locale.FRANCE, FORMAT_TYPE_LANGUAGE_ONLY); + + assertFormatType(FR_AZERTY, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.CANADA_FRENCH, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CH_SWISS, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_QWERTY, false, Locale.CANADA_FRENCH, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CH_QWERTZ, false, Locale.CANADA_FRENCH, FORMAT_TYPE_LANGUAGE_ONLY); + + assertFormatType(FR_AZERTY, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CA_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CH_SWISS, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); + assertFormatType(FR_CH_QWERTY, false, Locale.JAPAN, FORMAT_TYPE_FULL_LOCALE); + assertFormatType(FR_CH_QWERTZ, false, Locale.JAPAN, FORMAT_TYPE_LANGUAGE_ONLY); } } diff --git a/tests/src/com/android/inputmethod/latin/BinaryDictionaryDecayingTests.java b/tests/src/com/android/inputmethod/latin/BinaryDictionaryDecayingTests.java index 039330c87..cff489dd5 100644 --- a/tests/src/com/android/inputmethod/latin/BinaryDictionaryDecayingTests.java +++ b/tests/src/com/android/inputmethod/latin/BinaryDictionaryDecayingTests.java @@ -22,6 +22,8 @@ import android.util.Pair; import com.android.inputmethod.latin.NgramContext.WordInfo; import com.android.inputmethod.latin.common.CodePointUtils; +import com.android.inputmethod.latin.common.FileUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.makedict.BinaryDictIOUtils; import com.android.inputmethod.latin.makedict.DictDecoder; import com.android.inputmethod.latin.makedict.DictionaryHeader; @@ -30,8 +32,6 @@ import com.android.inputmethod.latin.makedict.FusionDictionary; import com.android.inputmethod.latin.makedict.FusionDictionary.PtNode; import com.android.inputmethod.latin.makedict.UnsupportedFormatException; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; -import com.android.inputmethod.latin.utils.FileUtils; -import com.android.inputmethod.latin.utils.LocaleUtils; import com.android.inputmethod.latin.utils.WordInputEventForPersonalization; import java.io.File; diff --git a/tests/src/com/android/inputmethod/latin/BinaryDictionaryTests.java b/tests/src/com/android/inputmethod/latin/BinaryDictionaryTests.java index fcaa8cdca..60d2de18c 100644 --- a/tests/src/com/android/inputmethod/latin/BinaryDictionaryTests.java +++ b/tests/src/com/android/inputmethod/latin/BinaryDictionaryTests.java @@ -24,12 +24,12 @@ import android.util.Pair; import com.android.inputmethod.latin.NgramContext.WordInfo; import com.android.inputmethod.latin.common.CodePointUtils; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.FileUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; import com.android.inputmethod.latin.makedict.FormatSpec; import com.android.inputmethod.latin.makedict.WeightedString; import com.android.inputmethod.latin.makedict.WordProperty; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; -import com.android.inputmethod.latin.utils.FileUtils; import java.io.File; import java.io.IOException; diff --git a/tests/src/com/android/inputmethod/latin/InputTestsBase.java b/tests/src/com/android/inputmethod/latin/InputTestsBase.java index 926a2d3e1..00e0b52cb 100644 --- a/tests/src/com/android/inputmethod/latin/InputTestsBase.java +++ b/tests/src/com/android/inputmethod/latin/InputTestsBase.java @@ -44,10 +44,10 @@ import com.android.inputmethod.latin.Dictionary.PhonyDictionary; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; import com.android.inputmethod.latin.common.Constants; import com.android.inputmethod.latin.common.InputPointers; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.common.StringUtils; import com.android.inputmethod.latin.settings.DebugSettings; import com.android.inputmethod.latin.settings.Settings; -import com.android.inputmethod.latin.utils.LocaleUtils; import com.android.inputmethod.latin.utils.SubtypeLocaleUtils; import java.util.Locale; @@ -387,7 +387,7 @@ public class InputTestsBase extends ServiceTestCase<LatinIMEForTests> { false /* isAuxiliary */, false /* overridesImplicitlyEnabledSubtype */, 0 /* id */); - SubtypeSwitcher.forceSubtype(subtype); + RichInputMethodManager.forceSubtype(subtype); mLatinIME.onCurrentInputMethodSubtypeChanged(subtype); runMessages(); mKeyboard = mLatinIME.mKeyboardSwitcher.getKeyboard(); diff --git a/tests/src/com/android/inputmethod/latin/utils/SpacebarLanguageUtilsTests.java b/tests/src/com/android/inputmethod/latin/RichInputMethodSubtypeTests.java index 83afd782d..aed7d6ad6 100644 --- a/tests/src/com/android/inputmethod/latin/utils/SpacebarLanguageUtilsTests.java +++ b/tests/src/com/android/inputmethod/latin/RichInputMethodSubtypeTests.java @@ -1,5 +1,5 @@ /* - * Copyright (C) 2011 The Android Open Source Project + * Copyright (C) 2014 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -14,7 +14,7 @@ * limitations under the License. */ -package com.android.inputmethod.latin.utils; +package com.android.inputmethod.latin; import android.content.Context; import android.content.res.Resources; @@ -26,12 +26,15 @@ import android.view.inputmethod.InputMethodSubtype; import com.android.inputmethod.latin.R; import com.android.inputmethod.latin.RichInputMethodManager; import com.android.inputmethod.latin.RichInputMethodSubtype; +import com.android.inputmethod.latin.utils.AdditionalSubtypeUtils; +import com.android.inputmethod.latin.utils.RunInLocale; +import com.android.inputmethod.latin.utils.SubtypeLocaleUtils; import java.util.ArrayList; import java.util.Locale; @SmallTest -public class SpacebarLanguageUtilsTests extends AndroidTestCase { +public class RichInputMethodSubtypeTests extends AndroidTestCase { // All input method subtypes of LatinIME. private final ArrayList<RichInputMethodSubtype> mSubtypesList = new ArrayList<>(); diff --git a/tests/src/com/android/inputmethod/latin/WordComposerTests.java b/tests/src/com/android/inputmethod/latin/WordComposerTests.java index 20256e670..8ae475f7e 100644 --- a/tests/src/com/android/inputmethod/latin/WordComposerTests.java +++ b/tests/src/com/android/inputmethod/latin/WordComposerTests.java @@ -20,8 +20,8 @@ import android.test.AndroidTestCase; import android.test.suitebuilder.annotation.SmallTest; import com.android.inputmethod.latin.common.Constants; +import com.android.inputmethod.latin.common.CoordinateUtils; import com.android.inputmethod.latin.common.StringUtils; -import com.android.inputmethod.latin.utils.CoordinateUtils; /** * Unit tests for WordComposer. diff --git a/tests/src/com/android/inputmethod/latin/makedict/Ver4DictDecoder.java b/tests/src/com/android/inputmethod/latin/makedict/Ver4DictDecoder.java index 7e54ce986..63ea89c1d 100644 --- a/tests/src/com/android/inputmethod/latin/makedict/Ver4DictDecoder.java +++ b/tests/src/com/android/inputmethod/latin/makedict/Ver4DictDecoder.java @@ -18,7 +18,7 @@ package com.android.inputmethod.latin.makedict; import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.latin.BinaryDictionary; -import com.android.inputmethod.latin.utils.FileUtils; +import com.android.inputmethod.latin.common.FileUtils; import java.io.File; import java.io.FileNotFoundException; diff --git a/tests/src/com/android/inputmethod/latin/makedict/Ver4DictEncoder.java b/tests/src/com/android/inputmethod/latin/makedict/Ver4DictEncoder.java index 155421922..1e4bd768c 100644 --- a/tests/src/com/android/inputmethod/latin/makedict/Ver4DictEncoder.java +++ b/tests/src/com/android/inputmethod/latin/makedict/Ver4DictEncoder.java @@ -20,10 +20,10 @@ import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.latin.BinaryDictionary; import com.android.inputmethod.latin.Dictionary; import com.android.inputmethod.latin.NgramContext; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.makedict.FormatSpec.FormatOptions; import com.android.inputmethod.latin.makedict.FusionDictionary.PtNode; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; -import com.android.inputmethod.latin.utils.LocaleUtils; import java.io.File; import java.io.IOException; diff --git a/tests/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryTests.java b/tests/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryTests.java index 778f6e800..813a71239 100644 --- a/tests/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryTests.java +++ b/tests/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryTests.java @@ -23,9 +23,9 @@ import android.util.Log; import com.android.inputmethod.latin.ExpandableBinaryDictionary; import com.android.inputmethod.latin.NgramContext; import com.android.inputmethod.latin.NgramContext.WordInfo; +import com.android.inputmethod.latin.common.FileUtils; import com.android.inputmethod.latin.utils.BinaryDictionaryUtils; import com.android.inputmethod.latin.utils.DistracterFilter; -import com.android.inputmethod.latin.utils.FileUtils; import java.io.File; import java.io.FilenameFilter; diff --git a/tests/src/com/android/inputmethod/latin/utils/BinaryDictionaryUtilsTests.java b/tests/src/com/android/inputmethod/latin/utils/BinaryDictionaryUtilsTests.java index 131865ab2..f50b8e0b8 100644 --- a/tests/src/com/android/inputmethod/latin/utils/BinaryDictionaryUtilsTests.java +++ b/tests/src/com/android/inputmethod/latin/utils/BinaryDictionaryUtilsTests.java @@ -20,6 +20,8 @@ import android.test.AndroidTestCase; import android.test.suitebuilder.annotation.LargeTest; import com.android.inputmethod.latin.BinaryDictionary; +import com.android.inputmethod.latin.common.FileUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.makedict.DictionaryHeader; import com.android.inputmethod.latin.makedict.FormatSpec; diff --git a/tests/src/com/android/inputmethod/latin/utils/CapsModeUtilsTests.java b/tests/src/com/android/inputmethod/latin/utils/CapsModeUtilsTests.java index 4646a823d..9680d85b3 100644 --- a/tests/src/com/android/inputmethod/latin/utils/CapsModeUtilsTests.java +++ b/tests/src/com/android/inputmethod/latin/utils/CapsModeUtilsTests.java @@ -21,8 +21,8 @@ import android.test.AndroidTestCase; import android.test.suitebuilder.annotation.SmallTest; import android.text.TextUtils; +import com.android.inputmethod.latin.common.LocaleUtils; import com.android.inputmethod.latin.settings.SpacingAndPunctuations; -import com.android.inputmethod.latin.utils.LocaleUtils; import java.util.Locale; diff --git a/tests/src/com/android/inputmethod/latin/utils/CollectionUtilsTests.java b/tests/src/com/android/inputmethod/latin/utils/CollectionUtilsTests.java index dc4e2e4bb..47fd5feaa 100644 --- a/tests/src/com/android/inputmethod/latin/utils/CollectionUtilsTests.java +++ b/tests/src/com/android/inputmethod/latin/utils/CollectionUtilsTests.java @@ -19,6 +19,8 @@ package com.android.inputmethod.latin.utils; import android.test.AndroidTestCase; import android.test.suitebuilder.annotation.SmallTest; +import com.android.inputmethod.latin.common.CollectionUtils; + import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; diff --git a/tools/dicttool/Android.mk b/tools/dicttool/Android.mk index 42659253a..1a9f029ae 100644 --- a/tools/dicttool/Android.mk +++ b/tools/dicttool/Android.mk @@ -47,14 +47,10 @@ LATINIME_SRC_FILES_FOR_DICTTOOL := \ latin/Dictionary.java \ latin/NgramContext.java \ latin/SuggestedWords.java \ - latin/settings/NativeSuggestOptions.java \ latin/settings/SettingsValuesForSuggestion.java \ latin/utils/BinaryDictionaryUtils.java \ latin/utils/CombinedFormatUtils.java \ - latin/utils/CoordinateUtils.java \ - latin/utils/FileUtils.java \ - latin/utils/JniUtils.java \ - latin/utils/LocaleUtils.java + latin/utils/JniUtils.java LATINIME_OVERRIDABLE_SRC_FILES_FOR_DICTTOOL := \ latin/define/DebugFlags.java diff --git a/tools/dicttool/src/com/android/inputmethod/latin/dicttool/Test.java b/tools/dicttool/src/com/android/inputmethod/latin/dicttool/Test.java index b6383d788..e2dd5199b 100644 --- a/tools/dicttool/src/com/android/inputmethod/latin/dicttool/Test.java +++ b/tools/dicttool/src/com/android/inputmethod/latin/dicttool/Test.java @@ -16,10 +16,10 @@ package com.android.inputmethod.latin.dicttool; +import com.android.inputmethod.latin.common.FileUtils; import com.android.inputmethod.latin.makedict.BinaryDictDecoderEncoderTests; import com.android.inputmethod.latin.makedict.BinaryDictEncoderFlattenTreeTests; import com.android.inputmethod.latin.makedict.FusionDictionaryTest; -import com.android.inputmethod.latin.utils.FileUtils; import java.io.File; import java.io.IOException; |