Keyboard events
By Flavio Copes
Learn how to handle keyboard events in JavaScript with keydown and keyup on the document, and read the KeyboardEvent key, code, and modifier properties.
There are two keyboard events you’ll work with:
keydownthe keyboard key has been pressedkeyupthe keyboard key has been released
A third one, keypress, is obsolete. Browsers still fire it, but don’t use it in new code. When you care about the text typed into a field, use the input event instead (more on this below).
keydown is also fired when the key repeats while the button stays pressed.
While mouse and touch events are typically listened on a specific element, it’s common to listen for keyboard events on the document:
document.addEventListener('keydown', (event) => {
// key pressed
})
The parameter passed to the event listener is a KeyboardEvent.
This event object, in addition to the Event object properties offers us (among others) these unique properties:
altKeytrue if alt key was pressed when the event was firedcodethe physical key pressed, returned as a string. It does not change with the keyboard layoutctrlKeytrue if ctrl key was pressed when the event was firedisComposingtrue while the user is composing text with an IMEkeythe value of the key pressed, returned as a string. Prefer this for most checkslocationthe location of the key on the keyboardmetaKeytrue if meta key was pressed when the event was firedrepeattrue if the key has been repeated (e.g. the key has not been released)shiftKeytrue if shift key was pressed when the event was fired
You can also call event.getModifierState('CapsLock') (and similar modifier names) when you need the lock state of a modifier key.
This demo is a keylogger which will show you the values of some of the properties I listed above: https://codepen.io/flaviocopes/pen/LopWmq/
key vs code
key is the character or action the user meant. code is the physical key they pressed.
On a US keyboard, the key labeled A gives you:
document.addEventListener('keydown', (event) => {
console.log(event.key) // 'a' (or 'A' with Shift)
console.log(event.code) // 'KeyA'
})
Press Enter and you get event.key === 'Enter' and event.code === 'Enter'. Press the left arrow and you get event.key === 'ArrowLeft' and event.code === 'ArrowLeft'.
Use key when you care about the meaning: save, submit, move left. Use code when you care about the physical position, like WASD controls that should stay on those keys even on a non-US layout.
Detecting a keyboard shortcut
The modifier properties let you detect shortcuts. A common pattern is Cmd+S on Mac and Ctrl+S elsewhere:
document.addEventListener('keydown', (event) => {
const savePressed =
(event.metaKey || event.ctrlKey) && event.key.toLowerCase() === 's'
if (!savePressed) {
return
}
event.preventDefault()
// save the document
})
metaKey is the Command key on Mac. ctrlKey is Control on Windows and Linux. Checking both covers both platforms. toLowerCase() keeps the check working when Shift or Caps Lock is on, since key is then 'S'.
When preventDefault matters
Browsers already react to some keys. Space scrolls the page. Enter submits a focused form. Ctrl/Cmd+S opens the browser save dialog.
Call event.preventDefault() when your handler should own that key and the default action would get in the way:
document.addEventListener('keydown', (event) => {
if (event.key !== ' ') {
return
}
event.preventDefault()
// space triggers your action, the page does not scroll
})
Only cancel what you handle. Leave Tab, Escape, and browser shortcuts alone unless you have a real reason. For the broader difference between preventDefault and stopPropagation, see preventDefault vs stopPropagation.
Prefer the input event for text fields
keydown tells you a key was pressed. It does not tell you the field value after that key.
When the user is typing into an <input> or <textarea>, listen for input on that field. You get the updated value after every change, including paste and autofill:
const search = document.querySelector('#search')
search.addEventListener('input', (event) => {
console.log(event.target.value)
})
Keep keydown for shortcuts and navigation. Use input when you care about the text itself. Form field events such as change, focus, and blur are covered in Handling forms in JavaScript.
Want me to talk about your product? You can sponsor this site.
Related posts about platform: