【问题标题】:How to edit input value in React Js?如何在 React Js 中编辑输入值?
【发布时间】:2021-06-19 18:17:59
【问题描述】:

我正在尝试为我的应用程序创建一个组件,当我单击按钮时,输入字段打开,添加文本后,我再次单击该按钮并打开另一个输入,依此类推。然后所有这些输入的 e.target.value 应该以不同的状态保存并显示在另一个组件中。到目前为止,我能够创建这样的输入,但我不知道如何编辑输入字段。我的代码:

import "./styles.css";
import React, { useState } from "react";

export default function App() {
  const [input, setInput] = useState([{}]);
  const [data, setData] = useState([]);

  function handleChange(i, e) {
    e.preventDefault();

    setInput([
      {
        id: i,
        value: e.target.value
      }
    ]);
  }

  function handleAddInput() {
    const values = [...input];
    values.push({ value: null });
    setInput(values);
  }

  const handleSave = () => {
    let value = input?.map((item) => {
      return item.value;
    });
    if (!value || /^\s*$/.test(value)) {
      return;
    }

    const newData = [...data, ...input];

    setData(newData);

    setInput([])
  };

  return (
      <div className="App">
        <button type="button" className="btn" onClick={() => handleAddInput()}>
          Add  Input fields
        </button>

        {input?.map((input, idx) => {
          return (
            <div key={input.id}>
              <input
                type="text"
                placeholder="Enter text"
                onChange={(e) => handleChange(idx, e)}
                value={input.value}
              />
            </div>
          );
        })}

       
    
<h2>Display Added Fields and Edit</h2>
      {data?.map((item) => {
        return (
          <>
            <input defaultValue={item.value}
            
            
            
            />
          </>
        );
      })}

<button className="btn" onClick={handleSave}>Save</button>

      {data?.map((item) => {
        return (
          <div style={{ display: "flex", flexDorection: "column", marginTop:"20px" }}>
            {item.value}
          </div>
        );
      })}
        </div>
  );
}

codeSandbox

当我单击“添加输入字段”时,弹出新输入,我输入任何输入文本,然后再次单击“添加输入字段”并打开另一个输入,当我单击“保存”按钮时,所有输入值都是保存到状态(作为数据)并显示为输入,之后我可以映射“数据”并显示接收到的输入。就像在图像上我添加了“第一”,然后是“第二”,它们显示得很好,但我不知道如何编辑它们,例如将“第一”更改为“第三”并在保存按钮上“第三”应该显示而不是“第一”。非常感谢任何帮助和建议。

【问题讨论】:

标签: javascript reactjs input react-hooks default-value


【解决方案1】:

问题

  1. 使用索引作为 id 不是一个好主意,它们不是唯一的。
  2. handleChange 不会保留现有的输入状态。
  3. React 键的其他各种问题,以及将状态从 input 复制到 data

解决方案

  1. 您不需要输入对象,您可以存储来自输入的字符串原语。这意味着您也不需要 id 属性,按索引更新很简单。
  2. 应该使用功能状态更新来更新之前的状态。
  3. 我建议使用表单和onSubmit 处理程序来处理更新data 状态数组值。

代码:

function App() {
  const [input, setInput] = useState([]);
  const [data, setData] = useState([]);

  function handleChange(i, e) {
    e.preventDefault();

    setInput((values) =>
      values.map((value, index) => (index === i ? e.target.value : value))
    );
  }

  function handleAddInput() {
    setInput((input) => input.concat(""));
  }

  const saveHandler = (e) => {
    e.preventDefault();

    // Map all existing form field values
    setData((data) => data.map((_, i) => e.target[i].value));

    // If there are any input values, add these and clear inputs
    if (input.length) {
      setData((data) => data.concat(input));
      setInput([]);
    }
  };

  return (
    <div className="App">
      <button type="button" className="btn" onClick={handleAddInput}>
        Add Input fields
      </button>

      {input.map((input, idx) => {
        return (
          <div key={idx}>
            <input
              type="text"
              placeholder="Enter text"
              onChange={(e) => handleChange(idx, e)}
              value={input.value}
            />
          </div>
        );
      })}

      <h2>Display Added Fields and Edit</h2>
      <form onSubmit={saveHandler}>
        {data.map((item, i) => {
          return (
            <div key={i}>
              <input id={i} defaultValue={item} />
            </div>
          );
        })}

        <button className="btn" type="submit">
          Save
        </button>
      </form>

      {data.map((item, i) => {
        return (
          <div
            key={i}
            style={{
              display: "flex",
              flexDirection: "column",
              marginTop: "20px"
            }}
          >
            {item}
          </div>
        );
      })}
    </div>
  );
}

演示

编辑

编辑以生成 GUID 并将 id 属性保持到 data 状态。

  1. 添加新输入字段时生成新的 GUID。
  2. 使用id 匹配任何值更新的元素。
  3. 保存输入字段时,只需将input 数组复制到data
  4. 在示例中,我还在每一步都渲染了id,因此很明显数据元素仍然是相同的对象。

代码:

function App() {
  const [input, setInput] = useState([]);
  const [data, setData] = useState([]);

  const handleChange = (id) => (e) => {
    e.preventDefault();

    setInput((values) =>
      values.map((el) =>
        el.id === id
          ? {
              ...el,
              value: e.target.value
            }
          : el
      )
    );
  };

  function handleAddInput() {
    setInput((input) =>
      input.concat({
        id: uuidV4(),
        value: ""
      })
    );
  }

  const saveHandler = (e) => {
    e.preventDefault();

    setData((data) =>
      data.map((el) => ({
        ...el,
        value: e.target[el.id].value
      }))
    );

    if (input.length) {
      setData((data) => data.concat(input));
      setInput([]);
    }
  };

  return (
    <div className="App">
      <button type="button" className="btn" onClick={handleAddInput}>
        Add Input fields
      </button>

      {input.map((input) => {
        return (
          <label key={input.id}>
            {input.id}
            <input
              type="text"
              placeholder="Enter text"
              onChange={handleChange(input.id)}
              value={input.value}
            />
          </label>
        );
      })}

      <h2>Display Added Fields and Edit</h2>
      <form onSubmit={saveHandler}>
        {data.map((item) => {
          return (
            <div key={item.id}>
              <label>
                {item.id}
                <input id={item.id} defaultValue={item.value} />
              </label>
            </div>
          );
        })}

        <button className="btn" type="submit">
          Save
        </button>
      </form>

      {data.map((item) => {
        return (
          <div
            key={item.id}
            style={{
              display: "flex",
              flexDirection: "column",
              marginTop: "20px"
            }}
          >
            <div>
              {item.id} - {item.value}
            </div>
          </div>
        );
      })}
    </div>
  );
}

演示 2

【讨论】:

  • 谢谢,这很有帮助。只有一个问题,如何将 id 添加到 [data] 并使其成为对象?像这样 {id: 1, value: input}
  • @new_reactjs 请检查此updated codesandbox 它使用id 属性的GUID。它不使用传递的索引,而是匹配 id 来更新输入值。
  • 感谢您更新代码,检查并输入有 id,但没有数据。很抱歉一直问,但我不确定如何将 id 添加到数据中,而不是输入。
  • @new_reactjs 不是将其剥离,而是将input 的全部内容复制到data 中。这需要更新 data 数组元素的显示,因为它们现在也将是对象。我用第二个代码框的更新代码更新了我的答案。请再次检查,希望这会让它更清楚。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-06-28
相关资源
最近更新 更多