Ben*_*Ben 4 reactjs react-ref react-hooks
const Comp1 = forwardRef((props, ref) => {
useImperativeHandle(ref, () => ({
print: () => {
console.log('comp1')
}
}), []);
return <div>comp1</div>
});
const Comp2 = () => <div>comp2</div>;
const App = () => {
const ref1 = useRef(null);
const ref2 = useRef(null);
useEffect(() => {
console.log(ref1); // prints ref1 with the expected current
console.log(ref2); // prints ref2 with current: null
})
return <div><Comp1 ref={ref1}/><Comp2 ref={ref2}/></div>
}
Run Code Online (Sandbox Code Playgroud)
反应文档说:
您不能在函数组件上使用 ref 属性,因为它们没有实例。(更多)
这意味着您不能将 refs 绑定到功能组件。这就是为什么你ref2.current的null. 如果要将 ref 绑定到组件,则需要使用类组件。您ref1不是对Comp1组件的引用。它实际上包含一个你在useImperativeHandle钩子中传递的对象。即它包含下一个对象:
{
print: () => {
console.log('comp1')
}
}
Run Code Online (Sandbox Code Playgroud)
forwardRef如果要将 ref 与组件呈现的某些 HTML 元素或类组件绑定,则必须使用功能组件。或者您可以使用useImperativeHandle钩子将您的 ref 与某个对象绑定。
更新
的使用与useImperativeHandle向类组件添加方法相同:
class Comp1 extends React.Component {
print() {
console.log('comp1');
}
render() {
return (<div>comp1</div>)
}
}
Run Code Online (Sandbox Code Playgroud)
是相同的
const Comp1 = forwardRef((props, ref) => {
useImperativeHandle(ref, () => ({
print: () => {
console.log('comp1')
}
}), []);
return <div>comp1</div>
});
Run Code Online (Sandbox Code Playgroud)
你在评论中问:
因此,在使用钩子(并且仍然避免使用类)之后,使用 ref 的唯一方法是使用
useImperativeHandle(实际上是使用“假”引用)?这是一个好习惯吗?
回答:使用 ofuseImperativeHandle与在类组件中通过 refs 调用子组件方法是同样的坏习惯。React doc 说你应该避免通过 refs 调用子组件方法,你应该避免使用useImperativeHandle. 此外,您需要避免在没有它们的情况下可以做事情的地方使用 refs。
| 归档时间: |
|
| 查看次数: |
11392 次 |
| 最近记录: |