2020-01-20 15:14:08 +02:00
|
|
|
///
|
2020-02-20 10:26:43 +02:00
|
|
|
/// Copyright © 2016-2020 The Thingsboard Authors
|
2020-01-20 15:14:08 +02:00
|
|
|
///
|
|
|
|
|
/// Licensed under the Apache License, Version 2.0 (the "License");
|
|
|
|
|
/// you may not use this file except in compliance with the License.
|
|
|
|
|
/// You may obtain a copy of the License at
|
|
|
|
|
///
|
|
|
|
|
/// http://www.apache.org/licenses/LICENSE-2.0
|
|
|
|
|
///
|
|
|
|
|
/// Unless required by applicable law or agreed to in writing, software
|
|
|
|
|
/// distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
|
|
/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
|
|
/// See the License for the specific language governing permissions and
|
|
|
|
|
/// limitations under the License.
|
|
|
|
|
///
|
|
|
|
|
|
|
|
|
|
import {Directive, Input, OnInit, OnDestroy, ElementRef} from '@angular/core';
|
|
|
|
|
import {Hotkey, ExtendedKeyboardEvent} from 'angular2-hotkeys';
|
|
|
|
|
import 'mousetrap';
|
|
|
|
|
import { TbCheatSheetComponent } from '@shared/components/cheatsheet.component';
|
|
|
|
|
|
|
|
|
|
@Directive({
|
|
|
|
|
selector : '[tb-hotkeys]'
|
|
|
|
|
})
|
|
|
|
|
export class TbHotkeysDirective implements OnInit, OnDestroy {
|
|
|
|
|
@Input() hotkeys: Hotkey[] = [];
|
|
|
|
|
@Input() cheatSheet: TbCheatSheetComponent;
|
|
|
|
|
|
|
|
|
|
private mousetrap: MousetrapInstance;
|
|
|
|
|
private hotkeysList: Hotkey[] = [];
|
|
|
|
|
|
2020-02-04 15:14:17 +02:00
|
|
|
private preventIn = ['INPUT', 'SELECT', 'TEXTAREA'];
|
2020-01-20 15:14:08 +02:00
|
|
|
|
2020-02-04 15:14:17 +02:00
|
|
|
constructor(private elementRef: ElementRef) {
|
|
|
|
|
this.mousetrap = new Mousetrap(this.elementRef.nativeElement);
|
|
|
|
|
(this.elementRef.nativeElement as HTMLElement).tabIndex = -1;
|
|
|
|
|
(this.elementRef.nativeElement as HTMLElement).style.outline = '0';
|
2020-01-20 15:14:08 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
ngOnInit() {
|
2020-02-04 15:14:17 +02:00
|
|
|
for (const hotkey of this.hotkeys) {
|
2020-01-20 15:14:08 +02:00
|
|
|
this.hotkeysList.push(hotkey);
|
|
|
|
|
this.bindEvent(hotkey);
|
|
|
|
|
}
|
|
|
|
|
if (this.cheatSheet) {
|
2020-02-04 15:14:17 +02:00
|
|
|
const hotkeyObj: Hotkey = new Hotkey(
|
2020-01-20 15:14:08 +02:00
|
|
|
'?',
|
|
|
|
|
(event: KeyboardEvent) => {
|
|
|
|
|
this.cheatSheet.toggleCheatSheet();
|
|
|
|
|
return false;
|
|
|
|
|
},
|
|
|
|
|
[],
|
|
|
|
|
'Show / hide this help menu',
|
|
|
|
|
);
|
|
|
|
|
this.hotkeysList.unshift(hotkeyObj);
|
|
|
|
|
this.bindEvent(hotkeyObj);
|
|
|
|
|
this.cheatSheet.setHotKeys(this.hotkeysList);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private bindEvent(hotkey: Hotkey): void {
|
2020-02-04 15:14:17 +02:00
|
|
|
this.mousetrap.bind((hotkey as Hotkey).combo, (event: KeyboardEvent, combo: string) => {
|
2020-01-20 15:14:08 +02:00
|
|
|
let shouldExecute = true;
|
2020-02-04 15:14:17 +02:00
|
|
|
if (event) {
|
|
|
|
|
const target: HTMLElement = (event.target || event.srcElement) as HTMLElement;
|
|
|
|
|
const nodeName: string = target.nodeName.toUpperCase();
|
|
|
|
|
if ((' ' + target.className + ' ').indexOf(' mousetrap ') > -1) {
|
2020-01-20 15:14:08 +02:00
|
|
|
shouldExecute = true;
|
2020-02-04 15:14:17 +02:00
|
|
|
} else if (this.preventIn.indexOf(nodeName) > -1 && (hotkey as Hotkey).
|
|
|
|
|
allowIn.map(allow => allow.toUpperCase()).indexOf(nodeName) === -1) {
|
2020-01-20 15:14:08 +02:00
|
|
|
shouldExecute = false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2020-02-04 15:14:17 +02:00
|
|
|
if (shouldExecute) {
|
|
|
|
|
return (hotkey as Hotkey).callback.apply(this, [event, combo]);
|
2020-01-20 15:14:08 +02:00
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
ngOnDestroy() {
|
2020-02-04 15:14:17 +02:00
|
|
|
for (const hotkey of this.hotkeysList) {
|
2020-01-20 15:14:08 +02:00
|
|
|
this.mousetrap.unbind(hotkey.combo);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|