赞
踩
在oncreate方法中加载解析完xml资源创建view对象之后,Activity中的makeVisible方法会将这些对象依次测量,确定位置并且显示在幕布上。总体的流程图如下,
重点分析onMeasure,onLayout,和onDraw方法。
measure是测量的意思,那么onMeasure()方法顾名思义就是用于测量视图的大小的.
首先看没有子view的测量方法.
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- setMeasuredDimension(getDefaultSize(getSuggestedMinimumWidth(), widthMeasureSpec),
- getDefaultSize(getSuggestedMinimumHeight(), heightMeasureSpec));
- }
public static int getDefaultSize(int size, int measureSpec) { int result = size; int specMode = MeasureSpec.getMode(measureSpec); int specSize = MeasureSpec.getSize(measureSpec); switch (specMode) { case MeasureSpec.UNSPECIFIED: result = size; break; case MeasureSpec.AT_MOST: case MeasureSpec.EXACTLY: result = specSize; break; } return result; }
MeasureSpec的值由specSize和specMode共同组成的,其中specSize记录的是大小(后30位),specMode记录的是规格(前2位). specMode一共有三种类型。
变量widthMeasureSpec和heightMeasureSpec都是ViewRoot的performTraversals方法中获取的,
- int childWidthMeasureSpec = getRootMeasureSpec(mWidth, lp.width);
- int childHeightMeasureSpec = getRootMeasureSpec(mHeight, lp.height);
private static int getRootMeasureSpec(int windowSize, int rootDimension) { int measureSpec; switch (rootDimension) { case ViewGroup.LayoutParams.MATCH_PARENT: // Window can't resize. Force root view to be windowSize. measureSpec = MeasureSpec.makeMeasureSpec(windowSize, MeasureSpec.EXACTLY); break; case ViewGroup.LayoutParams.WRAP_CONTENT: // Window can resize. Set max size for root view. measureSpec = MeasureSpec.makeMeasureSpec(windowSize, MeasureSpec.AT_MOST); break; default: // Window wants to be an exact size. Force root view to be that size. measureSpec = MeasureSpec.makeMeasureSpec(rootDimension, MeasureSpec.EXACTLY); break; } return measureSpec; }
根视图总是会充满全屏的。
既然子view都实现了o
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。