Refactor text range to be able to get spans larger than the word

This changes how the Range class stores its data, but not its
functionality. It also improves encapsulation a bit.

Bug: 8839763
Bug: 8862327
Change-Id: I5bd583b3fc96a99b93a2632882d8fd587c03ab76
This commit is contained in:
Jean Chalard 2013-06-20 18:58:58 +09:00
parent 564ad4927c
commit e8c4b99e56
2 changed files with 34 additions and 26 deletions

View File

@ -2495,11 +2495,13 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
if (null == range) return; // Happens if we don't have an input connection at all if (null == range) return; // Happens if we don't have an input connection at all
// If for some strange reason (editor bug or so) we measure the text before the cursor as // If for some strange reason (editor bug or so) we measure the text before the cursor as
// longer than what the entire text is supposed to be, the safe thing to do is bail out. // longer than what the entire text is supposed to be, the safe thing to do is bail out.
if (range.mCharsBefore > mLastSelectionStart) return; final int numberOfCharsInWordBeforeCursor = range.getNumberOfCharsInWordBeforeCursor();
if (numberOfCharsInWordBeforeCursor > mLastSelectionStart) return;
final ArrayList<SuggestedWordInfo> suggestions = CollectionUtils.newArrayList(); final ArrayList<SuggestedWordInfo> suggestions = CollectionUtils.newArrayList();
final String typedWord = range.mWord.toString(); final CharSequence word = range.mWord;
if (range.mWord instanceof SpannableString) { final String typedWord = word.toString();
final SpannableString spannableString = (SpannableString)range.mWord; if (word instanceof SpannableString) {
final SpannableString spannableString = (SpannableString)word;
int i = 0; int i = 0;
for (Object object : spannableString.getSpans(0, spannableString.length(), for (Object object : spannableString.getSpans(0, spannableString.length(),
SuggestionSpan.class)) { SuggestionSpan.class)) {
@ -2515,9 +2517,10 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
} }
} }
mWordComposer.setComposingWord(typedWord, mKeyboardSwitcher.getKeyboard()); mWordComposer.setComposingWord(typedWord, mKeyboardSwitcher.getKeyboard());
mWordComposer.setCursorPositionWithinWord(range.mCharsBefore); mWordComposer.setCursorPositionWithinWord(numberOfCharsInWordBeforeCursor);
mConnection.setComposingRegion(mLastSelectionStart - range.mCharsBefore, mConnection.setComposingRegion(
mLastSelectionEnd + range.mCharsAfter); mLastSelectionStart - numberOfCharsInWordBeforeCursor,
mLastSelectionEnd + range.getNumberOfCharsInWordAfterCursor());
final SuggestedWords suggestedWords; final SuggestedWords suggestedWords;
if (suggestions.isEmpty()) { if (suggestions.isEmpty()) {
// We come here if there weren't any suggestion spans on this word. We will try to // We come here if there weren't any suggestion spans on this word. We will try to

View File

@ -17,7 +17,6 @@
package com.android.inputmethod.latin; package com.android.inputmethod.latin;
import android.inputmethodservice.InputMethodService; import android.inputmethodservice.InputMethodService;
import android.text.SpannableString;
import android.text.TextUtils; import android.text.TextUtils;
import android.util.Log; import android.util.Log;
import android.view.KeyEvent; import android.view.KeyEvent;
@ -441,25 +440,33 @@ public final class RichInputConnection {
* Represents a range of text, relative to the current cursor position. * Represents a range of text, relative to the current cursor position.
*/ */
public static final class Range { public static final class Range {
/** Characters before selection start */ private final CharSequence mTextAtCursor;
public final int mCharsBefore; private final int mWordAtCursorStartIndex;
private final int mWordAtCursorEndIndex;
private final int mCursorIndex;
/**
* Characters after selection start, including one trailing word
* separator.
*/
public final int mCharsAfter;
/** The actual characters that make up a word */
public final CharSequence mWord; public final CharSequence mWord;
public Range(int charsBefore, int charsAfter, CharSequence word) { public int getNumberOfCharsInWordBeforeCursor() {
if (charsBefore < 0 || charsAfter < 0) { return mCursorIndex - mWordAtCursorStartIndex;
}
public int getNumberOfCharsInWordAfterCursor() {
return mWordAtCursorEndIndex - mCursorIndex;
}
public Range(final CharSequence textAtCursor, final int wordAtCursorStartIndex,
final int wordAtCursorEndIndex, final int cursorIndex) {
if (wordAtCursorStartIndex < 0 || cursorIndex < wordAtCursorStartIndex
|| cursorIndex > wordAtCursorEndIndex
|| wordAtCursorEndIndex > textAtCursor.length()) {
throw new IndexOutOfBoundsException(); throw new IndexOutOfBoundsException();
} }
this.mCharsBefore = charsBefore; mTextAtCursor = textAtCursor;
this.mCharsAfter = charsAfter; mWordAtCursorStartIndex = wordAtCursorStartIndex;
this.mWord = word; mWordAtCursorEndIndex = wordAtCursorEndIndex;
mCursorIndex = cursorIndex;
mWord = mTextAtCursor.subSequence(mWordAtCursorStartIndex, mWordAtCursorEndIndex);
} }
} }
@ -571,10 +578,8 @@ public final class RichInputConnection {
} }
} }
final SpannableString word = new SpannableString(TextUtils.concat( return new Range(TextUtils.concat(before, after), startIndexInBefore,
before.subSequence(startIndexInBefore, before.length()), before.length() + endIndexInAfter, before.length());
after.subSequence(0, endIndexInAfter)));
return new Range(before.length() - startIndexInBefore, endIndexInAfter, word);
} }
public boolean isCursorTouchingWord(final SettingsValues settingsValues) { public boolean isCursorTouchingWord(final SettingsValues settingsValues) {