一、概念
1、出现的原因
在react典型的数据流中,props传递是父子组件交互的唯一方式;通过传递一个新的props值来使子组件重新re-render,从而达到父子组件通信。当然,就像react官网所描述的一样,在react典型的数据流之外,某些情况下(例如和第三方的dom库整合,或者某个dom元素focus等)为了修改子组件我们可能需要另一种方式,这就是ref方式。
2、介绍
React提供的这个ref属性,表示为对组件真正实例的引用,其实就是ReactDOM.render()返回的组件实例;需要区分一下,ReactDOM.render()渲染组件时返回的是组件实例;而渲染dom元素时,返回是具体的dom节点
二、ref获取dom
import React from "react";
export default class LearnRef extends React.Component {constructor(props) {super(props);/*** 使用React.createRef 创建一个ref对象* 来接收dom元素的*/this.myInput = React.createRef();}getInputDom() {console.log(this.myInput);}render() {return (<div>哈喽 ref{/* 给dom元素添加ref属性这个属性值使我们之前创建的ref对象注意:ref 是react里面的保留字,做组件传值的时候不推荐设置ref的属性*/}<input ref={this.myInput} /><button onClick={() => this.getInputDom()}>获取input的dom</button></div>);}
}
三、使用ref实现父组件访问子组件中的数据和方法
import React from "react";export default class LearnRef2 extends React.Component {state = {name: "张三",age: 11,};addAge () {this.setState({age: this.state.age + 1})}render() {return (<div><div>{this.state.name} -- {this.state.age}</div></div>);}
}
四、给ref设置一个回调函数,获取dom元素或者组件实例
1、能够更准确的控制何时refs 被设置和解除
React 会在组件挂载时,调用 ref 回调函数并传入 DOM元素(或React实例),当卸载时调用它并传入 null。在 componentDidMount 或 componentDidUpdate 触发前,React 会保证 Refs 一定是最新的。
2、例子
import React from "react";
import LearnRef2 from "./learn-ref2";export default class LearnRef3 extends React.Component {state = {learnRef2: null}/*** 初始化的时候会传入ref组件的实例* 组件卸载的时候会传入null* @param {} component */initComponentRef = (component) => {this.learnRef2 = component};addAge () {if (this.learnRef2) {this.learnRef2.current.addAge()}}render() {return (<div><div>哈喽 ref</div><LearnRef2 ref={this.getComponent}></LearnRef2><button onClick={() => this.addAge()}>修改子组件里的年龄</button></div>);}
}