React 组件渲染和更新的实现代码示例

 更新时间:2019年02月21日 08:25:47   作者:柒青衿  
这篇文章主要介绍了React-组件渲染和更新的实现代码示例,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧

最近一直写React,慢慢就对里面的一些实现很好奇。最好奇的就是自定义标签的实现和this.setState的实现。这里不分析JSX是如何解析的,所有组件都用ES5方式编写。

组件渲染

渲染时候,我们会调用render方法。类似下面这样:

var SayHi = React.createClass({
 getInitialState: function() {
  return {verb: 'say:'};
 },
 componentWillMount: function() {
  console.log('I will mount');
 },
 componentDidMount: function() {
  console.log('I have mounted');
 },
 render: function() {
  return React.createElement("div", null,this.state.verb, "Hello ", this.props.name);
 }
});

React.render(React.createElement(SayHi, {name: "Cynthia"}), document.getElementById("container"));

结果:

页面打印:
say: Hello Cynthia
控制台打印:
I will mount
I have mounted

这是我画的React对象上的一些属性和方法。

当调用render方法时,render会去调用一个map方法,根据传入参数的不同,把被render的对象分为以下三类:
* 文本
* 原生
* 自定义标签

文本

对于文本,React会实例化一个文本节点的对象,并且调用该对象的mount方法。在这个mount方法中,把文本放到一个span中,调用容器组件的innerHTML,进行渲染。

原生标签

对于原生标签,React会实例化一个处理原生标签的对象,并且调用该对象的mount方法。在这个mount方法中,拼接一个字符串,并且不断递归上面的map方法,最后把拼接好的字符串放到容器组件的innerHTML中,进行渲染。

自定义标签

这个应该是大家最好奇的。自定义标签虽然叫标签,其实就是一个类。实例化一个处理自定义标签的对象后,首先React会处理自定义标签的生命周期方法,然后再次递归调用子组件的render方法进而调用map方法,直至把自定义标签分解为前两种标签。

更新

首先,我们统一一下认识。在React里调用this.setState()会使得组件更新,调用this.state = {}只会更改本组件的状态,但是不会使得组件更新。

如果我要更新一个组件,我会这样写。

var SayHi = React.createClass({
 getInitialState: function() {
  return {verb: 'say:'};
 },
 componentWillMount: function() {
  console.log('I will mount');
 },
 componentDidMount: function() {
  console.log('I have mounted');
 },
 changeVerb: function(){
  this.setState({verb: 'write:'});
 }
 render: function() {
  return React.createElement("div", this.changeVerb.bind(this),this.state.verb, "Hello ", this.props.name);
 }
});

React.render(React.createElement(SayHi, {name: "Cynthia"}), document.getElementById("container"));

执行结果:

页面打印:
say: Hello Cynthia
点击文本,页面内容更新成:
write: Hello Cynthia

与更新相关的属性和方法如下:

在调用this.setState()以后,也是调用了一个map方法,根据传入参数不同,依然把要更新的标签分为文本、原生标签、自定义标签三类。具体处理过程如下。

文本

文本节点处理很简单,判断要更新后的文本与当前文本是否===,不是全等就删除原来文本,插入新文本。

自定义标签

对于自定义标签,首先根据对象的引用、key是否相同,判断是否需要更新。如果需要更新,就继续调用上述map方法进行子组件的更新。又是一个递归。但是注意,这里的map方法和渲染部分的map方法不是一个方法哟。

原生标签

对于原生标签,首先更新组件的属性,然后update子树,用diff算法来比较新的子树与目前标签的子树的不同,形成一个差异树,然后用patch方法,把这个差异树更新到真正的DOM树上。

总结

很复杂的过程,让我用流水账写了一遍。没能道出其中精华。以后继续探索,写的详细一些。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

相关文章

  • 详解使用React进行组件库开发

    详解使用React进行组件库开发

    本篇文章主要介绍了详解使用React进行组件库开发,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-02-02
  • react实现Radio组件的示例代码

    react实现Radio组件的示例代码

    这篇文章主要介绍了react实现Radio组件的示例代码,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2021-04-04
  • React Native之ListView实现九宫格效果的示例

    React Native之ListView实现九宫格效果的示例

    本篇文章主要介绍了React Native之ListView实现九宫格效果的示例,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-08-08
  • react-native DatePicker日期选择组件的实现代码

    react-native DatePicker日期选择组件的实现代码

    本篇文章主要介绍了react-native DatePicker日期选择组件的实现代码,具有一定的参考价值,有兴趣的可以了解下
    2017-09-09
  • 在React项目中使用Eslint代码检查工具及常见问题

    在React项目中使用Eslint代码检查工具及常见问题

    这篇文章主要介绍了在React项目中使用Eslint代码检查工具及常见问题,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-10-10
  • React.Js添加与删除onScroll事件的方法详解

    React.Js添加与删除onScroll事件的方法详解

    这篇文章主要给大家介绍了关于React.Js添加与删除onScroll事件的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧。
    2017-11-11
  • React Native中TabBarIOS的简单使用方法示例

    React Native中TabBarIOS的简单使用方法示例

    最近在学习过程中遇到了很多问题,TabBarIOS的使用就是一个,所以下面这篇文章主要给大家介绍了关于React Native中TabBarIOS简单使用的相关资料,文中通过示例代码介绍的非常详细,需要的朋友可以参考下。
    2017-10-10
  • 浅谈react-router HashRouter和BrowserRouter的使用

    浅谈react-router HashRouter和BrowserRouter的使用

    本篇文章主要介绍了浅谈react-router HashRouter和BrowserRouter的使用,具有一定的参考价值,有兴趣的可以了解一下
    2017-12-12
  • React星星评分组件的实现

    React星星评分组件的实现

    评分插件在购物的应用中经常可以看得到,但是用着别人的总是没有自己写的顺手,本文就使用React实现星星评分组件,感兴趣的可以了解一下
    2021-06-06
  • react实现antd线上主题动态切换功能

    react实现antd线上主题动态切换功能

    这篇文章主要介绍了react实现antd线上主题动态切换功能,本文给大家介绍的非常详细,具有一定的参考借鉴价值,需要的朋友可以参考下
    2019-08-08

最新评论