React 中的受控复选框
Controlled checkbox in React
我正在尝试将所有选中的复选框放入状态数组中。我可以将值添加到数组,但是当我取消选中该框时我无法删除该值。我尝试过使用拼接和按索引删除,也尝试过通过过滤器删除。它可以工作,但工作缓慢且不正确。例如,我可以取消选中所有复选框,并且一个值保留在状态中。请检查我做错了什么
这是一个沙盒 link 和下面的代码
const [state, setState] = useState({
address: [],
})
const checkboxChange = (e) => {
const { name, checked } = e.target
if (checked === true) {
setState((prevState) => ({
...prevState,
address: [...prevState.address, name],
}))
}
if (checked === false) {
setState((prevState) => ({
...prevState,
address: [...prevState.address].filter((it) => it.id !== it.id),
}))
}
}
{list.map((it, index) => (
<div key={it.id}>
<label>
<input
className="mr-2"
checked={state.address.index}
key={it.id}
name={it.id}
defaultValue="false"
onChange={checkboxChange}
type="checkbox"
/>
{it.name}
</label>
</div>
))}
问题
您正在比较 it.id !== it.id
,它将总是 评估为 false。
解决方案
state.address
是一个 id 数组,而不是具有 id
属性 的对象,并且您想将每个对象与 name
中的输入进行比较=16=]事件对象。
- 只过滤
prevState.address
- 比较
el !== name
代码
const checkboxChange = (e) => {
const { name, checked } = e.target;
if (checked) {
setState((prevState) => ({
...prevState,
address: [...prevState.address, name],
}))
} else {
setState((prevState) => ({
...prevState,
address: prevState.address.filter((el) => el !== name),
}))
}
}
受控输入
如果你真的想控制你的输入,那么我建议:
- 将选中的值存储在映射中
- 只需切换
onChange
事件 中选中的值
- 使用
value
属性与输入的 defaultValue
属性
代码
const App = (props) => {
const [state, setState] = useState({
address: {}, // <-- object map
})
useEffect(() => {
console.log(state)
}, [state])
const checkboxChange = (e) => {
const { name } = e.target
setState((prevState) => ({
...prevState,
address: {
...prevState.address,
[name]: !prevState.address[name], // <-- toggle state
},
}))
}
return (
<div>
{list.map((it, index) => (
<div key={it.id}>
<label>
<input
className="mr-2"
checked={state.address.index}
key={it.id}
name={it.id}
value={state.address[it.id]} // <-- set from checked state
onChange={checkboxChange}
type="checkbox"
/>
{it.name}
</label>
</div>
))}
</div>
)
}
我正在尝试将所有选中的复选框放入状态数组中。我可以将值添加到数组,但是当我取消选中该框时我无法删除该值。我尝试过使用拼接和按索引删除,也尝试过通过过滤器删除。它可以工作,但工作缓慢且不正确。例如,我可以取消选中所有复选框,并且一个值保留在状态中。请检查我做错了什么 这是一个沙盒 link 和下面的代码
const [state, setState] = useState({
address: [],
})
const checkboxChange = (e) => {
const { name, checked } = e.target
if (checked === true) {
setState((prevState) => ({
...prevState,
address: [...prevState.address, name],
}))
}
if (checked === false) {
setState((prevState) => ({
...prevState,
address: [...prevState.address].filter((it) => it.id !== it.id),
}))
}
}
{list.map((it, index) => (
<div key={it.id}>
<label>
<input
className="mr-2"
checked={state.address.index}
key={it.id}
name={it.id}
defaultValue="false"
onChange={checkboxChange}
type="checkbox"
/>
{it.name}
</label>
</div>
))}
问题
您正在比较 it.id !== it.id
,它将总是 评估为 false。
解决方案
state.address
是一个 id 数组,而不是具有 id
属性 的对象,并且您想将每个对象与 name
中的输入进行比较=16=]事件对象。
- 只过滤
prevState.address
- 比较
el !== name
代码
const checkboxChange = (e) => {
const { name, checked } = e.target;
if (checked) {
setState((prevState) => ({
...prevState,
address: [...prevState.address, name],
}))
} else {
setState((prevState) => ({
...prevState,
address: prevState.address.filter((el) => el !== name),
}))
}
}
受控输入
如果你真的想控制你的输入,那么我建议:
- 将选中的值存储在映射中
- 只需切换
onChange
事件 中选中的值
- 使用
value
属性与输入的defaultValue
属性
代码
const App = (props) => {
const [state, setState] = useState({
address: {}, // <-- object map
})
useEffect(() => {
console.log(state)
}, [state])
const checkboxChange = (e) => {
const { name } = e.target
setState((prevState) => ({
...prevState,
address: {
...prevState.address,
[name]: !prevState.address[name], // <-- toggle state
},
}))
}
return (
<div>
{list.map((it, index) => (
<div key={it.id}>
<label>
<input
className="mr-2"
checked={state.address.index}
key={it.id}
name={it.id}
value={state.address[it.id]} // <-- set from checked state
onChange={checkboxChange}
type="checkbox"
/>
{it.name}
</label>
</div>
))}
</div>
)
}