前端性能優化:寫出高性能的JavaScript

減少瀏覽器的repaint/reflow

1.什麼是瀏覽器的repaint/reflow

頁面在加載的過程中,需要對文檔結構進行解析,同時需要結合各種各樣的樣式來計算這個頁面長什麼樣子,最後再經過瀏覽器的渲染頁面就出現了。這整個過程細說起來還是比較複雜,其中充滿了repaint和reflow。對於DOM結構中的各個元素都有自己的盒子模型,這些都需要瀏覽器根據各種樣式(瀏覽器的、開發人員定義的等)來計算並根據計算結果將元素放到它該出現的位置,這個過程稱之爲reflow;當各種盒子的位置、大小以及其他屬性,例如顏色、字體大小等都確定下來後,瀏覽器於是便把這些元素都按照各自的特性繪製了一遍,於是頁面的內容出現了,這個過程稱之爲repaint。

在頁面加載完成後,用戶的一些操作、腳本的一些操作都會導致瀏覽器發生這種行爲。

2.如何觸發瀏覽器的repaint/reflow

DOM元素的添加、修改(內容)、刪除( Reflow + Repaint) 僅修改DOM元素的字體顏色(只有Repaint,因爲不需要調整佈局) 應用新的樣式或者修改任何影響元素外觀的屬性 Resize瀏覽器窗口、滾動頁面 讀取元素的某些屬性(offsetLeft、offsetTop、offsetHeight、offsetWidth、scrollTop/Left/Width/Height、clientTop/Left/Width/Height、getComputedStyle()、currentStyle(in IE))

3.爲什麼要避免repaint/reflow

每一次觸發repaint/reflow都會導致祖先節點和子節點重新渲染

4.如何避免觸發repaint/reflow

Fast because there’s no repaint/reflow(通過避免repaint/reflow提高js性能) Techniques:
  • –Remove element from the document, make changes, insert back into document( 先將元素從document中刪除,完成修改後再把元素放回原來的位置)
  • –Set element’s display to “none”, make changes, set display back to default(將元素的display設置爲”none”,完成修改後再把display修改爲原來的值)
  • –Build up DOM changes on a DocumentFragment then apply all at once(如果需要創建多個DOM節點,可以使用DocumentFragment創建完後一次性的加入document)

DocumentFragment

JS中提供了一個DocumentFragment的機制,相信大家對這個並不陌生,它可以提供一個緩衝的機制,將DOM節點先放到內存中,當節點都構造完成後,再將DocumentFragment對象添加到頁面中,這時所有的節點都會一次渲染出來,這樣就能減少瀏覽器很多的負擔,明顯的提高頁面渲染速度。

function CreateNodes(){

for(var i = 0;i < 10000;i++){

var tmpNode = document.createElement(“div”);
tmpNode.innerHTML = “test” + i + ” <br />”;
document.body.appendChild(tmpNode);//每次循環都要執行一次appendChild,也就是觸發了reflow

}
}

function CreateFragments(){

var fragment = document.createDocumentFragment();//構造緩存空間

for(var i = 0;i < 10000;i++){

var tmpNode = document.createElement(“div”);
tmpNode.innerHTML = “test” + i + “<br />”;
fragment.appendChild(tmpNode);//把節點緩存到緩存空間中
}

document.body.appendChild(fragment);//最後一次提交
}

發佈了46 篇原創文章 · 獲贊 8 · 訪問量 8萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章