aboutsummaryrefslogtreecommitdiffstats
path: root/tests/src/org/kelar/inputmethod/latin/InputLogicTests.java
diff options
context:
space:
mode:
authorAmin Bandali <bandali@kelar.org>2024-12-16 21:45:41 -0500
committerAmin Bandali <bandali@kelar.org>2025-01-11 14:17:35 -0500
commite9a0e66716dab4dd3184d009d8920de1961efdfa (patch)
tree02dcc096643d74645bf28459c2834c3d4a2ad7f2 /tests/src/org/kelar/inputmethod/latin/InputLogicTests.java
parentfb3b9360d70596d7e921de8bf7d3ca99564a077e (diff)
downloadlatinime-e9a0e66716dab4dd3184d009d8920de1961efdfa.tar.gz
latinime-e9a0e66716dab4dd3184d009d8920de1961efdfa.tar.xz
latinime-e9a0e66716dab4dd3184d009d8920de1961efdfa.zip
Rename to Kelar Keyboard (org.kelar.inputmethod.latin)
Diffstat (limited to 'tests/src/org/kelar/inputmethod/latin/InputLogicTests.java')
-rw-r--r--tests/src/org/kelar/inputmethod/latin/InputLogicTests.java786
1 files changed, 786 insertions, 0 deletions
diff --git a/tests/src/org/kelar/inputmethod/latin/InputLogicTests.java b/tests/src/org/kelar/inputmethod/latin/InputLogicTests.java
new file mode 100644
index 000000000..689ee88bb
--- /dev/null
+++ b/tests/src/org/kelar/inputmethod/latin/InputLogicTests.java
@@ -0,0 +1,786 @@
+/*
+ * 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 org.kelar.inputmethod.latin;
+
+import static android.test.MoreAsserts.assertNotEqual;
+
+import android.text.TextUtils;
+import android.view.inputmethod.BaseInputConnection;
+
+import androidx.test.filters.LargeTest;
+
+import org.kelar.inputmethod.latin.common.Constants;
+import org.kelar.inputmethod.latin.define.DecoderSpecificConstants;
+import org.kelar.inputmethod.latin.settings.Settings;
+
+@LargeTest
+public class InputLogicTests extends InputTestsBase {
+
+ private boolean mNextWordPrediction;
+
+ @Override
+ public void setUp() throws Exception {
+ super.setUp();
+ mNextWordPrediction = getBooleanPreference(Settings.PREF_BIGRAM_PREDICTIONS, true);
+ }
+
+ @Override
+ public void tearDown() throws Exception {
+ setBooleanPreference(Settings.PREF_BIGRAM_PREDICTIONS, mNextWordPrediction, true);
+ super.tearDown();
+ }
+
+ public void testTypeWord() {
+ final String WORD_TO_TYPE = "abcd";
+ type(WORD_TO_TYPE);
+ assertEquals("type word", WORD_TO_TYPE, mEditText.getText().toString());
+ }
+
+ public void testPickSuggestionThenBackspace() {
+ final String WORD_TO_TYPE = "this";
+ final String EXPECTED_RESULT = "thi";
+ type(WORD_TO_TYPE);
+ pickSuggestionManually(WORD_TO_TYPE);
+ sendUpdateForCursorMoveTo(WORD_TO_TYPE.length());
+ type(Constants.CODE_DELETE);
+ assertEquals("press suggestion then backspace", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testPickAutoCorrectionThenBackspace() {
+ final String WORD_TO_TYPE = "tgis";
+ final String WORD_TO_PICK = "this";
+ final String EXPECTED_RESULT = "thi";
+ type(WORD_TO_TYPE);
+ // Choose the auto-correction. For "tgis", the auto-correction should be "this".
+ pickSuggestionManually(WORD_TO_PICK);
+ sendUpdateForCursorMoveTo(WORD_TO_TYPE.length());
+ assertEquals("pick typed word over auto-correction then backspace", WORD_TO_PICK,
+ mEditText.getText().toString());
+ type(Constants.CODE_DELETE);
+ assertEquals("pick typed word over auto-correction then backspace", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testPickTypedWordOverAutoCorrectionThenBackspace() {
+ final String WORD_TO_TYPE = "tgis";
+ final String EXPECTED_RESULT = "tgi";
+ type(WORD_TO_TYPE);
+ // Choose the typed word.
+ pickSuggestionManually(WORD_TO_TYPE);
+ sendUpdateForCursorMoveTo(WORD_TO_TYPE.length());
+ assertEquals("pick typed word over auto-correction then backspace", WORD_TO_TYPE,
+ mEditText.getText().toString());
+ type(Constants.CODE_DELETE);
+ assertEquals("pick typed word over auto-correction then backspace", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testPickDifferentSuggestionThenBackspace() {
+ final String WORD_TO_TYPE = "tgis";
+ final String WORD_TO_PICK = "thus";
+ final String EXPECTED_RESULT = "thu";
+ type(WORD_TO_TYPE);
+ // Choose the second suggestion, which should be "thus" when "tgis" is typed.
+ pickSuggestionManually(WORD_TO_PICK);
+ sendUpdateForCursorMoveTo(WORD_TO_TYPE.length());
+ assertEquals("pick different suggestion then backspace", WORD_TO_PICK,
+ mEditText.getText().toString());
+ type(Constants.CODE_DELETE);
+ assertEquals("pick different suggestion then backspace", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testDeleteSelection() {
+ final String STRING_TO_TYPE = "some text delete me some text";
+ final int typedLength = STRING_TO_TYPE.length();
+ final int SELECTION_START = 10;
+ final int SELECTION_END = 19;
+ final String EXPECTED_RESULT = "some text some text";
+ type(STRING_TO_TYPE);
+ // Don't use the sendUpdateForCursorMove* family of methods here because they
+ // don't handle selections.
+ // Send once to simulate the cursor actually responding to the move caused by typing.
+ // This is necessary because LatinIME is bookkeeping to avoid confusing a real cursor
+ // move with a move triggered by LatinIME inputting stuff.
+ mLatinIME.onUpdateSelection(0, 0, typedLength, typedLength, -1, -1);
+ mInputConnection.setSelection(SELECTION_START, SELECTION_END);
+ // And now we simulate the user actually selecting some text.
+ mLatinIME.onUpdateSelection(typedLength, typedLength,
+ SELECTION_START, SELECTION_END, -1, -1);
+ type(Constants.CODE_DELETE);
+ assertEquals("delete selection", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testDeleteSelectionTwice() {
+ final String STRING_TO_TYPE = "some text delete me some text";
+ final int typedLength = STRING_TO_TYPE.length();
+ final int SELECTION_START = 10;
+ final int SELECTION_END = 19;
+ final String EXPECTED_RESULT = "some text some text";
+ type(STRING_TO_TYPE);
+ // Don't use the sendUpdateForCursorMove* family of methods here because they
+ // don't handle selections.
+ // Send once to simulate the cursor actually responding to the move caused by typing.
+ // This is necessary because LatinIME is bookkeeping to avoid confusing a real cursor
+ // move with a move triggered by LatinIME inputting stuff.
+ mLatinIME.onUpdateSelection(0, 0, typedLength, typedLength, -1, -1);
+ mInputConnection.setSelection(SELECTION_START, SELECTION_END);
+ // And now we simulate the user actually selecting some text.
+ mLatinIME.onUpdateSelection(typedLength, typedLength,
+ SELECTION_START, SELECTION_END, -1, -1);
+ type(Constants.CODE_DELETE);
+ type(Constants.CODE_DELETE);
+ assertEquals("delete selection twice", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testAutoCorrect() {
+ final String STRING_TO_TYPE = "tgis ";
+ final String EXPECTED_RESULT = "this ";
+ type(STRING_TO_TYPE);
+ assertEquals("simple auto-correct", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectWithQuote() {
+ final String STRING_TO_TYPE = "didn' ";
+ final String EXPECTED_RESULT = "didn't ";
+ type(STRING_TO_TYPE);
+ assertEquals("auto-correct with quote", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectWithPeriod() {
+ final String STRING_TO_TYPE = "tgis.";
+ final String EXPECTED_RESULT = "this.";
+ type(STRING_TO_TYPE);
+ assertEquals("auto-correct with period", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectWithPeriodThenRevert() {
+ final String STRING_TO_TYPE = "tgis.";
+ final String EXPECTED_RESULT = "tgis.";
+ type(STRING_TO_TYPE);
+ sendUpdateForCursorMoveTo(STRING_TO_TYPE.length());
+ type(Constants.CODE_DELETE);
+ assertEquals("auto-correct with period then revert", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectWithSpaceThenRevert() {
+ // Backspacing to cancel the "tgis"->"this" autocorrection should result in
+ // a "phantom space": if the user presses space immediately after,
+ // only one space will be inserted in total.
+ final String STRING_TO_TYPE = "tgis ";
+ final String EXPECTED_RESULT = "tgis";
+ type(STRING_TO_TYPE);
+ sendUpdateForCursorMoveTo(STRING_TO_TYPE.length());
+ type(Constants.CODE_DELETE);
+ assertEquals("auto-correct with space then revert", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectWithSpaceThenRevertThenTypeMore() {
+ final String STRING_TO_TYPE_FIRST = "tgis ";
+ final String STRING_TO_TYPE_SECOND = "a";
+ final String EXPECTED_RESULT = "tgis a";
+ type(STRING_TO_TYPE_FIRST);
+ sendUpdateForCursorMoveTo(STRING_TO_TYPE_FIRST.length());
+ type(Constants.CODE_DELETE);
+
+ type(STRING_TO_TYPE_SECOND);
+ sendUpdateForCursorMoveTo(STRING_TO_TYPE_FIRST.length() - 1
+ + STRING_TO_TYPE_SECOND.length());
+ assertEquals("auto-correct with space then revert then type more", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectToSelfDoesNotRevert() {
+ final String STRING_TO_TYPE = "this ";
+ final String EXPECTED_RESULT = "this";
+ type(STRING_TO_TYPE);
+ sendUpdateForCursorMoveTo(STRING_TO_TYPE.length());
+ type(Constants.CODE_DELETE);
+ assertEquals("auto-correct with space does not revert", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testDoubleSpace() {
+ // U+1F607 is an emoji
+ final String[] STRINGS_TO_TYPE =
+ new String[] { "this ", "a+ ", "\u1F607 ", ".. ", ") ", "( ", "% " };
+ final String[] EXPECTED_RESULTS =
+ new String[] { "this. ", "a+. ", "\u1F607. ", ".. ", "). ", "( ", "%. " };
+ verifyDoubleSpace(STRINGS_TO_TYPE, EXPECTED_RESULTS);
+ }
+
+ public void testDoubleSpaceHindi() {
+ changeLanguage("hi");
+ // U+1F607 is an emoji
+ final String[] STRINGS_TO_TYPE =
+ new String[] { "this ", "a+ ", "\u1F607 ", "|| ", ") ", "( ", "% " };
+ final String[] EXPECTED_RESULTS =
+ new String[] { "this| ", "a+| ", "\u1F607| ", "|| ", ")| ", "( ", "%| " };
+ verifyDoubleSpace(STRINGS_TO_TYPE, EXPECTED_RESULTS);
+ }
+
+ private void verifyDoubleSpace(String[] stringsToType, String[] expectedResults) {
+ // Set default pref just in case
+ setBooleanPreference(Settings.PREF_KEY_USE_DOUBLE_SPACE_PERIOD, true, true);
+ for (int i = 0; i < stringsToType.length; ++i) {
+ mEditText.setText("");
+ type(stringsToType[i]);
+ assertEquals("double space processing", expectedResults[i],
+ mEditText.getText().toString());
+ }
+ }
+
+ public void testCancelDoubleSpaceEnglish() {
+ final String STRING_TO_TYPE = "this ";
+ final String EXPECTED_RESULT = "this ";
+ type(STRING_TO_TYPE);
+ type(Constants.CODE_DELETE);
+ assertEquals("double space make a period", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testCancelDoubleSpaceHindi() {
+ changeLanguage("hi");
+ final String STRING_TO_TYPE = "this ";
+ final String EXPECTED_RESULT = "this ";
+ type(STRING_TO_TYPE);
+ type(Constants.CODE_DELETE);
+ assertEquals("double space make a period", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ private void testDoubleSpacePeriodWithSettings(final boolean expectsPeriod,
+ final Object... settingsKeysValues) {
+ final Object[] oldSettings = new Object[settingsKeysValues.length / 2];
+ final String STRING_WITHOUT_PERIOD = "this ";
+ final String STRING_WITH_PERIOD = "this. ";
+ final String EXPECTED_RESULT = expectsPeriod ? STRING_WITH_PERIOD : STRING_WITHOUT_PERIOD;
+ try {
+ for (int i = 0; i < settingsKeysValues.length; i += 2) {
+ if (settingsKeysValues[i + 1] instanceof String) {
+ oldSettings[i / 2] = setStringPreference((String)settingsKeysValues[i],
+ (String)settingsKeysValues[i + 1], "0");
+ } else {
+ oldSettings[i / 2] = setBooleanPreference((String)settingsKeysValues[i],
+ (Boolean)settingsKeysValues[i + 1], false);
+ }
+ }
+ mLatinIME.loadSettings();
+ mEditText.setText("");
+ type(STRING_WITHOUT_PERIOD);
+ assertEquals("double-space-to-period with specific settings "
+ + TextUtils.join(" ", settingsKeysValues),
+ EXPECTED_RESULT, mEditText.getText().toString());
+ } finally {
+ // Restore old settings
+ for (int i = 0; i < settingsKeysValues.length; i += 2) {
+ if (null == oldSettings[i / 2]) {
+ break;
+ } if (oldSettings[i / 2] instanceof String) {
+ setStringPreference((String)settingsKeysValues[i], (String)oldSettings[i / 2],
+ "");
+ } else {
+ setBooleanPreference((String)settingsKeysValues[i], (Boolean)oldSettings[i / 2],
+ false);
+ }
+ }
+ }
+ }
+
+ public void testDoubleSpacePeriod() {
+ // Reset settings to default, else these tests will go flaky.
+ setBooleanPreference(Settings.PREF_SHOW_SUGGESTIONS, true, true);
+ setBooleanPreference(Settings.PREF_AUTO_CORRECTION, true, true);
+ setBooleanPreference(Settings.PREF_KEY_USE_DOUBLE_SPACE_PERIOD, true, true);
+ testDoubleSpacePeriodWithSettings(true);
+ // "Suggestion visibility" to off
+ testDoubleSpacePeriodWithSettings(true, Settings.PREF_SHOW_SUGGESTIONS, false);
+ // "Suggestion visibility" to on
+ testDoubleSpacePeriodWithSettings(true, Settings.PREF_SHOW_SUGGESTIONS, true);
+
+ // "Double-space period" to "off"
+ testDoubleSpacePeriodWithSettings(false, Settings.PREF_KEY_USE_DOUBLE_SPACE_PERIOD, false);
+
+ // "Auto-correction" to "off"
+ testDoubleSpacePeriodWithSettings(true, Settings.PREF_AUTO_CORRECTION, false);
+ // "Auto-correction" to "on"
+ testDoubleSpacePeriodWithSettings(true, Settings.PREF_AUTO_CORRECTION, true);
+
+ // "Suggestion visibility" to "always hide" and "Auto-correction" to "off"
+ testDoubleSpacePeriodWithSettings(true, Settings.PREF_SHOW_SUGGESTIONS, false,
+ Settings.PREF_AUTO_CORRECTION, false);
+ // "Suggestion visibility" to "always hide" and "Auto-correction" to "off"
+ testDoubleSpacePeriodWithSettings(false, Settings.PREF_SHOW_SUGGESTIONS, false,
+ Settings.PREF_AUTO_CORRECTION, false,
+ Settings.PREF_KEY_USE_DOUBLE_SPACE_PERIOD, false);
+ }
+
+ public void testBackspaceAtStartAfterAutocorrect() {
+ final String STRING_TO_TYPE = "tgis ";
+ final int typedLength = STRING_TO_TYPE.length();
+ final String EXPECTED_RESULT = "this ";
+ final int NEW_CURSOR_POSITION = 0;
+ type(STRING_TO_TYPE);
+ sendUpdateForCursorMoveTo(typedLength);
+ mInputConnection.setSelection(NEW_CURSOR_POSITION, NEW_CURSOR_POSITION);
+ sendUpdateForCursorMoveTo(NEW_CURSOR_POSITION);
+ type(Constants.CODE_DELETE);
+ assertEquals("auto correct then move cursor to start of line then backspace",
+ EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testAutoCorrectThenMoveCursorThenBackspace() {
+ final String STRING_TO_TYPE = "and tgis ";
+ final int typedLength = STRING_TO_TYPE.length();
+ final String EXPECTED_RESULT = "andthis ";
+ final int NEW_CURSOR_POSITION = STRING_TO_TYPE.indexOf('t');
+ type(STRING_TO_TYPE);
+ sendUpdateForCursorMoveTo(typedLength);
+ mInputConnection.setSelection(NEW_CURSOR_POSITION, NEW_CURSOR_POSITION);
+ sendUpdateForCursorMoveTo(NEW_CURSOR_POSITION);
+ type(Constants.CODE_DELETE);
+ assertEquals("auto correct then move cursor then backspace",
+ EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testNoSpaceAfterManualPick() {
+ final String WORD_TO_TYPE = "this";
+ final String EXPECTED_RESULT = WORD_TO_TYPE;
+ type(WORD_TO_TYPE);
+ pickSuggestionManually(WORD_TO_TYPE);
+ assertEquals("no space after manual pick", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testManualPickThenType() {
+ final String WORD1_TO_TYPE = "this";
+ final String WORD2_TO_TYPE = "is";
+ final String EXPECTED_RESULT = "this is";
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ type(WORD2_TO_TYPE);
+ assertEquals("manual pick then type", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testManualPickThenSeparator() {
+ final String WORD1_TO_TYPE = "this";
+ final String WORD2_TO_TYPE = "!";
+ final String EXPECTED_RESULT = "this!";
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ type(WORD2_TO_TYPE);
+ assertEquals("manual pick then separator", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ // This test matches testClusteringPunctuationForFrench.
+ // In some non-English languages, ! and ? are clustering punctuation signs.
+ public void testClusteringPunctuation() {
+ final String WORD1_TO_TYPE = "test";
+ final String WORD2_TO_TYPE = "!!?!:!";
+ final String EXPECTED_RESULT = "test!!?!:!";
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ type(WORD2_TO_TYPE);
+ assertEquals("clustering punctuation", EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testManualPickThenStripperThenPick() {
+ final String WORD_TO_TYPE = "this";
+ final String STRIPPER = "\n";
+ final String EXPECTED_RESULT = "this\nthis";
+ type(WORD_TO_TYPE);
+ pickSuggestionManually(WORD_TO_TYPE);
+ type(STRIPPER);
+ type(WORD_TO_TYPE);
+ pickSuggestionManually(WORD_TO_TYPE);
+ assertEquals("manual pick then \\n then manual pick", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testManualPickThenSpaceThenType() {
+ final String WORD1_TO_TYPE = "this";
+ final String WORD2_TO_TYPE = " is";
+ final String EXPECTED_RESULT = "this is";
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ type(WORD2_TO_TYPE);
+ assertEquals("manual pick then space then type", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testManualPickThenManualPick() {
+ final String WORD1_TO_TYPE = "this";
+ final String WORD2_TO_PICK = "is";
+ final String EXPECTED_RESULT = "this is";
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ // Here we fake picking a word through bigram prediction.
+ pickSuggestionManually(WORD2_TO_PICK);
+ assertEquals("manual pick then manual pick", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testDeleteWholeComposingWord() {
+ final String WORD_TO_TYPE = "this";
+ type(WORD_TO_TYPE);
+ for (int i = 0; i < WORD_TO_TYPE.length(); ++i) {
+ type(Constants.CODE_DELETE);
+ }
+ assertEquals("delete whole composing word", "", mEditText.getText().toString());
+ }
+
+ public void testResumeSuggestionOnBackspace() {
+ final String STRING_TO_TYPE = "and this ";
+ final int typedLength = STRING_TO_TYPE.length();
+ type(STRING_TO_TYPE);
+ assertEquals("resume suggestion on backspace", -1,
+ BaseInputConnection.getComposingSpanStart(mEditText.getText()));
+ assertEquals("resume suggestion on backspace", -1,
+ BaseInputConnection.getComposingSpanEnd(mEditText.getText()));
+ sendUpdateForCursorMoveTo(typedLength);
+ type(Constants.CODE_DELETE);
+ assertEquals("resume suggestion on backspace", 4,
+ BaseInputConnection.getComposingSpanStart(mEditText.getText()));
+ assertEquals("resume suggestion on backspace", 8,
+ BaseInputConnection.getComposingSpanEnd(mEditText.getText()));
+ }
+
+ private void helperTestComposing(final String wordToType, final boolean shouldBeComposing) {
+ mEditText.setText("");
+ type(wordToType);
+ assertEquals("start composing inside text", shouldBeComposing ? 0 : -1,
+ BaseInputConnection.getComposingSpanStart(mEditText.getText()));
+ assertEquals("start composing inside text", shouldBeComposing ? wordToType.length() : -1,
+ BaseInputConnection.getComposingSpanEnd(mEditText.getText()));
+ }
+
+ public void testStartComposing() {
+ // Should start composing on a letter
+ helperTestComposing("a", true);
+ type(" "); // To reset the composing state
+ // Should not start composing on quote
+ helperTestComposing("'", false);
+ type(" ");
+ helperTestComposing("'-", false);
+ type(" ");
+ // Should not start composing on dash
+ helperTestComposing("-", false);
+ type(" ");
+ helperTestComposing("-'", false);
+ type(" ");
+ helperTestComposing("a-", true);
+ type(" ");
+ helperTestComposing("a'", true);
+ }
+
+ // TODO: Add some tests for non-BMP characters
+
+ public void testAutoCorrectByUserHistory() {
+ type("qpmz");
+ type(Constants.CODE_SPACE);
+
+ int startIndex = mEditText.getText().length();
+ type("qpmx");
+ type(Constants.CODE_SPACE);
+ int endIndex = mEditText.getText().length();
+ assertEquals("auto-corrected by user history",
+ "qpmz ", mEditText.getText().subSequence(startIndex, endIndex).toString());
+ }
+
+ public void testPredictionsAfterSpace() {
+ final String WORD_TO_TYPE = "Barack ";
+ type(WORD_TO_TYPE);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ // Test the first prediction is displayed
+ final SuggestedWords suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ assertEquals("predictions after space", "Obama",
+ suggestedWords.size() > 0 ? suggestedWords.getWord(0) : null);
+ }
+
+ public void testPredictionsWithDoubleSpaceToPeriod() {
+ mLatinIME.clearPersonalizedDictionariesForTest();
+ final String WORD_TO_TYPE = "Barack ";
+ type(WORD_TO_TYPE);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+
+ type(Constants.CODE_DELETE);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+
+ SuggestedWords suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ assertEquals("predictions after cancel double-space-to-period", "Obama",
+ mLatinIME.getSuggestedWordsForTest().getWord(0));
+ }
+
+ public void testPredictionsAfterManualPick() {
+ final String WORD_TO_TYPE = "Barack";
+ type(WORD_TO_TYPE);
+ // Choose the auto-correction. For "Barack", the auto-correction should be "Barack".
+ pickSuggestionManually(WORD_TO_TYPE);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ // Test the first prediction is displayed
+ final SuggestedWords suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ assertEquals("predictions after manual pick", "Obama",
+ suggestedWords.size() > 0 ? suggestedWords.getWord(0) : null);
+ }
+
+ public void testPredictionsAfterPeriod() {
+ mLatinIME.clearPersonalizedDictionariesForTest();
+ final String WORD_TO_TYPE = "Barack. ";
+ type(WORD_TO_TYPE);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+
+ SuggestedWords suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ assertFalse(mLatinIME.getSuggestedWordsForTest().isEmpty());
+ }
+
+ public void testPredictionsAfterRecorrection() {
+ final String PREFIX = "A ";
+ final String WORD_TO_TYPE = "Barack";
+ final String FIRST_NON_TYPED_SUGGESTION = "Barrack";
+ final int endOfPrefix = PREFIX.length();
+ final int endOfWord = endOfPrefix + WORD_TO_TYPE.length();
+ final int endOfSuggestion = endOfPrefix + FIRST_NON_TYPED_SUGGESTION.length();
+ final int indexForManualCursor = endOfPrefix + 3; // +3 because it's after "Bar" in "Barack"
+ type(PREFIX);
+ sendUpdateForCursorMoveTo(endOfPrefix);
+ type(WORD_TO_TYPE);
+ pickSuggestionManually(FIRST_NON_TYPED_SUGGESTION);
+ sendUpdateForCursorMoveTo(endOfSuggestion);
+ runMessages();
+ type(" ");
+ sendUpdateForCursorMoveBy(1);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ // Simulate a manual cursor move
+ mInputConnection.setSelection(indexForManualCursor, indexForManualCursor);
+ sendUpdateForCursorMoveTo(indexForManualCursor);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ pickSuggestionManually(WORD_TO_TYPE);
+ sendUpdateForCursorMoveTo(endOfWord);
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ // Test the first prediction is displayed
+ final SuggestedWords suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ assertEquals("predictions after recorrection", "Obama",
+ suggestedWords.size() > 0 ? suggestedWords.getWord(0) : null);
+ }
+
+ public void testComposingMultipleBackspace() {
+ final String WORD_TO_TYPE = "radklro";
+ final int TIMES_TO_TYPE = 3;
+ final int TIMES_TO_BACKSPACE = 8;
+ type(WORD_TO_TYPE);
+ type(Constants.CODE_DELETE);
+ type(Constants.CODE_DELETE);
+ type(Constants.CODE_DELETE);
+ type(WORD_TO_TYPE);
+ type(Constants.CODE_DELETE);
+ type(Constants.CODE_DELETE);
+ type(WORD_TO_TYPE);
+ type(Constants.CODE_DELETE);
+ type(Constants.CODE_DELETE);
+ type(Constants.CODE_DELETE);
+ assertEquals("composing with multiple backspace",
+ WORD_TO_TYPE.length() * TIMES_TO_TYPE - TIMES_TO_BACKSPACE,
+ mEditText.getText().length());
+ }
+
+ public void testManySingleQuotes() {
+ final String WORD_TO_AUTOCORRECT = "i";
+ final String WORD_AUTOCORRECTED = "I";
+ final String QUOTES = "''''''''''''''''''''";
+ final String WORD_TO_TYPE = WORD_TO_AUTOCORRECT + QUOTES + " ";
+ final String EXPECTED_RESULT = WORD_AUTOCORRECTED + QUOTES + " ";
+ type(WORD_TO_TYPE);
+ assertEquals("auto-correct with many trailing single quotes", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testManySingleQuotesOneByOne() {
+ final String WORD_TO_AUTOCORRECT = "i";
+ final String WORD_AUTOCORRECTED = "I";
+ final String QUOTES = "''''''''''''''''''''";
+ final String WORD_TO_TYPE = WORD_TO_AUTOCORRECT + QUOTES + " ";
+ final String EXPECTED_RESULT = WORD_AUTOCORRECTED + QUOTES + " ";
+
+ for (int i = 0; i < WORD_TO_TYPE.length(); ++i) {
+ type(WORD_TO_TYPE.substring(i, i+1));
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ }
+ assertEquals("type many trailing single quotes one by one", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testTypingSingleQuotesOneByOne() {
+ final String WORD_TO_TYPE = "it's ";
+ final String EXPECTED_RESULT = WORD_TO_TYPE;
+ for (int i = 0; i < WORD_TO_TYPE.length(); ++i) {
+ type(WORD_TO_TYPE.substring(i, i+1));
+ sleep(DELAY_TO_WAIT_FOR_PREDICTIONS_MILLIS);
+ runMessages();
+ }
+ assertEquals("type words letter by letter", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testBasicGesture() {
+ gesture("this");
+ assertEquals("this", mEditText.getText().toString());
+ }
+
+ public void testGestureGesture() {
+ gesture("got");
+ gesture("milk");
+ assertEquals("got milk", mEditText.getText().toString());
+ }
+
+ public void testGestureBackspaceGestureAgain() {
+ gesture("this");
+ type(Constants.CODE_DELETE);
+ assertEquals("gesture then backspace", "", mEditText.getText().toString());
+ gesture("this");
+ if (DecoderSpecificConstants.SHOULD_REMOVE_PREVIOUSLY_REJECTED_SUGGESTION) {
+ assertNotEqual("this", mEditText.getText().toString());
+ } else {
+ assertEquals("this", mEditText.getText().toString());
+ }
+ }
+
+ private void typeOrGestureWordAndPutCursorInside(final boolean gesture, final String word,
+ final int startPos) {
+ final int END_OF_WORD = startPos + word.length();
+ final int NEW_CURSOR_POSITION = startPos + word.length() / 2;
+ if (gesture) {
+ gesture(word);
+ } else {
+ type(word);
+ }
+ sendUpdateForCursorMoveTo(END_OF_WORD);
+ runMessages();
+ sendUpdateForCursorMoveTo(NEW_CURSOR_POSITION);
+ sleep(DELAY_TO_WAIT_FOR_UNDERLINE_MILLIS);
+ runMessages();
+ }
+
+ private void typeWordAndPutCursorInside(final String word, final int startPos) {
+ typeOrGestureWordAndPutCursorInside(false /* gesture */, word, startPos);
+ }
+
+ private void gestureWordAndPutCursorInside(final String word, final int startPos) {
+ typeOrGestureWordAndPutCursorInside(true /* gesture */, word, startPos);
+ }
+
+ private void ensureComposingSpanPos(final String message, final int from, final int to) {
+ assertEquals(message, from, BaseInputConnection.getComposingSpanStart(mEditText.getText()));
+ assertEquals(message, to, BaseInputConnection.getComposingSpanEnd(mEditText.getText()));
+ }
+
+ public void testTypeWithinComposing() {
+ final String WORD_TO_TYPE = "something";
+ final String EXPECTED_RESULT = "some thing";
+ typeWordAndPutCursorInside(WORD_TO_TYPE, 0 /* startPos */);
+ type(" ");
+ ensureComposingSpanPos("space while in the middle of a word cancels composition", -1, -1);
+ assertEquals("space in the middle of a composing word", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ int cursorPos = sendUpdateForCursorMoveToEndOfLine();
+ runMessages();
+ type(" ");
+ assertEquals("mbo", "some thing ", mEditText.getText().toString());
+ typeWordAndPutCursorInside(WORD_TO_TYPE, cursorPos + 1 /* startPos */);
+ type(Constants.CODE_DELETE);
+ ensureComposingSpanPos("delete while in the middle of a word cancels composition", -1, -1);
+ }
+
+ public void testTypeWithinGestureComposing() {
+ final String WORD_TO_TYPE = "something";
+ final String EXPECTED_RESULT = "some thing";
+ gestureWordAndPutCursorInside(WORD_TO_TYPE, 0 /* startPos */);
+ type(" ");
+ ensureComposingSpanPos("space while in the middle of a word cancels composition", -1, -1);
+ assertEquals("space in the middle of a composing word", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ int cursorPos = sendUpdateForCursorMoveToEndOfLine();
+ runMessages();
+ type(" ");
+ typeWordAndPutCursorInside(WORD_TO_TYPE, cursorPos + 1 /* startPos */);
+ type(Constants.CODE_DELETE);
+ sleep(DELAY_TO_WAIT_FOR_UNDERLINE_MILLIS);
+ ensureComposingSpanPos("delete while in the middle of a word cancels composition", -1, -1);
+ }
+
+ public void testManualPickThenSeparatorForFrench() {
+ final String WORD1_TO_TYPE = "test";
+ final String WORD2_TO_TYPE = "!";
+ final String EXPECTED_RESULT = "test !";
+ changeLanguage("fr");
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ type(WORD2_TO_TYPE);
+ assertEquals("manual pick then separator for French", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testClusteringPunctuationForFrench() {
+ final String WORD1_TO_TYPE = "test";
+ final String WORD2_TO_TYPE = "!!?!:!";
+ // In English, the expected result would be "test!!?!:!"
+ final String EXPECTED_RESULT = "test !!?! : !";
+ changeLanguage("fr");
+ type(WORD1_TO_TYPE);
+ pickSuggestionManually(WORD1_TO_TYPE);
+ type(WORD2_TO_TYPE);
+ assertEquals("clustering punctuation for French", EXPECTED_RESULT,
+ mEditText.getText().toString());
+ }
+
+ public void testWordThenSpaceThenPunctuationFromStripTwice() {
+ setBooleanPreference(Settings.PREF_BIGRAM_PREDICTIONS, false, true);
+
+ final String WORD_TO_TYPE = "test ";
+ final String PUNCTUATION_FROM_STRIP = "!";
+ final String EXPECTED_RESULT = "test!! ";
+ type(WORD_TO_TYPE);
+ sleep(DELAY_TO_WAIT_FOR_UNDERLINE_MILLIS);
+ runMessages();
+ assertTrue("type word then type space should display punctuation strip",
+ mLatinIME.getSuggestedWordsForTest().isPunctuationSuggestions());
+ pickSuggestionManually(PUNCTUATION_FROM_STRIP);
+ pickSuggestionManually(PUNCTUATION_FROM_STRIP);
+ assertEquals(EXPECTED_RESULT, mEditText.getText().toString());
+ }
+
+ public void testWordThenSpaceDisplaysPredictions() {
+ final String WORD_TO_TYPE = "Barack ";
+ final String EXPECTED_RESULT = "Obama";
+ type(WORD_TO_TYPE);
+ sleep(DELAY_TO_WAIT_FOR_UNDERLINE_MILLIS);
+ runMessages();
+ final SuggestedWords suggestedWords = mLatinIME.getSuggestedWordsForTest();
+ assertEquals("type word then type space yields predictions for French",
+ EXPECTED_RESULT, suggestedWords.size() > 0 ? suggestedWords.getWord(0) : null);
+ }
+}