美文网首页
自定义流式布局 MyFlowLayout

自定义流式布局 MyFlowLayout

作者: sometimes_ | 来源:发表于2018-08-04 14:30 被阅读0次

自定义流式布局,只对match_parent、padding进行了处理、子view的margin未进行处理(可通过horizontal_spacing属性处理子view水平间距 ,vertical_spacing处理行间距)

排版修复版,点击查看https://www.jianshu.com/p/28e7eb3039ab

一、基本实现逻辑

1.成员

private float vertical_spacing= 20f; //默认行间距

private float horizontal_spacing = 20f;//默认view间距

2.读取自定义属性,赋值间距

@SuppressLint("CustomViewStyleable")

TypedArray array= context.obtainStyledAttributes(attrs, R.styleable.MyFlowLayout);

horizontal_spacing = array.getDimension(R.styleable.MyFlowLayout_horizontal_spacing, horizontal_spacing);

vertical_spacing = array.getDimension(R.styleable.MyFlowLayout_vertical_spacing, vertical_spacing);

array.recycle();

3.重写onMeasure、onLayout方法

@Override

protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {

    int width= MeasureSpec.getSize(widthMeasureSpec);

    int mode_width= MeasureSpec.getMode(widthMeasureSpec);

    int currentLineUsedWidth= getPaddingLeft() + getPaddingRight();

    int parentViewHeight= getPaddingTop() + getPaddingBottom();

    if (mode_width!= MeasureSpec.EXACTLY) {

        throw new Error("Pleach set view width_size to Match_parent");

    } else {

        //由于flowLayout设置最大  只需计算 高度就可

        int childSize= getChildCount();

        for (int i= 0; i< childSize; i++) {

            View view= getChildAt(i);

            measureChild(view, widthMeasureSpec, heightMeasureSpec);

            if (i== 0) {

                parentViewHeight+= view.getMeasuredHeight();

            }

            if (currentLineUsedWidth!= getPaddingLeft() + getPaddingRight() &&

                    view.getMeasuredWidth() + horizontal_spacing > width- currentLineUsedWidth) {

                currentLineUsedWidth= getPaddingLeft() + getPaddingRight(); //重置下一行宽

                parentViewHeight+= view.getMeasuredHeight() + vertical_spacing;

            }

            if (currentLineUsedWidth!= getPaddingLeft() + getPaddingRight()) {

                currentLineUsedWidth+= horizontal_spacing;

            }

            currentLineUsedWidth+= view.getMeasuredWidth();

            }

            }

    setMeasuredDimension(width, parentViewHeight);

}

@Override

protected void onLayout(boolean changed, int l, int t, int r, int b) {

    //定位所有子view的位置  左上右下

    int width= getMeasuredWidth();

    int lastViewHeight= 0;

    int size= getChildCount();

    int left= getPaddingLeft();

    int top= getPaddingTop();

    int right;

    int bottom;

    for (int i= 0; i< size; i++) {

        View view= getChildAt(i);

        //定位当前子view位置

        int view_height= view.getMeasuredHeight();

        int viwe_width= view.getMeasuredWidth();

        if (viwe_width+ getPaddingRight() > width- left) {

            //换行定位

            left= getPaddingLeft();

            top+= lastViewHeight+ vertical_spacing;

        }

        right= left+ viwe_width;

        bottom= top+ view_height;

        view.layout(left, top, right, bottom);

        lastViewHeight= view_height;

        left+= viwe_width+ horizontal_spacing; //加上间距

    }

}

二、自定义属性

  <attr name = "vertical_spacing" format ="dimension"/>

  <attr name ="horizontal_spacing" format="dimension"/>

相关文章

网友评论

      本文标题:自定义流式布局 MyFlowLayout

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