MeasureSpec 的三中类型
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/root" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".MainActivity" > <!-- --> <FrameLayout android:layout_width="match_parent" android:layout_height="wrap_content" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="match_parent" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="wrap_content" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="wrap_content" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="wrap_content" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="100dp" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="match_parent" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="match_parent" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="match_parent" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="wrap_content" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="match_parent" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="100dp" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="100dp" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="match_parent" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="100dp" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="wrap_content" > </com.example.test.MeasTestLayout> </FrameLayout> <FrameLayout android:layout_width="match_parent" android:layout_height="100dp" > <com.example.test.MeasTestLayout android:layout_width="match_parent" android:layout_height="50dp" > </com.example.test.MeasTestLayout> </FrameLayout> </FrameLayout>
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { // TODO Auto-generated method stub super.onMeasure(widthMeasureSpec, heightMeasureSpec); print(widthMeasureSpec, heightMeasureSpec); } private void print(int widthMeasureSpec, int heightMeasureSpec){ int widthMode = MeasureSpec.getMode(widthMeasureSpec); int heightMode = MeasureSpec.getMode(heightMeasureSpec); log("begin>>>"); log("width -- mode: "+getMode(widthMode) +" size: "+MeasureSpec.getSize(widthMeasureSpec)); log("height -- mode: "+getMode(heightMode) +" size: "+MeasureSpec.getSize(heightMeasureSpec)); log("<<<"); }
11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: AT_MOST size: 1599->1467 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: AT_MOST size: 1599->1467 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: EXACTLY size: 275 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: EXACTLY size: 1599->1467 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: AT_MOST size: 1599->1467 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: EXACTLY size: 275 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: EXACTLY size: 275 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: AT_MOST size: 275 11-16 15:19:27.155: D/View(8127): measure: <<< 11-16 15:19:27.155: D/View(8127): measure: begin>>> 11-16 15:19:27.155: D/View(8127): measure: width -- mode: EXACTLY size: 1080 11-16 15:19:27.155: D/View(8127): measure: height -- mode: EXACTLY size: 138 11-16 15:19:27.155: D/View(8127): measure: <<<
结论:1、自定义控件中的onMeasure方法接收的参数的Mode与它的父控件的w、h以及它自身的宽高有关
2、如果自定义控件自身的高度为固定的dp值,传入的参数的mode一定是EXACTLY
3、如果自定义控件自身的高度为wrap_content,传入的参数的mode一定是AT_MOST
4、如果自定义控件自身的高度为match_parent,其父控件的高度为固定dp值,传入的参数的mode一定是EXACTLY
5、如果自定义控件自身的高度为match_parent,其父控件的高度为wrap_content,传入的参数的mode一定是AT_MOST
6、如果自定义控件自身的高度为match_parent,其父控件的高度为match_parent,传入的参数的mode依赖更上层的父控件,并且可能在多次onMeasure中变化
7、MeasureSpec.UNSPECIFIED是未指定尺寸,这种情况不多,一般都是父控件是AdapterView,通过measure方法传入的模式。