zoukankan      html  css  js  c++  java
  • react 反模式——不使用jsx动态显示异步组件

    前言:

      react反模式 (anti-patterns)指的是违背react思想(flux)的coding方式。

      本文在 App 组件中,通过 Model.show 动态显示 Model 组件,通过 Promise 异步的形式实现数据交互。

      本例子包括了 1.不使用jsx动态显示组件;2.在 getInitialState 中使用 this.props 

      代码地址:https://github.com/miaowwwww/react-anti-patterns

        参考文章:

        React反模式 —— 如何不使用JSX地动态显示组件

        怎么样理解reactjs中组件的反模式? 

        react-patterns

    先看一下效果:

      

      调用代码:

        

     实现1:如何不通过父组件jsx嵌套,动态显示 Model 组件?

      (抛开父组件,也就是怎么把一个react组件渲染到DOM中去而已)

      过程:新容器(div) ---> Model注入div ---> div注入body;

      代码:(就是红框部分:不管什么时候执行  show()  这三行代码,都可以放一个Model组件到body里面)

        

      

     实现2:如何实现使用者与Model组件的数据交互?

      (要把点了什么以及新名字告诉调用 Model.show() 的人)

      要点:异步传递数据Promise, Model.show()  是Model里面的static方法--是类本身的

      过程:App 调用 Model.show ---> Model.show 返回一个Promise ---> App在Promise中获取数据

      代码:

        1.App调用Model.show(),并接受、处理promise

        

        2.Model如何返回一个Promise

          2.1 在Model中声明Promise(注意:Model现在是没有this._promise的,<Model />实例化之后,实例里面有_promise)

          2.2 在show函数中,

            2.2.1:使用ReactDOM.render(<Model />, div),实例化一个Model组件,并把该实例返回。因此_model 有一个_promise

        

    实现3:Promise的resolve & reject 返回交互数据

      使用组件内使用定义好的 this._resolve, this._reject就好了

      

    实现4: 销毁Model组件和产生的div容器

       4.1 ReactDOM.unmountComponentAtNode(container);

         用于销毁react组件,container:ReactDOM.render(<Model />, div),这里的div就是;所以知道show的时候为什么要留着引用了吧

      4.2 div容器还是留着的,所以必须要用基本js销毁;(先remove 再 unmount行不行?好像更好,减少一次dom操作)

      

    Model的完整代码

    import React, { PureComponent, PropTypes } from 'react';
    import ReactDOM from 'react-dom';
    
    import style from './Model.less';
    
    export default class Model extends PureComponent {
        constructor(props) {
            super(props);
            // 使用this.props初始化this.state也是反模式的一种
            this.state = {name: this.props.name};
    
            this._reject = null;
            this._resolve = null;
            this._promise = new Promise((resolve, reject) => {
                this._resolve = resolve;
                this._reject = reject;
            });
            this._container = null;
        }
    
        static show = (name) => {
            // 显示组件
            let div = document.createElement('div');
                // _model 就是当前的 Model的一个实例
            let _model = ReactDOM.render(<Model name={name} />, div);
            document.querySelector('body').appendChild(div);
            
            _model._container = div; //在_model实例中保存div的引用,销毁要用
            // 返回一个promise
            return _model._promise;
        }
    
        // 销毁 1.销毁react组件 2.销毁 div 元素
        _removeModel = () => {
            this._container.remove();
            ReactDOM.unmountComponentAtNode(this._container);
        }
    
        handleChange = (e) => {
            this.setState({name: e.target.value});
        }
    
        handleClickSave = () => {
            this._resolve(this.state.name);
            this._removeModel();
        }
    
        handleClickCancel = () => {
            this._reject(`cancen update name`);
            this._removeModel();
        }
    
        render() {
            return (
                <section className={style.model}>
                    <div className={style.content}>
                        <h1>请输入新名字</h1>
                        <input type="text" 
                                    value={this.state.name} 
                                    onChange={this.handleChange} />
                        <div>
                            <a onClick={this.handleClickCancel} >取消</a>
                            <a onClick={this.handleClickSave} >保存</a>
                        </div>
                    </div>
                </section>
            )
        }
    }
    Model.PropTypes = {
        name: PropTypes.string.isRequired
    }
  • 相关阅读:
    axis2依赖的其他jar, 版本不是最新的
    mysql: 安装后的目录结构
    视图的使用
    索引
    递归查询 start with connect by prior
    oracle创建表
    C#中 ??、 ?、 ?: 、?.、?[ ] 和$
    C#关键字static、virtual和abstract笔记
    js调用后台,后台调用前台等方法总结
    java基础序列化
  • 原文地址:https://www.cnblogs.com/miaowwwww/p/6438745.html
Copyright © 2011-2022 走看看