reactjs 为什么不const { innerRef,... props } = this.props;在react ref forwarding中获取对this.props.innerRef的引用?

k2fxgqgv  于 2023-06-05  发布在  React
关注(0)|答案(1)|浏览(68)

在阅读了react legacy docs中的转发引用并遵循SO post中关于在类上使用引用转发的示例之后,我尝试创建一个工作示例,如下所示:

class Card extends React.Component {

  constructor(props) {
    super(props);
    this.myRef = React.createRef();
    //after three seconds focus myRef
    setTimeout(() => {
      console.log(this.myRef);
      this.myRef.current.focus();
    }, 3000);
  }

  render() {
    return <FancybtnWthRef ref={this.myRef} txt="random"/>;
  }
}

//Fancybtn class based componenet with ref forwarding

class Fancybtn extends React.Component {
  constructor(props) {
    super(props);
    const { innerRef, ...props2 } = this.props;
    console.log(innerRef, this.props.innerRef); //doesn't get live binding to this.props.innerRef
  }

  render() {
    return (
      <button className="fancy-btn" ref={this.innerRef} {...this.props2}>
        {this.props.txt}
      </button>
    );
  }
}

const FancybtnWthRef = React.forwardRef((props, ref) => {
  return <Fancybtn {...props} innerRef={ref} />;
});



ReactDOM.render(
  <Card />,
  document.getElementById('root')
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

<div id="root"></div>

另一方面,如果我直接为button抓取this.props.innerRef对象,那么它可以工作:

class Card extends React.Component {

  constructor(props) {
    super(props);
    this.myRef = React.createRef();
    //after three seconds focus myRef
    setTimeout(() => {
      console.log(this.myRef);
      this.myRef.current.focus();
    }, 3000);
  }

  render() {
    return <FancybtnWthRef ref={this.myRef} txt="random"/>;
  }
}

//Fancybtn class based componenet with ref forwarding

class Fancybtn extends React.Component {
  constructor(props) {
    super(props);
    const { innerRef, ...props2 } = this.props;
    console.log(innerRef, this.props.innerRef);
  }

  render() {
    return (
      <button className="fancy-btn" ref={this.props.innerRef} {...this.props2}>
        {this.props.txt}
      </button>
    );
  }
}

const FancybtnWthRef = React.forwardRef((props, ref) => {
  return <Fancybtn {...props} innerRef={ref} />;
});



ReactDOM.render(
  <Card />,
  document.getElementById('root')
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

<div id="root"></div>

在简单的javascript中,解构获得对象的实时绑定,如下所示:

var obj = {x:1, obj2: {y: 33}}
const {x, obj2} = obj;
obj2.y = 44;
cconsole.log(obj.obj2.y); //gives 44

使用相同的参数,为什么const { innerRef, ...props } = this.props;不为button获取实际的this.props.innerRef

ds97pgxw

ds97pgxw1#

const { innerRef, ...props2 } = this.props;正确地从props获取innerRef属性。但是,这会创建两个局部变量。它不会在示例本身上设置实际的innerRef属性。因此,this.innerRefundefined,将其作为ref传递给<button>没有任何效果。请注意,与Java等其他语言不同,不使用this访问变量将不会尝试在封闭类示例的字段中查找该变量。
您必须手动将innerRef分配给示例才能看到它工作:

this.innerRef = innerRef;

或者,要将属性解构到this上,可以这样重命名属性:

({ innerRef: this.innerRef, ...this.props2 } = this.props);

相关问题