@keybindy/core
Advanced tools
| var Keybindy=function(){"use strict";const e={ctrl:["ctrl (left)","ctrl (right)"],shift:["shift (left)","shift (right)"],alt:["alt (left)","alt (right)"],meta:["meta (left)","meta (right)","cmd"]};function t(t){const s=[[]];for(const o of t){const t=o.toLowerCase(),i=e[t]??[t],n=[];for(const e of s)for(const t of i)n.push([...e,t]);s.splice(0,s.length,...n)}return s}const s={ControlLeft:"Ctrl (Left)",ControlRight:"Ctrl (Right)",ShiftLeft:"Shift (Left)",ShiftRight:"Shift (Right)",AltLeft:"Alt (Left)",AltRight:"Alt (Right)",MetaLeft:"Meta (Left)",MetaRight:"Meta (Right)",OSLeft:"Meta (Left)",OSRight:"Meta (Right)",KeyA:"A",KeyB:"B",KeyC:"C",KeyD:"D",KeyE:"E",KeyF:"F",KeyG:"G",KeyH:"H",KeyI:"I",KeyJ:"J",KeyK:"K",KeyL:"L",KeyM:"M",KeyN:"N",KeyO:"O",KeyP:"P",KeyQ:"Q",KeyR:"R",KeyS:"S",KeyT:"T",KeyU:"U",KeyV:"V",KeyW:"W",KeyX:"X",KeyY:"Y",KeyZ:"Z",Digit0:"0",Digit1:"1",Digit2:"2",Digit3:"3",Digit4:"4",Digit5:"5",Digit6:"6",Digit7:"7",Digit8:"8",Digit9:"9",Numpad0:"Numpad 0",Numpad1:"Numpad 1",Numpad2:"Numpad 2",Numpad3:"Numpad 3",Numpad4:"Numpad 4",Numpad5:"Numpad 5",Numpad6:"Numpad 6",Numpad7:"Numpad 7",Numpad8:"Numpad 8",Numpad9:"Numpad 9",NumpadAdd:"Numpad +",NumpadSubtract:"Numpad -",NumpadMultiply:"Numpad *",NumpadDivide:"Numpad /",NumpadEnter:"Numpad Enter",NumpadDecimal:"Numpad .",NumpadEqual:"Numpad =",NumpadComma:"Numpad ,",NumpadParenLeft:"Numpad (",NumpadParenRight:"Numpad )",Minus:"-",Equal:"=",BracketLeft:"[",BracketRight:"]",Backslash:"\\",Semicolon:";",Quote:"'",Comma:",",Period:".",Slash:"/",Backquote:"`",IntlBackslash:"Intl \\",IntlRo:"Intl Ro",IntlYen:"Intl Yen",Escape:"Esc",Tab:"Tab",CapsLock:"Caps Lock",Enter:"Enter",Space:"Space",Backspace:"Backspace",NumLock:"Num Lock",ScrollLock:"Scroll Lock",Pause:"Pause",ContextMenu:"Context Menu",PrintScreen:"Print Screen",Insert:"Insert",Delete:"Delete",Home:"Home",End:"End",PageUp:"Page Up",PageDown:"Page Down",ArrowUp:"Arrow Up",ArrowDown:"Arrow Down",ArrowLeft:"Arrow Left",ArrowRight:"Arrow Right",F1:"F1",F2:"F2",F3:"F3",F4:"F4",F5:"F5",F6:"F6",F7:"F7",F8:"F8",F9:"F9",F10:"F10",F11:"F11",F12:"F12",F13:"F13",F14:"F14",F15:"F15",F16:"F16",F17:"F17",F18:"F18",F19:"F19",F20:"F20",F21:"F21",F22:"F22",F23:"F23",F24:"F24",AudioVolumeMute:"Volume Mute",AudioVolumeDown:"Volume Down",AudioVolumeUp:"Volume Up",VolumeMute:"Volume Mute",VolumeDown:"Volume Down",VolumeUp:"Volume Up",MediaTrackNext:"Media Next Track",MediaTrackPrevious:"Media Previous Track",MediaPlayPause:"Media Play/Pause",MediaStop:"Media Stop",MediaSelect:"Media Select",BrowserHome:"Browser Home",BrowserSearch:"Browser Search",BrowserFavorites:"Browser Favorites",BrowserRefresh:"Browser Refresh",BrowserStop:"Browser Stop",BrowserForward:"Browser Forward",BrowserBack:"Browser Back",LaunchApp1:"Launch App 1",LaunchApp2:"Launch App 2",LaunchMail:"Launch Mail",LaunchMediaPlayer:"Launch Media Player",LaunchCalculator:"Launch Calculator",Convert:"Convert",NonConvert:"Non Convert",KanaMode:"Kana Mode",Lang1:"Language 1",Lang2:"Language 2",Lang3:"Language 3",Lang4:"Language 4",Lang5:"Language 5",Power:"Power",Sleep:"Sleep",WakeUp:"Wake Up",Eject:"Eject",Undo:"Undo",Redo:"Redo",Copy:"Copy",Cut:"Cut",Paste:"Paste",Select:"Select",Again:"Again",Find:"Find",Open:"Open",Props:"Properties",Help:"Help",Fn:"Fn",BrightnessUp:"Brightness Up",BrightnessDown:"Brightness Down"};function o(e){return s[e].toLowerCase()||e.toLowerCase()}class i{silent;constructor(e={}){this.silent=e.silent||!1}log(e,t={}){this.silent||t.silent||console.log("[Keybindy]",e)}warn(e,t={}){this.silent||t.silent||console.warn("[Keybindy]",e)}error(e,t={}){this.silent||t.silent||console.error("[Keybindy]",e)}}new i;const n=(r="warn",(e,t={})=>{t.silent||console[r]("[Keybindy]",e)});var r;class a{scopeStack=["global"];pushScope(e){e&&(this.scopeStack.includes(e)||this.scopeStack.push(e))}popScope(){this.scopeStack.length>1&&this.scopeStack.pop()}swap(e,t){const s=this.scopeStack[t];this.scopeStack[t]=e,this.scopeStack[this.scopeStack.length-1]=s}setActiveScope(e){if(!e)return;if(!this.scopeStack.includes(e))return void n("Scope not found: "+e);const t=this.scopeStack.indexOf(e);-1!==t&&this.swap(this.getActiveScope(),t)}resetScope(){this.scopeStack=["global"]}getActiveScope(){return this.scopeStack[this.scopeStack.length-1]}isScopeActive(e){return this.getActiveScope()===(e||"global")}getScopes(){return[...this.scopeStack]}}class c{listeners=[];on(e){return this.listeners.push(e),()=>this.off(e)}off(e){this.listeners=this.listeners.filter(t=>t!==e)}emit(e){this.listeners.forEach(t=>t(e))}}return class extends a{shortcuts=[];pressedKeys=new Set;activeHoldShortcuts=new Set;typingEmitter=new c;activeSequences=[];onShortcutFired=()=>{};logger=new i;constructor({onShortcutFired:e,silent:t=!1}={}){if(super(),this.onShortcutFired=e||(()=>{}),this.logger=new i({silent:t}),"undefined"!=typeof window)this.start();else if("test"!==process.env.NODE_ENV)throw new Error("[Keybindy] Unsupported environment")}start(){window.addEventListener("keydown",this.handleKeyDown),window.addEventListener("keyup",this.handleKeyUp)}disableAll(e){e?this.shortcuts.forEach(t=>t.options?.scope===e?t.enabled=!1:null):this.shortcuts.forEach(e=>e.enabled=!1)}enableAll(e){e?this.shortcuts.forEach(t=>t.options?.scope===e?t.enabled=!0:null):this.shortcuts.forEach(e=>e.enabled=!0)}onTyping(e){return this.typingEmitter.on(e)}handleKeyDown=e=>{const t=o(e.code).toLowerCase(),s=Date.now();e.repeat||this.pressedKeys.add(t),this.typingEmitter.emit({key:e.key,event:e});const i=[];let n=!1,r=!1;for(const o of this.shortcuts){if(!o.enabled||(o.options?.scope||"global")!==this.getActiveScope())continue;const a=o.keys.map(e=>e.toLowerCase()),c=a.every(e=>this.pressedKeys.has(e));if(o.options?.hold){if(c&&!this.activeHoldShortcuts.has(o.id)){if(e.repeat&&!o.options.repeat)continue;o.options.preventDefault&&e.preventDefault(),o.handler(e,"down"),this.activeHoldShortcuts.add(o.id),this.onShortcutFired(o),r=!0}}else if(o.options?.sequential){if(e.repeat)continue;const i=o.options.sequenceDelay??1e3;let r=this.activeSequences.find(e=>JSON.stringify(e.keys)===JSON.stringify(a));if(r){r.buffer.push({key:t,time:s}),r.buffer=r.buffer.filter(e=>s-e.time<=i);const c=r.buffer.map(e=>e.key);a.every((e,t)=>c[t]===e)&&a.length===c.length&&(o.options.preventDefault&&e.preventDefault(),o.handler(e),this.onShortcutFired(o),this.clearSequence(r.keys),n=!0)}else t===a[0]&&(r={keys:a,buffer:[{key:t,time:s}]},this.activeSequences.push(r))}else if(c&&"keydown"===o.options?.triggerOn){if(e.repeat&&!o.options.repeat)continue;i.push(o)}}if(!r&&!n){if(i.length>0){const t=i.reduce((e,t)=>t.keys.length>e.keys.length?t:e);t.options?.preventDefault&&e.preventDefault(),t.handler(e),this.onShortcutFired(t)}this.activeSequences=this.activeSequences.filter(e=>{const t=this.shortcuts.find(t=>JSON.stringify(t.keys)===JSON.stringify(e.keys))?.options?.sequenceDelay??1e3;return s-e.buffer[0]?.time<=t})}};clearSequence(e){this.activeSequences=this.activeSequences.filter(t=>JSON.stringify(t.keys)!==JSON.stringify(e))}handleKeyUp=e=>{const t=o(e.code).toLowerCase();for(const s of this.activeHoldShortcuts){const o=this.shortcuts.find(e=>e.id===s);o&&o.keys.map(e=>e.toLowerCase()).includes(t)&&(o.options?.preventDefault&&e.preventDefault(),o.handler(e,"up"),this.activeHoldShortcuts.delete(s))}const s=[];for(const e of this.shortcuts)if(e.enabled&&(e.options?.scope||"global")===this.getActiveScope()&&"keyup"===e.options?.triggerOn&&!e.options.sequential&&!e.options.hold){const o=e.keys.map(e=>e.toLowerCase());o.filter(e=>e!==t).every(e=>this.pressedKeys.has(e))&&o.includes(t)&&s.push(e)}if(s.length>0){const t=s.reduce((e,t)=>t.keys.length>e.keys.length?t:e);t.options?.preventDefault&&e.preventDefault(),t.handler(e),this.onShortcutFired(t)}this.pressedKeys.delete(t)};register(e,s,o){const i=Array.isArray(e[0])?e:[e],n=o?.data?.id||"uid-"+Date.now().toString(36)+"-"+Math.random().toString(36).substring(2,8);for(const e of i){const i=t(e);for(const e of i){const t=e.map(e=>e.toLowerCase());this.shortcuts=this.shortcuts.filter(e=>JSON.stringify(e.keys)!==JSON.stringify(t)||e.options?.scope!==(o?.scope||this.getActiveScope())||e.id!==n),this.shortcuts.push({id:n,keys:t,handler:s,options:{...o,sequential:o?.sequential||!1,sequenceDelay:o?.sequenceDelay||1e3,scope:o?.scope||this.getActiveScope(),hold:o?.hold||!1,triggerOn:o?.triggerOn||"keydown",repeat:!0===o?.repeat},enabled:!0}),this.pushScope(o?.scope??"global")}}}unregister(e,s="global"){const o=t(e);for(const e of o){const t=e.map(e=>e.toLowerCase());this.shortcuts=this.shortcuts.filter(e=>e.options?.scope!==s||JSON.stringify(e.keys)!==JSON.stringify(t))}}toggleState(e,s,o){const i=t(e);let n=!1;for(const e of i){const t=e.map(e=>e.toLowerCase());this.shortcuts.forEach(e=>{const i=!e.options?.scope||e.options.scope===s;JSON.stringify(e.keys)===JSON.stringify(t)&&i&&(n=!0,e.enabled="toggle"===o?!e.enabled:o)})}n||this.logger.warn(`No matching shortcut for ${JSON.stringify(e)} in scope "${s}"`)}enable(e,t="global"){this.toggleState(e,t,!0)}disable(e,t="global"){this.toggleState(e,t,!1)}toggle(e,t="global"){this.toggleState(e,t,"toggle")}clear(){this.pressedKeys.clear(),this.activeHoldShortcuts.clear(),window.removeEventListener("keydown",this.handleKeyDown),window.removeEventListener("keyup",this.handleKeyUp),this.logger.log("Instance cleared")}destroy(){this.clear(),this.shortcuts=[],this.resetScope(),this.activeSequences=[],this.activeHoldShortcuts.clear(),this.logger.log("Instance destroyed")}getCheatSheet(e=this.getActiveScope()){const t=new Map;for(const s of this.shortcuts){if(s.options?.scope&&s.options.scope!==e)continue;const o=s.id,i=s.keys.map(e=>e.startsWith("ctrl")?"ctrl":e.startsWith("shift")?"shift":e.startsWith("alt")?"alt":e.startsWith("meta")?"meta":e).join(s.options?.sequential?" β ":" + ").toUpperCase();t.has(o)?t.get(o).keys.add(i):t.set(o,{keys:new Set([i]),data:s.options?.data??{}})}return Array.from(t.values()).map(e=>({keys:Array.from(e.keys),...e.data}))}getScopesInfo(e){const t={};for(const s of this.shortcuts){const o=s.options?.scope||"global";e&&o!==e||(t[o]||(t[o]={shortcuts:[]}),t[o].shortcuts.push({keys:s.keys.map(e=>e.toUpperCase()),id:s.id,enabled:s.enabled??!0,data:s.options?.data??{}}),o===this.getActiveScope()&&(t[o].isActive=!0))}return e?t[e]||null:t}}}(); |
+10
-8
@@ -8,4 +8,4 @@ /** | ||
| */ | ||
| type Keys = "Ctrl" | "Ctrl (Left)" | "Ctrl (Right)" | "Shift" | "Shift (Left)" | "Shift (Right)" | "Alt" | "Alt (Left)" | "Alt (Right)" | "Meta" | "Meta (Left)" | "Meta (Right)" | "A" | "B" | "C" | "D" | "E" | "F" | "G" | "H" | "I" | "J" | "K" | "L" | "M" | "N" | "O" | "P" | "Q" | "R" | "S" | "T" | "U" | "V" | "W" | "X" | "Y" | "Z" | "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" | "Numpad 0" | "Numpad 1" | "Numpad 2" | "Numpad 3" | "Numpad 4" | "Numpad 5" | "Numpad 6" | "Numpad 7" | "Numpad 8" | "Numpad 9" | "Numpad +" | "Numpad -" | "Numpad *" | "Numpad /" | "Numpad Enter" | "Numpad ." | "Numpad =" | "Numpad ," | "Numpad (" | "Numpad )" | "-" | "=" | "[" | "]" | "\\" | ";" | "'" | "," | "." | "/" | "`" | "Intl \\" | "Intl Ro" | "Intl Yen" | "Esc" | "Tab" | "Caps Lock" | "Enter" | "Space" | "Backspace" | "Num Lock" | "Scroll Lock" | "Pause" | "Context Menu" | "Print Screen" | "Insert" | "Delete" | "Home" | "End" | "Page Up" | "Page Down" | "Arrow Up" | "Arrow Down" | "Arrow Left" | "Arrow Right" | "F1" | "F2" | "F3" | "F4" | "F5" | "F6" | "F7" | "F8" | "F9" | "F10" | "F11" | "F12" | "F13" | "F14" | "F15" | "F16" | "F17" | "F18" | "F19" | "F20" | "F21" | "F22" | "F23" | "F24" | "Volume Mute" | "Volume Down" | "Volume Up" | "Media Next Track" | "Media Previous Track" | "Media Play/Pause" | "Media Stop" | "Media Select" | "Browser Home" | "Browser Search" | "Browser Favorites" | "Browser Refresh" | "Browser Stop" | "Browser Forward" | "Browser Back" | "Launch App 1" | "Launch App 2" | "Launch Mail" | "Launch Media Player" | "Launch Calculator" | "Convert" | "Non Convert" | "Kana Mode" | "Language 1" | "Language 2" | "Language 3" | "Language 4" | "Language 5" | "Power" | "Sleep" | "Wake Up" | "Eject" | "Undo" | "Redo" | "Copy" | "Cut" | "Paste" | "Select" | "Again" | "Find" | "Open" | "Properties" | "Help" | "Fn" | "Brightness Up" | "Brightness Down"; | ||
| type HoldState = "down" | "up"; | ||
| type Keys = 'Ctrl' | 'Ctrl (Left)' | 'Ctrl (Right)' | 'Shift' | 'Shift (Left)' | 'Shift (Right)' | 'Alt' | 'Alt (Left)' | 'Alt (Right)' | 'Meta' | 'Meta (Left)' | 'Meta (Right)' | 'A' | 'B' | 'C' | 'D' | 'E' | 'F' | 'G' | 'H' | 'I' | 'J' | 'K' | 'L' | 'M' | 'N' | 'O' | 'P' | 'Q' | 'R' | 'S' | 'T' | 'U' | 'V' | 'W' | 'X' | 'Y' | 'Z' | '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9' | 'Numpad 0' | 'Numpad 1' | 'Numpad 2' | 'Numpad 3' | 'Numpad 4' | 'Numpad 5' | 'Numpad 6' | 'Numpad 7' | 'Numpad 8' | 'Numpad 9' | 'Numpad +' | 'Numpad -' | 'Numpad *' | 'Numpad /' | 'Numpad Enter' | 'Numpad .' | 'Numpad =' | 'Numpad ,' | 'Numpad (' | 'Numpad )' | '-' | '=' | '[' | ']' | '\\' | ';' | "'" | ',' | '.' | '/' | '`' | 'Intl \\' | 'Intl Ro' | 'Intl Yen' | 'Esc' | 'Tab' | 'Caps Lock' | 'Enter' | 'Space' | 'Backspace' | 'Num Lock' | 'Scroll Lock' | 'Pause' | 'Context Menu' | 'Print Screen' | 'Insert' | 'Delete' | 'Home' | 'End' | 'Page Up' | 'Page Down' | 'Arrow Up' | 'Arrow Down' | 'Arrow Left' | 'Arrow Right' | 'F1' | 'F2' | 'F3' | 'F4' | 'F5' | 'F6' | 'F7' | 'F8' | 'F9' | 'F10' | 'F11' | 'F12' | 'F13' | 'F14' | 'F15' | 'F16' | 'F17' | 'F18' | 'F19' | 'F20' | 'F21' | 'F22' | 'F23' | 'F24' | 'Volume Mute' | 'Volume Down' | 'Volume Up' | 'Media Next Track' | 'Media Previous Track' | 'Media Play/Pause' | 'Media Stop' | 'Media Select' | 'Browser Home' | 'Browser Search' | 'Browser Favorites' | 'Browser Refresh' | 'Browser Stop' | 'Browser Forward' | 'Browser Back' | 'Launch App 1' | 'Launch App 2' | 'Launch Mail' | 'Launch Media Player' | 'Launch Calculator' | 'Convert' | 'Non Convert' | 'Kana Mode' | 'Language 1' | 'Language 2' | 'Language 3' | 'Language 4' | 'Language 5' | 'Power' | 'Sleep' | 'Wake Up' | 'Eject' | 'Undo' | 'Redo' | 'Copy' | 'Cut' | 'Paste' | 'Select' | 'Again' | 'Find' | 'Open' | 'Properties' | 'Help' | 'Fn' | 'Brightness Up' | 'Brightness Down'; | ||
| type HoldState = 'down' | 'up'; | ||
| type HoldShortcutHandler = (event: KeyboardEvent, state: HoldState) => void; | ||
@@ -27,3 +27,3 @@ /** | ||
| */ | ||
| scope?: "global" | string; | ||
| scope?: 'global' | string; | ||
| /** | ||
@@ -53,3 +53,3 @@ * Enables sequential key combinations. | ||
| */ | ||
| triggerOn?: "keydown" | "keyup"; | ||
| triggerOn?: 'keydown' | 'keyup'; | ||
| /** | ||
@@ -88,5 +88,7 @@ * Controls the behavior of a shortcut when keys are held down. | ||
| /** | ||
| * Single or sequential key combinations for a shortcut. | ||
| * Defines the key combinations that can trigger a shortcut. | ||
| * It can be a single combination (e.g., `['Ctrl', 'S']`) or multiple | ||
| * combinations for the same shortcut (e.g., `[['Ctrl', 'K'], ['Meta', 'K']]`). | ||
| */ | ||
| type KeyBinding = Keys[] | Keys[][]; | ||
| type ShortcutBinding = Keys[] | Keys[][]; | ||
@@ -201,3 +203,3 @@ declare class ScopeManager { | ||
| */ | ||
| register(keys: KeyBinding, handler: ShortcutHandler, options?: ShortcutOptions): void; | ||
| register(binding: ShortcutBinding, handler: ShortcutHandler, options?: ShortcutOptions): void; | ||
| /** | ||
@@ -281,2 +283,2 @@ * Unregisters a previously registered shortcut based on the key combination and scope. | ||
| export { ShortcutManager as default }; | ||
| export type { HoldShortcutHandler, HoldState, KeyBinding, Keys, Shortcut, ShortcutHandler, ShortcutOptions }; | ||
| export type { Keys, Shortcut, ShortcutHandler, ShortcutOptions }; |
@@ -125,3 +125,4 @@ import { expandAliases } from './utils/expandAliases.cjs'; | ||
| } | ||
| else { // Simultaneous | ||
| else { | ||
| // Simultaneous | ||
| if (allMatch && shortcut.options?.triggerOn === 'keydown') { | ||
@@ -209,4 +210,6 @@ if (e.repeat && !shortcut.options.repeat) | ||
| */ | ||
| register(keys, handler, options) { | ||
| const bindings = Array.isArray(keys[0]) ? keys : [keys]; | ||
| register(binding, handler, options) { | ||
| const bindings = Array.isArray(binding[0]) | ||
| ? binding | ||
| : [binding]; | ||
| const id = options?.data?.id || generateUID(); | ||
@@ -213,0 +216,0 @@ for (const binding of bindings) { |
@@ -125,3 +125,4 @@ import { expandAliases } from './utils/expandAliases.js'; | ||
| } | ||
| else { // Simultaneous | ||
| else { | ||
| // Simultaneous | ||
| if (allMatch && shortcut.options?.triggerOn === 'keydown') { | ||
@@ -209,4 +210,6 @@ if (e.repeat && !shortcut.options.repeat) | ||
| */ | ||
| register(keys, handler, options) { | ||
| const bindings = Array.isArray(keys[0]) ? keys : [keys]; | ||
| register(binding, handler, options) { | ||
| const bindings = Array.isArray(binding[0]) | ||
| ? binding | ||
| : [binding]; | ||
| const id = options?.data?.id || generateUID(); | ||
@@ -213,0 +216,0 @@ for (const binding of bindings) { |
+1
-1
| { | ||
| "name": "@keybindy/core", | ||
| "version": "1.1.3", | ||
| "version": "1.1.4", | ||
| "description": "A lightweight and framework-agnostic keyboard shortcut manager for web apps. Define, register, and handle keybindings with ease.", | ||
@@ -5,0 +5,0 @@ "author": { |
+12
-12
@@ -172,12 +172,12 @@ # Keybindy | ||
| | Option | Type | Default | Description | | ||
| | --------------- | --------- | ----------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | ||
| | `scope` | `string` | `"global"` | The scope in which the shortcut is active. | | ||
| | `preventDefault`| `boolean` | `false` | If `true`, calls `event.preventDefault()` to block the browser's default action. | | ||
| | `sequential` | `boolean` | `false` | If `true`, treats the key combination as a sequence (e.g., `G` then `H`). | | ||
| | `sequenceDelay` | `number` | `1000` | The maximum time (in ms) between key presses for a sequential shortcut. | | ||
| | `triggerOn` | `string` | `"keydown"` | For simultaneous shortcuts, specifies whether to trigger on `"keydown"` or `"keyup"`. | | ||
| | `hold` | `boolean` | `false` | If `true`, treats the shortcut as a "hold" action. The handler will be called on both key down and key up with a `state` argument (`"down"` or `"up"`). | | ||
| | `repeat` | `boolean` | `false` | If `true`, allows the shortcut to be repeatedly fired when the key is held down. By default, shortcuts only fire once. | | ||
| | `data` | `object` | `{}` | An object for any custom metadata you want to associate with the shortcut, useful for building features like cheat sheets. | | ||
| | Option | Type | Default | Description | | ||
| | ---------------- | --------- | ----------- | ------------------------------------------------------------------------------------------------------------------------------------------------------- | | ||
| | `scope` | `string` | `"global"` | The scope in which the shortcut is active. | | ||
| | `preventDefault` | `boolean` | `false` | If `true`, calls `event.preventDefault()` to block the browser's default action. | | ||
| | `sequential` | `boolean` | `false` | If `true`, treats the key combination as a sequence (e.g., `G` then `H`). | | ||
| | `sequenceDelay` | `number` | `1000` | The maximum time (in ms) between key presses for a sequential shortcut. | | ||
| | `triggerOn` | `string` | `"keydown"` | For simultaneous shortcuts, specifies whether to trigger on `"keydown"` or `"keyup"`. | | ||
| | `hold` | `boolean` | `false` | If `true`, treats the shortcut as a "hold" action. The handler will be called on both key down and key up with a `state` argument (`"down"` or `"up"`). | | ||
| | `repeat` | `boolean` | `false` | If `true`, allows the shortcut to be repeatedly fired when the key is held down. By default, shortcuts only fire once. | | ||
| | `data` | `object` | `{}` | An object for any custom metadata you want to associate with the shortcut, useful for building features like cheat sheets. | | ||
@@ -445,6 +445,6 @@ --- | ||
| manager.register( | ||
| ['Ctrl', 'Shift'], | ||
| ['Ctrl', 'Shift'], | ||
| (event, state) => { | ||
| console.log(`Mic is ${state === 'down' ? 'on' : 'off'}`); | ||
| }, | ||
| }, | ||
| { hold: true } | ||
@@ -451,0 +451,0 @@ ); |
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 1 instance in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 1 instance in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
87451
13.46%23
4.55%1810
2.72%0
-100%1
Infinity%