Young L.
Young L.

Reputation: 1042

Why is my component state updating only once

i think it is not soo big problem but i don't understand why is it happening like that. I have Component structure like this: Parrent->Child1->Child2

In parrent i have method to setState of count checked checkbox in Child2. It looks like this:

  setKnowledgeCountState(value) {
        this.setState({countChooseKnowledge: this.state.countChooseKnowledge + value});
    }

This method i am passing throught Child1 to Child2. In Child2 i am using this method like this:


    componentDidUpdate(prevProps, prevState, snapshot) {
        if(this.props.knowledge.isChecked !== prevProps.knowledge.isChecked){
        console.log(prevProps.knowledge.isChecked);
        console.log("---");
        console.log(this.props.knowledge.isChecked);
        this.updateCountOfSelected(this.props.knowledge.isChecked);
        }
    }

  updateCountOfSelected(isChecked){
        if(isChecked)
            this.props.setKnowledgeCountState(1);
        else
            this.props.setKnowledgeCountState(-1);
    }

This works as i want separatly, when i am clicking on checkboxes one by one. But in Child1 i have option to select all checkboxes. I am doing it like this:

  toggleCheckBox(event) {
        event.stopPropagation();
        const themePartCopy = cloneDeep(this.props.part);
        themePartCopy.isChecked = !themePartCopy.isChecked;
        themePartCopy.isOpen = themePartCopy.isChecked;
        themePartCopy.knowledges.forEach((knowledge) => {
            knowledge.isChecked = themePartCopy.isChecked;
        });

        this.props.changePart(themePartCopy);
    }

Now the problem is, when i select all checkboxes (in my case there are 4xChild2 under Child1) the state in Parrent is updating only once. So count at the end is 1. It should be 4.I checked console.logs() in child2 and looks like the method updateCountofsELECTED() is called 4x. Why then tha count is only 1 and not 4? Thx for your help

Upvotes: 1

Views: 376

Answers (2)

Khabir
Khabir

Reputation: 5862

React Docs recommends using function with prevState inside of setState

// Wrong
this.setState({
  counter: this.state.counter + this.props.increment,
});

// es6 way
// Correct
this.setState((prevState, props) => ({
  counter: prevState.counter + props.increment
}));

// es5 way
// Correct
this.setState(function(prevState, props) {
  return {
    counter: prevState.counter + props.increment
  };
});

Source

Upvotes: 1

Jagrati
Jagrati

Reputation: 12222

use prevstate while updating the state value. React setState is an asynchronous update and does batch updating. Using prevState makes sure that the state value is updated before calculating new state value.

  setKnowledgeCountState = value => {
    this.setState(prevState => {
      return {
        countChooseKnowledge: prevState.countChooseKnowledge + value
      };
    });
  };

DOCUMENTATION would help understand the concept

Upvotes: 3

Related Questions