前两篇文章讲了一下自定义view中的OnMeasure这篇文章就来简单的说一下OnLayout()
OnLayout()在view中
/**
* Called from layout when this view should
* assign a size and position to each of its children.
*
* Derived classes with children should override
* this method and call layout on each of
* their children.
* @param changed This is a new size or position for this view
* @param left Left position, relative to parent
* @param top Top position, relative to parent
* @param right Right position, relative to parent
* @param bottom Bottom position, relative to parent
*/
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
}
它是一个空方法,没有实现,方法的注释大家可以详细的看下
在viewGroup 中
@Override
protected abstract void onLayout(boolean changed,
int l, int t, int r, int b);
是个抽象方法,也就是说onLayout只在view group中起作用,因为只有view group中才有子 view,如果自定义view group 则必须实现这个方法,很好理解啊,你包含子view,测量出来大小了,你得告诉我在具体哪个位置显示啊。
下面这段代码就是下篇文章中具体讲解自定义view group中的onLayout()先拿过来用一下了
@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
page = 0;
int row = 0; //每页六行,默认第0行,到第七行换页
int flowWidth = getWidth();
int childLeft = 0;
int childTop = 0;
//遍历子控件,记录每个子view的位置
for (int i = 0, childCount = getChildCount(); i < childCount; i++) {
View childView = getChildAt(i);
//跳过View.GONE的子View
if (childView.getVisibility() == View.GONE) {
continue;
}
//获取到测量的宽和高
int childWidth = childView.getMeasuredWidth();
int childHeight = childView.getMeasuredHeight();
//因为子View可能设置margin,这里要加上margin的距离
MarginLayoutParams mlp = (MarginLayoutParams) childView.getLayoutParams();
if (childLeft + mlp.leftMargin + childWidth + mlp.rightMargin > (flowWidth+page*flowWidth)) {
//换行处理
childTop += (mlp.topMargin + childHeight + mlp.bottomMargin);
childLeft = 0+page*flowWidth;
row ++;
}
//换页处理
if ((row!=0)&&(row%6 == 0)) {
//换行处理
childTop = 0;
page++;
childLeft = 0+page*flowWidth;
row = 0;
}
//布局
int left = childLeft + mlp.leftMargin;
int top = childTop + mlp.topMargin;
int right = childLeft + mlp.leftMargin + childWidth;
int bottom = childTop + mlp.topMargin + childHeight;
childView.layout(left, top, right, bottom);
childLeft += (mlp.leftMargin + childWidth + mlp.rightMargin);
}
}
具体view中渲染的方法是这行代码,其他的都是再计算要把子 view放在哪里
childView.layout(left, top, right, bottom);
onLayout很简单吧,咱也别老讲理论知识了,下篇文章以FlowTagLayout为例,用代码写一下流式标签布局,在代码中细细的体会
冰冻三尺,非一日之寒~大家一起努力~