Skip to content Skip to sidebar Skip to footer

Textview Catch Clicking On Link When Autolink Is Set To "web"

I have TextView in my layout with autoLink='web' and when I click on it, internal internet browser is opened with URL that is provided as a text in that TextView and everything is

Solution 1:

Actually,

I solved this by abandoning autolLink='web' and by parsing html url, creating SpannableString and setting additional spans.

So, let's say that I want to do the following:

  • if user clicks on the part of the text of textView which is not url, method someMethod() should be called
  • if user clicks on the part of the text of textView which is url, method someMethod() should be called and browser should be openned with given URL

So, first we have the content which is in the variable message and method String extractFirstLink(String text) will be used to get the url.

privatestaticStringextractFirstLink(String text) {
    Matcher m = Patterns.WEB_URL.matcher(text);
    return m.find() ? m.group() : null;
}

Note: in my case I know that I will have only one url, but if you can expect more than one url, this solution (found somewhere on StackOverflow, can't find it right now) will do the work:

publicstaticString[] extractLinks(String text) {
    List<String> links = newArrayList<String>();
    Matcher m = Patterns.WEB_URL.matcher(text);
    while (m.find()) {
        String url = m.group();
        links.add(url);
    }
    return links.toArray(newString[links.size()]);
}

So, here is the code:

intcontentTextColor= ...; // color of non-url text in textViewinturlTextColor= ...;
Stringmessage= notification.getMessage(); // content storedfinalStringfoundLink= extractFirstLink(message);
SpannableStringstyledString=newSpannableString(message);

if (foundLink != null) {
    intstartPosition= message.indexOf(foundLink);
    intendPosition= startPosition + foundLink.length();
    styledString.setSpan(newForegroundColorSpan(urlTextColor), startPosition, endPosition, 0);

    ClickableSpanclickableURLSpan=newClickableSpan() {
        @OverridepublicvoidonClick(View widget) {
            someMethod();
            IntentbrowserIntent=newIntent(Intent.ACTION_VIEW, Uri.parse(foundLink));
            widget.getContext().startActivity(browserIntent);
        }
    };

    ClickableSpanclickableNonURLSpan1=newClickableSpan() {
        @OverridepublicvoidonClick(View view) {
            someMethod();
        }

        @OverridepublicvoidupdateDrawState(TextPaint ds) {
            ds.setUnderlineText(false);
        }
    };
    ClickableSpanclickableNonURLSpan2=newClickableSpan() {
        @OverridepublicvoidonClick(View view) {
            someMethod();
        }

        @OverridepublicvoidupdateDrawState(TextPaint ds) {
            ds.setUnderlineText(false);
        }
    };
    styledString.setSpan(clickableURLSpan, startPosition, endPosition, 0);
    if (startPosition > 0) {
        styledString.setSpan(clickableNonURLSpan1, 0, startPosition - 1, 0);
        styledString.setSpan(newForegroundColorSpan(contentTextColor), 0, startPosition -1, 0);
    }
    if (endPosition < message.length() -1) {
        styledString.setSpan(clickableNonURLSpan2, endPosition + 1, message.length(),  0);
        styledString.setSpan(newForegroundColorSpan(contentTextColor), endPosition + 1, message.length(),  0);
    }

    txtView.setMovementMethod(LinkMovementMethod.getInstance());
}

txtView.setText(styledString);

There are some interesting things here. For example, when I wish to make span responsive to click, I have to use ClickableSpan, but! I must handle situation where I have format text1-url-text2. So, since all these three parts should be ClickableSpans and text1 and text2 should not have underline, which is the default behaviour of it, I had to override updateDrawState method in my implementation of ClickableSpan for text1 and text2.

There is another catch, I had to create two implementation of ClickableSpan interface in order to have to work as intended. That's why I created clickableNonURLSpan1 and clickableNonURLSpan2.

Post a Comment for "Textview Catch Clicking On Link When Autolink Is Set To "web""