Реагировать состояние компонента сбрасывается на значение по умолчанию - PullRequest
0 голосов
/ 30 марта 2020

Я пытаюсь отследить форму в this.state с обработчиками событий на входах, но по какой-то причине this.state сбрасывается обратно в состояние по умолчанию, когда обработчик событий пытается обновить его. Это пример того, как выглядит Компонент.

class ExampleReport extends React.Component {
    constructor(props) {
        super(props)
        this.state = {
            reportDetails: null,
            report: this.props.report,
            form: {}
        }
        this.textInputHandler = this.textInputHandler.bind(this)
    }

    textInputHandler(e) {
        var reportForm = this.state.form;
        var target = e.target;
        var name = target.className;
        var value = target.value;
        reportForm[name] = value;
        this.setState({ form: reportForm })
    }

    render(){
      return(
        <form>
          <input className="example" type="text" onChange={(e) => {this.textInputHandler(e)}} />
        </form>
      )
    }
}

До вызова textInputHandler в this.state хранятся объект и массив, но после вызова setState они сбрасываются обратно по умолчанию в конструкторе. При последующих обновлениях текстовый ввод this.state.form сохраняется, но все остальное сбрасывается. Как я могу предотвратить это?

ОБНОВЛЕНИЕ

Попробовав некоторые из предложенных ниже решений, я вернулся и зарегистрировал this.state практически во всех возможных точках и обнаружил, что он сбрасывается даже до вызова setState() во входном обработчике.

Ответы [ 3 ]

0 голосов
/ 30 марта 2020

Один из способов решения этой проблемы будет выглядеть следующим образом: распространение reportForm в новом объекте

  textInputHandler(e) {
        var reportForm = this.state.form;
        var target = e.target;
        var name = target.className;
        var value = target.value;
        reportForm[name] = value;
        this.setState({ form: { ...reportForm } }) // <----------------------
    }

Однако вы можете использовать более декларативное решение, предоставленное Кириллом, но без ненужных изменений состояния

  textInputHandler(e) {
        const { className: name, value } = e.target;
        this.setState(prevState => { form: { ...prevState.form, [name]: value } }) // <----------------------
    }
0 голосов
/ 30 марта 2020

попробуйте изменить свой onChange на этот

onChange={this.textInputHandler}

, как, например, в документации по реактивному реагированию EX)

<input type="text" value={this.state.value} onChange={this.handleChange} />

, тогда распространяющие вещи не добавляют, e. warnDefault, потому что это работает только для отправки

Посмотрите на ответ Криля, у него есть все, что вам нужно, сравните его с вашим сверху, у вас много чего не хватает

0 голосов
/ 30 марта 2020

Вы забыли о входном значении и состоянии обновления по ref (сделать мутацию).

class ExampleReport extends React.Component {
    constructor(props) {
        super(props)
        this.state = {
            reportDetails: null,
            report: this.props.report,
            form: { example: '', },
        }

        this.textInputHandler = this.textInputHandler.bind(this)
    }

    textInputHandler(e) {
        const { target: { name, value } } = e;

        this.setState(prevState => ({
          ...prevState,
          form: {
            ...prevState.form,
            [name]: value,
          },
        }));
    }

    render() {
      const { form: { example } } = this.state;

      return (
        <form>
          <input
            className="example"
            type="text"
            name="example"
            value={example}
            onChange={this.textInputHandler}
          />
        </form>
      )
    }
}
...