useHotkeys calls a function when a key combination is pressed. It skips keys typed into a text field, textarea, select or editable region by default, so a shortcut on c or space does not fire while someone is writing a word with a c in it. It listens on the window, or on one element, and stops when the component unmounts.
The callback receives the KeyboardEvent and the hotkey string that matched. It need not be memoised: the listener is bound once per set of keys and options, and always calls the latest callback.
The same string drives KeyTip, which draws it as keycaps, so one constant can register a shortcut and show it.
Modifiers match exactly: mod+z does not fire on mod+shift+z, and z does not fire on mod+z. Letters match by the character typed, and fall back to the physical key when Option or a non-Latin layout changes the character (⌥K types "˚").
Keys pressed in an input that takes text, a textarea, a select, a contenteditable region or an element with the textbox, searchbox or combobox role are ignored. Checkboxes, radios, sliders and buttons still trigger shortcuts. Set allowWhileTyping for combinations that never type a character, such as mod+s or escape:
By default the hook listens on the window. Pass target to listen on one element, so the keys work only while focus is inside it: a timeline's arrow keys, say, which should not move the playhead while focus is in the inspector beside it.
Turn a set of shortcuts off with enabled: false, while a dialog that uses the same keys is open, for instance.
The hook binds nothing until the component mounts, so it is safe in a component that renders on the server. Keys pressed while an input method is composing text are ignored, and so is a modifier pressed on its own.