useImperativeHandle的使用

你不能在函数组件上使用 ref 属性,因为它们没有实例:

import React, { Component } from 'react';

function MyFunctionComponent() {
  return <input />
}

class Parent extends React.Component {
  constructor(props) {
    super(props);
    this.textInput = React.createRef();
  }
  render() {
    return (
      <MyFunctionComponent ref={this.textInput} />
    );
  }
}

如果你需要使用 ref,你应该将组件转化为一个 class,就像当你需要使用生命周期钩子或 state 时一样。

不管怎样,你可以在函数组件内部使用 ref 属性,只要它指向一个 DOM 元素或 class 组件:

function CustomTextInput(props) {
  // 这里必须声明 textInput,这样 ref 才可以引用它
  let textInput = React.createRef();

  function handleClick() {
    textInput.current.focus();
  }

  return (
    <div>
      <input
        type="text"
        ref={textInput} />

      <input
        type="button"
        value="Focus the text input"
        onClick={handleClick}
      />
    </div>
  );
}

在下面的示例中,MyFunctionComponent 使用 React.forwardRef 来获取传递给它的 ref,然后转发到它渲染的 DOM button

const MyFunctionComponent = React.forwardRef((props, ref) => (
  <button ref={ref}>
    {props.children}
  </button>
))

class Parent extends React.Component {
  constructor(props) {
    super(props);
    this.textInput = React.createRef();
  }
  componentDidMount() {
    console.log(this.textInput.current)
  }
  render() {
    return (
      <MyFunctionComponent ref={this.textInput} />
    );
  }
}

第二个参数 ref 只在使用 React.forwardRef 定义组件时存在。常规函数和 class 组件不接收 ref 参数,且 props 中也不存在 ref

useImperativeHandle

useImperativeHandle 可以让你在使用 ref 时自定义暴露给父组件的实例值。useImperativeHandle 应当与 forwardRef 一起使用:

const MyFunctionComponent = React.forwardRef((props, ref) => {
  const inputRef = useRef();
  useImperativeHandle(ref, () => ({
    focus: () => {
      inputRef.current.focus();
    }
  }));
  return (
    <input ref={inputRef} />
  )
})

class Parent extends React.Component {
  constructor(props) {
    super(props);
    this.textInput = React.createRef();
  }
  componentDidMount() {
    this.textInput.current.focus()
  }
  render() {
    return (
      <MyFunctionComponent ref={this.textInput} />
    );
  }
}
已标记关键词 清除标记
相关推荐
©️2020 CSDN 皮肤主题: 技术工厂 设计师:CSDN官方博客 返回首页