为何无法通过useRef获取DOM元素?React自定义组件场景
问题:使用forwardRef后仍无法获取自定义输入组件的DOM元素,ref始终为null
在Home组件中尝试通过useRef获取自定义组件MyInput内部的input元素,已经为MyInput使用了forwardRef,但控制台打印的ref始终为null,无法拿到input元素。
Home组件代码
const Home = () => { let inputRef = useRef<HTMLInputElement>(null); const deleteInputText = (e: React.MouseEvent<HTMLDivElement>) => { dispatch(changeInputSearh("")); if (inputRef && inputRef.current) { inputRef.current.focus(); } }; return ( <div className="input-home"> <MyInput type="text" placeholder="поиск..." value={inputOption} onChange={changeInputRedux} className="input-home__inp" ref={inputRef} /> </div> ); };
MyInput组件代码
const MyInput = React.forwardRef((props: any, ref) => { console.log(ref); return <input {...props}></input>; });
控制台输出
{current: null} current: null [[Prototype]]:Object
原因及解决方案
原因
你虽然给MyInput组件添加了forwardRef来接收外部传入的ref参数,但没有将这个ref绑定到组件内部的input元素上。目前只是把props传递给了input,ref并没有被传递到真实的DOM节点,所以外部的inputRef.current始终是null。
解决方案
方案一:直接绑定ref到内部input
这是最直接的方式,把外部传入的ref直接赋值给内部input的ref属性:
const MyInput = React.forwardRef((props: any, ref) => { // 将外部ref绑定到内部input元素 return <input {...props} ref={ref} />; });
方案二:使用useImperativeHandle自定义暴露的方法(可选)
如果需要在MyInput组件内部也操作input的ref,同时只想给外部暴露特定方法而非整个DOM节点,可以用useImperativeHandle:
import { forwardRef, useImperativeHandle, useRef } from 'react'; const MyInput = forwardRef((props: any, ref) => { const internalInputRef = useRef<HTMLInputElement>(null); // 自定义暴露给外部的方法 useImperativeHandle(ref, () => ({ focus: () => { internalInputRef.current?.focus(); }, clearValue: () => { if (internalInputRef.current) { internalInputRef.current.value = ''; props.onChange?.({ target: { value: '' } }); } } })); return <input {...props} ref={internalInputRef} />; });
使用方案二时,外部调用方式会变成:
// 聚焦输入框 inputRef.current?.focus(); // 清空输入框 inputRef.current?.clearValue();
内容的提问来源于stack exchange,提问作者Максим Дмитриевич
相关产品推荐
相关产品推荐

