【问题标题】:Clearing forms in React after submission提交后在 React 中清除表单
【发布时间】:2019-01-18 16:29:25
【问题描述】:

我正在尝试在使用 Axios 创建表单提交后清除表单数据。消息顺利通过,响应记录到页面,但每个文本字段中的数据在提交后仍保留在页面上。

我尝试添加一个resetForm 函数,将表单设置回原来的空白状态,但这不起作用。

import React, { Component } from 'react';
import { Grid, Cell, Textfield, Button } from 'react-mdl';
import './Contact.css';
import axios from "axios";

class Contact extends Component {
    constructor(props){
        super(props);
        this.state = {fullName: "", email: "", message: ""};
    }  

    resetForm = () => {
        this.baseState = this.state
        this.setState(this.baseState)
    }

    handleForm = e => {
        axios.post(
        "https://formcarry.com/s/axiosID", 
        this.state, 
        {headers: {"Accept": "application/json"}}
        )
        .then(function (response) {
            let successMessage = document.querySelector('.success-message');
            successMessage.innerHTML = JSON.stringify(response.data.title);
        })
        .catch(function (error) {
            let successMessage = document.querySelector('.success-message');
            successMessage.innerHTML = JSON.stringify(error);
        });

        e.preventDefault();
    }
    handleFields = e => this.setState({ [e.target.name]: 'e.target.value' });

        render() {
            return (
                    <Grid>
                        <Cell col={6}>
                            <h2>Contact Me</h2>
                            <hr/>
                            <div style={{ width: '100%' }} className="contact-list">
                                <form onSubmit={this.handleForm}>
                                    <Cell col={12}>
                                        <Textfield type="text" id="fullName" name="fullName" className="full-name"
                                        onChange={this.handleFields}
                                        label="Full name"
                                        floatingLabel
                                        style={{width: '200px'}}
                                        />
                                    </Cell>
                                    <Cell col={12}>
                                    {/* Textfield with floating label */}
                                        <Textfield type="email" id="email" name="email" className="email-address"
                                        onChange={this.handleFields}
                                        label="Email address"
                                        floatingLabel
                                        style={{width: '200px'}}
                                        />
                                    </Cell>
                                    <Cell col={12}>
                                        {/* Floating Multiline Textfield */}
                                        <Textfield name="message" id="message" className="text-body"
                                        onChange={this.handleFields}
                                        label="Your message..."
                                        rows={10}
                                        style={{width: '400px'}}
                                        />
                                    </Cell>
                                    <Button raised accent ripple type="submit" onClick={this.resetForm}>Send</Button>
                                    <div className="success-message">
                                        <label></label>
                                    </div>
                                </form>
                            </div>
                        </Cell>
                    </Grid>
            )
        }
    }


export default Contact;

我真正想要的只是在我提交表单后清除文本字段fullName, email and message,但数据仍保留在页面上。

【问题讨论】:

    标签: reactjs forms state


    【解决方案1】:

    您不需要 resetForm 函数(完全摆脱它),只需像这样在 handleForm 中设置您的状态:

    更新:您还需要将 value 属性添加到每个输入以使其成为受控输入,如下所示:

    import React, { Component } from 'react';
    import { Grid, Cell, Textfield, Button } from 'react-mdl';
    import './Contact.css';
    import axios from "axios";
    
    class Contact extends Component {
      constructor(props) {
        super(props);
        this.state = { fullName: "", email: "", message: "" };
      }
    
      handleForm = e => {
        axios.post(
          "https://formcarry.com/s/axiosID",
          this.state,
          { headers: { "Accept": "application/json" } }
        )
          .then(function (response) {
            let successMessage = document.querySelector('.success-message');
            successMessage.innerHTML = JSON.stringify(response.data.title);
          })
          .catch(function (error) {
            let successMessage = document.querySelector('.success-message');
            successMessage.innerHTML = JSON.stringify(error);
          });
    
        e.preventDefault();
        this.setState({fullName: '', email: '', message: ''}) // <= here
      }
      handleFields = e => this.setState({ [e.target.name]: e.target.value }); 
    
      render() {
        return (
          <Grid>
            <Cell col={6}>
              <h2>Contact Me</h2>
              <hr />
              <div style={{ width: '100%' }} className="contact-list">
                <form onSubmit={this.handleForm}>
                  <Cell col={12}>
                    <Textfield type="text" id="fullName" name="fullName" className="full-name"
                      onChange={this.handleFields}
                      value={this.state.fullName} // <= here
                      label="Full name"
                      floatingLabel
                      style={{ width: '200px' }}
                    />
                  </Cell>
                  <Cell col={12}>
                    {/* Textfield with floating label */}
                    <Textfield type="email" id="email" name="email" className="email-address"
                      onChange={this.handleFields}
                      value={this.state.email} // <= here
                      label="Email address"
                      floatingLabel
                      style={{ width: '200px' }}
                    />
                  </Cell>
                  <Cell col={12}>
                    {/* Floating Multiline Textfield */}
                    <Textfield name="message" id="message" className="text-body"
                      onChange={this.handleFields}
                      value={this.state.message} // <= here
                      label="Your message..."
                      rows={10}
                      style={{ width: '400px' }}
                    />
                  </Cell>
                  <Button raised accent ripple type="submit">Send</Button>
                  <div className="success-message">
                    <label></label>
                  </div>
                </form>
              </div>
            </Cell>
          </Grid>
        )
      }
    }
    
    
    export default Contact;
    

    附带说明:查看 React refs 以获取 dom 元素...在此处阅读更多内容:https://reactjs.org/docs/refs-and-the-dom.html

    【讨论】:

    • 感谢 SakoBu。同样的问题。它没有抛出任何错误,但即使在尝试了您的方法后它仍然无法清除。
    • @Ang - 哦,那也是因为它不是受控输入...我会更新我的答案...
    • 我尝试了您更新的代码,但是每当我在任何文本框中输入时,它都会显示为e.target.value,我无法更改这些值。
    • @Ang... 在你的 handleFields 中去掉 'e.target.value' 的引号,而不是你得到字符串的实际值
    【解决方案2】:

    提交后需要清除状态。调用 setState 后,将使用我们设置的空值再次调用反应渲染,希望这会有所帮助

     .then(function (response) {
            let successMessage = document.querySelector('.success-message');
             // here clear the state,
             this.setState({
               fullName: '',
               email: '',
               message: '',
             });
            successMessage.innerHTML = JSON.stringify(response.data.title);
        })
    

    【讨论】:

      【解决方案3】:

      你可以这样做

       resetForm = () => {
          this.setState({fullName: "", email: "", message: ""});
      }
      

      这会将这些值重置为空。

      【讨论】:

      • 谢谢大家。我尝试了所有这些方法,但似乎都不起作用。
      • @JackJack 你找到解决办法了吗?
      【解决方案4】:

      当您更改表单输入时,您的状态会更新。

      handleFields = e => this.setState({ [e.target.name]: 'e.target.value' });
      

      状态不是静态对象。

      您必须手动更新字段值。

      resetForm = () => {
          this.setState({fullName: "", email: "", message: ""})
      }
      

      【讨论】:

        【解决方案5】:

        如果表单字段的值已由状态值分配,​​则从显示的代码中看不到。 (例如fullName field: value = this.state.fullName)。如果未分配值,则不会重新呈现表单,即使 setState 已正确定义。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2021-09-24
          • 2018-03-14
          • 1970-01-01
          • 1970-01-01
          • 2023-03-22
          • 2020-07-17
          • 2013-01-25
          • 1970-01-01
          相关资源
          最近更新 更多