Android 繪制流程
問(wèn)題:Android繪制流程是怎么樣的顽铸?
ActivityThread.handleLaunchActivity()中完成準(zhǔn)備工作谓松,Activity.attach創(chuàng)建PhoneWindow Activity.onCreate的setContent
ActivityThread.handleResumeActivity()中調(diào)用WindowManager.addView把DecorView傳入鬼譬,實(shí)例化一個(gè)ViewRootImpl對(duì)象后通過(guò)Handler向主線程發(fā)送了一條觸發(fā)遍歷操作的消息,開(kāi)始View的三大流程优质。
Activity
Activity并不負(fù)責(zé)視圖控制竣贪,它只是控制生命周期和處理事件。
真正控制視圖的是Window巩螃。
一個(gè)Activity包含了一個(gè)Window演怎。
Window
Window是視圖的承載器,內(nèi)部持有一個(gè) DecorView牺六。
Window是一個(gè)抽象類颤枪,實(shí)際在Activity中持有的是其子類PhoneWindow。
Window通過(guò)WindowManager將DecorView加載其中淑际,并將DecorView交給ViewRoot畏纲,進(jìn)行視圖繪制以及其他交互。
DecorView
頂層View春缕,即 Android 視圖樹(shù)的根節(jié)點(diǎn)盗胀;同時(shí)也是 FrameLayout 的子類。
顯示 & 加載布局锄贼。View層的事件都先經(jīng)過(guò)DecorView票灰,再傳遞到View內(nèi)含1個(gè)豎直方向的LinearLayout,分為2部分:
- 上 = 標(biāo)題欄(titlebar)
- 下 = 內(nèi)容欄(content)
ViewRoot
ViewRoot可能比較陌生宅荤,但是其作用非常重大屑迂。所有View的繪制以及事件分發(fā)等交互都是通過(guò)它來(lái)執(zhí)行或傳遞的。
ViewRoot對(duì)應(yīng)ViewRootImpl類冯键,它是連接WindowManagerService和DecorView的紐帶惹盼,View的三大流程(測(cè)量(measure),布局(layout)惫确,繪制(draw))均通過(guò)ViewRoot來(lái)完成手报。
流程 基于Android7 Android8會(huì)有差別(EXECUTE_TRANSACTION)
ActivityThread.handleLaunchActivity
ActivityThread.performLaunchActivity
Application.onCreate
Activity.performCreate
Activity.onCreate
Activity.performRestoreInstanceState
Activity.onRestoreInstanceState
ActivityThread.handleResumeActivity
ActivityThread.performResumeActivity
Activity.performResume
Activity.performRestart
Activity.onRestart
Activity.onStart
Activity.onResume
ActivityThread.handleLaunchActivity()
里performLaunchActivity()
有Activity.attach()
中創(chuàng)建PhoneWindow。
調(diào)用Activity的onCreate方法改化,setContentView()掩蛤,調(diào)用Window類實(shí)例的setContentView進(jìn)行inflate。
ActivityThread.handleResumeActivity()
getWindowManager陈肛,其實(shí)現(xiàn)類是WindowManagerImpl揍鸟,調(diào)用實(shí)現(xiàn)類的addView方法,add DecorView到WindowManager中
WindowManagerImpl.addView()
WindowManagerGlobal.addView()
實(shí)例化一個(gè)ViewRootImpl對(duì)象
ViewRootImpl.setView()
ViewRootImpl.requestLayout()
ViewRootImpl.scheduleTraversals()
通過(guò)Handler
向主線程發(fā)送了一條觸發(fā)遍歷操作的消息
ViewRootImpl.doTraversal()
ViewRootImpl.performTraversals()
最終performTraversals()方法觸發(fā)了View的繪制燥爷。該方法內(nèi)部蜈亩,依次調(diào)用了performMeasure(),performLayout(),performDraw(),將View的measure懦窘,layout,draw過(guò)程稚配,從頂層View分發(fā)了下去畅涂。
measure layout draw
測(cè)量:父View調(diào)用子View measure()方法,傳入建議值道川,子類onMeasure() setMeasuredDimension
布局:父ViewGroup在onLayout()中調(diào)用子View layout()方法進(jìn)行定位
繪制
- 背景 drawBackground()
- 主體(
onDraw()
) - 子 View(
dispatchDraw()
) - 滑動(dòng)邊緣漸變和滑動(dòng)條 onDrawScrollbars()
- 前景
參考
http://gityuan.com/2017/01/22/start-activity-wms/
https://zhuanlan.zhihu.com/p/44976896 集中在后部分
https://jsonchao.github.io/2018/10/28/Android%20View%E7%9A%84%E7%BB%98%E5%88%B6%E6%B5%81%E7%A8%8B/ 一般
剖析Activity午衰、Window、ViewRootImpl和View之間的關(guān)系http://www.reibang.com/p/a7596afb1aa1