瀏覽器渲染過程

解析HTML

當瀏覽器向服務器發(fā)出請求獲得頁面時遭商,服務器用二進制流返回一個HTML船殉,響應頭Content-Type=text/html; charset=UTF-8
如果不帶這個請求頭,瀏覽器會直接展示HTML文本,將如下代碼顯示在頁面中

<!DOCTYPE HTML>
<html>
    <head>
        <title>Rendering Test</title>
        <link rel="stylesheet" href="./style.css"/>
    </head>
    <body>
        <div class="container">
          <h1>Hello World!</h1>
          <p>This is a sample paragraph.</p>
        </div>
        <script src="./main.js"></script>
    </body>
</html>

構建DOM樹

瀏覽器獲得html后秤朗,開始解讀這個代碼,它為每一個html標簽創(chuàng)建Javascript Node笔喉。不過每一個標簽都有不同的屬性取视,所以它們的Class也不一樣,比如div使用HTMLDivElement創(chuàng)建

var divEle = document.querySelector('div.container');
divEle instanceof HTMLDivElement // true
divEle instanceof Node // true

Chrome提供DOMParserAPI用來構建DOM樹

const dom = new DOMParser();
dom.parseFromString('<div><h1>123</h1></div>', 'text/html'); // #document
DOM (Document Object Model)

以一個h標簽為例常挚,它的原型鏈大概是這個樣子:

h1 -> HTMLHeadingElement -> HTMLElement -> Element -> Node -> EventTarget -> Object

Javascript 本身不理解什么是DOM作谭,DOM是瀏覽器提供的web api,用來渲染頁面并且暴露給開發(fā)者用來操作DOM奄毡。
最終相互嵌套的html標簽被解讀成DOM樹折欠。

構建CSSOM樹

CSSOM (CSS Object Model),構建好DOM樹之后,瀏覽器從各處加載CSS資源(內(nèi)置锐秦,外部咪奖,user-agent,內(nèi)聯(lián))酱床,然后構建CSSOM樹赡艰,CSSOM樹的結構大致與DOM樹一致,但它不包含不會打印在頁面上的標簽斤葱。

構建Render樹

渲染樹是DOM樹和CSSOM樹的組合慷垮,它會排除掉那些不占地方的元素,比如display:none 和 長寬都為0的元素揍堕。

Layout & Paint

現(xiàn)在瀏覽器構建好了渲染樹料身,它就開始在頁面上繪制這些元素了。瀏覽器首先計算每個元素的大小和位置(以像素為單位)衩茸,這個過程是reflow(回流或者重排)芹血。然后是繪制 (Paint),本質(zhì)上就是填充像素的過程楞慈,包括繪制文字幔烛、顏色、圖像囊蓝、邊框和陰影等饿悬,也就是一個DOM元素所有的可視效果。一般來說聚霜,這個繪制過程是在多個層上完成的狡恬。最后是渲染層合并(Composite),將所有層按照合理的順序合并成一個圖層蝎宇。

到目前為止弟劲,構建DOM樹,CSSOM樹姥芥,處理渲染邏輯都是渲染引擎做的兔乞。這里列舉了一些市面上常見的渲染引擎。

name browser css suffix
Trident IE -ms
WebKit Safari -webkit
Blink Chrome Edge Opera -webkit
Gecko Firefox -moz
Blink Edge -ms

DOM Parser Block

