前端进阶之旅前端进阶之旅
基础篇
进阶篇
高频篇
精选篇
手写篇
原理篇
面经篇
自检篇
每日一题
  • 综合
    • 综合题型
    • 其他问题
    • 设计模式
    • 思维导图
    • 学习路线
  • 前端基础
    • HTTP
    • 浏览器
    • 计算机基础
  • 进阶学习
    • NPM工作流
    • Docker
    • Canvas
    • Node学习指南
    • 前端综合文章
  • 其他
    • Handbook
    • 职场话题
    • CSS可视化
小程序题库
公众号动态
博客动态
开发者导航
基础篇
进阶篇
高频篇
精选篇
手写篇
原理篇
面经篇
自检篇
每日一题
  • 综合
    • 综合题型
    • 其他问题
    • 设计模式
    • 思维导图
    • 学习路线
  • 前端基础
    • HTTP
    • 浏览器
    • 计算机基础
  • 进阶学习
    • NPM工作流
    • Docker
    • Canvas
    • Node学习指南
    • 前端综合文章
  • 其他
    • Handbook
    • 职场话题
    • CSS可视化
小程序题库
公众号动态
博客动态
开发者导航
  • Vue

    • 从源码解读Vue生命周期
    • 组件的本质
    • 有状态组件的设计
    • 设计 VNode
    • 辅助创建 VNode 的 h 函数
    • 自定义渲染器和异步渲染
    • 渲染器之挂载
    • 渲染器的核心 Diff 算法
    • 渲染器之patch
    • 图解 Vue 响应式原理
    • 图解 Vue 异步更新
    • 剖析 Vue 内部运行机制
    • vue响应式原理模拟
    • vue状态管理之vuex
    • 理解Vue的设计思想及实现Vue
    • diff算法深入
    • vue router vuex原理分析
    • Vue3初探响应式原理.
    • vue2源码分析
    • vue组件化实践
  • React

  • Webpack

  • Node

  • Javascript

  • 综合

完整面试题地址:
作者:程序员poetry
扫码关注作者公众号:「前端进阶之旅」 每天分享技术干货
前端进阶之旅公众号二维码

从本讲开始,我们将以首次渲染为切入点,拆解 Fiber 架构下 ReactDOM.render 所触发的渲染链路,结合源码理解整个链路中所涉及的初始化、render 和 commit 等过程

# 一、ReactDOM.render 调用栈的逻辑分层

开篇先给到你一个简单的 React AppDemo:

import React from "react";
import ReactDOM from "react-dom";

function App() {
    return (
      <div className="App">
        <div className="container">
          <h1>我是标题</h1>
          <p>我是第一段话</p>
          <p>我是第二段话</p>
        </div>
      </div>
    );
}

const rootElement = document.getElementById("root");
ReactDOM.render(<App />, rootElement);
@前端进阶之旅: 代码已经复制到剪贴板

Demo 启动后,渲染出的界面如下图所示:

现在请你打开 Chrome 的 Performance 面板,点击下图红色圈圈所圈住的这个“记录”按钮:

然后重新访问 Demo 页面对应的本地服务地址,待页面刷新后,终止记录,便能够得到如下图右下角所示的这样一个调用栈大图:

放大该图,定位“src/index.js”这个文件路径,我们就可以找到 ReactDOM.render 方法对应的调用栈,如下图所示:

从图中你可以看到,ReactDOM.render 方法对应的调用栈非常深,中间涉及的函数量也比较大。如果这张图使你心里发虚,请先不要急于撤退——分析调用栈只是我们理解渲染链路的一个手段,我们的目的是借此提取关键逻辑,而非理解调用栈中的每一个方法。就这张图来说,你首先需要把握的,就是整个调用链路中所包含的三个阶段

图中 scheduleUpdateOnFiber 方法的作用是调度更新,在由 ReactDOM.render 发起的首屏渲染这个场景下,它触发的就是 performSyncWorkOnRoot。performSyncWorkOnRoot 开启的正是我们反复强调的 render 阶段;而 commitRoot 方法开启的则是真实 DOM 的渲染过程(commit 阶段)。因此以 scheduleUpdateOnFiber 和 commitRoot 两个方法为界,我们可以大致把 ReactDOM.render 的调用栈划分为三个阶段:

  • 初始化阶段
  • render 阶段
  • commit 阶段

# 二、初始化阶段

# 拆解 ReactDOM.render 调用栈——初始化阶段

首先我们提取出初始化过程中涉及的调用栈大图:

图中的方法虽然看上去又多又杂,但做的事情清清爽爽,那就是完成 Fiber 树中基本实体的创建。

什么是基本实体?基本实体有哪些?问题的答案藏在源码里,这里我为你提取了源码中的关键逻辑,首先是 legacyRenderSubtreeIntoContainer 方法。在 ReactDOM.render 函数体中,以下面代码所示的姿势调用了它:

fe
基础篇
进阶篇
高频篇
精选篇
手写篇
原理篇
面经篇
自检篇
每日一题
  • 综合
    • 综合题型
    • 其他问题
    • 设计模式
    • 思维导图
    • 学习路线
  • 前端基础
    • HTTP
    • 浏览器
    • 计算机基础
  • 进阶学习
    • NPM工作流
    • Docker
    • Canvas
    • Node学习指南
    • 前端综合文章
  • 其他
    • Handbook
    • 职场话题
    • CSS可视化
小程序题库
公众号动态
博客动态
开发者导航
  • Vue

    • 从源码解读Vue生命周期
    • 组件的本质
    • 有状态组件的设计
    • 设计 VNode
    • 辅助创建 VNode 的 h 函数
    • 自定义渲染器和异步渲染
    • 渲染器之挂载
    • 渲染器的核心 Diff 算法
    • 渲染器之patch
    • 图解 Vue 响应式原理
    • 图解 Vue 异步更新
    • 剖析 Vue 内部运行机制
    • vue响应式原理模拟
    • vue状态管理之vuex
    • 理解Vue的设计思想及实现Vue
    • diff算法深入
    • vue router vuex原理分析
    • Vue3初探响应式原理.
    • vue2源码分析
    • vue组件化实践
  • React

  • Webpack

  • Node

  • Javascript

  • 综合