MeasureSpec内容

项目中看见一行代码很有趣,自定义了一个gridview。这个自定义中 重写了 onmeasure方法:

public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        int expandSpec = MeasureSpec.makeMeasureSpec(Integer.MAX_VALUE >> 2,
                MeasureSpec.AT_MOST);
        super.onMeasure(widthMeasureSpec, expandSpec);

    }

没见过啊 然后我就研究一下 发现蛮有趣的。

这串代码的背景::可能经常遇到嵌套ListView、ScrollView的问题,百度一搜,都是现成的代码,而且都是一样的,就是重写onMeasure方法

首先 在 Android里面,用32位的int值来表示一个控件的模式与大小。

模式用最高两位表示:

      private static final int MODE_SHIFT = 30;

    • public static final int UNSPECIFIED = 0 << MODE_SHIFT;
    • public static final int EXACTLY = 1 << MODE_SHIFT;(相当于match——parent)
    • public static final int AT_MOST = 2 << MODE_SHIFT;(相当于wrap——content)

      不确定模式是0左移30位,也就是int类型的最高两位是00
      精确模式是1左移30位,也就是int类型的最高两位是01
      最大模式是是2左移30位,也就是int类型的最高两位是10kop

低位30位表示大小。

所以Integer.MAX_VALUE >> 2就是将 Integer.MAX_VALUE这个32位的值右移两位 。就保留下了 大小  也就是size值。

MeasureSpec.AT_MOST 这个模式值就相当于 给出了 模式值 这个 32位数的前两位。

以此,MeasureSpec的makeMeasureSpec的方法根据输入的大小值 与模式值来生成一个32位t值,这个int值封装了模式和大小信息

再通过 MeasureSpec的两个组装方法:

public static int getMode(int measureSpec),这个方法的作用是通过一个int值来获取里面的模式信息
public static int getSize(int measureSpec),这个方法的作用是通过一个int值来获取里面的大小信息

最后super.onMeasure(widthMeasureSpec, expandSpec);实现onmeasure全部功能。

 

最后根据这个例子讲一下怎么理解这一串代码:

给出了控件最大极限的size(实际不可能这么大),与 atmost模式   就是说 根据32位值 计算调整 将结果的大小值传递给父控件。

super.onMeasure(widthMeasureSpec, expandSpec);说明 调整的只是 高度  宽度不改变。

 

posted @ 2017-07-26 11:53  callMeVita  阅读(289)  评论(0编辑  收藏  举报