HTML多选仅支持checkbox和select[multiple];checkbox需同name、唯value、包label;select[multiple]交互受限且兼容性差;JS获取需querySelectorAll+checked;全选需手动处理indeterminate状态。

HTML里没有叫“多项选择”的独立控件,真正能用的只有两种:一是 <input type="checkbox">,二是 <select multiple>。其他写法(比如 input[multiple] 或 select 不加 multiple)都无效,浏览器直接忽略。
用 <input type="checkbox"> 实现多选时 name 和 value 怎么设
name 必须相同,value 必须唯一且有意义——这是后端能收到数组、前端能准确读值的前提。
- name 相同(如
name="tag")才能让表单提交时聚合成多个同名参数,例如tag=js&tag=css&tag=html - value 不能留空或全写
"on",必须是可区分的标识,比如数据库 ID、语义化字符串(value="react"),别用1/2这类无上下文数字 - name 里别带空格或方括号(如
name="tags[]"),虽然某些后端框架认,但 JS 里读el.name会得到字面字符串,容易误判;且不符合 HTML 规范 - 所有 checkbox 都要包在
<label>里,否则移动端点击文字不触发,可访问性也差
用 <select multiple> 时用户操作和兼容性要注意什么
<select multiple> 是原生多选,但交互和样式限制极多,不是“点一下展开打钩”的下拉复选框。
- 用户必须按住 Ctrl(Windows)或 Cmd(macOS)再点选项,Shift 可连续选;纯鼠标点击默认只保留最后一项
- iOS Safari 完全忽略
multiple属性,点开会弹出单选原生 Picker;Android 各厂商行为也不统一 - CSS 几乎无法定制:伪元素不生效、appearance: none 失效、滚动条样式不可控、无法加勾选图标
- 如果需要搜索、展开收起、视觉反馈,必须放弃原生
<select>,改用<div>+<input type="checkbox">模拟
JS 获取选中值时为什么 querySelector 总只拿到一个
因为 querySelector 的设计目标就是找第一个匹配元素,而多选场景下你必然需要全部已勾选项。
立即学习“前端免费学习笔记(深入)”;
- 要读当前勾选的 checkbox,用
document.querySelectorAll('input[name="tag"]:checked')—— 加:checked过滤,返回静态 NodeList - 要操作全部 checkbox(比如全选),用
document.querySelectorAll('input[name="tag"]'),不加:checked - 别用
getElementsByName:返回的是实时 HTMLCollection,不支持forEach,动态插入新项后可能不更新 - 获取值的稳写法:
Array.from(document.querySelectorAll('input[name="tag"]:checked')).map(cb => cb.value)
全选/反选逻辑里最容易漏掉的 indeterminate 状态
当部分子项被勾选时,全选框应该显示为“横线”状态(即 indeterminate),但这不是自动的,必须手动设置。
- 先设
mainCheckbox.checked = false,再设mainCheckbox.indeterminate = true,顺序反了可能无效 -
indeterminate不触发change事件,所以监听click或单独处理更稳妥 - 子项变更后,得重新统计
document.querySelectorAll('input[name="tag"]:checked').length,再决定全选框的checked和indeterminate - 分页或搜索后 DOM 重排,必须重新绑定事件,否则新增项不会响应全选逻辑
真正麻烦的从来不是怎么写几个 checkbox,而是当表格支持分页、搜索、虚拟滚动甚至服务端排序时,DOM 顺序和数据顺序早已脱钩——这时候还靠 rows[i].dataset.id 或 cells[1].textContent 取值,基本等于随机返回。



















