流式布局

流式布局实现了跟下图类似的功能
在这里插入图片描述
流式布局实现是根据自定义View的基础上
那么我们如何实现该图片的效果呢?
下面展示代码

我们需要创建一个View类继承LinearLayout
自定义View里边还需要我们设置子的LinearLayout和一个TextView
因为我们实现的效果是一个大的LinearLayout里边有一行一行小的LinearLayout
在小的LinearLayout里边添加TextView,然后添加数据实现该效果
看一下我们自定义View类的代码

public class View_LS_List extends LinearLayout {
    private int mScreenWidth;

    public View_LS_List(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);

        DisplayMetrics metrics = context.getResources().getDisplayMetrics();
        mScreenWidth = metrics.widthPixels;
        //设置这个布局垂直显示
        setOrientation(VERTICAL);
    }

    public void removeChildView() {
        //移除所有子控件
        removeAllViews();
    }

    public void setData(List<String> data) {
        LinearLayout linearLayout = initLearLayouy();//[lvxx,lxs,lzs,lzzs]
        for (int i = 0; i < data.size(); i++) {//lvxx
            String tmp = data.get(i);
            int numWidth = 0;
            //得到一行LinearLayout到底有多少子控件  因为我要计算每个子控件加在一起的宽度
            int childCount = linearLayout.getChildCount();
            //这个for循环只是计算一行LinearLayout的所有子控件的宽的和
            for (int j = 0; j < childCount; j++) {
                //通过index得到每一个子控件
                TextView tv = (TextView) linearLayout.getChildAt(j);
                LayoutParams layoutParams = (LayoutParams) tv.getLayoutParams();
                int leftMargin = layoutParams.leftMargin;
                //测量这个tv的高和宽
                tv.measure(getMeasuredWidth(), getMeasuredHeight());
                numWidth += tv.getMeasuredWidth() + leftMargin+tv.getPaddingLeft()+getPaddingRight();
            }

            TextView dataText = initText();
            //设置属性
            LayoutParams params = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
            params.leftMargin = 10;
            params.topMargin = 2;
            dataText.setLayoutParams(params);
            dataText.setText(tmp);
            dataText.measure(getMeasuredWidth(), getMeasuredHeight());
            int dataTextWidth = dataText.getMeasuredWidth()+dataText.getPaddingLeft()+dataText.getPaddingRight();
            //考虑到一个字符串很长 就直接超过整个屏幕的高了
            if (dataTextWidth>=mScreenWidth){
                String s = tmp.substring(0, 4);
                dataText.setText(s+"...");
                dataText.measure(getMeasuredWidth(), getMeasuredHeight());
                dataTextWidth = dataText.getMeasuredWidth();
            }
            //当TextView放满整一行的时候我们需要重新创建一个子LinearLayout重新放置TextView
            if (mScreenWidth >= numWidth + dataTextWidth) {
                linearLayout.addView(dataText);
            } else {
                //这里面对LinearLayout重新赋值  通过getLin换行
                linearLayout = initLearLayouy();
                linearLayout.addView(dataText);
            }

        }

    }


    //初始化TextView
    private TextView initText() {
        TextView textView = new TextView(getContext());
        textView.setTextSize(20);
        textView.setTextColor(Color.BLACK);
        //引用XML实现TextView带边框
        textView.setBackgroundResource(R.drawable.text_shape);
        textView.setPadding(10,10,10,10);
        return textView;
    }

    //初始化子LinearLayout

    private LinearLayout initLearLayouy() {
        LinearLayout linearLayout = new LinearLayout(getContext());
        //LayoutParams 控制组件大小的一个工具类
        LayoutParams params = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
        linearLayout.setLayoutParams(params);
        //this本类对象
        this.addView(linearLayout);//只要重新添加View了自动换行了
        return linearLayout;
    }

}

下面是我的activity_main.xml引用自定义View还有一个搜索框和按钮

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <EditText
        android:id="@+id/ed_text"
        android:hint="请输入数据"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

    <Button
        android:id="@+id/ed_btn"
        android:text="搜索"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

    <text.bwie.com.zdyview_lsbj.View_LS_List
        android:id="@+id/zdyView"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

</LinearLayout>

这里是我的MainActivity调用自定义View里边设置好的方法并传参数

public class MainActivity extends AppCompatActivity implements View.OnClickListener {

