Choreographer是什么
Choreographer主要用来申请垂直脉冲信号,指导ViewRootImpl完成屏幕刷新
Choreographer也可以用来监听卡顿,监听的api=postFrameCallback
源码分析
讲Choreographer要从ViewRootImpl开始讲起
- scheduleTraversals是Chorographer工作的起点
应用在requestLayout,invalidate后都会开始调用ViewRootImpl.scheduleTraversals来调度Choreographer
- ViewRootImpl.scheduleTraversals
关于下图中的mTraversalRunnable,它会在适当的时机被Choreographer回调,回调后会依次执行ViewRootImpl.doTraversal方法--> performTraversals。其中performTraversals就是用来处理View中子view 的布局、测量、绘制的。
- Choreographer.postCallback方法
这里就是Choreographer申请垂直脉冲信号的开始
这里代码最终会执行到postCallbackDelayedInternal方法
- Choreographer.postCallbackDelayedInternal
- scheduleFrameLocked方法
以下的方法最终都会调度到scheduleVsyncLocked方法处理
- scheduleVsyncLocked方法
- FrameDisplayEventReceiver.scheduleVsync方法
方法实现在FrameDisplayEventReceiver的子类DisplayEventReceiver中
nativeScheduleVsync用来申请脉冲垂直信号,当下一个信号到来的时候会回调FrameDisplayEventReceiver的onVsync方法
为什么下一个vsync信号能回调到我们呢?看下图
- 前面的流程讲的实际就是申请vsync信号的流程,下面就到了我们处理vsync信号的逻辑中。
- FrameDisplayEventReceiver.run方法逻辑
- doFrame
- 上一步的关键方法是doCallbacks,那么我们看看doCallbacks方法的逻辑是如何的
这个方法看完,我们Choreographer刷新的逻辑就完成闭环了。一切看起来不过如此简单而已
总结
流程总结描述
Choreographer源码要从ViewRootImpl说起,当我们调用requestLayout或invalidate方法的时候,最终会回调到ViewRootImpl的schedulerTraversal方法,最终经过几次简单调用会调用Choreographer.postCallbacks方法(将TraversalRunnable作为postCallbacks方法参数传入)。
然后Choreographer会去调用底层申请vsync信号,当下一个vsync信号到达的时候,Choreographer会遍历mCallbackQueues中的所有回调类型。最后会回调TraversalRunnable.run方法,后面的逻辑ViewRootImpl会帮助我们完成ui的绘制流程。