diff options
| author | yingleiw <yingleiw@google.com> | 2021-11-02 18:31:40 -0700 |
|---|---|---|
| committer | yingleiw <yingleiw@google.com> | 2021-11-17 20:01:30 -0800 |
| commit | 63ab661d5a8c83ed9f02924f17f79116865275ea (patch) | |
| tree | d40e85fd4298262629154e61118054eead6b10e7 /core/java/android/widget/TextView.java | |
| parent | e551c20dc8a295ebf3b7b729a321210c37e430dd (diff) | |
Send TYPE_VIEW_TEXT_CHANGED a11y event when SuggestionSpan is added
When user types space after a word, we receive a text
change event, but the suggestion span is not added to
the text yet. The spell checker adds the span after the
text change event is sent. Previously we send the event
in onSpanAdded in TextView, but we don't do anything or
update the before text for span removed. This is a bit
confusing and error prone. This change moves the send
event logic into spell checker.
Bug: b/143378480
Test: tested with talkback.
Change-Id: Ibd45843494304602b177df8da520a51058989f10
Diffstat (limited to 'core/java/android/widget/TextView.java')
| -rw-r--r-- | core/java/android/widget/TextView.java | 68 |
1 files changed, 17 insertions, 51 deletions
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java index 8fba58364c94..496fa67498eb 100644 --- a/core/java/android/widget/TextView.java +++ b/core/java/android/widget/TextView.java @@ -12501,6 +12501,11 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener return TextUtils.trimToParcelableSize(mTransformed); } + boolean isVisibleToAccessibility() { + return AccessibilityManager.getInstance(mContext).isEnabled() + && (isFocused() || (isSelected() && isShown())); + } + void sendAccessibilityEventTypeViewTextChanged(CharSequence beforeText, int fromIndex, int removedCount, int addedCount) { AccessibilityEvent event = @@ -12512,6 +12517,16 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener sendAccessibilityEventUnchecked(event); } + void sendAccessibilityEventTypeViewTextChanged(CharSequence beforeText, + int fromIndex, int toIndex) { + AccessibilityEvent event = + AccessibilityEvent.obtain(AccessibilityEvent.TYPE_VIEW_TEXT_CHANGED); + event.setFromIndex(fromIndex); + event.setToIndex(toIndex); + event.setBeforeText(beforeText); + sendAccessibilityEventUnchecked(event); + } + private InputMethodManager getInputMethodManager() { return getContext().getSystemService(InputMethodManager.class); } @@ -13826,10 +13841,9 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener } TextView.this.handleTextChanged(buffer, start, before, after); - if (AccessibilityManager.getInstance(mContext).isEnabled() - && (isFocused() || (isSelected() && isShown()))) { + if (isVisibleToAccessibility()) { sendAccessibilityEventTypeViewTextChanged(mBeforeText, start, before, after); - mBeforeText = TextUtils.stringOrSpannedString(mTransformed); + mBeforeText = null; } } @@ -13857,54 +13871,6 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener Log.v(LOG_TAG, "onSpanAdded s=" + s + " e=" + e + " what=" + what + ": " + buf); } TextView.this.spanChange(buf, what, -1, s, -1, e); - // Note we don't update mBeforeText here. We look for SuggestionSpans added after the - // text content changes. - if (AccessibilityManager.getInstance(mContext).isEnabled() - && (isFocused() || (isSelected() && isShown())) - && (what instanceof SuggestionSpan)) { - // When the user types a new word, and SuggestionSpans on the existing words will be - // removed and added again. We don't need to send out events for existing - // SuggestionSpans. Multiple spans can be placed on the range. - if (mBeforeText instanceof SpannedString) { - final SpannedString beforeSpannedString = (SpannedString) mBeforeText; - if ((beforeSpannedString.getSpanStart(what) == s) - && (beforeSpannedString.getSpanEnd(what) == e)) { - // Exactly same span is found. - return; - } - // Suggestion span couldn't be found. Try to find a suggestion span that has the - // same contents. - SuggestionSpan[] suggestionSpans = beforeSpannedString.getSpans(s, e, - SuggestionSpan.class); - for (final SuggestionSpan suggestionSpan : suggestionSpans) { - final int start = beforeSpannedString.getSpanStart(suggestionSpan); - if (start != s) { - continue; - } - final int end = beforeSpannedString.getSpanEnd(suggestionSpan); - if (end != e) { - continue; - } - if (equalSuggestionSpan(suggestionSpan, (SuggestionSpan) what)) { - return; - } - } - } - AccessibilityEvent event = - AccessibilityEvent.obtain(AccessibilityEvent.TYPE_VIEW_TEXT_CHANGED); - event.setFromIndex(s); - event.setToIndex(e); - event.setBeforeText(mBeforeText); - sendAccessibilityEventUnchecked(event); - } - } - - private boolean equalSuggestionSpan(SuggestionSpan span1, SuggestionSpan span2) { - // We compare flags because flags will determine the underline color. - return Arrays.equals(span1.getSuggestions(), span2.getSuggestions()) - && Objects.equals(span1.getLocaleObject(), span2.getLocaleObject()) - && span1.getLocale().equals(span2.getLocale()) - && (span1.getFlags() == span2.getFlags()); } public void onSpanRemoved(Spannable buf, Object what, int s, int e) { |
