【问题标题】:How to disable form submit button until all input fields are filled?! ReactJS ES2015如何在填写所有输入字段之前禁用表单提交按钮?! ReactJS ES2015
【发布时间】:2016-03-14 01:21:38
【问题描述】:

您好,我为单个字段表单找到了答案...但是如果我们有一个包含多个字段的表单怎么办?

如果您有 1 个字段,这可以禁用它,但是当您想基于多个字段禁用它时它不起作用:

getInitialState() {
    return {email: ''}
  },
  handleChange(e) {
    this.setState({email: e.target.value})
  },
  render() {
    return <div>
      <input name="email" value={this.state.email} onChange={this.handleChange}/>
      <button type="button" disabled={!this.state.email}>Button</button>
    </div>
  }
})

【问题讨论】:

  • 我不知道 React,但我猜你可以在状态对象中添加一个 isSubmitAllowed 并在按钮的 disabled 属性中引用它。然后isSubmitAllowed 将实现您需要的任何逻辑来测试表单是否完整。
  • 完全取决于有问题的具体形式。没有什么能阻止你为每个按钮设置一个标志。
  • IMO 最简单和最可靠的方法是在渲染方法中计算它。为清楚起见,您可以计算例如const canSubmit = ...return 语句之前的单独行中,并将disabled={!canSubmit} 设置为按钮的道具。

标签: javascript reactjs


【解决方案1】:

这是表单验证的基本设置:

getInitialState() {
    return {
      email: '',
      text: '',
      emailValid: false,         // valid flags for each field
      textValid: false, 
      submitDisabled: true       // separate flag for submit
    }
  },
  handleChangeEmail(e) {         // separate handler for each field
    let emailValid = e.target.value ? true : false;        // basic email validation
    let submitValid = this.state.textValid && emailvalid   // validate total form
    this.setState({
      email: e.target.value
      emailValid: emailValid, 
      submitDisabled: !submitValid
    })
  },
  handleChangeText(e) {         // separate handler for each field
    let textValid = e.target.value ? true : false;        // basic text validation
    let submitValid = this.state.emailValid && textvalid   // validate total form
    this.setState({
      text: '',
      textValid: textValid, 
      submitDisabled: !submitValid
    })
  },
  render() {
    return <div>
      <input name="email" value={this.state.email} onChange={this.handleChangeEmail}/>
      <input name="text" value={this.state.text} onChange={this.handleChangeText}/>
      <button type="button" disabled={this.state.submitDisabled}>Button</button>
    </div>
  }
})

在更复杂的设置中,您可能希望将每个输入字段放在单独的组件中。并使代码更干燥(注意更改处理程序中的重复)。
还有各种反应形式的解决方案,比如here

【讨论】:

    【解决方案2】:

    我会在这里采取一些不同的方式......

    我不会在每个 onChange 处理程序中设置 submitDisabled,而是挂钩到生命周期方法以监听更改。
    确切地说是componentWillUpdate(nextProps, nextState)。在每次更改组件之前调用此方法 - 道具更改或状态更改。在这里,您可以验证您的表单数据并设置您需要的标志 - 所有这些都在一个地方。
    代码示例:

    componentWillUpdate(nextProps, nextState) {
      nextState.invalidData = !(nextState.email && nextState.password);
    },
    

    完整的工作小提琴https://jsfiddle.net/4emdsb28/

    【讨论】:

    • 不错的设置!您可能也指描述中的componentWillUpdate()。 (componentWillMount() 不接受任何参数)并且您可能需要另一个生命周期事件来进行初始验证。
    【解决方案3】:

    当且仅当我的输入元素的所有状态均为true 的所有输入字段都已填充时,我将通过仅渲染普通按钮元素来做到这一点。否则,它将呈现一个禁用的按钮。

    下面是一个结合 useState 钩子并使用 if 语句创建组件 SubmitButton 的示例。

    import React, { useState } from 'react';
    
    export function App() {
      const [firstname, setFirstname] = useState('');
      const [lastname, setLastname] = useState('');
      const [email, setEmail] = useState('');
        
      function SubmitButton(){
        if (firstname && lastname && email){
          return <button type="button">Button</button>
        } else {
          return <button type="button" disabled>Button</button>
        };
      };
    
      return (
        <div>
          <input value={email} onChange={ e => setEmail(e.target.value)}/>
          <input value={firstname} onChange={ e => setFirstname(e.target.value)}/>
          <input value={lastname} onChange={ e => setLastname(e.target.value)}/>
          <SubmitButton/>
        </div>
      );
    };
    

    【讨论】:

      【解决方案4】:

      这可能会有所帮助。 (学分 - https://goshakkk.name/form-recipe-disable-submit-button-react/

      import React from "react";
      import ReactDOM from "react-dom";
      
      class SignUpForm extends React.Component {
        constructor() {
          super();
          this.state = {
            email: "",
            password: ""
          };
        }
      
        handleEmailChange = evt => {
          this.setState({ email: evt.target.value });
        };
      
        handlePasswordChange = evt => {
          this.setState({ password: evt.target.value });
        };
      
        handleSubmit = () => {
          const { email, password } = this.state;
          alert(`Signed up with email: ${email} password: ${password}`);
        };
      
        render() {
          const { email, password } = this.state;
          const isEnabled = email.length > 0 && password.length > 0;
          return (
            <form onSubmit={this.handleSubmit}>
              <input
                type="text"
                placeholder="Enter email"
                value={this.state.email}
                onChange={this.handleEmailChange}
              />
              <input
                type="password"
                placeholder="Enter password"
                value={this.state.password}
                onChange={this.handlePasswordChange}
              />
              <button disabled={!isEnabled}>Sign up</button>
            </form>
          );
        }
      }
      
      const rootElement = document.getElementById("root");
      ReactDOM.render(<SignUpForm />, rootElement);
      

      【讨论】:

        【解决方案5】:
          export default function SignUpForm() {
        
            const [firstName, onChangeFirstName] = useState("");
            const [lastName, onChangeLastName] = useState("");
            const [phoneNumber, onChangePhoneNumber] = useState("");
        
            const areAllFieldsFilled = (firstName != "") && (lastName != "") && (phoneNumber != "")
        
            return (
              <Button
                title="SUBMIT"
                disabled={!areAllFieldsFilled}
                onPress={() => {
                  signIn()
                }
                }
              />
            )
            }
        

        与 Shafie Mukhre 的方法类似!

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2013-05-21
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多