Android自定义超链接TextView

在Android中查找链接非常简单,您可能听说过Linkify ,这是一个很棒的类,其中有许多静态方法可以完成简单的工作,但问题是在Linkify中您无法指定单击链接时所需的行为最重要的是,Linkify所做的只是根据您提供的“模式”查找链接,并添加“方案”字符串以完成URL,并创建了用于启动浏览器的Android目的。 Linkify行为不能被覆盖,因为Linkify类中的所有方法都是static final。

这个问题启发了我创建一个自定义TextView小部件,该小部件用于收集我的场景中的链接,我也对其进行了编程,以收集以“ @”和“#”开头的字符串,但是可以通过简单地更改您需要的模式,并为其提供适当的正则表达式。

LinkEnableTextView类是这样的:

import java.util.ArrayList;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import android.content.Context;
import android.text.Spannable;
import android.text.SpannableString;
import android.text.style.ClickableSpan;
import android.util.AttributeSet;
import android.view.View;
import android.widget.TextView;


public class LinkEnabledTextView  extends TextView
{
// The String Containing the Text that we have to gather links from private SpannableString linkableText;
// Populating and gathering all the links that are present in the Text
private ArrayList<Hyperlink> listOfLinks; 

// A Listener Class for generally sending the Clicks to the one which requires it
TextLinkClickListener mListener;

// Pattern for gathering @usernames from the Text
Pattern screenNamePattern = Pattern.compile('(@[a-zA-Z0-9_]+)');

// Pattern for gathering #hasttags from the Text
Pattern hashTagsPattern = Pattern.compile('(#[a-zA-Z0-9_-]+)');

// Pattern for gathering http:// links from the Text
Pattern hyperLinksPattern = Pattern.compile('([Hh][tT][tT][pP][sS]?:\\/\\/[^ ,'\'>\\]\\)]*[^\\. ,'\'>\\]\\)])');

public LinkEnabledTextView(Context context, AttributeSet attrs)
{
    super(context, attrs);
    listOfLinks = new ArrayList<Hyperlink>();

}

public void gatherLinksForText(String text)
{
    linkableText = new SpannableString(text);
 //gatherLinks basically collects the Links depending upon the Pattern that we supply
 //and add the links to the ArrayList of the links
  
    gatherLinks(listOfLinks, linkableText, screenNamePattern);
    gatherLinks(listOfLinks, linkableText, hashTagsPattern);
    gatherLinks(listOfLinks, linkableText, hyperLinksPattern);

    for(int i = 0; i< listOfLinks.size(); i++)
    {
        Hyperlink linkSpec = listOfLinks.get(i);
        android.util.Log.v('listOfLinks :: ' + linkSpec.textSpan, 'listOfLinks :: ' + linkSpec.textSpan);
        
        // this process here makes the Clickable Links from the text
         
        linkableText.setSpan(linkSpec.span, linkSpec.start, linkSpec.end, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
    }

    
     // sets the text for the TextView with enabled links
     
    setText(linkableText);
}


 // sets the Listener for later click propagation purpose
 
public void setOnTextLinkClickListener(TextLinkClickListener newListener)
{
    mListener = newListener;
}

  //The Method mainly performs the Regex Comparison for the Pattern and adds them to
  //listOfLinks array list
 

private final void gatherLinks(ArrayList<Hyperlink> links,
                               Spannable s, Pattern pattern)
{
    // Matcher matching the pattern
    Matcher m = pattern.matcher(s);

    while (m.find())
    {
        int start = m.start();
        int end = m.end();

        
    // Hyperlink is basically used like a structure for storing the information about
    // where the link was found.
        
        Hyperlink spec = new Hyperlink();

        spec.textSpan = s.subSequence(start, end);
        spec.span = new InternalURLSpan(spec.textSpan.toString());
        spec.start = start;
        spec.end = end;

        links.add(spec);
    }
}


// This is class which gives us the clicks on the links which we then can use.
 

public class InternalURLSpan extends ClickableSpan
{
    private String clickedSpan;

    public InternalURLSpan (String clickedString)
    {
        clickedSpan = clickedString;
    }

    @Override
    public void onClick(View textView)
    {
        mListener.onTextLinkClick(textView, clickedSpan);
    }
}


// Class for storing the information about the Link Location


class Hyperlink
{
    CharSequence textSpan;
    InternalURLSpan span;
    int start;
    int end;
}

现在,有了这个,您只需要另一个界面即可将点击传播到您需要处理的位置,我在我的Activity中实现了该界面,并在其中简单地编写了一个Log Command。

TextLinkClickListener接口是这样的:

import android.view.View;

public interface TextLinkClickListener
{

 
  //  This method is called when the TextLink is clicked from LinkEnabledTextView
  
public void onTextLinkClick(View textView, String clickedString)
}

完成所有这些操作后,您只需要使用Custom LinkEnabledTextView创建一个Activity,然后自己检查一下即可。 创建自定义LinkEnabledTextView的对象时,您必须做一些事情,以下活动代码中对此进行了提及和描述:

import android.text.method.MovementMethod;
import com.umundoinc.Tvider.Component.LinkEnabledTextView.LinkEnabledTextView;
import com.umundoinc.Tvider.Component.LinkEnabledTextView.TextLinkClickListener;
import android.app.Activity;
import android.graphics.Color;
import android.os.Bundle;
import android.text.method.LinkMovementMethod;
import android.view.View;

//Here the Activity is implementing the TextLinkClickListener the one we have created
//the Clicks over the Links are forwarded over here from the LinkEnabledTextView
 
public class TextViewActivity  extends Activity  implements TextLinkClickListener 
{
private LinkEnabledTextView check;
protected void onCreate(Bundle savedInstance)
{
    super.onCreate(savedInstance);

    String text  =  "This is a #test of regular expressions with http://example.com/ links as used in @twitter for performing various operations based on the links this handles multiple links like http://this_is_fun.com/ and #Awesomess and @Cool";

    check = new LinkEnabledTextView(this, null);
    check.setOnTextLinkClickListener(this);
    check.gatherLinksForText(text);
    check.setTextColor(Color.WHITE);
    check.setLinkTextColor(Color.GREEN);

    MovementMethod m = check.getMovementMethod();
    if ((m == null) || !(m instanceof LinkMovementMethod)) {
        if (check.getLinksClickable()) {
            check.setMovementMethod(LinkMovementMethod.getInstance());
        }
    }

    setContentView(check);
}

public void onTextLinkClick(View textView, String clickedString)
{
    android.util.Log.v('Hyperlink clicked is :: ' + clickedString, 'Hyperlink clicked is :: ' + clickedString);
}

这里是屏幕快照,它描述了我在Listener方法中输出的内容,我对其进行了编程以显示Toast,但使用同一方法可以实现任何目的。

现在,这几乎是使Custom LinkEnabledTextView正常工作所需要的全部,请尝试一下并分享您的意见和评论。

参考:来自OrangeApple博客的JCG合作伙伴 Y Kamesh Rao的Android自定义超链接TextView


翻译自: https://www.javacodegeeks.com/2012/09/android-custom-hyperlinked-textview.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值