View的绘制机制

一、view树的绘制流程

        mesure(是否重新计算视图大小)->layout(是否从新安置视图位置)->draw(是否需要重绘)         

二、measure

    

mesure的测量是一个树的递归过程,重上到下有序进行遍历,根据父容器对子容器的测量规格和参数获取子容器的长宽高,然后把子容器的长宽高返回给父容器进行统一的测量。

        1、ViewGroup.LayoutParams:就是指定视图宽高的参数

                (1)指定一个确定的值;

                (2)MATCH_PARENT:

                (3)WRAP_CONTEXT;

        2、MesureSpec:测量规格,代表一个32位的值,高两位代表SpecMode,低30位标识SpecSize,SpecMode是指测量模式,而specSize是指在某种测量模式下的规格大小。 

                

UNSPECIFIED

父容器不对View有任何限制,要多大给多大,这种情况一般用于系统内部,表示一种测量的状态。

EXACTLY

父容器已经测量出View所需要的精确大小,这个时候View的最终大小就是SpecSize所指定的值。它对应于LayoutParams中的match_parent和具体的数值这两种模式。

AT_MOST

父容器指定了一个可用大小即SpecSize,View大小不能大于这个值,具体是什么值要看不同View的具体实现。它对应于LayoutParams中的Wrap_content 

    3、onMeasure:在之前的measure方法中获取了宽高的测量规格,并且传递到onMeasure方法中。onMeasure方法中获得计算的尺寸传给onMeasure中的setMeasureDimension方法。

      4、setMeasureDimension:这是一个测量计算结束最终决定view的大小的方法,在重写onMeasure中这个方法必须要调用的,否则会出现异常。


三、Layout

        跟measure一样,同样是跟图中的自上而下进行遍历,在这个过程中Layout方法会根据测量的尺寸摆放子视图的位置,子视图的位置是相对于父视图而言的,所以View.onLayout方法是空实现,在自定义view中继承ViewGroup的话就要实现onLayout这个方法。

        

在LinearLayout中他实现了onLayout方法,所以他分成了垂直布局和水平布局。



在他的垂直布局方法中有这么一个循环,他遍历每一个子View然后取出他们的宽高,还有就是根据下面子VIew的LayoutParama的测量规格,最终利用这些测量参数会调用serChildFrame方法去绘制子View中屏幕中的位置。

四、draw

        在经过了测量和摆放之后,就可以在屏幕上绘制流程。

        draw中两个容易混淆的方法:

        (1)、invalidate():当调用的时候就是请求安卓系统,如果视图大小没有变化就不会调动onLayout这个试图摆放方法。

        (2)、requestLayout():当布局的尺寸、方向发生变化的时候我们就会手动去调用这个方法,这个方法就会触发meare、layout过程,但是不会调用draw方法。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值