Friday, June 8, 2012

How do I make links in a TextView clickable?


I have the following TextView defined:




<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content" android:text="@string/txtCredits"
android:autoLink="web" android:id="@+id/infoTxtCredits"
android:layout_centerInParent="true"
android:linksClickable="true"></TextView>



where @string/txtCredits is a string resource that contains Link text.



Android is highlighting the links in the TextView, but they do not respond to clicks. Can someone tell me what I'm doing wrong? Do I have to set an onClickListener for the TextView in my activity for something as simple as this?



Looks like it has to do with the way I define my string resource. This does not work: <string name="txtCredits"><a href="http://www.google.com">Google</a></string>



But this does: <string name="txtCredits">www.google.com</string>



Which is a bummer because I would much rather show a text link than show the full url.


Source: Tips4all

7 comments:

  1. Buried in the API demos I found the solution to my problem:

    Link.java:

    // text2 has links specified by putting <a> tags in the string
    // resource. By default these links will appear but not
    // respond to user input. To make them active, you need to
    // call setMovementMethod() on the TextView object.

    TextView t2 = (TextView) findViewById(R.id.text2);
    t2.setMovementMethod(LinkMovementMethod.getInstance());


    I removed most of the attributes on my TextView to match what was in the demo.

    <TextView android:layout_width="wrap_content"
    android:layout_height="wrap_content" android:text="@string/txtCredits"
    android:id="@+id/infoTxtCredits"
    android:layout_below="@+id/imgCredits" android:layout_centerInParent="true"
    android:layout_marginTop="20dp"></TextView>


    That solved it. Pretty difficult to uncover and fix.

    ReplyDelete
  2. I'm using only android:autoLink="web" and it works fine. A click on the link opens the browser and shows the correct page.

    One thing I could guess is that some other view is above the link. Something that is transparent fills the whole parent but don't displays anything above the link. In this case the click goes to this view instead of the link.

    ReplyDelete
  3. The above solutions didn't work for me, but the following did (and it seems a bit cleaner).
    First, in the string resource, define your tag opening chevrons using the HTML entity encoding, i.e.:

    &lt;a href="http://www.google.com">Google&lt;/a>


    and NOT:

    <a href="http://www.google.com">Google</a>


    In general, encode all the chevrons in the string like that. BTW, the link must start with http://

    Then (as suggested here) set this option on your TextView:

    android:linksClickable="true"


    Finally, in code, do:

    ((TextView) findViewById(R.id.your_text_view)).setMovementMethod(LinkMovementMethod.getInstance());
    ((TextView) findViewById(R.id.your_text_view)).setText(Html.fromHtml(getResources().getString(R.string.string_with_links)));


    That's it, no regexes or other manual hacks required.

    ReplyDelete
  4. The reason you're having the problem is that it only tries to match "naked" addresses. things like "www.google.com" or "http://www.google.com".

    Running your text through Html.fromHtml() should do the trick. You have to do it programatically, but it works.

    ReplyDelete
  5. Only what do you need to add this in text view in xml

    android:autoLink="web"

    <TextView
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:autoLink="web"/>

    ReplyDelete
  6. This is how I solved clickable and Visible links in a TextView (by code)

    private void setAsLink(TextView view, String url){
    Pattern pattern = Pattern.compile(url);
    Linkify.addLinks(view, pattern, "http://");
    view.setText(Html.fromHtml("<a href='http://"+url+"'>http://"+url+"</a>"));
    }

    ReplyDelete
  7. Be sure to not use setAutoLinkMask(Linkify.ALL) when using setMovementMethod(LinkMovementMethod.getInstance()) and Html.fromHTML() on properly formatted HTML links (for example, <a href="http://www.google.com/">Google</a>).

    ReplyDelete