How to I handle the <a> tag #87
Comments
Do you mean that you want a custom onClick handler for the links? |
Yes. That I what I'd like to have. |
OK. If you look at the source for the HtmlTextView class you can see public void setHtml(@NonNull String html, @Nullable Html.ImageGetter imageGetter) Within that method is the following code if (removeFromHtmlSpace) {
setText(removeHtmlBottomPadding(Html.fromHtml(html, imageGetter, htmlTagHandler)));
} else {
setText(Html.fromHtml(html, imageGetter, htmlTagHandler));
}
If you have an tag in there, it will have been parsed to URLSpan. Rather than setting the text straight away, you can modify that part of the method to this final Spanned text;
if(removeFromHtmlSpace) {
text = removeHtmlBottomPadding(Html.fromHtml(overridden, imageGetter, htmlTagHandler));
} else {
text = Html.fromHtml(overridden, imageGetter, htmlTagHandler);
}
text now holds the spans that you need. Now, we want to modify the URLSpans so that they do what you want. First, we need a click listener. public interface LinkClickHandler {
void onClick(String url);
} Then we add an instance of this interface and a setter to HtmlTextView. Secondly, we need to use this listener. In order to modify the Spanned, it needs to be a buffer, so we create one. final SpannableString buffer = new SpannableString(text); If you want to handle links like www.somewebsite.com as well, you need to enable those separately with Linkify Linkify.addLinks(buffer, Linkify.WEB_URLS | Linkify.EMAIL_ADDRESSES); Now that we get all the URLSpans which we want to replace final URLSpan[] spans = text.getSpans(0, text.length(), URLSpan.class); Then we replace them for(URLSpan us : spans) {
final int end = text.getSpanEnd(us); //Getting the spans position
final int start = text.getSpanStart(us);
buffer.setSpan(new URLSpan(us.getURL()) { // A new span with the same URL
@Override
public void onClick(View widget) {
if(mLinkHandler != null) {
mLinkHandler.onClick(getURL());
} else {
super.OnClick(widget);
}
}
}, start, end, 0); //Overwriting the old span
} Finally, we set the text setText(buffer);
setMovementMethod(LocalLinkMovementMethod.getInstance()); In order to use your onClickListener, you use the setter method that you created earlier on your instance of HtmlTextView. |
I should probably say, the reason for getting the start and end positions from text rather than the buffer that was just created, is that if you use Linkify, it removes all of the URLSpans that were in the text Spanned. |
@tpb1908 Can you clarify on what the |
@vishnumad Yes it should be. Either call super.onClick(widget), or you can use the widget context to launch an activity of your choice. final Intent i = new Intent(Intent.ACTION_VIEW);
i.setData(Uri.parse(getURL());
widget.getContext().startActivity(i); |
I'd consider this more of a feature request, it would be nice to have 'HtmlTextView.setOnLinkClick' to override the default opening of this |
I ended up modifying the whole thing a while back to allow click handling for code, images, links, and tables. There is also an EditText version which can be toggled between raw markdown and formatted, as well as a WebView version and support for Emoji tags. Also inline code spans and proper strikethroughs, tick box lists, relative image links for github, as well as github issue and user links. |
That looks pretty useful! Bookmarked.
Edit: Fixed, I needed to set Here is my code for reference: https://gist.github.com/rubenwardy/a503aaaee25f02566dc98654809d55cb#file-myhtmltextview-kt-L52 |
It's a bit of a mess hacked together for a college project. I have been meaning to rewrite the whole thing in Kotlin with some proper architecture. |
@rubenwardy You should try out https://github.com/saket/Better-Link-Movement-Method The trick is that you need to call I extracted the class MyViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
private val onLinkClickLinkClickListener =
BetterLinkMovementMethod.OnLinkClickListener { textView, url ->
// Handle URL
true
}
fun bind(html: String) {
itemView.htmlTextView.setHtml(html)
BetterLinkMovementMethod
.linkifyHtml(itemView.htmlTextView)
.setOnLinkClickListener(onLinkClickLinkClickListener)
}
} |
I ended up just using a web view, and have since resigned from the company so :D |
Welp, I guess that works too :D |
You can look here. |
Your fork uses other library instead of what the original one uses. Besides that, the leading margin of the bullet/number is too small and cannot be customized. |
@fikr4n You are right, so I modified it based on the original library, now it can support the click event of a tag. see xiandanin/html-textview or #181 |
I would like the tag to be handled a little differently. I would need a custom handler for this tag. It should technically open one of my WebViews and load the URL in it.
How do I go about doing this?
The text was updated successfully, but these errors were encountered: