自定义流式布局

效果
在这里插入图片描述

<com.yaxin.liushibuju.FloatLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    >
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="可乐鸡翅"
        android:textColor="@color/colorAccent" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="水果汉堡"
        android:textColor="@color/colorAccent" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="麻辣小龙虾"
        android:textColor="@color/colorAccent" />


    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="宫保鸡丁"
        android:textColor="@color/colorAccent" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="红烧茄子"
        android:textColor="@color/colorAccent" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="酱香土豆"
        android:textColor="@color/colorAccent" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="麻婆豆腐"
        android:textColor="@color/colorAccent" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="5dp"
        android:background="@drawable/shape_tv_blue"
        android:padding="5dp"
        android:text="三鲜"
        android:textColor="@color/colorAccent" />
</com.yaxin.liushibuju.FloatLayout>


public class FloatLayout extends ViewGroup {
public FloatLayout(Context context) {
    this(context,null);
}

public FloatLayout(Context context, AttributeSet attrs) {
    this(context, attrs,0);
}

public FloatLayout(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    //setMeasuredDimension(1000,1000);
}

private List<List<View>> mLineViews = new ArrayList<List<View>>();
private List<Integer> mLineHeight = new ArrayList<Integer>();
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    super.onMeasure(widthMeasureSpec, heightMeasureSpec);
    mLineViews.clear();
    mLineHeight.clear();

    int widthMode = MeasureSpec.getMode(widthMeasureSpec);
    int widthSize = MeasureSpec.getSize(widthMeasureSpec)-getPaddingLeft()-getPaddingRight();
    int heightMode = MeasureSpec.getMode(heightMeasureSpec);
    int heightSize = MeasureSpec.getSize(heightMeasureSpec)+getPaddingTop()+getPaddingBottom();


    //ViewGroup宽高
    int viewGroupWidth = 0-getPaddingLeft()-getPaddingRight();
    int viewGroupHeight = getPaddingTop()+getPaddingBottom();

    if (widthMode == MeasureSpec.EXACTLY && heightMode == MeasureSpec.EXACTLY) {
        viewGroupWidth = widthSize;
        viewGroupHeight = heightSize;
    } else {
        //当前所占的宽高
        int currentLineWidth = 0;
        int currentLineHeight = 0;

        //用来存储每行上的子View
        List<View> lineView = new ArrayList<View>();
        int childViewsCount = getChildCount();
        for (int i = 0; i < childViewsCount; i++) {
            View childView = getChildAt(i);
            //对子View进行测量
            measureChild(childView, widthMeasureSpec, heightMeasureSpec);
            MarginLayoutParams marginLayoutParams = (MarginLayoutParams) childView.getLayoutParams();
            int childViewWidth = childView.getMeasuredWidth() + marginLayoutParams.leftMargin + marginLayoutParams.rightMargin;
            int childViewHeight = childView.getMeasuredHeight() + marginLayoutParams.topMargin + marginLayoutParams.bottomMargin;
            if (currentLineWidth + childViewWidth > widthSize) {
                //当前行宽+子View+左右外边距>ViewGroup的宽度,换行
                viewGroupWidth = Math.max(currentLineWidth, widthSize);
                viewGroupHeight += currentLineHeight;
                //添加行高
                mLineHeight.add(currentLineHeight);
                //添加行对象
                mLineViews.add(lineView);

                //new新的一行
                lineView = new ArrayList<View>();
                //添加行对象里的子View
                lineView.add(childView);
                currentLineWidth = childViewWidth;

            } else {
                //当前行宽+子View+左右外边距<=ViewGroup的宽度,不换行
                currentLineWidth += childViewWidth;
                currentLineHeight = Math.max(currentLineHeight, childViewHeight);
                //添加行对象里的子View
                lineView.add(childView);
            }

            if (i == childViewsCount - 1) {
                //最后一个子View的时候
                //添加行对象
                mLineViews.add(lineView);
                viewGroupWidth = Math.max(childViewWidth, viewGroupWidth);
                viewGroupHeight += childViewHeight;
                //添加行高
                mLineHeight.add(currentLineHeight);

            }
        }
    }
    setMeasuredDimension(viewGroupWidth, viewGroupHeight);
}

@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
    int left = getPaddingLeft();
    int top = getPaddingTop();
    //一共有几行
    int lines = mLineViews.size();
    for (int i = 0; i < lines; i++) {
        //每行行高
        int lineHeight = mLineHeight.get(i);
        //行内有几个子View
        List<View> viewList = mLineViews.get(i);
        int views = viewList.size();

        for (int j = 0; j < views; j++) {
            View view = viewList.get(j);
            MarginLayoutParams marginLayoutParams = (MarginLayoutParams) view.getLayoutParams();
            int vl = left + marginLayoutParams.leftMargin;
            int vt = top + marginLayoutParams.topMargin;
            int vr = vl + view.getMeasuredWidth();
            int vb = vt + view.getMeasuredHeight();
            view.layout(vl, vt, vr, vb);
            left += view.getMeasuredWidth() + marginLayoutParams.leftMargin + marginLayoutParams.rightMargin;
        }
        left = getPaddingLeft();
        top += lineHeight;

    }
}

@Override
public LayoutParams generateLayoutParams(AttributeSet attrs) {
    return new MarginLayoutParams(getContext(), attrs);
}
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值