Android中需要给TextView中的个别字设置为超链接,或者设置个别字的颜色、字体等,需要用到Spannable对象。

效果如下:

baidu和youku字段做了autolink,设置字体大小和颜色,youku并取消了下划线。

private void initView() {        TextView textView = (TextView) findViewById(R.id.tv_content);        String content = textView.getText().toString();        // This is a test,you can click baidu or youku.        SpannableString ss = new SpannableString(content);        // flag:标识在 Span 范围内的文本前后输入新的字符时是否把它们也应用这个效果        //  Spanned.SPAN_EXCLUSIVE_EXCLUSIVE(前后都不包括)、        //  Spanned.SPAN_INCLUSIVE_EXCLUSIVE(前面包括,后面不包括)、        // Spanned.SPAN_EXCLUSIVE_INCLUSIVE(前面不包括,后面包括)、        // Spanned.SPAN_INCLUSIVE_INCLUSIVE(前后都包括)        // 设置网络超链接        ss.setSpan(new URLSpan("http://www.baidu.com"), content.indexOf("baidu"), content.indexOf(" or"), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        ss.setSpan(new URLSpan("http://www.youku.com"), content.indexOf("youku"), ss.length(), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        // 设置字体颜色        ss.setSpan(new ForegroundColorSpan(Color.parseColor("#ff0000")), content.indexOf("baidu"), content.indexOf(" or"), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        ss.setSpan(new ForegroundColorSpan(Color.parseColor("#ff00ff")), content.indexOf("youku"), ss.length(), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        // 设置字体大小        ss.setSpan(new AbsoluteSizeSpan(sp2px(this, 25)), content.indexOf("baidu"), content.indexOf(" or"), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        ss.setSpan(new AbsoluteSizeSpan(sp2px(this, 30)), content.indexOf("youku"), ss.length(), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        // 取消下划线        ss.setSpan(new MyUnderlineSpan(), content.indexOf("youku"), ss.length(), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);        textView.setText(ss);        textView.setMovementMethod(LinkMovementMethod.getInstance());    }// 通过继承UnderlineSpan重写updateDrawState方法setUnderlineText(false)取消下划线    class MyUnderlineSpan extends  UnderlineSpan{        @Override        public void updateDrawState(TextPaint ds) {            ds.setUnderlineText(false);        }    }    private int sp2px(Context context, float spValue) {        final float fontScale = context.getResources().getDisplayMetrics().scaledDensity;        return (int) (spValue * fontScale + 0.5f);    }

UnderLineSpan源码很简单,在updateDrawState设置下划线

public class UnderlineSpan extends CharacterStyle        implements UpdateAppearance, ParcelableSpan {    public UnderlineSpan() {    }    public UnderlineSpan(Parcel src) {    }    public int getSpanTypeId() {        return TextUtils.UNDERLINE_SPAN;    }    public int describeContents() {        return 0;    }    public void writeToParcel(Parcel dest, int flags) {    }    @Override    public void updateDrawState(TextPaint ds) {        ds.setUnderlineText(true);    }}

因此只要继承UnderlineSpan重写下updateDrawState方法即可去掉下划线

    class MyUnderlineSpan extends  UnderlineSpan{        @Override        public void updateDrawState(TextPaint ds) {            ds.setUnderlineText(false);        }    }

ClickableSpan源码的话可看到 updateDrawState默认设置带有下划线

public abstract class ClickableSpan extends CharacterStyle implements UpdateAppearance {    /**     * Performs the click action associated with this span.     */    public abstract void onClick(View widget);    /**     * Makes the text underlined and in the link color.     */    @Override    public void updateDrawState(TextPaint ds) {        ds.setColor(ds.linkColor);        ds.setUnderlineText(true);    }}

URLSpan 源码继承于ClickableSpan 并在onClick发起一个意图调用浏览器进行网址的浏览,由于继承于ClickableSpan所以默认带下划线

public class URLSpan extends ClickableSpan implements ParcelableSpan {    private final String mURL;    public URLSpan(String url) {        mURL = url;    }    public URLSpan(Parcel src) {        mURL = src.readString();    }    public int getSpanTypeId() {        return TextUtils.URL_SPAN;    }    public int describeContents() {        return 0;    }    public void writeToParcel(Parcel dest, int flags) {        dest.writeString(mURL);    }    public String getURL() {        return mURL;    }    @Override    public void onClick(View widget) {        Uri uri = Uri.parse(getURL());        Context context = widget.getContext();        Intent intent = new Intent(Intent.ACTION_VIEW, uri);        intent.putExtra(Browser.EXTRA_APPLICATION_ID, context.getPackageName());        context.startActivity(intent);    }}

我们想自己定义webview加载内容的话可以继承URLSpan 进行处理

class MyURLSpan extends URLSpan {        @Override        public void onClick(View widget) {            Uri uri = Uri.parse(getURL());            // 这里拿到uri进行自己的加载操作即可            dosomething();        }    }

可以看到Spannable是个相当实用的类,想起以前用textview大小颜色或要分开做点击处理的时候,用几个textview拼凑起来就想打自己脸。。。
还有很多属性可以设置,这里就不详细说了,我常用的就这么几个。
讲解完毕,( ^_^ )/~~拜拜

更多相关文章

  1. Android——ImageView.ScaleType设置图解
  2. Android(安卓)windowTranslucentStatus属性源码分析
  3. Android(安卓)第十三课——ListView ListActivity SimpleAdapter
  4. 如何隐藏APP名字
  5. Android(安卓)8.0 高通代码预制apk可卸载,恢复出厂设置apk可恢复
  6. Android踩坑日记:FloatingActionButton的设置大小问题
  7. ListView改变里面TextView的字体颜色
  8. android中设置Animation 动画效果
  9. Android(安卓)Phone 类的详细 分析 各个类的功能

随机推荐

  1. Android(安卓)Glide传Context引发的非法
  2. android Error generating final archive
  3. Android(安卓)activity和fragment隐藏软
  4. Android(安卓)dimens.xml中保存不带单位
  5. Android(安卓)LayoutInflater
  6. android开发笔记之一些有用资料的汇总
  7. android 源码编译遇到得一些问题
  8. Ubuntu 安装 ADT和SDK
  9. Android(安卓)Dialog 对话框
  10. Android:一个很简单的扑克游戏(从项目资源