React 穿透获取被高级组件装饰的目标组件实例

栏目: IOS · Android · 发布时间: 5年前

内容简介:图片来源于互联网React 中常规的父子组件通信都是通过 props 进行的,子组件通过 props 来接收父组件传递的状态值以及方法,从而响应视图的更新以及事件的执行。在不同的业务场景中也会存在非常规的通信方式,例如需要在父组件中调用子组件属性或者方法,这个时候就需要获取子组件的实例来解决这个问题。
React 穿透获取被高级组件装饰的目标组件实例

图片来源于互联网

React 中常规的父子组件通信都是通过 props 进行的,子组件通过 props 来接收父组件传递的状态值以及方法,从而响应视图的更新以及事件的执行。

为什么要获取组件实例

在不同的业务场景中也会存在非常规的通信方式,例如需要在父组件中调用子组件属性或者方法,这个时候就需要获取子组件的实例来解决这个问题。

获取组件实例的方法

首先需要说明的是,只有类组件才有实例,函数式组件是没有组件实例的。

React 官方提供了 3 中使用 ref 获取实例的方式。

  1. ref 接收一个字符串作为参数 (不推荐)
class Index extends React.PureComponent {
    
        componentDidMount() {
            // 调用实例
            console.log(this.refs.classComponentInstance)
        }
        
        render() {
            return (
                <ClassComponent ref="classComponentInstance" />
            )
        }
    }
复制代码
  1. ref 接收一个回调函数作为参数
class Index extends React.PureComponent {
    
        componentDidMount() {
            // 调用实例
            console.log(this.classComponentInstance)
        }
        
        classComponentInstance = null
        
        render() {
            return (
                <ClassComponent ref={instance => {this.classComponentInstance=instance}} />
            )
        }
    }
复制代码
  1. ref 接收 React.createRef 作为参数
class Index extends React.PureComponent {
    
        componentDidMount() {
            // 调用实例
            console.log(this.classComponentInstance.current)
        }
        
        classComponentInstance = React.createRef()
        
        render() {
            return (
                <ClassComponent ref={this.classComponentInstance} />
            )
        }
    }
复制代码

被高级组件装饰的组件

所谓的高级组件也就一个函数,以组件作为参数,以组件作为返回值,主要是用于处理一些相似的逻辑,使组件可高度复用。

// Child.js
    
    @HocComponent
    export default class Child extends React.PureComponent {
        
        render(
            return (
                <div>this is Child</div>
            )
        )
    }
    
    
    // Parent.js
    
    import Child from './Child'
    
    class Parent extends React.PureComponent {
    
        childComponentInstance = null
        
        render(
            return (
                <Child ref={instance => {this.childComponentInstance=instance}} />
            )
        )
    }
    
复制代码

关于装饰符可查看教程

上面示例中 Child 就是一个被高级组件使用装饰符装饰的类组件,当在 Parent 组件中调用并使用 ref 获取其实例的时候就会发现 this.childComponentInstance 被赋值的实例并不是 Child 的实例,而是 HocComponent 组件的实例。

获取被装饰组件的实例

// Child.js
    
    @HocComponent
    export default class Child extends React.PureComponent {
    
        componentDidMount() {
            // 在 componentDidMount 周期中或者在 constructor 构造函数中执行父组件中传递过来的 getRef 方法,将实例 this 作为参数
            this.props.getRef(this)
        }
        
        render(
            return (
                <div>this is Child</div>
            )
        )
    }
    
    
    // Parent.js
    
    import Child from './Child'
    
    class Parent extends React.PureComponent {
    
        childComponentInstance = null
        
        render(
            return (
                <Child getRef={instance => {this.childComponentInstance=instance}} />
            )
        )
    }

复制代码

通过上面的方式就可以穿透高级组件,获取到目标组件的实例

抽象封装为可复用的高级组件

上面的方法虽然已经实现了我们需要的功能,但是代码侵入性太强,没有复用度可言,所以我们需要把这个功能提取出来。

// util.js
    
    export const getRef = WrapperdComponent => {
        return props => {
            const { getRef, ...otherProps }  = props
            return <WrapperdComponent ref={getRef} {...otherProps} />
        }
    }
    
复制代码

当把穿透方法提取为一个高级组件之后就可以在任何需要的地方调用即可

// 使用示例
    // Child.js
    
    import { getRef } from './util'
    
    @HocComponent
    @getRef
    export default class Child extends React.PureComponent {
        
        render(
            return (
                <div>this is Child</div>
            )
        )
    }
    
    
    
    // Parent.js
    
    import Child from './Child'
    
    class Parent extends React.PureComponent {
    
        childComponentInstance = null
        
        render(
            return (
                <Child getRef={instance => {this.childComponentInstance=instance}} />
            )
        )
    }
    
复制代码

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

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

游戏编程模式

游戏编程模式

Robert Nystrom / GPP翻组 / 人民邮电出版社 / 2016-9-1 / 61.4

游戏开发一直是热门的领域,掌握良好的游戏编程模式是开发人员的应备技能。本书细致地讲解了游戏开发需要用到的各种编程模式,并提供了丰富的示例。 全书共分20章,通过三大部分内容全面介绍了与游戏编程模式相关的各类知识点。首部分介绍了基础知识和框架;第二部分深入探索设计模式,并介绍了模式与游戏开发之间的关联;第三部分介绍了13种有效的游戏设计模式。 本书提供了丰富的代码示例,通过理论和代码示例......一起来看看 《游戏编程模式》 这本书的介绍吧!

SHA 加密
SHA 加密

SHA 加密工具

html转js在线工具
html转js在线工具

html转js在线工具

HSV CMYK 转换工具
HSV CMYK 转换工具

HSV CMYK互换工具