Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

React Checkbox Does Not Update

I want to update an array each time a checkbox is toggled to true. With this current code, if I click on a checkbox it will log that it's false. Even though I have just updated the state. Does setState just take some time, like an API call? That doesn't make sense to me.

import React, {Component} from 'react';

class Person extends Component {

  constructor(props) {
    super(props);

    this.state = {
      boxIsChecked: false
    };

    this.checkboxToggle = this.checkboxToggle.bind(this);
  }

  checkboxToggle() {
    // state is updated first
    this.setState({ boxIsChecked: !this.state.boxIsChecked });
    console.log("boxIsChecked: " + this.state.boxIsChecked);
    if (this.state.boxIsChecked === false) {
      console.log("box is false. should do nothing.");
    }
    else if (this.state.boxIsChecked === true) {
      console.log("box is true. should be added.");
      this.props.setForDelete(this.props.person._id);
    }

  }

    render() {
        return (
          <div>
            <input type="checkbox" name="person" checked={this.state.boxIsChecked} onClick={this.checkboxToggle} />
            {this.props.person.name} ({this.props.person.age})
          </div>
        );
    }
}

export default Person;

I have tried onChange instead of onClick. I feel like I'm already following advice I've read about for the basic component formulation from here and here. Is the fact I'm using Redux for other values affecting anything? Is there a way to just read what the checkbox is, instead of trying to control it? (The checkbox itself works fine and the DOM updates wether it's checked or not correctly.)

like image 448
Gabriel Kunkel Avatar asked Apr 18 '17 15:04

Gabriel Kunkel


People also ask

How to change state of checkbox in React?

Using setState with React Checkbox onChange Toggle the text of a paragraph with the checkbox using the 'useState' hook. */ import React, {useState} from 'react'; function Checkbox() { const [checked, setChecked] = useState(false); const handleChange = () => { setChecked(! checked); }; return ( <div> <p> {checked ?

How do you keep checkbox checked even after page refresh in React?

select to checked like this checked={d.select is === true box will be checked) it gets saved in localStorage as select:true but doesn't display checked on refresh.

How do you check if checkbox is checked React?

Use the target. checked property on the event object to check if a checkbox is checked in React, e.g. if (event. target. checked) {} .


Video Answer


2 Answers

I know that this thread is answered but i also have a solution for this, you see the checkbox didn't update with the provided value of setState, i don't know the exact reason for this problem but here is a solution.

<input
  key={Math.random()}
  type="checkbox"
  name="insurance"
  defaultChecked={data.insurance}
 />

by giving the key value of random the checkbox gets re-rendered and the value of the checkbox is updated, this worked for me. Also i am using hooks, but it should work for class based implementation to.

reference: https://www.reddit.com/r/reactjs/comments/8unyps/am_i_doing_stupid_or_is_this_a_bug_checkbox_not/

like image 194
Nabeel Hussain Shah Avatar answered Sep 23 '22 15:09

Nabeel Hussain Shah


setState() is indeed not reflected right away:

Read here in the docs:

setState() enqueues changes to the component state and tells React that this component and its children need to be re-rendered with the updated state. This is the primary method you use to update the user interface in response to event handlers and server responses.

Think of setState() as a request rather than an immediate command to update the component. For better perceived performance, React may delay it, and then update several components in a single pass. React does not guarantee that the state changes are applied immediately.

setState() does not always immediately update the component. It may batch or defer the update until later. This makes reading this.state right after calling setState() a potential pitfall. Instead, use componentDidUpdate or a setState callback (setState(updater, callback)), either of which are guaranteed to fire after the update has been applied. If you need to set the state based on the previous state, read about the updater argument below.

setState() will always lead to a re-render unless shouldComponentUpdate() returns false. If mutable objects are being used and conditional rendering logic cannot be implemented in shouldComponentUpdate(), calling setState() only when the new state differs from the previous state will avoid unnecessary re-renders.

and here some experiments

So it might be better to catch the event and check it, and not depend on the this.setState() Something like that:

handleChange: function (event)  {
   //you code
    if (event.target.checked) {
      console.log("box is true. should be added.");
      this.props.setForDelete(this.props.person._id);
    }

  }

and

    render() {
            return (
              <div>
                <input type="checkbox" name="person" checked={this.state.boxIsChecked} 
                   onChange={this.handleChange.bind(this)}/>
                {this.props.person.name} ({this.props.person.age})
              </div>
            );
        }
like image 28
Battle_Slug Avatar answered Sep 23 '22 15:09

Battle_Slug