美文网首页
Android实现简单的ExpandTextview

Android实现简单的ExpandTextview

作者: 单身狗的清香 | 来源:发表于2017-04-30 10:48 被阅读278次

最近工作中需要使用到ExpandTextview,因为没有原生的控件可以使用,GitHub上面有没有找到合适的,那就自己造一个轮子吧:)

最终要实现的效果就是TextView的行数最大不超过两行,大于两行的会有下拉按钮可以让用户展开或者收缩内容,如果本来的内容就在两行以下的,就隐藏下拉按钮,行数保持原有的样子。最后我们希望达到的效果是这样的:

收缩的样子 展开的样子

内容超过两行可以收缩或者展开,内容没有超过两行的则保持不变。


因为我的实际需求是要在列表中展示内容,那么就先来创建一个列表:

  • activity_main.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/activity_main"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <android.support.v7.widget.RecyclerView
        android:id="@+id/recycleView"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
</RelativeLayout>
  • item_expand.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="vertical">

    <LinearLayout
        android:id="@+id/view_item_container"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical">

        <TextView
            android:id="@+id/tv_item_content"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:ellipsize="end"
            android:padding="10dp"
            android:text="我是内容"
            android:textColor="@android:color/black" />

        <ImageView
            android:id="@+id/iv_item_arrow"
            android:layout_width="wrap_content"
            android:layout_gravity="right"
            android:layout_height="wrap_content"
            android:layout_marginRight="10dp"
            android:layout_marginBottom="10dp"
            android:src="@drawable/arrow_down" />
    </LinearLayout>

</LinearLayout>

布局完成了之后,那么接下来我们的主要关注点就是adapter里面的实现了,自定义一个CustomAdapter,并在binding方法中实现我们的逻辑代码:

package com.lxy.mew.expandtextview.adapter;

import android.content.Context;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.TextView;

import com.lxy.mew.expandtextview.R;

import java.util.ArrayList;
import java.util.List;

/**
 *
 * Created by master on 2017/4/29.
 */
public class CustomAdapter extends RecyclerView.Adapter<CustomAdapter.ViewHolder>
{

    private Context context;
    private List<String> datas = new ArrayList<>();


    public CustomAdapter(Context context)
    {
        this.context = context;
    }

    public void setDatas(List<String> datas)
    {
        this.datas = datas;
    }

    @Override
    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType)
    {
        return new ViewHolder(LayoutInflater.from(context).inflate(R.layout.item_expand, parent, false));
    }

    @Override
    public void onBindViewHolder(final ViewHolder holder, int position)
    {

        String item = datas.get(position);
        holder.tvContent.setText(item);

        final View.OnClickListener listener = new View.OnClickListener()
        {
            boolean isExpand;//设置是否展开的标记

            @Override
            public void onClick(View v)
            {
                if (isExpand)
                {
                    holder.tvContent.setMaxLines(2);//如果当前是展开的,则设置为闭合
                    holder.ivArrow.setRotation(0);//箭头重置为向下的状态
                    isExpand = false;
                } else
                {
                    holder.tvContent.setMaxLines(Integer.MAX_VALUE);//如果是闭合的,则展开
                    holder.ivArrow.setRotation(180);//箭头设置为向上
                    isExpand = true;
                }

            }
        };
        holder.tvContent.post(new Runnable()
        {
            @Override
            public void run()
            {
                /**
                 * 在子线程中获取textview的行数,等页面加载完成之后才能取到行数
                 */
                int lineCount = holder.tvContent.getLineCount();
                if (lineCount > 2)//如果行数大于2,就让textview闭合
                {
                    holder.tvContent.setMaxLines(2);
                    holder.viewContainer.setOnClickListener(listener);//可以相应点击事件
                    holder.ivArrow.setVisibility(View.VISIBLE);
                } else
                {
                    holder.viewContainer.setOnClickListener(null);//行数没有超过两行,保持原状,无需改变
                    holder.ivArrow.setVisibility(View.GONE);//让箭头消失
                }
            }
        });

    }

    @Override
    public int getItemCount()
    {
        return datas.size();
    }

    class ViewHolder extends RecyclerView.ViewHolder
    {

        View viewContainer;
        TextView tvContent;
        ImageView ivArrow;

        ViewHolder(View itemView)
        {
            super(itemView);

            viewContainer = itemView.findViewById(R.id.view_item_container);
            tvContent = (TextView) itemView.findViewById(R.id.tv_item_content);
            ivArrow = (ImageView) itemView.findViewById(R.id.iv_item_arrow);

        }
    }
}

个人感觉主要用到的知识点就是获取TextView行数,因为lineCount属性是在UI绘制加载完成之后才会有值的,所以不能在主线程中getLineCount();那样取到的值永远都是0.

整个实现思路大致就是这样,当然可以自己根据需求扩展和改进它的功能。
源码

相关文章

网友评论

      本文标题:Android实现简单的ExpandTextview

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