【问题标题】:react function components' setState not applying changes反应功能组件的 setState 未应用更改
【发布时间】:2020-12-28 18:58:39
【问题描述】:

我有一个反应函数组件,它返回一个简单的表单。 我要做的就是在提交时清除字段以前的错误,然后再次验证字段。 令人惊讶的是,第一次调用 setState 并没有应用更改,但其他调用正常。

这是整个代码:

import React from "react";
import { TextField, Button } from "@material-ui/core";

export default function EditPresonalInfo() {
  const [fields, setFields] = React.useState({
    username: "",
    usernameHelper: "",
    usernameError: false,
    name: "",
    nameHelper: "",
    nameError: false,
  });

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

    setFields({
      ...fields,
      usernameError: false,
      usernameHelper: "",
      nameError: false,
      nameHelper: "",
    });

    if (fields.username.length < 4) {
      setFields({
        ...fields,
        usernameHelper: "use at least 4 characters",
        usernameError: true,
      });
      return;
    }

    if (fields.name.length < 2) {
      setFields({
        ...fields,
        nameHelper: "use at least 2 characters",
        nameError: true,
      });
      return;
    }
  };

  const handleChange = (fieldName) => (event) => {
    setFields({
      ...fields,
      [fieldName]: event.target.value,
    });
  };

  return (
    <form onSubmit={submitForm}>
      <TextField
        label="username"
        onChange={handleChange("username")}
        error={fields.usernameError}
        value={fields.username}
        helperText={fields.usernameHelper}
      />
      <TextField
        label="name"
        onChange={handleChange("name")}
        error={fields.nameError}
        value={fields.name}
        helperText={fields.nameHelper}
      />
      <Button type="submit">submit</Button>
    </form>
  );
}

有人可以帮我解决我所缺少的和有什么问题吗?

【问题讨论】:

  • 我宁愿使用通常的语法(import { useState } from 'react'; 然后 useState())开始。您提到的其他电话在哪里?
  • 您的fields 不会在您的函数submitForm 开始时直接更新,它将在生命周期结束时更新。因此,当您稍后在函数上使用 fields 时,它仍然是“原始”值。
  • @DavidThery 我的意思是 if 语句中正确设置帮助文本的调用
  • @Nico_ 你的意思是因为使用了 ...fields 而字段还没有更新?

标签: reactjs setstate arrow-functions use-state


【解决方案1】:

您不必为每个验证设置状态。对于这种情况,我认为最好先根据验证创建新状态,然后再设置状态。

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

  const newFields = { ...fields };

  if (fields.username.length < 4) {
    newFields["usernameHelper"] = "use at least 4 characters";
    newFields["usernameError"] = true;
  } else {
    newFields["usernameHelper"] = "";
    newFields["usernameError"] = false;
  }

  if (fields.name.length < 2) {
    newFields["nameHelper"] = "use at least 2 characters";
    newFields["nameError"] = true;
  } else {
    newFields["nameHelper"] = "";
    newFields["nameError"] = false;
  }

  setFields(newFields);
};

【讨论】:

  • 谢谢!在我犯错后这真的很有帮助
【解决方案2】:

这个对我有用

 const submitForm = (e) => {
    e.preventDefault();
    let usernameHelper = "";
    let usernameError = false;
    let nameError = false;
    let nameHelper = "";

    if (fields.username.length < 4) {
      usernameHelper = "use at least 4 characters";
      usernameError = true;
    }
    if (fields.name.length < 2) {
      nameHelper = "use at least 2 characters";
      nameError = true;
    }
    setFields({
      ...fields,
      usernameError: usernameError,
      usernameHelper: usernameHelper,
      nameError: nameError,
      nameHelper: nameHelper,
    });
  };

【讨论】:

    【解决方案3】:

    据我了解,您希望对表单应用一些验证,因此您已经在使用 MaterialUI,我建议您点击此链接 https://react-hook-form.com/get-started#Applyvalidation。您会在那里找到最佳实践和更容易的实施。

    【讨论】:

    • 感谢您的帮助,但我正在学习 React 作为初学者,我真的很想看看这种方法发生了什么
    • 输“返回;”在每个 if 语句中,在 java 脚本中,代码不会被执行行买线,因此您的 on Submit 函数可以执行其中一个 if 语句并在执行其余代码之前结束(很可能是第一个 setFields)
    • 没错,我也是误会了。因为有多个错误,只出现了一个
    【解决方案4】:

    我当时误用setFieldsfields, 它可以像这样明确地完成

    const submitForm = (e) => {
        e.preventDefault();
    
        fields.nameError= false
        fields.usernameError= false
        fields.nameHelper= ""
        fields.usernameHelper= ""
    
        if (fields.name.length < 2) {
          fields.nameHelper = "use at least 2 characters";
          fields.nameError = true;
        }
    
        if (fields.username.length < 4) {
          fields.usernameHelper = "use at least 4 characters";
          fields.usernameError = true;
        }
    
        setFields({
          ...fields
        })
      };
    

    【讨论】:

      猜你喜欢
      • 2022-01-16
      • 2022-06-27
      • 1970-01-01
      • 2020-09-02
      • 2022-11-22
      • 2022-01-05
      • 2019-08-13
      • 1970-01-01
      • 2019-07-24
      相关资源
      最近更新 更多