@genesislcap/foundation-utils 14.311.0 → 14.312.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/custom-elements.json +810 -129
- package/dist/dts/index.d.ts +1 -0
- package/dist/dts/index.d.ts.map +1 -1
- package/dist/dts/shortcut-manager/index.d.ts +3 -0
- package/dist/dts/shortcut-manager/index.d.ts.map +1 -0
- package/dist/dts/shortcut-manager/shortcut-listener.d.ts +21 -0
- package/dist/dts/shortcut-manager/shortcut-listener.d.ts.map +1 -0
- package/dist/dts/shortcut-manager/shortcut-manager.d.ts +120 -0
- package/dist/dts/shortcut-manager/shortcut-manager.d.ts.map +1 -0
- package/dist/dts/utils/os-platform.d.ts +31 -0
- package/dist/dts/utils/os-platform.d.ts.map +1 -0
- package/dist/esm/index.js +1 -0
- package/dist/esm/shortcut-manager/index.js +2 -0
- package/dist/esm/shortcut-manager/shortcut-listener.js +140 -0
- package/dist/esm/shortcut-manager/shortcut-manager.js +286 -0
- package/dist/esm/utils/os-platform.js +63 -0
- package/dist/foundation-utils.api.json +8414 -5799
- package/dist/foundation-utils.d.ts +145 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.clearactivecontext.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.executeshortcut.md +50 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.executeshortcutbycontext.md +64 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.findshortcutbykeycombination.md +114 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.getactivecontext.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.getcontexts.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.getshortcuts.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.getshortcutsbycontext.md +50 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.getshortcutsbycontextmap.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.ispaused.md +11 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.ispaused_.md +11 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.ispausedsubject.md +11 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.md +321 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.pause.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.registercontext.md +50 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.registershortcut.md +50 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.registershortcuts.md +50 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.resume.md +15 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.setactivecontext.md +50 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.unregistershortcut.md +64 -0
- package/docs/api/foundation-utils.defaultshortcutmanager.unregistershortcutsbycontext.md +50 -0
- package/docs/api/foundation-utils.foundationshortcutlistener.connectedcallback.md +15 -0
- package/docs/api/foundation-utils.foundationshortcutlistener.disconnectedcallback.md +15 -0
- package/docs/api/foundation-utils.foundationshortcutlistener.md +105 -0
- package/docs/api/foundation-utils.foundationshortcutlistener.shortcutmanager.md +11 -0
- package/docs/api/foundation-utils.md +77 -0
- package/docs/api/foundation-utils.shortcutdefinition.action.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.altkey.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.canexecute.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.context.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.ctrlkey.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.description.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.elementref.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.id.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.key.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.md +276 -0
- package/docs/api/foundation-utils.shortcutdefinition.metakey.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.optionkey.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.priority.md +11 -0
- package/docs/api/foundation-utils.shortcutdefinition.shiftkey.md +11 -0
- package/docs/api/foundation-utils.shortcutexecutionstatus.md +16 -0
- package/docs/api/foundation-utils.shortcutmanager.clearactivecontext.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.executeshortcut.md +58 -0
- package/docs/api/foundation-utils.shortcutmanager.executeshortcutbycontext.md +70 -0
- package/docs/api/foundation-utils.shortcutmanager.findshortcutbykeycombination.md +114 -0
- package/docs/api/foundation-utils.shortcutmanager.getactivecontext.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.getcontexts.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.getshortcuts.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.getshortcutsbycontext.md +50 -0
- package/docs/api/foundation-utils.shortcutmanager.getshortcutsbycontextmap.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.ispaused.md +11 -0
- package/docs/api/foundation-utils.shortcutmanager.ispaused_.md +11 -0
- package/docs/api/foundation-utils.shortcutmanager.ispausedsubject.md +11 -0
- package/docs/api/foundation-utils.shortcutmanager.md +13 -0
- package/docs/api/foundation-utils.shortcutmanager.pause.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.registercontext.md +50 -0
- package/docs/api/foundation-utils.shortcutmanager.registershortcut.md +50 -0
- package/docs/api/foundation-utils.shortcutmanager.registershortcuts.md +50 -0
- package/docs/api/foundation-utils.shortcutmanager.resume.md +15 -0
- package/docs/api/foundation-utils.shortcutmanager.setactivecontext.md +50 -0
- package/docs/api/foundation-utils.shortcutmanager.unregistershortcut.md +64 -0
- package/docs/api/foundation-utils.shortcutmanager.unregistershortcutsbycontext.md +50 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.disabled.md +11 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.id.md +11 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.keycombination.md +11 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.keycombinationdisplay.md +11 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.md +141 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.shortcut.md +11 -0
- package/docs/api/foundation-utils.shortcutregistrationresult.tooltip.md +11 -0
- package/docs/api-report.md.api.md +153 -0
- package/package.json +12 -11
package/dist/dts/index.d.ts
CHANGED
package/dist/dts/index.d.ts.map
CHANGED
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,QAAQ,CAAC;AACvB,cAAc,cAAc,CAAC;AAC7B,cAAc,iBAAiB,CAAC;AAChC,cAAc,cAAc,CAAC;AAC7B,cAAc,YAAY,CAAC;AAC3B,cAAc,OAAO,CAAC;AACtB,cAAc,SAAS,CAAC;AACxB,cAAc,cAAc,CAAC;AAC7B,cAAc,UAAU,CAAC;AACzB,cAAc,WAAW,CAAC;AAC1B,cAAc,UAAU,CAAC;AACzB,cAAc,YAAY,CAAC;AAC3B,cAAc,WAAW,CAAC;AAC1B,cAAc,YAAY,CAAC;AAC3B,cAAc,eAAe,CAAC;AAC9B,cAAc,SAAS,CAAC;AACxB,cAAc,UAAU,CAAC;AACzB,cAAc,SAAS,CAAC;AACxB,cAAc,QAAQ,CAAC;AACvB,cAAc,UAAU,CAAC"}
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,QAAQ,CAAC;AACvB,cAAc,cAAc,CAAC;AAC7B,cAAc,iBAAiB,CAAC;AAChC,cAAc,cAAc,CAAC;AAC7B,cAAc,YAAY,CAAC;AAC3B,cAAc,OAAO,CAAC;AACtB,cAAc,SAAS,CAAC;AACxB,cAAc,cAAc,CAAC;AAC7B,cAAc,UAAU,CAAC;AACzB,cAAc,WAAW,CAAC;AAC1B,cAAc,UAAU,CAAC;AACzB,cAAc,YAAY,CAAC;AAC3B,cAAc,WAAW,CAAC;AAC1B,cAAc,YAAY,CAAC;AAC3B,cAAc,eAAe,CAAC;AAC9B,cAAc,oBAAoB,CAAC;AACnC,cAAc,SAAS,CAAC;AACxB,cAAc,UAAU,CAAC;AACzB,cAAc,SAAS,CAAC;AACxB,cAAc,QAAQ,CAAC;AACvB,cAAc,UAAU,CAAC"}
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/shortcut-manager/index.ts"],"names":[],"mappings":"AAAA,cAAc,oBAAoB,CAAC;AACnC,cAAc,qBAAqB,CAAC"}
|
@@ -0,0 +1,21 @@
|
|
1
|
+
import { FASTElement } from '@microsoft/fast-element';
|
2
|
+
import { ShortcutManager } from './shortcut-manager';
|
3
|
+
/**
|
4
|
+
* A custom element that listens for keyboard shortcuts.
|
5
|
+
* @public
|
6
|
+
* @remarks Part of the ShortcutManager Service.
|
7
|
+
*/
|
8
|
+
export declare class FoundationShortcutListener extends FASTElement {
|
9
|
+
shortcutManager: ShortcutManager;
|
10
|
+
private keyListener;
|
11
|
+
private isListening;
|
12
|
+
connectedCallback(): void;
|
13
|
+
disconnectedCallback(): void;
|
14
|
+
private setupStateSubscription;
|
15
|
+
private addKeyListener;
|
16
|
+
private removeKeyListener;
|
17
|
+
private handleKeyDown;
|
18
|
+
private extractKeyFromCode;
|
19
|
+
private isInputElement;
|
20
|
+
}
|
21
|
+
//# sourceMappingURL=shortcut-listener.d.ts.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"shortcut-listener.d.ts","sourceRoot":"","sources":["../../../src/shortcut-manager/shortcut-listener.ts"],"names":[],"mappings":"AAAA,OAAO,EAAiB,WAAW,EAAE,MAAM,yBAAyB,CAAC;AAErE,OAAO,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAErD;;;;GAIG;AACH,qBAGa,0BAA2B,SAAQ,WAAW;IAChC,eAAe,EAAE,eAAe,CAAC;IAE1D,OAAO,CAAC,WAAW,CAAiD;IACpE,OAAO,CAAC,WAAW,CAAS;IAE5B,iBAAiB;IAKjB,oBAAoB;IAKpB,OAAO,CAAC,sBAAsB;IAgB9B,OAAO,CAAC,cAAc;IAQtB,OAAO,CAAC,iBAAiB;IAQzB,OAAO,CAAC,aAAa;IA6BrB,OAAO,CAAC,kBAAkB;IA6C1B,OAAO,CAAC,cAAc;CAuBvB"}
|
@@ -0,0 +1,120 @@
|
|
1
|
+
import { BehaviorSubject, Observable } from 'rxjs';
|
2
|
+
/**
|
3
|
+
* A type which represents the disabled status and tooltip of an item
|
4
|
+
* @public
|
5
|
+
* */
|
6
|
+
export type ShortcutExecutionStatus = {
|
7
|
+
disabled?: boolean;
|
8
|
+
tooltip?: string;
|
9
|
+
};
|
10
|
+
/**
|
11
|
+
* A definition of a keyboard shortcut
|
12
|
+
* @public
|
13
|
+
*/
|
14
|
+
export interface ShortcutDefinition {
|
15
|
+
id: string;
|
16
|
+
key: string;
|
17
|
+
ctrlKey?: boolean;
|
18
|
+
altKey?: boolean;
|
19
|
+
optionKey?: boolean;
|
20
|
+
shiftKey?: boolean;
|
21
|
+
metaKey?: boolean;
|
22
|
+
description: string;
|
23
|
+
action: () => void;
|
24
|
+
context: string;
|
25
|
+
priority?: number;
|
26
|
+
elementRef?: HTMLElement;
|
27
|
+
canExecute?: () => ShortcutExecutionStatus;
|
28
|
+
}
|
29
|
+
/**
|
30
|
+
* A result of registering a keyboard shortcut
|
31
|
+
* @public
|
32
|
+
*/
|
33
|
+
export interface ShortcutRegistrationResult {
|
34
|
+
shortcut: ShortcutDefinition;
|
35
|
+
id: string;
|
36
|
+
keyCombination: string;
|
37
|
+
keyCombinationDisplay: string;
|
38
|
+
disabled: () => boolean;
|
39
|
+
tooltip: () => string | undefined;
|
40
|
+
}
|
41
|
+
/**
|
42
|
+
* Interface of a manager for keyboard shortcuts
|
43
|
+
* @public
|
44
|
+
*/
|
45
|
+
export interface ShortcutManager {
|
46
|
+
registerShortcuts(shortcuts: ShortcutDefinition[]): void;
|
47
|
+
registerShortcut(shortcut: ShortcutDefinition): ShortcutRegistrationResult;
|
48
|
+
unregisterShortcut(context: string, id: string): void;
|
49
|
+
unregisterShortcutsByContext(context: string): void;
|
50
|
+
/**
|
51
|
+
* Execute a shortcut by its id
|
52
|
+
* @param id - The id of the shortcut to execute
|
53
|
+
* @remarks This method will execute the shortcut in the active context
|
54
|
+
*/
|
55
|
+
executeShortcut(id: string): void;
|
56
|
+
/**
|
57
|
+
* Execute a shortcut by its id and context
|
58
|
+
* @param context - The context of the shortcut to execute
|
59
|
+
* @param id - The id of the shortcut to execute
|
60
|
+
*/
|
61
|
+
executeShortcutByContext(context: string, id: string): void;
|
62
|
+
getShortcuts(): ShortcutDefinition[];
|
63
|
+
getShortcutsByContext(context: string): ShortcutDefinition[];
|
64
|
+
getContexts(): string[];
|
65
|
+
getShortcutsByContextMap(): Map<string, Map<string, ShortcutDefinition>>;
|
66
|
+
registerContext(context: string): void;
|
67
|
+
setActiveContext(context: string): void;
|
68
|
+
getActiveContext(): string | undefined;
|
69
|
+
clearActiveContext(): void;
|
70
|
+
findShortcutByKeyCombination(key: string, ctrlKey?: boolean, altKey?: boolean, shiftKey?: boolean, metaKey?: boolean): ShortcutDefinition | undefined;
|
71
|
+
pause(): void;
|
72
|
+
resume(): void;
|
73
|
+
isPaused: boolean;
|
74
|
+
isPaused$: Observable<boolean>;
|
75
|
+
isPausedSubject: BehaviorSubject<boolean>;
|
76
|
+
}
|
77
|
+
/**
|
78
|
+
* Default implementation of the ShortcutManager interface
|
79
|
+
* @public
|
80
|
+
*/
|
81
|
+
export declare class DefaultShortcutManager implements ShortcutManager {
|
82
|
+
private shortcuts;
|
83
|
+
private shortcutLookup;
|
84
|
+
private keyCombinationMap;
|
85
|
+
private _isPausedSubject;
|
86
|
+
private _activeContext;
|
87
|
+
get isPaused(): boolean;
|
88
|
+
get isPaused$(): Observable<boolean>;
|
89
|
+
get isPausedSubject(): BehaviorSubject<boolean>;
|
90
|
+
registerShortcuts(shortcuts: ShortcutDefinition[]): void;
|
91
|
+
registerShortcut(shortcut: ShortcutDefinition): ShortcutRegistrationResult;
|
92
|
+
unregisterShortcut(context: string, id: string): void;
|
93
|
+
unregisterShortcutsByContext(context: string): void;
|
94
|
+
executeShortcut(id: string): void;
|
95
|
+
executeShortcutByContext(context: string, id: string): void;
|
96
|
+
getShortcuts(): ShortcutDefinition[];
|
97
|
+
getShortcutsByContext(context: string): ShortcutDefinition[];
|
98
|
+
findShortcutByKeyCombination(key: string, ctrlKey?: boolean, altKey?: boolean, shiftKey?: boolean, metaKey?: boolean): ShortcutDefinition | undefined;
|
99
|
+
getContexts(): string[];
|
100
|
+
getShortcutsByContextMap(): Map<string, Map<string, ShortcutDefinition>>;
|
101
|
+
registerContext(context: string): void;
|
102
|
+
setActiveContext(context: string): void;
|
103
|
+
getActiveContext(): string | undefined;
|
104
|
+
clearActiveContext(): void;
|
105
|
+
pause(): void;
|
106
|
+
resume(): void;
|
107
|
+
/**
|
108
|
+
* Normalizes a shortcut definition to handle option/alt equivalence
|
109
|
+
* If optionKey is set, altKey will also be set to true (and vice versa)
|
110
|
+
*/
|
111
|
+
private normalizeShortcutDefinition;
|
112
|
+
private createKeyCombinationKey;
|
113
|
+
private isElementFocused;
|
114
|
+
}
|
115
|
+
/**
|
116
|
+
* A dependency injection token for the ShortcutManager interface.
|
117
|
+
* @public
|
118
|
+
*/
|
119
|
+
export declare const ShortcutManager: import("@microsoft/fast-foundation").InterfaceSymbol<ShortcutManager>;
|
120
|
+
//# sourceMappingURL=shortcut-manager.d.ts.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"shortcut-manager.d.ts","sourceRoot":"","sources":["../../../src/shortcut-manager/shortcut-manager.ts"],"names":[],"mappings":"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"}
|
@@ -0,0 +1,31 @@
|
|
1
|
+
/**
|
2
|
+
* Platform detection utilities for cross-platform compatibility
|
3
|
+
*/
|
4
|
+
export declare class OperatingSystemUtils {
|
5
|
+
/**
|
6
|
+
* Detects if the current platform is macOS
|
7
|
+
*/
|
8
|
+
static get isMacOS(): boolean;
|
9
|
+
/**
|
10
|
+
* Detects if the current platform is Windows
|
11
|
+
*/
|
12
|
+
static get isWindows(): boolean;
|
13
|
+
/**
|
14
|
+
* Detects if the current platform is Linux
|
15
|
+
*/
|
16
|
+
static get isLinux(): boolean;
|
17
|
+
/**
|
18
|
+
* Gets the appropriate modifier key symbols for the current platform
|
19
|
+
*/
|
20
|
+
static getModifierSymbols(): {
|
21
|
+
ctrl: string;
|
22
|
+
alt: string;
|
23
|
+
shift: string;
|
24
|
+
meta: string;
|
25
|
+
};
|
26
|
+
/**
|
27
|
+
* Formats a key combination with platform-appropriate symbols
|
28
|
+
*/
|
29
|
+
static formatKeyCombination(key: string, ctrlKey?: boolean, altKey?: boolean, shiftKey?: boolean, metaKey?: boolean): string;
|
30
|
+
}
|
31
|
+
//# sourceMappingURL=os-platform.d.ts.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"os-platform.d.ts","sourceRoot":"","sources":["../../../src/utils/os-platform.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,qBAAa,oBAAoB;IAC/B;;OAEG;IACH,MAAM,KAAK,OAAO,IAAI,OAAO,CAK5B;IAED;;OAEG;IACH,MAAM,KAAK,SAAS,IAAI,OAAO,CAK9B;IAED;;OAEG;IACH,MAAM,KAAK,OAAO,IAAI,OAAO,CAK5B;IAED;;OAEG;IACH,MAAM,CAAC,kBAAkB,IAAI;QAC3B,IAAI,EAAE,MAAM,CAAC;QACb,GAAG,EAAE,MAAM,CAAC;QACZ,KAAK,EAAE,MAAM,CAAC;QACd,IAAI,EAAE,MAAM,CAAC;KACd;IAkBD;;OAEG;IACH,MAAM,CAAC,oBAAoB,CACzB,GAAG,EAAE,MAAM,EACX,OAAO,UAAQ,EACf,MAAM,UAAQ,EACd,QAAQ,UAAQ,EAChB,OAAO,UAAQ,GACd,MAAM;CAcV"}
|
package/dist/esm/index.js
CHANGED
@@ -0,0 +1,140 @@
|
|
1
|
+
import { __decorate } from "tslib";
|
2
|
+
import { customElement, FASTElement } from '@microsoft/fast-element';
|
3
|
+
import { inject } from '@microsoft/fast-foundation';
|
4
|
+
import { ShortcutManager } from './shortcut-manager';
|
5
|
+
/**
|
6
|
+
* A custom element that listens for keyboard shortcuts.
|
7
|
+
* @public
|
8
|
+
* @remarks Part of the ShortcutManager Service.
|
9
|
+
*/
|
10
|
+
let FoundationShortcutListener = class FoundationShortcutListener extends FASTElement {
|
11
|
+
constructor() {
|
12
|
+
super(...arguments);
|
13
|
+
this.keyListener = null;
|
14
|
+
this.isListening = false;
|
15
|
+
}
|
16
|
+
connectedCallback() {
|
17
|
+
super.connectedCallback();
|
18
|
+
this.setupStateSubscription();
|
19
|
+
}
|
20
|
+
disconnectedCallback() {
|
21
|
+
super.disconnectedCallback();
|
22
|
+
this.removeKeyListener();
|
23
|
+
}
|
24
|
+
setupStateSubscription() {
|
25
|
+
// Subscribe to the pause state changes
|
26
|
+
this.shortcutManager.isPaused$.subscribe((isPaused) => {
|
27
|
+
if (isPaused) {
|
28
|
+
this.removeKeyListener();
|
29
|
+
}
|
30
|
+
else {
|
31
|
+
this.addKeyListener();
|
32
|
+
}
|
33
|
+
});
|
34
|
+
// Set initial state
|
35
|
+
if (!this.shortcutManager.isPaused) {
|
36
|
+
this.addKeyListener();
|
37
|
+
}
|
38
|
+
}
|
39
|
+
addKeyListener() {
|
40
|
+
if (this.isListening)
|
41
|
+
return;
|
42
|
+
this.keyListener = this.handleKeyDown.bind(this);
|
43
|
+
document.addEventListener('keydown', this.keyListener);
|
44
|
+
this.isListening = true;
|
45
|
+
}
|
46
|
+
removeKeyListener() {
|
47
|
+
if (!this.isListening || !this.keyListener)
|
48
|
+
return;
|
49
|
+
document.removeEventListener('keydown', this.keyListener);
|
50
|
+
this.keyListener = null;
|
51
|
+
this.isListening = false;
|
52
|
+
}
|
53
|
+
handleKeyDown(event) {
|
54
|
+
// Don't handle shortcuts if the service is paused
|
55
|
+
if (this.shortcutManager.isPaused) {
|
56
|
+
return;
|
57
|
+
}
|
58
|
+
// Don't handle shortcuts if user is typing in an input field
|
59
|
+
if (this.isInputElement(event.target)) {
|
60
|
+
return;
|
61
|
+
}
|
62
|
+
// Extract key from event.code with proper mapping for all key types
|
63
|
+
const key = this.extractKeyFromCode(event.code);
|
64
|
+
const shortcut = this.shortcutManager.findShortcutByKeyCombination(key, event.ctrlKey, event.altKey, event.shiftKey, event.metaKey);
|
65
|
+
if (shortcut) {
|
66
|
+
event.preventDefault();
|
67
|
+
event.stopPropagation();
|
68
|
+
this.shortcutManager.executeShortcut(shortcut.id);
|
69
|
+
}
|
70
|
+
}
|
71
|
+
extractKeyFromCode(code) {
|
72
|
+
// Handle regular letter keys (KeyA, KeyB, etc.)
|
73
|
+
if (code.startsWith('Key')) {
|
74
|
+
return code.replace('Key', '').toLowerCase();
|
75
|
+
}
|
76
|
+
// Handle digit keys (Digit0, Digit1, etc.)
|
77
|
+
if (code.startsWith('Digit')) {
|
78
|
+
return code.replace('Digit', '');
|
79
|
+
}
|
80
|
+
// Handle special keys with direct mapping
|
81
|
+
const specialKeyMap = {
|
82
|
+
Space: 'space',
|
83
|
+
Enter: 'enter',
|
84
|
+
Escape: 'escape',
|
85
|
+
Tab: 'tab',
|
86
|
+
Backspace: 'backspace',
|
87
|
+
Delete: 'delete',
|
88
|
+
Insert: 'insert',
|
89
|
+
Home: 'home',
|
90
|
+
End: 'end',
|
91
|
+
PageUp: 'pageup',
|
92
|
+
PageDown: 'pagedown',
|
93
|
+
ArrowUp: 'arrowup',
|
94
|
+
ArrowDown: 'arrowdown',
|
95
|
+
ArrowLeft: 'arrowleft',
|
96
|
+
ArrowRight: 'arrowright',
|
97
|
+
F1: 'f1',
|
98
|
+
F2: 'f2',
|
99
|
+
F3: 'f3',
|
100
|
+
F4: 'f4',
|
101
|
+
F5: 'f5',
|
102
|
+
F6: 'f6',
|
103
|
+
F7: 'f7',
|
104
|
+
F8: 'f8',
|
105
|
+
F9: 'f9',
|
106
|
+
F10: 'f10',
|
107
|
+
F11: 'f11',
|
108
|
+
F12: 'f12',
|
109
|
+
};
|
110
|
+
return specialKeyMap[code] || code.toLowerCase();
|
111
|
+
}
|
112
|
+
isInputElement(element) {
|
113
|
+
if (!element)
|
114
|
+
return false;
|
115
|
+
const inputTypes = ['input', 'textarea', 'select'];
|
116
|
+
const tagName = element.tagName.toLowerCase();
|
117
|
+
if (inputTypes.includes(tagName)) {
|
118
|
+
return true;
|
119
|
+
}
|
120
|
+
// Check for contenteditable
|
121
|
+
if (element.contentEditable === 'true') {
|
122
|
+
return true;
|
123
|
+
}
|
124
|
+
// Check for role="textbox" or similar
|
125
|
+
const role = element.getAttribute('role');
|
126
|
+
if (role && ['textbox', 'searchbox', 'combobox'].includes(role)) {
|
127
|
+
return true;
|
128
|
+
}
|
129
|
+
return false;
|
130
|
+
}
|
131
|
+
};
|
132
|
+
__decorate([
|
133
|
+
inject(ShortcutManager)
|
134
|
+
], FoundationShortcutListener.prototype, "shortcutManager", void 0);
|
135
|
+
FoundationShortcutListener = __decorate([
|
136
|
+
customElement({
|
137
|
+
name: 'foundation-shortcut-listener',
|
138
|
+
})
|
139
|
+
], FoundationShortcutListener);
|
140
|
+
export { FoundationShortcutListener };
|
@@ -0,0 +1,286 @@
|
|
1
|
+
import { DI } from '@microsoft/fast-foundation';
|
2
|
+
import { BehaviorSubject } from 'rxjs';
|
3
|
+
import { logger } from '../utils';
|
4
|
+
import { OperatingSystemUtils } from '../utils/os-platform';
|
5
|
+
/**
|
6
|
+
* Default implementation of the ShortcutManager interface
|
7
|
+
* @public
|
8
|
+
*/
|
9
|
+
export class DefaultShortcutManager {
|
10
|
+
constructor() {
|
11
|
+
this.shortcuts = new Map(); // context -> id -> ShortcutDefinition
|
12
|
+
this.shortcutLookup = new Map(); // context:id -> ShortcutDefinition for quick lookups
|
13
|
+
this.keyCombinationMap = new Map(); // key combination -> set of "context:id" strings
|
14
|
+
this._isPausedSubject = new BehaviorSubject(false);
|
15
|
+
}
|
16
|
+
get isPaused() {
|
17
|
+
return this._isPausedSubject.value;
|
18
|
+
}
|
19
|
+
get isPaused$() {
|
20
|
+
return this._isPausedSubject.asObservable();
|
21
|
+
}
|
22
|
+
get isPausedSubject() {
|
23
|
+
return this._isPausedSubject;
|
24
|
+
}
|
25
|
+
registerShortcuts(shortcuts) {
|
26
|
+
shortcuts.forEach((shortcut) => {
|
27
|
+
this.registerShortcut(shortcut);
|
28
|
+
});
|
29
|
+
}
|
30
|
+
registerShortcut(shortcut) {
|
31
|
+
const compositeKey = `${shortcut.context}:${shortcut.id}`;
|
32
|
+
// Normalize shortcut definition: handle option/alt equivalence
|
33
|
+
const normalizedShortcut = this.normalizeShortcutDefinition(shortcut);
|
34
|
+
// Check if there's already a shortcut with the same key combination
|
35
|
+
const keyCombo = this.createKeyCombinationKey(normalizedShortcut.key, normalizedShortcut.ctrlKey, normalizedShortcut.altKey, normalizedShortcut.shiftKey, normalizedShortcut.metaKey);
|
36
|
+
// Create platform-friendly display format
|
37
|
+
const keyCombinationDisplay = OperatingSystemUtils.formatKeyCombination(normalizedShortcut.key, normalizedShortcut.ctrlKey, normalizedShortcut.altKey, normalizedShortcut.shiftKey, normalizedShortcut.metaKey);
|
38
|
+
const existingShortcutIds = this.keyCombinationMap.get(keyCombo);
|
39
|
+
if (existingShortcutIds) {
|
40
|
+
// Check if we should replace any existing shortcuts
|
41
|
+
const shortcutsToRemove = [];
|
42
|
+
for (const existingCompositeId of existingShortcutIds) {
|
43
|
+
const existingShortcut = this.shortcutLookup.get(existingCompositeId);
|
44
|
+
if (existingShortcut) {
|
45
|
+
// Replace if same context (prevents conflicts within same component/page)
|
46
|
+
if (existingShortcut.context === normalizedShortcut.context) {
|
47
|
+
// Log warning about shortcut replacement
|
48
|
+
logger.warn(`Shortcut with key combination '${keyCombo}' already exists in context '${normalizedShortcut.context}' (id: '${existingShortcut.id}'). It will be replaced by new shortcut '${normalizedShortcut.id}'.`);
|
49
|
+
shortcutsToRemove.push(existingCompositeId);
|
50
|
+
}
|
51
|
+
}
|
52
|
+
}
|
53
|
+
// Remove shortcuts that should be replaced
|
54
|
+
shortcutsToRemove.forEach((compositeId) => {
|
55
|
+
const shortcutToRemove = this.shortcutLookup.get(compositeId);
|
56
|
+
if (shortcutToRemove) {
|
57
|
+
const contextMap = this.shortcuts.get(shortcutToRemove.context);
|
58
|
+
if (contextMap) {
|
59
|
+
contextMap.delete(shortcutToRemove.id);
|
60
|
+
if (contextMap.size === 0) {
|
61
|
+
this.shortcuts.delete(shortcutToRemove.context);
|
62
|
+
}
|
63
|
+
}
|
64
|
+
this.shortcutLookup.delete(compositeId);
|
65
|
+
}
|
66
|
+
existingShortcutIds.delete(compositeId);
|
67
|
+
});
|
68
|
+
// If no shortcuts remain for this key combination, remove the entry
|
69
|
+
if (existingShortcutIds.size === 0) {
|
70
|
+
this.keyCombinationMap.delete(keyCombo);
|
71
|
+
}
|
72
|
+
}
|
73
|
+
// Register the new shortcut
|
74
|
+
if (!this.shortcuts.has(normalizedShortcut.context)) {
|
75
|
+
this.shortcuts.set(normalizedShortcut.context, new Map());
|
76
|
+
}
|
77
|
+
this.shortcuts.get(normalizedShortcut.context).set(normalizedShortcut.id, normalizedShortcut);
|
78
|
+
this.shortcutLookup.set(compositeKey, normalizedShortcut);
|
79
|
+
// Add to key combination map
|
80
|
+
if (!this.keyCombinationMap.has(keyCombo)) {
|
81
|
+
this.keyCombinationMap.set(keyCombo, new Set());
|
82
|
+
}
|
83
|
+
this.keyCombinationMap.get(keyCombo).add(compositeKey);
|
84
|
+
return {
|
85
|
+
shortcut: normalizedShortcut,
|
86
|
+
id: normalizedShortcut.id,
|
87
|
+
keyCombination: keyCombo,
|
88
|
+
keyCombinationDisplay,
|
89
|
+
// Functions that can be directly used in AG Grid menu items
|
90
|
+
disabled: () => {
|
91
|
+
if (this.isPaused)
|
92
|
+
return true;
|
93
|
+
if (normalizedShortcut.canExecute) {
|
94
|
+
const status = normalizedShortcut.canExecute();
|
95
|
+
return status.disabled || false;
|
96
|
+
}
|
97
|
+
return false;
|
98
|
+
},
|
99
|
+
tooltip: () => {
|
100
|
+
if (this.isPaused)
|
101
|
+
return 'Shortcuts are paused';
|
102
|
+
if (normalizedShortcut.canExecute) {
|
103
|
+
const status = normalizedShortcut.canExecute();
|
104
|
+
return status.tooltip;
|
105
|
+
}
|
106
|
+
return undefined;
|
107
|
+
},
|
108
|
+
};
|
109
|
+
}
|
110
|
+
unregisterShortcut(context, id) {
|
111
|
+
const compositeKey = `${context}:${id}`;
|
112
|
+
const contextMap = this.shortcuts.get(context);
|
113
|
+
if (contextMap) {
|
114
|
+
const shortcut = contextMap.get(id);
|
115
|
+
if (shortcut) {
|
116
|
+
// Normalize the shortcut to ensure consistent key combination
|
117
|
+
const normalizedShortcut = this.normalizeShortcutDefinition(shortcut);
|
118
|
+
const keyCombo = this.createKeyCombinationKey(normalizedShortcut.key, normalizedShortcut.ctrlKey, normalizedShortcut.altKey, normalizedShortcut.shiftKey, normalizedShortcut.metaKey);
|
119
|
+
// Remove from shortcuts map
|
120
|
+
contextMap.delete(id);
|
121
|
+
if (contextMap.size === 0) {
|
122
|
+
this.shortcuts.delete(context);
|
123
|
+
}
|
124
|
+
// Remove from lookup map
|
125
|
+
this.shortcutLookup.delete(compositeKey);
|
126
|
+
// Remove from key combination map
|
127
|
+
const shortcutIds = this.keyCombinationMap.get(keyCombo);
|
128
|
+
if (shortcutIds) {
|
129
|
+
shortcutIds.delete(compositeKey);
|
130
|
+
if (shortcutIds.size === 0) {
|
131
|
+
this.keyCombinationMap.delete(keyCombo);
|
132
|
+
}
|
133
|
+
}
|
134
|
+
}
|
135
|
+
}
|
136
|
+
}
|
137
|
+
unregisterShortcutsByContext(context) {
|
138
|
+
const contextMap = this.shortcuts.get(context);
|
139
|
+
if (contextMap) {
|
140
|
+
const shortcutIds = Array.from(contextMap.keys());
|
141
|
+
shortcutIds.forEach((id) => this.unregisterShortcut(context, id));
|
142
|
+
}
|
143
|
+
}
|
144
|
+
executeShortcut(id) {
|
145
|
+
this.executeShortcutByContext(this.getActiveContext(), id);
|
146
|
+
}
|
147
|
+
executeShortcutByContext(context, id) {
|
148
|
+
if (this.isPaused) {
|
149
|
+
return; // Don't execute shortcuts when paused
|
150
|
+
}
|
151
|
+
const contextMap = this.shortcuts.get(context);
|
152
|
+
if (contextMap) {
|
153
|
+
const shortcut = contextMap.get(id);
|
154
|
+
if (shortcut) {
|
155
|
+
// Check if shortcut requires a specific element to be focused
|
156
|
+
if (shortcut.elementRef && !this.isElementFocused(shortcut.elementRef)) {
|
157
|
+
return; // Don't execute if the required element is not focused
|
158
|
+
}
|
159
|
+
// Check if shortcut can be executed
|
160
|
+
if (shortcut.canExecute) {
|
161
|
+
const executionStatus = shortcut.canExecute();
|
162
|
+
if (executionStatus.disabled) {
|
163
|
+
return; // Don't execute if disabled
|
164
|
+
}
|
165
|
+
}
|
166
|
+
try {
|
167
|
+
shortcut.action();
|
168
|
+
}
|
169
|
+
catch (error) {
|
170
|
+
logger.error(`Error executing shortcut ${context}:${id}:`, error);
|
171
|
+
}
|
172
|
+
}
|
173
|
+
}
|
174
|
+
}
|
175
|
+
getShortcuts() {
|
176
|
+
const allShortcuts = [];
|
177
|
+
// Iterate through all contexts and collect all shortcuts
|
178
|
+
for (const contextMap of this.shortcuts.values()) {
|
179
|
+
allShortcuts.push(...contextMap.values());
|
180
|
+
}
|
181
|
+
return allShortcuts;
|
182
|
+
}
|
183
|
+
getShortcutsByContext(context) {
|
184
|
+
const contextMap = this.shortcuts.get(context);
|
185
|
+
return contextMap ? Array.from(contextMap.values()) : [];
|
186
|
+
}
|
187
|
+
findShortcutByKeyCombination(key, ctrlKey = false, altKey = false, shiftKey = false, metaKey = false) {
|
188
|
+
const keyCombo = this.createKeyCombinationKey(key, ctrlKey, altKey, shiftKey, metaKey);
|
189
|
+
const shortcutIds = this.keyCombinationMap.get(keyCombo);
|
190
|
+
if (!shortcutIds) {
|
191
|
+
return undefined;
|
192
|
+
}
|
193
|
+
// First, try to find a shortcut in the active context if one is set
|
194
|
+
if (this._activeContext) {
|
195
|
+
const activeContextMap = this.shortcuts.get(this._activeContext);
|
196
|
+
if (!activeContextMap) {
|
197
|
+
// Continue to search all shortcuts
|
198
|
+
}
|
199
|
+
else {
|
200
|
+
for (const compositeId of shortcutIds) {
|
201
|
+
const [context, id] = compositeId.split(':');
|
202
|
+
if (context !== this._activeContext)
|
203
|
+
continue;
|
204
|
+
const shortcut = activeContextMap.get(id);
|
205
|
+
if (shortcut) {
|
206
|
+
return shortcut;
|
207
|
+
}
|
208
|
+
}
|
209
|
+
}
|
210
|
+
}
|
211
|
+
// If no active context or no shortcut found in active context,
|
212
|
+
// return the first shortcut found for this key combination
|
213
|
+
for (const compositeId of shortcutIds) {
|
214
|
+
const shortcut = this.shortcutLookup.get(compositeId);
|
215
|
+
if (shortcut) {
|
216
|
+
return shortcut;
|
217
|
+
}
|
218
|
+
}
|
219
|
+
return undefined;
|
220
|
+
}
|
221
|
+
getContexts() {
|
222
|
+
return Array.from(this.shortcuts.keys());
|
223
|
+
}
|
224
|
+
getShortcutsByContextMap() {
|
225
|
+
return new Map(this.shortcuts);
|
226
|
+
}
|
227
|
+
registerContext(context) {
|
228
|
+
if (!this.shortcuts.has(context)) {
|
229
|
+
this.shortcuts.set(context, new Map());
|
230
|
+
}
|
231
|
+
}
|
232
|
+
setActiveContext(context) {
|
233
|
+
this.registerContext(context);
|
234
|
+
this._activeContext = context;
|
235
|
+
}
|
236
|
+
getActiveContext() {
|
237
|
+
return this._activeContext;
|
238
|
+
}
|
239
|
+
clearActiveContext() {
|
240
|
+
this._activeContext = undefined;
|
241
|
+
}
|
242
|
+
pause() {
|
243
|
+
this._isPausedSubject.next(true);
|
244
|
+
}
|
245
|
+
resume() {
|
246
|
+
this._isPausedSubject.next(false);
|
247
|
+
}
|
248
|
+
/**
|
249
|
+
* Normalizes a shortcut definition to handle option/alt equivalence
|
250
|
+
* If optionKey is set, altKey will also be set to true (and vice versa)
|
251
|
+
*/
|
252
|
+
normalizeShortcutDefinition(shortcut) {
|
253
|
+
const normalized = Object.assign({}, shortcut);
|
254
|
+
// Handle option/alt equivalence
|
255
|
+
if (normalized.optionKey || normalized.altKey) {
|
256
|
+
normalized.altKey = true;
|
257
|
+
normalized.optionKey = true;
|
258
|
+
}
|
259
|
+
return normalized;
|
260
|
+
}
|
261
|
+
createKeyCombinationKey(key, ctrlKey = false, altKey = false, shiftKey = false, metaKey = false) {
|
262
|
+
const modifiers = [];
|
263
|
+
if (ctrlKey)
|
264
|
+
modifiers.push('ctrl');
|
265
|
+
if (altKey)
|
266
|
+
modifiers.push('alt');
|
267
|
+
if (shiftKey)
|
268
|
+
modifiers.push('shift');
|
269
|
+
if (metaKey)
|
270
|
+
modifiers.push('meta');
|
271
|
+
// Create a consistent format like "ctrl+alt+s" instead of "ctrl+alt:s"
|
272
|
+
const keyCombo = modifiers.length > 0 ? `${modifiers.join('+')}+${key}` : key;
|
273
|
+
return keyCombo.toLowerCase();
|
274
|
+
}
|
275
|
+
isElementFocused(element) {
|
276
|
+
if (element instanceof HTMLElement) {
|
277
|
+
return document.activeElement === element;
|
278
|
+
}
|
279
|
+
return false;
|
280
|
+
}
|
281
|
+
}
|
282
|
+
/**
|
283
|
+
* A dependency injection token for the ShortcutManager interface.
|
284
|
+
* @public
|
285
|
+
*/
|
286
|
+
export const ShortcutManager = DI.createInterface((x) => x.singleton(DefaultShortcutManager));
|