combi

A tiny keyboard shortcut handling library

Usage no npm install needed!

<script type="module">
  import combi from 'https://cdn.skypack.dev/combi';
</script>

README

Combi

npm License:MIT Build Status Coverage Status Type Declarations

⌨️ A tiny keyboard shortcut handling library.

Features

  • Pocket-sized – library size is less than 600 bytes (~350 bytes gzipped!)
  • Minimal – pass a callback function => get results.
  • Specialized – only handles key combinations with at least one or more modifier keys pressed and at most one regular key (read more)
  • Framework-agnostic – can be plugged on any standard KeyboardEvent listener (keyup, keydown, keypress, etc.)

Use Cases

  • Declaratively listen for shortcut events
  • Key combination input field for user-friendly shortcut configuration
  • Handle simple or complex shortcut UIs with a standardized format

Bundle Sizes

minizipped size minizipped size

Example

import combi from 'combi'

const onShortcut = combi((shortcut, keyEvent) => {
  console.log(shortcut) // -> 'ctrl+z'
})

window.addEventListener('keydown', onShortcut)

Installation

Via npm

npm install --save combi

Via unpkg

Alternatively, you can download and/or import it from unpkg.com/combi as an ES or UMD module.

Import as ES Module

import combi from 'https://unpkg.com/combi/dist/combi.es.js'

Use as UMD Module

<!-- This adds `combi` to the global context (`window`) -->
<script src="https://unpkg.com/combi/dist/combi.umd.js"></script>

You can find the library on window.combi

Usage Examples

Listening for Shortcuts

combi takes a handler function as an argument. This handler function should take two arguments. The first one: the keyboard shortcut that has been pressed. The second one: the original keyboard event. You can match these shortcuts however you want.

See it in action

import combi from 'combi'

const onShortcut = combi((shortcut) => {
  switch ((shortcut, event)) {
    case 'meta+s':
    case 'ctrl+s':
      event.preventDefault()
      action('save')
      break
    case 'shift+meta+z':
    case 'ctrl+y':
      event.preventDefault()
      action('redo')
      break
    case localStorage.getItem('shortcut'):
      event.preventDefault()
      action('custom-action')
      break
    default:
    // do nothing.
  }
})

window.addEventListener('keydown', onShortcut)

Key Combination Input Field

You can use combi to create custom input fields for specifying key combinations. Useful when building apps with configurable keyboard shortcuts.

See it in action

import combi from 'combi'

// pass `true` as second argument to call preventDefault() when a combination is used
const onShortcut = combi((combination, event) => {
  event.target.value = combination
  localStorage.setItem('shortcut', combination)
}, true)

const inputElement = document.querySelector('#shortcut-input')

inputElement.addEventListener('keydown', onShortcut)

Reference

API

combi(callback, [preventDefault])

combi(callback: Function, preventDefault?: Boolean)
callback {Function}

A function that handles shortcuts, that looks like this:

(shortcut: String, event: KeyboardEvent) => any

shortcut {String} - keyboard shortcut that has been pressed (e.g. shift+meta+x, ctrl+y)

event {KeyboardEvent} - the original KeyboardEvent passed to combi by the event listener

preventDefault {Boolean}

Whether combi should always call .preventDefault() when receiving a keyboard event. Defaults to false

Supported Modifiers

These are the modifiers combi supports. Shortcuts detected will always be parsed in this order:

  • ctrl
  • alt
  • shift
  • meta
    • Command key () on macOS
    • Windows key () on Windows (note: using meta on Windows is highly discouraged for non-system shortcuts)

Considerations

In order to maintain combi as simple as possible, while enabling the most common and standard use cases, some rules are in place:

  • Only key combinations of two or more keys are allowed, with the following conditions:
    • at least one or more modifiers (ctrl, shift, alt, etc.)
    • at most one regular key (a-z, 0-9, -, +, [, ], \, etc.)
    • Example: shift+k+z won't work
  • Key combinations are represented as a string concatenation of modifier keys and an (optional, if the combination is of more than two ) regular key in the following normative order: ctrl+alt+shift+meta+somekey
  • All non-modifier keys are lowercased versions of KeyboardEvent.code with the words Key and Digit removed
    • Examples:
      • KeyA becomes a
      • Digit0 becomes 0
      • BracketLeft becomes bracketleft

Note: These considerations are not arbitrary. Most of them are derived from the following guidelines:

Contributing

Bug Reports & Feature Requests

Something does not work as expected or perhaps you think this project needs a feature? Please open an issue using GitHub issue tracker.

Make sure that an issue pointing out your specific problem does not exist already. Please be as specific and straightforward as possible.

Pull Requests

Pull Requests (PRs) are welcome! You should follow the same basic stylistic conventions as the original code.

Make sure that a pull request solving your specific problem does not exist already. Your changes must be concise and focus on solving a discrete problem.

License

The MIT License (MIT)

Copyright (c) 2018 Kristian Muñiz