I. Introduction
More than a year after the React Fiber architecture came out, React recently released the latest version 16.8.0, another exciting feature: React Hooks is officially launched, and my willingness to upgrade React is getting stronger and stronger. Before upgrading, you may wish to go back to the original point and understand why the talented React team has to spend a lot of time to rewrite the React architecture, and what is the concept of Fiber.
Second, the problem of React 15
In scenes where there are many page elements and frequent refreshing is required, React 15 will drop frames. Consider the following example:
https://claudiopro.github.io/...
The root cause is that a large number of synchronous computing tasks block the browser's UI rendering. By default, JS calculations, page layout, and page drawing are all running in the main thread of the browser, and they are mutually exclusive. If JS calculations continue to occupy the main thread, the page cannot be updated in time. When we call setState to update the page, React will traverse all the nodes of the application, calculate the difference, and then update the UI. The whole process was done in one go and could not be interrupted. If there are a lot of page elements, the entire process may take more than 16 milliseconds, and frame drops are prone to occur.
In response to this problem, the React team optimized the operating mechanism of the web page from the framework level and achieved good results.
Three, problem-solving ideas
The basic idea to solve the problem that the main thread is occupied by JS operations for a long time is to divide the operation into multiple steps and complete them in batches. That is to say, after completing part of the task, the control is returned to the browser, so that the browser has time to render the page. After the browser is busy, continue with the unfinished tasks.
The old version of React renders recursively, using the function call stack of the JS engine itself, and it will execute until the stack is empty. Fiber implements its own component call stack, which traverses the component tree in the form of a linked list, and can flexibly pause, continue, and discard the executed tasks. The implementation method is to use the browser's requestIdleCallback API. The official explanation is this:
window.requestIdleCallback() will call the function in turn during the idle period of the browser, which allows developers to perform background or low-priority tasks in the main event loop, and will not trigger delays such as animation and user interaction but critical The incident has an impact. Functions are generally executed in the order of first-in-first-invocation unless the function reaches its timeout period before the browser calls it.
After understanding the problem idea, let's take a look at how React specifically does it.
Fourth, React's answer sheet
The internal operation of the React framework can be divided into 3 layers:
- The Virtual DOM layer describes what the page looks like.
- The Reconciler layer is responsible for calling component life cycle methods, performing Diff operations, etc.
- The Renderer layer renders the corresponding pages according to different platforms. The more common ones are ReactDOM and ReactNative.
The biggest change this time is the Reconciler layer, and the React team also gave it a new name called Fiber Reconciler. This introduces another keyword: Fiber.
Fiber actually refers to a data structure, which can be represented by a pure JS object:
const fiber = {
stateNode, // 节点实例
child, // 子节点
sibling, // 兄弟节点
return, // 父节点
}
In order to distinguish, the former Reconciler was named Stack Reconciler. The operation of Stack Reconciler cannot be interrupted, and it must go to the black one by one:
And Fiber Reconciler will return control to the browser every time it is executed for a period of time, which can be executed in segments:
In order to achieve this effect, a scheduler (Scheduler) is needed for task allocation. There are six priority levels of tasks:
- synchronous, same as the previous Stack Reconciler operation, synchronous execution
- task, executed before next tick
- animation, executed before the next frame
- high, execute immediately in the near future
- low, it’s okay to delay execution slightly
- offscreen, execute when next render or scroll
High-priority tasks (such as keyboard input) can interrupt the execution of low-priority tasks (such as Diff) and take effect faster.
During the execution of Fiber Reconciler, it will be divided into 2 stages.
In the first stage, the Fiber tree is generated, and the node information that needs to be updated is obtained. This step is a gradual process and can be interrupted.
In the second stage, the nodes that need to be updated are updated in batches at one time, and this process cannot be interrupted.
The feature of phase one that can be interrupted allows higher priority tasks to be executed first, greatly reducing the probability of page drop frames from the framework level.
Five, fiber tree
When Fiber Reconciler performs Diff calculation in Phase 1, it will generate a Fiber tree. This tree is generated by adding additional information on the basis of the Virtual DOM tree. It is essentially a linked list.
- The Fiber tree will be generated in one go when it is first rendered. When Diff is needed later, a new tree will be generated based on the information of the existing tree and the latest-Virtual DOM. Every time this new tree generates a new node, it will return control to the main thread to check if there are any higher priority tasks that need to be executed. If not, continue the process of building the tree:
If there is a higher priority task that needs to be performed in the process, Fiber Reconciler will discard the tree being generated and execute it again when it is free.
In the process of constructing the Fiber tree, the Fiber Reconciler will save the node information that needs to be updated in the Effect List. When phase two is executed, the corresponding nodes will be updated in batches.
Six, summary
This article starts from the problems of React 15, introduces the idea of React Fiber to solve the problem, and introduces the workflow of Fiber Reconciler. From Stack Reconciler to Fiber Reconciler, the source code level is actually doing a recursive change cycle. If I have the opportunity in the future, I will combine the source code to make a further introduction.
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。