View刷新机制

View刷新中的疑问

解释View刷新机制之前,我们先看看平时可能遇到的一些疑问:

  1. 我们都知道Android每隔16.6ms刷新一次屏幕,是指每隔16.6ms调用一次onDraw()?
  2. 如果当前界面没有任何变化,还会每隔16.6ms刷新一次屏幕吗?
  3. 我们调用完了view的invalidate()方法或者对界面的一些操作后,屏幕会马上刷新吗?
  4. 我们说的主线程耗时会导致丢帧,这丢帧到底是怎么发生的?

显示系统基本概念

显示系统分为:CPU、GPU、Display三个部分

  • CPU负责计算数据,把计算好的数据交给GPU
  • GPU会对图形数据进行渲染,渲染好后放到buffer里存起来
  • Display负责把buffer里的数据呈现到屏幕上

对于Android,CPU计算数据就是指的View树的绘制过程,包含每个View的测量、布局、绘制 我们常说的Android每隔16.6ms刷新一次屏幕其实是指:底层以固定的频率将buffer里的屏幕数据显示出来

  1. 底层以固定频率发出VSync信号,这个固定频率也就是我们说的16.6ms间隔。
  2. 刷新信号到的时候CPU开始计算下一帧数据。
  3. 刷新信号到的时候,屏幕切换下一帧画面。

解答疑问

  1. 我们说的16.6ms刷新一次屏幕其实是指底层会以这个固定频率来切换每一帧画面。
  2. CPU绘制视图是等刷新信号来的时候才开始计算下一帧数据的,而当这个计算工作完成后,也不会马上显示出来,而是等下个信号来的时候才交由底层将数据显示出来。

遗留疑问:为什么界面不刷新app就接收不到刷新信号?              

                 为什么绘制视图的计算是等屏幕刷新信号来的时候才开始的? 

Read The Fucking Source Code

ViewRootImpl

我们知道DecorView是整个ViewTree的最顶层View,是一个ViewGroup。 而DecorView的parent又是ViewRootImpl(具体DecorView和ViewRootImpl是怎么绑定上的可以在Activity的启动中找到,这里就不做详细解释了),所有跟View刷新相关的操作,循环找parent时都会走到ViewRootImpl里来。

我们以invalidate()为例来看看View的刷新机制

子view的invalidate(),最终走到了父布局ViewGroup的invalidateChild()方法

通过一个do while循环查找父布局,最终指向了ViewRootImpl的invalidateChildInParent()方法

最后走到了ViewRootImpl的scheduleTraversals()

小结

View的invalidate()方法,通过一系列条件判断和循环查找父布局的工作,最终走到ViewRootImpl的scheduleTraversals()方法里。 类似,除了invalidate(),requestLayout()、requestFocus()、Animation等等跟View相关的刷新操作,最后也都会走到这个方法里。

scheduleTraversals()

  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值