reactjs - 带有钩子的函数组件中的数组未在 React 状态下更新
问题描述
我正在探索表单验证并在 State 中有一个 validationMessages 数组来存储验证消息。当用户提交表单时,我运行验证并尝试更新 State 中的 validationMessages 数组。但是只添加了最后一个validationMessage,而没有添加之前的validationMessage。代码如下:
import React, { useState } from 'react';
function Form(props) {
const [validationMessages, setValidationMessages] = useState([]);
const [formData, setFormData] = useState({});
const handleChange = ({ target }) => {
setFormData({ ...formData, [target.name]: target.value });
}
const handleClick = (evt) => {
validateForm();
if (validationMessages.length > 0) {
evt.preventDefault();
}
}
const validateForm = () => {
const { firstName, lastName, DOB, gender } = formData;
setValidationMessages([]);
if (!firstName) {
setValidationMessages([...validationMessages, "First Name is required"]);
}
if (!lastName) {
setValidationMessages([...validationMessages, "Last Name is required"]);
}
if (!gender) {
setValidationMessages([...validationMessages, "Please select a Gender"]);
}
if (!DOB) {
setValidationMessages([...validationMessages, "Date of Birth is required"]);
}
}
return <div style={{ display: 'flex', flexDirection: 'row' }} >
<form style={{ display: 'flex', flexDirection: 'column' }}>
<label>First Name</label>
<input value={formData.firstName || ''} onChange={handleChange} type="text" name="firstName" />
<label>Last Name</label>
<input value={formData.lastName || ''} onChange={handleChange} type="text" name="lastName" />
<label>Date of Birth</label>
<input value={formData.DOB || ''} onChange={handleChange} type="datetime-local" name="DOB" />
<label>Gender</label>
<div><input value="Male" checked={formData.gender === "Male"} onChange={handleChange} type="radio" name="gender" />Male</div>
<div><input value="Female" checked={formData.gender === "Female"} onChange={handleChange} type="radio" name="gender" />Female</div>
<div><input value="None" checked={formData.gender === "None"} onChange={handleChange} type="radio" name="gender" />Prefer not to say</div>
<button type="button" onClick={handleClick}>Save</button>
</form><div>{validationMessages.length > 0 && <span>Validation Summary</span>}
<ul>
{validationMessages.map(vm => <li key={vm}>{vm}</li>)}
</ul></div></div>;
}
export default Form;
问题是如果我将所有字段留空,那么仍然只有最后一条验证消息被添加到validationMessages 的状态数组中。即使花了很多时间在 StackOverflow.com 上查看类似问题及其答案,也无法弄清楚。任何指针或帮助表示赞赏。
解决方案
In your validateForm
, you call setValidationMessages
several times to add a message to the state array. But setValidationMessages
is asynchronous, so the second call won't have the new version of validationMessages
and therefore only the last message will be saved to state
Here is a possible solution:
const validateForm = () => {
const { firstName, lastName, DOB, gender } = formData;
const messages = [];
if (!firstName) {
messages.push("First Name is required");
}
if (!lastName) {
messages.push"Last Name is required");
}
if (!gender) {
messages.push("Please select a Gender");
}
if (!DOB) {
messages.push("Date of Birth is required");
}
setValidationMessages(messages);
}
推荐阅读
- javascript - Maphilight() 在放大/缩小图像地图后停止正常工作
- php - 将数据从 CSV 插入数据库 codeigniter
- javascript - 用javascript打印页面时显示文本框
- mysql - 总和值的总和值
- java - 如何使用 spring boot 和 aspect 记录请求正文
- php - 如何将 if/else if 转换为循环
- database - 可以拆分数据库中的值和参数吗
- android - 如何从多个活动中调用单个服务?
- facebook - 批准 Facebook 上的应用程序需要多长时间?
- angular - 访问 json 中的数组对象以在 Angular 5 中显示下拉值