网站搜索

reactjs - 如果输入为空且有错误则禁用按钮


我正在构建注册表单。我有一个 signup.tsx 文件,其中对输入进行了验证。但我遇到了一个问题,我想在输入为空或注册过程中输入有一个或多个错误时禁用按钮。我不知道如何使用 disable={} 来禁用按钮。我尝试这样做:disable={!input}。但当然,这样是不对的。

我在 signup.tsx 中的代码:

import React, { useState } from 'react';
import './signup.css';

function Signup() {

const [input, setInput] = useState({
    username: "",
    email: "",
    password: ""
});

const [error, setError] = useState({
    username: "",
    email: "",
    password: ""
});

const onInputChange = (e: any) => {
      const { name, value } = e.target;
      setInput(prev => ({
        ...prev,
        [name]: value
      }));
      validateInput(e);
};
const validateInput = (e: any) => {
  let { name, value } = e.target;
  setError(prev => {
  const stateObj = { ...prev, [name]: "" };
  const minLengthUser = /.{4,}/;
  const minLengthUsername = minLengthUser.test(value);
  const minLenghtPass = /.{6,}/;
  const minLenghtPassword = minLenghtPass.test(value);

switch (name) {
  case "username":
    if (!value) {
      stateObj[name as keyof typeof stateObj] = "Username is required";
    } else if (!minLengthUsername) {
        stateObj[name as keyof typeof stateObj] = "Username should be minimum 4 characters"
    };
break;

  case "email":
    if (!value) {
        stateObj[name as keyof typeof stateObj] = "Email address is required"
    } else if (!/^[A-Z0-9._%+-]+@[A-Z0-9.-]+\.[A-Z]{2,4}$/i.test(input.email)) {
        stateObj[name as keyof typeof stateObj] = 'Invalid email address'
    }
  break;

  case "password":
    if (!value) {
      stateObj[name as keyof typeof stateObj] = "Password is required";
    } else if (!minLenghtPassword) {
        stateObj[name as keyof typeof stateObj] = "Password should be minimum 6 characters";
    }
  break;

  default:
  break;
}

return stateObj;
});
}

return (
<div className="container">
 <div className="box">
    <h1>
      <p className="title">Create an account</p>
    </h1>
    <form className="form">
        <div className="form-outline">
            <label className="input-label">Your Name</label>
            <input
              name="username"
              type="text"
              className="input"
              value={input.username}
              onChange={onInputChange}
              onBlur={validateInput}
            />
            {error.username && <div className="alert"><span className="err">{error.username}</span></div>}
        </div>

        <div className="form-outline">
            <label className="input-label">Your Email</label>
            <input
              name="email"
              type="email"
              className="input"
              value={input.email}
              onChange={onInputChange}
              onBlur={validateInput}
            />
            {error.email && <div className="alert"><span className="err">{error.email}</span></div>}
        </div>

        <div className="form-outline">
            <label className="input-label">Password</label>
            <input
              name="password"
              type="password"
              className="input"
              value={input.password}
              onChange={onInputChange}
              onBlur={validateInput}
            />
            {error.password && <div className="alert"><span className='err'>{error.password}</span></div>}
        </div>

        <div className="button">
            <button className="btn">Create account</button>
        </div>

    </form>
 </div>
</div>
)
}

export default Signup;

答案#1

你可以创建一个方法 isInputValid,它返回一个布尔值。它会遍历错误对象,检查错误,如果它们不是 默认 值 "" 就返回 false。如果它们全都是默认值则返回 true。

const isInputValid = Object.values(error).reduce((isValid: boolean, err) => {
  if (err !== "") return false;
  // will return true if isValid is true else returns false
  return isValid && true;
}, true);

你可以这样使用它

<button className="btn" disabled={!isInputValid}>
  Create account
</button>

编辑:

要在开始时禁用按钮,您可以使用 null 作为值。

type ErrorType = {
  username: string | null;
  email: string | null;
  password: string | null;
};

const [error, setError] = useState<ErrorType>({
  username: null,
  email: null,
  password: null,
});
const isValid = Object.values(error).reduce((isValid: boolean, error) => {
  if (error === null || error !== "") return false;
  return isValid && true;
}, true);