我无法理解 React 中的 ref 是什么。我知道这是一个回调函数,你把它放在渲染函数中,但除此之外我无法理解它是什么以及它的目的是什么。
React 中的引用是什么?
Refs 是您获取已创建组件的句柄的一种方式。
IE。
<Text ref={(component)=>{this.textComponent = component}} > Here is some Text</Text>
然后在您的代码中,您可以通过执行以下操作访问您的文本:
this.textComponent
这将使您能够以面向对象的方式调用组件上的函数。
我只想指出 React/React-Native 使用声明式编程范式,其中数据和“控制”通过自上而下的属性传递进行管理。而在命令式风格中,您处理对象和指针并传递它们以便调用它们上的函数。在这种情况下,Refs 是一个逃生舱口,它允许您获得一个声明的组件,以便您可以以命令式风格调用它们上的函数。
参考 React 官方文档:https : //reactjs.org/docs/refs-and-the-dom.html
React 有典型的处理孩子的方式。它props
以自上而下的方式使用。并且要修改孩子,您必须使用新props重新渲染。但是在某些情况下,您希望在此典型流程之外修改/处理子项。在这些情况下,您使用 refs。
Ref 是一个接受回调的属性,每当安装或卸载组件时都会调用此回调。可以将 Refs 添加到 dom 元素或组件。例子:
return (
<div>
<input
type="text"
// ref to a dom element
ref={(input) => { this.textInput = input; }} />
</div>
);
return (
<MyComponent
// ref to a MyComponent(child component)
ref={(component) => { this.childComponent = component; }}
{...props}
/>
);
每当安装组件时,都会使用 dom 元素或子组件实例调用 ref 回调。每当组件卸载时,它都会用null
.
现在您可以使用this.textInput
orthis.childComponent
并在其上调用其不同的可用方法。
Refs 只能提供给 DOM 元素或类组件。它们不适用于功能组件。例子:
function MyFunctionalComponent(props) {
return <input type="text" />;
}
return (
<MyFunctionalComponent
// This won't work
ref={(component) => { this.childComponent = component; }}
{...props}
/>
);
仅在绝对必要时才应使用 Refs,因为它们使您可以直接访问 DOM 中的元素/组件。
Refs 是一种在 DOM 元素或类组件实例上设置变量的方法。
有两种类型的引用:回调引用和对象引用。
对象引用
使用useRef()
或创建对象引用React.createRef()
。
要使用它们(一个带有引用 DOM 元素的函数组件的示例):
声明一个“容器”变量(您将在下一步中指向一个 DOM 元素)并将其设置为等于
useRef()
. 这是您的“参考对象”。ref
向 DOM 元素添加属性。将其设置为等于您的ref
对象。现在这个
ref
对象代表了你指向它的 DOM 元素,可以用来访问它的方法和属性。function InputField() { const refForInput = useRef(); // 1. initializing `refForInput` as a reference object. return ( <div> <input type='text' ref={refForInput} /> //2. passing it to the input element as its ref <button onClick={() => refForInput.current.focus()}>Click to focus the input field</button> // 3. now, calling `refForInput` will refer to the DOM <input> element, and you can access its `focus()` method. </div> ) }
如果使用类组件,过程类似;有关详细信息,请参阅React 文档。
回调引用
回调引用功能类似,但允许更细粒度的控制。
要创建回调引用,您可以类似地ref
向 DOM 元素添加一个属性,但不是传入ref
对象,而是传入回调。这个回调接收元素本身作为回调的参数;然后,您可以将其设置为等于现有值(this.something
在类中;在函数组件中已声明的变量。)
这是来自 Avid Programmer 优秀示例的示例的带注释的 vversion;有关类的示例,请参阅他的回答。
function CustomForm({handleSubmit}) {
let inputElement;
return (
<form onSubmit={() => handleSubmit(inputElement.value)}> // 2. Now, this refers to the `value` of the `<input>` element just below.
<input
type='text'
ref={(input) => inputElement = input} // 1. so, here, `input` in the callback refers to the DOM element. Now, when the component mounts, `inputElement` will *reference* this DOM <input> element.
/>
<button type='submit'>Submit</button>
</form>
)
}
请注意,将null
在组件卸载时调用回调。
它们为什么有用?
它们不应该经常使用;它们是逃生舱口。它们允许您访问focus()
在 React 组件上可能不可用的实际 html 元素上可用的API 方法(是一个常见示例)。如果这看起来令人困惑,请记住,例如,React 按钮组件与 html 按钮组件不同。您可以调用focus()
html 按钮元素,但不能调用React 按钮元素。
Refs 是一个逃生舱,它允许您直接访问 DOM 元素或组件的实例。为了使用它们,您向组件添加一个 ref 属性,该属性的值是一个回调函数,它将接收底层 DOM 元素或组件的已安装实例作为其第一个参数。
class UnControlledForm extends Component {
handleSubmit = () => {
console.log("Input Value: ", this.input.value)
}
render () {
return (
<form onSubmit={this.handleSubmit}>
<input
type='text'
ref={(input) => this.input = input} />
<button type='submit'>Submit</button>
</form>
)
}
}
通过利用 JavaScript 中的闭包,refs 还可以与功能组件一起使用。
function CustomForm ({handleSubmit}) {
let inputElement
return (
<form onSubmit={() => handleSubmit(inputElement.value)}>
<input
type='text'
ref={(input) => inputElement = input} />
<button type='submit'>Submit</button>
</form>
)
}
(“闭包”只是引用在函数外声明的变量的一种奇特方式 - 在这种情况下,inputElement
- 在您的函数内,在这种情况下ref={(input) => inputElement = input}
。)