    private EditText ed_text;
    private Button ed_btn;
    private View_LS_List zdyView;
    private List<String> dataAll = new ArrayList<>();
    private List<String> newDataAll = new ArrayList<>();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        initData();
        initView();
        zdyView.setData(dataAll);
    }

    private void initData() {
        for (int i = 0; i < 20; i++) {
            dataAll.add("sss"+i);
        }
    }

    private void initView() {
        ed_text = (EditText) findViewById(R.id.ed_text);
        ed_btn = (Button) findViewById(R.id.ed_btn);
        zdyView = (View_LS_List) findViewById(R.id.zdyView);
        ed_btn.setOnClickListener(this);
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.ed_btn:
                String trim = ed_text.getText().toString().trim();
                zdyView.removeChildView();
                newDataAll.add(trim);
                zdyView.setData(newDataAll);
                zdyView.setData(dataAll);
                break;
        }
    }

}

到这里就可以实现如上图所展示的效果,数据自拟

上面这个传入的集合,那么下面传入一个String字符串处理的方法

public class View_LS_List extends LinearLayout {
    private int mScreenWidth;

    public View_LS_List(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);

        DisplayMetrics metrics = context.getResources().getDisplayMetrics();
        mScreenWidth = metrics.widthPixels;
        //设置这个布局垂直显示
        setOrientation(VERTICAL);
    }

    public void removeChildView() {
        //移除所有子控件
        removeAllViews();
    }

    public void setData(List<String> data) {
        LinearLayout linearLayout = initLearLayouy();//[lvxx,lxs,lzs,lzzs]
        for (int i = 0; i < data.size(); i++) {//lvxx
            String tmp = data.get(i);
            int numWidth = 0;
            //得到一行LinearLayout到底有多少子控件  因为我要计算每个子控件加在一起的宽度
            int childCount = linearLayout.getChildCount();
            //这个for循环只是计算一行LinearLayout的所有子控件的宽的和
            for (int j = 0; j < childCount; j++) {
                //通过index得到每一个子控件
                TextView tv = (TextView) linearLayout.getChildAt(j);
                LayoutParams layoutParams = (LayoutParams) tv.getLayoutParams();
                int leftMargin = layoutParams.leftMargin;
                //测量这个tv的高和宽
                tv.measure(getMeasuredWidth(), getMeasuredHeight());
                numWidth += tv.getMeasuredWidth() + leftMargin+tv.getPaddingLeft()+getPaddingRight();
            }

            TextView dataText = initText();
            //设置属性
            LayoutParams params = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
            params.leftMargin = 10;
            params.topMargin = 2;
            dataText.setLayoutParams(params);
            dataText.setText(tmp);
            dataText.measure(getMeasuredWidth(), getMeasuredHeight());
            int dataTextWidth = dataText.getMeasuredWidth()+dataText.getPaddingLeft()+dataText.getPaddingRight();
            //考虑到一个字符串很长 就直接超过整个屏幕的高了
            if (dataTextWidth>=mScreenWidth){
                String s = tmp.substring(0, 4);
                dataText.setText(s+"...");
                dataText.measure(getMeasuredWidth(), getMeasuredHeight());
                dataTextWidth = dataText.getMeasuredWidth();
            }
            //当TextView放满整一行的时候我们需要重新创建一个子LinearLayout重新放置TextView
            if (mScreenWidth >= numWidth + dataTextWidth) {
                linearLayout.addView(dataText);
            } else {
                //这里面对LinearLayout重新赋值  通过getLin换行
                linearLayout = initLearLayouy();
                linearLayout.addView(dataText);
            }

        }

    }


    //初始化TextView
    private TextView initText() {
        TextView textView = new TextView(getContext());
        textView.setTextSize(20);
        textView.setTextColor(Color.BLACK);
        //引用XML实现TextView带边框
        textView.setBackgroundResource(R.drawable.text_shape);
        textView.setPadding(10,10,10,10);
        return textView;
    }

    //初始化子LinearLayout

    private LinearLayout initLearLayouy() {
        LinearLayout linearLayout = new LinearLayout(getContext());
        //LayoutParams 控制组件大小的一个工具类
        LayoutParams params = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
        linearLayout.setLayoutParams(params);
        //this本类对象
        this.addView(linearLayout);//只要重新添加View了自动换行了
        return linearLayout;
    }

}

到这里就是我的全部代码,如果还有不太清楚的地方可以参考一下代码
地址:https://github.com/qq1341738311/Fluid-layout-Demo

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值