跟着写一遍就会了,手写一个mini版本的React(2.render)

2021-10-20 10:15:51 浏览数 (1)

本节目标实现ReactDOM.render,只关心向 DOM 添加内容,之后处理更新和删除内容; ​

本节代码实现目录为:react/react-dom.js文件;

有了虚拟 DOM 数据结构,接下来要把它转换成真实的DOM结构渲染到页面上,基本分为四步: ​

  • 创建不同类型节点
  • 添加属性 props
  • 遍历 children,递归调用 render
  • 将生成的节点 append 到 root 根节点上

具体实现步骤: ​

1、新建react-dom.js文件

2、创建 DOM 节点,然后将新节点添加到容器

代码语言:javascript复制
// react/react-dom.js
/**
 * 将虚拟 DOM 转换为真实 DOM 并添加到容器中
 * @param {element} 虚拟 DOM
 * @param {container} 真实 DOM
 */
function render(element, container) {
  const dom = document.createElement(element.type)
  container.appendChild(dom)
}
复制代码

3、将 element.props.children 都添加至 dom 节点中

代码语言:javascript复制
 element.props.children.forEach(child =>
    render(child, dom)
  )
复制代码

4、处理文本节点

代码语言:javascript复制
const dom =
    element.type == "TEXT_ELEMENT"
      ? document.createTextNode("")
      : document.createElement(element.type)
复制代码

5、为节点绑定属性

代码语言:javascript复制
// 为节点绑定属性
  const isProperty = key => key !== "children"
  Object.keys(element.props)
    .filter(isProperty)
    .forEach(name => {
      dom[name] = element.props[name]
    })
复制代码

6、测试

以上我们实现了一个jsx转换为dom的库,测试一下:

6.1 将render方法引入到react/index.js文件中

6.2 添加React.render方法

在src/index.js文件添加React.render方法:

代码语言:javascript复制
// src/index
import React from '../react';

const element = (
  <div id="foo">
    <a>bar</a>
    <b />
  </div>
)

React.render(element, document.getElementById('root'))
复制代码

6.3 修改webpack配置

在src目录下添加index.html文件,并添加一个dom属性为id的节点:

修改webpack配置,添加html模板:

6.4 运行

运行命令 npm run start 启动,可以看到已经成功显示出结果:

7、总结

使用流程图简单总结一下2、3小节:

8、本节代码

代码地址:gitee.com/linhexs/rea…

0 人点赞