Transcription: https://juejin.cn/post/6844903569087266823

Written in the book before

Before we discuss backflow and redraw, we need to know:

Browsers use a Flow Based Layout model. Browsers parse HTML to DOM and CSS to CSSOM. DOM and CSSOM are combined to produce a Render Tree. With RenderTree, we know the style of all the nodes, calculate their size and position on the page, and finally draw the nodes on the page. Because browsers use streaming layouts, calculations of Render Tree are usually done once, except for tables and their internal elements, which can be evaluated multiple times and usually take three times as long as equivalent elements, which is one of the reasons to avoid table layouts.

In a word: redrawing does not necessarily cause redrawing.

Reflow, rearrangement

When the size, structure, or attributes of some or all of the elements in the Render Tree change, the process by which the browser rerenders some or all of the document is called reflux.

Operations that cause backflow:

  • Page first render
  • The browser window size changed. Procedure
  • The size or position of the element changed
  • Element content changes (number of words or image size, etc.)
  • Element font size changes
  • Add or remove visible DOM elements
  • Activate CSS pseudo-classes (such as: :hover)
  • Query some properties or call some methods

Some common properties and methods that cause backflow:

  • ClientWidth, clientHeight, clientTop, clientLeft
  • OffsetWidth, offsetHeight, offsetTop, offsetLeft
  • ScrollWidth, scrollHeight, scrollTop, scrollLeft
  • ScrollIntoView (), scrollIntoViewIfNeeded ()
  • getComputedStyle()
  • getBoundingClientRect()
  • scrollTo()

Redraw (Repaint)

When a change in the style of an element in a page does not affect its position in the document flow (e.g., color, background-color, visibility, etc.), the browser assigns the new style to the element and redraws it, a process called redraw.

Performance impact

Reflux is more expensive than drawing.

Sometimes even if only a single element is backflowed, its parent element and any elements that follow it will also backflow.

Modern browsers are optimized for frequent backflow or redraw operations:

The browser maintains a queue that queues all operations that cause backflow and redraw, and if the number of tasks or time intervals in the queue reaches a threshold, the browser emptying the queue and doing a batch, thereby turning multiple backflow and redraw into one.

The browser clears the queue immediately when you access the following properties or methods:

  • ClientWidth, clientHeight, clientTop, clientLeft
  • OffsetWidth, offsetHeight, offsetTop, offsetLeft
  • ScrollWidth, scrollHeight, scrollTop, scrollLeft
  • Width, height,
  • getComputedStyle()
  • getBoundingClientRect()

Because there may be operations in the queue that affect the return value of these properties or methods, even if the information you want is not related to the change caused by the operation in the queue, the browser will force the queue to empty to make sure you get the most accurate value.

How to avoid

CSS

  • Avoid table layouts.
  • Change the class at the very end of the DOM tree whenever possible.
  • Avoid setting multiple inline styles.
  • Apply the animation to an element whose position attribute is absolute or fixed.
  • Avoid USING CSS expressions (such as calc()).

JavaScript

  • To avoid manipulating styles too often, it is best to override the style property once, or define the style list as class and change the class property once.
  • To avoid frequent DOM manipulation, create a documentFragment, apply all DOM manipulation to it, and finally add it to the document.
  • You can also set display: None to the element and display it after the operation is complete. Because DOM operations on elements with the display attribute none do not cause backflow and redraw.
  • Avoid frequently reading properties that cause backflow/redraw, and if you do need to use them more than once, cache them in a variable.
  • Use absolute positioning on elements with complex animations to keep them out of the document stream, which would otherwise cause frequent backflow of parent elements and subsequent elements.