一旦瀏覽器在解析html標簽時遇到外部資源凉唐,比如一個script file <script src="url"></script>庸追,一個樣式表<link rel="stylesheet" href="url"/>或者一張圖片
<img src="url" />,瀏覽器都會開始下載這些資源熊榛。
我們都知道锚国,解析DOM樹是在主線程上做的,如果主線程忙碌玄坦,DOM解析也暫停血筑。只有script會阻塞渲染绘沉。假如是內(nèi)嵌腳本,那么主線程會暫停解析DOM豺总,開始執(zhí)行腳本车伞;如果是外部文件,主線程同樣會暫停解析DOM喻喳,直至文件下載成功并且執(zhí)行完畢后才會繼續(xù)解析DOM另玖。至于為什么瀏覽器要這么做,因為瀏覽器將操作DOM的API暴露給了Javascript表伦,萬一腳本中有大量的操作DOM的邏輯谦去,等待DOM構建完畢再執(zhí)行,只會帶來更大的性能問題蹦哼。
但我們也知道鳄哭,很多時候這種阻塞是無意義的,比如腳本中如果沒有操作DOM的邏輯纲熏,此時妆丘,我們可以使用async屬性,帶有async的script標簽局劲,下載不會暫停主線程勺拣,但腳本一旦下載完畢,仍然需要占據(jù)主線程鱼填,阻塞渲染药有。我們還可以使用defer屬性,帶有這個屬性的script標簽不僅下載不會暫停主線程剔氏,下載之后也不需要立刻執(zhí)行塑猖,所有的defer腳本都是DOM樹構建好之后再執(zhí)行的竹祷,執(zhí)行順序組照他們在DOM樹中出現(xiàn)的順序谈跛。
很多時候我們說script阻塞了渲染(render-blocking,其實本質(zhì)上是阻塞了解析(parser-blocking)塑陵,因為阻塞了解析感憾,才阻塞了渲染。

剛才我們說css資源不是parser- blocking令花,只能說它沒有直接導致parser blocked阻桅,但某種情況確實會block parser。
當瀏覽器遇到外部內(nèi)聯(lián)樣式文件兼都,它首先會靜默下載嫂沉,此時DOM parsing不會被阻塞。但渲染樹的構建 (critical rendering path CRP) 會被暫停(后續(xù)的內(nèi)容暫時不會顯示在頁面上扮碧,但并不意味著頁面無內(nèi)容趟章,當瀏覽器加載到部分HTML字節(jié)流時即開始構建DOM樹杏糙,然后構建渲染樹,顯示在頁面上)蚓土。
假設我們的外部樣式標簽沒有寫在head里宏侍,就會出現(xiàn)頁面的樣式一直在更換的情況,我們稱之為Flash of Unstyled Content (FOUC)蜀漆,因此我們建議盡早加載所有的樣式文件谅河。
當正在加載樣式文件時遇到script標簽會發(fā)生什么呢?首先script標簽直接阻塞了DOM parser确丢,script標簽是否可以執(zhí)行呢绷耍?答案是不能,因為此時script標簽拿不到最新的樣式鲜侥,因此樣式文件加載會阻塞script execution锨天,間接的阻塞了DOM parser。
如何讓外部樣式表不阻塞render呢剃毒,可以加上media='non-render-blocking'

Loaded

+ DOMContentLoaded DCL事件意味著瀏覽器已經(jīng)完成了完整的DOM樹構建(意味著腳本執(zhí)行完畢病袄,CSSOM樹構建完成)。
+ load 其他資源文件也全部加載完畢

瀏覽器首屏會出現(xiàn)的問題

  1. 過長的加載時間
  2. 無格式頁面閃現(xiàn)或者樣式發(fā)生變化(FOUC)
  3. 加載不必要的資源
最后編輯于
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末赘阀,一起剝皮案震驚了整個濱河市益缠,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌基公,老刑警劉巖幅慌,帶你破解...
    沈念sama閱讀 216,470評論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異轰豆,居然都是意外死亡胰伍,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,393評論 3 392
  • 文/潘曉璐 我一進店門酸休,熙熙樓的掌柜王于貴愁眉苦臉地迎上來骂租,“玉大人,你說我怎么就攤上這事斑司∩” “怎么了?”我有些...
    開封第一講書人閱讀 162,577評論 0 353
  • 文/不壞的土叔 我叫張陵宿刮,是天一觀的道長互站。 經(jīng)常有香客問我,道長僵缺,這世上最難降的妖魔是什么胡桃? 我笑而不...
    開封第一講書人閱讀 58,176評論 1 292
  • 正文 為了忘掉前任,我火速辦了婚禮磕潮,結果婚禮上翠胰,老公的妹妹穿的比我還像新娘懊纳。我一直安慰自己,他們只是感情好亡容,可當我...
    茶點故事閱讀 67,189評論 6 388
  • 文/花漫 我一把揭開白布嗤疯。 她就那樣靜靜地躺著,像睡著了一般闺兢。 火紅的嫁衣襯著肌膚如雪茂缚。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,155評論 1 299
  • 那天屋谭,我揣著相機與錄音脚囊,去河邊找鬼。 笑死桐磁,一個胖子當著我的面吹牛悔耘,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播我擂,決...
    沈念sama閱讀 40,041評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼衬以,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了校摩?” 一聲冷哼從身側響起看峻,我...
    開封第一講書人閱讀 38,903評論 0 274
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎衙吩,沒想到半個月后互妓,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,319評論 1 310
  • 正文 獨居荒郊野嶺守林人離奇死亡坤塞,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,539評論 2 332
  • 正文 我和宋清朗相戀三年冯勉,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片摹芙。...
    茶點故事閱讀 39,703評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡灼狰,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出瘫辩,到底是詐尸還是另有隱情伏嗜,我是刑警寧澤,帶...
    沈念sama閱讀 35,417評論 5 343
  • 正文 年R本政府宣布伐厌,位于F島的核電站,受9級特大地震影響裸影,放射性物質(zhì)發(fā)生泄漏挣轨。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,013評論 3 325
  • 文/蒙蒙 一轩猩、第九天 我趴在偏房一處隱蔽的房頂上張望卷扮。 院中可真熱鬧荡澎,春花似錦、人聲如沸晤锹。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,664評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽鞭铆。三九已至或衡,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間车遂,已是汗流浹背封断。 一陣腳步聲響...
    開封第一講書人閱讀 32,818評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留舶担,地道東北人坡疼。 一個月前我還...
    沈念sama閱讀 47,711評論 2 368
  • 正文 我出身青樓,卻偏偏與公主長得像衣陶,于是被迫代替她去往敵國和親柄瑰。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 44,601評論 2 353

推薦閱讀更多精彩內(nèi)容