DEV Community

Muhammad Yusuf
Muhammad Yusuf

Posted on

Handling multiple checkboxes in react

Let's say we want to have input for our favorite foods and we want to show it on the page.

First, we should prepare two variables, one for the food list, and another for a list of the selected food which is empty by default.

this.state = {
  foods: [
    {
      id: 1,
      name: '🍕'
    },
    {
      id: 2,
      name: '🍙'
    },
    {
      id: 3,
      name: '🍰'
    },
  ],
  selected: [],
}
Enter fullscreen mode Exit fullscreen mode

Now we make the form and show the selected state.

<form>
  <p>
    { JSON.stringify(this.state.selected) }
  </p>
  <p>Foods</p>
  {
    this.state.foods.map(item => {
      return (
        <label key={ item.id }>
          <input type="checkbox"></input>
          <span>{ item.name }</span>
        </label>
      )
    })
  }
</form>
Enter fullscreen mode Exit fullscreen mode

For checkbox input, we need to add selected and the usual onChange attributes.

<input type="checkbox"
  onChange={ () => this.onChange(item.id) }
  selected={ this.state.selected.includes(item.id) }
  ></input>
Enter fullscreen mode Exit fullscreen mode

The selected attribute accepts a boolean value that specifies if the input should be 'pre-selected' (checked) or not. And the onChange attribute will be triggered each time the input is checked and unchecked.

So because of this behavior, we have to put a function on the onChange attribute.

onChange(id) {
  let selected = this.state.selected
  let find = selected.indexOf(id)

  if(find > -1) {
    selected.splice(find, 1)
  } else {
    selected.push(id)
  }

  this.setState({ selected })
}
Enter fullscreen mode Exit fullscreen mode

find is a variable that checks whether the checked item is in the selected array or not. find > -1 means that the item exists in the selected variable and it is checked so we want to remove it from the selected list while find == -1 means the opposite. The item doesn't exist in the selected array so we want to add it to the array.

Now it should look like this

React Checkboxes

Beyond IDs

If you want to keep the whole object (not only the id), we can change the way we find the index and push the item to the selected array

onChange(id) {
  let selected = this.state.selected
  // instead of using indexOf, we can use findIndex to look through array of objects
  let find = selected.findIndex(item => item.id === id)

  if(find > -1) {
    selected.splice(find, 1)
  } else {
    // We can use find to get the item based on its id
    selected.push(this.state.foods.find(item => item.id === id))
  }

  this.setState({ selected })
}
Enter fullscreen mode Exit fullscreen mode

Now it should look like this

React Checkboxes

Sorting

And finally, basically the selected array has no specific order so if you want to keep the order you can add some sorting method before we use the setState.

// sort by id in ascending order
selected.sort((a, b) => a.id - b.id)
Enter fullscreen mode Exit fullscreen mode

Top comments (2)

Collapse
 
vanpariyar profile image
Ronak J Vanpariya

Hey Thank you So Much,

I got inspiration for the WordPress Gutenberg block....

Collapse
 
mhmmdysf profile image
Muhammad Yusuf

You're welcome!