如果我没有完全解释我的问题,请提前道歉。我会尽力的。我有一个项目管理器应用程序,能够添加包含项目详细信息(例如标题、截止日期和说明)的新项目。所有添加的项目都显示在左侧的旁注中,项目详细信息显示在右侧。选择特定项目将在应用程序的右侧呈现其详细信息。我最近添加了单击“详细信息”文本进行编辑的功能 - 本质上我添加了一个 onClick 事件来在输入字段中打开该内容详细信息。
它基本上按预期工作,打开正确的字段,可以编辑内容并按预期保存 - 更新上下文存储中的我的主项目对象。
但是,如果编辑(输入)字段保持打开状态并且项目切换到另一个项目,则输入字段在不应该打开的情况下保持打开状态,我需要修复此问题。
这是我的 EditableField.jsx 组件:
import { useState, useRef, useContext, forwardRef } from "react";
import { PMContext } from "../store/pm_context";
const EditableField = forwardRef(function EditableField(
{ data, type, edit, children, ...props },
ref
) {
const { editProject } = useContext(PMContext);
const [fieldInput, setFieldInput] = useState();
const [isEdit, setEdit] = useState(false);
function handleEditProjectField() {
setFieldInput(data[type]);
setEdit((prevState) => {
return !prevState;
});
}
function handleChange(event) {
const input = event.target.value;
setFieldInput(input);
}
function handleSaveProjectField() {
if (fieldInput.trim() === "") {
modal.current.open();
return;
}
editProject(fieldInput, type);
setEdit((prevState) => {
return !prevState;
});
}
let inputField =
type === "description" ? (
<textarea
ref={ref}
className="input-field"
type="text"
value={fieldInput}
onChange={handleChange}
/>
) : type === "dueDate" ? (
<input
ref={ref}
className="input-field"
type="date"
value={fieldInput}
onChange={handleChange}
/>
) : (
<input
ref={ref}
className="input-field"
type="text"
value={fieldInput}
onChange={handleChange}
/>
);
let editField = isEdit ? (
<div className="editable-field">
{inputField}
<button
id={data.id}
onClick={() => handleSaveProjectField(data.id)}
className="save"
>
Save
</button>
</div>
) : (
<div className="editable-field" onClick={handleEditProjectField} {...props}>
{children}
</div>
);
return <>{editField}</>;
});
export default EditableField;
我想,通过将 isEdit 的默认状态设置为 false,当组件重新渲染时,isEdit 将为 false,因此只有 {children} 会在可编辑字段 div 中渲染,但情况并非如此,而 {inputField}持续存在。
我在这里设置了一个正在运行的应用程序的codesandbox:CodeSandbox链接
任何有关如何正确使用此功能及其原因的帮助,我们将不胜感激。
useState
钩子的默认状态是在组件安装阶段初始化的。重新渲染后(当您选择不同的项目时会发生这种情况),<ProjectDetails />
组件不会被卸载而是重新渲染,因此子组件EditableField
的状态保持不变。 React 组件重新渲染时会重置其状态吗?
一个简单的修复方法是将状态重置逻辑添加到
useEffect
,其中项目 ID 将位于依赖项数组中:
// EditableField.tsx
useEffect(() => {
setEdit(false);
}, [data.id])