键盘码速查表
常见按键的 event.key、event.code 与旧 keyCode 三者对照,编写快捷键与键盘事件时快速查阅。
原理解析
键盘事件里有两套关键标识:event.key 是「逻辑键」(显示的字符,如 "a"、"Enter"),event.code 是「物理键」(键盘上的位置,如 "KeyA"、"Digit1")。布局不同(QWERTY/Dvorak)时同一 key 可能来自不同 code。
做快捷键时应按意图选择:绑定到物理位置用 code(适合游戏/演奏),绑定到输入字符用 key(适合文本处理)。event.keyCode 已废弃,新代码不应再依赖它。
实务上怎么选:先看你要不要跨布局一致。游戏、乐器、CAD 这类绑定物理位置的场景直接用 code,因为用户换 QWERTY/Dvorak/AZERTY 后字母键位置完全不同,用 key 会让「同一个键」指向不同字母。反过来,登录框、搜索框、聊天输入这类纯文本录入,只关心输入了哪个字符,用 key 即可,不必引入 code 增加复杂度。真正需要两者配合的是快捷键——用 code 锁定物理键,用 ctrlKey/metaKey/shiftKey/altKey 判断修饰键,这样 Shift+1 在美式键盘上出 "!"、在法式键盘上出 "1" 时你绑定的仍是同一个物理组合。
还要留意事件的触发时机:keydown 在按键按下瞬间触发(按住会重复),keyup 在松开时触发,而 input/change 属于内容真正改变后才触发。快捷键的「触发」通常用 keydown,判断「最终输入了什么」用 input,混用会在 IME 组合或长按时拿到中间态。另外 form 里的 Enter 键会隐式提交表单,这是浏览器行为而非需要自己监听的快捷键,写 preventDefault 前要确认不会破坏无障碍提交。
什么时候该查这张表
这张表在三种情况下值得查:① 你在实现快捷键(hotkey)并且要区分「按了哪个字符」还是「按了哪个物理键」;② 你在排查线上只在某台机器上复现的键盘问题;③ 你在维护仍返回 keyCode 的旧代码。
不该查的情况:你只是想让输入框接收文本。那属于表单与输入处理,不需要键盘码——直接用 input 事件和表单控件即可,硬套 keyCode 只会增加复杂度。
另一个不该查的信号:你在设计「游戏操作」却打算用 key 做绑定。游戏、乐器、绘图软件需要的是物理位置(同一排的 WASD 在不同布局上不是同一排),这类场景应当用 event.code,否则用户换布局就操作错位。
判断标准很简单:你的逻辑需要「用户按了哪个意思」就用 key,需要「用户手放在哪个位置」就用 code。两者都不需要时,就不该出现在这段代码里。
边界与常见陷阱
keyCode 不是「键的编号」,而是「老 API 的残留」
keyCode 来自 IE 时代,编号与键盘布局不一致:同一个键在不同布局/输入法下可能返回不同数字。新代码不应再依赖它。它唯一还有用的场景是识别某些浏览器/输入法无法映射的按键(如「全角/半角」「滚动锁定」),此时 key 与 code 可能都是空字符串,只能退回 keyCode。
event.key 的值会随输入法与修饰键变化
组合键在 keydown 与 keyup 阶段取值不同:按住 Ctrl 再按 S,Ctrl+S 的 keydown 阶段 event.key 常是 undefined 或 "s",实际发生改变要等 keyup 阶段。在输入法组合期间(拼音候选中),event.key 可能被吞掉或返回 "Process"。因此判断组合键应优先看 event.code 加修饰键标志,而不是等 event.key 出现期望字符。
数字键与符号键在不同布局上位置不同
event.code 中数字恒为 Digit0–Digit9、字母恒为 KeyA–KeyZ,这正是它「与布局无关」的价值。但要注意主键盘区、小键盘(numpad)、功能区各有独立命名空间:主键盘 1 是 Digit1,小键盘 1 是 Numpad1,而 Numpad1 在某些布局上输出 End。混用会让「小键盘回车」这类需求出错。
preventDefault 拦不住浏览器进程层快捷键
F11 全屏、Ctrl+Shift+I / Ctrl+Shift+J(开发者工具)、Ctrl+T / Ctrl+N / Ctrl+W(标签页与窗口)在多数浏览器中由浏览器进程或 UI 层处理,网页的 keydown 监听收不到或拦不住。设计「屏蔽 Ctrl+W」这类需求前必须先确认目标浏览器是否允许,否则会得到一个看似生效、实际无效的实现。
自动重复事件会放大副作用
长按方向键会让 keydown 以操作系统的重复速率(通常每秒 10–30 次)连续触发。若处理函数里有写入、请求或重计算,必须用 e.repeat 判断或做节流;否则用户按住方向键浏览列表时会瞬间打出上百次请求。
与相邻内容的分工
event.key 返回的字符要转成 ASCII/码点数值时,用站内「ASCII 码」页;它给出的是十进制/十六进制/八进制对照,比自己写 charCodeAt 更省事。
键位名称本身(.key / .code)与字符编码是两件事:要查「这个字符怎么变成字节」,应去「字符编码」页而不是本页。
Emoji 与符号的码位查询属于 Unicode 而非键盘布局,站内「Emoji 速查」页提供码点与搜索。
若需求是「让用户在输入框里粘贴格式化后的文本」,那属于输入处理与剪贴板范畴,不需要本页的键位表。
实战片段
要点:① 用 e.code 而非 e.key 判定组合键,避开输入法与大小写干扰;② 先判 e.repeat 挡掉长按重复;③ 小键盘与主键盘是独立命名空间(NumpadEnter vs Enter),混用会让「小键盘回车」失效;④ Ctrl 与 ⌘ 的差异用 navigator.platform 在运行时判断,不要靠用户代理字符串。
// 稳定的组合键判定:用 code + 修饰键,不等 key
function onKeydown(e: KeyboardEvent) {
// 长按自动重复:避免同一次按住触发多次副作用
if (e.repeat) return
// Mac 用 metaKey(⌘),Windows/Linux 用 ctrlKey
const mod = navigator.platform.includes('Mac') ? e.metaKey : e.ctrlKey
// 小键盘回车:注意主键盘 Enter 叫 "Enter",小键盘叫 "NumpadEnter"
if (e.code === 'NumpadEnter' && mod) {
e.preventDefault()
submit()
return
}
// 方向键:只响应主键盘区,避免小键盘误触
if (e.code.startsWith('Arrow') && e.target === document.activeElement) return
// 保存:Cmd/Ctrl + S。code 稳定,不受输入法与大小写影响
if (e.code === 'KeyS' && mod) {
e.preventDefault()
save()
}
}实践注解
- keyCode 已废弃,且与 key 的语义不同keyCode 在标准里已标记 deprecated(如 Enter 恒为 13),而 event.key 给出的是字符值、event.code 给出的是物理键位。三者混用会让 IME 输入、键盘布局切换时行为异常,新代码应使用 key 或 code。
- 中文输入法会触发两次 Enter用 IME 输入时,确认候选词的 Enter 会先以 isComposing / keyCode 229 上报,然后才触发实际提交。表单的「回车提交」若不判断 event.isComposing,会在用户选词时误提交。
- key 值在按下修饰键时会变化按住 Shift 时 event.key 是大写 A,不按是小写 a;而 event.code 始终是 KeyA。快捷键判定要用 code(物理键位)还是 key(字符),取决于你想实现的是「按哪个键」还是「输入什么字符」。
数据来源
- W3C UI Events (key and code values)
- MDN Web Docs (KeyboardEvent)
上述编号、名称与定义均来自公开规范,本站不主张对规范数据本身的独创性;本页的编排方式、中文释义与实践注解由本站撰写。
| 按键 | event.key | event.code | keyCode |
|---|---|---|---|
| A | 'a' / 'A' | 'KeyA' | 65 |
| Z | 'z' / 'Z' | 'KeyZ' | 90 |
| 0 | '0' | 'Digit0' | 48 |
| 1 | '1' | 'Digit1' | 49 |
| Enter | 'Enter' | 'Enter' | 13 |
| 空格 Space | ' ' | 'Space' | 32 |
| Tab | 'Tab' | 'Tab' | 9 |
| Esc | 'Escape' | 'Escape' | 27 |
| Backspace | 'Backspace' | 'Backspace' | 8 |
| Delete | 'Delete' | 'Delete' | 46 |
| ← | 'ArrowLeft' | 'ArrowLeft' | 37 |
| → | 'ArrowRight' | 'ArrowRight' | 39 |
| ↑ | 'ArrowUp' | 'ArrowUp' | 38 |
| ↓ | 'ArrowDown' | 'ArrowDown' | 40 |
| Shift | 'Shift' | 'ShiftLeft' / 'ShiftRight' | 16 |
| Ctrl | 'Control' | 'ControlLeft' / 'ControlRight' | 17 |
| Alt | 'Alt' | 'AltLeft' / 'AltRight' | 18 |
| F1 | 'F1' | 'F1' | 112 |
| F12 | 'F12' | 'F12' | 123 |
| / | '/' | 'Slash' | 191 |
| . | '.' | 'Period' | 190 |
| , | ',' | 'Comma' | 188 |
常见问题
event.key 和 event.code 有什么区别?
event.key 是按键的「字符值」(受 Shift/大小写影响,如按 A 出 "a" 或 "A");event.code 是按键的「物理位置」(始终为 "KeyA",不受布局影响)。做快捷键通常优先考虑 event.code 或 event.key 配合修饰键判断。
keyCode 为什么被弃用?
KeyboardEvent.keyCode 是旧 IE 时代的数字编号,与键盘布局不一致、已被 Web 标准标记为 deprecated。新代码应使用 event.key / event.code,但存量库仍常返回 keyCode,排查旧代码时仍需对照本表。
如何屏蔽浏览器默认快捷键(如 Ctrl+S、F12)?
在 keydown 事件里对目标组合调用 event.preventDefault() 即可阻止默认行为。注意:部分快捷键(如某些浏览器的 F11 全屏、DevTools 组合键)由浏览器进程层拦截,网页无法完全屏蔽。
如何判断组合键如 Ctrl+C / Ctrl+Enter?
在 keydown 中同时检查 event.ctrlKey(Mac 用 metaKey)、event.key 或 event.code。例如 Ctrl+C:event.ctrlKey && (event.key === "c" || event.code === "KeyC")。建议用 code 避免输入法/大小写干扰。