小白浅谈:react - ref 的多种使用

370 阅读2分钟

这是我参与8月更文挑战的第3天,活动详情查看:8月更文挑战

按惯例看下react官网对ref的介绍:Ref 转发是一项将 ref 自动地通过组件传递到其一子组件的技巧。对于大多数应用中的组件来说,这通常不是必需的。但其对某些组件,尤其是可重用的组件库是很有用的。

就像上述所说,在未涉及到组件化或者复杂交互式基本用不到ref,BUT,这怎么可能呢!!!

1.jpg

对于组件复用的情况,总会有你需要子组件里的方法调用或者状态返回的时候,那么这时候你就需要获取组件的一些属性了,对此在面对不同项目时,ref的创建还是有所不同的;

1. 看下使用场景:

  • 需要获取子组件方法或状态 (这种情况最为多见)
  • 需要获取子组件DOM元素相关信息时
  • 需要获取子组件聚焦或失焦状态时

2. ref 的5种创建方式

1). 类组件
  • 最为粗暴的方式calback(this)
// 父组件
import React, { Component } from "react";
import Child1 from "./Child1";

class Index extends Component {
  constructor(props) {
    super(props);
    this.state = {
      childRef: null,
    };
  }
  callback = (childRef) => {
    // 存储子组件实例   想要用什么怎么用不就为所欲为了
    this.setState({ childRef });
  };
  render() {
    return (
      <Child1 childRef={this.callback} />
    );
  }
}
export default Index;

// 子组件
import React, { Component } from "react";
class Index extends Component {
  constructor(props) {
    super(props);
  }
  componentDidMount() {
    // 将其子组件的this实例直接返回
    this.props.childRef(this);
  }
  render() {
    return (
      <div className="border">
        <h3>child1</h3>
      </div>
    );
  }
}
export default Index;
  • 高阶组件wrappedComponentRef
// 父组件这样写
<Child2 wrappedComponentRef={(ref) => {
  this.childRef = ref
}} />
// 子组件为高阶组件
// 装饰器或者包裹或等等
@Form.create()
class Index extends Component {
  • 官网推荐 React.createRef()
// 父组件---获取子组件实例
const ref = React.createRef();
<Child3 ref={ref} />
2).函数组件
  • React.useRef()
// 获取DOM元素实例
const Index = () => {
const ref4 = useRef();
 const handleClick = () => {
    console.log(ref4, "child4");
  };
  return (
    <div>
      <Button ref={ref4} onClick={handleClick}>点击</Button>
    </div>
  );
};
  • React.useImperativeHandle()
// 父组件
const ref4 = useRef();
<Child4 ref={ref4} />
//子组件
import React, { useImperativeHandle } from "react";
const Index = React.forwardRef((props, ref) => {
  // 这里返回的对象就是父组件创建的ref4实例,需要的方法或者属性直接注册即可 
  useImperativeHandle(ref, () => ({
    a: 1,
  }));
  return (
    <div className="border">
      <h3>child4</h3>
    </div>
  );
});
export default Index;

以上便是ref的几种创建方式,对于ref 的每次使用都要查相关资料,很是苦恼呀,于是乎就有了这篇关于ref的纯干货,不管你是面对class的老项目,还是hook的新项目应该都可以帮到你。