在 ReactJS 中,我如何跟踪一组复选框的状态?
In ReactJS how do I keep track of the state of a group of checkboxes?
我正在尝试跟踪在我所在的州选中了哪些复选框(您可以选中多个复选框)。我希望能够选中和取消选中这些框,并跟踪选中的框的 ID。稍后我会用这些值做一些事情。这是我目前所拥有的:
import React, { Component } from 'react'
import './App.css'
import CheckBox from './CheckBox'
class App extends Component {
constructor(props) {
super(props)
this.state = {
fruits: [
{id: 1, value: "banana", isChecked: false},
{id: 2, value: "apple", isChecked: false},
{id: 3, value: "mango", isChecked: false},
{id: 4, value: "grape", isChecked: false}
],
fruitIds: []
}
}
handleCheckChildElement = (e) => {
const index = this.state.fruits.findIndex((fruit) => fruit.value === e.target.value),
fruits = [...this.state.fruits],
checkedOrNot = e.target.checked === true ? true : false;
fruits[index] = {id: fruits[index].id, value: fruits[index].value, isChecked: checkedOrNot};
this.setState({fruits});
this.updateCheckedIds(e);
}
updateCheckedIds = (e) => {
const fruitIds = [...this.state.fruitIds],
updatedFruitIds= fruitIds.concat(e.target.id);
this.setState({updatedFruitIds});
}
render() {
const { fruits } = this.state;
if (!fruits) return;
const fruitOptions = fruits.map((fruit, index) => {
return (
<CheckBox key={index}
handleCheckChildElement={this.handleCheckChildElement}
isChecked={fruit.isChecked}
id={fruit.id}
value={fruit.value}
/>
);
})
return (
<div className="App">
<h1>Choose one or more fruits</h1>
<ul>
{ fruitOptions }
</ul>
</div>
);
}
}
export default App
所以基本上我可以选中和取消选中这些框,但我似乎无法更新和存储 fruitId。这也是我的复选框组件:
import React from 'react'
export const CheckBox = props => {
return (
<li>
<input key={props.id}
onChange={props.handleCheckChildElement}
type="checkbox"
id={props.id}
checked={props.isChecked}
value={props.value}
/>
{props.value}
</li>
)
}
export default CheckBox
此外,如果您有比我这样做更简洁的方法来做到这一点,我很乐意看到它。
如果我要接近它,我会这样做。我将创建一个一维数组,当单击(选中)一个水果时,它保存水果的 id,我会将它的 id 添加到数组中,当它第二次单击时,我检查数组是否已经具有我将其删除的 id。那么 id 在数组中的存在将意味着水果被检查,否则它没有被检查所以我会做类似下面的事情
this.state={
fruitsIds: []
}
handleCheckChildElement=(id) => {
//the logic here is to remove the id if its already exist else add it. and set it back to state
const fruitsIds = this.state.fruitsIds;
this.setState({fruitsIds: fruitsIds.contains(id) ? fruitsIds.filter(i => i != id) : [...fruitsIds, id] })
}
然后我将复选框呈现为
<CheckBox key={index}
handleCheckChildElement={this.handleCheckChildElement}
isChecked = { this.state.fruitsIds.contains(fruit.id)}
id={fruit.id}
/>
这是因为您始终可以使用 id 获取水果的所有其他属性,因此绝对不需要再次存储它们。
那么复选框组件应该如下
export const CheckBox = props => {
return (
<li>
<input key={props.id}
onChange={() => props.handleCheckChildElement(props.id)}
type="checkbox"
id={props.id}
checked={props.isChecked}
value={props.value}
/>
{props.value}
</li>
)
}
您没有更新 ID 的原因是:
- 您正在尝试将非数组元素连接到数组。
concat
用于连接两个或多个数组。
updatedFruitIds = fruitIds.concat(e.target.id);
- 您没有更新实际的
fruitIds
状态字段。我不知道你为什么要使用 "updatedFruitIds" 这个变量,但由于上述错误,它总是会导致单个元素数组。
this.setState({ updatedFruitIds });
updateCheckedIds = e => {
const fruitIds = [...this.state.fruitIds],
updatedFruitIds = fruitIds.concat([e.target.id]);
this.setState({ fruitIds: updatedFruitIds });
};
或
updateCheckedIds = e => {
const fruitIds = [...this.state.fruitIds, e.target.id],
this.setState({ fruitIds });
};
我正在尝试跟踪在我所在的州选中了哪些复选框(您可以选中多个复选框)。我希望能够选中和取消选中这些框,并跟踪选中的框的 ID。稍后我会用这些值做一些事情。这是我目前所拥有的:
import React, { Component } from 'react'
import './App.css'
import CheckBox from './CheckBox'
class App extends Component {
constructor(props) {
super(props)
this.state = {
fruits: [
{id: 1, value: "banana", isChecked: false},
{id: 2, value: "apple", isChecked: false},
{id: 3, value: "mango", isChecked: false},
{id: 4, value: "grape", isChecked: false}
],
fruitIds: []
}
}
handleCheckChildElement = (e) => {
const index = this.state.fruits.findIndex((fruit) => fruit.value === e.target.value),
fruits = [...this.state.fruits],
checkedOrNot = e.target.checked === true ? true : false;
fruits[index] = {id: fruits[index].id, value: fruits[index].value, isChecked: checkedOrNot};
this.setState({fruits});
this.updateCheckedIds(e);
}
updateCheckedIds = (e) => {
const fruitIds = [...this.state.fruitIds],
updatedFruitIds= fruitIds.concat(e.target.id);
this.setState({updatedFruitIds});
}
render() {
const { fruits } = this.state;
if (!fruits) return;
const fruitOptions = fruits.map((fruit, index) => {
return (
<CheckBox key={index}
handleCheckChildElement={this.handleCheckChildElement}
isChecked={fruit.isChecked}
id={fruit.id}
value={fruit.value}
/>
);
})
return (
<div className="App">
<h1>Choose one or more fruits</h1>
<ul>
{ fruitOptions }
</ul>
</div>
);
}
}
export default App
所以基本上我可以选中和取消选中这些框,但我似乎无法更新和存储 fruitId。这也是我的复选框组件:
import React from 'react'
export const CheckBox = props => {
return (
<li>
<input key={props.id}
onChange={props.handleCheckChildElement}
type="checkbox"
id={props.id}
checked={props.isChecked}
value={props.value}
/>
{props.value}
</li>
)
}
export default CheckBox
此外,如果您有比我这样做更简洁的方法来做到这一点,我很乐意看到它。
如果我要接近它,我会这样做。我将创建一个一维数组,当单击(选中)一个水果时,它保存水果的 id,我会将它的 id 添加到数组中,当它第二次单击时,我检查数组是否已经具有我将其删除的 id。那么 id 在数组中的存在将意味着水果被检查,否则它没有被检查所以我会做类似下面的事情
this.state={
fruitsIds: []
}
handleCheckChildElement=(id) => {
//the logic here is to remove the id if its already exist else add it. and set it back to state
const fruitsIds = this.state.fruitsIds;
this.setState({fruitsIds: fruitsIds.contains(id) ? fruitsIds.filter(i => i != id) : [...fruitsIds, id] })
}
然后我将复选框呈现为
<CheckBox key={index}
handleCheckChildElement={this.handleCheckChildElement}
isChecked = { this.state.fruitsIds.contains(fruit.id)}
id={fruit.id}
/>
这是因为您始终可以使用 id 获取水果的所有其他属性,因此绝对不需要再次存储它们。 那么复选框组件应该如下
export const CheckBox = props => {
return (
<li>
<input key={props.id}
onChange={() => props.handleCheckChildElement(props.id)}
type="checkbox"
id={props.id}
checked={props.isChecked}
value={props.value}
/>
{props.value}
</li>
)
}
您没有更新 ID 的原因是:
- 您正在尝试将非数组元素连接到数组。
concat
用于连接两个或多个数组。updatedFruitIds = fruitIds.concat(e.target.id);
- 您没有更新实际的
fruitIds
状态字段。我不知道你为什么要使用 "updatedFruitIds" 这个变量,但由于上述错误,它总是会导致单个元素数组。this.setState({ updatedFruitIds });
updateCheckedIds = e => {
const fruitIds = [...this.state.fruitIds],
updatedFruitIds = fruitIds.concat([e.target.id]);
this.setState({ fruitIds: updatedFruitIds });
};
或
updateCheckedIds = e => {
const fruitIds = [...this.state.fruitIds, e.target.id],
this.setState({ fruitIds });
};