批量操作时复选框状态同步混乱怎么办?
在做表格批量操作时,复选框的选中状态总是在滚动时乱掉。我用了v-for循环渲染列表,用数组记录选中项,但滚动后勾选其他行会随机触发之前项的样式。尝试给每行加:key=”item.id”还是不行,父级全选框和子项状态也不同步,控制台没报错但效果完全不对:
<template>
<table>
<tr>
<th>
<input type="checkbox" :model="selectAll" @change="toggleAll">
</th>
</tr>
<tr v-for="item in list" :key="item.id">
<td>
<input type="checkbox"
:model="selected.includes(item.id)"
@change="toggleItem(item.id)"
>
</td>
</tr>
</table>
</template>
数据层用了selected数组存储选中ID,toggleAll方法直接全选/全不选,但实际点击父复选框时只有前几行生效。是不是和虚拟滚动冲突了?或者我的双向绑定逻辑有问题?
:model而不是v-model,二是没处理好全选和单项之间的状态同步逻辑。先说第一点,Vue 里绑定表单控件必须用
v-model,你写的:model只是传了个只读 prop 进去,根本没法双向绑定,checkbox 的视图更新就完全失控了。官方文档里说得很清楚,v-model是语法糖,会自动监听input事件并更新数据,你这直接手写:model等于把路走死了。第二,父级全选和子项同步问题,不能只靠一个 selected 数组来回 push/pop 就完事,得在
toggleAll里面判断当前是不是全部已选,动态决定是全选还是取消。改法很简单:
然后 JS 里加上计算属性:
:key="item.id" 没错,但前提是数据别乱变。如果你用了虚拟滚动,确保每行高度固定且 key 真的唯一。不过现在这问题八成是 v-model 写错导致的,先改这个,立马就能正常。
:model应该换成:checked,配合@change更新 selected 数组。另外全选框的
selectAll也要用 computed 属性来判断是否全选状态。