上传图片控件自定义,流式布局

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/jakezhang1990/article/details/81908782

控件模仿微信的,点击“+”上传图片,封装为一个控件,实现流式布局,超过一行自动换行排布。
这个流式布局的作用只是,排布,摆放,具体展示的图片是通过将xml布局inflate然后添加到该流式布局中来实现的。

package com.family.fw.view;

import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build;
import android.util.AttributeSet;
import android.view.View;
import android.view.ViewGroup;

/**
 * 流式布局。可根据子View的宽度实现自动换行。
 * 
 */
public class FlowLayout extends ViewGroup {

    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
    public FlowLayout(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
    }

    public FlowLayout(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    public FlowLayout(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public FlowLayout(Context context) {
        super(context);
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        int[] size = measure(this, widthMeasureSpec, heightMeasureSpec);
        setMeasuredDimension(size[0], size[1]);
    }

    static int[] measure(ViewGroup group, int widthMeasureSpec, int heightMeasureSpec) {
        int width = resolveSize(0, widthMeasureSpec);

        int pl = group.getPaddingLeft();
        int pt = group.getPaddingTop();
        int pr = group.getPaddingRight();
        int pb = group.getPaddingBottom();

        int left = pl;
        int top = pt;
        int right = width - pr;
        int lineHeight = 0;

        // 通过计算每一个子控件的高度,得到自己的高度
        for (int i = 0, childCount = group.getChildCount(); i < childCount; ++i) {
            View child = group.getChildAt(i);
            if (child.getVisibility() == View.GONE) {
                continue;
            }

            MarginLayoutParams layout = (MarginLayoutParams) child.getLayoutParams();
            child.measure(getChildMeasureSpec(widthMeasureSpec, pl + pr, layout.width),
                    getChildMeasureSpec(heightMeasureSpec, pt + pb, layout.height));

            int cow = child.getMeasuredWidth() + layout.leftMargin;
            int coh = child.getMeasuredHeight() + layout.topMargin + layout.bottomMargin;
            left += cow;

            if (left > right) {
                left = pl + cow;
                top += lineHeight;
                lineHeight = coh;
            } else if (coh > lineHeight) {
                lineHeight = coh;
            }
            left += layout.rightMargin;
        }

        return new int[] { width, resolveSize(top + lineHeight + pb, heightMeasureSpec) };
    }

    @Override
    protected void onLayout(boolean changed, int l, int t, int r, int b) {
        layout(this, changed, l, t, r, b);
    }

    static void layout(ViewGroup group, boolean changed, int l, int t, int r, int b) {
        int pl = group.getPaddingLeft();
        int left = pl;
        int top = group.getPaddingTop();
        int right = r - l - group.getPaddingRight();

        int lineHeight = 0;
        // 根据子控件的宽高,计算子控件应该出现的位置。
        for (int i = 0, childCount = group.getChildCount(); i < childCount; ++i) {
            View child = group.getChildAt(i);
            if (child.getVisibility() == View.GONE) {
                continue;
            }

            MarginLayoutParams layout = (MarginLayoutParams) child.getLayoutParams();
            int cw = child.getMeasuredWidth();
            int ch = child.getMeasuredHeight();
            int ml = layout.leftMargin;
            int mt = layout.topMargin;
            int thisH = ch + mt + layout.bottomMargin;
            left += ml;

            if (left + cw > right) {
                left = pl + ml;
                top += lineHeight;
                lineHeight = thisH;
            } else {
                lineHeight = Math.max(thisH, lineHeight);
            }
            child.layout(left, top + mt, left + cw, top + mt + ch);
            left += cw + layout.rightMargin;
        }
    }

    @Override
    public LayoutParams generateLayoutParams(AttributeSet attrs) {
        return new MarginLayoutParams(getContext(), attrs);
    }

}

在xml布局中:

<com.family.fw.view.FlowLayout
    android:id="@+id/evaluationImgs"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:paddingLeft="20dp"
    android:paddingRight="20dp" >

    <ImageView
      android:id="@+id/img"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:layout_marginTop="10dp"
      android:background="@drawable/advice_image"
      android:contentDescription="@string/desc"
      android:scaleType="centerCrop"
      round:radius="5dp" />
  </com.family.fw.view.FlowLayout>

效果图:
上传图片2

上传图片1

猜你喜欢

转载自blog.csdn.net/jakezhang1990/article/details/81908782