验证码输入框不必用 type="text",推荐 type="tel" 并关闭 autocorrect 和 autocapitalize;禁用 type="number";应保留原生 input 可访问性;需添加 inputmode="numeric" 和 pattern="[0-9]*";粘贴需 js 清洗并分拆。

验证码输入框必须用 <input type="text"> 吗?
不是。用 <input type="tel"> 更合理——它能唤起数字键盘,减少用户切换输入法的麻烦,同时避免字母和符号干扰。但要注意:iOS Safari 对 type="tel" 的 autocorrect 和 autocapitalize 默认是开启的,可能意外修正数字,必须显式关闭:autocorrect="off" autocapitalize="none"。别用 type="number",它会触发浏览器自动增减按钮、小数点输入,且部分安卓机型提交时把 "0000" 变成 0(丢前导零)。
为什么不能只靠 CSS 隐藏原生输入框?
常见做法是用一个 <div> 模拟 4 个格子,再把真实 <code><input> 设为 opacity: 0 或 position: absolute; left: -9999px。问题在于:屏幕阅读器可能跳过它,导致视障用户无法聚焦;部分浏览器(如旧版微信内置浏览器)会忽略 aria-hidden="true",仍播报隐藏内容;更关键的是,当用户粘贴验证码时,原生 <input> 若未正确绑定 onpaste 事件,粘贴内容不会自动分拆到各格子。正确做法是保留原生 <input> 为可聚焦、可读、可交互元素,用 CSS 控制视觉呈现,而非“藏起来”。
inputmode="numeric" 和 pattern="[0-9]*" 要不要加?
要加,但作用不同,缺一不可:
• inputmode="numeric" 是告诉移动端浏览器“这个输入框预期输入数字”,比 type="tel" 更语义明确,Android Chrome 和新版 Safari 都支持;
• pattern="[0-9]*" 不影响输入行为,但配合 title="请输入4位数字" 可在表单提交校验失败时给出提示;
• 注意:不要用 maxlength="4" 直接限制长度——用户长按粘贴时,如果粘贴内容超过 4 位,整个粘贴会被截断或失败;应改用 JavaScript 监听 input 事件,手动截取前 4 位并更新值。
如何让粘贴自动分拆到每个格子?
不能只监听 paste 事件后简单赋值——剪贴板内容可能是 "1234"、"1 2 3 4"、"1-2-3-4",甚至带换行。实操建议:
• 用 event.preventDefault() 阻止默认粘贴;
• 调用 event.clipboardData.getData('text') 获取原始文本;
• 正则清洗:value.replace(/\D/g, '').slice(0, 4);
• 再逐字符分配给各格子(假设你用 4 个 <input> 元素,用 ref 或 querySelectorAll 获取);
• 最后 focus 到最后一个非空格子,方便用户继续操作。别忘了在 PC 端也处理 Ctrl+V,不能只认右键粘贴。
真正的难点不在结构,而在同步:光标位置、删除逻辑(Backspace 跨格)、剪贴板格式兼容、无障碍焦点管理——这些都得靠 JS 补足,HTML 本身只负责提供可访问、语义正确、行为可控的基础容器。











