一文教會你何為重繪、回流?

文章目錄

  • css圖層
  • 圖層創建的條件
  • 重繪(Repaint)
  • 回流
  • 觸發重繪的屬性
  • 觸發回流的屬性
  • 常見的觸發回流的操作
  • 優化方案
  • requestAnimationFrame----請求動畫幀
  • 寫在最后

學習目標:

  • 了解前端Dom代碼、css樣式、js邏輯代碼到瀏覽器展現過程
  • 了解什么是圖層
  • 了解重繪與回流
  • 了解前端層面針對重繪、回流如何優化

css圖層

瀏覽器在渲染一個頁面時,會將頁面分為很多個圖層,圖層有大有小,每個圖層上有一個或多個節點。
也就是我們各種各樣的Dom標簽
在這里插入圖片描述
在渲染DOM的時候,瀏覽器所做的工作實際上是:
1. 獲取DOM后分割為多個圖層
2. 對每個圖層的節點計算樣式結果 (Recalculate style–樣式重計算)
3. 為每個節點生成圖形和位置 (Layout–布局,重排,回流)
4. 將每個節點繪制填充到圖層位圖中 (Paint–重繪)
5. 圖層作為紋理上傳至GPU
6. 組合多個圖層到頁面上生成最終屏幕圖像 (Composite Layers–圖層重組)

圖層創建的條件

在這里插入圖片描述

Chrome瀏覽器滿足以下任意情況就會創建圖層:
1. 擁有具有3D變換的CSS屬性
2. 使用加速視頻解碼的節點
3. 節點
4. CSS3動畫的節點
5. 擁有CSS加速屬性的元素(will-change)

重繪(Repaint)

重繪是一個元素外觀的改變所觸發的瀏覽器行為,例如改變outline、背景色等屬性。瀏覽器會根據元素的新屬性重新繪制,
使元素呈現新的外觀。重繪不會帶來重新布局,所以并不一定伴隨回流。

需要注意的是:重繪是以圖層為單位,如果圖層中某個元素需要重繪,那么整個圖層都需要重繪。
所以為了提高性能,我們應該讓這些“變化的東西”擁有一個自己一個圖層,
不過好在絕大多數的瀏覽器自己會為CSS3動畫的節點自動創建圖層。

回流

渲染對象在創建完成并添加到渲染樹時,并不包含位置和大小信息。計算這些值的過程稱為布局或回流

“重繪"不一定需要"回流”,比如改變某個網頁元素的顏色,就只會觸發"重繪",不會觸發"回流",因為布局沒有改變。
“回流"大多數情況下會導致"重繪”,比如改變一個網頁元素的位置,就會同時觸發"回流"和"重繪",因為布局改變了。

觸發重繪的屬性

    * color							* background								* outline-color* border-style					* background-image							* outline* border-radius					* background-position						* outline-style* visibility					* background-repeat							* outline-width* text-decoration				* background-size							* box-shadow

觸發回流的屬性

    * width						* top									* text-align* height					* bottom								* overflow-y* padding					* left									* font-weight* margin					* right									* overflow* display					* position								* font-family* border-width				* float									* line-height* border					* clear									* vertival-align* min-height														* white-space

常見的觸發回流的操作

在這里插入圖片描述

Reflow(回流) 的成本比 Repaint(重繪) 的成本高很多很多。
一個結點的 Reflow 很有可能導致子結點,甚至父點以及同級結點的 Reflow。
在一些高性能的電腦上也許還沒什么,但是如果 Reflow 發生在手機上,那么這個過程是非常痛苦和耗電的。

所以,下面這些動作有很大可能會是成本比較高的。
當你增加、刪除、修改 DOM 結點時,會導致 Reflow , Repaint。
當你移動 DOM 的位置
當你修改 CSS 樣式的時候。
當你 Resize 窗口的時候(移動端沒有這個問題,因為移動端的縮放沒有影響布局視口)
當你修改網頁的默認字體時。
【獲取某些屬性時(width,height…)!!!!!】
注:display:none 會觸發 reflow,而 visibility:hidden 只會觸發 repaint,因為沒有發生位置變化。

