【发布时间】:2021-01-09 03:31:05
【问题描述】:
我想使用自定义挂钩来切换输入元素。
这是我的自定义钩子:
import { RefObject, useEffect } from "react";
export const useEscape = (
ref: RefObject<HTMLElement>,
triggerFn: () => void
) => {
useEffect(() => {
const handleClickOutside = (event: MouseEvent) => {
if (ref.current && !ref.current.contains(event.target as Node)) {
triggerFn();
}
};
document.addEventListener("click", handleClickOutside);
return () => window.removeEventListener("click", handleClickOutside);
});
};
以及使用钩子的示例
import * as React from "react";
import "./styles.css";
import { useEscape } from "./useEscape";
export default function App() {
const [showInput, setShowInput] = React.useState(false);
const inputRef = React.useRef(null);
useEscape(inputRef, () => {
if (showInput) setShowInput(false);
});
return (
<div>
{showInput && (
<input ref={inputRef} placeholder="click outside to toggle" />
)}
{!showInput && (
<span
style={{ border: "1px solid black" }}
onClick={() => {
console.log("toggle to trigger");
setShowInput(true);
}}
>
click to toggle input
</span>
)}
</div>
);
}
这是 link 到代码沙盒演示。
这就是问题所在。在我单击span 元素以切换到输入状态后。在输入元素之外单击后,它将永远无法再次切换回输入状态。
我想我知道为什么会这样。 react ref 仍然指向最初创建的 input 元素。但是,当 react 切换到显示 span 状态时,它会卸载 input 元素,并且我的自定义钩子永远不会与 React 同步以获取新的 input 元素。如何自定义我的 useEscape 挂钩,以便 react ref 同步? (顺便说一句,我不想将样式用作视觉上“隐藏”输入元素的解决方法)。
【问题讨论】:
标签: reactjs react-hooks react-state-management react-ref