在我的 React 项目管理器应用程序中,为什么切换项目时编辑(输入)字段保持打开状态?

问题描述 投票:0回答:1

如果我没有完全解释我的问题,请提前道歉。我会尽力的。我有一个项目管理器应用程序,能够添加包含项目详细信息(例如标题、截止日期和说明)的新项目。所有添加的项目都显示在左侧的旁注中,项目详细信息显示在右侧。选择特定项目将在应用程序的右侧呈现其详细信息。我最近添加了单击“详细信息”文本进行编辑的功能 - 本质上我添加了一个 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链接

任何有关如何正确使用此功能及其原因的帮助,我们将不胜感激。

reactjs
1个回答
0
投票

useState
钩子的默认状态是在组件安装阶段初始化的。重新渲染后(当您选择不同的项目时会发生这种情况),
<ProjectDetails />
组件不会被卸载而是重新渲染,因此子组件
EditableField
的状态保持不变。 React 组件重新渲染时会重置其状态吗?

一个简单的修复方法是将状态重置逻辑添加到

useEffect
,其中项目 ID 将位于依赖项数组中:

// EditableField.tsx

useEffect(() => {
  setEdit(false);
}, [data.id]) 
© www.soinside.com 2019 - 2024. All rights reserved.