子View們的寬度加起來超過一行,會自動換行顯示。java
核心就兩步:git
再複雜的自定義View都是這樣從最簡單的形式,不斷增長代碼,迭代出來的 github
最簡單的自定義ViewGroup:app
public class FlowLayout extends ViewGroup { public FlowLayout(Context context) { this(context, null); } public FlowLayout(Context context, AttributeSet attrs) { this(context, attrs, 0); } public FlowLayout(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); int childCount = getChildCount(); for (int i = 0; i < childCount; i++) { measureChild(getChildAt(i), widthMeasureSpec, heightMeasureSpec); } } @Override protected void onLayout(boolean changed, int l, int t, int r, int b) { int childCount = getChildCount(); int layoutWidth = r-l; int left = 0; int right = 0; int top = 0; for (int i = 0; i < childCount; i++) { View view = getChildAt(i); // 換行:比較right,right若是大於Layout寬度,那麼要換行 right = left + view.getMeasuredWidth(); if (right > layoutWidth) { left = 0; right = left + view.getMeasuredWidth(); top += view.getMeasuredHeight(); } getChildAt(i).layout(left, top, right, top + view.getMeasuredHeight()); left += view.getWidth(); } } }
上述這些我也都實現了,但還有一個我沒有去弄,對gravity的支持(由於其非必需就暫時不加,我現有其它事),若是你有興趣完成它,能夠fork,弄好了pull request。ide
完整代碼查看this