優化方案

我們已知:瀏覽器渲染頁面時經歷了如下“細致”的環節:
1. 計算需要被加載到節點上的樣式結果(Recalculate style–樣式重計算)
2. 為每個節點生成圖形和位置(Layout–重排或回流)
3. 將每個節點填充到圖層中(Paint–重繪)
4. 組合圖層到頁面上(Composite Layers–圖層重組)
如果我們需要提升性能,需要做的就是減少瀏覽器在運行時所需要做的工作,即:盡量減少1234步。

【具體優化方案如下】:
1.元素位置移動變換時盡量使用CSS3的transform來代替對top left等的操作
變換(transform)和透明度(opacity)的改變僅僅影響圖層的組合
2.【使用opacity來代替visibility】
(1).使用visibility不觸發回流,但是依然重繪。
(2).直接使用opacity即觸發重繪,又觸發回流(GPU底層設計如此!)。
(3).opacity配合圖層使用,即不觸發重繪也不觸發回流。
原因:
透明度的改變時,GPU在繪畫時只是簡單的降低之前已經畫好的紋理的alpha值來達到效果,并不需要整體的重繪。
不過這個前提是這個被修改opacity本身必須是一個圖層。
3.【不要使用table布局】
table-cell
4.將【多次改變樣式屬性的操作合并成一次】操作
不要一條一條地修改DOM的樣式,預先定義好class,然后修改DOM的className
5.【將DOM離線后再修改】
由于display屬性為none的元素不在渲染樹中,對隱藏的元素操作不會引發其他元素的回流。
如果要對一個元素進行復雜的操作時,可以先隱藏它,操作完成后再顯示。這樣只在隱藏和顯示時觸發2次回流。
6.【利用文檔碎片】(documentFragment)------vue使用了該種方式提升性能。
7.【不要把獲取某些DOM節點的屬性值放在一個循環里當成循環的變量】
當你請求向瀏覽器請求一些 style信息的時候,就會讓瀏覽器flush隊列,比如:
1. offsetTop, offsetLeft, offsetWidth, offsetHeight
2. scrollTop/Left/Width/Height
3. clientTop/Left/Width/Height
4. width,height
當你請求上面的一些屬性的時候,瀏覽器為了給你最精確的值,需要刷新內部隊列,
因為隊列中可能會有影響到這些值的操作。即使你獲取元素的布局和樣式信息跟最近發生或改變的布局信息無關,
瀏覽器都會強行刷新渲染隊列。
8.動畫實現過程中,啟用GPU硬件加速:transform: tranlateZ(0)
9.為動畫元素新建圖層,提高動畫元素的z-index
10.編寫動畫時,盡量使用如下的API

requestAnimationFrame----請求動畫幀

在這里插入圖片描述

1.window.requestAnimationFrame()
說明:該方法會告訴瀏覽器在下一次重繪回流之前調用你所指定的函數
1.參數:該方法使用一個回調函數作為參數,這個回調函數會在瀏覽器下一次重繪之前調用。
回調函數會被自動傳入一個參數,DOMHighResTimeStamp,標識requestAnimationFrame()開始觸發回調函數的當前時間

2.返回值:
一個 long 整數,請求 ID ,是回調列表中唯一的標識。是個非零值,沒別的意義。你可以傳這個值給 window.cancelAnimationFrame() 以取消回調函數。

備注:若你想在瀏覽器下次重繪之前繼續更新下一幀動畫,那么回調函數自身必須再次調用window.requestAnimationFrame()

2.window.cancelAnimationFrame(requestID)
取消一個先前通過調用window.requestAnimationFrame()方法添加到計劃中的動畫幀請求。
requestID是先前調用window.requestAnimationFrame()方法時返回的值,它是一個時間標識,用法與定時器的id類似。

寫在最后

?原創不易,還希望各位大佬支持一下\textcolor{blue}{原創不易,還希望各位大佬支持一下}

