The keyboard service helps you let your app respond to keyboard input.
You can either do this declaratively with a DSL mixin, or use the lower level service, that gives you more control.
I'd recommend using ember-keyboard
ember install ember-keyboard-service
You can specify normal key characters by using the literal value. Examples:
'a'
, '$'
, ' '
.
You can add modifier keys using 'ctrl'
, 'alt'
, 'shift'
or 'meta'
.
'cmd'
is an alias for 'meta'
, 'option'
is an alias for 'alt'
.
An example of a combo with modifiers: 'ctrl+v'
.
There is also a special modifier: 'nctrl'
, on OS X this modifier is an alias
for 'cmd'
, on any other system it is just 'ctrl'
.
Use it do declare shortcuts in a simple manner.
import KeyboardMixin from 'ember-keyboard-service/mixins/keyboard';
Ember.Object.extend(KeyboardMixin, {
keyboardHandlers: [
{ key: 'ctrl+x', handler: 'cut' }
{ key: 'ctrl+c', handler: 'copy' }
{ key: 'ctrl+v', handler: 'paste' }
],
cut() {
console.log("every day i'm cuttin");
},
copy() {
console.log("every day i'm copyin");
},
paste() {
console.log("every day i'm pastin");
}
});
You can also specify static arguments for keyboard handlers:
Ember.Object.extend(KeyboardMixin, {
keyboardHandlers: [
{ key: 'ctrl+g', handler: 'goto', arguments: [42] }
],
goto(e, line) {
console.log(`going to line ${line}`);
}
});
You can choose to bind multiple key shortcuts to the same handler:
keyboardHandlers: [
{ key: ['a', 'b'], handler: 'doStuff' }
]
You can use some of the Ember run loop features:
keyboardHandlers: [
// debounces key handlers by 30ms
{ key: 'a', handler: 'debouncedHandler', debounce: 30 },
// throttles key handlers by 30ms
{ key: 'b', handler: 'throttledHandler', throttle: 30 },
// only calls the handler once every run loop
{ key: 'c', handler: 'scheduleOnceHandler', scheduleOnce: true }
]
For more usage examples you can check out the tests
Use Ember.inject.service
to inject the service onto your Ember object.
Ember.Object.extend({
keyboard: service()
});
Then use listenFor
to start listening for keyboard events:
(The key names are equal to those used for KeyboardEvent.key
.)
this.get('keyboard').listenFor('x', this, eventHandler);
You can alternatively pass a function name instead of an eventHandler:
this.get('keyboard').listenFor('x', this, 'xEventHandler');
You can optionally specify modifier keys:
// possible modifiers are: ctrl, cmd, alt, shift
this.get('keyboard').listenFor('ctrl+alt+Delete', this, eventHandler);
You can listen for a key stroke once:
this.get('keyboard').listenForOnce('x', this, eventHandler);
You can stop listening for key strokes, you must supply the exact same
arguments as you did to listenFor
.
this.get('keyboard').stopListeningFor('x', this, eventHandler);
The service will not handle the event if the even target was an input or similar element. To override this you can do:
this.get('keyboard').listenFor('x', this, eventHandler, {
actOnInputElement: true
});
For more usage examples you can check out the tests