美文网首页自定义android酷炫的UI效果
android ExpandableTextView-自定义可以

android ExpandableTextView-自定义可以

作者: carbs | 来源:发表于2016-07-29 09:20 被阅读4231次

    前言:

    为了保持界面UI的整洁以及将尽可能多的内容显示在有限的空间中,往往需要将长度过长的TextView进行内容截取。本控件满足了TextView可在"完整内容"与"截取内容"两种模式下进行切换的需求,且可应用在ListView/RecyclerView中并可以动态更新内容。

    截图:

    静态截图如下:

    这里写图片描述

    动态效果图可点击如下链接:

    流量党慎点
    项目地址:
    https://github.com/Carbs0126/ExpandableTextView

    主要功能:

    1. 限制行数,行尾添加ClickSpan,点击可以"展开"/"收起"两种状态切换;
    2. 可使用在ListView/RecyclerView中,效率较高;
    3. 可在任意时刻更新ExpandableTextView内容(布局显示之前或者显示之后);
    4. 可自定义行数限制,默认最多显示2行;
    5. 可自定义行尾ClickSpan是否显示,颜色,文字,按下的背景颜色;
    6. 可添加点击此view后是否在"展开"/"收起"状态间切换;
    7. 文字不足最大限制行数时,不截断文字,不显示末尾的"展开"/"收起"的指示标识;
    8. 可自定义行尾省略语与行尾"展开"/"收起"的指示标识之间的gap文字;

    说明:

    1. 效果参考了jQuery的readmore.js,部分代码参考了ReadMoreTextView
    2. 与Github上star数最多的ExpandableTextView实现原理及UI完全不同。
    3. 暂时未添加"收缩"/"展开"时的动画效果。

    优化:

    1. 解决末尾显示的指示标识文字与原来文字宽度不一致时的显示问题(如原始文字与行尾指示标识文字为不同语言)。如当结尾指示标识文字较宽时,可能会显示到下一行。以此优化UI体验。
    2. 解决末尾单词过长或者跟随标点后,换行留下的空白问题。此问题源于TextView自带的一个属性:当结尾为完整单词或者跟随标点时会连同之前的部分文字一起换行。
    3. 解决文字过短时,截取文字超出边界的问题。
    4. 解决任何时刻为ExpandableTextView更新文字的问题。

    不具有的功能:

    1. 限制字符长度。此控件只限制最大行数,不限制字符长度;
    2. 省略标识的位置自定义。省略标识的位置暂时只能显示在行尾,不能够指定是否在"行首"/"行中"/"行尾";
    3. 暂时未添加"收缩"/"展开"时的动画效果。

    添加依赖

    compile 'cn.carbs.android:ExpandableTextView:1.0.0'
    

    使用方法:

    有两种方法设置文字:

    (1)在java中更新文字

    //普通视图中的更新
    etv.setText(text);
    //在ListView/RecyclerView中的应用,etvWidth为控件的真实宽度,state是控件所处的状态,“收缩”/“伸展”状态
    etv.updateForRecyclerView(text, etvWidth, state);
    

    (2)在xml中直接设置文字

    <cn.carbs.android.expandabletextview.library.ExpandableTextView 
    android:id="@+id/etv" 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="@string/long_poem" />
    

    实现原理:

    1. 控件继承自TextViewTextView中的setText(CharSequence text)方法为 final 类型,且其内部最终调用了setText(CharSequence text, BufferType type),因此ExpandableTextView Override了setText(CharSequence text, BufferType type)方法,且TextView在通过xml布局文件设置text时,同样最终是通过setText(CharSequence text, BufferType type)进行赋值,因此通过Override此方法达到自定义显示text的效果;
    2. 采用android.text.Layout类来确定在一定宽度下,特定的文本所达到的行数,如果超过最大行数,则添加收缩/展开效果;
    3. 为文本特定位置添加ClickableSpan,以此添加点击部分文本的响应效果;自定义ClickableSpanLinkMovementMethod,达到添加点击ClickableSpan文字背景颜色改变的效果,感谢stackoverflow的解答;
    4. 通过Paint.measureText(String text)方法,找到文本截取的最优位置,使得在行尾添加了ClickableSpan后,不会出现因文字宽度不同而导致的文本换行或者文本末尾空余过大的现象;

    项目地址

    https://github.com/Carbs0126/ExpandableTextView

    相关文章

      网友评论

      • 冬记:表示,设置TextView的setMaxLines()不可以吗?这样会更简便
      • 小辉灰:我再xrecyclerview里面用的时候有的item会自动展开,当往上滑回去的时候又会自动收起来了,为啥呢
        Johnson_Coding:@总是说 请问你解决了吗,我现在也碰到这个问题,急
        Van_Tinker:我的在ScrollView中,如果之前是“收起”状态,下次从别的地方进来这个ScrollView,总会快速闪一下(先展开再收起)
        总是说:你好,这个滑动后状态改变你后来改好了么?我也是这个问题
      • carbs:非常抱歉,评论没有及时看到,大家提的问题我都会仔细看看,感谢大家的关注
        Johnson_Coding:解决了吗?
      • 二不吝:用了会有些不顺手
        private static final int MAX_LINES_ON_SHRINK = 1;这个是设置可以显示最大行数的。
        如果放在listview中的某一部分会拦截item的点击事件,发生冲突的话,android:descendantFocusability="blocksDescendants"
        android:focusable="true"
        android:focusableInTouchMode="true"三个布局文件中添加,具体位置自行调试。
        之后这个Text和item都可以分别触发不同的点击事件
        踩了好多坑
        有问题欢迎私信
        七岁小猫:@二不吝 其实你仔细查看 后面个展开/收缩其实就是个提示 点击整个textview都会有触发事件 不过楼主做出来 我没做出来 所以还是技不如人甘拜下风
        二不吝:@七岁小猫 :smile: 我好像不能用了,不知道为啥
        七岁小猫:@二不吝 你说的这些坑 我两年前就踩过 想起来仍记忆犹新 :sweat_smile:
      • 卧水莱藤:google了一下午就这一个是能用的
      • 024f9a2057cd:还有持续更新吗?
      • 晚睡晚起的:网上看了好多 终于有一个能用的了.. :smile:

      本文标题:android ExpandableTextView-自定义可以

      本文链接:https://www.haomeiwen.com/subject/hhczjttx.html