👍 點贊,你的認可是我創作的動力!\textcolor{green}{點贊,你的認可是我創作的動力!}

?? 收藏,你的青睞是我努力的方向!\textcolor{green}{收藏,你的青睞是我努力的方向!}

?? 評論,你的意見是我進步的財富!\textcolor{green}{評論,你的意見是我進步的財富!}

文章看完了,參與個投票吧,前端目前比較火的三大框架你更喜歡哪個?

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/248503.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/248503.shtml
英文地址,請注明出處:http://en.pswp.cn/news/248503.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

mockjs中的方法(三)

1)Mock.mock(); Mock.mock( url, type, template, function(options) ); 其中 url 是定義我們要請求的 url 地址,以便于我們請求的時候 mock 去進行攔截,知道我們要去請求那個值;但是它也是可選的,而且格式…

js函數、js對象的這些點你真的懂嗎?

本篇學習目標 ?了解函數(高級)原型原型鏈概念\textcolor{green}{了解函數(高級)原型原型鏈概念}了解函數(高級)原型原型鏈概念 ?掌握函數作用域\textcolor{green}{掌握函數作用域}掌握函數作用域 ?掌握…

前端處理跨域的幾種方式

什么是跨域&#xff1f; 跨域是指一個域下的文檔或腳本試圖去請求另一個域下的資源&#xff0c;這里跨域是廣義的。 廣義的跨域&#xff1a; 1、資源跳轉&#xff1a;A鏈接、重定向、表單提交 2、資源嵌入&#xff1a; <link>、<script>、<img>、<frame&g…

程序員必知的緩存套圖

文章目錄1. 線程與進程1.1 進程:1.2. 線程:1.3. 關系2. 瀏覽器內核模塊組成4. 事件循環機制5. 緩存5.1. 緩存理解5.2. 緩存分類5.3. 緩存使用示意圖5.4. 緩存中的header參數1. 線程與進程 1.1 進程: 進程是計算機中的程序關于某數據集合上的一次運行活動&#xff0c;是系統進…

安裝webpack及使用

前言 你是否也是只會運用框架中集成好的Webpack配置呢&#xff1f;你明白每一項的意義么&#xff1f;你懂多少Webpack的個性化配置項呢&#xff1f;本篇文章為你講解Webpack中的各種配置項參數及作用&#xff01; 文章目錄了解Webpack相關開啟項目編譯打包應用使用webpack配置…

Python基礎-os模塊 sys模塊

sys模塊 與操作系統交互的一個接口 文件夾相關 os.makedirs(dirname1/dirname2) 可生成多層遞歸目錄os.removedirs(dirname1) 若目錄為空&#xff0c;則刪除&#xff0c;并遞歸到上一級目錄&#xff0c;如若也為空&#xff0c;則刪除&#xff0c;依此類推os.mkdir(dirnam…

php單例型(singleton pattern)

搞定&#xff0c;吃飯 <?php /* The purpose of singleton pattern is to restrict instantiation of class to a single object. It is implemented by creating a method within the class that creates a new instance of that class if one does not exist. If an obje…

開啟關閉各種服務

開啟&關閉 Mac版 查找被占用的8080端口&#xff0c;根據pid殺掉進程 查找8080端口 losf -i:8080 根據pid殺掉進程 kill -9 pid iMac:~ acui$ lsof -i:8080 COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME java 62948 ting 93u IPv6 0x6697d6…

助你提高效率的幾個Vue指令

前言 很多使用Vue的同學往往最容易忽略的指令&#xff0c;由于在這里考慮到很多初學甚至還沒有開始接觸Vue的同學呢&#xff0c;在介紹v-clos之前呢就先以大家都熟知的v-model編寫小demo v-model 相信大家對v-model并不陌生&#xff0c;簡單來講他就是用于在表單控件以及組建…

掌握Mock擺脫后端同學的束縛

文章目錄前言Mock概述mock.js安裝Mock規范Mock的使用總結前言 當下采用前后端分離模式開發Web應用已經成為氣候&#xff0c;在開發階段有一個不成文的規定則是 項目開發后端先行 但是作為前端開發工程師的我們&#xff0c;難道在搭建完頁面后只能等待后端的接口么&#xff1f;…

