diff --git a/src/app.module.ts b/src/app.module.ts
index d7e404aa..242f0e93 100644
--- a/src/app.module.ts
+++ b/src/app.module.ts
@@ -62,6 +62,7 @@ import { MainAppComponent, appRoutingProviders, routing } from './main-app';
import { CancelableDirective } from './directives';
+import { CaptureService } from './services/capture.service';
import { MapperService } from './services/mapper.service';
import { KeymapEffects, MacroEffects } from './store/effects';
@@ -154,7 +155,8 @@ const storeConfig = {
MapperService,
appRoutingProviders,
KeymapEditGuard,
- MacroNotFoundGuard
+ MacroNotFoundGuard,
+ CaptureService
],
bootstrap: [MainAppComponent]
})
diff --git a/src/components/popover/tab/keypress/keypress-tab.component.html b/src/components/popover/tab/keypress/keypress-tab.component.html
index 9082a15b..8afd46b8 100644
--- a/src/components/popover/tab/keypress/keypress-tab.component.html
+++ b/src/components/popover/tab/keypress/keypress-tab.component.html
@@ -7,7 +7,7 @@
[width]="200"
[options]="options"
>
-
+
Modifiers:
diff --git a/src/components/popover/tab/keypress/keypress-tab.component.ts b/src/components/popover/tab/keypress/keypress-tab.component.ts
index eebc321d..43670ce3 100644
--- a/src/components/popover/tab/keypress/keypress-tab.component.ts
+++ b/src/components/popover/tab/keypress/keypress-tab.component.ts
@@ -66,6 +66,17 @@ export class KeypressTabComponent implements OnChanges, Tab {
return keystrokeAction.scancode > 0 || keystrokeAction.modifierMask > 0;
}
+ onKeysCapture(event: {code: number, left: boolean[], right: boolean[]}) {
+ if (event.code) {
+ this.scanCode = event.code;
+ } else {
+ this.scanCode = 0;
+ }
+
+ this.leftModifierSelects = event.left;
+ this.rightModifierSelects = event.right;
+ }
+
fromKeyAction(keyAction: KeyAction): boolean {
if (!(keyAction instanceof KeystrokeAction)) {
return false;
@@ -139,17 +150,11 @@ export class KeypressTabComponent implements OnChanges, Tab {
modifierSelects[index] = !modifierSelects[index];
}
- // TODO: change to the correct type when the wrapper has added it.
- /* tslint:disable:no-unused-variable: It is used in the template. */
- private onLongpressChange(event: any) {
- /* tslint:enable:no-unused-variable: */
+ onLongpressChange(event: {value: string}) {
this.selectedLongPressIndex = +event.value;
}
- // TODO: change to the correct type when the wrapper has added it.
- /* tslint:disable:no-unused-variable: It is used in the template. */
- private onScancodeChange(event: any) {
- /* tslint:enable:no-unused-variable */
+ onScancodeChange(event: {value: string}) {
this.scanCode = +event.value;
}
diff --git a/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.html b/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.html
index d27114dd..91e06d41 100644
--- a/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.html
+++ b/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.html
@@ -1,11 +1,12 @@
\ No newline at end of file
diff --git a/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.ts b/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.ts
index ebb2d271..129df98c 100644
--- a/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.ts
+++ b/src/components/popover/widgets/capture-keystroke/capture-keystroke-button.component.ts
@@ -1,23 +1,76 @@
-import { Component, OnInit } from '@angular/core';
+import { Component, EventEmitter, HostListener, Output } from '@angular/core';
+import { CaptureService } from '../../../../services/capture.service';
@Component({
selector: 'capture-keystroke-button',
template: require('./capture-keystroke-button.component.html'),
styles: [require('./capture-keystroke-button.component.scss')]
})
-export class CaptureKeystrokeButtonComponent implements OnInit {
+export class CaptureKeystrokeButtonComponent {
+ @Output() capture = new EventEmitter
();
+
private record: boolean;
+ private first: boolean; // enable usage of Enter to start capturing
- constructor() { }
+ constructor(private captureService: CaptureService) {
+ this.record = false;
+ this.captureService.initModifiers();
+ this.captureService.populateMapping();
+ }
- ngOnInit() { }
+ @HostListener('keyup')
+ onKeyUp() {
+ if (this.record && !this.first) {
+ this.saveScanCode();
+ }
+ }
+
+ @HostListener('keydown', ['$event'])
+ onKeyDown(e: KeyboardEvent) {
+ const code: number = e.keyCode;
+ const enter = 13;
+
+ if (this.record) {
+ e.preventDefault();
+ this.first = false;
+
+ if (this.captureService.hasMap(code)) {
+ this.saveScanCode(this.captureService.getMap(code));
+ } else {
+ this.captureService.setModifier((e.location === 1), code);
+ }
+ } else if (code === enter) {
+ this.record = true;
+ this.first = true;
+ }
+ }
+
+ @HostListener('focusout')
+ onFocusOut() {
+ this.record = false;
+ this.reset();
+ }
start(): void {
this.record = true;
}
- stop(): void {
+ private saveScanCode(code?: number) {
this.record = false;
+ const left: boolean[] = this.captureService.getModifiers(true);
+ const right: boolean[] = this.captureService.getModifiers(false);
+
+ this.capture.emit({
+ code,
+ left,
+ right
+ });
+
+ this.reset();
}
+ private reset() {
+ this.first = false;
+ this.captureService.initModifiers();
+ }
}
diff --git a/src/services/capture.service.ts b/src/services/capture.service.ts
new file mode 100644
index 00000000..dbb4b84b
--- /dev/null
+++ b/src/services/capture.service.ts
@@ -0,0 +1,142 @@
+import { Injectable } from '@angular/core';
+
+@Injectable()
+export class CaptureService {
+ private mapping: Map;
+ private leftModifiers: Map;
+ private rightModifiers: Map;
+
+ constructor() {
+ this.leftModifiers = new Map();
+ this.rightModifiers = new Map();
+ this.mapping = new Map();
+ }
+
+ public getMap(code: number) {
+ return this.mapping.get(code);
+ }
+
+ public hasMap(code: number) {
+ return this.mapping.has(code);
+ }
+
+ public setModifier(left: boolean, code: number) {
+ return left ? this.leftModifiers.set(code, true) : this.rightModifiers.set(code, true);
+ }
+
+ public getModifiers(left: boolean) {
+ return left ? this.reMap(this.leftModifiers) : this.reMap(this.rightModifiers);
+ }
+
+ public initModifiers() {
+ this.leftModifiers.set(16, false); // Shift
+ this.leftModifiers.set(17, false); // Ctrl
+ this.leftModifiers.set(18, false); // Alt
+ this.leftModifiers.set(91, false); // Super
+
+ this.rightModifiers.set(16, false); // Shift
+ this.rightModifiers.set(17, false); // Ctrl
+ this.rightModifiers.set(18, false); // Alt
+ this.rightModifiers.set(91, false); // Super
+ }
+
+ public populateMapping () {
+ this.mapping.set(8, 42); // Backspace
+ this.mapping.set(9, 43); // Tab
+ this.mapping.set(13, 40); // Enter
+ this.mapping.set(19, 72); // Pause/break
+ this.mapping.set(20, 57); // Caps lock
+ this.mapping.set(27, 41); // Escape
+ this.mapping.set(32, 44); // (space)
+ this.mapping.set(33, 75); // Page up
+ this.mapping.set(34, 78); // Page down
+ this.mapping.set(35, 77); // End
+ this.mapping.set(36, 74); // Home
+ this.mapping.set(37, 80); // Left arrow
+ this.mapping.set(38, 82); // Up arrow
+ this.mapping.set(39, 79); // Right arrow
+ this.mapping.set(40, 81); // Down arrow
+ this.mapping.set(45, 73); // Insert
+ this.mapping.set(46, 76); // Delete
+ this.mapping.set(48, 39); // 0
+ this.mapping.set(49, 30); // 1
+ this.mapping.set(50, 31); // 2
+ this.mapping.set(51, 32); // 3
+ this.mapping.set(52, 33); // 4
+ this.mapping.set(53, 34); // 5
+ this.mapping.set(54, 35); // 6
+ this.mapping.set(55, 36); // 7
+ this.mapping.set(56, 37); // 8
+ this.mapping.set(57, 38); // 9
+ this.mapping.set(65, 4); // A
+ this.mapping.set(66, 5); // B
+ this.mapping.set(67, 6); // C
+ this.mapping.set(68, 7); // D
+ this.mapping.set(69, 8); // E
+ this.mapping.set(70, 9); // F
+ this.mapping.set(71, 10); // G
+ this.mapping.set(72, 11); // H
+ this.mapping.set(73, 12); // I
+ this.mapping.set(74, 13); // J
+ this.mapping.set(75, 14); // K
+ this.mapping.set(76, 15); // L
+ this.mapping.set(77, 16); // M
+ this.mapping.set(78, 17); // N
+ this.mapping.set(79, 18); // O
+ this.mapping.set(80, 19); // P
+ this.mapping.set(81, 20); // Q
+ this.mapping.set(82, 21); // R
+ this.mapping.set(83, 22); // S
+ this.mapping.set(84, 23); // T
+ this.mapping.set(85, 24); // U
+ this.mapping.set(86, 25); // V
+ this.mapping.set(87, 26); // W
+ this.mapping.set(88, 27); // X
+ this.mapping.set(89, 28); // Y
+ this.mapping.set(90, 29); // Z
+ this.mapping.set(96, 98); // Num pad 0
+ this.mapping.set(97, 89); // Num pad 1
+ this.mapping.set(98, 90); // Num pad 2
+ this.mapping.set(99, 91); // Num pad 3
+ this.mapping.set(100, 92); // Num pad 4
+ this.mapping.set(101, 93); // Num pad 5
+ this.mapping.set(102, 94); // Num pad 6
+ this.mapping.set(103, 95); // Num pad 7
+ this.mapping.set(104, 96); // Num pad 8
+ this.mapping.set(105, 97); // Num pad 9
+ this.mapping.set(106, 85); // Multiply
+ this.mapping.set(107, 87); // Add
+ this.mapping.set(109, 86); // Subtract
+ this.mapping.set(110, 99); // Decimal point
+ this.mapping.set(111, 84); // Divide
+ this.mapping.set(112, 58); // F1
+ this.mapping.set(113, 59); // F2
+ this.mapping.set(114, 60); // F3
+ this.mapping.set(115, 61); // F4
+ this.mapping.set(116, 62); // F5
+ this.mapping.set(117, 63); // F6
+ this.mapping.set(118, 64); // F7
+ this.mapping.set(119, 65); // F8
+ this.mapping.set(120, 66); // F9
+ this.mapping.set(121, 67); // F10
+ this.mapping.set(122, 68); // F11
+ this.mapping.set(123, 69); // F12
+ this.mapping.set(144, 83); // Num lock
+ this.mapping.set(145, 71); // Scroll lock
+ this.mapping.set(186, 51); // Semi-colon
+ this.mapping.set(187, 46); // Equal sign
+ this.mapping.set(188, 54); // Comma
+ this.mapping.set(189, 45); // Dash
+ this.mapping.set(190, 55); // Period
+ this.mapping.set(191, 56); // Forward slash
+ this.mapping.set(192, 53); // Grave accent
+ this.mapping.set(219, 47); // Open bracket
+ this.mapping.set(220, 49); // Back slash
+ this.mapping.set(221, 48); // Close bracket
+ this.mapping.set(222, 52); // Single quote
+ }
+
+ private reMap(value: Map): boolean[] {
+ return [value.get(16), value.get(17), value.get(91), value.get(18)];
+ }
+}