diff options
Diffstat (limited to 'java')
30 files changed, 726 insertions, 272 deletions
diff --git a/java/res/anim/alt_code_key_while_typing_fadein.xml b/java/res/anim/alt_code_key_while_typing_fadein.xml new file mode 100644 index 000000000..3f5fd5d48 --- /dev/null +++ b/java/res/anim/alt_code_key_while_typing_fadein.xml @@ -0,0 +1,26 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** +** Copyright 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. +*/ +--> + +<animator + xmlns:android="http://schemas.android.com/apk/res/android" + android:valueType="intType" + android:duration="100" + android:valueFrom="128" + android:valueTo="255" /> diff --git a/java/res/anim/alt_code_key_while_typing_fadeout.xml b/java/res/anim/alt_code_key_while_typing_fadeout.xml new file mode 100644 index 000000000..ed4a6f298 --- /dev/null +++ b/java/res/anim/alt_code_key_while_typing_fadeout.xml @@ -0,0 +1,26 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** +** Copyright 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. +*/ +--> + +<animator + xmlns:android="http://schemas.android.com/apk/res/android" + android:valueType="intType" + android:duration="70" + android:valueFrom="255" + android:valueTo="128" /> diff --git a/java/res/anim/language_on_spacebar_fadeout.xml b/java/res/anim/language_on_spacebar_fadeout.xml new file mode 100644 index 000000000..f66e1627b --- /dev/null +++ b/java/res/anim/language_on_spacebar_fadeout.xml @@ -0,0 +1,27 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** +** Copyright 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. +*/ +--> + +<animator + xmlns:android="http://schemas.android.com/apk/res/android" + android:valueType="intType" + android:startOffset="1200" + android:duration="200" + android:valueFrom="255" + android:valueTo="128" /> diff --git a/java/res/values-fa/donottranslate-more-keys.xml b/java/res/values-fa/donottranslate-more-keys.xml new file mode 100644 index 000000000..3e13c795a --- /dev/null +++ b/java/res/values-fa/donottranslate-more-keys.xml @@ -0,0 +1,160 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** +** Copyright 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. +*/ +--> +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- U+061F: "؟" ARABIC QUESTION MARK + U+060C: "،" ARABIC COMMA + U+061B: "؛" ARABIC SEMICOLON --> + <!-- U+0650: "ِ" ARABIC KASRA + U+064E: "َ" ARABIC FATHA + U+064D: "ٍ" ARABIC KASRATAN + U+064B: "ً" ARABIC FATHATAN + U+0656: "ٖ" ARABIC SUBSCRIPT ALEF + U+0670: "ٰ" ARABIC LETTER SUPERSCRIPT ALEF + U+0655: "ٕ" ARABIC HAMZA BELOW + U+0654: "ٔ" ARABIC HAMZA ABOVE --> + <!-- U+064F: "ُ" ARABIC DAMMA + U+064C: "ٌ" ARABIC DAMMATAN + U+0651: "ّ" ARABIC SHADDA + U+0652: "ْ" ARABIC SUKUN + U+0653: "ٓ" ARABIC MADDAH ABOVE + U+0640: "ـ" ARABIC TATWEEL --> + <!-- In order to make Tatweel easily distinguishable from other punctuations, we use consecutive Tatweels only for its displayed label. --> + <string name="more_keys_for_punctuation">"!fixedColumnOrder!8,\",\',-,:,!,؟,،,؛,ِ,َ,ٍ,ً,ٖ,ٰ,ٕ,ٔ,ُ,ٌ,ّ,ْ,ٓ,ـــ|ـ,/"</string> + <string name="keyhintlabel_for_punctuation">ً</string> + <!-- U+0661: "١" ARABIC-INDIC DIGIT ONE --> + <string name="keylabel_for_symbols_1">١</string> + <!-- U+0662: "٢" ARABIC-INDIC DIGIT TWO --> + <string name="keylabel_for_symbols_2">٢</string> + <!-- U+0663: "٣" ARABIC-INDIC DIGIT THREE --> + <string name="keylabel_for_symbols_3">٣</string> + <!-- U+0664: "٤" ARABIC-INDIC DIGIT FOUR --> + <string name="keylabel_for_symbols_4">٤</string> + <!-- U+0665: "٥" ARABIC-INDIC DIGIT FIVE --> + <string name="keylabel_for_symbols_5">٥</string> + <!-- U+0666: "٦" ARABIC-INDIC DIGIT SIX --> + <string name="keylabel_for_symbols_6">٦</string> + <!-- U+0667: "٧" ARABIC-INDIC DIGIT SEVEN --> + <string name="keylabel_for_symbols_7">٧</string> + <!-- U+0668: "٨" ARABIC-INDIC DIGIT EIGHT --> + <string name="keylabel_for_symbols_8">٨</string> + <!-- U+0669: "٩" ARABIC-INDIC DIGIT NINE --> + <string name="keylabel_for_symbols_9">٩</string> + <!-- U+0660: "٠" ARABIC-INDIC DIGIT ZERO --> + <string name="keylabel_for_symbols_0">٠</string> + <string name="additional_more_keys_for_symbols_1">1</string> + <string name="additional_more_keys_for_symbols_2">2</string> + <string name="additional_more_keys_for_symbols_3">3</string> + <string name="additional_more_keys_for_symbols_4">4</string> + <string name="additional_more_keys_for_symbols_5">5</string> + <string name="additional_more_keys_for_symbols_6">6</string> + <string name="additional_more_keys_for_symbols_7">7</string> + <string name="additional_more_keys_for_symbols_8">8</string> + <string name="additional_more_keys_for_symbols_9">9</string> + <!-- U+066B: "٫" ARABIC DECIMAL SEPARATOR + U+066C: "٬" ARABIC THOUSANDS SEPARATOR --> + <string name="additional_more_keys_for_symbols_0">0,٫,٬</string> + <!-- U+060C: "،" ARABIC COMMA --> + <string name="keylabel_for_comma">،</string> + <string name="more_keys_for_comma">"\\,"</string> + <string name="keylabel_for_symbols_question">؟</string> + <string name="keylabel_for_symbols_semicolon">؛</string> + <!-- U+066A: "٪" ARABIC PERCENT SIGN --> + <string name="keylabel_for_symbols_percent">٪</string> + <string name="more_keys_for_symbols_question">\?</string> + <string name="more_keys_for_symbols_semicolon">;</string> + <!-- U+2030: "‰" PER MILLE SIGN --> + <string name="more_keys_for_symbols_percent">%,‰</string> + <!-- U+060C: "،" ARABIC COMMA + U+061B: "؛" ARABIC SEMICOLON + U+061F: "؟" ARABIC QUESTION MARK --> + <string name="keylabel_for_apostrophe">،</string> + <string name="keylabel_for_dash">"."</string> + <string name="keyhintlabel_for_apostrophe">؟</string> + <string name="keyhintlabel_for_dash">ً</string> + <string name="more_keys_for_apostrophe">"؟,؛,!,:,-,/,\',\""</string> + <!-- U+0651: "ّ" ARABIC SHADDA + U+0652: "ْ" ARABIC SUKUN + U+064C: "ٌ" ARABIC DAMMATAN + U+0653: "ٓ" ARABIC MADDAH ABOVE + U+064F: "ُ" ARABIC DAMMA --> + <!-- U+0650: "ِ" ARABIC KASRA + U+064E: "َ" ARABIC FATHA + U+064B: "ً" ARABIC FATHATAN + U+0640: "ـ" ARABIC TATWEEL + U+064D: "ٍ" ARABIC KASRATAN --> + <!-- U+0670: "ٰ" ARABIC LETTER SUPERSCRIPT ALEF + U+0656: "ٖ" ARABIC SUBSCRIPT ALEF + U+0654: "ٔ" ARABIC HAMZA ABOVE + U+0655: "ٕ" ARABIC HAMZA BELOW --> + <!-- In order to make Tatweel easily distinguishable from other punctuations, we use consecutive Tatweels only for its displayed label. --> + <string name="more_keys_for_dash">"ّ,ْ,ٌ,ٓ,ُ,ِ,َ,ً,ـــ|ـ,ٍ,ٔ,ٖ,ٕ,ٰ"</string> + <!-- U+266A: "♪" EIGHTH NOTE --> + <string name="more_keys_for_bullet">♪</string> + <!-- U+2605: "★" BLACK STAR + U+066D: "٭" ARABIC FIVE POINTED STAR --> + <string name="more_keys_for_star">★,٭</string> + <!-- The all letters need to be mirrored are found at + http://www.unicode.org/Public/6.1.0/ucd/BidiMirroring.txt --> + <!-- U+0029: ")" RIGHT PARENTHESIS --> + <integer name="keycode_for_left_parenthesis">0x0029</integer> + <!-- U+0028: "(" LEFT PARENTHESIS --> + <integer name="keycode_for_right_parenthesis">0x0028</integer> + <!-- U+FD3E: "﴾" ORNATE LEFT PARENTHESIS + U+FD3F: "﴿" ORNATE RIGHT PARENTHESIS --> + <!-- TODO: DroidSansArabic lacks the glyph of U+FD3E ORNATE LEFT PARENTHESIS --> + <!-- TODO: DroidSansArabic lacks the glyph of U+FD3F ORNATE RIGHT PARENTHESIS --> + <string name="more_keys_for_left_parenthesis">!fixedColumnOrder!4,﴾|﴿,<|>,{|},[|]</string> + <string name="more_keys_for_right_parenthesis">!fixedColumnOrder!4,﴿|﴾,>|<,}|{,]|[</string> + <!-- U+003E: ">" GREATER-THAN SIGN --> + <integer name="keycode_for_less_than">0x003E</integer> + <!-- U+003C: "<" LESS-THAN SIGN --> + <integer name="keycode_for_greater_than">0x003C</integer> + <!-- U+2264: "≤" LESS-THAN OR EQUAL TO + U+2265: "≥" GREATER-THAN EQUAL TO + U+00AB: "«" LEFT-POINTING DOUBLE ANGLE QUOTATION MARK + U+00BB: "»" RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK + U+2039: "‹" SINGLE LEFT-POINTING ANGLE QUOTATION MARK + U+203A: "›" SINGLE RIGHT-POINTING ANGLE QUOTATION MARK + The following characters don't need BIDI mirroring. + U+2018: "‘" LEFT SINGLE QUOTATION MARK + U+2019: "’" RIGHT SINGLE QUOTATION MARK + U+201A: "‚" SINGLE LOW-9 QUOTATION MARK + U+201B: "‛" SINGLE HIGH-REVERSED-9 QUOTATION MARK + U+201C: "“" LEFT DOUBLE QUOTATION MARK + U+201D: "”" RIGHT DOUBLE QUOTATION MARK + U+201E: "„" DOUBLE LOW-9 QUOTATION MARK + U+201F: "‟" DOUBLE HIGH-REVERSED-9 QUOTATION MARK --> + <string name="more_keys_for_less_than">!fixedColumnOrder!3,‹|›,≤|≥,«|»</string> + <string name="more_keys_for_greater_than">!fixedColumnOrder!3,›|‹,≥|≤,»|«</string> + <!-- U+005D: "]" RIGHT SQUARE BRACKET --> + <integer name="keycode_for_left_square_bracket">0x005D</integer> + <!-- U+005B: "[" LEFT SQUARE BRACKET --> + <integer name="keycode_for_right_square_bracket">0x005B</integer> + <!-- U+007D: "}" RIGHT CURLY BRACKET --> + <integer name="keycode_for_left_curly_bracket">0x007D</integer> + <!-- U+007B: "{" LEFT CURLY BRACKET --> + <integer name="keycode_for_right_curly_bracket">0x007B</integer> + <!-- TODO: Neither DroidSans nor Roboto have the glyph for U+201F DOUBLE HIGH-REVERSED-9 QUOTATION MARK --> + <!-- <string name="more_keys_for_double_quote">“,”,„,‟,«|»,»|«</string> --> + <string name="more_keys_for_double_quote">!fixedColumnOrder!4,“,”,«|»,»|«</string> + <!-- TODO: Neither DroidSans nor Roboto have the glyph for U+201F DOUBLE HIGH-REVERSED-9 QUOTATION MARK --> + <!-- <string name="more_keys_for_tablet_double_quote">!fixedColumnOrder!6,“,”,„,‟,«|»,»|«;,‘,’,‚,‛</string> --> + <string name="more_keys_for_tablet_double_quote">!fixedColumnOrder!4,“,”,«|»,»|«,‘,’,‚,‛</string> +</resources> diff --git a/java/res/values-fa/donottranslate.xml b/java/res/values-fa/donottranslate.xml new file mode 100644 index 000000000..57de2538b --- /dev/null +++ b/java/res/values-fa/donottranslate.xml @@ -0,0 +1,25 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** +** Copyright 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. +*/ +--> +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- The all letters need to be mirrored are found at + http://www.unicode.org/Public/6.1.0/ucd/BidiMirroring.txt --> + <!-- Symbols that are suggested between words --> + <string name="suggested_punctuations">!,?,\\,,:,;,\",(|),)|(,\',-,/,@,_</string> +</resources> diff --git a/java/res/values-in/strings.xml b/java/res/values-in/strings.xml index 1f03a05a7..f10d613f2 100644 --- a/java/res/values-in/strings.xml +++ b/java/res/values-in/strings.xml @@ -45,7 +45,7 @@ <skip /> <string name="key_preview_popup_dismiss_delay" msgid="6213164897443068248">"Tundaan singkir munculan kunci"</string> <string name="key_preview_popup_dismiss_no_delay" msgid="2096123151571458064">"Tanpa penundaan"</string> - <string name="key_preview_popup_dismiss_default_delay" msgid="2166964333903906734">"Bawaan"</string> + <string name="key_preview_popup_dismiss_default_delay" msgid="2166964333903906734">"Default"</string> <string name="use_contacts_dict" msgid="4435317977804180815">"Sarankan nama Kenalan"</string> <string name="use_contacts_dict_summary" msgid="6599983334507879959">"Menggunakan nama dari Kenalan untuk saran dan koreksi"</string> <string name="enable_span_insert" msgid="7204653105667167620">"Aktifkan koreksi ulang"</string> diff --git a/java/res/values/attrs.xml b/java/res/values/attrs.xml index 8df51d648..e619ad0a8 100644 --- a/java/res/values/attrs.xml +++ b/java/res/values/attrs.xml @@ -132,14 +132,11 @@ <attr name="spacebarTextRatio" format="fraction" /> <attr name="spacebarTextColor" format="color" /> <attr name="spacebarTextShadowColor" format="color" /> - <!-- Animation parameters for spacebar language label. --> - <attr name="durationOfFadeoutLanguageOnSpacebar" format="integer|enum"> - <!-- This should be aligned with LatinKeyboardView.LANGUAGE_ON_SPACEBAR_* --> - <enum name="neverDisplay" value="0" /> - <enum name="alwaysDisplay" value="-1" /> - </attr> - <attr name="delayBeforeFadeoutLangageOnSpacebar" format="integer" /> - <attr name="finalAlphaOfLanguageOnSpacebar" format="integer" /> + <!-- Fadeout animator for spacebar language label. --> + <attr name="languageOnSpacebarFadeoutAnimator" format="reference" /> + <!-- Fadeout and fadein animator for altCodeWhileTyping keys. --> + <attr name="altCodeKeyWhileTypingFadeoutAnimator" format="reference" /> + <attr name="altCodeKeyWhileTypingFadeinAnimator" format="reference" /> <!-- Key detection hysteresis distance. --> <attr name="keyHysteresisDistance" format="dimension" /> <!-- Touch noise threshold time in millisecond --> @@ -159,7 +156,7 @@ <!-- Long press timeout of space key in millisecond. --> <attr name="longPressSpaceKeyTimeout" format="integer" /> <!-- Ignore special key timeout while typing in millisecond. --> - <attr name="ignoreSpecialKeyTimeout" format="integer" /> + <attr name="ignoreAltCodeKeyTimeout" format="integer" /> <!-- More keys keyboard will shown at touched point. --> <attr name="showMoreKeysKeyboardAtTouchedPoint" format="boolean" /> </declare-styleable> diff --git a/java/res/values/config.xml b/java/res/values/config.xml index a02b84ff0..c51800fb0 100644 --- a/java/res/values/config.xml +++ b/java/res/values/config.xml @@ -65,7 +65,7 @@ <!-- Long pressing space will invoke IME switcher if > 0, never invoke IME switcher if == 0 --> <integer name="config_long_press_space_key_timeout"> @integer/config_long_press_key_timeout</integer> - <integer name="config_ignore_special_key_timeout">700</integer> + <integer name="config_ignore_alt_code_key_timeout">700</integer> <!-- Showing more keys keyboard, just above the touched point if true, aligned to the key if false --> <bool name="config_show_more_keys_keyboard_at_touched_point">false</bool> diff --git a/java/res/values/styles.xml b/java/res/values/styles.xml index eaca642b6..7d8b7ddf2 100644 --- a/java/res/values/styles.xml +++ b/java/res/values/styles.xml @@ -76,11 +76,11 @@ <item name="longPressKeyTimeout">@integer/config_long_press_key_timeout</item> <item name="longPressShiftKeyTimeout">@integer/config_long_press_shift_key_timeout</item> <item name="longPressSpaceKeyTimeout">@integer/config_long_press_space_key_timeout</item> - <item name="ignoreSpecialKeyTimeout">@integer/config_ignore_special_key_timeout</item> + <item name="ignoreAltCodeKeyTimeout">@integer/config_ignore_alt_code_key_timeout</item> <item name="showMoreKeysKeyboardAtTouchedPoint">@bool/config_show_more_keys_keyboard_at_touched_point</item> - <item name="durationOfFadeoutLanguageOnSpacebar">200</item> - <item name="delayBeforeFadeoutLangageOnSpacebar">1200</item> - <item name="finalAlphaOfLanguageOnSpacebar">128</item> + <item name="languageOnSpacebarFadeoutAnimator">@anim/language_on_spacebar_fadeout</item> + <item name="altCodeKeyWhileTypingFadeoutAnimator">@anim/alt_code_key_while_typing_fadeout</item> + <item name="altCodeKeyWhileTypingFadeinAnimator">@anim/alt_code_key_while_typing_fadein</item> </style> <style name="LatinKeyboardView" diff --git a/java/res/xml-fa/keyboard_set.xml b/java/res/xml-fa/keyboard_set.xml new file mode 100644 index 000000000..9bd105093 --- /dev/null +++ b/java/res/xml-fa/keyboard_set.xml @@ -0,0 +1,42 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** +** Copyright 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. +*/ +--> + +<KeyboardSet + xmlns:latin="http://schemas.android.com/apk/res/com.android.inputmethod.latin" + latin:keyboardLocale="fa" > + <Element + latin:elementName="alphabet" + latin:elementKeyboard="@xml/kbd_arabic" /> + <Element + latin:elementName="symbols" + latin:elementKeyboard="@xml/kbd_symbols" /> + <Element + latin:elementName="symbolsShifted" + latin:elementKeyboard="@xml/kbd_symbols_shift" /> + <Element + latin:elementName="phone" + latin:elementKeyboard="@xml/kbd_phone" /> + <Element + latin:elementName="phoneSymbols" + latin:elementKeyboard="@xml/kbd_phone_symbols" /> + <Element + latin:elementName="number" + latin:elementKeyboard="@xml/kbd_number" /> +</KeyboardSet> diff --git a/java/res/xml-sw600dp/key_styles_common.xml b/java/res/xml-sw600dp/key_styles_common.xml index 2fa8b3812..a263acd9b 100644 --- a/java/res/xml-sw600dp/key_styles_common.xml +++ b/java/res/xml-sw600dp/key_styles_common.xml @@ -79,9 +79,10 @@ latin:code="@integer/key_space" latin:keyActionFlags="noKeyPreview" /> <key-style - latin:styleName="nonSpecialBackgroundSpaceKeyStyle" - latin:code="@integer/key_space" - latin:keyActionFlags="noKeyPreview" /> + latin:styleName="zwnjKeyStyle" + latin:keyLabel="‌" + latin:moreKeys="‍" + latin:keyLabelFlags="hasPopupHint" /> <key-style latin:styleName="smileyKeyStyle" latin:keyLabel=":-)" diff --git a/java/res/xml-sw600dp/row_qwerty4.xml b/java/res/xml-sw600dp/row_qwerty4.xml index 3c2f06d02..eec35b078 100644 --- a/java/res/xml-sw600dp/row_qwerty4.xml +++ b/java/res/xml-sw600dp/row_qwerty4.xml @@ -50,10 +50,24 @@ latin:keyStyle="hasShiftedLetterHintStyle" /> </default> </switch> - <Key - latin:keyStyle="spaceKeyStyle" - latin:keyXPos="30.750%p" - latin:keyWidth="39.750%p" /> + <switch> + <case + latin:languageCode="fa" + > + <Key + latin:keyStyle="spaceKeyStyle" + latin:keyXPos="30.750%p" + latin:keyWidth="30.850%p" /> + <Key + latin:keyStyle="zwnjKeyStyle" /> + </case> + <default> + <Key + latin:keyStyle="spaceKeyStyle" + latin:keyXPos="30.750%p" + latin:keyWidth="39.750%p" /> + </default> + </switch> <switch> <case latin:languageCode="iw" diff --git a/java/res/xml-sw600dp/rows_number_normal.xml b/java/res/xml-sw600dp/rows_number_normal.xml index 3704c5284..be5776b20 100644 --- a/java/res/xml-sw600dp/rows_number_normal.xml +++ b/java/res/xml-sw600dp/rows_number_normal.xml @@ -143,7 +143,7 @@ latin:keyStyle="numTabKeyStyle" latin:keyWidth="11.00%p" /> <Key - latin:keyStyle="nonSpecialBackgroundSpaceKeyStyle" + latin:keyStyle="spaceKeyStyle" latin:keyWidth="27.75%p" latin:keyXPos="12.75%p" /> <Key diff --git a/java/res/xml-sw600dp/rows_phone.xml b/java/res/xml-sw600dp/rows_phone.xml index 4c896e962..e8926936f 100644 --- a/java/res/xml-sw600dp/rows_phone.xml +++ b/java/res/xml-sw600dp/rows_phone.xml @@ -112,7 +112,7 @@ latin:keyStyle="numTabKeyStyle" latin:keyWidth="11.00%p" /> <Key - latin:keyStyle="nonSpecialBackgroundSpaceKeyStyle" + latin:keyStyle="spaceKeyStyle" latin:keyWidth="27.75%p" latin:keyXPos="12.75%p" /> <Key diff --git a/java/res/xml-sw768dp/key_styles_common.xml b/java/res/xml-sw768dp/key_styles_common.xml index 5c35f1cfb..fade151ed 100644 --- a/java/res/xml-sw768dp/key_styles_common.xml +++ b/java/res/xml-sw768dp/key_styles_common.xml @@ -78,9 +78,10 @@ latin:code="@integer/key_space" latin:keyActionFlags="noKeyPreview" /> <key-style - latin:styleName="nonSpecialBackgroundSpaceKeyStyle" - latin:code="@integer/key_space" - latin:keyActionFlags="noKeyPreview" /> + latin:styleName="zwnjKeyStyle" + latin:keyLabel="‌" + latin:moreKeys="‍" + latin:keyLabelFlags="hasPopupHint" /> <key-style latin:styleName="smileyKeyStyle" latin:keyLabel=":-)" diff --git a/java/res/xml-sw768dp/row_qwerty4.xml b/java/res/xml-sw768dp/row_qwerty4.xml index 24c081eb7..0aa04f8f7 100644 --- a/java/res/xml-sw768dp/row_qwerty4.xml +++ b/java/res/xml-sw768dp/row_qwerty4.xml @@ -76,10 +76,30 @@ </switch> </default> </switch> - <Key - latin:keyStyle="spaceKeyStyle" - latin:keyXPos="31.250%p" - latin:keyWidth="37.500%p" /> + <switch> + <case + latin:languageCode="fa" + > + <Key + latin:keyStyle="spaceKeyStyle" + latin:keyXPos="31.250%p" + latin:keyWidth="29.453%p" /> + <!-- U+200C: "" ZERO WIDTH NON-JOINER + U+200D: "" ZERO WIDTH JOINER --> + <Key + latin:keyLabel="‌" + latin:moreKeys="‍" + latin:keyLabelFlags="hasPopupHint" + latin:altCode="@integer/key_space" + latin:keyActionFlags="altCodeWhileTyping" /> + </case> + <default> + <Key + latin:keyStyle="spaceKeyStyle" + latin:keyXPos="31.250%p" + latin:keyWidth="37.500%p" /> + </default> + </switch> <switch> <case latin:languageCode="iw" diff --git a/java/res/xml-sw768dp/rows_number_normal.xml b/java/res/xml-sw768dp/rows_number_normal.xml index 8bf1a173f..2eeb6c9d4 100644 --- a/java/res/xml-sw768dp/rows_number_normal.xml +++ b/java/res/xml-sw768dp/rows_number_normal.xml @@ -145,7 +145,7 @@ latin:keyboardLayout="@xml/key_settings" latin:keyWidth="8.047%p" /> <Key - latin:keyStyle="nonSpecialBackgroundSpaceKeyStyle" + latin:keyStyle="spaceKeyStyle" latin:keyXPos="13.829%p" latin:keyWidth="24.140%p" /> <Key diff --git a/java/res/xml-sw768dp/rows_phone.xml b/java/res/xml-sw768dp/rows_phone.xml index 69c9e86ff..216fbedfb 100644 --- a/java/res/xml-sw768dp/rows_phone.xml +++ b/java/res/xml-sw768dp/rows_phone.xml @@ -114,7 +114,7 @@ latin:keyboardLayout="@xml/key_settings" latin:keyWidth="8.047%p" /> <Key - latin:keyStyle="nonSpecialBackgroundSpaceKeyStyle" + latin:keyStyle="spaceKeyStyle" latin:keyXPos="13.829%p" latin:keyWidth="24.140%p" /> <Key diff --git a/java/res/xml/key_styles_common.xml b/java/res/xml/key_styles_common.xml index f153a7d96..087b8952f 100644 --- a/java/res/xml/key_styles_common.xml +++ b/java/res/xml/key_styles_common.xml @@ -108,6 +108,12 @@ latin:keyActionFlags="noKeyPreview|enableLongPress" latin:backgroundType="functional" /> <key-style + latin:styleName="zwnjKeyStyle" + latin:keyLabel="‌" + latin:moreKeys="‍" + latin:keyLabelFlags="hasPopupHint" + latin:backgroundType="functional" /> + <key-style latin:styleName="shortcutKeyStyle" latin:code="@integer/key_shortcut" latin:keyIcon="iconShortcutKey" @@ -123,6 +129,8 @@ latin:keyActionFlags="noKeyPreview|altCodeWhileTyping|enableLongPress" latin:altCode="@integer/key_space" latin:backgroundType="functional" /> + <!-- U+200C: "" ZERO WIDTH NON-JOINER + U+200D: "" ZERO WIDTH JOINER --> <key-style latin:styleName="tabKeyStyle" latin:code="@integer/key_tab" diff --git a/java/res/xml/method.xml b/java/res/xml/method.xml index f330b268e..cdcea0ed0 100644 --- a/java/res/xml/method.xml +++ b/java/res/xml/method.xml @@ -33,6 +33,7 @@ en_GB: English Great Britain/qwerty es: Spanish/spanish et: Estonian/nordic + fa: Persian/arabic fi: Finnish/nordic fr: French/azerty fr_CA: French Canada/qwerty @@ -140,6 +141,12 @@ /> <subtype android:icon="@drawable/ic_subtype_keyboard" android:label="@string/subtype_generic" + android:imeSubtypeLocale="fa" + android:imeSubtypeMode="keyboard" + android:imeSubtypeExtraValue="SupportTouchPositionCorrection" + /> + <subtype android:icon="@drawable/ic_subtype_keyboard" + android:label="@string/subtype_generic" android:imeSubtypeLocale="fi" android:imeSubtypeMode="keyboard" android:imeSubtypeExtraValue="AsciiCapable,SupportTouchPositionCorrection" diff --git a/java/res/xml/row_qwerty4.xml b/java/res/xml/row_qwerty4.xml index 0dd2177e8..b2b47e9b5 100644 --- a/java/res/xml/row_qwerty4.xml +++ b/java/res/xml/row_qwerty4.xml @@ -59,6 +59,28 @@ </switch> <switch> <case + latin:languageCode="fa" + latin:languageSwitchKeyEnabled="true" + > + <Key + latin:keyStyle="languageSwitchKeyStyle" /> + <Key + latin:keyStyle="spaceKeyStyle" + latin:keyWidth="30%p" /> + <Key + latin:keyStyle="zwnjKeyStyle" /> + </case> + <case + latin:languageCode="fa" + latin:languageSwitchKeyEnabled="false" + > + <Key + latin:keyStyle="spaceKeyStyle" + latin:keyWidth="40%p" /> + <Key + latin:keyStyle="zwnjKeyStyle" /> + </case> + <case latin:languageSwitchKeyEnabled="true" > <Key diff --git a/java/src/com/android/inputmethod/keyboard/Keyboard.java b/java/src/com/android/inputmethod/keyboard/Keyboard.java index 19795e764..cdf07ed70 100644 --- a/java/src/com/android/inputmethod/keyboard/Keyboard.java +++ b/java/src/com/android/inputmethod/keyboard/Keyboard.java @@ -41,6 +41,7 @@ import java.io.IOException; import java.util.ArrayList; import java.util.Arrays; import java.util.HashMap; +import java.util.HashSet; import java.util.List; import java.util.Map; @@ -225,7 +226,7 @@ public class Keyboard { public int GRID_WIDTH; public int GRID_HEIGHT; - public final ArrayList<Key> mKeys = new ArrayList<Key>(); + public final HashSet<Key> mKeys = new HashSet<Key>(); public final ArrayList<Key> mShiftKeys = new ArrayList<Key>(); public final ArrayList<Key> mAltCodeKeysWhileTyping = new ArrayList<Key>(); public final KeyboardIconsSet mIconsSet = new KeyboardIconsSet(); @@ -316,8 +317,8 @@ public class Keyboard { private int mMaxHeightCount = 0; private int mMaxWidthCount = 0; - private final Map<Integer, Integer> mHeightHistogram = new HashMap<Integer, Integer>(); - private final Map<Integer, Integer> mWidthHistogram = new HashMap<Integer, Integer>(); + private final HashMap<Integer, Integer> mHeightHistogram = new HashMap<Integer, Integer>(); + private final HashMap<Integer, Integer> mWidthHistogram = new HashMap<Integer, Integer>(); private void clearHistogram() { mMostCommonKeyHeight = 0; @@ -329,7 +330,8 @@ public class Keyboard { mWidthHistogram.clear(); } - private static int updateHistogramCounter(Map<Integer, Integer> histogram, Integer key) { + private static int updateHistogramCounter(HashMap<Integer, Integer> histogram, + Integer key) { final int count = (histogram.containsKey(key) ? histogram.get(key) : 0) + 1; histogram.put(key, count); return count; diff --git a/java/src/com/android/inputmethod/keyboard/KeyboardView.java b/java/src/com/android/inputmethod/keyboard/KeyboardView.java index 4c65522ec..847174c0a 100644 --- a/java/src/com/android/inputmethod/keyboard/KeyboardView.java +++ b/java/src/com/android/inputmethod/keyboard/KeyboardView.java @@ -95,6 +95,8 @@ 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 ALPHA_OPAQUE = 255; + // Main keyboard private Keyboard mKeyboard; private final KeyDrawParams mKeyDrawParams; @@ -201,6 +203,7 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { public int mKeyHintLetterSize; public int mKeyShiftedLetterHintSize; public int mKeyHintLabelSize; + public int mAnimAlpha; public KeyDrawParams(TypedArray a) { mKeyBackground = a.getDrawable(R.styleable.KeyboardView_keyBackground); @@ -256,6 +259,12 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { mKeyShiftedLetterHintSize = (int)(keyHeight * mKeyShiftedLetterHintRatio); mKeyHintLabelSize = (int)(keyHeight * mKeyHintLabelRatio); } + + public void brendAlpha(Paint paint) { + final int color = paint.getColor(); + paint.setARGB((paint.getAlpha() * mAnimAlpha) / ALPHA_OPAQUE, + Color.red(color), Color.green(color), Color.blue(color)); + } } /* package */ static class KeyPreviewDrawParams { @@ -343,7 +352,6 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { mPaint.setAntiAlias(true); mPaint.setTextAlign(Align.CENTER); - mPaint.setAlpha(255); } // Read fraction value in TypedArray as float. @@ -492,6 +500,7 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { final int keyDrawY = key.mY + getPaddingTop(); canvas.translate(keyDrawX, keyDrawY); + params.mAnimAlpha = ALPHA_OPAQUE; if (!key.isSpacer()) { onDrawKeyBackground(key, canvas, params); } @@ -535,6 +544,9 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { // Draw key label. final Drawable icon = key.getIcon(mKeyboard.mIconsSet); + if (icon != null) { + icon.setAlpha(params.mAnimAlpha); + } float positionX = centerX; if (key.mLabel != null) { final String label = key.mLabel; @@ -589,6 +601,7 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { // Make label invisible paint.setColor(Color.TRANSPARENT); } + params.brendAlpha(paint); canvas.drawText(label, 0, label.length(), positionX, baseline, paint); // Turn off drop shadow and reset x-scale. paint.setShadowLayer(0, 0, 0, 0); @@ -633,6 +646,7 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { hintSize = params.mKeyHintLetterSize; } paint.setColor(hintColor); + params.brendAlpha(paint); paint.setTextSize(hintSize); final float hintX, hintY; if (key.hasHintLabel()) { @@ -701,6 +715,7 @@ public class KeyboardView extends View implements PointerTracker.DrawingProxy { paint.setTextSize(params.mKeyHintLetterSize); paint.setColor(params.mKeyHintLabelColor); + params.brendAlpha(paint); paint.setTextAlign(Align.CENTER); final float hintX = keyWidth - params.mKeyHintLetterPadding - getCharWidth(KEY_LABEL_REFERENCE_CHAR, paint) / 2; diff --git a/java/src/com/android/inputmethod/keyboard/LatinKeyboardView.java b/java/src/com/android/inputmethod/keyboard/LatinKeyboardView.java index f4e766cb0..97f4d07d9 100644 --- a/java/src/com/android/inputmethod/keyboard/LatinKeyboardView.java +++ b/java/src/com/android/inputmethod/keyboard/LatinKeyboardView.java @@ -16,7 +16,11 @@ package com.android.inputmethod.keyboard; +import android.animation.Animator; +import android.animation.AnimatorInflater; +import android.animation.AnimatorListenerAdapter; import android.animation.ValueAnimator; +import android.animation.ValueAnimator.AnimatorUpdateListener; import android.content.Context; import android.content.pm.PackageManager; import android.content.res.TypedArray; @@ -75,12 +79,9 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke private Key mSpaceKey; private Drawable mSpaceIcon; // Stuff to draw language name on spacebar. - private ValueAnimator mLanguageOnSpacebarAnimator; + private ValueAnimator mLanguageOnSpacebarFadeoutAnimator; private int mFinalAlphaOfLanguageOnSpacebar; - private int mDurationOfFadeoutLanguageOnSpacebar; private static final int ALPHA_OPAQUE = 255; - private static final int LANGUAGE_ON_SPACEBAR_NEVER_DISPLAY = 0; - private static final int LANGUAGE_ON_SPACEBAR_ALWAYS_DISPLAY = -1; private boolean mNeedsToDisplayLanguage; private Locale mSpacebarLocale; private int mSpacebarTextAlpha; @@ -97,6 +98,11 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke private final Drawable mAutoCorrectionSpacebarLedIcon; private static final int SPACE_LED_LENGTH_PERCENT = 80; + // Stuff to draw altCodeWhileTyping keys. + private ValueAnimator mAltCodeKeyWhileTypingFadeoutAnimator; + private ValueAnimator mAltCodeKeyWhileTypingFadeinAnimator; + private int mAltCodeKeyWhileTypingAnimAlpha; + // More keys keyboard private PopupWindow mMoreKeysWindow; private MoreKeysPanel mMoreKeysPanel; @@ -121,7 +127,7 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke private static final int MSG_REPEAT_KEY = 1; private static final int MSG_LONGPRESS_KEY = 2; private static final int MSG_DOUBLE_TAP = 3; - private static final int MSG_KEY_TYPED = 4; + private static final int MSG_TYPING_STATE_EXPIRED = 4; private final KeyTimerParams mParams; private boolean mInKeyRepeat; @@ -147,6 +153,18 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke KeyboardSwitcher.getInstance().onLongPressTimeout(msg.arg1); } break; + case MSG_TYPING_STATE_EXPIRED: + final ValueAnimator fadeout = keyboardView.mAltCodeKeyWhileTypingFadeoutAnimator; + if (fadeout != null && fadeout.isStarted()) { + fadeout.cancel(); + } + // TODO: Start the fade in animation with an initial value that is the same as the + // final value when the above fade out animation gets cancelled. + final ValueAnimator fadein = keyboardView.mAltCodeKeyWhileTypingFadeinAnimator; + if (fadein != null && !fadein.isStarted()) { + fadein.start(); + } + break; } } @@ -221,14 +239,30 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke } @Override - public void startKeyTypedTimer() { - removeMessages(MSG_KEY_TYPED); - sendMessageDelayed(obtainMessage(MSG_KEY_TYPED), mParams.mIgnoreSpecialKeyTimeout); + public void startTypingStateTimer() { + final boolean isTyping = isTypingState(); + removeMessages(MSG_TYPING_STATE_EXPIRED); + sendMessageDelayed( + obtainMessage(MSG_TYPING_STATE_EXPIRED), mParams.mIgnoreAltCodeKeyTimeout); + final LatinKeyboardView keyboardView = getOuterInstance(); + if (isTyping) { + return; + } + final ValueAnimator fadein = keyboardView.mAltCodeKeyWhileTypingFadeinAnimator; + if (fadein != null && fadein.isStarted()) { + fadein.cancel(); + } + // TODO: Start the fade out animation with an initial value that is the same as the + // final value when the above fade in animation gets cancelled. + final ValueAnimator fadeout = keyboardView.mAltCodeKeyWhileTypingFadeoutAnimator; + if (fadeout != null && !fadeout.isStarted()) { + fadeout.start(); + } } @Override - public boolean isTyping() { - return hasMessages(MSG_KEY_TYPED); + public boolean isTypingState() { + return hasMessages(MSG_TYPING_STATE_EXPIRED); } @Override @@ -287,7 +321,7 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke public final int mLongPressKeyTimeout; public final int mLongPressShiftKeyTimeout; public final int mLongPressSpaceKeyTimeout; - public final int mIgnoreSpecialKeyTimeout; + public final int mIgnoreAltCodeKeyTimeout; KeyTimerParams() { mKeyRepeatStartTimeout = 0; @@ -295,7 +329,7 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke mLongPressKeyTimeout = 0; mLongPressShiftKeyTimeout = 0; mLongPressSpaceKeyTimeout = 0; - mIgnoreSpecialKeyTimeout = 0; + mIgnoreAltCodeKeyTimeout = 0; } public KeyTimerParams(TypedArray latinKeyboardViewAttr) { @@ -309,8 +343,8 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke R.styleable.LatinKeyboardView_longPressShiftKeyTimeout, 0); mLongPressSpaceKeyTimeout = latinKeyboardViewAttr.getInt( R.styleable.LatinKeyboardView_longPressSpaceKeyTimeout, 0); - mIgnoreSpecialKeyTimeout = latinKeyboardViewAttr.getInt( - R.styleable.LatinKeyboardView_ignoreSpecialKeyTimeout, 0); + mIgnoreAltCodeKeyTimeout = latinKeyboardViewAttr.getInt( + R.styleable.LatinKeyboardView_ignoreAltCodeKeyTimeout, 0); } } @@ -339,13 +373,12 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke mSpacebarTextColor = a.getColor(R.styleable.LatinKeyboardView_spacebarTextColor, 0); mSpacebarTextShadowColor = a.getColor( R.styleable.LatinKeyboardView_spacebarTextShadowColor, 0); - mDurationOfFadeoutLanguageOnSpacebar = a.getInt( - R.styleable.LatinKeyboardView_durationOfFadeoutLanguageOnSpacebar, - LANGUAGE_ON_SPACEBAR_NEVER_DISPLAY); - final int delayBeforeFadeoutLanguageOnSpacebar = a.getInt( - R.styleable.LatinKeyboardView_delayBeforeFadeoutLangageOnSpacebar, 0); - mFinalAlphaOfLanguageOnSpacebar = a.getInt( - R.styleable.LatinKeyboardView_finalAlphaOfLanguageOnSpacebar, 0); + final int languageOnSpacebarFadeoutAnimatorResId = a.getResourceId( + R.styleable.LatinKeyboardView_languageOnSpacebarFadeoutAnimator, 0); + final int altCodeKeyWhileTypingFadeoutAnimatorResId = a.getResourceId( + R.styleable.LatinKeyboardView_altCodeKeyWhileTypingFadeoutAnimator, 0); + final int altCodeKeyWhileTypingFadeinAnimatorResId = a.getResourceId( + R.styleable.LatinKeyboardView_altCodeKeyWhileTypingFadeinAnimator, 0); final KeyTimerParams keyTimerParams = new KeyTimerParams(a); mPointerTrackerParams = new PointerTrackerParams(a); @@ -361,19 +394,67 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke PointerTracker.setParameters(mPointerTrackerParams); - mLanguageOnSpacebarAnimator = ValueAnimator.ofInt( - ALPHA_OPAQUE, mFinalAlphaOfLanguageOnSpacebar); - mLanguageOnSpacebarAnimator.setStartDelay(delayBeforeFadeoutLanguageOnSpacebar); - if (mDurationOfFadeoutLanguageOnSpacebar > 0) { - mLanguageOnSpacebarAnimator.setDuration(mDurationOfFadeoutLanguageOnSpacebar); - } - mLanguageOnSpacebarAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { - @Override - public void onAnimationUpdate(ValueAnimator animation) { - mSpacebarTextAlpha = (Integer)animation.getAnimatedValue(); - invalidateKey(mSpaceKey); - } - }); + final ValueAnimator animator = loadValueAnimator(languageOnSpacebarFadeoutAnimatorResId); + if (animator != null) { + animator.addUpdateListener(new AnimatorUpdateListener() { + @Override + public void onAnimationUpdate(ValueAnimator animation) { + mSpacebarTextAlpha = (Integer)animation.getAnimatedValue(); + invalidateKey(mSpaceKey); + } + }); + animator.addListener(new AnimatorListenerAdapter() { + @Override + public void onAnimationEnd(Animator a) { + final ValueAnimator valueAnimator = (ValueAnimator)a; + mFinalAlphaOfLanguageOnSpacebar = (Integer)valueAnimator.getAnimatedValue(); + } + }); + // In order to get the final value of animator. + animator.end(); + } + mLanguageOnSpacebarFadeoutAnimator = animator; + + final ValueAnimator fadeout = loadValueAnimator(altCodeKeyWhileTypingFadeoutAnimatorResId); + if (fadeout != null) { + fadeout.addUpdateListener(new AnimatorUpdateListener() { + @Override + public void onAnimationUpdate(ValueAnimator animation) { + mAltCodeKeyWhileTypingAnimAlpha = (Integer)animation.getAnimatedValue(); + updateAltCodeKeyWhileTyping(); + } + }); + fadeout.addListener(new AnimatorListenerAdapter() { + @Override + public void onAnimationEnd(Animator a) { + final ValueAnimator valueAnimator = (ValueAnimator)a; + } + }); + } + mAltCodeKeyWhileTypingFadeoutAnimator = fadeout; + + final ValueAnimator fadein = loadValueAnimator(altCodeKeyWhileTypingFadeinAnimatorResId); + if (fadein != null) { + fadein.addUpdateListener(new AnimatorUpdateListener() { + @Override + public void onAnimationUpdate(ValueAnimator animation) { + mAltCodeKeyWhileTypingAnimAlpha = (Integer)animation.getAnimatedValue(); + updateAltCodeKeyWhileTyping(); + } + }); + fadein.addListener(new AnimatorListenerAdapter() { + @Override + public void onAnimationEnd(Animator a) { + final ValueAnimator valueAnimator = (ValueAnimator)a; + } + }); + } + mAltCodeKeyWhileTypingFadeinAnimator = fadein; + } + + private ValueAnimator loadValueAnimator(int resId) { + if (resId == 0) return null; + return (ValueAnimator)AnimatorInflater.loadAnimator(getContext(), resId); } public void setKeyboardActionListener(KeyboardActionListener listener) { @@ -429,6 +510,8 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke final int keyHeight = keyboard.mMostCommonKeyHeight - keyboard.mVerticalGap; mSpacebarTextSize = keyHeight * mSpacebarTextRatio; mSpacebarLocale = keyboard.mId.mLocale; + mSpacebarTextAlpha = ALPHA_OPAQUE; + mAltCodeKeyWhileTypingAnimAlpha = ALPHA_OPAQUE; } /** @@ -789,18 +872,27 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke invalidateKey(shortcutKey); } + private void updateAltCodeKeyWhileTyping() { + final Keyboard keyboard = getKeyboard(); + if (keyboard == null) return; + for (final Key key : keyboard.mAltCodeKeysWhileTyping) { + invalidateKey(key); + } + } + public void startDisplayLanguageOnSpacebar(boolean subtypeChanged, boolean needsToDisplayLanguage) { - mLanguageOnSpacebarAnimator.cancel(); + final ValueAnimator animator = mLanguageOnSpacebarFadeoutAnimator; + if (animator != null) { + animator.cancel(); + } mNeedsToDisplayLanguage = needsToDisplayLanguage; - if (mDurationOfFadeoutLanguageOnSpacebar == LANGUAGE_ON_SPACEBAR_NEVER_DISPLAY) { + if (animator == null) { mNeedsToDisplayLanguage = false; - } else if (mDurationOfFadeoutLanguageOnSpacebar == LANGUAGE_ON_SPACEBAR_ALWAYS_DISPLAY) { - mSpacebarTextAlpha = ALPHA_OPAQUE; } else { if (subtypeChanged && needsToDisplayLanguage) { mSpacebarTextAlpha = ALPHA_OPAQUE; - mLanguageOnSpacebarAnimator.start(); + animator.start(); } else { mSpacebarTextAlpha = mFinalAlphaOfLanguageOnSpacebar; } @@ -816,6 +908,9 @@ public class LatinKeyboardView extends KeyboardView implements PointerTracker.Ke @Override protected void onDrawKeyTopVisuals(Key key, Canvas canvas, Paint paint, KeyDrawParams params) { + if (key.altCodeWhileTyping() && key.isEnabled()) { + params.mAnimAlpha = mAltCodeKeyWhileTypingAnimAlpha; + } if (key.mCode == Keyboard.CODE_SPACE) { drawSpacebar(key, canvas, paint); diff --git a/java/src/com/android/inputmethod/keyboard/PointerTracker.java b/java/src/com/android/inputmethod/keyboard/PointerTracker.java index 607b33bb4..ed889712a 100644 --- a/java/src/com/android/inputmethod/keyboard/PointerTracker.java +++ b/java/src/com/android/inputmethod/keyboard/PointerTracker.java @@ -68,8 +68,8 @@ public class PointerTracker { } public interface TimerProxy { - public void startKeyTypedTimer(); - public boolean isTyping(); + public void startTypingStateTimer(); + public boolean isTypingState(); public void startKeyRepeatTimer(PointerTracker tracker); public void startLongPressTimer(PointerTracker tracker); public void startLongPressTimer(int code); @@ -81,9 +81,9 @@ public class PointerTracker { public static class Adapter implements TimerProxy { @Override - public void startKeyTypedTimer() {} + public void startTypingStateTimer() {} @Override - public boolean isTyping() { return false; } + public boolean isTypingState() { return false; } @Override public void startKeyRepeatTimer(PointerTracker tracker) {} @Override @@ -251,25 +251,26 @@ public class PointerTracker { // primaryCode is different from {@link Key#mCode}. private void callListenerOnCodeInput(Key key, int primaryCode, int x, int y) { final boolean ignoreModifierKey = mIgnoreModifierKey && key.isModifier(); - final boolean alterCode = key.altCodeWhileTyping() && mTimerProxy.isTyping(); - final int code = alterCode ? key.mAltCode : primaryCode; + final boolean altersCode = key.altCodeWhileTyping() && mTimerProxy.isTypingState(); + final int code = altersCode ? key.mAltCode : primaryCode; if (DEBUG_LISTENER) { Log.d(TAG, "onCodeInput: " + Keyboard.printableCode(code) + " text=" + key.mOutputText + " x=" + x + " y=" + y - + " ignoreModifier=" + ignoreModifierKey + " alterCode=" + alterCode + + " ignoreModifier=" + ignoreModifierKey + " altersCode=" + altersCode + " enabled=" + key.isEnabled()); } if (ignoreModifierKey) { return; } - if (key.isEnabled()) { + // Even if the key is disabled, it should respond if it is in the altCodeWhileTyping state. + if (key.isEnabled() || altersCode) { if (code == Keyboard.CODE_OUTPUT_TEXT) { mListener.onTextInput(key.mOutputText); } else if (code != Keyboard.CODE_UNSPECIFIED) { mListener.onCodeInput(code, x, y); } if (!key.altCodeWhileTyping() && !key.isModifier()) { - mTimerProxy.startKeyTypedTimer(); + mTimerProxy.startTypingStateTimer(); } } } @@ -322,10 +323,11 @@ public class PointerTracker { private void setReleasedKeyGraphics(Key key) { mDrawingProxy.dismissKeyPreview(this); - if (key == null || !key.isEnabled()) { + if (key == null) { return; } + // Even if the key is disabled, update the key release graphics just in case. updateReleaseKeyGraphics(key); if (key.isShift()) { @@ -351,7 +353,14 @@ public class PointerTracker { } private void setPressedKeyGraphics(Key key) { - if (key == null || !key.isEnabled()) { + if (key == null) { + return; + } + + // Even if the key is disabled, it should respond if it is in the altCodeWhileTyping state. + final boolean altersCode = key.altCodeWhileTyping() && mTimerProxy.isTypingState(); + final boolean needsToUpdateGraphics = key.isEnabled() || altersCode; + if (!needsToUpdateGraphics) { return; } @@ -368,7 +377,7 @@ public class PointerTracker { } } - if (key.altCodeWhileTyping() && mTimerProxy.isTyping()) { + if (key.altCodeWhileTyping() && mTimerProxy.isTypingState()) { final int altCode = key.mAltCode; final Key altKey = mKeyboard.getKey(altCode); if (altKey != null) { diff --git a/java/src/com/android/inputmethod/keyboard/ProximityInfo.java b/java/src/com/android/inputmethod/keyboard/ProximityInfo.java index e2a48306a..61d75e278 100644 --- a/java/src/com/android/inputmethod/keyboard/ProximityInfo.java +++ b/java/src/com/android/inputmethod/keyboard/ProximityInfo.java @@ -124,40 +124,40 @@ public class ProximityInfo { final float[] sweetSpotCenterXs; final float[] sweetSpotCenterYs; final float[] sweetSpotRadii; - final boolean calculateSweetSpotParams; + + for (int i = 0; i < keyCount; ++i) { + final Key key = keys[i]; + keyXCoordinates[i] = key.mX; + keyYCoordinates[i] = key.mY; + keyWidths[i] = key.mWidth; + keyHeights[i] = key.mHeight; + keyCharCodes[i] = key.mCode; + } + if (touchPositionCorrection != null && touchPositionCorrection.isValid()) { sweetSpotCenterXs = new float[keyCount]; sweetSpotCenterYs = new float[keyCount]; sweetSpotRadii = new float[keyCount]; - calculateSweetSpotParams = true; for (int i = 0; i < keyCount; i++) { final Key key = keys[i]; - keyXCoordinates[i] = key.mX; - keyYCoordinates[i] = key.mY; - keyWidths[i] = key.mWidth; - keyHeights[i] = key.mHeight; - keyCharCodes[i] = key.mCode; - if (calculateSweetSpotParams) { - final Rect hitBox = key.mHitBox; - final int row = hitBox.top / mKeyHeight; - if (row < touchPositionCorrection.mRadii.length) { - final float hitBoxCenterX = (hitBox.left + hitBox.right) * 0.5f; - final float hitBoxCenterY = (hitBox.top + hitBox.bottom) * 0.5f; - final float hitBoxWidth = hitBox.right - hitBox.left; - final float hitBoxHeight = hitBox.bottom - hitBox.top; - final float x = touchPositionCorrection.mXs[row]; - final float y = touchPositionCorrection.mYs[row]; - final float radius = touchPositionCorrection.mRadii[row]; - sweetSpotCenterXs[i] = hitBoxCenterX + x * hitBoxWidth; - sweetSpotCenterYs[i] = hitBoxCenterY + y * hitBoxHeight; - sweetSpotRadii[i] = radius * (float) Math.sqrt( - hitBoxWidth * hitBoxWidth + hitBoxHeight * hitBoxHeight); - } + final Rect hitBox = key.mHitBox; + final int row = hitBox.top / mKeyHeight; + if (row < touchPositionCorrection.mRadii.length) { + final float hitBoxCenterX = (hitBox.left + hitBox.right) * 0.5f; + final float hitBoxCenterY = (hitBox.top + hitBox.bottom) * 0.5f; + final float hitBoxWidth = hitBox.right - hitBox.left; + final float hitBoxHeight = hitBox.bottom - hitBox.top; + final float x = touchPositionCorrection.mXs[row]; + final float y = touchPositionCorrection.mYs[row]; + final float radius = touchPositionCorrection.mRadii[row]; + sweetSpotCenterXs[i] = hitBoxCenterX + x * hitBoxWidth; + sweetSpotCenterYs[i] = hitBoxCenterY + y * hitBoxHeight; + sweetSpotRadii[i] = radius * (float) Math.sqrt( + hitBoxWidth * hitBoxWidth + hitBoxHeight * hitBoxHeight); } } } else { sweetSpotCenterXs = sweetSpotCenterYs = sweetSpotRadii = null; - calculateSweetSpotParams = false; } mNativeProximityInfo = setProximityInfoNative(mLocaleStr, MAX_PROXIMITY_CHARS_SIZE, diff --git a/java/src/com/android/inputmethod/latin/LatinIME.java b/java/src/com/android/inputmethod/latin/LatinIME.java index f41972e8b..9f5931de9 100644 --- a/java/src/com/android/inputmethod/latin/LatinIME.java +++ b/java/src/com/android/inputmethod/latin/LatinIME.java @@ -924,17 +924,17 @@ public class LatinIME extends InputMethodServiceCompatWrapper implements Keyboar } final List<SuggestedWords.SuggestedWordInfo> applicationSuggestedWords = - SuggestedWords.Builder.getFromApplicationSpecifiedCompletions( + SuggestedWords.getFromApplicationSpecifiedCompletions( applicationSpecifiedCompletions); - SuggestedWords.Builder builder = new SuggestedWords.Builder(applicationSuggestedWords, + final SuggestedWords suggestedWords = new SuggestedWords( + applicationSuggestedWords, false /* typedWordValid */, - false /* hasMinimalSuggestion */, + false /* hasAutoCorrectionCandidate */, false /* allowsToBeAutoCorrected */, false /* isPunctuationSuggestions */); // When in fullscreen mode, show completions generated by the application - final SuggestedWords words = builder.build(); final boolean isAutoCorrection = false; - setSuggestions(words, isAutoCorrection); + setSuggestions(suggestedWords, isAutoCorrection); setAutoCorrectionIndicator(isAutoCorrection); // TODO: is this the right thing to do? What should we auto-correct to in // this case? This says to keep whatever the user typed. @@ -1767,7 +1767,7 @@ public class LatinIME extends InputMethodServiceCompatWrapper implements Keyboar final CharSequence typedWord = mWordComposer.getTypedWord(); // getSuggestedWordBuilder handles gracefully a null value of prevWord - final SuggestedWords.Builder builder = mSuggest.getSuggestedWordBuilder(mWordComposer, + final SuggestedWords suggestedWords = mSuggest.getSuggestedWords(mWordComposer, prevWord, mKeyboardSwitcher.getKeyboard().getProximityInfo(), mCorrectionMode); // Basically, we update the suggestion strip only when suggestion count > 1. However, @@ -1776,24 +1776,25 @@ public class LatinIME extends InputMethodServiceCompatWrapper implements Keyboar // in most cases, suggestion count is 1 when typed word's length is 1, but we do always // need to clear the previous state when the user starts typing a word (i.e. typed word's // length == 1). - if (builder.size() > 1 || typedWord.length() == 1 || !builder.allowsToBeAutoCorrected() + if (suggestedWords.size() > 1 || typedWord.length() == 1 + || !suggestedWords.mAllowsToBeAutoCorrected || mSuggestionsView.isShowingAddToDictionaryHint()) { - showSuggestions(builder.build(), typedWord); + showSuggestions(suggestedWords, typedWord); } else { SuggestedWords previousSuggestions = mSuggestionsView.getSuggestions(); if (previousSuggestions == mSettingsValues.mSuggestPuncList) { previousSuggestions = SuggestedWords.EMPTY; } final ArrayList<SuggestedWords.SuggestedWordInfo> typedWordAndPreviousSuggestions = - SuggestedWords.Builder.getTypedWordAndPreviousSuggestions( + SuggestedWords.getTypedWordAndPreviousSuggestions( typedWord, previousSuggestions); - final SuggestedWords.Builder obsoleteSuggestionsBuilder = - new SuggestedWords.Builder(typedWordAndPreviousSuggestions, + final SuggestedWords obsoleteSuggestedWords = + new SuggestedWords(typedWordAndPreviousSuggestions, false /* typedWordValid */, - false /* hasMinimalSuggestion */, + false /* hasAutoCorrectionCandidate */, false /* allowsToBeAutoCorrected */, false /* isPunctuationSuggestions */); - showSuggestions(obsoleteSuggestionsBuilder.build(), typedWord); + showSuggestions(obsoleteSuggestedWords, typedWord); } } @@ -1973,23 +1974,23 @@ public class LatinIME extends InputMethodServiceCompatWrapper implements Keyboar return; } - final SuggestedWords.Builder builder; + final SuggestedWords suggestedWords; if (mCorrectionMode == Suggest.CORRECTION_FULL_BIGRAM) { final CharSequence prevWord = EditingUtils.getThisWord(getCurrentInputConnection(), mSettingsValues.mWordSeparators); if (!TextUtils.isEmpty(prevWord)) { - builder = mSuggest.getBigramPredictionWordBuilder(prevWord); + suggestedWords = mSuggest.getBigramPredictions(prevWord); } else { - builder = null; + suggestedWords = null; } } else { - builder = null; + suggestedWords = null; } - if (null != builder && builder.size() > 0) { + if (null != suggestedWords && suggestedWords.size() > 0) { // Explicitly supply an empty typed word (the no-second-arg version of // showSuggestions will retrieve the word near the cursor, we don't want that here) - showSuggestions(builder.build(), ""); + showSuggestions(suggestedWords, ""); } else { if (!isShowingPunctuationList()) setPunctuationSuggestions(); } diff --git a/java/src/com/android/inputmethod/latin/SettingsValues.java b/java/src/com/android/inputmethod/latin/SettingsValues.java index 0a4aea140..d12b9c428 100644 --- a/java/src/com/android/inputmethod/latin/SettingsValues.java +++ b/java/src/com/android/inputmethod/latin/SettingsValues.java @@ -183,12 +183,11 @@ public class SettingsValues { KeySpecParser.getLabel(puncSpec))); } } - final SuggestedWords.Builder builder = new SuggestedWords.Builder(puncList, + return new SuggestedWords(puncList, false /* typedWordValid */, - false /* hasMinimalSuggestion */, + false /* hasAutoCorrectionCandidate */, false /* allowsToBeAutoCorrected */, true /* isPunctuationSuggestions */); - return builder.build(); } private static SuggestedWords createSuggestPuncOutputTextList(final String[] puncs) { @@ -205,12 +204,11 @@ public class SettingsValues { } } } - final SuggestedWords.Builder builder = new SuggestedWords.Builder(puncOutputTextList, + return new SuggestedWords(puncOutputTextList, false /* typedWordValid */, - false /* hasMinimalSuggestion */, + false /* hasAutoCorrectionCandidate */, false /* allowsToBeAutoCorrected */, true /* isPunctuationSuggestions */); - return builder.build(); } private static String createWordSeparators(final String weakSpaceStrippers, diff --git a/java/src/com/android/inputmethod/latin/Suggest.java b/java/src/com/android/inputmethod/latin/Suggest.java index 28d3b4437..3089625e7 100644 --- a/java/src/com/android/inputmethod/latin/Suggest.java +++ b/java/src/com/android/inputmethod/latin/Suggest.java @@ -239,7 +239,7 @@ public class Suggest implements Dictionary.WordCallback { } private static final WordComposer sEmptyWordComposer = new WordComposer(); - public SuggestedWords.Builder getBigramPredictionWordBuilder(CharSequence prevWordForBigram) { + public SuggestedWords getBigramPredictions(CharSequence prevWordForBigram) { LatinImeLogger.onStartSuggestion(prevWordForBigram); mIsFirstCharCapitalized = false; mIsAllUpperCase = false; @@ -269,16 +269,15 @@ public class Suggest implements Dictionary.WordCallback { StringUtils.removeDupes(mSuggestions); - return new SuggestedWords.Builder( - SuggestedWords.Builder.getFromCharSequenceList(mSuggestions), + return new SuggestedWords(SuggestedWords.getFromCharSequenceList(mSuggestions), false /* typedWordValid */, - false /* hasMinimalSuggestion */, + false /* hasAutoCorrectionCandidate */, false /* allowsToBeAutoCorrected */, false /* isPunctuationSuggestions */); } // TODO: cleanup dictionaries looking up and suggestions building with SuggestedWords.Builder - public SuggestedWords.Builder getSuggestedWordBuilder( + public SuggestedWords getSuggestedWords( final WordComposer wordComposer, CharSequence prevWordForBigram, final ProximityInfo proximityInfo, final int correctionMode) { LatinImeLogger.onStartSuggestion(prevWordForBigram); @@ -344,21 +343,22 @@ public class Suggest implements Dictionary.WordCallback { } } else if (wordComposer.size() > 1) { + final WordComposer wordComposerForLookup; + if (mTrailingSingleQuotesCount > 0) { + wordComposerForLookup = new WordComposer(wordComposer); + for (int i = mTrailingSingleQuotesCount - 1; i >= 0; --i) { + wordComposerForLookup.deleteLast(); + } + } else { + wordComposerForLookup = wordComposer; + } // At second character typed, search the unigrams (scores being affected by bigrams) for (final String key : mUnigramDictionaries.keySet()) { // Skip UserUnigramDictionary and WhitelistDictionary to lookup if (key.equals(DICT_KEY_USER_UNIGRAM) || key.equals(DICT_KEY_WHITELIST)) continue; final Dictionary dictionary = mUnigramDictionaries.get(key); - if (mTrailingSingleQuotesCount > 0) { - final WordComposer tmpWordComposer = new WordComposer(wordComposer); - for (int i = mTrailingSingleQuotesCount - 1; i >= 0; --i) { - tmpWordComposer.deleteLast(); - } - dictionary.getWords(tmpWordComposer, this, proximityInfo); - } else { - dictionary.getWords(wordComposer, this, proximityInfo); - } + dictionary.getWords(wordComposerForLookup, this, proximityInfo); } } @@ -392,42 +392,36 @@ public class Suggest implements Dictionary.WordCallback { mSuggestions.add(0, typedWord); StringUtils.removeDupes(mSuggestions); - final SuggestedWords.Builder builder; - final ArrayList<SuggestedWords.SuggestedWordInfo> scoreInfoList; + final ArrayList<SuggestedWords.SuggestedWordInfo> suggestionsList; if (DBG) { // TODO: this doesn't take into account the fact that removing dupes from mSuggestions // may have made mScores[] and mSuggestions out of sync. final CharSequence autoCorrectionSuggestion = mSuggestions.get(0); - final int autoCorrectionSuggestionScore = mScores[0]; double normalizedScore = BinaryDictionary.calcNormalizedScore( - typedWord, autoCorrectionSuggestion.toString(), - autoCorrectionSuggestionScore); - scoreInfoList = new ArrayList<SuggestedWords.SuggestedWordInfo>(); - scoreInfoList.add(new SuggestedWords.SuggestedWordInfo(autoCorrectionSuggestion, "+", + typedWord, autoCorrectionSuggestion.toString(), mScores[0]); + suggestionsList = new ArrayList<SuggestedWords.SuggestedWordInfo>(); + suggestionsList.add(new SuggestedWords.SuggestedWordInfo(autoCorrectionSuggestion, "+", false)); final int suggestionsSize = mSuggestions.size(); // Note: i here is the index in mScores[], but the index in mSuggestions is one more // than i because we added the typed word to mSuggestions without touching mScores. for (int i = 0; i < mScores.length && i < suggestionsSize - 1; ++i) { + final String scoreInfoString; if (normalizedScore > 0) { - final String scoreThreshold = String.format("%d (%4.2f)", mScores[i], - normalizedScore); - scoreInfoList.add( - new SuggestedWords.SuggestedWordInfo(mSuggestions.get(i + 1), - scoreThreshold, false)); + scoreInfoString = String.format("%d (%4.2f)", mScores[i], normalizedScore); normalizedScore = 0.0; } else { - final String score = Integer.toString(mScores[i]); - scoreInfoList.add(new SuggestedWords.SuggestedWordInfo(mSuggestions.get(i + 1), - score, false)); + scoreInfoString = Integer.toString(mScores[i]); } + suggestionsList.add(new SuggestedWords.SuggestedWordInfo(mSuggestions.get(i + 1), + scoreInfoString, false)); } for (int i = mScores.length; i < suggestionsSize; ++i) { - scoreInfoList.add(new SuggestedWords.SuggestedWordInfo(mSuggestions.get(i), + suggestionsList.add(new SuggestedWords.SuggestedWordInfo(mSuggestions.get(i), "--", false)); } } else { - scoreInfoList = SuggestedWords.Builder.getFromCharSequenceList(mSuggestions); + suggestionsList = SuggestedWords.getFromCharSequenceList(mSuggestions); } boolean autoCorrectionAvailable = hasAutoCorrection; @@ -437,16 +431,20 @@ public class Suggest implements Dictionary.WordCallback { } // Don't auto-correct words with multiple capital letter autoCorrectionAvailable &= !wordComposer.isMostlyCaps(); - builder = new SuggestedWords.Builder(scoreInfoList, + final boolean shouldBlockAutoCorrectionBySatefyNet; + if (allowsToBeAutoCorrected && suggestionsList.size() > 1 && mAutoCorrectionThreshold > 0 + && Suggest.shouldBlockAutoCorrectionBySafetyNet(typedWord, + suggestionsList.get(1).mWord)) { + shouldBlockAutoCorrectionBySatefyNet = true; + } else { + shouldBlockAutoCorrectionBySatefyNet = false; + } + return new SuggestedWords(suggestionsList, !allowsToBeAutoCorrected /* typedWordValid */, - autoCorrectionAvailable /* hasMinimalSuggestion */, + autoCorrectionAvailable & !shouldBlockAutoCorrectionBySatefyNet + /* hasAutoCorrectionCandidate */, allowsToBeAutoCorrected /* allowsToBeAutoCorrected */, false /* isPunctuationSuggestions */); - if (allowsToBeAutoCorrected && builder.size() > 1 && mAutoCorrectionThreshold > 0 - && Suggest.shouldBlockAutoCorrectionBySafetyNet(typedWord, builder.getWord(1))) { - builder.setShouldBlockAutoCorrectionBySafetyNet(); - } - return builder; } @Override diff --git a/java/src/com/android/inputmethod/latin/SuggestedWords.java b/java/src/com/android/inputmethod/latin/SuggestedWords.java index 144e67482..6b231f81c 100644 --- a/java/src/com/android/inputmethod/latin/SuggestedWords.java +++ b/java/src/com/android/inputmethod/latin/SuggestedWords.java @@ -16,31 +16,35 @@ package com.android.inputmethod.latin; +import android.text.TextUtils; import android.view.inputmethod.CompletionInfo; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collections; import java.util.HashSet; import java.util.List; public class SuggestedWords { - public static final SuggestedWords EMPTY = new SuggestedWords(false, false, false, false, - Collections.<SuggestedWordInfo>emptyList()); + public static final SuggestedWords EMPTY = new SuggestedWords( + Collections.<SuggestedWordInfo>emptyList(), false, false, false, false); public final boolean mTypedWordValid; public final boolean mHasAutoCorrectionCandidate; public final boolean mIsPunctuationSuggestions; + public final boolean mAllowsToBeAutoCorrected; private final List<SuggestedWordInfo> mSuggestedWordInfoList; - SuggestedWords(boolean typedWordValid, - boolean hasAutoCorrectionCandidate, boolean isPunctuationSuggestions, - boolean shouldBlockAutoCorrectionBySafetyNet, - List<SuggestedWordInfo> suggestedWordInfoList) { + public SuggestedWords(final List<SuggestedWordInfo> suggestedWordInfoList, + final boolean typedWordValid, + final boolean hasAutoCorrectionCandidate, + final boolean allowsToBeAutoCorrected, + final boolean isPunctuationSuggestions) { + mSuggestedWordInfoList = suggestedWordInfoList; mTypedWordValid = typedWordValid; - mHasAutoCorrectionCandidate = hasAutoCorrectionCandidate - && !shouldBlockAutoCorrectionBySafetyNet; + mHasAutoCorrectionCandidate = hasAutoCorrectionCandidate; + mAllowsToBeAutoCorrected = allowsToBeAutoCorrected; mIsPunctuationSuggestions = isPunctuationSuggestions; - mSuggestedWordInfoList = suggestedWordInfoList; } public int size() { @@ -69,104 +73,51 @@ public class SuggestedWords { return "SuggestedWords:" + " mTypedWordValid=" + mTypedWordValid + " mHasAutoCorrectionCandidate=" + mHasAutoCorrectionCandidate - + " mIsPunctuationSuggestions=" + mIsPunctuationSuggestions; + + " mAllowsToBeAutoCorrected=" + mAllowsToBeAutoCorrected + + " mIsPunctuationSuggestions=" + mIsPunctuationSuggestions + + " words=" + Arrays.toString(mSuggestedWordInfoList.toArray()); } - public static class Builder { - private final boolean mTypedWordValid; - private final boolean mHasMinimalSuggestion; - private final boolean mIsPunctuationSuggestions; - private boolean mShouldBlockAutoCorrectionBySafetyNet; - private final boolean mAllowsToBeAutoCorrected; - private final List<SuggestedWordInfo> mSuggestedWordInfoList; - - public Builder(final List<SuggestedWordInfo> suggestedWordInfoList, - final boolean typedWordValid, - final boolean hasMinimalSuggestion, - final boolean allowsToBeAutoCorrected, - final boolean isPunctuationSuggestions) { - mSuggestedWordInfoList = suggestedWordInfoList; - mTypedWordValid = typedWordValid; - mHasMinimalSuggestion = hasMinimalSuggestion; - mAllowsToBeAutoCorrected = allowsToBeAutoCorrected; - mIsPunctuationSuggestions = isPunctuationSuggestions; - } - - public static ArrayList<SuggestedWordInfo> getFromCharSequenceList( - final List<CharSequence> wordList) { - final ArrayList<SuggestedWordInfo> result = new ArrayList<SuggestedWordInfo>(); - for (CharSequence word : wordList) { - if (null != word) result.add(new SuggestedWordInfo(word, null, false)); - } - return result; - } - - public static List<SuggestedWordInfo> getFromApplicationSpecifiedCompletions( - final CompletionInfo[] infos) { - final ArrayList<SuggestedWordInfo> result = new ArrayList<SuggestedWordInfo>(); - for (CompletionInfo info : infos) { - if (null != info) result.add(new SuggestedWordInfo(info.getText(), null, false)); - } - return result; + public static ArrayList<SuggestedWordInfo> getFromCharSequenceList( + final List<CharSequence> wordList) { + final ArrayList<SuggestedWordInfo> result = new ArrayList<SuggestedWordInfo>(); + for (CharSequence word : wordList) { + if (null != word) result.add(new SuggestedWordInfo(word, null, false)); } + return result; + } - public Builder setShouldBlockAutoCorrectionBySafetyNet() { - mShouldBlockAutoCorrectionBySafetyNet = true; - return this; + public static List<SuggestedWordInfo> getFromApplicationSpecifiedCompletions( + final CompletionInfo[] infos) { + final ArrayList<SuggestedWordInfo> result = new ArrayList<SuggestedWordInfo>(); + for (CompletionInfo info : infos) { + if (null != info) result.add(new SuggestedWordInfo(info.getText(), null, false)); } + return result; + } - // Should get rid of the first one (what the user typed previously) from suggestions - // and replace it with what the user currently typed. - public static ArrayList<SuggestedWordInfo> getTypedWordAndPreviousSuggestions( - final CharSequence typedWord, final SuggestedWords previousSuggestions) { - final ArrayList<SuggestedWordInfo> suggestionsList = new ArrayList<SuggestedWordInfo>(); - final HashSet<String> alreadySeen = new HashSet<String>(); - suggestionsList.add(new SuggestedWordInfo(typedWord, null, false)); - alreadySeen.add(typedWord.toString()); - final int previousSize = previousSuggestions.size(); - for (int pos = 1; pos < previousSize; pos++) { - final String prevWord = previousSuggestions.getWord(pos).toString(); - // Filter out duplicate suggestion. - if (!alreadySeen.contains(prevWord)) { - suggestionsList.add(new SuggestedWordInfo(prevWord, null, true)); - alreadySeen.add(prevWord); - } + // Should get rid of the first one (what the user typed previously) from suggestions + // and replace it with what the user currently typed. + public static ArrayList<SuggestedWordInfo> getTypedWordAndPreviousSuggestions( + final CharSequence typedWord, final SuggestedWords previousSuggestions) { + final ArrayList<SuggestedWordInfo> suggestionsList = new ArrayList<SuggestedWordInfo>(); + final HashSet<String> alreadySeen = new HashSet<String>(); + suggestionsList.add(new SuggestedWordInfo(typedWord, null, false)); + alreadySeen.add(typedWord.toString()); + final int previousSize = previousSuggestions.size(); + for (int pos = 1; pos < previousSize; pos++) { + final String prevWord = previousSuggestions.getWord(pos).toString(); + // Filter out duplicate suggestion. + if (!alreadySeen.contains(prevWord)) { + suggestionsList.add(new SuggestedWordInfo(prevWord, null, true)); + alreadySeen.add(prevWord); } - return suggestionsList; - } - - public SuggestedWords build() { - return new SuggestedWords(mTypedWordValid, mHasMinimalSuggestion, - mIsPunctuationSuggestions, mShouldBlockAutoCorrectionBySafetyNet, - mSuggestedWordInfoList); - } - - public int size() { - return mSuggestedWordInfoList.size(); - } - - public CharSequence getWord(int pos) { - return mSuggestedWordInfoList.get(pos).mWord; - } - - public boolean allowsToBeAutoCorrected() { - return mAllowsToBeAutoCorrected; - } - - @Override - public String toString() { - // Pretty-print method to help debug - return "SuggestedWords.Builder:" - + " mTypedWordValid=" + mTypedWordValid - + " mHasMinimalSuggestion=" + mHasMinimalSuggestion - + " mIsPunctuationSuggestions=" + mIsPunctuationSuggestions - + " mShouldBlockAutoCorrectionBySafetyNet=" - + mShouldBlockAutoCorrectionBySafetyNet; } + return suggestionsList; } public static class SuggestedWordInfo { - private final CharSequence mWord; + public final CharSequence mWord; private final CharSequence mDebugString; private final boolean mPreviousSuggestedWord; @@ -194,5 +145,14 @@ public class SuggestedWords { public boolean isObsoleteSuggestedWord () { return mPreviousSuggestedWord; } + + @Override + public String toString() { + if (TextUtils.isEmpty(mDebugString)) { + return mWord.toString(); + } else { + return mWord.toString() + " (" + mDebugString.toString() + ")"; + } + } } } |