diff options
-rw-r--r-- | core/java/android/widget/TextView.java | 82 | ||||
-rw-r--r-- | core/res/res/values/attrs.xml | 3 |
2 files changed, 57 insertions, 28 deletions
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java index b5d994dc7c81..3e6d121ba4c8 100644 --- a/core/java/android/widget/TextView.java +++ b/core/java/android/widget/TextView.java @@ -3366,10 +3366,17 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener } /** - * Sets whether the movement method will automatically be set to - * {@link LinkMovementMethod} if {@link #setAutoLinkMask} has been - * set to nonzero and links are detected in {@link #setText}. - * The default is true. + * Sets whether the movement method will automatically be set to {@link LinkMovementMethod} + * after {@link #setText} or {@link #append} is called. The movement method is set if one of the + * following is true: + * <ul> + * <li>{@link #setAutoLinkMask} has been set to nonzero and links are detected in + * {@link #setText} or {@link #append}. + * <li>The input for {@link #setText} or {@link #append} contains a {@link ClickableSpan}. + * </ul> + * + * <p>This function does not have an immediate effect, movement method will be set only after a + * call to {@link #setText} or {@link #append}. The default is true.</p> * * @attr ref android.R.styleable#TextView_linksClickable */ @@ -3379,10 +3386,14 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener } /** - * Returns whether the movement method will automatically be set to - * {@link LinkMovementMethod} if {@link #setAutoLinkMask} has been - * set to nonzero and links are detected in {@link #setText}. - * The default is true. + * Returns whether the movement method will automatically be set to {@link LinkMovementMethod} + * after {@link #setText} or {@link #append} is called. + * + * See {@link #setLinksClickable} for details. + * + * <p>The default is true.</p> + * + * @see #setLinksClickable * * @attr ref android.R.styleable#TextView_linksClickable */ @@ -3976,13 +3987,19 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener ((Editable) mText).append(text, start, end); + boolean hasClickableSpans = false; if (mAutoLinkMask != 0) { - boolean linksWereAdded = Linkify.addLinks((Spannable) mText, mAutoLinkMask); - // Do not change the movement method for text that support text selection as it - // would prevent an arbitrary cursor displacement. - if (linksWereAdded && mLinksClickable && !textCanBeSelected()) { - setMovementMethod(LinkMovementMethod.getInstance()); - } + hasClickableSpans = Linkify.addLinks((Spannable) mText, mAutoLinkMask); + } else if (mLinksClickable && text instanceof Spanned) { + ClickableSpan[] clickableSpans = + ((Spanned) text).getSpans(0, text.length(), ClickableSpan.class); + hasClickableSpans = clickableSpans != null && clickableSpans.length > 0; + } + + // Do not change the movement method for text that supports text selection as it + // would prevent an arbitrary cursor displacement. + if (hasClickableSpans && mLinksClickable && !textCanBeSelected()) { + setMovementMethod(LinkMovementMethod.getInstance()); } } @@ -4327,6 +4344,7 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener text = TextUtils.stringOrSpannedString(text); } + boolean hasClickableSpans = false; if (mAutoLinkMask != 0) { Spannable s2; @@ -4336,22 +4354,32 @@ public class TextView extends View implements ViewTreeObserver.OnPreDrawListener s2 = mSpannableFactory.newSpannable(text); } - if (Linkify.addLinks(s2, mAutoLinkMask)) { + hasClickableSpans = Linkify.addLinks(s2, mAutoLinkMask); + if (hasClickableSpans) { text = s2; - type = (type == BufferType.EDITABLE) ? BufferType.EDITABLE : BufferType.SPANNABLE; + } + } else if (mLinksClickable && text instanceof Spanned) { + ClickableSpan[] clickableSpans = + ((Spanned) text).getSpans(0, text.length(), ClickableSpan.class); + hasClickableSpans = clickableSpans != null && clickableSpans.length > 0; + if (hasClickableSpans && !(text instanceof Spannable)) { + text = mSpannableFactory.newSpannable(text); + } + } - /* - * We must go ahead and set the text before changing the - * movement method, because setMovementMethod() may call - * setText() again to try to upgrade the buffer type. - */ - mText = text; + if (hasClickableSpans) { + type = (type == BufferType.EDITABLE) ? BufferType.EDITABLE : BufferType.SPANNABLE; + /* + * We must go ahead and set the text before changing the + * movement method, because setMovementMethod() may call + * setText() again to try to upgrade the buffer type. + */ + mText = text; - // Do not change the movement method for text that support text selection as it - // would prevent an arbitrary cursor displacement. - if (mLinksClickable && !textCanBeSelected()) { - setMovementMethod(LinkMovementMethod.getInstance()); - } + // Do not change the movement method for text that supports text selection as it + // would prevent an arbitrary cursor displacement. + if (mLinksClickable && !textCanBeSelected()) { + setMovementMethod(LinkMovementMethod.getInstance()); } } diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml index 50cf30262f69..40290a68b308 100644 --- a/core/res/res/values/attrs.xml +++ b/core/res/res/values/attrs.xml @@ -4240,7 +4240,8 @@ i <attr name="autoLink" /> <!-- If set to false, keeps the movement method from being set to the link movement method even if autoLink causes links - to be found. --> + to be found or the input text contains a + {@link android.text.style.ClickableSpan ClickableSpan}. --> <attr name="linksClickable" format="boolean" /> <!-- If set, specifies that this TextView has a numeric input method. The default is false. |