Merge remote-tracking branch 'goog/master' into mergescriptpackage
Conflicts: java/res/values-af/strings.xml java/res/values-cs/strings.xml java/res/values-et/strings.xml java/res/values-fi/strings.xml java/res/values-hi/strings.xml java/res/values-hr/strings.xml java/res/values-hu/strings.xml java/res/values-in/strings.xml java/res/values-ja/strings.xml java/res/values-ko/strings.xml java/res/values-lt/strings.xml java/res/values-lv/strings.xml java/res/values-ms/strings.xml java/res/values-pt/strings.xml java/res/values-ro/strings.xml java/res/values-ru/strings.xml java/res/values-sk/strings.xml java/res/values-sl/strings.xml java/res/values-sr/strings.xml java/res/values-sw/strings.xml java/res/values-tr/strings.xml java/res/values-vi/strings.xml java/res/values-zh-rCN/strings.xml java/res/values-zh-rTW/strings.xml Change-Id: Ib4141aca0b35148d62d22d4f32309f890c84303amain
commit
44456dcbf2
|
@ -28,9 +28,7 @@ LOCAL_JNI_SHARED_LIBRARIES := libjni_latinime
|
|||
# We want to install libjni_latinime.so to the system partition if LatinIME gets installed.
|
||||
LOCAL_REQUIRED_MODULES := libjni_latinime
|
||||
|
||||
LOCAL_STATIC_JAVA_LIBRARIES := android-common
|
||||
LOCAL_STATIC_JAVA_LIBRARIES += inputmethod-common
|
||||
LOCAL_STATIC_JAVA_LIBRARIES += android-support-v4
|
||||
LOCAL_STATIC_JAVA_LIBRARIES := android-common inputmethod-common android-support-v4
|
||||
|
||||
# Do not compress dictionary files to mmap dict data runtime
|
||||
LOCAL_AAPT_FLAGS := -0 .dict
|
||||
|
|
|
@ -18,6 +18,8 @@
|
|||
coreApp="true"
|
||||
package="com.android.inputmethod.latin">
|
||||
|
||||
<uses-sdk android:minSdkVersion="16" android:targetSdkVersion="16" />
|
||||
|
||||
<uses-permission android:name="android.permission.VIBRATE"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
|
||||
<uses-permission android:name="android.permission.READ_USER_DICTIONARY" />
|
||||
|
@ -26,7 +28,8 @@
|
|||
<application android:label="@string/aosp_android_keyboard_ime_name"
|
||||
android:icon="@drawable/ic_ime_settings"
|
||||
android:backupAgent="BackupAgent"
|
||||
android:killAfterRestore="false">
|
||||
android:killAfterRestore="false"
|
||||
android:supportsRtl="true">
|
||||
|
||||
<service android:name="LatinIME"
|
||||
android:label="@string/aosp_android_keyboard_ime_name"
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Gebaseer op vorige woord"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Gebaarinvoer"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Voer \'n woord in deur die letters van \'n woord te trek"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Wys gebaarspoor"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Wys gebaar se woord"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Wys swewende voorskouwoord saam met die gebaar"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Gestoor"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Gaan"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Volgende"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Soek"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punt"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Verander taal"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Volgende"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Vorige"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift geaktiveer"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Kasslot geaktiveer"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift gedeaktiveer"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"በቀዳሚው ቃል ላይ የተመሠረተ"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"የእጅ ምልክት ግብዓት"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"የአንድ ቃል ፊደሎችን በመከታተል አንድ ቃል አስገባ"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"ምልክት የሚሄድበት መንገድ አሳይ"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"የምልክት ቃል አሳይ"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"ተንሳፋፊ የቅድመ እይታ ቃል ከምልክት ጋር አሳይ"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : ተቀምጧል"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"ሂድ"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"በመቀጠል"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"ተመለስ"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"ፍለጋ"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"ነጥብ"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"ቋንቋ ቀይር"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"ቀጣይ"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"ቀዳሚ"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"ቅያር ቁልፍ ነቅቷል"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"አቢያት ማድረጊያ ነቅቷል"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"ቅያር ተሰናክሏል"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"استنادًا إلى الكلمة السابقة"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"إدخال الإيماءة"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"يمكنك إدخال كلمة من خلال تتبع أحرف كلمة ما"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"عرض مسار الإيماءة"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"عرض كلمة الإيماءة"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"عرض كلمة معاينة متحركة مع الإيماءة"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : تم الحفظ"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"تنفيذ"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"التالي"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"رجوع"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"بحث"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"نقطة"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"تبديل اللغة"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"التالي"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"السابق"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"تم تمكين Shift"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"تم تمكين Caps lock"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"تم تعطيل Shift"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"На аснове папярэдняга слова"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Уваход жэстам"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Увядзiце слова, адсочваючы лiтары"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Паказаць след жэста"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Паказаць слова жэста"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Паказаць плаваючы прагляд слова з жэстам"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Захаваныя"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Пачаць"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Далей"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Увод"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Пошук"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Кропка"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Пераключыць мову"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Далей"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Назад"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift уключаны"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock уключаны"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift адключаны"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Въз основа на предишната дума"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Въвеждане чрез жест"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Въвеждане на дума чрез проследяване на буквите й"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Следа на жестовете: Показване"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Показване на дума при жестове"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Показване на дума с плаваща визуализация при жест"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Запазено"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Старт"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Напред"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Търсене"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Точка"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Смяна на езика"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Следващ"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Предишен"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"„Shift“ е активиран"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"„Caps Lock“ е активиран"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"„Shift“ е деактивиран"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"En funció de la paraula anterior"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Entrada de gestos"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Dibuixa les lletres d\'una paraula per escriure-la"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mostra el recorregut del gest"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mostra paraules en fer gestos"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mostra la paraula de visualització prèvia flotant en fer gestos"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: desada"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Vés"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Següent"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Retorn"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Cerca"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punt"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Canvia l\'idioma"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Següent"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Anterior"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Maj activat"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Bloq Maj activat"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Maj desactivat"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Na základě předchozího slova"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Zadávání gesty"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Napište slovo zadáním jeho písmen."</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Zobrazovat stopu gesta"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Zobrazovat slovo gesta"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Zobrazovat plovoucí náhled slova gesta"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: Uloženo"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Přejít"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Další"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"vyhledávací tlačítko"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Tečka"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Přepnout jazyk"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Další"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Předchozí"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Klávesa Shift je aktivní"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Klávesa Caps Lock je aktivní"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Klávesa Shift je neaktivní"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Baseret på tidligere ord"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Berøringsindtastning"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Indtast et ord ved at skrive bogstaverne for et ord med fingeren"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Vis spor af berøring"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Vis berøringsord"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Vis flydende eksempelord under berøring"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: Gemt"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Gå"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Næste"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Tilbage"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Søg"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punktum"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Skift sprog"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Næste"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Forrige"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Skift er aktiveret"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock er aktiveret"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Skift er deaktiveret"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Auf Grundlage des vorherigen Wortes"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Bewegungseingabe"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Wort durch Nachzeichnen der Buchstaben eingeben"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Spur der Bewegung anzeigen"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Wort bei Bewegung anzeigen"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Vorgeschlagenes Wort bei Bewegung anzeigen"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: gespeichert"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Los"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Weiter"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Eingabe"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Suchen"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Aufzählungspunkt"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Sprache wechseln"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Nächste"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Vorherige"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Umschalttaste aktiviert"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Feststelltaste aktiviert"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Umschalttaste deaktiviert"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Βάσει προηγούμενης λέξης"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Καταχώριση κίνησης"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Καταχώριση μιας λέξης με εντοπισμό των γραμμάτων μιας λέξης"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Εμφάνιση διαδρομής χειρονομίας"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Εμφάνιση λέξης χειρονομίας"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Εμφάνιση κινούμενης προεπισκόπησης λέξης με χειρονομία"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Αποθηκεύτηκε"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Μετ."</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Επόμενο"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Πλήκτρο Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Αναζήτηση"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Κουκκίδα"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Αλλαγή γλώσσας"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Επόμενο"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Προηγούμενο"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Το Shift ενεργοποιημένο"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Το Caps lock είναι ενεργοποιημένο"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Το Shift είναι απενεργοποιημένο"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Based on previous word"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Gesture input"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Input a word by tracing the letters of a word"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Show gesture trail"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Show gesture word"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Show floating preview word with gesture"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Saved"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Go"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Next"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Search"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Dot"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Switch language"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Next"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Previous"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift enabled"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock enabled"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift disabled"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Según la palabra anterior"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Entrada de gestos"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Ingresa una palabra trazando sus letras."</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mostrar recorrido de gesto"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mostrar palabra de gesto"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mostrar palabra de vista previa flotante al realizar gestos"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: guardada"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Ir"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Siguiente"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Volver"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Buscar"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punto"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Cambiar idioma"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Siguiente"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Anterior"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Se activó el modo Mayúscula."</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Se activó el bloqueo de mayúsculas."</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Se desactivó el modo Mayúscula"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Según la palabra anterior"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Entrada de gestos"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Trazar las letras de una palabra para introducirla"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mostrar recorrido del gesto"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mostrar palabra del gesto"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mostrar la palabra de vista previa flotante al realizar un gesto"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: guardada"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Ir"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Sig."</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Tecla Intro"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Buscar"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punto"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Cambiar idioma"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Siguiente"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Anterior"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Mayúsculas habilitadas"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Bloqueo de mayúsculas habilitado"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Mayúsculas inhabilitadas"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Eelmise sõna põhjal"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Liigutusega sisest."</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Sisestage sõna, kirjutades sõna tähed sõrmega"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Näita liigutuse jälge"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Näita liigutuse sõna"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Ujuva sõna eelvaate näitamine koos liigutusega"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : salvestatud"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Mine"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Edasi"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Tagasi"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Otsing"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punkt"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Keele vahetamine"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Järgmine"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Eelmine"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Tõstuklahv on lubatud"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Suurtähelukk on lubatud"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Tõstuklahv on keelatud"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"بر اساس کلمه قبلی"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"ورودی اشاره"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"با دنبال کردن حروف یک کلمه، کلمه را وارد کنید"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"نمایش نسخه آزمایشی حرکت"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"نمایش کلمه در طول ورودی حرکتی"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"نمایش کلمه پیشنمایش متحرک با حرکت"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : ذخیره شد"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"برو"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"بعدی"</string>
|
||||
|
@ -94,6 +97,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"جستجو"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"نقطه"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"تغییر زبان"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"بعدی"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"قبلی"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift فعال است"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock فعال شد"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift غیرفعال است"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Perustuu edelliseen sanan"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Eleiden syöttö"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Syötä sana piirtämällä kirjaimet sormella"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Näytä eleen jälki"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Näytä elesanat"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Näytä eleen yhteydessä kelluva esikatselusana"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Tallennettu"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Siirry"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Seur."</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Haku"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Piste"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Vaihda kieli"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Seuraava"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Edellinen"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Vaihto päällä"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock päällä"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Vaihto pois käytöstä"</string>
|
||||
|
|
|
@ -25,5 +25,7 @@
|
|||
<!-- Symbols that should promote magic spaces into real space -->
|
||||
<string name="phantom_space_promoting_symbols">;:!?([*&@{<>+=|</string>
|
||||
<!-- Symbols that do NOT separate words -->
|
||||
<string name="symbols_excluded_from_word_separators">\'</string>
|
||||
<!-- Note that this is identical to the default value, but since the above ones are different
|
||||
and those variables only make sense together, this is kept here for readability. -->
|
||||
<string name="symbols_excluded_from_word_separators">\'-</string>
|
||||
</resources>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Suggestions basées sur le mot précédent"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Saisie gestuelle"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Saisir un mot en traçant ses lettres avec le doigt"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Afficher le tracé du geste"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Afficher un mot lors du geste"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Afficher un aperçu flottant du mot lors de la saisie gestuelle"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : enregistré"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"OK"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Suiv."</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Entrée"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Rechercher"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Point"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Changer de langue"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Touche suivante"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Touche précédente"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Touche Maj activée"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Verrouillage des majuscules activé"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Touche Maj désactivée"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"पिछले शब्द के आधार पर"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"जेस्चर इनपुट"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"किसी शब्द के अक्षरों को ट्रेस करके कोई शब्द इनपुट करें"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"जेस्चर ट्रेल दिखाएं"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"जेस्चर शब्द दिखाएं"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"जेस्चर के साथ फ़्लोटिंग पूर्वावलोकन शब्द दिखाएं"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: सहेजा गया"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"जाएं"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"अगला"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"रिटर्न"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"खोजें"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"बिंदु"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"भाषा स्विच करें"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"अगला"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"पिछला"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift सक्षम किया गया"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock सक्षम किया गया"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift अक्षम किया गया"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Na temelju prethodne riječi"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Unos pokretom"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Unos riječi ispisivanjem slova riječi"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Prikaži trag pokreta"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Prikaži riječ pokreta"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Prikaži lebdeći pregled riječi uz pokret"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Spremljeno"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Idi"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Dalje"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Pretraživanje"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Točka"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Promijeni jezik"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Sljedeće"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Prethodno"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Omogućena tipka Shift"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Omogućeno pisanje velikih slova"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Onemogućena tipka Shift"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Az előző szó alapján"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Kézi bevitel"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Szó beírása a betűk megrajzolásával"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mozdulat irányának mutatása"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mozdulatot leíró szó mutatása"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mozdulatot leíró szó mutatása lebegő előnézetben"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : mentve"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Ugrás"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Tovább"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Keresés"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Pont"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Nyelvek felcserélése"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Következő"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Előző"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift bekapcsolva"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock bekapcsolva"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift kikapcsolva"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Berdasarkan kata sebelumnya"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Masukan isyarat"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Masukkan kata dengan melacak huruf dari sebuah kata"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Tampilkan jalur isyarat"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Tampilkan kata isyarat"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Tampilkan kata pratinjau melayang dengan isyarat"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Telah disimpan"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Buka"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Berikutnya"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Kembali"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Telusuri"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Titik"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Ganti bahasa"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Berikutnya"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Sebelumnya"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift diaktifkan"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock diaktifkan"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift dinonaktifkan"</string>
|
||||
|
|
|
@ -1,23 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
/*
|
||||
**
|
||||
** Copyright 2009, 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.
|
||||
*/
|
||||
-->
|
||||
<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
|
||||
<!-- Symbols that do NOT separate words -->
|
||||
<string name="symbols_excluded_from_word_separators"></string>
|
||||
</resources>
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"In base alla parola precedente"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Inserimento con gesti"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Inserisci una parola tracciandone le lettere"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mostra traccia con gesto"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mostra parola con gesto"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mostra parola di anteprima floating con gesto"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : parola salvata"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Vai"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Avanti"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Invio"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Cerca"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Pallino"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Cambia lingua"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Successivo"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Precedente"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Maiuscolo attivo"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Blocco maiuscole attivo"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Maiuscolo disattivato"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"בהתבסס על המילה הקודמת"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"קלט מחווה"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"הזן מילה על ידי החלקת האצבע מאות לאות"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"הצג שובל מחווה"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"הצג מילת מחווה"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"הצג תצוגה מקדימה צפה של המילה בזמן המחווה"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : נשמרה"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"בצע"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"הבא"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"חזור"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"חיפוש"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"נקודה"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"החלף שפה"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"הבא"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"הקודם"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift מופעל"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock מופעל"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift מושבת"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"前の語句に基づいた入力候補表示"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"ジェスチャー入力"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"単語の文字をトレースして単語を入力"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"ジェスチャートレイルを表示"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"ジェスチャーワードを表示"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"ジェスチャーでプレビューワードをフローティング表示できます"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>:保存しました"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"実行"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"次へ"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"検索"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"中点"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"言語を切り替え"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"次へ"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"前へ"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift有効"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock有効"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift解除"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"이전 단어에 기반한 추천"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"동작 입력"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"한번에 문자를 그려서 단어 입력"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"동작 흔적 표시"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"동작 단어 표시"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"동작에 따라 단어 미리보기 표시"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: 저장됨"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"이동"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"다음"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"리턴 키"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"검색"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"점"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"언어 전환"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"다음"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"이전"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift 사용"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock 사용"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift 사용중지"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Pagal ankstesnį žodį"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Įvestis gestais"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Įveskite žodį brėždami jo raides"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Rodyti gestų kelią"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Rodyti gesto žodį"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Rodyti kintantį peržiūros žodį gestu"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: išsaugota"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Pradėti"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Kitas"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Grįžti"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Ieškoti"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Taškas"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Keisti kalbą"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Kitas"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Ankstesnis"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Įgalintas antrasis lygis"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Įgalintos didžiosios raidės"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Antrasis lygis išjungtas"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Pamatojoties uz iepriekšējo vārdu"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Ievade ar žestu"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Ievadiet vārdu, norādot tā burtus."</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Rādīt žesta pēdas"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Rādīt žesta vārdu"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Rādīt peldošo priekšskatījuma vārdu ar žestu"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: saglabāts"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Sākt"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Tālāk"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Ievadīšanas taustiņš"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Meklēt"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punkts"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Mainīt valodu"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Nākamā"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Iepriekšējā"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Pārslēgšanas režīms iespējots"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Burtslēgs iespējots"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Pārslēgšanas režīms atspējots"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Berdasarkan perkataan sebelumnya"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Input gerak isyarat"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Masukkan perkataan dengan menyurih huruf perkataan itu."</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Tunjukkan jejak gerak isyarat"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Tunjukkan perkataan gerak isyarat"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Tunjukkan perkataan pratonton terapung dengan gerak isyarat"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Disimpan"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Pergi"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Seterusnya"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Carian"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Titik"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Tukar bahasa"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Seterusnya"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Sebelumnya"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Kunci anjak didayakan"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Kunci huruf besar didayakan"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Kunci anjak dilumpuhkan"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Basert på det forrige ordet"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Bevegelseskommandoer"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Angi et ord ved å skrive bokstavene på skjermen med fingeren"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Vis bevegelsesspor"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Vis bevegelsesord"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Vis flytende forhåndsvisningsord under bevegelser"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: Lagret"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Utfør"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Neste"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Søk"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Prikk"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Bytt språk"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Neste"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Forrige"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift er aktivert"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock er aktivert"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift er deaktivert"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Op basis van het vorige woord"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Invoer met gebaren"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Voer een woord in door de letters van een woord te volgen"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Gebarenspoor weergeven"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Woord met gebaar weergeven"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Zwevend voorbeeldwoord met gebaar weergeven"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: opgeslagen"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Start"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Verder"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Zoeken"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Stip"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Taal wijzigen"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Volgende"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Vorige"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift ingeschakeld"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock ingeschakeld"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift uitgeschakeld"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Na podstawie poprzedniego słowa"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Wprowadzanie gestem"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Podaj słowo, pisząc litery palcem"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Pokazuj ślad gestu"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Podpowiadaj przy pisaniu gestem"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Pokazuj pływający podgląd słowa podczas pisania gestem"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Zapisano"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"OK"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Dalej"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Szukaj"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punkt"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Przełącz język"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Dalej"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Wstecz"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift włączony"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock włączony"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift wyłączony"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Com base na palavra anterior"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Introd. por gestos"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Introduza uma palavra, desenhando as letras de uma palavra"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mostrar percurso do gesto"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mostrar palavra gesto"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mostrar palavra de visualização flutuante com gesto"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: guardada"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"OK"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Avançar"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Pesquisar"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Ponto"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Mudar de idioma"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Seguinte"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Anterior"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift ativado"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock ativado"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift desativado"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Com base na palavra anterior"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Entrada por gesto"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Introduza uma palavra traçando suas letras"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Mostrar percurso do gesto"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Mostrar palavra do gesto"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Mostrar visualização flutuante da palavra com gesto"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Salvo"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Ir"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Avançar"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Voltar"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Pesquisar"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Ponto"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Alterar idioma"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Próximo"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Anterior"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift ativado"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock ativado"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift desativado"</string>
|
||||
|
|
|
@ -96,6 +96,12 @@
|
|||
<skip />
|
||||
<!-- no translation found for gesture_input_summary (7019742443455085809) -->
|
||||
<skip />
|
||||
<!-- no translation found for gesture_preview_trail (3802333369335722221) -->
|
||||
<skip />
|
||||
<!-- no translation found for gesture_floating_preview_text (6859416520117939680) -->
|
||||
<skip />
|
||||
<!-- no translation found for gesture_floating_preview_text_summary (3333754126434989709) -->
|
||||
<skip />
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Memorisà"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Dai"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Vinavant"</string>
|
||||
|
@ -151,6 +157,12 @@
|
|||
<skip />
|
||||
<!-- no translation found for spoken_description_dot (40711082435231673) -->
|
||||
<skip />
|
||||
<!-- no translation found for spoken_description_language_switch (5507091328222331316) -->
|
||||
<skip />
|
||||
<!-- no translation found for spoken_description_action_next (8636078276664150324) -->
|
||||
<skip />
|
||||
<!-- no translation found for spoken_description_action_previous (800872415009336208) -->
|
||||
<skip />
|
||||
<!-- no translation found for spoken_description_shiftmode_on (5700440798609574589) -->
|
||||
<skip />
|
||||
<!-- no translation found for spoken_description_shiftmode_locked (593175803181701830) -->
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Bazate pe cuvântul precedent"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Utilizaţi gesturi"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Introduceţi un cuvânt desenând literele acestuia"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Se afişează urma gestului"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Sugestie cuvinte la gesturi"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Se afişează previzualizarea cuvântului flotant la gesturi"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: salvat"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"OK"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Înainte"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Căutaţi"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punct"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Schimbaţi limba"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Înainte"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Înapoi"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Tasta Shift a fost activată"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Tasta Caps Lock a fost activată"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Tasta Shift a fost dezactivată"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Подсказки, основанные на предыдущих словах"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Ввод жестами"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Перемещайте палец от буквы к букве, чтобы составить слово"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Рисовать линию"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Подсказывать слово"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Показывать подсказку во время ввода"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: сохранено"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Поиск"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Далее"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Клавиша \"Ввод\""</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Поиск"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Точка"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Сменить язык"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Далее"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Назад"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Верхний регистр включен"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock включен"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Верхний регистр отключен"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Na základe predchádzajúceho slova"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Zadávanie gestami"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Napíšte slovo zadaním jeho písmen"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Zobrazovať stopu gesta"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Zobrazovať slovo gesta"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Zobrazovať plávajúcu ukážku slova gesta"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Uložené"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Hľadať"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Ďalej"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Hľadať"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Bodka"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Prepnúť jazyk"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Ďalšie"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Predchádzajúce"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Kláves Shift je povolený"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Kláves Caps Lock je povolený"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Kláves Shift je zakázaný"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Na podlagi prejšnje besede"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Vnos s potezo"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Vnašanje besede z drsenjem po zaslonu od črke do črke"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Prikaži pot poteze"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Pokaži besedo za potezo"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Pokaži plavajoči predogled besede za potezo"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: shranjeno"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Pojdi"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Naprej"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Vračalka"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Iskanje"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Pika"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Preklop jezika"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Naprej"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Nazaj"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Način »Shift« je omogočen"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Način »Caps Lock« je omogočen"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Način »Shift« je onemogočen"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"На основу претходне речи"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Унос покретом"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Унесите реч исписивањем слова речи"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Прикажи траг покрета"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Прикажи реч уз покрет"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Приказ плутајућег прегледа речи уз покрет"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Сачувано"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Иди"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Следеће"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Претражи"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Тачка"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Пребаци језик"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Следеће"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Претходно"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift је омогућен"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock је омогућен"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift је онемогућен"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Baserat på föregående ord"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Gestinmatning"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Skriv ett ord för hand genom att rita bokstäverna i ordet"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Visa spår efter rörelse"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Visa svävande ord för rörelse"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Visa förhandsgranskning av svävande ord med rörelse"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>: sparat"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Kör"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Nästa"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Retur"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Sök"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Punkt"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Byt språk"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Nästa"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Föregående"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Skift är aktiverat"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock är aktiverat"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Skift är inaktiverat"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Kulingana na neno la awali"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Ingizo la ishara"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Ingiza neno kwa kufuatilia herufi za neno"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Onyesha njia ya ishara"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Onyesha neno la ishara"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Onyesha neno hakiki linaloelea lililo na ishara"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Imehifadhiwa"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Nenda"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Ifuatayo"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Rudi"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Tafuta"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Nukta"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Badili lugha"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Inayofuata"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Iliyotangulia"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift imewezeshwa"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps lock imewezeshwa"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift imelemazwa"</string>
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
-->
|
||||
|
||||
<resources>
|
||||
<!-- Device form factor. This value must be aligned with {@link KeyboardId.DEVICE_FORM_FACTOR_TABLET7} -->
|
||||
<integer name="config_device_form_factor">1</integer>
|
||||
<bool name="config_enable_show_voice_key_option">false</bool>
|
||||
<bool name="config_enable_show_popup_on_keypress_option">false</bool>
|
||||
<bool name="config_enable_bigram_suggestions_option">false</bool>
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
-->
|
||||
|
||||
<resources>
|
||||
<!-- Device form factor. This value must be aligned with {@link KeyboardId.DEVICE_FORM_FACTOR_TABLET10} -->
|
||||
<integer name="config_device_form_factor">2</integer>
|
||||
<bool name="config_enable_show_voice_key_option">false</bool>
|
||||
<bool name="config_enable_show_popup_on_keypress_option">false</bool>
|
||||
<bool name="config_enable_bigram_suggestions_option">false</bool>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"ตามคำก่อนหน้า"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"ป้อนท่าทางสัมผัส"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"ป้อนคำโดยลากนิ้วเป็นรูปตัวอักษรที่อยู่ในคำ โดยไม่ยกนิ้วขึ้น"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"แสดงรอยทางเดินของท่าทาง"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"แสดงคำแนะนำท่าทาง"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"แสดงตัวอย่างคำแนะนำพร้อมด้วยท่าทาง"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : บันทึกแล้ว"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"ไป"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"ถัดไป"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"ค้นหา"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"เครื่องหมายจุด"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"เปลี่ยนภาษา"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"ถัดไป"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"ก่อนหน้า"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"เปิดใช้งาน Shift แล้ว"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"เปิดใช้งาน Caps Lock แล้ว"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"ปิดใช้งาน Shift แล้ว"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Batay sa nakaraang salita"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Pagpasok ng galaw"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Magpasok ng salita sa gamit ang pagsulat sa mga titik ng salita"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Ipakita ang trail ng galaw"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Ipakita ang salita ng galaw"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Ipakita ang lumulutang na preview ng salita na may galaw"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Na-save"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Punta"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Susunod"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Bumalik"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Paghahanap"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Tuldok"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Magpalit ng wika"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Susunod"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Nakaraan"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Pinagana ang shift"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Pinagana ang caps lock"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Hindi pinagana ang shift"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Önceki kelimeye dayanarak"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Hareket girişi"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Bir kelimeyi harflerini izleyerek girin"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Hareket izini göster"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Hareketle yazılan kelimeyi göster"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Hareketle kayan önizleme kelimesini göster"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Kaydedildi"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Git"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"İleri"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Enter"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Ara"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Nokta"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Dili değiştir"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Sonraki"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Önceki"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Üst karakter etkin"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Büyük harf kilidi etkin"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Üst karakter devre dışı"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"На основі попереднього слова"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Введення жестами"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Введіть слово, малюючи літери, з яких воно складається"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Показувати слід жестів"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Показувати слово для жесту"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Показувати спливаючий перегляд слова під час жесту"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : збережено"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Іти"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Далі"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Клавіша Return"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Пошук"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Крапка"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Змінити мову"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Далі"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Назад"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift увімкнено"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Caps Lock увімкнено"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift вимкнено"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Dựa trên từ trước đó"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Nhập bằng cử chỉ"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Nhập từ bằng cách lần theo các chữ cái của từ"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Hiển thị vệt cử chỉ"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Hiển thị từ theo cử chỉ"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Hiển thị từ xem trước nổi bằng cử chỉ"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Đã lưu"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Tìm"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Tiếp theo"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Quay lại"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Tìm kiếm"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Dấu chấm"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Chuyển ngôn ngữ"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Tiếp theo"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Trước"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Đã bật Shift"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Đã bật Caps lock"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Đã tắt Shift"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"根据上一个字词提供建议"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"手势输入"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"连笔书写输入字词"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"显示手指操作轨迹"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"显示手指操作文字"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"进行手指操作时显示浮动预览文字"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>:已保存"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"开始"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"下一步"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"返回"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"搜索"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"点"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"切换语言"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"下一个"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"上一个"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift 模式已启用"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"大写锁定已启用"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift 模式已停用"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"根據上一個字詞產生"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"手勢輸入"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"以手指寫出字詞中字母的方式來輸入字詞"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"顯示手勢軌跡"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"顯示手勢字詞"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"使用手勢輸入時顯示浮動預覽字詞"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g>:已儲存"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"開始"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"繼續"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"返回"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"搜尋"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"點"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"切換語言"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"下一步"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"上一步"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"Shift 鍵已啟用"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"大寫鎖定已啟用"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"Shift 鍵已停用"</string>
|
||||
|
|
|
@ -60,6 +60,9 @@
|
|||
<string name="bigram_prediction_summary" msgid="3253961591626441019">"Ngokususela egameni langaphambilini"</string>
|
||||
<string name="gesture_input" msgid="3310827802759290774">"Okokufaka kokuthinta"</string>
|
||||
<string name="gesture_input_summary" msgid="7019742443455085809">"Faka igama ngokulandela ngomkhondo izinhlamvu zegama"</string>
|
||||
<string name="gesture_preview_trail" msgid="3802333369335722221">"Bonisa i-trail yokuthinta"</string>
|
||||
<string name="gesture_floating_preview_text" msgid="6859416520117939680">"Bonisa igama lokuthinta"</string>
|
||||
<string name="gesture_floating_preview_text_summary" msgid="3333754126434989709">"Bonisa igama lokuhlola kuqala elintantayo nokuthinta"</string>
|
||||
<string name="added_word" msgid="8993883354622484372">"<xliff:g id="WORD">%s</xliff:g> : Kulondoloziwe"</string>
|
||||
<string name="label_go_key" msgid="1635148082137219148">"Iya"</string>
|
||||
<string name="label_next_key" msgid="362972844525672568">"Okulandelayo"</string>
|
||||
|
@ -90,6 +93,9 @@
|
|||
<string name="spoken_description_return" msgid="8178083177238315647">"Buyisela"</string>
|
||||
<string name="spoken_description_search" msgid="1247236163755920808">"Sesha"</string>
|
||||
<string name="spoken_description_dot" msgid="40711082435231673">"Icashazi"</string>
|
||||
<string name="spoken_description_language_switch" msgid="5507091328222331316">"Shintsha ulimi"</string>
|
||||
<string name="spoken_description_action_next" msgid="8636078276664150324">"Okulandelayo"</string>
|
||||
<string name="spoken_description_action_previous" msgid="800872415009336208">"Okwangaphambilini"</string>
|
||||
<string name="spoken_description_shiftmode_on" msgid="5700440798609574589">"U-Shift uvunyelwe"</string>
|
||||
<string name="spoken_description_shiftmode_locked" msgid="593175803181701830">"Ofeleba bavunyelwe"</string>
|
||||
<string name="spoken_description_shiftmode_off" msgid="657219998449174808">"U-Shift uvimbelwe"</string>
|
||||
|
|
|
@ -118,6 +118,18 @@
|
|||
<enum name="italic" value="2" />
|
||||
<enum name="boldItalic" value="3" />
|
||||
</attr>
|
||||
|
||||
<attr name="gestureFloatingPreviewTextSize" format="dimension" />
|
||||
<attr name="gestureFloatingPreviewTextColor" format="color" />
|
||||
<attr name="gestureFloatingPreviewTextOffset" format="dimension" />
|
||||
<attr name="gestureFloatingPreviewTextShadingColor" format="color" />
|
||||
<attr name="gestureFloatingPreviewTextShadingBorder" format="dimension" />
|
||||
<attr name="gestureFloatingPreviewTextShadowColor" format="color" />
|
||||
<attr name="gestureFloatingPreviewTextShadowBorder" format="dimension" />
|
||||
<attr name="gestureFloatingPreviewTextConnectorColor" format="color" />
|
||||
<attr name="gestureFloatingPreviewTextConnectorWidth" format="dimension" />
|
||||
<attr name="gesturePreviewTrailColor" format="color" />
|
||||
<attr name="gesturePreviewTrailWidth" format="dimension" />
|
||||
</declare-styleable>
|
||||
|
||||
<declare-styleable name="MainKeyboardView">
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
-->
|
||||
|
||||
<resources>
|
||||
<!-- Device form factor. This value must be aligned with {@link KeyboardId.DEVICE_FORM_FACTOR_PHONE} -->
|
||||
<integer name="config_device_form_factor">0</integer>
|
||||
<bool name="config_use_fullscreen_mode">false</bool>
|
||||
<bool name="config_enable_show_voice_key_option">true</bool>
|
||||
<bool name="config_enable_show_popup_on_keypress_option">true</bool>
|
||||
|
|
|
@ -93,4 +93,12 @@
|
|||
<dimen name="more_suggestions_hint_text_size">27dp</dimen>
|
||||
<integer name="suggestions_count_in_strip">3</integer>
|
||||
<integer name="center_suggestion_percentile">36</integer>
|
||||
|
||||
<!-- Gesture preview parameters -->
|
||||
<dimen name="gesture_preview_trail_width">2.5dp</dimen>
|
||||
<dimen name="gesture_floating_preview_text_size">35dp</dimen>
|
||||
<dimen name="gesture_floating_preview_text_offset">75dp</dimen>
|
||||
<dimen name="gesture_floating_preview_text_shadow_border">17.5dp</dimen>
|
||||
<dimen name="gesture_floating_preview_text_shading_border">7.5dp</dimen>
|
||||
<dimen name="gesture_floating_preview_text_connector_width">1.0dp</dimen>
|
||||
</resources>
|
||||
|
|
|
@ -111,10 +111,16 @@
|
|||
<!-- Description for "next word suggestion" option. This displays suggestions even when there is no input, based on the previous word. -->
|
||||
<string name="bigram_prediction_summary">Based on previous word</string>
|
||||
|
||||
<!-- Option to enable gesture input. The user can input a word by tracing the letters of a word without releasing the finger from the screen. [CHAR LIMIT=20]-->
|
||||
<!-- Option to enable gesture input. The user can input a word by tracing the letters of a word without releasing the finger from the screen. [CHAR LIMIT=30]-->
|
||||
<string name="gesture_input">Gesture input</string>
|
||||
<!-- Description for "gesture_input" option. The user can input a word by tracing the letters of a word without releasing the finger from the screen. [CHAR LIMIT=65]-->
|
||||
<string name="gesture_input_summary">Input a word by tracing the letters of a word</string>
|
||||
<!-- Option to enable gesture trail preview. The user can see a trail of the gesture during gesture input. [CHAR LIMIT=30]-->
|
||||
<string name="gesture_preview_trail">Show gesture trail</string>
|
||||
<!-- Option to enable gesture floating text preview. The user can see a suggested word floating under the moving finger during a gesture input. [CHAR LIMIT=30]-->
|
||||
<string name="gesture_floating_preview_text">Show gesture word</string>
|
||||
<!-- Description for "gesture_floating_preview_text" option. The user can see a suggested word floating under the moving finger during a gesture input. [CHAR LIMIT=65]-->
|
||||
<string name="gesture_floating_preview_text_summary">Show floating preview word with gesture</string>
|
||||
|
||||
<!-- Indicates that a word has been added to the dictionary -->
|
||||
<string name="added_word"><xliff:g id="word">%s</xliff:g> : Saved</string>
|
||||
|
@ -181,6 +187,12 @@
|
|||
<string name="spoken_description_search">Search</string>
|
||||
<!-- Spoken description for the "U+2022" (BULLET) keyboard key. -->
|
||||
<string name="spoken_description_dot">Dot</string>
|
||||
<!-- Spoken description for the "Switch language" keyboard key. -->
|
||||
<string name="spoken_description_language_switch">Switch language</string>
|
||||
<!-- Spoken description for the "Next" action keyboard key. -->
|
||||
<string name="spoken_description_action_next">Next</string>
|
||||
<!-- Spoken description for the "Previous" action keyboard key. -->
|
||||
<string name="spoken_description_action_previous">Previous</string>
|
||||
|
||||
<!-- Spoken feedback after turning "Shift" mode on. -->
|
||||
<string name="spoken_description_shiftmode_on">Shift enabled</string>
|
||||
|
@ -303,6 +315,15 @@
|
|||
<!-- Description for English (United States) keyboard subtype with explicit keyboard layout [CHAR LIMIT=25]
|
||||
This should be identical to subtype_en_US aside from the trailing (%s). -->
|
||||
<string name="subtype_with_layout_en_US">English (US) (<xliff:g id="layout">%s</xliff:g>)</string>
|
||||
<!-- TODO: Uncomment once we can handle IETF language tag with script name specified.
|
||||
Description for Serbian Cyrillic keyboard subtype [CHAR LIMIT=25]
|
||||
<string name="subtype_serbian_cyrillic">Serbian (Cyrillic)</string>
|
||||
Description for Serbian Latin keyboard subtype [CHAR LIMIT=25]
|
||||
<string name="subtype_serbian_latin">Serbian (Latin)</string>
|
||||
Description for Serbian Latin keyboard subtype with explicit keyboard layout [CHAR LIMIT=25]
|
||||
This should be identical to subtype_serbian_latin aside from the trailing (%s).
|
||||
<string name="subtype_with_layout_sr-Latn">Serbian (Latin) (<xliff:g id="layout">%s</xliff:g>)</string>
|
||||
-->
|
||||
<!-- Description for language agnostic keyboard subtype [CHAR LIMIT=25] -->
|
||||
<string name="subtype_no_language">No language</string>
|
||||
<!-- Description for language agnostic QWERTY keyboard subtype [CHAR LIMIT=25] -->
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
limitations under the License.
|
||||
-->
|
||||
|
||||
<resources>
|
||||
<resources xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<!-- Theme "Basic" -->
|
||||
<style name="Keyboard">
|
||||
<!-- This should be aligned with KeyboardSwitcher.KEYBOARD_THEMES[] -->
|
||||
|
@ -67,6 +67,18 @@
|
|||
<item name="shadowColor">#BB000000</item>
|
||||
<item name="shadowRadius">2.75</item>
|
||||
<item name="backgroundDimAlpha">128</item>
|
||||
<!-- android:color/holo_blue_light=#FF33B5E5 -->
|
||||
<item name="gestureFloatingPreviewTextSize">@dimen/gesture_floating_preview_text_size</item>
|
||||
<item name="gestureFloatingPreviewTextColor">@android:color/white</item>
|
||||
<item name="gestureFloatingPreviewTextOffset">@dimen/gesture_floating_preview_text_offset</item>
|
||||
<item name="gestureFloatingPreviewTextShadingColor">@android:color/holo_blue_light</item>
|
||||
<item name="gestureFloatingPreviewTextShadingBorder">@dimen/gesture_floating_preview_text_shading_border</item>
|
||||
<item name="gestureFloatingPreviewTextShadowColor">#FF252525</item>
|
||||
<item name="gestureFloatingPreviewTextShadowBorder">@dimen/gesture_floating_preview_text_shadow_border</item>
|
||||
<item name="gestureFloatingPreviewTextConnectorColor">@android:color/white</item>
|
||||
<item name="gestureFloatingPreviewTextConnectorWidth">@dimen/gesture_floating_preview_text_connector_width</item>
|
||||
<item name="gesturePreviewTrailColor">@android:color/holo_blue_light</item>
|
||||
<item name="gesturePreviewTrailWidth">@dimen/gesture_preview_trail_width</item>
|
||||
<!-- Common attributes of MainKeyboardView -->
|
||||
<item name="keyHysteresisDistance">@dimen/config_key_hysteresis_distance</item>
|
||||
<item name="touchNoiseThresholdTime">@integer/config_touch_noise_threshold_time</item>
|
||||
|
|
|
@ -24,15 +24,36 @@
|
|||
<switch>
|
||||
<case
|
||||
latin:languageCode="fa"
|
||||
latin:languageSwitchKeyEnabled="true"
|
||||
>
|
||||
<Key
|
||||
latin:keyStyle="languageSwitchKeyStyle" />
|
||||
<Key
|
||||
latin:keyStyle="spaceKeyStyle"
|
||||
latin:keyWidth="24.141%p" />
|
||||
<Key
|
||||
latin:keyStyle="zwnjKeyStyle" />
|
||||
</case>
|
||||
<case
|
||||
latin:languageCode="fa"
|
||||
latin:languageSwitchKeyEnabled="false"
|
||||
>
|
||||
<Key
|
||||
latin:keyStyle="spaceKeyStyle"
|
||||
latin:keyWidth="32.188%p" />
|
||||
<!-- U+200C: "" ZERO WIDTH NON-JOINER
|
||||
U+200D: "" ZERO WIDTH JOINER -->
|
||||
<Key
|
||||
latin:keyStyle="zwnjKeyStyle" />
|
||||
</case>
|
||||
<case
|
||||
latin:languageSwitchKeyEnabled="true"
|
||||
>
|
||||
<Key
|
||||
latin:keyStyle="languageSwitchKeyStyle" />
|
||||
<Key
|
||||
latin:keyStyle="spaceKeyStyle"
|
||||
latin:keyWidth="32.188%p" />
|
||||
</case>
|
||||
<!-- languageSwitchKeyEnabled="false" -->
|
||||
<default>
|
||||
<Key
|
||||
latin:keyStyle="spaceKeyStyle"
|
||||
|
|
|
@ -76,7 +76,7 @@
|
|||
<key-style
|
||||
latin:styleName="spaceKeyStyle"
|
||||
latin:code="!code/key_space"
|
||||
latin:keyActionFlags="noKeyPreview" />
|
||||
latin:keyActionFlags="noKeyPreview|enableLongPress" />
|
||||
<!-- U+200C: ZERO WIDTH NON-JOINER
|
||||
U+200D: ZERO WIDTH JOINER -->
|
||||
<key-style
|
||||
|
@ -99,6 +99,12 @@
|
|||
latin:keyIconDisabled="!icon/shortcut_key_disabled"
|
||||
latin:keyActionFlags="noKeyPreview"
|
||||
latin:backgroundType="functional" />
|
||||
<key-style
|
||||
latin:styleName="languageSwitchKeyStyle"
|
||||
latin:code="!code/key_language_switch"
|
||||
latin:keyIcon="!icon/language_switch_key"
|
||||
latin:keyActionFlags="noKeyPreview|altCodeWhileTyping|enableLongPress"
|
||||
latin:altCode="!code/key_space" />
|
||||
<key-style
|
||||
latin:styleName="settingsKeyStyle"
|
||||
latin:code="!code/key_settings"
|
||||
|
|
|
@ -33,9 +33,8 @@
|
|||
<include
|
||||
latin:keyboardLayout="@xml/rowkeys_east_slavic1"
|
||||
latin:keyLabelFlags="disableAdditionalMoreKeys|disableKeyHintLabel" />
|
||||
<!-- U+044A: "ъ" CYRILLIC SMALL LETTER HARD SIGN -->
|
||||
<Key
|
||||
latin:keyLabel="ъ" />
|
||||
latin:keyLabel="!text/keylabel_for_east_slavic_row1_12" />
|
||||
<Key
|
||||
latin:keyStyle="deleteKeyStyle"
|
||||
latin:keyWidth="fillRight" />
|
||||
|
|
|
@ -22,10 +22,12 @@
|
|||
|
||||
<!-- Supported subtypes
|
||||
keyboard_locale: script_name/keyboard_layout_set[:keyboard_locale]
|
||||
af: Afrikaans/qwerty
|
||||
ar: Arabic/arabic
|
||||
be: Belarusian/east_slavic
|
||||
bg: Bulgarian/bulgarian
|
||||
bg: Bulgarian/bulgarian_bds
|
||||
ca: Catalan/spanish
|
||||
cs: Czech/qwertz
|
||||
da: Danish/nordic
|
||||
de: German/qwertz
|
||||
|
@ -41,14 +43,16 @@
|
|||
hi: Hindi/hindi
|
||||
hr: Croatian/qwertz
|
||||
hu: Hungarian/qwertz
|
||||
in: Indonesian/qwerty # "id" is official language code of Indonesian.
|
||||
is: Icelandic/qwerty
|
||||
it: Italian/qwerty
|
||||
iw: Hebrew/hebrew
|
||||
iw: Hebrew/hebrew # "he" is official language code of Hebrew.
|
||||
ka: Georgian/georgian
|
||||
ky: Kyrgyz/east_slavic
|
||||
lt: Lithuanian/qwerty
|
||||
lv: Latvian/qwerty
|
||||
mk: Macedonian/south_slavic
|
||||
ms: Malay/qwerty
|
||||
nb: Norwegian Bokmål/nordic
|
||||
nl: Dutch/qwerty
|
||||
pl: Polish/qwerty
|
||||
|
@ -59,11 +63,15 @@
|
|||
sk: Slovak/qwerty
|
||||
sl: Slovenian/qwerty
|
||||
sr: Serbian/south_slavic
|
||||
(sr-Latn: Serbian/qwerty) # not yet implemented.
|
||||
sv: Swedish/nordic
|
||||
sw: Swahili/qwerty
|
||||
th: Thai/thai
|
||||
tl: Tagalog/spanish
|
||||
tr: Turkish/qwerty
|
||||
uk: Ukrainian/east_slavic
|
||||
vi: Vietnamese/qwerty
|
||||
zu: Zulu/qwerty
|
||||
zz: QWERTY/qwerty
|
||||
-->
|
||||
<!-- TODO: use <lang>_keyboard icon instead of a common keyboard icon. -->
|
||||
|
@ -84,6 +92,12 @@
|
|||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="TrySuppressingImeSwitcher,AsciiCapable,SupportTouchPositionCorrection"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="af"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="ar"
|
||||
|
@ -108,6 +122,12 @@
|
|||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=bulgarian_bds"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="ca"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=spanish,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="cs"
|
||||
|
@ -186,6 +206,13 @@
|
|||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="AsciiCapable,SupportTouchPositionCorrection"
|
||||
/>
|
||||
<!-- Java uses the deprecated "in" code instead of the standard "id" code for Indonesian. -->
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="in"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="is"
|
||||
|
@ -235,6 +262,12 @@
|
|||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=south_slavic"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="ms"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="nb"
|
||||
|
@ -295,18 +328,44 @@
|
|||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="SupportTouchPositionCorrection"
|
||||
/>
|
||||
<!-- TODO: Uncomment once we can handle IETF language tag with script name specified.
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_serbian_cyrillic"
|
||||
android:imeSubtypeLocale="sr"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="SupportTouchPositionCorrection"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_serbian_latin"
|
||||
android:imeSubtypeLocale="sr-Latn"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
-->
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="sv"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="AsciiCapable,SupportTouchPositionCorrection"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="sw"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="th"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=thai"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="tl"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=spanish,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="tr"
|
||||
|
@ -325,6 +384,12 @@
|
|||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_generic"
|
||||
android:imeSubtypeLocale="zu"
|
||||
android:imeSubtypeMode="keyboard"
|
||||
android:imeSubtypeExtraValue="KeyboardLayoutSet=qwerty,AsciiCapable"
|
||||
/>
|
||||
<subtype android:icon="@drawable/ic_subtype_keyboard"
|
||||
android:label="@string/subtype_no_language_qwerty"
|
||||
android:imeSubtypeLocale="zz"
|
||||
|
|
|
@ -101,6 +101,12 @@
|
|||
android:key="pref_advanced_settings"
|
||||
android:title="@string/advanced_settings"
|
||||
android:summary="@string/advanced_settings_summary">
|
||||
<CheckBoxPreference
|
||||
android:key="pref_key_use_contacts_dict"
|
||||
android:title="@string/use_contacts_dict"
|
||||
android:summary="@string/use_contacts_dict_summary"
|
||||
android:persistent="true"
|
||||
android:defaultValue="true" />
|
||||
<CheckBoxPreference
|
||||
android:key="pref_suppress_language_switch_key"
|
||||
android:title="@string/suppress_language_switch_key"
|
||||
|
@ -120,18 +126,23 @@
|
|||
<ListPreference
|
||||
android:key="pref_key_preview_popup_dismiss_delay"
|
||||
android:title="@string/key_preview_popup_dismiss_delay" />
|
||||
<CheckBoxPreference
|
||||
android:key="pref_key_use_contacts_dict"
|
||||
android:title="@string/use_contacts_dict"
|
||||
android:summary="@string/use_contacts_dict_summary"
|
||||
android:persistent="true"
|
||||
android:defaultValue="true" />
|
||||
<PreferenceScreen
|
||||
android:key="pref_vibration_duration_settings"
|
||||
android:title="@string/prefs_keypress_vibration_duration_settings"/>
|
||||
<PreferenceScreen
|
||||
android:key="pref_keypress_sound_volume"
|
||||
android:title="@string/prefs_keypress_sound_volume_settings" />
|
||||
<CheckBoxPreference
|
||||
android:key="pref_gesture_preview_trail"
|
||||
android:title="@string/gesture_preview_trail"
|
||||
android:persistent="true"
|
||||
android:defaultValue="true" />
|
||||
<CheckBoxPreference
|
||||
android:key="pref_gesture_floating_preview_text"
|
||||
android:title="@string/gesture_floating_preview_text"
|
||||
android:summary="@string/gesture_floating_preview_text_summary"
|
||||
android:persistent="true"
|
||||
android:defaultValue="true" />
|
||||
</PreferenceScreen>
|
||||
</PreferenceCategory>
|
||||
</PreferenceScreen>
|
||||
|
|
|
@ -47,7 +47,7 @@
|
|||
latin:keyLabel="е"
|
||||
latin:keyHintLabel="5"
|
||||
latin:additionalMoreKeys="5"
|
||||
latin:moreKeys="!text/more_keys_for_cyrillic_ye" />
|
||||
latin:moreKeys="!text/more_keys_for_cyrillic_ie" />
|
||||
<!-- U+043D: "н" CYRILLIC SMALL LETTER EN -->
|
||||
<Key
|
||||
latin:keyLabel="н"
|
||||
|
@ -58,7 +58,8 @@
|
|||
<Key
|
||||
latin:keyLabel="г"
|
||||
latin:keyHintLabel="7"
|
||||
latin:additionalMoreKeys="7" />
|
||||
latin:additionalMoreKeys="7"
|
||||
latin:moreKeys="!text/more_keys_for_cyrillic_ghe" />
|
||||
<!-- U+0448: "ш" CYRILLIC SMALL LETTER SHA -->
|
||||
<Key
|
||||
latin:keyLabel="ш"
|
||||
|
@ -75,6 +76,5 @@
|
|||
latin:additionalMoreKeys="0" />
|
||||
<!-- U+0445: "х" CYRILLIC SMALL LETTER HA -->
|
||||
<Key
|
||||
latin:keyLabel="х"
|
||||
latin:moreKeys="!text/more_keys_for_cyrillic_ha" />
|
||||
latin:keyLabel="х" />
|
||||
</merge>
|
||||
|
|
|
@ -52,7 +52,6 @@
|
|||
<!-- U+0436: "ж" CYRILLIC SMALL LETTER ZHE -->
|
||||
<Key
|
||||
latin:keyLabel="ж" />
|
||||
<!-- U+044D: "э" CYRILLIC SMALL LETTER E -->
|
||||
<Key
|
||||
latin:keyLabel="э" />
|
||||
latin:keyLabel="!text/keylabel_for_east_slavic_row2_11" />
|
||||
</merge>
|
||||
|
|
|
@ -60,10 +60,8 @@ public class KeyCodeDescriptionMapper {
|
|||
// Manual label substitutions for key labels with no string resource
|
||||
mKeyLabelMap.put(":-)", R.string.spoken_description_smiley);
|
||||
|
||||
// Symbols that most TTS engines can't speak
|
||||
mKeyCodeMap.put(' ', R.string.spoken_description_space);
|
||||
|
||||
// Special non-character codes defined in Keyboard
|
||||
mKeyCodeMap.put(Keyboard.CODE_SPACE, R.string.spoken_description_space);
|
||||
mKeyCodeMap.put(Keyboard.CODE_DELETE, R.string.spoken_description_delete);
|
||||
mKeyCodeMap.put(Keyboard.CODE_ENTER, R.string.spoken_description_return);
|
||||
mKeyCodeMap.put(Keyboard.CODE_SETTINGS, R.string.spoken_description_settings);
|
||||
|
@ -71,6 +69,9 @@ public class KeyCodeDescriptionMapper {
|
|||
mKeyCodeMap.put(Keyboard.CODE_SHORTCUT, R.string.spoken_description_mic);
|
||||
mKeyCodeMap.put(Keyboard.CODE_SWITCH_ALPHA_SYMBOL, R.string.spoken_description_to_symbol);
|
||||
mKeyCodeMap.put(Keyboard.CODE_TAB, R.string.spoken_description_tab);
|
||||
mKeyCodeMap.put(Keyboard.CODE_LANGUAGE_SWITCH, R.string.spoken_description_language_switch);
|
||||
mKeyCodeMap.put(Keyboard.CODE_ACTION_NEXT, R.string.spoken_description_action_next);
|
||||
mKeyCodeMap.put(Keyboard.CODE_ACTION_PREVIOUS, R.string.spoken_description_action_previous);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -274,8 +275,7 @@ public class KeyCodeDescriptionMapper {
|
|||
return context.getString(OBSCURED_KEY_RES_ID);
|
||||
}
|
||||
|
||||
final int resId = mKeyCodeMap.get(code);
|
||||
if (resId != 0) {
|
||||
if (mKeyCodeMap.indexOfKey(code) >= 0) {
|
||||
return context.getString(mKeyCodeMap.get(code));
|
||||
} else if (isDefinedNonCtrl) {
|
||||
return Character.toString((char) code);
|
||||
|
|
|
@ -0,0 +1,34 @@
|
|||
/*
|
||||
* Copyright (C) 2012 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.compat;
|
||||
|
||||
import android.inputmethodservice.InputMethodService;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
public class InputMethodServiceCompatUtils {
|
||||
private static final Method METHOD_enableHardwareAcceleration =
|
||||
CompatUtils.getMethod(InputMethodService.class, "enableHardwareAcceleration");
|
||||
|
||||
private InputMethodServiceCompatUtils() {
|
||||
// This utility class is not publicly instantiable.
|
||||
}
|
||||
|
||||
public static boolean enableHardwareAcceleration(InputMethodService ims) {
|
||||
return (Boolean)CompatUtils.invoke(ims, false, METHOD_enableHardwareAcceleration);
|
||||
}
|
||||
}
|
|
@ -414,8 +414,14 @@ public class Key {
|
|||
|
||||
@Override
|
||||
public String toString() {
|
||||
return String.format("%s/%s %d,%d %dx%d %s/%s/%s",
|
||||
Keyboard.printableCode(mCode), mLabel, mX, mY, mWidth, mHeight, mHintLabel,
|
||||
final String label;
|
||||
if (StringUtils.codePointCount(mLabel) == 1 && mLabel.codePointAt(0) == mCode) {
|
||||
label = "";
|
||||
} else {
|
||||
label = "/" + mLabel;
|
||||
}
|
||||
return String.format("%s%s %d,%d %dx%d %s/%s/%s",
|
||||
Keyboard.printableCode(mCode), label, mX, mY, mWidth, mHeight, mHintLabel,
|
||||
KeyboardIconsSet.getIconName(mIconId), backgroundName(mBackgroundType));
|
||||
}
|
||||
|
||||
|
|
|
@ -25,7 +25,6 @@ public class KeyDetector {
|
|||
private Keyboard mKeyboard;
|
||||
private int mCorrectionX;
|
||||
private int mCorrectionY;
|
||||
private boolean mProximityCorrectOn;
|
||||
|
||||
/**
|
||||
* This class handles key detection.
|
||||
|
@ -38,8 +37,9 @@ public class KeyDetector {
|
|||
}
|
||||
|
||||
public void setKeyboard(Keyboard keyboard, float correctionX, float correctionY) {
|
||||
if (keyboard == null)
|
||||
if (keyboard == null) {
|
||||
throw new NullPointerException();
|
||||
}
|
||||
mCorrectionX = (int)correctionX;
|
||||
mCorrectionY = (int)correctionY;
|
||||
mKeyboard = keyboard;
|
||||
|
@ -59,19 +59,9 @@ public class KeyDetector {
|
|||
}
|
||||
|
||||
public Keyboard getKeyboard() {
|
||||
if (mKeyboard == null)
|
||||
throw new IllegalStateException("keyboard isn't set");
|
||||
return mKeyboard;
|
||||
}
|
||||
|
||||
public void setProximityCorrectionEnabled(boolean enabled) {
|
||||
mProximityCorrectOn = enabled;
|
||||
}
|
||||
|
||||
public boolean isProximityCorrectionEnabled() {
|
||||
return mProximityCorrectOn;
|
||||
}
|
||||
|
||||
public boolean alwaysAllowsSlidingInput() {
|
||||
return false;
|
||||
}
|
||||
|
|
|
@ -604,9 +604,6 @@ public class Keyboard {
|
|||
}
|
||||
|
||||
public float getKeyX(TypedArray keyAttr) {
|
||||
final int widthType = Builder.getEnumValue(keyAttr,
|
||||
R.styleable.Keyboard_Key_keyWidth, KEYWIDTH_NOT_ENUM);
|
||||
|
||||
final int keyboardRightEdge = mParams.mOccupiedWidth
|
||||
- mParams.mHorizontalEdgesPadding;
|
||||
if (keyAttr.hasValue(R.styleable.Keyboard_Key_keyXPos)) {
|
||||
|
|
|
@ -55,10 +55,15 @@ public class KeyboardId {
|
|||
public static final int ELEMENT_PHONE_SYMBOLS = 8;
|
||||
public static final int ELEMENT_NUMBER = 9;
|
||||
|
||||
public static final int FORM_FACTOR_PHONE = 0;
|
||||
public static final int FORM_FACTOR_TABLET7 = 1;
|
||||
public static final int FORM_FACTOR_TABLET10 = 2;
|
||||
|
||||
private static final int IME_ACTION_CUSTOM_LABEL = EditorInfo.IME_MASK_ACTION + 1;
|
||||
|
||||
public final InputMethodSubtype mSubtype;
|
||||
public final Locale mLocale;
|
||||
public final int mDeviceFormFactor;
|
||||
public final int mOrientation;
|
||||
public final int mWidth;
|
||||
public final int mMode;
|
||||
|
@ -72,11 +77,12 @@ public class KeyboardId {
|
|||
|
||||
private final int mHashCode;
|
||||
|
||||
public KeyboardId(int elementId, InputMethodSubtype subtype, int orientation, int width,
|
||||
int mode, EditorInfo editorInfo, boolean clobberSettingsKey, boolean shortcutKeyEnabled,
|
||||
boolean hasShortcutKey, boolean languageSwitchKeyEnabled) {
|
||||
public KeyboardId(int elementId, InputMethodSubtype subtype, int deviceFormFactor,
|
||||
int orientation, int width, int mode, EditorInfo editorInfo, boolean clobberSettingsKey,
|
||||
boolean shortcutKeyEnabled, boolean hasShortcutKey, boolean languageSwitchKeyEnabled) {
|
||||
mSubtype = subtype;
|
||||
mLocale = SubtypeLocale.getSubtypeLocale(subtype);
|
||||
mDeviceFormFactor = deviceFormFactor;
|
||||
mOrientation = orientation;
|
||||
mWidth = width;
|
||||
mMode = mode;
|
||||
|
@ -94,6 +100,7 @@ public class KeyboardId {
|
|||
|
||||
private static int computeHashCode(KeyboardId id) {
|
||||
return Arrays.hashCode(new Object[] {
|
||||
id.mDeviceFormFactor,
|
||||
id.mOrientation,
|
||||
id.mElementId,
|
||||
id.mMode,
|
||||
|
@ -115,7 +122,8 @@ public class KeyboardId {
|
|||
private boolean equals(KeyboardId other) {
|
||||
if (other == this)
|
||||
return true;
|
||||
return other.mOrientation == mOrientation
|
||||
return other.mDeviceFormFactor == mDeviceFormFactor
|
||||
&& other.mOrientation == mOrientation
|
||||
&& other.mElementId == mElementId
|
||||
&& other.mMode == mMode
|
||||
&& other.mWidth == mWidth
|
||||
|
@ -184,11 +192,11 @@ public class KeyboardId {
|
|||
|
||||
@Override
|
||||
public String toString() {
|
||||
return String.format("[%s %s:%s %s%d %s %s %s%s%s%s%s%s%s%s]",
|
||||
return String.format("[%s %s:%s %s-%s:%d %s %s %s%s%s%s%s%s%s%s]",
|
||||
elementIdToName(mElementId),
|
||||
mLocale,
|
||||
mSubtype.getExtraValueOf(KEYBOARD_LAYOUT_SET),
|
||||
(mOrientation == 1 ? "port" : "land"), mWidth,
|
||||
deviceFormFactor(mDeviceFormFactor), (mOrientation == 1 ? "port" : "land"), mWidth,
|
||||
modeName(mMode),
|
||||
imeAction(),
|
||||
(navigateNext() ? "navigateNext" : ""),
|
||||
|
@ -226,6 +234,15 @@ public class KeyboardId {
|
|||
}
|
||||
}
|
||||
|
||||
public static String deviceFormFactor(int devoceFormFactor) {
|
||||
switch (devoceFormFactor) {
|
||||
case FORM_FACTOR_PHONE: return "phone";
|
||||
case FORM_FACTOR_TABLET7: return "tablet7";
|
||||
case FORM_FACTOR_TABLET10: return "tablet10";
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
public static String modeName(int mode) {
|
||||
switch (mode) {
|
||||
case MODE_TEXT: return "text";
|
||||
|
|
|
@ -115,6 +115,7 @@ public class KeyboardLayoutSet {
|
|||
boolean mNoSettingsKey;
|
||||
boolean mLanguageSwitchKeyEnabled;
|
||||
InputMethodSubtype mSubtype;
|
||||
int mDeviceFormFactor;
|
||||
int mOrientation;
|
||||
int mWidth;
|
||||
// Sparse array of KeyboardLayoutSet element parameters indexed by element's id.
|
||||
|
@ -211,9 +212,10 @@ public class KeyboardLayoutSet {
|
|||
final boolean noLanguage = SubtypeLocale.isNoLanguage(params.mSubtype);
|
||||
final boolean voiceKeyEnabled = params.mVoiceKeyEnabled && !noLanguage;
|
||||
final boolean hasShortcutKey = voiceKeyEnabled && (isSymbols != params.mVoiceKeyOnMain);
|
||||
return new KeyboardId(keyboardLayoutSetElementId, params.mSubtype, params.mOrientation,
|
||||
params.mWidth, params.mMode, params.mEditorInfo, params.mNoSettingsKey,
|
||||
voiceKeyEnabled, hasShortcutKey, params.mLanguageSwitchKeyEnabled);
|
||||
return new KeyboardId(keyboardLayoutSetElementId, params.mSubtype, params.mDeviceFormFactor,
|
||||
params.mOrientation, params.mWidth, params.mMode, params.mEditorInfo,
|
||||
params.mNoSettingsKey, voiceKeyEnabled, hasShortcutKey,
|
||||
params.mLanguageSwitchKeyEnabled);
|
||||
}
|
||||
|
||||
public static class Builder {
|
||||
|
@ -239,9 +241,11 @@ public class KeyboardLayoutSet {
|
|||
mPackageName, NO_SETTINGS_KEY, mEditorInfo);
|
||||
}
|
||||
|
||||
public Builder setScreenGeometry(int orientation, int widthPixels) {
|
||||
mParams.mOrientation = orientation;
|
||||
mParams.mWidth = widthPixels;
|
||||
public Builder setScreenGeometry(int deviceFormFactor, int orientation, int widthPixels) {
|
||||
final Params params = mParams;
|
||||
params.mDeviceFormFactor = deviceFormFactor;
|
||||
params.mOrientation = orientation;
|
||||
params.mWidth = widthPixels;
|
||||
return this;
|
||||
}
|
||||
|
||||
|
|
|
@ -74,7 +74,6 @@ public class KeyboardSwitcher implements KeyboardState.SwitchActions {
|
|||
private MainKeyboardView mKeyboardView;
|
||||
private LatinIME mLatinIME;
|
||||
private Resources mResources;
|
||||
private SettingsValues mCurrentSettingsValues;
|
||||
|
||||
private KeyboardState mState;
|
||||
|
||||
|
@ -136,11 +135,11 @@ public class KeyboardSwitcher implements KeyboardState.SwitchActions {
|
|||
}
|
||||
|
||||
public void loadKeyboard(EditorInfo editorInfo, SettingsValues settingsValues) {
|
||||
mCurrentSettingsValues = settingsValues;
|
||||
final KeyboardLayoutSet.Builder builder = new KeyboardLayoutSet.Builder(
|
||||
mThemeContext, editorInfo);
|
||||
builder.setScreenGeometry(mThemeContext.getResources().getConfiguration().orientation,
|
||||
mThemeContext.getResources().getDisplayMetrics().widthPixels);
|
||||
final Resources res = mThemeContext.getResources();
|
||||
builder.setScreenGeometry(res.getInteger(R.integer.config_device_form_factor),
|
||||
res.getConfiguration().orientation, res.getDisplayMetrics().widthPixels);
|
||||
builder.setSubtype(mSubtypeSwitcher.getCurrentSubtype());
|
||||
builder.setOptions(
|
||||
settingsValues.isVoiceKeyEnabled(editorInfo),
|
||||
|
@ -171,20 +170,20 @@ public class KeyboardSwitcher implements KeyboardState.SwitchActions {
|
|||
}
|
||||
|
||||
private void setKeyboard(final Keyboard keyboard) {
|
||||
final Keyboard oldKeyboard = mKeyboardView.getKeyboard();
|
||||
mKeyboardView.setGestureInputEnabled(mCurrentSettingsValues.mGestureInputEnabled);
|
||||
mKeyboardView.setKeyboard(keyboard);
|
||||
final MainKeyboardView keyboardView = mKeyboardView;
|
||||
final Keyboard oldKeyboard = keyboardView.getKeyboard();
|
||||
keyboardView.setKeyboard(keyboard);
|
||||
mCurrentInputView.setKeyboardGeometry(keyboard.mTopPadding);
|
||||
mKeyboardView.setKeyPreviewPopupEnabled(
|
||||
keyboardView.setKeyPreviewPopupEnabled(
|
||||
SettingsValues.isKeyPreviewPopupEnabled(mPrefs, mResources),
|
||||
SettingsValues.getKeyPreviewPopupDismissDelay(mPrefs, mResources));
|
||||
mKeyboardView.updateAutoCorrectionState(mIsAutoCorrectionActive);
|
||||
mKeyboardView.updateShortcutKey(mSubtypeSwitcher.isShortcutImeReady());
|
||||
keyboardView.updateAutoCorrectionState(mIsAutoCorrectionActive);
|
||||
keyboardView.updateShortcutKey(mSubtypeSwitcher.isShortcutImeReady());
|
||||
final boolean subtypeChanged = (oldKeyboard == null)
|
||||
|| !keyboard.mId.mLocale.equals(oldKeyboard.mId.mLocale);
|
||||
final boolean needsToDisplayLanguage = mSubtypeSwitcher.needsToDisplayLanguage(
|
||||
keyboard.mId.mLocale);
|
||||
mKeyboardView.startDisplayLanguageOnSpacebar(subtypeChanged, needsToDisplayLanguage,
|
||||
keyboardView.startDisplayLanguageOnSpacebar(subtypeChanged, needsToDisplayLanguage,
|
||||
ImfUtils.hasMultipleEnabledIMEsOrSubtypes(mLatinIME, true));
|
||||
}
|
||||
|
||||
|
@ -350,7 +349,7 @@ public class KeyboardSwitcher implements KeyboardState.SwitchActions {
|
|||
return mKeyboardView;
|
||||
}
|
||||
|
||||
public View onCreateInputView() {
|
||||
public View onCreateInputView(boolean isHardwareAcceleratedDrawingEnabled) {
|
||||
if (mKeyboardView != null) {
|
||||
mKeyboardView.closing();
|
||||
}
|
||||
|
@ -373,6 +372,10 @@ public class KeyboardSwitcher implements KeyboardState.SwitchActions {
|
|||
}
|
||||
|
||||
mKeyboardView = (MainKeyboardView) mCurrentInputView.findViewById(R.id.keyboard_view);
|
||||
if (isHardwareAcceleratedDrawingEnabled) {
|
||||
mKeyboardView.setLayerType(View.LAYER_TYPE_HARDWARE, null);
|
||||
// TODO: Should use LAYER_TYPE_SOFTWARE when hardware acceleration is off?
|
||||
}
|
||||
mKeyboardView.setKeyboardActionListener(mLatinIME);
|
||||
if (mForceNonDistinctMultitouch) {
|
||||
mKeyboardView.setDistinctMultitouch(false);
|
||||
|
|
|
@ -25,7 +25,7 @@ import android.graphics.Paint;
|
|||
import android.graphics.Paint.Align;
|
||||
import android.graphics.PorterDuff;
|
||||
import android.graphics.Rect;
|
||||
import android.graphics.Region.Op;
|
||||
import android.graphics.Region;
|
||||
import android.graphics.Typeface;
|
||||
import android.graphics.drawable.Drawable;
|
||||
import android.os.Message;
|
||||
|
@ -35,9 +35,9 @@ import android.util.TypedValue;
|
|||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.RelativeLayout;
|
||||
import android.widget.TextView;
|
||||
|
||||
import com.android.inputmethod.keyboard.internal.PreviewPlacerView;
|
||||
import com.android.inputmethod.latin.Constants;
|
||||
import com.android.inputmethod.latin.LatinImeLogger;
|
||||
import com.android.inputmethod.latin.R;
|
||||
|
@ -97,9 +97,6 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
// The maximum key label width in the proportion to the key width.
|
||||
private static final float MAX_LABEL_RATIO = 0.90f;
|
||||
|
||||
private final static int GESTURE_DRAWING_WIDTH = 5;
|
||||
private final static int GESTURE_DRAWING_COLOR = 0xff33b5e5;
|
||||
|
||||
// Main keyboard
|
||||
private Keyboard mKeyboard;
|
||||
protected final KeyDrawParams mKeyDrawParams;
|
||||
|
@ -109,10 +106,10 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
protected final KeyPreviewDrawParams mKeyPreviewDrawParams;
|
||||
private boolean mShowKeyPreviewPopup = true;
|
||||
private int mDelayAfterPreview;
|
||||
private ViewGroup mPreviewPlacer;
|
||||
private final PreviewPlacerView mPreviewPlacerView;
|
||||
|
||||
/** True if the gesture input is enabled. */
|
||||
protected boolean mGestureInputEnabled;
|
||||
/** True if {@link KeyboardView} should handle gesture events. */
|
||||
protected boolean mShouldHandleGesture;
|
||||
|
||||
// Drawing
|
||||
/** True if the entire keyboard needs to be dimmed. */
|
||||
|
@ -123,16 +120,15 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
private boolean mInvalidateAllKeys;
|
||||
/** The keys that should be drawn */
|
||||
private final HashSet<Key> mInvalidatedKeys = new HashSet<Key>();
|
||||
/** The region of invalidated keys */
|
||||
private final Rect mInvalidatedKeysRect = new Rect();
|
||||
/** The region of invalidated gestures */
|
||||
private final Rect mInvalidatedGesturesRect = new Rect();
|
||||
/** The working rectangle variable */
|
||||
private final Rect mWorkingRect = new Rect();
|
||||
/** The keyboard bitmap buffer for faster updates */
|
||||
private Bitmap mBuffer;
|
||||
/** The clip region to draw keys */
|
||||
private final Region mClipRegion = new Region();
|
||||
private Bitmap mOffscreenBuffer;
|
||||
/** The canvas for the above mutable keyboard bitmap */
|
||||
private Canvas mCanvas;
|
||||
private Canvas mOffscreenCanvas;
|
||||
private final Paint mPaint = new Paint();
|
||||
private final Paint mGesturePaint = new Paint();
|
||||
private final Paint.FontMetrics mFontMetrics = new Paint.FontMetrics();
|
||||
// This sparse array caches key label text height in pixel indexed by key label text size.
|
||||
private static final SparseArray<Float> sTextHeightCache = new SparseArray<Float>();
|
||||
|
@ -261,10 +257,12 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
}
|
||||
|
||||
public void updateKeyHeight(int keyHeight) {
|
||||
if (mKeyLetterRatio >= 0.0f)
|
||||
if (mKeyLetterRatio >= 0.0f) {
|
||||
mKeyLetterSize = (int)(keyHeight * mKeyLetterRatio);
|
||||
if (mKeyLabelRatio >= 0.0f)
|
||||
}
|
||||
if (mKeyLabelRatio >= 0.0f) {
|
||||
mKeyLabelSize = (int)(keyHeight * mKeyLabelRatio);
|
||||
}
|
||||
mKeyLargeLabelSize = (int)(keyHeight * mKeyLargeLabelRatio);
|
||||
mKeyLargeLetterSize = (int)(keyHeight * mKeyLargeLetterRatio);
|
||||
mKeyHintLetterSize = (int)(keyHeight * mKeyHintLetterRatio);
|
||||
|
@ -346,13 +344,16 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
}
|
||||
|
||||
public void updateKeyHeight(int keyHeight) {
|
||||
mPreviewTextSize = (int)(keyHeight * mPreviewTextRatio);
|
||||
mKeyLetterSize = (int)(keyHeight * mKeyLetterRatio);
|
||||
if (mPreviewTextRatio >= 0.0f) {
|
||||
mPreviewTextSize = (int)(keyHeight * mPreviewTextRatio);
|
||||
}
|
||||
if (mKeyLetterRatio >= 0.0f) {
|
||||
mKeyLetterSize = (int)(keyHeight * mKeyLetterRatio);
|
||||
}
|
||||
}
|
||||
|
||||
private static void setAlpha(Drawable drawable, int alpha) {
|
||||
if (drawable == null)
|
||||
return;
|
||||
if (drawable == null) return;
|
||||
drawable.setAlpha(alpha);
|
||||
}
|
||||
}
|
||||
|
@ -377,18 +378,12 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
R.styleable.KeyboardView_verticalCorrection, 0);
|
||||
mMoreKeysLayout = a.getResourceId(R.styleable.KeyboardView_moreKeysLayout, 0);
|
||||
mBackgroundDimAlpha = a.getInt(R.styleable.KeyboardView_backgroundDimAlpha, 0);
|
||||
mPreviewPlacerView = new PreviewPlacerView(context, a);
|
||||
a.recycle();
|
||||
|
||||
mDelayAfterPreview = mKeyPreviewDrawParams.mLingerTimeout;
|
||||
|
||||
mPaint.setAntiAlias(true);
|
||||
|
||||
// TODO: These paint parameters should be specified via attribute of the view and styleable.
|
||||
mGesturePaint.setAntiAlias(true);
|
||||
mGesturePaint.setStyle(Paint.Style.STROKE);
|
||||
mGesturePaint.setStrokeJoin(Paint.Join.ROUND);
|
||||
mGesturePaint.setColor(GESTURE_DRAWING_COLOR);
|
||||
mGesturePaint.setStrokeWidth(GESTURE_DRAWING_WIDTH);
|
||||
}
|
||||
|
||||
// Read fraction value in TypedArray as float.
|
||||
|
@ -443,8 +438,11 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
return mShowKeyPreviewPopup;
|
||||
}
|
||||
|
||||
public void setGestureInputEnabled(boolean gestureInputEnabled) {
|
||||
mGestureInputEnabled = gestureInputEnabled;
|
||||
public void setGestureHandlingMode(boolean shouldHandleGesture,
|
||||
boolean drawsGesturePreviewTrail, boolean drawsGestureFloatingPreviewText) {
|
||||
mShouldHandleGesture = shouldHandleGesture;
|
||||
mPreviewPlacerView.setGesturePreviewMode(
|
||||
drawsGesturePreviewTrail, drawsGestureFloatingPreviewText);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -461,65 +459,107 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
@Override
|
||||
public void onDraw(Canvas canvas) {
|
||||
super.onDraw(canvas);
|
||||
if (mBufferNeedsUpdate || mBuffer == null) {
|
||||
mBufferNeedsUpdate = false;
|
||||
onBufferDraw();
|
||||
if (canvas.isHardwareAccelerated()) {
|
||||
onDrawKeyboard(canvas);
|
||||
return;
|
||||
}
|
||||
canvas.drawBitmap(mBuffer, 0, 0, null);
|
||||
if (mBufferNeedsUpdate || mOffscreenBuffer == null) {
|
||||
mBufferNeedsUpdate = false;
|
||||
if (maybeAllocateOffscreenBuffer()) {
|
||||
mInvalidateAllKeys = true;
|
||||
// TODO: Stop using the offscreen canvas even when in software rendering
|
||||
if (mOffscreenCanvas != null) {
|
||||
mOffscreenCanvas.setBitmap(mOffscreenBuffer);
|
||||
} else {
|
||||
mOffscreenCanvas = new Canvas(mOffscreenBuffer);
|
||||
}
|
||||
}
|
||||
onDrawKeyboard(mOffscreenCanvas);
|
||||
}
|
||||
canvas.drawBitmap(mOffscreenBuffer, 0, 0, null);
|
||||
}
|
||||
|
||||
private void onBufferDraw() {
|
||||
private boolean maybeAllocateOffscreenBuffer() {
|
||||
final int width = getWidth();
|
||||
final int height = getHeight();
|
||||
if (width == 0 || height == 0)
|
||||
return;
|
||||
if (mBuffer == null || mBuffer.getWidth() != width || mBuffer.getHeight() != height) {
|
||||
if (mBuffer != null)
|
||||
mBuffer.recycle();
|
||||
mBuffer = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
|
||||
mInvalidateAllKeys = true;
|
||||
if (mCanvas != null) {
|
||||
mCanvas.setBitmap(mBuffer);
|
||||
} else {
|
||||
mCanvas = new Canvas(mBuffer);
|
||||
}
|
||||
if (width == 0 || height == 0) {
|
||||
return false;
|
||||
}
|
||||
if (mOffscreenBuffer != null && mOffscreenBuffer.getWidth() == width
|
||||
&& mOffscreenBuffer.getHeight() == height) {
|
||||
return false;
|
||||
}
|
||||
freeOffscreenBuffer();
|
||||
mOffscreenBuffer = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
|
||||
return true;
|
||||
}
|
||||
|
||||
private void freeOffscreenBuffer() {
|
||||
if (mOffscreenBuffer != null) {
|
||||
mOffscreenBuffer.recycle();
|
||||
mOffscreenBuffer = null;
|
||||
}
|
||||
}
|
||||
|
||||
private void onDrawKeyboard(final Canvas canvas) {
|
||||
if (mKeyboard == null) return;
|
||||
|
||||
final Canvas canvas = mCanvas;
|
||||
final int width = getWidth();
|
||||
final int height = getHeight();
|
||||
final Paint paint = mPaint;
|
||||
final KeyDrawParams params = mKeyDrawParams;
|
||||
|
||||
if (mInvalidateAllKeys || mInvalidatedKeys.isEmpty()) {
|
||||
mInvalidatedKeysRect.set(0, 0, width, height);
|
||||
canvas.clipRect(mInvalidatedKeysRect, Op.REPLACE);
|
||||
canvas.drawColor(Color.BLACK, PorterDuff.Mode.CLEAR);
|
||||
// Calculate clip region and set.
|
||||
final boolean drawAllKeys = mInvalidateAllKeys || mInvalidatedKeys.isEmpty();
|
||||
final boolean isHardwareAccelerated = canvas.isHardwareAccelerated();
|
||||
// TODO: Confirm if it's really required to draw all keys when hardware acceleration is on.
|
||||
if (drawAllKeys || isHardwareAccelerated) {
|
||||
mClipRegion.set(0, 0, width, height);
|
||||
} else {
|
||||
mClipRegion.setEmpty();
|
||||
for (final Key key : mInvalidatedKeys) {
|
||||
if (mKeyboard.hasKey(key)) {
|
||||
final int x = key.mX + getPaddingLeft();
|
||||
final int y = key.mY + getPaddingTop();
|
||||
mWorkingRect.set(x, y, x + key.mWidth, y + key.mHeight);
|
||||
mClipRegion.union(mWorkingRect);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!isHardwareAccelerated) {
|
||||
canvas.clipRegion(mClipRegion, Region.Op.REPLACE);
|
||||
}
|
||||
|
||||
// Draw keyboard background.
|
||||
canvas.drawColor(Color.BLACK, PorterDuff.Mode.CLEAR);
|
||||
final Drawable background = getBackground();
|
||||
if (background != null) {
|
||||
background.draw(canvas);
|
||||
}
|
||||
|
||||
// TODO: Confirm if it's really required to draw all keys when hardware acceleration is on.
|
||||
if (drawAllKeys || isHardwareAccelerated) {
|
||||
// Draw all keys.
|
||||
for (final Key key : mKeyboard.mKeys) {
|
||||
onDrawKey(key, canvas, paint, params);
|
||||
}
|
||||
if (mNeedsToDimEntireKeyboard) {
|
||||
drawDimRectangle(canvas, mInvalidatedKeysRect, mBackgroundDimAlpha, paint);
|
||||
}
|
||||
} else {
|
||||
// Draw invalidated keys.
|
||||
for (final Key key : mInvalidatedKeys) {
|
||||
if (!mKeyboard.hasKey(key)) {
|
||||
continue;
|
||||
}
|
||||
final int x = key.mX + getPaddingLeft();
|
||||
final int y = key.mY + getPaddingTop();
|
||||
mInvalidatedKeysRect.set(x, y, x + key.mWidth, y + key.mHeight);
|
||||
canvas.clipRect(mInvalidatedKeysRect, Op.REPLACE);
|
||||
canvas.drawColor(Color.BLACK, PorterDuff.Mode.CLEAR);
|
||||
onDrawKey(key, canvas, paint, params);
|
||||
if (mNeedsToDimEntireKeyboard) {
|
||||
drawDimRectangle(canvas, mInvalidatedKeysRect, mBackgroundDimAlpha, paint);
|
||||
if (mKeyboard.hasKey(key)) {
|
||||
onDrawKey(key, canvas, paint, params);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Overlay a dark rectangle to dim.
|
||||
if (mNeedsToDimEntireKeyboard) {
|
||||
paint.setColor(Color.BLACK);
|
||||
paint.setAlpha(mBackgroundDimAlpha);
|
||||
// Note: clipRegion() above is in effect if it was called.
|
||||
canvas.drawRect(0, 0, width, height, paint);
|
||||
}
|
||||
|
||||
// ResearchLogging indicator.
|
||||
// TODO: Reimplement using a keyboard background image specific to the ResearchLogger,
|
||||
// and remove this call.
|
||||
|
@ -528,7 +568,6 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
}
|
||||
|
||||
mInvalidatedKeys.clear();
|
||||
mInvalidatedKeysRect.setEmpty();
|
||||
mInvalidateAllKeys = false;
|
||||
}
|
||||
|
||||
|
@ -853,13 +892,6 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
canvas.translate(-x, -y);
|
||||
}
|
||||
|
||||
// Overlay a dark rectangle to dim.
|
||||
private static void drawDimRectangle(Canvas canvas, Rect rect, int alpha, Paint paint) {
|
||||
paint.setColor(Color.BLACK);
|
||||
paint.setAlpha(alpha);
|
||||
canvas.drawRect(rect, paint);
|
||||
}
|
||||
|
||||
public Paint newDefaultLabelPaint() {
|
||||
final Paint paint = new Paint();
|
||||
paint.setAntiAlias(true);
|
||||
|
@ -888,58 +920,33 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
mDrawingHandler.dismissKeyPreview(mDelayAfterPreview, tracker);
|
||||
}
|
||||
|
||||
private static class PreviewView extends RelativeLayout {
|
||||
KeyPreviewDrawParams mParams;
|
||||
Paint mGesturePaint;
|
||||
|
||||
public PreviewView(Context context, KeyPreviewDrawParams params, Paint gesturePaint) {
|
||||
super(context);
|
||||
setWillNotDraw(false);
|
||||
mParams = params;
|
||||
mGesturePaint = gesturePaint;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDraw(Canvas canvas) {
|
||||
super.onDraw(canvas);
|
||||
canvas.translate(mParams.mCoordinates[0], mParams.mCoordinates[1]);
|
||||
PointerTracker.drawGestureTrailForAllPointerTrackers(canvas, mGesturePaint);
|
||||
canvas.translate(-mParams.mCoordinates[0], -mParams.mCoordinates[1]);
|
||||
}
|
||||
}
|
||||
|
||||
private void addKeyPreview(TextView keyPreview) {
|
||||
if (mPreviewPlacer == null) {
|
||||
createPreviewPlacer();
|
||||
}
|
||||
mPreviewPlacer.addView(
|
||||
keyPreview, ViewLayoutUtils.newLayoutParam(mPreviewPlacer, 0, 0));
|
||||
locatePreviewPlacerView();
|
||||
mPreviewPlacerView.addView(
|
||||
keyPreview, ViewLayoutUtils.newLayoutParam(mPreviewPlacerView, 0, 0));
|
||||
}
|
||||
|
||||
private void createPreviewPlacer() {
|
||||
mPreviewPlacer = new PreviewView(getContext(), mKeyPreviewDrawParams, mGesturePaint);
|
||||
private void locatePreviewPlacerView() {
|
||||
if (mPreviewPlacerView.getParent() != null) {
|
||||
return;
|
||||
}
|
||||
final int[] viewOrigin = new int[2];
|
||||
getLocationInWindow(viewOrigin);
|
||||
mPreviewPlacerView.setOrigin(viewOrigin[0], viewOrigin[1]);
|
||||
final ViewGroup windowContentView =
|
||||
(ViewGroup)getRootView().findViewById(android.R.id.content);
|
||||
windowContentView.addView(mPreviewPlacer);
|
||||
windowContentView.addView(mPreviewPlacerView);
|
||||
}
|
||||
|
||||
public void showGestureFloatingPreviewText(String gestureFloatingPreviewText) {
|
||||
locatePreviewPlacerView();
|
||||
mPreviewPlacerView.setGestureFloatingPreviewText(gestureFloatingPreviewText);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void showGestureTrail(PointerTracker tracker) {
|
||||
if (mPreviewPlacer == null) {
|
||||
createPreviewPlacer();
|
||||
}
|
||||
final Rect r = tracker.getBoundingBox();
|
||||
if (!r.isEmpty()) {
|
||||
// Invalidate the rectangular region encompassing the gesture. This is needed because
|
||||
// past points along the gesture will fade and gradually disappear.
|
||||
final KeyPreviewDrawParams params = mKeyPreviewDrawParams;
|
||||
mInvalidatedGesturesRect.set(r);
|
||||
mInvalidatedGesturesRect.offset(params.mCoordinates[0], params.mCoordinates[1]);
|
||||
mInvalidatedGesturesRect.inset(-GESTURE_DRAWING_WIDTH, -GESTURE_DRAWING_WIDTH);
|
||||
mPreviewPlacer.invalidate(mInvalidatedGesturesRect);
|
||||
} else {
|
||||
mPreviewPlacer.invalidate();
|
||||
}
|
||||
locatePreviewPlacerView();
|
||||
mPreviewPlacerView.invalidatePointer(tracker);
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation") // setBackgroundDrawable is replaced by setBackground in API16
|
||||
|
@ -1055,9 +1062,9 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
mInvalidatedKeys.add(key);
|
||||
final int x = key.mX + getPaddingLeft();
|
||||
final int y = key.mY + getPaddingTop();
|
||||
mInvalidatedKeysRect.union(x, y, x + key.mWidth, y + key.mHeight);
|
||||
mWorkingRect.set(x, y, x + key.mWidth, y + key.mHeight);
|
||||
mBufferNeedsUpdate = true;
|
||||
invalidate(mInvalidatedKeysRect);
|
||||
invalidate(mWorkingRect);
|
||||
}
|
||||
|
||||
public void closing() {
|
||||
|
@ -1082,12 +1089,7 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy {
|
|||
protected void onDetachedFromWindow() {
|
||||
super.onDetachedFromWindow();
|
||||
closing();
|
||||
if (mPreviewPlacer != null) {
|
||||
mPreviewPlacer.removeAllViews();
|
||||
}
|
||||
if (mBuffer != null) {
|
||||
mBuffer.recycle();
|
||||
mBuffer = null;
|
||||
}
|
||||
mPreviewPlacerView.removeAllViews();
|
||||
freeOffscreenBuffer();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -43,6 +43,7 @@ import com.android.inputmethod.accessibility.AccessibilityUtils;
|
|||
import com.android.inputmethod.accessibility.AccessibleKeyboardViewProxy;
|
||||
import com.android.inputmethod.keyboard.PointerTracker.DrawingProxy;
|
||||
import com.android.inputmethod.keyboard.PointerTracker.TimerProxy;
|
||||
import com.android.inputmethod.keyboard.internal.SuddenJumpingTouchEventHandler;
|
||||
import com.android.inputmethod.latin.Constants;
|
||||
import com.android.inputmethod.latin.LatinIME;
|
||||
import com.android.inputmethod.latin.LatinImeLogger;
|
||||
|
@ -153,8 +154,7 @@ public class MainKeyboardView extends KeyboardView implements PointerTracker.Key
|
|||
}
|
||||
break;
|
||||
case MSG_TYPING_STATE_EXPIRED:
|
||||
cancelAndStartAnimators(keyboardView.mAltCodeKeyWhileTypingFadeoutAnimator,
|
||||
keyboardView.mAltCodeKeyWhileTypingFadeinAnimator);
|
||||
startWhileTypingFadeinAnimation(keyboardView);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -228,7 +228,7 @@ public class MainKeyboardView extends KeyboardView implements PointerTracker.Key
|
|||
removeMessages(MSG_LONGPRESS_KEY);
|
||||
}
|
||||
|
||||
public static void cancelAndStartAnimators(final ObjectAnimator animatorToCancel,
|
||||
private static void cancelAndStartAnimators(final ObjectAnimator animatorToCancel,
|
||||
final ObjectAnimator animatorToStart) {
|
||||
float startFraction = 0.0f;
|
||||
if (animatorToCancel.isStarted()) {
|
||||
|
@ -240,18 +240,39 @@ public class MainKeyboardView extends KeyboardView implements PointerTracker.Key
|
|||
animatorToStart.setCurrentPlayTime(startTime);
|
||||
}
|
||||
|
||||
private static void startWhileTypingFadeinAnimation(final MainKeyboardView keyboardView) {
|
||||
cancelAndStartAnimators(keyboardView.mAltCodeKeyWhileTypingFadeoutAnimator,
|
||||
keyboardView.mAltCodeKeyWhileTypingFadeinAnimator);
|
||||
}
|
||||
|
||||
private static void startWhileTypingFadeoutAnimation(final MainKeyboardView keyboardView) {
|
||||
cancelAndStartAnimators(keyboardView.mAltCodeKeyWhileTypingFadeinAnimator,
|
||||
keyboardView.mAltCodeKeyWhileTypingFadeoutAnimator);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void startTypingStateTimer() {
|
||||
public void startTypingStateTimer(Key typedKey) {
|
||||
if (typedKey.isModifier() || typedKey.altCodeWhileTyping()) {
|
||||
return;
|
||||
}
|
||||
|
||||
final boolean isTyping = isTypingState();
|
||||
removeMessages(MSG_TYPING_STATE_EXPIRED);
|
||||
final MainKeyboardView keyboardView = getOuterInstance();
|
||||
|
||||
// When user hits the space or the enter key, just cancel the while-typing timer.
|
||||
final int typedCode = typedKey.mCode;
|
||||
if (typedCode == Keyboard.CODE_SPACE || typedCode == Keyboard.CODE_ENTER) {
|
||||
startWhileTypingFadeinAnimation(keyboardView);
|
||||
return;
|
||||
}
|
||||
|
||||
sendMessageDelayed(
|
||||
obtainMessage(MSG_TYPING_STATE_EXPIRED), mParams.mIgnoreAltCodeKeyTimeout);
|
||||
if (isTyping) {
|
||||
return;
|
||||
}
|
||||
final MainKeyboardView keyboardView = getOuterInstance();
|
||||
cancelAndStartAnimators(keyboardView.mAltCodeKeyWhileTypingFadeinAnimator,
|
||||
keyboardView.mAltCodeKeyWhileTypingFadeoutAnimator);
|
||||
startWhileTypingFadeoutAnimation(keyboardView);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -461,7 +482,7 @@ public class MainKeyboardView extends KeyboardView implements PointerTracker.Key
|
|||
super.setKeyboard(keyboard);
|
||||
mKeyDetector.setKeyboard(
|
||||
keyboard, -getPaddingLeft(), -getPaddingTop() + mVerticalCorrection);
|
||||
PointerTracker.setKeyDetector(mKeyDetector, mGestureInputEnabled);
|
||||
PointerTracker.setKeyDetector(mKeyDetector, mShouldHandleGesture);
|
||||
mTouchScreenRegulator.setKeyboard(keyboard);
|
||||
mMoreKeysPanelCache.clear();
|
||||
|
||||
|
@ -479,6 +500,14 @@ public class MainKeyboardView extends KeyboardView implements PointerTracker.Key
|
|||
AccessibleKeyboardViewProxy.getInstance().setKeyboard(keyboard);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setGestureHandlingMode(final boolean shouldHandleGesture,
|
||||
boolean drawsGesturePreviewTrail, boolean drawsGestureFloatingPreviewText) {
|
||||
super.setGestureHandlingMode(shouldHandleGesture, drawsGesturePreviewTrail,
|
||||
drawsGestureFloatingPreviewText);
|
||||
PointerTracker.setKeyDetector(mKeyDetector, shouldHandleGesture);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether the device has distinct multi-touch panel.
|
||||
* @return true if the device has distinct multi-touch panel.
|
||||
|
@ -491,23 +520,6 @@ public class MainKeyboardView extends KeyboardView implements PointerTracker.Key
|
|||
mHasDistinctMultitouch = hasDistinctMultitouch;
|
||||
}
|
||||
|
||||
/**
|
||||
* When enabled, calls to {@link KeyboardActionListener#onCodeInput} will include key
|
||||
* codes for adjacent keys. When disabled, only the primary key code will be
|
||||
* reported.
|
||||
* @param enabled whether or not the proximity correction is enabled
|
||||
*/
|
||||
public void setProximityCorrectionEnabled(boolean enabled) {
|
||||
mKeyDetector.setProximityCorrectionEnabled(enabled);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if proximity correction is enabled.
|
||||
*/
|
||||
public boolean isProximityCorrectionEnabled() {
|
||||
return mKeyDetector.isProximityCorrectionEnabled();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttachedToWindow() {
|
||||
super.onAttachedToWindow();
|
||||
|
|
|
@ -39,7 +39,11 @@ public class MoreKeysDetector extends KeyDetector {
|
|||
|
||||
Key nearestKey = null;
|
||||
int nearestDist = (y < 0) ? mSlideAllowanceSquareTop : mSlideAllowanceSquare;
|
||||
for (final Key key : getKeyboard().mKeys) {
|
||||
final Keyboard keyboard = getKeyboard();
|
||||
if (keyboard == null) {
|
||||
throw new NullPointerException("Keyboard isn't set");
|
||||
}
|
||||
for (final Key key : keyboard.mKeys) {
|
||||
final int dist = key.squaredDistanceToEdge(touchX, touchY);
|
||||
if (dist < nearestDist) {
|
||||
nearestKey = key;
|
||||
|
|
|
@ -18,7 +18,6 @@ package com.android.inputmethod.keyboard;
|
|||
|
||||
import android.graphics.Canvas;
|
||||
import android.graphics.Paint;
|
||||
import android.graphics.Rect;
|
||||
import android.os.SystemClock;
|
||||
import android.util.Log;
|
||||
import android.view.MotionEvent;
|
||||
|
@ -42,8 +41,8 @@ public class PointerTracker {
|
|||
private static final boolean DEBUG_LISTENER = false;
|
||||
private static boolean DEBUG_MODE = LatinImeLogger.sDBG;
|
||||
|
||||
// TODO: There should be an option to turn on/off the gesture input.
|
||||
private static boolean sIsGestureEnabled = true;
|
||||
/** True if {@link PointerTracker}s should handle gesture events. */
|
||||
private static boolean sShouldHandleGesture = false;
|
||||
|
||||
private static final int MIN_GESTURE_RECOGNITION_TIME = 100; // msec
|
||||
|
||||
|
@ -83,7 +82,7 @@ public class PointerTracker {
|
|||
}
|
||||
|
||||
public interface TimerProxy {
|
||||
public void startTypingStateTimer();
|
||||
public void startTypingStateTimer(Key typedKey);
|
||||
public boolean isTypingState();
|
||||
public void startKeyRepeatTimer(PointerTracker tracker);
|
||||
public void startLongPressTimer(PointerTracker tracker);
|
||||
|
@ -96,7 +95,7 @@ public class PointerTracker {
|
|||
|
||||
public static class Adapter implements TimerProxy {
|
||||
@Override
|
||||
public void startTypingStateTimer() {}
|
||||
public void startTypingStateTimer(Key typedKey) {}
|
||||
@Override
|
||||
public boolean isTypingState() { return false; }
|
||||
@Override
|
||||
|
@ -199,7 +198,7 @@ public class PointerTracker {
|
|||
sNeedsPhantomSuddenMoveEventHack = needsPhantomSuddenMoveEventHack;
|
||||
|
||||
setParameters(MainKeyboardView.PointerTrackerParams.DEFAULT);
|
||||
updateGestureInputEnabledState(null, false /* gestureInputEnabled */);
|
||||
updateGestureHandlingMode(null, false /* shouldHandleGesture */);
|
||||
}
|
||||
|
||||
public static void setParameters(MainKeyboardView.PointerTrackerParams params) {
|
||||
|
@ -208,14 +207,13 @@ public class PointerTracker {
|
|||
params.mTouchNoiseThresholdDistance * params.mTouchNoiseThresholdDistance);
|
||||
}
|
||||
|
||||
private static void updateGestureInputEnabledState(Keyboard keyboard,
|
||||
boolean gestureInputEnabled) {
|
||||
if (!gestureInputEnabled
|
||||
private static void updateGestureHandlingMode(Keyboard keyboard, boolean shouldHandleGesture) {
|
||||
if (!shouldHandleGesture
|
||||
|| AccessibilityUtils.getInstance().isTouchExplorationEnabled()
|
||||
|| (keyboard != null && keyboard.mId.passwordInput())) {
|
||||
sIsGestureEnabled = false;
|
||||
sShouldHandleGesture = false;
|
||||
} else {
|
||||
sIsGestureEnabled = true;
|
||||
sShouldHandleGesture = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -243,7 +241,7 @@ public class PointerTracker {
|
|||
}
|
||||
}
|
||||
|
||||
public static void setKeyDetector(KeyDetector keyDetector, boolean gestureInputEnabledByUser) {
|
||||
public static void setKeyDetector(KeyDetector keyDetector, boolean shouldHandleGesture) {
|
||||
final int trackersSize = sTrackers.size();
|
||||
for (int i = 0; i < trackersSize; ++i) {
|
||||
final PointerTracker tracker = sTrackers.get(i);
|
||||
|
@ -252,7 +250,7 @@ public class PointerTracker {
|
|||
tracker.mKeyboardLayoutHasBeenChanged = true;
|
||||
}
|
||||
final Keyboard keyboard = keyDetector.getKeyboard();
|
||||
updateGestureInputEnabledState(keyboard, gestureInputEnabledByUser);
|
||||
updateGestureHandlingMode(keyboard, shouldHandleGesture);
|
||||
}
|
||||
|
||||
public static void dismissAllKeyPreviews() {
|
||||
|
@ -297,17 +295,6 @@ public class PointerTracker {
|
|||
sAggregratedPointers.reset();
|
||||
}
|
||||
|
||||
// TODO: To handle multi-touch gestures we may want to move this method to
|
||||
// {@link PointerTrackerQueue}.
|
||||
public static void drawGestureTrailForAllPointerTrackers(Canvas canvas, Paint paint) {
|
||||
final int trackersSize = sTrackers.size();
|
||||
for (int i = 0; i < trackersSize; ++i) {
|
||||
final PointerTracker tracker = sTrackers.get(i);
|
||||
tracker.mGestureStroke.drawGestureTrail(canvas, paint, tracker.getLastX(),
|
||||
tracker.getLastY());
|
||||
}
|
||||
}
|
||||
|
||||
private PointerTracker(int id, KeyEventHandler handler) {
|
||||
if (handler == null)
|
||||
throw new NullPointerException();
|
||||
|
@ -342,9 +329,7 @@ public class PointerTracker {
|
|||
mListener.onPressKey(key.mCode);
|
||||
final boolean keyboardLayoutHasBeenChanged = mKeyboardLayoutHasBeenChanged;
|
||||
mKeyboardLayoutHasBeenChanged = false;
|
||||
if (!key.altCodeWhileTyping() && !key.isModifier()) {
|
||||
mTimerProxy.startTypingStateTimer();
|
||||
}
|
||||
mTimerProxy.startTypingStateTimer(key);
|
||||
return keyboardLayoutHasBeenChanged;
|
||||
}
|
||||
return false;
|
||||
|
@ -423,7 +408,7 @@ public class PointerTracker {
|
|||
if (mDrawingProxy != null) {
|
||||
setReleasedKeyGraphics(mCurrentKey);
|
||||
}
|
||||
mCurrentKey = newKey;
|
||||
// Keep {@link #mCurrentKey} that comes from previous keyboard.
|
||||
}
|
||||
final int keyQuarterWidth = mKeyboard.mMostCommonKeyWidth / 4;
|
||||
mKeyQuarterWidthSquared = keyQuarterWidth * keyQuarterWidth;
|
||||
|
@ -525,6 +510,12 @@ public class PointerTracker {
|
|||
mDrawingProxy.invalidateKey(key);
|
||||
}
|
||||
|
||||
public void drawGestureTrail(Canvas canvas, Paint paint) {
|
||||
if (mInGesture) {
|
||||
mGestureStroke.drawGestureTrail(canvas, paint, mLastX, mLastY);
|
||||
}
|
||||
}
|
||||
|
||||
public int getLastX() {
|
||||
return mLastX;
|
||||
}
|
||||
|
@ -536,9 +527,6 @@ public class PointerTracker {
|
|||
public long getDownTime() {
|
||||
return mDownTime;
|
||||
}
|
||||
public Rect getBoundingBox() {
|
||||
return mGestureStroke.getBoundingBox();
|
||||
}
|
||||
|
||||
private Key onDownKey(int x, int y, long eventTime) {
|
||||
mDownTime = eventTime;
|
||||
|
@ -669,8 +657,8 @@ public class PointerTracker {
|
|||
if (queue != null && queue.size() == 1) {
|
||||
mIsPossibleGesture = false;
|
||||
// A gesture should start only from the letter key.
|
||||
if (sIsGestureEnabled && mIsAlphabetKeyboard && !mIsShowingMoreKeysPanel && key != null
|
||||
&& Keyboard.isLetterCode(key.mCode)) {
|
||||
if (sShouldHandleGesture && mIsAlphabetKeyboard && !mIsShowingMoreKeysPanel
|
||||
&& key != null && Keyboard.isLetterCode(key.mCode)) {
|
||||
mIsPossibleGesture = true;
|
||||
// TODO: pointer times should be relative to first down even in entire batch input
|
||||
// instead of resetting to 0 for each new down event.
|
||||
|
@ -714,7 +702,7 @@ public class PointerTracker {
|
|||
private void onGestureMoveEvent(PointerTracker tracker, int x, int y, long eventTime,
|
||||
boolean isHistorical, Key key) {
|
||||
final int gestureTime = (int)(eventTime - tracker.getDownTime());
|
||||
if (sIsGestureEnabled && mIsPossibleGesture) {
|
||||
if (sShouldHandleGesture && mIsPossibleGesture) {
|
||||
final GestureStroke stroke = mGestureStroke;
|
||||
stroke.addPoint(x, y, gestureTime, isHistorical);
|
||||
if (!mInGesture && stroke.isStartOfAGesture(gestureTime, sWasInGesture)) {
|
||||
|
@ -804,13 +792,16 @@ public class PointerTracker {
|
|||
final int dx = x - lastX;
|
||||
final int dy = y - lastY;
|
||||
final int lastMoveSquared = dx * dx + dy * dy;
|
||||
// TODO: Should find a way to balance gesture detection and this hack.
|
||||
if (sNeedsPhantomSuddenMoveEventHack
|
||||
&& lastMoveSquared >= mKeyQuarterWidthSquared) {
|
||||
&& lastMoveSquared >= mKeyQuarterWidthSquared
|
||||
&& !mIsPossibleGesture) {
|
||||
if (DEBUG_MODE) {
|
||||
Log.w(TAG, String.format("onMoveEvent:"
|
||||
+ " phantom sudden move event is translated to "
|
||||
+ "up[%d,%d]/down[%d,%d] events", lastX, lastY, x, y));
|
||||
}
|
||||
// TODO: This should be moved to outside of this nested if-clause?
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.pointerTracker_onMoveEvent(x, y, lastX, lastY);
|
||||
}
|
||||
|
@ -826,7 +817,9 @@ public class PointerTracker {
|
|||
&& !sPointerTrackerQueue.hasModifierKeyOlderThan(this)) {
|
||||
onUpEventInternal(x, y, eventTime);
|
||||
}
|
||||
mKeyAlreadyProcessed = true;
|
||||
if (!mIsPossibleGesture) {
|
||||
mKeyAlreadyProcessed = true;
|
||||
}
|
||||
setReleasedKeyGraphics(oldKey);
|
||||
}
|
||||
}
|
||||
|
@ -842,7 +835,9 @@ public class PointerTracker {
|
|||
if (mIsAllowedSlidingKeyInput) {
|
||||
onMoveToNewKey(key, x, y);
|
||||
} else {
|
||||
mKeyAlreadyProcessed = true;
|
||||
if (!mIsPossibleGesture) {
|
||||
mKeyAlreadyProcessed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -881,6 +876,7 @@ public class PointerTracker {
|
|||
private void onUpEventInternal(int x, int y, long eventTime) {
|
||||
mTimerProxy.cancelKeyTimers();
|
||||
mIsInSlidingKeyInput = false;
|
||||
mIsPossibleGesture = false;
|
||||
// Release the last pressed key.
|
||||
setReleasedKeyGraphics(mCurrentKey);
|
||||
if (mIsShowingMoreKeysPanel) {
|
||||
|
@ -958,9 +954,7 @@ public class PointerTracker {
|
|||
public void onRegisterKey(Key key) {
|
||||
if (key != null) {
|
||||
detectAndSendKey(key, key.mX, key.mY);
|
||||
if (!key.altCodeWhileTyping() && !key.isModifier()) {
|
||||
mTimerProxy.startTypingStateTimer();
|
||||
}
|
||||
mTimerProxy.startTypingStateTimer(key);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -16,7 +16,6 @@ package com.android.inputmethod.keyboard.internal;
|
|||
|
||||
import android.graphics.Canvas;
|
||||
import android.graphics.Paint;
|
||||
import android.graphics.Rect;
|
||||
import android.util.FloatMath;
|
||||
|
||||
import com.android.inputmethod.latin.Constants;
|
||||
|
@ -41,7 +40,6 @@ public class GestureStroke {
|
|||
private int mMinGestureLength;
|
||||
private int mMinGestureLengthWhileInGesture;
|
||||
private int mMinGestureSampleLength;
|
||||
private final Rect mDrawingRect = new Rect();
|
||||
|
||||
// TODO: Move some of these to resource.
|
||||
private static final float MIN_GESTURE_LENGTH_RATIO_TO_KEY_WIDTH = 1.0f;
|
||||
|
@ -90,7 +88,6 @@ public class GestureStroke {
|
|||
mEventTimes.setLength(0);
|
||||
mXCoordinates.setLength(0);
|
||||
mYCoordinates.setLength(0);
|
||||
mDrawingRect.setEmpty();
|
||||
}
|
||||
|
||||
private void updateLastPoint(final int x, final int y, final int time) {
|
||||
|
@ -198,8 +195,4 @@ public class GestureStroke {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
public Rect getBoundingBox() {
|
||||
return mDrawingRect;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -84,6 +84,19 @@ public class KeySpecParser {
|
|||
}
|
||||
mIconId = getIconId(moreKeySpec);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
final String label = (mIconId == KeyboardIconsSet.ICON_UNDEFINED ? mLabel
|
||||
: PREFIX_ICON + KeyboardIconsSet.getIconName(mIconId));
|
||||
final String output = (mCode == Keyboard.CODE_OUTPUT_TEXT ? mOutputText
|
||||
: Keyboard.printableCode(mCode));
|
||||
if (StringUtils.codePointCount(label) == 1 && label.codePointAt(0) == mCode) {
|
||||
return output;
|
||||
} else {
|
||||
return label + "|" + output;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private KeySpecParser() {
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,185 @@
|
|||
/*
|
||||
* Copyright (C) 2012 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.keyboard.internal;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.res.TypedArray;
|
||||
import android.graphics.Canvas;
|
||||
import android.graphics.Paint;
|
||||
import android.graphics.Paint.Align;
|
||||
import android.text.TextUtils;
|
||||
import android.util.SparseArray;
|
||||
import android.widget.RelativeLayout;
|
||||
|
||||
import com.android.inputmethod.keyboard.PointerTracker;
|
||||
import com.android.inputmethod.latin.R;
|
||||
|
||||
public class PreviewPlacerView extends RelativeLayout {
|
||||
private final Paint mGesturePaint;
|
||||
private final Paint mTextPaint;
|
||||
private final int mGestureFloatingPreviewTextColor;
|
||||
private final int mGestureFloatingPreviewTextOffset;
|
||||
private final int mGestureFloatingPreviewTextShadowColor;
|
||||
private final int mGestureFloatingPreviewTextShadowBorder;
|
||||
private final int mGestureFloatingPreviewTextShadingColor;
|
||||
private final int mGestureFloatingPreviewTextShadingBorder;
|
||||
private final int mGestureFloatingPreviewTextConnectorColor;
|
||||
private final int mGestureFloatingPreviewTextConnectorWidth;
|
||||
|
||||
private int mXOrigin;
|
||||
private int mYOrigin;
|
||||
|
||||
private final SparseArray<PointerTracker> mPointers = new SparseArray<PointerTracker>();
|
||||
|
||||
private String mGestureFloatingPreviewText;
|
||||
private boolean mDrawsGesturePreviewTrail;
|
||||
private boolean mDrawsGestureFloatingPreviewText;
|
||||
|
||||
public PreviewPlacerView(Context context, TypedArray keyboardViewAttr) {
|
||||
super(context);
|
||||
setWillNotDraw(false);
|
||||
|
||||
final int gestureFloatingPreviewTextSize = keyboardViewAttr.getDimensionPixelSize(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextSize, 0);
|
||||
mGestureFloatingPreviewTextColor = keyboardViewAttr.getColor(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextColor, 0);
|
||||
mGestureFloatingPreviewTextOffset = keyboardViewAttr.getDimensionPixelOffset(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextOffset, 0);
|
||||
mGestureFloatingPreviewTextShadowColor = keyboardViewAttr.getColor(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextShadowColor, 0);
|
||||
mGestureFloatingPreviewTextShadowBorder = keyboardViewAttr.getDimensionPixelSize(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextShadowBorder, 0);
|
||||
mGestureFloatingPreviewTextShadingColor = keyboardViewAttr.getColor(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextShadingColor, 0);
|
||||
mGestureFloatingPreviewTextShadingBorder = keyboardViewAttr.getDimensionPixelSize(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextShadingBorder, 0);
|
||||
mGestureFloatingPreviewTextConnectorColor = keyboardViewAttr.getColor(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextConnectorColor, 0);
|
||||
mGestureFloatingPreviewTextConnectorWidth = keyboardViewAttr.getDimensionPixelSize(
|
||||
R.styleable.KeyboardView_gestureFloatingPreviewTextConnectorWidth, 0);
|
||||
final int gesturePreviewTrailColor = keyboardViewAttr.getColor(
|
||||
R.styleable.KeyboardView_gesturePreviewTrailColor, 0);
|
||||
final int gesturePreviewTrailWidth = keyboardViewAttr.getDimensionPixelSize(
|
||||
R.styleable.KeyboardView_gesturePreviewTrailWidth, 0);
|
||||
|
||||
mGesturePaint = new Paint();
|
||||
mGesturePaint.setAntiAlias(true);
|
||||
mGesturePaint.setStyle(Paint.Style.STROKE);
|
||||
mGesturePaint.setStrokeJoin(Paint.Join.ROUND);
|
||||
mGesturePaint.setColor(gesturePreviewTrailColor);
|
||||
mGesturePaint.setStrokeWidth(gesturePreviewTrailWidth);
|
||||
|
||||
mTextPaint = new Paint();
|
||||
mTextPaint.setAntiAlias(true);
|
||||
mTextPaint.setStrokeJoin(Paint.Join.ROUND);
|
||||
mTextPaint.setTextAlign(Align.CENTER);
|
||||
mTextPaint.setTextSize(gestureFloatingPreviewTextSize);
|
||||
}
|
||||
|
||||
public void setOrigin(int x, int y) {
|
||||
mXOrigin = x;
|
||||
mYOrigin = y;
|
||||
}
|
||||
|
||||
public void setGesturePreviewMode(boolean drawsGesturePreviewTrail,
|
||||
boolean drawsGestureFloatingPreviewText) {
|
||||
mDrawsGesturePreviewTrail = drawsGesturePreviewTrail;
|
||||
mDrawsGestureFloatingPreviewText = drawsGestureFloatingPreviewText;
|
||||
}
|
||||
|
||||
public void invalidatePointer(PointerTracker tracker) {
|
||||
synchronized (mPointers) {
|
||||
mPointers.put(tracker.mPointerId, tracker);
|
||||
// TODO: Should narrow the invalidate region.
|
||||
invalidate();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDraw(Canvas canvas) {
|
||||
super.onDraw(canvas);
|
||||
synchronized (mPointers) {
|
||||
canvas.translate(mXOrigin, mYOrigin);
|
||||
final int trackerCount = mPointers.size();
|
||||
boolean hasDrawnFloatingPreviewText = false;
|
||||
for (int index = 0; index < trackerCount; index++) {
|
||||
final PointerTracker tracker = mPointers.valueAt(index);
|
||||
if (mDrawsGesturePreviewTrail) {
|
||||
tracker.drawGestureTrail(canvas, mGesturePaint);
|
||||
}
|
||||
// TODO: Figure out more cleaner way to draw gesture preview text.
|
||||
if (mDrawsGestureFloatingPreviewText && !hasDrawnFloatingPreviewText) {
|
||||
drawGestureFloatingPreviewText(canvas, tracker, mGestureFloatingPreviewText);
|
||||
hasDrawnFloatingPreviewText = true;
|
||||
}
|
||||
}
|
||||
canvas.translate(-mXOrigin, -mYOrigin);
|
||||
}
|
||||
}
|
||||
|
||||
public void setGestureFloatingPreviewText(String gestureFloatingPreviewText) {
|
||||
mGestureFloatingPreviewText = gestureFloatingPreviewText;
|
||||
invalidate();
|
||||
}
|
||||
|
||||
private void drawGestureFloatingPreviewText(Canvas canvas, PointerTracker tracker,
|
||||
String gestureFloatingPreviewText) {
|
||||
if (TextUtils.isEmpty(gestureFloatingPreviewText)) {
|
||||
return;
|
||||
}
|
||||
|
||||
final Paint paint = mTextPaint;
|
||||
final int lastX = tracker.getLastX();
|
||||
final int lastY = tracker.getLastY();
|
||||
final int textSize = (int)paint.getTextSize();
|
||||
final int canvasWidth = canvas.getWidth();
|
||||
|
||||
final int halfTextWidth = (int)paint.measureText(gestureFloatingPreviewText) / 2 + textSize;
|
||||
final int textX = Math.min(Math.max(lastX, halfTextWidth), canvasWidth - halfTextWidth);
|
||||
|
||||
int textY = Math.max(-textSize, lastY - mGestureFloatingPreviewTextOffset);
|
||||
if (textY < 0) {
|
||||
// Paint black text shadow if preview extends above keyboard region.
|
||||
paint.setStyle(Paint.Style.FILL_AND_STROKE);
|
||||
paint.setColor(mGestureFloatingPreviewTextShadowColor);
|
||||
paint.setStrokeWidth(mGestureFloatingPreviewTextShadowBorder);
|
||||
canvas.drawText(gestureFloatingPreviewText, textX, textY, paint);
|
||||
}
|
||||
|
||||
// Paint the vertical line connecting the touch point to the preview text.
|
||||
paint.setStyle(Paint.Style.STROKE);
|
||||
paint.setColor(mGestureFloatingPreviewTextConnectorColor);
|
||||
paint.setStrokeWidth(mGestureFloatingPreviewTextConnectorWidth);
|
||||
final int lineTopY = textY - textSize / 4;
|
||||
canvas.drawLine(lastX, lastY, lastX, lineTopY, paint);
|
||||
if (lastX != textX) {
|
||||
// Paint the horizontal line connection the touch point to the preview text.
|
||||
canvas.drawLine(lastX, lineTopY, textX, lineTopY, paint);
|
||||
}
|
||||
|
||||
// Paint the shading for the text preview
|
||||
paint.setStyle(Paint.Style.FILL_AND_STROKE);
|
||||
paint.setColor(mGestureFloatingPreviewTextShadingColor);
|
||||
paint.setStrokeWidth(mGestureFloatingPreviewTextShadingBorder);
|
||||
canvas.drawText(gestureFloatingPreviewText, textX, textY, paint);
|
||||
|
||||
// Paint the text preview
|
||||
paint.setColor(mGestureFloatingPreviewTextColor);
|
||||
paint.setStyle(Paint.Style.FILL);
|
||||
canvas.drawText(gestureFloatingPreviewText, textX, textY, paint);
|
||||
}
|
||||
}
|
|
@ -14,12 +14,14 @@
|
|||
* the License.
|
||||
*/
|
||||
|
||||
package com.android.inputmethod.keyboard;
|
||||
package com.android.inputmethod.keyboard.internal;
|
||||
|
||||
import android.content.Context;
|
||||
import android.util.Log;
|
||||
import android.view.MotionEvent;
|
||||
|
||||
import com.android.inputmethod.keyboard.Keyboard;
|
||||
import com.android.inputmethod.keyboard.MainKeyboardView;
|
||||
import com.android.inputmethod.latin.LatinImeLogger;
|
||||
import com.android.inputmethod.latin.R;
|
||||
import com.android.inputmethod.latin.Utils;
|
|
@ -654,9 +654,12 @@ public class ExpandableDictionary extends Dictionary {
|
|||
--index;
|
||||
mLookedUpString[index] = node.mCode;
|
||||
node = node.mParent;
|
||||
} while (node != null);
|
||||
} while (node != null && index > 0);
|
||||
|
||||
if (freq >= 0) {
|
||||
// If node is null, we have a word longer than MAX_WORD_LENGTH in the dictionary.
|
||||
// It's a little unclear how this can happen, but just in case it does it's safer
|
||||
// to ignore the word in this case.
|
||||
if (freq >= 0 && node == null) {
|
||||
suggestions.add(new SuggestedWordInfo(new String(mLookedUpString, index,
|
||||
BinaryDictionary.MAX_WORD_LENGTH - index),
|
||||
freq, SuggestedWordInfo.KIND_CORRECTION, mDictType));
|
||||
|
|
|
@ -31,11 +31,7 @@ public class JniUtils {
|
|||
try {
|
||||
System.loadLibrary(JniLibName.JNI_LIB_NAME);
|
||||
} catch (UnsatisfiedLinkError ule) {
|
||||
Log.e(TAG, "Could not load native library " + JniLibName.JNI_LIB_NAME);
|
||||
if (LatinImeLogger.sDBG) {
|
||||
throw new RuntimeException(
|
||||
"Could not load native library " + JniLibName.JNI_LIB_NAME);
|
||||
}
|
||||
Log.e(TAG, "Could not load native library " + JniLibName.JNI_LIB_NAME, ule);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -60,6 +60,7 @@ import com.android.inputmethod.accessibility.AccessibilityUtils;
|
|||
import com.android.inputmethod.accessibility.AccessibleKeyboardViewProxy;
|
||||
import com.android.inputmethod.compat.CompatUtils;
|
||||
import com.android.inputmethod.compat.InputMethodManagerCompatWrapper;
|
||||
import com.android.inputmethod.compat.InputMethodServiceCompatUtils;
|
||||
import com.android.inputmethod.compat.SuggestionSpanUtils;
|
||||
import com.android.inputmethod.keyboard.KeyDetector;
|
||||
import com.android.inputmethod.keyboard.Keyboard;
|
||||
|
@ -82,7 +83,8 @@ import java.util.Locale;
|
|||
* Input method implementation for Qwerty'ish keyboard.
|
||||
*/
|
||||
public class LatinIME extends InputMethodService implements KeyboardActionListener,
|
||||
SuggestionStripView.Listener, TargetApplicationGetter.OnTargetApplicationKnownListener {
|
||||
SuggestionStripView.Listener, TargetApplicationGetter.OnTargetApplicationKnownListener,
|
||||
Suggest.SuggestInitializationListener {
|
||||
private static final String TAG = LatinIME.class.getSimpleName();
|
||||
private static final boolean TRACE = false;
|
||||
private static boolean DEBUG;
|
||||
|
@ -174,6 +176,8 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
|
||||
private AlertDialog mOptionsDialog;
|
||||
|
||||
private final boolean mIsHardwareAcceleratedDrawingEnabled;
|
||||
|
||||
public final UIHandler mHandler = new UIHandler(this);
|
||||
|
||||
public static class UIHandler extends StaticInnerHandlerWrapper<LatinIME> {
|
||||
|
@ -346,6 +350,9 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
super();
|
||||
mSubtypeSwitcher = SubtypeSwitcher.getInstance();
|
||||
mKeyboardSwitcher = KeyboardSwitcher.getInstance();
|
||||
mIsHardwareAcceleratedDrawingEnabled =
|
||||
InputMethodServiceCompatUtils.enableHardwareAcceleration(this);
|
||||
Log.i(TAG, "Hardware accelerated drawing: " + mIsHardwareAcceleratedDrawingEnabled);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -426,6 +433,12 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
resetContactsDictionary(null == mSuggest ? null : mSuggest.getContactsDictionary());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onUpdateMainDictionaryAvailability(boolean isMainDictionaryAvailable) {
|
||||
mIsMainDictionaryAvailable = isMainDictionaryAvailable;
|
||||
updateKeyboardViewGestureHandlingModeByMainDictionaryAvailability();
|
||||
}
|
||||
|
||||
private void initSuggest() {
|
||||
final Locale subtypeLocale = mSubtypeSwitcher.getCurrentSubtypeLocale();
|
||||
final String localeStr = subtypeLocale.toString();
|
||||
|
@ -437,7 +450,8 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
} else {
|
||||
oldContactsDictionary = null;
|
||||
}
|
||||
mSuggest = new Suggest(this, subtypeLocale);
|
||||
mSuggest = new Suggest(this /* Context */, subtypeLocale,
|
||||
this /* SuggestInitializationListener */);
|
||||
if (mCurrentSettings.mCorrectionEnabled) {
|
||||
mSuggest.setAutoCorrectionThreshold(mCurrentSettings.mAutoCorrectionThreshold);
|
||||
}
|
||||
|
@ -531,15 +545,16 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
commitTyped(LastComposedWord.NOT_A_SEPARATOR);
|
||||
mConnection.finishComposingText();
|
||||
mConnection.endBatchEdit();
|
||||
if (isShowingOptionDialog())
|
||||
if (isShowingOptionDialog()) {
|
||||
mOptionsDialog.dismiss();
|
||||
}
|
||||
}
|
||||
super.onConfigurationChanged(conf);
|
||||
}
|
||||
|
||||
@Override
|
||||
public View onCreateInputView() {
|
||||
return mKeyboardSwitcher.onCreateInputView();
|
||||
return mKeyboardSwitcher.onCreateInputView(mIsHardwareAcceleratedDrawingEnabled);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -651,40 +666,61 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
accessUtils.onStartInputViewInternal(editorInfo, restarting);
|
||||
}
|
||||
|
||||
mSubtypeSwitcher.updateParametersOnStartInputView();
|
||||
if (!restarting) {
|
||||
mSubtypeSwitcher.updateParametersOnStartInputView();
|
||||
}
|
||||
|
||||
// The EditorInfo might have a flag that affects fullscreen mode.
|
||||
// Note: This call should be done by InputMethodService?
|
||||
updateFullscreenMode();
|
||||
mLastSelectionStart = editorInfo.initialSelStart;
|
||||
mLastSelectionEnd = editorInfo.initialSelEnd;
|
||||
mApplicationSpecifiedCompletions = null;
|
||||
|
||||
inputView.closing();
|
||||
mEnteredText = null;
|
||||
resetComposingState(true /* alsoResetLastComposedWord */);
|
||||
mDeleteCount = 0;
|
||||
mSpaceState = SPACE_STATE_NONE;
|
||||
final boolean selectionChanged = mLastSelectionStart != editorInfo.initialSelStart
|
||||
|| mLastSelectionEnd != editorInfo.initialSelEnd;
|
||||
if (!restarting || selectionChanged) {
|
||||
// If the selection changed, we reset the input state. Essentially, we come here with
|
||||
// restarting == true when the app called setText() or similar. We should reset the
|
||||
// state if the app set the text to something else, but keep it if it set a suggestion
|
||||
// or something.
|
||||
mEnteredText = null;
|
||||
resetComposingState(true /* alsoResetLastComposedWord */);
|
||||
mDeleteCount = 0;
|
||||
mSpaceState = SPACE_STATE_NONE;
|
||||
|
||||
loadSettings();
|
||||
|
||||
if (mSuggest != null && mCurrentSettings.mCorrectionEnabled) {
|
||||
mSuggest.setAutoCorrectionThreshold(mCurrentSettings.mAutoCorrectionThreshold);
|
||||
if (mSuggestionStripView != null) {
|
||||
mSuggestionStripView.clear();
|
||||
}
|
||||
}
|
||||
|
||||
switcher.loadKeyboard(editorInfo, mCurrentSettings);
|
||||
if (!restarting) {
|
||||
inputView.closing();
|
||||
loadSettings();
|
||||
|
||||
if (mSuggestionStripView != null)
|
||||
mSuggestionStripView.clear();
|
||||
if (mSuggest != null && mCurrentSettings.mCorrectionEnabled) {
|
||||
mSuggest.setAutoCorrectionThreshold(mCurrentSettings.mAutoCorrectionThreshold);
|
||||
}
|
||||
|
||||
switcher.loadKeyboard(editorInfo, mCurrentSettings);
|
||||
updateKeyboardViewGestureHandlingModeByMainDictionaryAvailability();
|
||||
}
|
||||
setSuggestionStripShownInternal(
|
||||
isSuggestionsStripVisible(), /* needsInputViewShown */ false);
|
||||
|
||||
mLastSelectionStart = editorInfo.initialSelStart;
|
||||
mLastSelectionEnd = editorInfo.initialSelEnd;
|
||||
// If we come here something in the text state is very likely to have changed.
|
||||
// We should update the shift state regardless of whether we are restarting or not, because
|
||||
// this is not perceived as a layout change that may be disruptive like we may have with
|
||||
// switcher.loadKeyboard; in apps like Talk, we come here when the text is sent and the
|
||||
// field gets emptied and we need to re-evaluate the shift state, but not the whole layout
|
||||
// which would be disruptive.
|
||||
mKeyboardSwitcher.updateShiftState();
|
||||
|
||||
mHandler.cancelUpdateSuggestionStrip();
|
||||
mHandler.cancelDoubleSpacesTimer();
|
||||
|
||||
inputView.setKeyPreviewPopupEnabled(mCurrentSettings.mKeyPreviewPopupOn,
|
||||
mCurrentSettings.mKeyPreviewPopupDismissDelay);
|
||||
inputView.setProximityCorrectionEnabled(true);
|
||||
|
||||
if (TRACE) Debug.startMethodTracing("/data/trace/latinime");
|
||||
}
|
||||
|
@ -856,13 +892,13 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
}
|
||||
}
|
||||
}
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_onDisplayCompletions(applicationSpecifiedCompletions);
|
||||
}
|
||||
if (!mCurrentSettings.isApplicationSpecifiedCompletionsOn()) return;
|
||||
mApplicationSpecifiedCompletions = applicationSpecifiedCompletions;
|
||||
if (applicationSpecifiedCompletions == null) {
|
||||
clearSuggestionStrip();
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_onDisplayCompletions(null);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -884,6 +920,9 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
// this case? This says to keep whatever the user typed.
|
||||
mWordComposer.setAutoCorrection(mWordComposer.getTypedWord());
|
||||
setSuggestionStripShown(true);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_onDisplayCompletions(applicationSpecifiedCompletions);
|
||||
}
|
||||
}
|
||||
|
||||
private void setSuggestionStripShownInternal(boolean shown, boolean needsInputViewShown) {
|
||||
|
@ -1003,15 +1042,11 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
final CharSequence typedWord = mWordComposer.getTypedWord();
|
||||
if (typedWord.length() > 0) {
|
||||
mConnection.commitText(typedWord, 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_commitText(typedWord);
|
||||
}
|
||||
final CharSequence prevWord = addToUserHistoryDictionary(typedWord);
|
||||
mLastComposedWord = mWordComposer.commitWord(
|
||||
LastComposedWord.COMMIT_TYPE_USER_TYPED_WORD, typedWord.toString(),
|
||||
separatorCode, prevWord);
|
||||
}
|
||||
updateSuggestionStrip();
|
||||
}
|
||||
|
||||
// Called from the KeyboardSwitcher which needs to know auto caps state to display
|
||||
|
@ -1048,12 +1083,9 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
if (lastTwo != null && lastTwo.length() == 2
|
||||
&& lastTwo.charAt(0) == Keyboard.CODE_SPACE) {
|
||||
mConnection.deleteSurroundingText(2, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(2);
|
||||
}
|
||||
mConnection.commitText(lastTwo.charAt(1) + " ", 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_swapSwapperAndSpaceWhileInBatchEdit();
|
||||
ResearchLogger.latinIME_swapSwapperAndSpace();
|
||||
}
|
||||
mKeyboardSwitcher.updateShiftState();
|
||||
}
|
||||
|
@ -1070,9 +1102,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
mHandler.cancelDoubleSpacesTimer();
|
||||
mConnection.deleteSurroundingText(2, 0);
|
||||
mConnection.commitText(". ", 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_doubleSpaceAutoPeriod();
|
||||
}
|
||||
mKeyboardSwitcher.updateShiftState();
|
||||
return true;
|
||||
}
|
||||
|
@ -1136,9 +1165,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
|
||||
private void performEditorAction(int actionId) {
|
||||
mConnection.performEditorAction(actionId);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_performEditorAction(actionId);
|
||||
}
|
||||
}
|
||||
|
||||
private void handleLanguageSwitchKey() {
|
||||
|
@ -1175,6 +1201,9 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
// For backward compatibility. See {@link InputMethodService#sendKeyChar(char)}.
|
||||
if (code >= '0' && code <= '9') {
|
||||
super.sendKeyChar((char)code);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_sendKeyCodePoint(code);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1191,9 +1220,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
final String text = new String(new int[] { code }, 0, 1);
|
||||
mConnection.commitText(text, text.length());
|
||||
}
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_sendKeyCodePoint(code);
|
||||
}
|
||||
}
|
||||
|
||||
// Implementation of {@link KeyboardActionListener}.
|
||||
|
@ -1205,11 +1231,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
}
|
||||
mLastKeyTime = when;
|
||||
mConnection.beginBatchEdit();
|
||||
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_onCodeInput(primaryCode, x, y);
|
||||
}
|
||||
|
||||
final KeyboardSwitcher switcher = mKeyboardSwitcher;
|
||||
// The space state depends only on the last character pressed and its own previous
|
||||
// state. Here, we revert the space state to neutral if the key is actually modifying
|
||||
|
@ -1291,21 +1312,22 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
mLastComposedWord.deactivate();
|
||||
mEnteredText = null;
|
||||
mConnection.endBatchEdit();
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_onCodeInput(primaryCode, x, y);
|
||||
}
|
||||
}
|
||||
|
||||
// Called from PointerTracker through the KeyboardActionListener interface
|
||||
@Override
|
||||
public void onTextInput(CharSequence text) {
|
||||
public void onTextInput(CharSequence rawText) {
|
||||
mConnection.beginBatchEdit();
|
||||
commitTyped(LastComposedWord.NOT_A_SEPARATOR);
|
||||
text = specificTldProcessingOnTextInput(text);
|
||||
mHandler.postUpdateSuggestionStrip();
|
||||
final CharSequence text = specificTldProcessingOnTextInput(rawText);
|
||||
if (SPACE_STATE_PHANTOM == mSpaceState) {
|
||||
sendKeyCodePoint(Keyboard.CODE_SPACE);
|
||||
}
|
||||
mConnection.commitText(text, 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_commitText(text);
|
||||
}
|
||||
mConnection.endBatchEdit();
|
||||
mKeyboardSwitcher.updateShiftState();
|
||||
mKeyboardSwitcher.onCodeInput(Keyboard.CODE_OUTPUT_TEXT);
|
||||
|
@ -1334,6 +1356,10 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
mWordComposer.setBatchInputPointers(batchPointers);
|
||||
final SuggestedWords suggestedWords = getSuggestedWords();
|
||||
showSuggestionStrip(suggestedWords, null);
|
||||
final String gestureFloatingPreviewText = (suggestedWords.size() > 0)
|
||||
? suggestedWords.getWord(0) : null;
|
||||
mKeyboardSwitcher.getKeyboardView()
|
||||
.showGestureFloatingPreviewText(gestureFloatingPreviewText);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -1341,6 +1367,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
mWordComposer.setBatchInputPointers(batchPointers);
|
||||
final SuggestedWords suggestedWords = getSuggestedWords();
|
||||
showSuggestionStrip(suggestedWords, null);
|
||||
mKeyboardSwitcher.getKeyboardView().showGestureFloatingPreviewText(null);
|
||||
if (suggestedWords == null || suggestedWords.size() == 0) {
|
||||
return;
|
||||
}
|
||||
|
@ -1395,9 +1422,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
// like the smiley key or the .com key.
|
||||
final int length = mEnteredText.length();
|
||||
mConnection.deleteSurroundingText(length, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(length);
|
||||
}
|
||||
// If we have mEnteredText, then we know that mHasUncommittedTypedChars == false.
|
||||
// In addition we know that spaceState is false, and that we should not be
|
||||
// reverting any autocorrect at this point. So we can safely return.
|
||||
|
@ -1417,9 +1441,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
mHandler.postUpdateSuggestionStrip();
|
||||
} else {
|
||||
mConnection.deleteSurroundingText(1, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(1);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (mLastComposedWord.canRevertCommit()) {
|
||||
|
@ -1448,9 +1469,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
final int lengthToDelete = mLastSelectionEnd - mLastSelectionStart;
|
||||
mConnection.setSelection(mLastSelectionEnd, mLastSelectionEnd);
|
||||
mConnection.deleteSurroundingText(lengthToDelete, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(lengthToDelete);
|
||||
}
|
||||
} else {
|
||||
// There is no selection, just delete one character.
|
||||
if (NOT_A_CURSOR_POSITION == mLastSelectionEnd) {
|
||||
|
@ -1469,14 +1487,8 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
} else {
|
||||
mConnection.deleteSurroundingText(1, 0);
|
||||
}
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(1);
|
||||
}
|
||||
if (mDeleteCount > DELETE_ACCELERATE_AT) {
|
||||
mConnection.deleteSurroundingText(1, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(1);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (mCurrentSettings.isSuggestionsRequested(mDisplayOrientation)) {
|
||||
|
@ -1579,11 +1591,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
boolean didAutoCorrect = false;
|
||||
// Handle separator
|
||||
if (mWordComposer.isComposingWord()) {
|
||||
// In certain languages where single quote is a separator, it's better
|
||||
// not to auto correct, but accept the typed word. For instance,
|
||||
// in Italian dov' should not be expanded to dove' because the elision
|
||||
// requires the last vowel to be removed.
|
||||
if (mCurrentSettings.mCorrectionEnabled && primaryCode != Keyboard.CODE_SINGLE_QUOTE) {
|
||||
if (mCurrentSettings.mCorrectionEnabled) {
|
||||
commitCurrentAutoCorrection(primaryCode);
|
||||
didAutoCorrect = true;
|
||||
} else {
|
||||
|
@ -1617,13 +1625,18 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
if (swapWeakSpace) {
|
||||
swapSwapperAndSpace();
|
||||
mSpaceState = SPACE_STATE_SWAP_PUNCTUATION;
|
||||
} else if (SPACE_STATE_PHANTOM == spaceState) {
|
||||
} else if (SPACE_STATE_PHANTOM == spaceState
|
||||
&& !mCurrentSettings.isWeakSpaceStripper(primaryCode)) {
|
||||
// If we are in phantom space state, and the user presses a separator, we want to
|
||||
// stay in phantom space state so that the next keypress has a chance to add the
|
||||
// space. For example, if I type "Good dat", pick "day" from the suggestion strip
|
||||
// then insert a comma and go on to typing the next word, I want the space to be
|
||||
// inserted automatically before the next word, the same way it is when I don't
|
||||
// input the comma.
|
||||
// The case is a little different if the separator is a space stripper. Such a
|
||||
// separator does not normally need a space on the right (that's the difference
|
||||
// between swappers and strippers), so we should not stay in phantom space state if
|
||||
// the separator is a stripper. Hence the additional test above.
|
||||
mSpaceState = SPACE_STATE_PHANTOM;
|
||||
}
|
||||
|
||||
|
@ -1647,8 +1660,9 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
commitTyped(LastComposedWord.NOT_A_SEPARATOR);
|
||||
requestHideSelf(0);
|
||||
MainKeyboardView inputView = mKeyboardSwitcher.getKeyboardView();
|
||||
if (inputView != null)
|
||||
if (inputView != null) {
|
||||
inputView.closing();
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: make this private
|
||||
|
@ -1799,10 +1813,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
+ "is empty? Impossible! I must commit suicide.");
|
||||
}
|
||||
Utils.Stats.onAutoCorrection(typedWord, autoCorrection.toString(), separatorCodePoint);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_commitCurrentAutoCorrection(typedWord,
|
||||
autoCorrection.toString());
|
||||
}
|
||||
mExpectingUpdateSelection = true;
|
||||
commitChosenWord(autoCorrection, LastComposedWord.COMMIT_TYPE_DECIDED_WORD,
|
||||
separatorCodePoint);
|
||||
|
@ -1828,13 +1838,13 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
// So, LatinImeLogger logs "" as a user's input.
|
||||
LatinImeLogger.logOnManualSuggestion("", suggestion.toString(), index, suggestedWords);
|
||||
// Rely on onCodeInput to do the complicated swapping/stripping logic consistently.
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_punctuationSuggestion(index, suggestion, x, y);
|
||||
}
|
||||
final int primaryCode = suggestion.charAt(0);
|
||||
onCodeInput(primaryCode,
|
||||
KeyboardActionListener.SUGGESTION_STRIP_COORDINATE,
|
||||
KeyboardActionListener.SUGGESTION_STRIP_COORDINATE);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_punctuationSuggestion(index, suggestion, x, y);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1861,10 +1871,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
final CompletionInfo completionInfo = mApplicationSpecifiedCompletions[index];
|
||||
mConnection.commitCompletion(completionInfo);
|
||||
mConnection.endBatchEdit();
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_pickApplicationSpecifiedCompletion(index,
|
||||
completionInfo.getText(), x, y);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1873,12 +1879,12 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
final String replacedWord = mWordComposer.getTypedWord().toString();
|
||||
LatinImeLogger.logOnManualSuggestion(replacedWord,
|
||||
suggestion.toString(), index, suggestedWords);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_pickSuggestionManually(replacedWord, index, suggestion, x, y);
|
||||
}
|
||||
mExpectingUpdateSelection = true;
|
||||
commitChosenWord(suggestion, LastComposedWord.COMMIT_TYPE_MANUAL_PICK,
|
||||
LastComposedWord.NOT_A_SEPARATOR);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_pickSuggestionManually(replacedWord, index, suggestion, x, y);
|
||||
}
|
||||
mConnection.endBatchEdit();
|
||||
// Don't allow cancellation of manual pick
|
||||
mLastComposedWord.deactivate();
|
||||
|
@ -1913,9 +1919,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
final SuggestedWords suggestedWords = mSuggestionStripView.getSuggestions();
|
||||
mConnection.commitText(SuggestionSpanUtils.getTextWithSuggestionSpan(
|
||||
this, chosenWord, suggestedWords, mIsMainDictionaryAvailable), 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_commitText(chosenWord);
|
||||
}
|
||||
// Add the word to the user history dictionary
|
||||
final CharSequence prevWord = addToUserHistoryDictionary(chosenWord);
|
||||
// TODO: figure out here if this is an auto-correct or if the best word is actually
|
||||
|
@ -1982,9 +1985,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
mWordComposer.setComposingWord(word, mKeyboardSwitcher.getKeyboard());
|
||||
final int length = word.length();
|
||||
mConnection.deleteSurroundingText(length, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(length);
|
||||
}
|
||||
mConnection.setComposingText(word, 1);
|
||||
mHandler.postUpdateSuggestionStrip();
|
||||
}
|
||||
|
@ -2012,9 +2012,6 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
}
|
||||
}
|
||||
mConnection.deleteSurroundingText(deleteLength, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(deleteLength);
|
||||
}
|
||||
if (!TextUtils.isEmpty(previousWord) && !TextUtils.isEmpty(committedWord)) {
|
||||
mUserHistoryDictionary.cancelAddingUserHistory(
|
||||
previousWord.toString(), committedWord.toString());
|
||||
|
@ -2044,18 +2041,30 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
|
|||
public void onRefreshKeyboard() {
|
||||
// When the device locale is changed in SetupWizard etc., this method may get called via
|
||||
// onConfigurationChanged before SoftInputWindow is shown.
|
||||
initSuggest();
|
||||
loadSettings();
|
||||
if (mKeyboardSwitcher.getKeyboardView() != null) {
|
||||
// Reload keyboard because the current language has been changed.
|
||||
mKeyboardSwitcher.loadKeyboard(getCurrentInputEditorInfo(), mCurrentSettings);
|
||||
updateKeyboardViewGestureHandlingModeByMainDictionaryAvailability();
|
||||
}
|
||||
initSuggest();
|
||||
loadSettings();
|
||||
// Since we just changed languages, we should re-evaluate suggestions with whatever word
|
||||
// we are currently composing. If we are not composing anything, we may want to display
|
||||
// predictions or punctuation signs (which is done by the updateSuggestionStrip anyway).
|
||||
mHandler.postUpdateSuggestionStrip();
|
||||
}
|
||||
|
||||
private void updateKeyboardViewGestureHandlingModeByMainDictionaryAvailability() {
|
||||
final MainKeyboardView keyboardView = mKeyboardSwitcher.getKeyboardView();
|
||||
if (keyboardView != null) {
|
||||
final boolean shouldHandleGesture = mCurrentSettings.mGestureInputEnabled
|
||||
&& mIsMainDictionaryAvailable;
|
||||
keyboardView.setGestureHandlingMode(shouldHandleGesture,
|
||||
mCurrentSettings.mGesturePreviewTrailEnabled,
|
||||
mCurrentSettings.mGestureFloatingPreviewTextEnabled);
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: Remove this method from {@link LatinIME} and move {@link FeedbackManager} to
|
||||
// {@link KeyboardSwitcher}. Called from KeyboardSwitcher
|
||||
public void hapticAndAudioFeedback(final int primaryCode) {
|
||||
|
|
|
@ -55,7 +55,9 @@ public class RichInputConnection {
|
|||
public void beginBatchEdit() {
|
||||
if (++mNestLevel == 1) {
|
||||
mIC = mParent.getCurrentInputConnection();
|
||||
if (null != mIC) mIC.beginBatchEdit();
|
||||
if (null != mIC) {
|
||||
mIC.beginBatchEdit();
|
||||
}
|
||||
} else {
|
||||
if (DBG) {
|
||||
throw new RuntimeException("Nest level too deep");
|
||||
|
@ -66,7 +68,9 @@ public class RichInputConnection {
|
|||
}
|
||||
public void endBatchEdit() {
|
||||
if (mNestLevel <= 0) Log.e(TAG, "Batch edit not in progress!"); // TODO: exception instead
|
||||
if (--mNestLevel == 0 && null != mIC) mIC.endBatchEdit();
|
||||
if (--mNestLevel == 0 && null != mIC) {
|
||||
mIC.endBatchEdit();
|
||||
}
|
||||
}
|
||||
|
||||
private void checkBatchEdit() {
|
||||
|
@ -79,12 +83,22 @@ public class RichInputConnection {
|
|||
|
||||
public void finishComposingText() {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.finishComposingText();
|
||||
if (null != mIC) {
|
||||
mIC.finishComposingText();
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_finishComposingText();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void commitText(final CharSequence text, final int i) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.commitText(text, i);
|
||||
if (null != mIC) {
|
||||
mIC.commitText(text, i);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_commitText(text, i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public int getCursorCapsMode(final int inputType) {
|
||||
|
@ -107,37 +121,72 @@ public class RichInputConnection {
|
|||
|
||||
public void deleteSurroundingText(final int i, final int j) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.deleteSurroundingText(i, j);
|
||||
if (null != mIC) {
|
||||
mIC.deleteSurroundingText(i, j);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_deleteSurroundingText(i, j);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void performEditorAction(final int actionId) {
|
||||
mIC = mParent.getCurrentInputConnection();
|
||||
if (null != mIC) mIC.performEditorAction(actionId);
|
||||
if (null != mIC) {
|
||||
mIC.performEditorAction(actionId);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_performEditorAction(actionId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void sendKeyEvent(final KeyEvent keyEvent) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.sendKeyEvent(keyEvent);
|
||||
if (null != mIC) {
|
||||
mIC.sendKeyEvent(keyEvent);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_sendKeyEvent(keyEvent);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setComposingText(final CharSequence text, final int i) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.setComposingText(text, i);
|
||||
if (null != mIC) {
|
||||
mIC.setComposingText(text, i);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_setComposingText(text, i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setSelection(final int from, final int to) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.setSelection(from, to);
|
||||
if (null != mIC) {
|
||||
mIC.setSelection(from, to);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_setSelection(from, to);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void commitCorrection(final CorrectionInfo correctionInfo) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.commitCorrection(correctionInfo);
|
||||
if (null != mIC) {
|
||||
mIC.commitCorrection(correctionInfo);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_commitCorrection(correctionInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void commitCompletion(final CompletionInfo completionInfo) {
|
||||
checkBatchEdit();
|
||||
if (null != mIC) mIC.commitCompletion(completionInfo);
|
||||
if (null != mIC) {
|
||||
mIC.commitCompletion(completionInfo);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.richInputConnection_commitCompletion(completionInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public CharSequence getNthPreviousWord(final String sentenceSeperators, final int n) {
|
||||
|
@ -315,9 +364,6 @@ public class RichInputConnection {
|
|||
if (lastOne != null && lastOne.length() == 1
|
||||
&& lastOne.charAt(0) == Keyboard.CODE_SPACE) {
|
||||
deleteSurroundingText(1, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -382,13 +428,7 @@ public class RichInputConnection {
|
|||
return false;
|
||||
}
|
||||
deleteSurroundingText(2, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(2);
|
||||
}
|
||||
commitText(" ", 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_revertDoubleSpaceWhileInBatchEdit();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -409,13 +449,7 @@ public class RichInputConnection {
|
|||
return false;
|
||||
}
|
||||
deleteSurroundingText(2, 0);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_deleteSurroundingText(2);
|
||||
}
|
||||
commitText(" " + textBeforeCursor.subSequence(0, 1), 1);
|
||||
if (ProductionFlag.IS_EXPERIMENTAL) {
|
||||
ResearchLogger.latinIME_revertSwapPunctuation();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -62,6 +62,7 @@ public class Settings extends InputMethodSettingsFragment
|
|||
public static final String PREF_LAST_USER_DICTIONARY_WRITE_TIME =
|
||||
"last_user_dictionary_write_time";
|
||||
public static final String PREF_ADVANCED_SETTINGS = "pref_advanced_settings";
|
||||
public static final String PREF_KEY_USE_CONTACTS_DICT = "pref_key_use_contacts_dict";
|
||||
public static final String PREF_SUPPRESS_LANGUAGE_SWITCH_KEY =
|
||||
"pref_suppress_language_switch_key";
|
||||
public static final String PREF_INCLUDE_OTHER_IMES_IN_LANGUAGE_SWITCH_LIST =
|
||||
|
@ -69,13 +70,15 @@ public class Settings extends InputMethodSettingsFragment
|
|||
public static final String PREF_CUSTOM_INPUT_STYLES = "custom_input_styles";
|
||||
public static final String PREF_KEY_PREVIEW_POPUP_DISMISS_DELAY =
|
||||
"pref_key_preview_popup_dismiss_delay";
|
||||
public static final String PREF_KEY_USE_CONTACTS_DICT = "pref_key_use_contacts_dict";
|
||||
public static final String PREF_BIGRAM_PREDICTIONS = "next_word_prediction";
|
||||
public static final String PREF_GESTURE_INPUT = "gesture_input";
|
||||
public static final String PREF_VIBRATION_DURATION_SETTINGS =
|
||||
"pref_vibration_duration_settings";
|
||||
public static final String PREF_KEYPRESS_SOUND_VOLUME =
|
||||
"pref_keypress_sound_volume";
|
||||
public static final String PREF_GESTURE_PREVIEW_TRAIL = "pref_gesture_preview_trail";
|
||||
public static final String PREF_GESTURE_FLOATING_PREVIEW_TEXT =
|
||||
"pref_gesture_floating_preview_text";
|
||||
|
||||
public static final String PREF_INPUT_LANGUAGE = "input_language";
|
||||
public static final String PREF_SELECTED_LANGUAGES = "selected_languages";
|
||||
|
@ -94,13 +97,17 @@ public class Settings extends InputMethodSettingsFragment
|
|||
private TextView mKeypressVibrationDurationSettingsTextView;
|
||||
private TextView mKeypressSoundVolumeSettingsTextView;
|
||||
|
||||
private static void setPreferenceEnabled(Preference preference, boolean enabled) {
|
||||
if (preference != null) {
|
||||
preference.setEnabled(enabled);
|
||||
}
|
||||
}
|
||||
|
||||
private void ensureConsistencyOfAutoCorrectionSettings() {
|
||||
final String autoCorrectionOff = getResources().getString(
|
||||
R.string.auto_correction_threshold_mode_index_off);
|
||||
final String currentSetting = mAutoCorrectionThresholdPreference.getValue();
|
||||
if (null != mBigramPrediction) {
|
||||
mBigramPrediction.setEnabled(!currentSetting.equals(autoCorrectionOff));
|
||||
}
|
||||
setPreferenceEnabled(mBigramPrediction, !currentSetting.equals(autoCorrectionOff));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -180,13 +187,11 @@ public class Settings extends InputMethodSettingsFragment
|
|||
if (null == mKeyPreviewPopupDismissDelay.getValue()) {
|
||||
mKeyPreviewPopupDismissDelay.setValue(popupDismissDelayDefaultValue);
|
||||
}
|
||||
mKeyPreviewPopupDismissDelay.setEnabled(
|
||||
setPreferenceEnabled(mKeyPreviewPopupDismissDelay,
|
||||
SettingsValues.isKeyPreviewPopupEnabled(prefs, res));
|
||||
}
|
||||
|
||||
final CheckBoxPreference includeOtherImesInLanguageSwitchList =
|
||||
(CheckBoxPreference)findPreference(PREF_INCLUDE_OTHER_IMES_IN_LANGUAGE_SWITCH_LIST);
|
||||
includeOtherImesInLanguageSwitchList.setEnabled(
|
||||
setPreferenceEnabled(findPreference(PREF_INCLUDE_OTHER_IMES_IN_LANGUAGE_SWITCH_LIST),
|
||||
!SettingsValues.isLanguageSwitchKeySupressed(prefs));
|
||||
|
||||
final PreferenceScreen dictionaryLink =
|
||||
|
@ -200,10 +205,19 @@ public class Settings extends InputMethodSettingsFragment
|
|||
|
||||
final boolean gestureInputEnabledByBuildConfig = res.getBoolean(
|
||||
R.bool.config_gesture_input_enabled_by_build_config);
|
||||
final Preference gesturePreviewTrail = findPreference(PREF_GESTURE_PREVIEW_TRAIL);
|
||||
final Preference gestureFloatingPreviewText = findPreference(
|
||||
PREF_GESTURE_FLOATING_PREVIEW_TEXT);
|
||||
if (!gestureInputEnabledByBuildConfig) {
|
||||
final Preference gestureInputPref = findPreference(PREF_GESTURE_INPUT);
|
||||
miscSettings.removePreference(gestureInputPref);
|
||||
miscSettings.removePreference(findPreference(PREF_GESTURE_INPUT));
|
||||
miscSettings.removePreference(gesturePreviewTrail);
|
||||
miscSettings.removePreference(gestureFloatingPreviewText);
|
||||
} else {
|
||||
final boolean gestureInputEnabledByUser = prefs.getBoolean(PREF_GESTURE_INPUT, true);
|
||||
setPreferenceEnabled(gesturePreviewTrail, gestureInputEnabledByUser);
|
||||
setPreferenceEnabled(gestureFloatingPreviewText, gestureInputEnabledByUser);
|
||||
}
|
||||
|
||||
final boolean showUsabilityStudyModeOption =
|
||||
res.getBoolean(R.bool.config_enable_usability_study_mode_option)
|
||||
|| ProductionFlag.IS_EXPERIMENTAL || ENABLE_EXPERIMENTAL_SETTINGS;
|
||||
|
@ -277,17 +291,22 @@ public class Settings extends InputMethodSettingsFragment
|
|||
public void onSharedPreferenceChanged(SharedPreferences prefs, String key) {
|
||||
(new BackupManager(getActivity())).dataChanged();
|
||||
if (key.equals(PREF_POPUP_ON)) {
|
||||
final ListPreference popupDismissDelay =
|
||||
(ListPreference)findPreference(PREF_KEY_PREVIEW_POPUP_DISMISS_DELAY);
|
||||
if (null != popupDismissDelay) {
|
||||
popupDismissDelay.setEnabled(prefs.getBoolean(PREF_POPUP_ON, true));
|
||||
}
|
||||
setPreferenceEnabled(findPreference(PREF_KEY_PREVIEW_POPUP_DISMISS_DELAY),
|
||||
prefs.getBoolean(PREF_POPUP_ON, true));
|
||||
} else if (key.equals(PREF_SUPPRESS_LANGUAGE_SWITCH_KEY)) {
|
||||
final CheckBoxPreference includeOtherImesInLanguageSwicthList =
|
||||
(CheckBoxPreference)findPreference(
|
||||
PREF_INCLUDE_OTHER_IMES_IN_LANGUAGE_SWITCH_LIST);
|
||||
includeOtherImesInLanguageSwicthList.setEnabled(
|
||||
setPreferenceEnabled(findPreference(PREF_INCLUDE_OTHER_IMES_IN_LANGUAGE_SWITCH_LIST),
|
||||
!SettingsValues.isLanguageSwitchKeySupressed(prefs));
|
||||
} else if (key.equals(PREF_GESTURE_INPUT)) {
|
||||
final boolean gestureInputEnabledByConfig = getResources().getBoolean(
|
||||
R.bool.config_gesture_input_enabled_by_build_config);
|
||||
if (gestureInputEnabledByConfig) {
|
||||
final boolean gestureInputEnabledByUser = prefs.getBoolean(
|
||||
PREF_GESTURE_INPUT, true);
|
||||
setPreferenceEnabled(findPreference(PREF_GESTURE_PREVIEW_TRAIL),
|
||||
gestureInputEnabledByUser);
|
||||
setPreferenceEnabled(findPreference(PREF_GESTURE_FLOATING_PREVIEW_TEXT),
|
||||
gestureInputEnabledByUser);
|
||||
}
|
||||
}
|
||||
ensureConsistencyOfAutoCorrectionSettings();
|
||||
updateVoiceModeSummary();
|
||||
|
@ -335,16 +354,18 @@ public class Settings extends InputMethodSettingsFragment
|
|||
private void refreshEnablingsOfKeypressSoundAndVibrationSettings(
|
||||
SharedPreferences sp, Resources res) {
|
||||
if (mKeypressVibrationDurationSettingsPref != null) {
|
||||
final boolean hasVibrator = VibratorUtils.getInstance(getActivity()).hasVibrator();
|
||||
final boolean vibrateOn = hasVibrator && sp.getBoolean(Settings.PREF_VIBRATE_ON,
|
||||
final boolean hasVibratorHardware = VibratorUtils.getInstance(getActivity())
|
||||
.hasVibrator();
|
||||
final boolean vibrateOnByUser = sp.getBoolean(Settings.PREF_VIBRATE_ON,
|
||||
res.getBoolean(R.bool.config_default_vibration_enabled));
|
||||
mKeypressVibrationDurationSettingsPref.setEnabled(vibrateOn);
|
||||
setPreferenceEnabled(mKeypressVibrationDurationSettingsPref,
|
||||
hasVibratorHardware && vibrateOnByUser);
|
||||
}
|
||||
|
||||
if (mKeypressSoundVolumeSettingsPref != null) {
|
||||
final boolean soundOn = sp.getBoolean(Settings.PREF_SOUND_ON,
|
||||
res.getBoolean(R.bool.config_default_sound_enabled));
|
||||
mKeypressSoundVolumeSettingsPref.setEnabled(soundOn);
|
||||
setPreferenceEnabled(mKeypressSoundVolumeSettingsPref, soundOn);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -84,6 +84,8 @@ public class SettingsValues {
|
|||
private final float mKeypressSoundVolumeRawValue;
|
||||
private final InputMethodSubtype[] mAdditionalSubtypes;
|
||||
public final boolean mGestureInputEnabled;
|
||||
public final boolean mGesturePreviewTrailEnabled;
|
||||
public final boolean mGestureFloatingPreviewTextEnabled;
|
||||
|
||||
// From the input box
|
||||
private final InputAttributes mInputAttributes;
|
||||
|
@ -174,6 +176,9 @@ public class SettingsValues {
|
|||
R.bool.config_gesture_input_enabled_by_build_config);
|
||||
mGestureInputEnabled = gestureInputEnabledByBuildConfig
|
||||
&& prefs.getBoolean(Settings.PREF_GESTURE_INPUT, true);
|
||||
mGesturePreviewTrailEnabled = prefs.getBoolean(Settings.PREF_GESTURE_PREVIEW_TRAIL, true);
|
||||
mGestureFloatingPreviewTextEnabled = prefs.getBoolean(
|
||||
Settings.PREF_GESTURE_FLOATING_PREVIEW_TEXT, true);
|
||||
mCorrectionEnabled = mAutoCorrectEnabled && !mInputAttributes.mInputTypeNoAutoCorrect;
|
||||
mSuggestionVisibility = createSuggestionVisibility(res);
|
||||
}
|
||||
|
|
|
@ -42,6 +42,10 @@ public class Suggest {
|
|||
// TODO: rename this to CORRECTION_ON
|
||||
public static final int CORRECTION_FULL = 1;
|
||||
|
||||
public interface SuggestInitializationListener {
|
||||
public void onUpdateMainDictionaryAvailability(boolean isMainDictionaryAvailable);
|
||||
}
|
||||
|
||||
private static final boolean DBG = LatinImeLogger.sDBG;
|
||||
|
||||
private Dictionary mMainDictionary;
|
||||
|
@ -55,11 +59,14 @@ public class Suggest {
|
|||
private float mAutoCorrectionThreshold;
|
||||
|
||||
// Locale used for upper- and title-casing words
|
||||
final private Locale mLocale;
|
||||
private final Locale mLocale;
|
||||
private final SuggestInitializationListener mListener;
|
||||
|
||||
public Suggest(final Context context, final Locale locale) {
|
||||
public Suggest(final Context context, final Locale locale,
|
||||
final SuggestInitializationListener listener) {
|
||||
initAsynchronously(context, locale);
|
||||
mLocale = locale;
|
||||
mListener = listener;
|
||||
}
|
||||
|
||||
/* package for test */ Suggest(final Context context, final File dictionary,
|
||||
|
@ -67,6 +74,7 @@ public class Suggest {
|
|||
final Dictionary mainDict = DictionaryFactory.createDictionaryForTest(context, dictionary,
|
||||
startOffset, length /* useFullEditDistance */, false, locale);
|
||||
mLocale = locale;
|
||||
mListener = null;
|
||||
mMainDictionary = mainDict;
|
||||
addOrReplaceDictionary(mDictionaries, Dictionary.TYPE_MAIN, mainDict);
|
||||
initWhitelistAndAutocorrectAndPool(context, locale);
|
||||
|
@ -98,6 +106,9 @@ public class Suggest {
|
|||
|
||||
public void resetMainDict(final Context context, final Locale locale) {
|
||||
mMainDictionary = null;
|
||||
if (mListener != null) {
|
||||
mListener.onUpdateMainDictionaryAvailability(hasMainDictionary());
|
||||
}
|
||||
new Thread("InitializeBinaryDictionary") {
|
||||
@Override
|
||||
public void run() {
|
||||
|
@ -105,6 +116,9 @@ public class Suggest {
|
|||
DictionaryFactory.createMainDictionaryFromManager(context, locale);
|
||||
addOrReplaceDictionary(mDictionaries, Dictionary.TYPE_MAIN, newMainDict);
|
||||
mMainDictionary = newMainDict;
|
||||
if (mListener != null) {
|
||||
mListener.onUpdateMainDictionaryAvailability(hasMainDictionary());
|
||||
}
|
||||
}
|
||||
}.start();
|
||||
}
|
||||
|
@ -219,7 +233,7 @@ public class Suggest {
|
|||
// the current settings. It may also be useful to know, when the setting is off, whether
|
||||
// the word *would* have been auto-corrected.
|
||||
if (!isCorrectionEnabled || !allowsToBeAutoCorrected || !wordComposer.isComposingWord()
|
||||
|| suggestionsSet.isEmpty()
|
||||
|| suggestionsSet.isEmpty() || wordComposer.hasDigits()
|
||||
|| wordComposer.isMostlyCaps() || wordComposer.isResumed()
|
||||
|| !hasMainDictionary()) {
|
||||
// If we don't have a main dictionary, we never want to auto-correct. The reason for
|
||||
|
|
|
@ -41,6 +41,7 @@ public class WordComposer {
|
|||
|
||||
// Cache these values for performance
|
||||
private int mCapsCount;
|
||||
private int mDigitsCount;
|
||||
private boolean mAutoCapitalized;
|
||||
private int mTrailingSingleQuotesCount;
|
||||
private int mCodePointSize;
|
||||
|
@ -65,6 +66,7 @@ public class WordComposer {
|
|||
mTypedWord = new StringBuilder(source.mTypedWord);
|
||||
mInputPointers.copy(source.mInputPointers);
|
||||
mCapsCount = source.mCapsCount;
|
||||
mDigitsCount = source.mDigitsCount;
|
||||
mIsFirstCharCapitalized = source.mIsFirstCharCapitalized;
|
||||
mAutoCapitalized = source.mAutoCapitalized;
|
||||
mTrailingSingleQuotesCount = source.mTrailingSingleQuotesCount;
|
||||
|
@ -80,6 +82,7 @@ public class WordComposer {
|
|||
mTypedWord.setLength(0);
|
||||
mAutoCorrection = null;
|
||||
mCapsCount = 0;
|
||||
mDigitsCount = 0;
|
||||
mIsFirstCharCapitalized = false;
|
||||
mTrailingSingleQuotesCount = 0;
|
||||
mIsResumed = false;
|
||||
|
@ -141,6 +144,7 @@ public class WordComposer {
|
|||
mIsFirstCharCapitalized = isFirstCharCapitalized(
|
||||
newIndex, primaryCode, mIsFirstCharCapitalized);
|
||||
if (Character.isUpperCase(primaryCode)) mCapsCount++;
|
||||
if (Character.isDigit(primaryCode)) mDigitsCount++;
|
||||
if (Keyboard.CODE_SINGLE_QUOTE == primaryCode) {
|
||||
++mTrailingSingleQuotesCount;
|
||||
} else {
|
||||
|
@ -213,6 +217,7 @@ public class WordComposer {
|
|||
mTypedWord.deleteCharAt(stringBuilderLength - 1);
|
||||
}
|
||||
if (Character.isUpperCase(lastChar)) mCapsCount--;
|
||||
if (Character.isDigit(lastChar)) mDigitsCount--;
|
||||
refreshSize();
|
||||
}
|
||||
// We may have deleted the last one.
|
||||
|
@ -267,6 +272,13 @@ public class WordComposer {
|
|||
return mCapsCount > 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if we have digits in the composing word.
|
||||
*/
|
||||
public boolean hasDigits() {
|
||||
return mDigitsCount > 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Saves the reason why the word is capitalized - whether it was automatic or
|
||||
* due to the user hitting shift in the middle of a sentence.
|
||||
|
@ -322,6 +334,7 @@ public class WordComposer {
|
|||
lastComposedWord.deactivate();
|
||||
}
|
||||
mCapsCount = 0;
|
||||
mDigitsCount = 0;
|
||||
mIsBatchMode = false;
|
||||
mTypedWord.setLength(0);
|
||||
mTrailingSingleQuotesCount = 0;
|
||||
|
|
|
@ -61,8 +61,8 @@ public class FusionDictionary implements Iterable<Word> {
|
|||
* This represents an "attribute", that is either a bigram or a shortcut.
|
||||
*/
|
||||
public static class WeightedString {
|
||||
final String mWord;
|
||||
int mFrequency;
|
||||
public final String mWord;
|
||||
public int mFrequency;
|
||||
public WeightedString(String word, int frequency) {
|
||||
mWord = word;
|
||||
mFrequency = frequency;
|
||||
|
|
|
@ -27,10 +27,10 @@ import java.util.Arrays;
|
|||
* This is chiefly used to iterate a dictionary.
|
||||
*/
|
||||
public class Word implements Comparable<Word> {
|
||||
final String mWord;
|
||||
final int mFrequency;
|
||||
final ArrayList<WeightedString> mShortcutTargets;
|
||||
final ArrayList<WeightedString> mBigrams;
|
||||
public final String mWord;
|
||||
public final int mFrequency;
|
||||
public final ArrayList<WeightedString> mShortcutTargets;
|
||||
public final ArrayList<WeightedString> mBigrams;
|
||||
|
||||
private int mHashCode = 0;
|
||||
|
||||
|
|
|
@ -18,10 +18,7 @@ package com.android.inputmethod.research;
|
|||
|
||||
import android.app.Activity;
|
||||
import android.os.Bundle;
|
||||
import android.text.Editable;
|
||||
import android.view.View;
|
||||
import android.widget.CheckBox;
|
||||
import android.widget.EditText;
|
||||
|
||||
import com.android.inputmethod.latin.R;
|
||||
|
||||
|
@ -31,6 +28,11 @@ public class FeedbackActivity extends Activity {
|
|||
super.onCreate(savedInstanceState);
|
||||
setContentView(R.layout.research_feedback_activity);
|
||||
final FeedbackLayout layout = (FeedbackLayout) findViewById(R.id.research_feedback_layout);
|
||||
final CheckBox checkbox = (CheckBox) findViewById(R.id.research_feedback_include_history);
|
||||
final CharSequence cs = checkbox.getText();
|
||||
final String actualString = String.format(cs.toString(),
|
||||
ResearchLogger.FEEDBACK_WORD_BUFFER_SIZE);
|
||||
checkbox.setText(actualString);
|
||||
layout.setActivity(this);
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,111 @@
|
|||
/*
|
||||
* Copyright (C) 2012 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.research;
|
||||
|
||||
import java.util.LinkedList;
|
||||
|
||||
/**
|
||||
* A buffer that holds a fixed number of LogUnits.
|
||||
*
|
||||
* LogUnits are added in and shifted out in temporal order. Only a subset of the LogUnits are
|
||||
* actual words; the other LogUnits do not count toward the word limit. Once the buffer reaches
|
||||
* capacity, adding another LogUnit that is a word evicts the oldest LogUnits out one at a time to
|
||||
* stay under the capacity limit.
|
||||
*/
|
||||
public class LogBuffer {
|
||||
protected final LinkedList<LogUnit> mLogUnits;
|
||||
/* package for test */ int mWordCapacity;
|
||||
// The number of members of mLogUnits that are actual words.
|
||||
protected int mNumActualWords;
|
||||
|
||||
/**
|
||||
* Create a new LogBuffer that can hold a fixed number of LogUnits that are words (and
|
||||
* unlimited number of non-word LogUnits), and that outputs its result to a researchLog.
|
||||
*
|
||||
* @param wordCapacity maximum number of words
|
||||
*/
|
||||
LogBuffer(final int wordCapacity) {
|
||||
if (wordCapacity <= 0) {
|
||||
throw new IllegalArgumentException("wordCapacity must be 1 or greater.");
|
||||
}
|
||||
mLogUnits = new LinkedList<LogUnit>();
|
||||
mWordCapacity = wordCapacity;
|
||||
mNumActualWords = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a new LogUnit to the front of the LIFO queue, evicting existing LogUnit's
|
||||
* (oldest first) if word capacity is reached.
|
||||
*/
|
||||
public void shiftIn(LogUnit newLogUnit) {
|
||||
if (newLogUnit.getWord() == null) {
|
||||
// This LogUnit isn't a word, so it doesn't count toward the word-limit.
|
||||
mLogUnits.add(newLogUnit);
|
||||
return;
|
||||
}
|
||||
if (mNumActualWords == mWordCapacity) {
|
||||
shiftOutThroughFirstWord();
|
||||
}
|
||||
mLogUnits.add(newLogUnit);
|
||||
mNumActualWords++; // Must be a word, or we wouldn't be here.
|
||||
}
|
||||
|
||||
private void shiftOutThroughFirstWord() {
|
||||
while (!mLogUnits.isEmpty()) {
|
||||
final LogUnit logUnit = mLogUnits.removeFirst();
|
||||
onShiftOut(logUnit);
|
||||
if (logUnit.hasWord()) {
|
||||
// Successfully shifted out a word-containing LogUnit and made space for the new
|
||||
// LogUnit.
|
||||
mNumActualWords--;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes all LogUnits from the buffer without calling onShiftOut().
|
||||
*/
|
||||
public void clear() {
|
||||
mLogUnits.clear();
|
||||
mNumActualWords = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when a LogUnit is removed from the LogBuffer as a result of a shiftIn. LogUnits are
|
||||
* removed in the order entered. This method is not called when shiftOut is called directly.
|
||||
*
|
||||
* Base class does nothing; subclasses may override.
|
||||
*/
|
||||
protected void onShiftOut(LogUnit logUnit) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called to deliberately remove the oldest LogUnit. Usually called when draining the
|
||||
* LogBuffer.
|
||||
*/
|
||||
public LogUnit shiftOut() {
|
||||
if (mLogUnits.isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
final LogUnit logUnit = mLogUnits.removeFirst();
|
||||
if (logUnit.hasWord()) {
|
||||
mNumActualWords--;
|
||||
}
|
||||
return logUnit;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,81 @@
|
|||
/*
|
||||
* Copyright (C) 2012 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.research;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
/**
|
||||
* A group of log statements related to each other.
|
||||
*
|
||||
* A LogUnit is collection of LogStatements, each of which is generated by at a particular point
|
||||
* in the code. (There is no LogStatement class; the data is stored across the instance variables
|
||||
* here.) A single LogUnit's statements can correspond to all the calls made while in the same
|
||||
* composing region, or all the calls between committing the last composing region, and the first
|
||||
* character of the next composing region.
|
||||
*
|
||||
* Individual statements in a log may be marked as potentially private. If so, then they are only
|
||||
* published to a ResearchLog if the ResearchLogger determines that publishing the entire LogUnit
|
||||
* will not violate the user's privacy. Checks for this may include whether other LogUnits have
|
||||
* been published recently, or whether the LogUnit contains numbers, etc.
|
||||
*/
|
||||
/* package */ class LogUnit {
|
||||
private final ArrayList<String[]> mKeysList = new ArrayList<String[]>();
|
||||
private final ArrayList<Object[]> mValuesList = new ArrayList<Object[]>();
|
||||
private final ArrayList<Boolean> mIsPotentiallyPrivate = new ArrayList<Boolean>();
|
||||
private String mWord;
|
||||
private boolean mContainsDigit;
|
||||
|
||||
public void addLogStatement(final String[] keys, final Object[] values,
|
||||
final Boolean isPotentiallyPrivate) {
|
||||
mKeysList.add(keys);
|
||||
mValuesList.add(values);
|
||||
mIsPotentiallyPrivate.add(isPotentiallyPrivate);
|
||||
}
|
||||
|
||||
public void publishTo(final ResearchLog researchLog, final boolean isIncludingPrivateData) {
|
||||
final int size = mKeysList.size();
|
||||
for (int i = 0; i < size; i++) {
|
||||
if (!mIsPotentiallyPrivate.get(i) || isIncludingPrivateData) {
|
||||
researchLog.outputEvent(mKeysList.get(i), mValuesList.get(i));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setWord(String word) {
|
||||
mWord = word;
|
||||
}
|
||||
|
||||
public String getWord() {
|
||||
return mWord;
|
||||
}
|
||||
|
||||
public boolean hasWord() {
|
||||
return mWord != null;
|
||||
}
|
||||
|
||||
public void setContainsDigit() {
|
||||
mContainsDigit = true;
|
||||
}
|
||||
|
||||
public boolean hasDigit() {
|
||||
return mContainsDigit;
|
||||
}
|
||||
|
||||
public boolean isEmpty() {
|
||||
return mKeysList.isEmpty();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,127 @@
|
|||
/*
|
||||
* Copyright (C) 2012 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.research;
|
||||
|
||||
import com.android.inputmethod.latin.Dictionary;
|
||||
import com.android.inputmethod.latin.Suggest;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
public class MainLogBuffer extends LogBuffer {
|
||||
// The size of the n-grams logged. E.g. N_GRAM_SIZE = 2 means to sample bigrams.
|
||||
private static final int N_GRAM_SIZE = 2;
|
||||
// The number of words between n-grams to omit from the log.
|
||||
private static final int DEFAULT_NUMBER_OF_WORDS_BETWEEN_SAMPLES = 18;
|
||||
|
||||
private final ResearchLog mResearchLog;
|
||||
private Suggest mSuggest;
|
||||
|
||||
// The minimum periodicity with which n-grams can be sampled. E.g. mWinWordPeriod is 10 if
|
||||
// every 10th bigram is sampled, i.e., words 1-8 are not, but the bigram at words 9 and 10, etc.
|
||||
// for 11-18, and the bigram at words 19 and 20. If an n-gram is not safe (e.g. it contains a
|
||||
// number in the middle or an out-of-vocabulary word), then sampling is delayed until a safe
|
||||
// n-gram does appear.
|
||||
/* package for test */ int mMinWordPeriod;
|
||||
|
||||
// Counter for words left to suppress before an n-gram can be sampled. Reset to mMinWordPeriod
|
||||
// after a sample is taken.
|
||||
/* package for test */ int mWordsUntilSafeToSample;
|
||||
|
||||
public MainLogBuffer(final ResearchLog researchLog) {
|
||||
super(N_GRAM_SIZE);
|
||||
mResearchLog = researchLog;
|
||||
mMinWordPeriod = DEFAULT_NUMBER_OF_WORDS_BETWEEN_SAMPLES + N_GRAM_SIZE;
|
||||
final Random random = new Random();
|
||||
mWordsUntilSafeToSample = random.nextInt(mMinWordPeriod);
|
||||
}
|
||||
|
||||
public void setSuggest(Suggest suggest) {
|
||||
mSuggest = suggest;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void shiftIn(final LogUnit newLogUnit) {
|
||||
super.shiftIn(newLogUnit);
|
||||
if (newLogUnit.hasWord()) {
|
||||
if (mWordsUntilSafeToSample > 0) {
|
||||
mWordsUntilSafeToSample--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void resetWordCounter() {
|
||||
mWordsUntilSafeToSample = mMinWordPeriod;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determines whether the content of the MainLogBuffer can be safely uploaded in its complete
|
||||
* form and still protect the user's privacy.
|
||||
*
|
||||
* The size of the MainLogBuffer is just enough to hold one n-gram, its corrections, and any
|
||||
* non-character data that is typed between words. The decision about privacy is made based on
|
||||
* the buffer's entire content. If it is decided that the privacy risks are too great to upload
|
||||
* the contents of this buffer, a censored version of the LogItems may still be uploaded. E.g.,
|
||||
* the screen orientation and other characteristics about the device can be uploaded without
|
||||
* revealing much about the user.
|
||||
*/
|
||||
public boolean isSafeToLog() {
|
||||
// Check that we are not sampling too frequently. Having sampled recently might disclose
|
||||
// too much of the user's intended meaning.
|
||||
if (mWordsUntilSafeToSample > 0) {
|
||||
return false;
|
||||
}
|
||||
if (mSuggest == null || !mSuggest.hasMainDictionary()) {
|
||||
// Main dictionary is unavailable. Since we cannot check it, we cannot tell if a word
|
||||
// is out-of-vocabulary or not. Therefore, we must judge the entire buffer contents to
|
||||
// potentially pose a privacy risk.
|
||||
return false;
|
||||
}
|
||||
// Reload the dictionary in case it has changed (e.g., because the user has changed
|
||||
// languages).
|
||||
final Dictionary dictionary = mSuggest.getMainDictionary();
|
||||
if (dictionary == null) {
|
||||
return false;
|
||||
}
|
||||
// Check each word in the buffer. If any word poses a privacy threat, we cannot upload the
|
||||
// complete buffer contents in detail.
|
||||
final int length = mLogUnits.size();
|
||||
for (int i = 0; i < length; i++) {
|
||||
final LogUnit logUnit = mLogUnits.get(i);
|
||||
final String word = logUnit.getWord();
|
||||
if (word == null) {
|
||||
// Digits outside words are a privacy threat.
|
||||
if (logUnit.hasDigit()) {
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
// Words not in the dictionary are a privacy threat.
|
||||
if (!(dictionary.isValidWord(word))) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
// All checks have passed; this buffer's content can be safely uploaded.
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onShiftOut(LogUnit logUnit) {
|
||||
if (mResearchLog != null) {
|
||||
mResearchLog.publish(logUnit, false /* isIncludingPrivateData */);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -26,7 +26,6 @@ import com.android.inputmethod.keyboard.Key;
|
|||
import com.android.inputmethod.latin.SuggestedWords;
|
||||
import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo;
|
||||
import com.android.inputmethod.latin.define.ProductionFlag;
|
||||
import com.android.inputmethod.research.ResearchLogger.LogUnit;
|
||||
|
||||
import java.io.BufferedWriter;
|
||||
import java.io.File;
|
||||
|
@ -37,6 +36,7 @@ import java.io.OutputStreamWriter;
|
|||
import java.util.Map;
|
||||
import java.util.concurrent.Callable;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.concurrent.RejectedExecutionException;
|
||||
import java.util.concurrent.ScheduledExecutorService;
|
||||
import java.util.concurrent.ScheduledFuture;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
@ -51,21 +51,22 @@ import java.util.concurrent.TimeUnit;
|
|||
*/
|
||||
public class ResearchLog {
|
||||
private static final String TAG = ResearchLog.class.getSimpleName();
|
||||
private static final JsonWriter NULL_JSON_WRITER = new JsonWriter(
|
||||
new OutputStreamWriter(new NullOutputStream()));
|
||||
private static final boolean DEBUG = false;
|
||||
private static final long FLUSH_DELAY_IN_MS = 1000 * 5;
|
||||
private static final int ABORT_TIMEOUT_IN_MS = 1000 * 4;
|
||||
|
||||
final ScheduledExecutorService mExecutor;
|
||||
/* package */ final ScheduledExecutorService mExecutor;
|
||||
/* package */ final File mFile;
|
||||
private JsonWriter mJsonWriter = NULL_JSON_WRITER;
|
||||
// true if at least one byte of data has been written out to the log file. This must be
|
||||
// remembered because JsonWriter requires that calls matching calls to beginObject and
|
||||
// endObject, as well as beginArray and endArray, and the file is opened lazily, only when
|
||||
// it is certain that data will be written. Alternatively, the matching call exceptions
|
||||
// could be caught, but this might suppress other errors.
|
||||
private boolean mHasWrittenData = false;
|
||||
|
||||
private int mLoggingState;
|
||||
private static final int LOGGING_STATE_UNSTARTED = 0;
|
||||
private static final int LOGGING_STATE_READY = 1; // don't create file until necessary
|
||||
private static final int LOGGING_STATE_RUNNING = 2;
|
||||
private static final int LOGGING_STATE_STOPPING = 3;
|
||||
private static final int LOGGING_STATE_STOPPED = 4;
|
||||
private static final long FLUSH_DELAY_IN_MS = 1000 * 5;
|
||||
|
||||
private static final JsonWriter NULL_JSON_WRITER = new JsonWriter(
|
||||
new OutputStreamWriter(new NullOutputStream()));
|
||||
private static class NullOutputStream extends OutputStream {
|
||||
/** {@inheritDoc} */
|
||||
@Override
|
||||
|
@ -84,128 +85,81 @@ public class ResearchLog {
|
|||
}
|
||||
}
|
||||
|
||||
public ResearchLog(File outputFile) {
|
||||
mExecutor = Executors.newSingleThreadScheduledExecutor();
|
||||
public ResearchLog(final File outputFile) {
|
||||
if (outputFile == null) {
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
mExecutor = Executors.newSingleThreadScheduledExecutor();
|
||||
mFile = outputFile;
|
||||
mLoggingState = LOGGING_STATE_UNSTARTED;
|
||||
}
|
||||
|
||||
public synchronized void start() throws IOException {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
mLoggingState = LOGGING_STATE_READY;
|
||||
break;
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
case LOGGING_STATE_STOPPING:
|
||||
case LOGGING_STATE_STOPPED:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
public synchronized void stop() {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
mLoggingState = LOGGING_STATE_STOPPED;
|
||||
break;
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
try {
|
||||
mJsonWriter.endArray();
|
||||
mJsonWriter.flush();
|
||||
mJsonWriter.close();
|
||||
} finally {
|
||||
boolean success = mFile.setWritable(false, false);
|
||||
mLoggingState = LOGGING_STATE_STOPPED;
|
||||
}
|
||||
return null;
|
||||
public synchronized void close() {
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
try {
|
||||
if (mHasWrittenData) {
|
||||
mJsonWriter.endArray();
|
||||
mJsonWriter.flush();
|
||||
mJsonWriter.close();
|
||||
mHasWrittenData = false;
|
||||
}
|
||||
});
|
||||
removeAnyScheduledFlush();
|
||||
mExecutor.shutdown();
|
||||
mLoggingState = LOGGING_STATE_STOPPING;
|
||||
break;
|
||||
case LOGGING_STATE_STOPPING:
|
||||
case LOGGING_STATE_STOPPED:
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isAlive() {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public void waitUntilStopped(final int timeoutInMs) throws InterruptedException {
|
||||
} catch (Exception e) {
|
||||
Log.d(TAG, "error when closing ResearchLog:");
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
if (mFile.exists()) {
|
||||
mFile.setWritable(false, false);
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
});
|
||||
removeAnyScheduledFlush();
|
||||
mExecutor.shutdown();
|
||||
mExecutor.awaitTermination(timeoutInMs, TimeUnit.MILLISECONDS);
|
||||
}
|
||||
|
||||
private boolean mIsAbortSuccessful;
|
||||
|
||||
public synchronized void abort() {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
mLoggingState = LOGGING_STATE_STOPPED;
|
||||
isAbortSuccessful = true;
|
||||
break;
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
try {
|
||||
mJsonWriter.endArray();
|
||||
mJsonWriter.close();
|
||||
} finally {
|
||||
isAbortSuccessful = mFile.delete();
|
||||
}
|
||||
return null;
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
try {
|
||||
if (mHasWrittenData) {
|
||||
mJsonWriter.endArray();
|
||||
mJsonWriter.close();
|
||||
mHasWrittenData = false;
|
||||
}
|
||||
});
|
||||
removeAnyScheduledFlush();
|
||||
mExecutor.shutdown();
|
||||
mLoggingState = LOGGING_STATE_STOPPING;
|
||||
break;
|
||||
case LOGGING_STATE_STOPPING:
|
||||
case LOGGING_STATE_STOPPED:
|
||||
}
|
||||
} finally {
|
||||
mIsAbortSuccessful = mFile.delete();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
});
|
||||
removeAnyScheduledFlush();
|
||||
mExecutor.shutdown();
|
||||
}
|
||||
|
||||
private boolean isAbortSuccessful;
|
||||
public boolean isAbortSuccessful() {
|
||||
return isAbortSuccessful;
|
||||
public boolean blockingAbort() throws InterruptedException {
|
||||
abort();
|
||||
mExecutor.awaitTermination(ABORT_TIMEOUT_IN_MS, TimeUnit.MILLISECONDS);
|
||||
return mIsAbortSuccessful;
|
||||
}
|
||||
|
||||
public void awaitTermination(int delay, TimeUnit timeUnit) throws InterruptedException {
|
||||
mExecutor.awaitTermination(delay, timeUnit);
|
||||
}
|
||||
|
||||
/* package */ synchronized void flush() {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
break;
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
removeAnyScheduledFlush();
|
||||
mExecutor.submit(mFlushCallable);
|
||||
break;
|
||||
case LOGGING_STATE_STOPPING:
|
||||
case LOGGING_STATE_STOPPED:
|
||||
}
|
||||
removeAnyScheduledFlush();
|
||||
mExecutor.submit(mFlushCallable);
|
||||
}
|
||||
|
||||
private Callable<Object> mFlushCallable = new Callable<Object>() {
|
||||
private final Callable<Object> mFlushCallable = new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
if (mLoggingState == LOGGING_STATE_RUNNING) {
|
||||
mJsonWriter.flush();
|
||||
}
|
||||
mJsonWriter.flush();
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
@ -224,56 +178,40 @@ public class ResearchLog {
|
|||
mFlushFuture = mExecutor.schedule(mFlushCallable, FLUSH_DELAY_IN_MS, TimeUnit.MILLISECONDS);
|
||||
}
|
||||
|
||||
public synchronized void publishPublicEvents(final LogUnit logUnit) {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
break;
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
logUnit.publishPublicEventsTo(ResearchLog.this);
|
||||
scheduleFlush();
|
||||
return null;
|
||||
}
|
||||
});
|
||||
break;
|
||||
case LOGGING_STATE_STOPPING:
|
||||
case LOGGING_STATE_STOPPED:
|
||||
}
|
||||
}
|
||||
|
||||
public synchronized void publishAllEvents(final LogUnit logUnit) {
|
||||
switch (mLoggingState) {
|
||||
case LOGGING_STATE_UNSTARTED:
|
||||
break;
|
||||
case LOGGING_STATE_READY:
|
||||
case LOGGING_STATE_RUNNING:
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
logUnit.publishAllEventsTo(ResearchLog.this);
|
||||
scheduleFlush();
|
||||
return null;
|
||||
}
|
||||
});
|
||||
break;
|
||||
case LOGGING_STATE_STOPPING:
|
||||
case LOGGING_STATE_STOPPED:
|
||||
public synchronized void publish(final LogUnit logUnit, final boolean isIncludingPrivateData) {
|
||||
try {
|
||||
mExecutor.submit(new Callable<Object>() {
|
||||
@Override
|
||||
public Object call() throws Exception {
|
||||
logUnit.publishTo(ResearchLog.this, isIncludingPrivateData);
|
||||
scheduleFlush();
|
||||
return null;
|
||||
}
|
||||
});
|
||||
} catch (RejectedExecutionException e) {
|
||||
// TODO: Add code to record loss of data, and report.
|
||||
}
|
||||
}
|
||||
|
||||
private static final String CURRENT_TIME_KEY = "_ct";
|
||||
private static final String UPTIME_KEY = "_ut";
|
||||
private static final String EVENT_TYPE_KEY = "_ty";
|
||||
|
||||
void outputEvent(final String[] keys, final Object[] values) {
|
||||
// not thread safe.
|
||||
// Not thread safe.
|
||||
if (keys.length == 0) {
|
||||
return;
|
||||
}
|
||||
if (DEBUG) {
|
||||
if (keys.length != values.length + 1) {
|
||||
Log.d(TAG, "Key and Value list sizes do not match. " + keys[0]);
|
||||
}
|
||||
}
|
||||
try {
|
||||
if (mJsonWriter == NULL_JSON_WRITER) {
|
||||
mJsonWriter = new JsonWriter(new BufferedWriter(new FileWriter(mFile)));
|
||||
mJsonWriter.setLenient(true);
|
||||
mJsonWriter.beginArray();
|
||||
mHasWrittenData = true;
|
||||
}
|
||||
mJsonWriter.beginObject();
|
||||
mJsonWriter.name(CURRENT_TIME_KEY).value(System.currentTimeMillis());
|
||||
|
@ -283,8 +221,8 @@ public class ResearchLog {
|
|||
for (int i = 0; i < length; i++) {
|
||||
mJsonWriter.name(keys[i + 1]);
|
||||
Object value = values[i];
|
||||
if (value instanceof String) {
|
||||
mJsonWriter.value((String) value);
|
||||
if (value instanceof CharSequence) {
|
||||
mJsonWriter.value(value.toString());
|
||||
} else if (value instanceof Number) {
|
||||
mJsonWriter.value((Number) value);
|
||||
} else if (value instanceof Boolean) {
|
||||
|
@ -331,14 +269,11 @@ public class ResearchLog {
|
|||
SuggestedWords words = (SuggestedWords) value;
|
||||
mJsonWriter.beginObject();
|
||||
mJsonWriter.name("typedWordValid").value(words.mTypedWordValid);
|
||||
mJsonWriter.name("willAutoCorrect")
|
||||
.value(words.mWillAutoCorrect);
|
||||
mJsonWriter.name("willAutoCorrect").value(words.mWillAutoCorrect);
|
||||
mJsonWriter.name("isPunctuationSuggestions")
|
||||
.value(words.mIsPunctuationSuggestions);
|
||||
mJsonWriter.name("isObsoleteSuggestions")
|
||||
.value(words.mIsObsoleteSuggestions);
|
||||
mJsonWriter.name("isPrediction")
|
||||
.value(words.mIsPrediction);
|
||||
.value(words.mIsPunctuationSuggestions);
|
||||
mJsonWriter.name("isObsoleteSuggestions").value(words.mIsObsoleteSuggestions);
|
||||
mJsonWriter.name("isPrediction").value(words.mIsPrediction);
|
||||
mJsonWriter.name("words");
|
||||
mJsonWriter.beginArray();
|
||||
final int size = words.size();
|
||||
|
@ -363,8 +298,8 @@ public class ResearchLog {
|
|||
try {
|
||||
mJsonWriter.close();
|
||||
} catch (IllegalStateException e1) {
|
||||
// assume that this is just the json not being terminated properly.
|
||||
// ignore
|
||||
// Assume that this is just the json not being terminated properly.
|
||||
// Ignore
|
||||
} catch (IOException e1) {
|
||||
e1.printStackTrace();
|
||||
} finally {
|
||||
|
|
|
@ -27,7 +27,6 @@ import android.os.BatteryManager;
|
|||
import android.util.Log;
|
||||
|
||||
import com.android.inputmethod.latin.R;
|
||||
import com.android.inputmethod.latin.R.string;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.File;
|
||||
|
@ -48,6 +47,7 @@ public final class ResearchLogUploader {
|
|||
private static final String TAG = ResearchLogUploader.class.getSimpleName();
|
||||
private static final int UPLOAD_INTERVAL_IN_MS = 1000 * 60 * 15; // every 15 min
|
||||
private static final int BUF_SIZE = 1024 * 8;
|
||||
protected static final int TIMEOUT_IN_MS = 1000 * 4;
|
||||
|
||||
private final boolean mCanUpload;
|
||||
private final Context mContext;
|
||||
|
@ -55,8 +55,6 @@ public final class ResearchLogUploader {
|
|||
private final URL mUrl;
|
||||
private final ScheduledExecutorService mExecutor;
|
||||
|
||||
private Runnable doUploadRunnable = new UploadRunnable(null, false);
|
||||
|
||||
public ResearchLogUploader(final Context context, final File filesDir) {
|
||||
mContext = context;
|
||||
mFilesDir = filesDir;
|
||||
|
@ -93,11 +91,15 @@ public final class ResearchLogUploader {
|
|||
|
||||
public void start() {
|
||||
if (mCanUpload) {
|
||||
Log.d(TAG, "scheduling regular uploading");
|
||||
mExecutor.scheduleWithFixedDelay(doUploadRunnable, UPLOAD_INTERVAL_IN_MS,
|
||||
UPLOAD_INTERVAL_IN_MS, TimeUnit.MILLISECONDS);
|
||||
} else {
|
||||
Log.d(TAG, "no permission to upload");
|
||||
mExecutor.scheduleWithFixedDelay(new UploadRunnable(null /* logToWaitFor */,
|
||||
null /* callback */, false /* forceUpload */),
|
||||
UPLOAD_INTERVAL_IN_MS, UPLOAD_INTERVAL_IN_MS, TimeUnit.MILLISECONDS);
|
||||
}
|
||||
}
|
||||
|
||||
public void uploadAfterCompletion(final ResearchLog researchLog, final Callback callback) {
|
||||
if (mCanUpload) {
|
||||
mExecutor.submit(new UploadRunnable(researchLog, callback, true /* forceUpload */));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -106,7 +108,8 @@ public final class ResearchLogUploader {
|
|||
// another upload happening right now, as it may have missed the latest changes.
|
||||
// TODO: Reschedule regular upload tests starting from now.
|
||||
if (mCanUpload) {
|
||||
mExecutor.submit(new UploadRunnable(callback, true));
|
||||
mExecutor.submit(new UploadRunnable(null /* logToWaitFor */, callback,
|
||||
true /* forceUpload */));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -130,19 +133,33 @@ public final class ResearchLogUploader {
|
|||
}
|
||||
|
||||
class UploadRunnable implements Runnable {
|
||||
private final ResearchLog mLogToWaitFor;
|
||||
private final Callback mCallback;
|
||||
private final boolean mForceUpload;
|
||||
|
||||
public UploadRunnable(final Callback callback, final boolean forceUpload) {
|
||||
public UploadRunnable(final ResearchLog logToWaitFor, final Callback callback,
|
||||
final boolean forceUpload) {
|
||||
mLogToWaitFor = logToWaitFor;
|
||||
mCallback = callback;
|
||||
mForceUpload = forceUpload;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
if (mLogToWaitFor != null) {
|
||||
waitFor(mLogToWaitFor);
|
||||
}
|
||||
doUpload();
|
||||
}
|
||||
|
||||
private void waitFor(final ResearchLog researchLog) {
|
||||
try {
|
||||
researchLog.awaitTermination(TIMEOUT_IN_MS, TimeUnit.MILLISECONDS);
|
||||
} catch (InterruptedException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
private void doUpload() {
|
||||
if (!mForceUpload && (!isExternallyPowered() || !hasWifiConnection())) {
|
||||
return;
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue