自定义View-计算控件尺寸

本文主要是自己学习的笔记,想学习的建议直接去看HenCoder视频教学地址

不同于上一篇:修改控件尺寸,有些时候需要自己计算控件尺寸而不是修改已经计算好的,所以在重写onMeasure的时候,就不需要调用super. onMeasure(),直接自己去算好宽高,然后setMeasuredDimension设置进去就好了。

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        ...
        // 自定义宽高
        width = ...;
        height = ...;

        // 过滤宽高(检查宽高是否合格)
        width = resolveSize(width, widthMeasureSpec);
        height = resolveSize(height, heightMeasureSpec);

        // 设置宽高
        setMeasuredDimension(width, height);
    }

上面代码有很重要的一步:resolveSize(),因为控件并不是想自己大多就能多大,我们算好的尺寸,或者说希望的尺寸,并不一定能成为最后的尺寸,比如父控件空间不足。所以要调用resolveSize去过滤一下,resolveSize是View中已经实现了的方法,点击去看下具体做了什么事情,resolveSize的代码大致如下:

    // resolveSize的简化实现,并不是完整源码
    public static int resolveSize(int size, int measureSpec){
        
        final int specMode = MeasureSpec.getMode(measureSpec);
        final int specSize = MeasureSpec.getSize(measureSpec);
        final int result;
        
        switch (specMode) {
            case MeasureSpec.AT_MOST:
                if (specSize < size) {
                    result = specSize;
                } else {
                    result = size;
                }
                break;
            case MeasureSpec.EXACTLY:
                result = specSize;
                break;
            case MeasureSpec.UNSPECIFIED:
            default:
                result = size;
        }
        return result ;
    }

在onMeasure中的两个参数widthMeasureSpec、heightMeasureSpec并不只包含了size,还包含了mode,mode只指父控件对其的限制,有三种AT_MOST(最大值)、EXACTLY(精确值)、UNSPECIFIED(无限制)。

resolveSize方法分析:

调用resolveSize过滤其实就是根据mode计算出准确的size返回,而并非子控件想自己多大就大多。
size:我们计算出来的值,也可以说是子控件自己希望的值。
specSize:从onMeasure的参数中获取的,是父控件调用子控件的measure()方法的时候传入的,是父控件对子控件的限制。

  • 当mode是AT_MOST,就是父控件规定了子控件的最大值,specSize就是这个最大值,所以:
return Math.min(size, specSize)
  • 当mode为EXACTLY,就是父控件要精确的控制子控件大小,子控件的大小必须是specSize,所以:
return specSize

当mode为UNSPECIFIED,也就是父控件对子控件没限制,子控件的大小可以为其自己希望的大小,所以:

return size

感谢HenCoder

    原文作者:CoderYuZ
    原文地址: https://www.jianshu.com/p/4b6668719be4
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