type ShortcutHandler = { key: string; ctrl?: boolean; shift?: boolean; handler: () => void; when?: () => boolean; }; let registered = false; let shortcuts: ShortcutHandler[] = []; let cleanup: (() => void) | null = null; export function setShortcuts(handlers: ShortcutHandler[]) { shortcuts = handlers; } export function registerShortcuts() { if (registered) return; registered = true; const onKeyDown = (e: KeyboardEvent) => { // skip when typing in inputs const tag = (e.target as HTMLElement)?.tagName; if (tag === 'INPUT' || tag === 'TEXTAREA' || tag === 'SELECT') return; for (const s of shortcuts) { const ctrlMatch = s.ctrl ? (e.ctrlKey || e.metaKey) : !(e.ctrlKey || e.metaKey); const shiftMatch = s.shift ? e.shiftKey : !e.shiftKey; const keyMatch = e.key === s.key || e.code === s.key; if (keyMatch && ctrlMatch && shiftMatch) { if (s.when && !s.when()) continue; e.preventDefault(); s.handler(); return; } } }; window.addEventListener('keydown', onKeyDown); cleanup = () => { window.removeEventListener('keydown', onKeyDown); registered = false; }; } export function unregisterShortcuts() { cleanup?.(); cleanup = null; shortcuts = []; }