戶外鞋簡介

. 單論品牌&#xff08;主要以登山鞋及徙步鞋為主&#xff09;&#xff1a; 高級品牌&#xff1a;SCARPA、ASOLO、MONTRAIL、ZAMBERLAN、vasque、Lowa、La Sportiva 價格都較高&#xff0c;單價都在千元以上&#xff0c;品質一流&#xff0c;做工精細。 中檔品牌&#xff1a;Tr…

Vue技能樹上線啦

前言 前端現在越來越多樣化&#xff0c;語言眾多&#xff0c;大家使用的框架也比較雜&#xff0c;在廣泛的前端技術棧面前我唯愛Vue&#xff08;僅代表個人觀點勿噴小伙伴們&#xff09;可能很多人覺得我是因為簡單&#xff0c;其實并不然&#xff0c;我嘗試過很多框架&#x…

ES6的新特性(8)——數組的擴展

數組的擴展 擴展運算符 含義 擴展運算符&#xff08;spread&#xff09;是三個點&#xff08;...&#xff09;。它好比 rest 參數的逆運算&#xff0c;將一個數組轉為用逗號分隔的參數序列。 console.log(...[1, 2, 3]) // 1 2 3console.log(1, ...[2, 3, 4], 5) // 1 2 3 4 5[…

《SpringMVC從入門到放肆》一、概述

一、SpringMVC概述 ViewServiceDaoDBSpring MVCinterfaceinterfaceMysqlimplsimplsSpringMVC也叫Spring web mvc&#xff0c;屬于表現層框架。SpringMVC是Spring框架的一部分&#xff0c;是在Spring3.0后發布的。 二、第一個SpringMVC程序功能描述&#xff1a;  用戶提交一個…

手握流量密碼,萬粉不是夢

前言 可能大家來到CSDN的目的初衷都是不一樣的&#xff0c;像我注冊CSDN的時候完全是為了解決自己項目中的各種問題&#xff0c;能夠有一個為我提供正確答案、正確解決方案的一個平臺&#xff0c;簡單的了解后我選擇CSDN&#xff0c;直到成為現在的創作者也說明我的選擇是對的…

秋季學期學習總結

轉載于:https://www.cnblogs.com/zx666/p/10408950.html

一文帶你了解React框架

前言 由于 React的設計思想極其獨特&#xff0c;屬于革命性創新&#xff0c;性能出眾&#xff0c;代碼邏輯卻非常簡單。所以&#xff0c;越來越多的人開始關注和使用&#xff0c;認為它可能是將來 Web 開發的主流工具。 這個項目本身也越滾越大&#xff0c;從最早的UI引擎變成…

Web前端JQuery面試題(一)

Web前端JQuery面試題&#xff08;一&#xff09; 一&#xff1a;選擇器 基本選擇器 什么是#id&#xff0c;element&#xff0c;.class&#xff0c;*&#xff0c;selector1, selector2, selectorN&#xff1f;答&#xff1a; 根據給定的id匹配一個元素&#xff0c;用于搜索&…

前端云原生——微信小程序云服務配置

前端同樣涉及云原生前言創建使用云開發項目搭建云環境測試云服務1. 獲取openid&#xff08;上傳本地login云函數&#xff09;1.1 創建部署login文件時報錯2. 自定義sum函數并創建部署3. 上傳圖片4. 前端操作數據庫5. 即時通信demo面試法寶歡迎各位小伙伴們&#xff01; 為大家推…

45天帶你玩轉Node(第一天)初探Node.js

45天帶你玩轉Node 粉絲要求博主系統的寫一篇關于Node.js的學習資料&#xff0c;但其實我們的Node.js知識點并不少&#xff0c;所以博主為大家搭建了一個專欄&#xff0c;為了方便大家系統的學習Node.js&#xff0c;大家記得訂閱哦&#xff01;雖然我們的Node.js還很年輕&#…