se-design 1.0.73-dev2 → 1.0.73-dev3

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.
Files changed (86) hide show
  1. package/dist/components/CustomModal/index.d.ts +18 -0
  2. package/dist/components/Modal/index.d.ts +1 -0
  3. package/dist/index11.js +53 -38
  4. package/dist/index11.js.map +1 -1
  5. package/dist/index12.js.map +1 -1
  6. package/dist/index15.js +1 -1
  7. package/dist/index18.js +1 -1
  8. package/dist/index188.js +5 -5
  9. package/dist/index192.js +43 -0
  10. package/dist/index192.js.map +1 -0
  11. package/dist/{index194.js → index195.js} +1 -1
  12. package/dist/{index194.js.map → index195.js.map} +1 -1
  13. package/dist/{index196.js → index197.js} +3 -3
  14. package/dist/{index196.js.map → index197.js.map} +1 -1
  15. package/dist/{index198.js → index199.js} +1 -1
  16. package/dist/{index198.js.map → index199.js.map} +1 -1
  17. package/dist/{index206.js → index207.js} +1 -1
  18. package/dist/{index206.js.map → index207.js.map} +1 -1
  19. package/dist/{index214.js → index215.js} +1 -1
  20. package/dist/{index214.js.map → index215.js.map} +1 -1
  21. package/dist/{index217.js → index218.js} +1 -1
  22. package/dist/{index217.js.map → index218.js.map} +1 -1
  23. package/dist/{index226.js → index227.js} +1 -1
  24. package/dist/{index226.js.map → index227.js.map} +1 -1
  25. package/dist/index229.js +57 -20
  26. package/dist/index229.js.map +1 -1
  27. package/dist/index230.js +20 -52
  28. package/dist/index230.js.map +1 -1
  29. package/dist/index231.js +51 -16
  30. package/dist/index231.js.map +1 -1
  31. package/dist/index232.js +18 -9
  32. package/dist/index232.js.map +1 -1
  33. package/dist/index233.js +9 -9
  34. package/dist/index233.js.map +1 -1
  35. package/dist/index234.js +9 -4
  36. package/dist/index234.js.map +1 -1
  37. package/dist/index235.js +5 -170
  38. package/dist/index235.js.map +1 -1
  39. package/dist/index236.js +170 -11
  40. package/dist/index236.js.map +1 -1
  41. package/dist/index237.js +11 -6
  42. package/dist/index237.js.map +1 -1
  43. package/dist/index238.js +5 -5
  44. package/dist/index238.js.map +1 -1
  45. package/dist/index239.js +5 -37
  46. package/dist/index239.js.map +1 -1
  47. package/dist/index24.js +1 -1
  48. package/dist/index240.js +38 -2
  49. package/dist/index240.js.map +1 -1
  50. package/dist/index241.js +2 -8
  51. package/dist/index241.js.map +1 -1
  52. package/dist/index242.js +7 -326
  53. package/dist/index242.js.map +1 -1
  54. package/dist/index243.js +324 -47
  55. package/dist/index243.js.map +1 -1
  56. package/dist/index244.js +50 -2
  57. package/dist/index244.js.map +1 -1
  58. package/dist/index245.js +2 -76
  59. package/dist/index245.js.map +1 -1
  60. package/dist/index246.js +65 -82
  61. package/dist/index246.js.map +1 -1
  62. package/dist/index247.js +89 -48
  63. package/dist/index247.js.map +1 -1
  64. package/dist/index248.js +51 -7
  65. package/dist/index248.js.map +1 -1
  66. package/dist/index249.js +7 -4
  67. package/dist/index249.js.map +1 -1
  68. package/dist/index250.js +4 -51
  69. package/dist/index250.js.map +1 -1
  70. package/dist/index251.js +52 -2
  71. package/dist/index251.js.map +1 -1
  72. package/dist/index252.js +2 -2
  73. package/dist/index253.js +5 -0
  74. package/dist/index253.js.map +1 -0
  75. package/dist/index27.js +1 -1
  76. package/dist/index37.js +1 -1
  77. package/dist/index39.js +1 -1
  78. package/dist/index44.js +1 -1
  79. package/dist/index45.js +2 -2
  80. package/dist/index48.js +1 -1
  81. package/dist/index52.js +1 -1
  82. package/dist/index62.js +1 -1
  83. package/dist/index64.js +1 -1
  84. package/package.json +1 -1
  85. package/dist/index228.js +0 -62
  86. package/dist/index228.js.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"file":"index229.js","sources":["../src/utils/a11y/focusableElements.ts"],"sourcesContent":["/**\n * Utilities for finding focusable elements within a container.\n * \n * Used for focus management in modals, popovers, and other interactive overlays.\n */\n\n/**\n * Base selector for standard focusable elements.\n * Matches: buttons, links, inputs, selects, textareas, elements with tabindex >= 0, contenteditable.\n */\nexport const FOCUSABLE_SELECTOR = [\n 'button:not([disabled])',\n '[href]',\n 'input:not([disabled])',\n 'select:not([disabled])',\n 'textarea:not([disabled])',\n '[tabindex]:not([tabindex=\"-1\"]):not([disabled])',\n '[contenteditable=\"true\"]'\n].join(', ');\n\n/**\n * Extended selector that includes ARIA role-based focusable elements.\n * Useful for composite widgets like menus, listboxes, etc.\n */\nexport const FOCUSABLE_WITH_ROLES_SELECTOR = [\n FOCUSABLE_SELECTOR,\n '[role=\"menuitem\"]',\n '[role=\"option\"]',\n '[role=\"menuitemcheckbox\"]',\n '[role=\"menuitemradio\"]'\n].join(', ');\n\n/**\n * Options for getFocusableElements\n */\nexport interface GetFocusableElementsOptions {\n /**\n * Container element to search within. If null/undefined, returns empty array.\n */\n container: HTMLElement | null;\n /**\n * Whether to include role-based focusable elements (menuitem, option, etc.).\n * Default: false (uses base selector only)\n */\n includeRoles?: boolean;\n /**\n * Additional custom selectors to include.\n */\n additionalSelectors?: string[];\n /**\n * Whether to filter out hidden/invisible elements.\n * Default: false (returns all matching elements regardless of visibility)\n */\n filterHidden?: boolean;\n}\n\n/**\n * Get all focusable elements within a container.\n * \n * @example Basic usage (standard focusable elements)\n * ```ts\n * const focusables = getFocusableElements({ container: dialogRef.current });\n * focusables[0]?.focus(); // Focus first element\n * ```\n * \n * @example With role-based elements (for menus/listboxes)\n * ```ts\n * const focusables = getFocusableElements({ \n * container: menuRef.current,\n * includeRoles: true \n * });\n * ```\n * \n * @example With custom selectors\n * ```ts\n * const focusables = getFocusableElements({ \n * container: customWidgetRef.current,\n * additionalSelectors: ['[data-focusable=\"true\"]']\n * });\n * ```\n */\nexport function getFocusableElements({\n container,\n includeRoles = false,\n additionalSelectors = [],\n filterHidden = false\n}: GetFocusableElementsOptions): HTMLElement[] {\n if (!container) return [];\n\n const selector = [\n includeRoles ? FOCUSABLE_WITH_ROLES_SELECTOR : FOCUSABLE_SELECTOR,\n ...additionalSelectors\n ].filter(Boolean).join(', ');\n\n const elements = Array.from(container.querySelectorAll<HTMLElement>(selector));\n\n if (!filterHidden) return elements;\n\n // Filter out hidden/invisible elements\n return elements.filter((el) => {\n const style = window.getComputedStyle(el);\n return (\n style.display !== 'none' &&\n style.visibility !== 'hidden' &&\n style.opacity !== '0' &&\n !el.hasAttribute('hidden') &&\n el.offsetWidth > 0 &&\n el.offsetHeight > 0\n );\n });\n}\n\n/**\n * Get the first focusable element in a container.\n * Returns null if none found.\n */\nexport function getFirstFocusableElement(\n options: GetFocusableElementsOptions\n): HTMLElement | null {\n const focusables = getFocusableElements(options);\n return focusables.length > 0 ? focusables[0] : null;\n}\n\n/**\n * Get the last focusable element in a container.\n * Returns null if none found.\n */\nexport function getLastFocusableElement(\n options: GetFocusableElementsOptions\n): HTMLElement | null {\n const focusables = getFocusableElements(options);\n return focusables.length > 0 ? focusables[focusables.length - 1] : null;\n}\n"],"names":["FOCUSABLE_SELECTOR","join","FOCUSABLE_WITH_ROLES_SELECTOR","getFocusableElements","container","includeRoles","additionalSelectors","filterHidden","selector","filter","Boolean","elements","Array","from","querySelectorAll","el","style","window","getComputedStyle","display","visibility","opacity","hasAttribute","offsetWidth","offsetHeight","getFirstFocusableElement","options","focusables","length"],"mappings":"AAUO,MAAMA,IAAqB,CAChC,0BACA,UACA,yBACA,0BACA,4BACA,mDACA,0BAA0B,EAC1BC,KAAK,IAAI,GAMEC,IAAgC,CAC3CF,GACA,qBACA,mBACA,6BACA,wBAAwB,EACxBC,KAAK,IAAI;AAmDJ,SAASE,EAAqB;AAAA,EACnCC,WAAAA;AAAAA,EACAC,cAAAA,IAAe;AAAA,EACfC,qBAAAA,IAAsB,CAAA;AAAA,EACtBC,cAAAA,IAAe;AACY,GAAkB;AAC7C,MAAI,CAACH,EAAW,QAAO,CAAA;AAEvB,QAAMI,IAAW,CACfH,IAAeH,IAAgCF,GAC/C,GAAGM,CAAmB,EACtBG,OAAOC,OAAO,EAAET,KAAK,IAAI,GAErBU,IAAWC,MAAMC,KAAKT,EAAUU,iBAA8BN,CAAQ,CAAC;AAE7E,SAAKD,IAGEI,EAASF,OAAQM,CAAAA,MAAO;AAC7B,UAAMC,IAAQC,OAAOC,iBAAiBH,CAAE;AACxC,WACEC,EAAMG,YAAY,UAClBH,EAAMI,eAAe,YACrBJ,EAAMK,YAAY,OAClB,CAACN,EAAGO,aAAa,QAAQ,KACzBP,EAAGQ,cAAc,KACjBR,EAAGS,eAAe;AAAA,EAEtB,CAAC,IAbyBb;AAc5B;AAMO,SAASc,EACdC,GACoB;AACpB,QAAMC,IAAaxB,EAAqBuB,CAAO;AAC/C,SAAOC,EAAWC,SAAS,IAAID,EAAW,CAAC,IAAI;AACjD;"}
1
+ {"version":3,"file":"index229.js","sources":["../src/utils/a11y/useFocusTrap.ts"],"sourcesContent":["import { useLayoutEffect, useRef } from 'react';\nimport { getFocusableElements, getFirstFocusableElement } from './focusableElements';\n\nexport interface UseFocusTrapOptions<T extends HTMLElement = HTMLElement> {\n /**\n * Whether the focus trap is active.\n */\n enabled: boolean;\n /**\n * Container element ref to trap focus within.\n */\n containerRef: React.RefObject<T | null>;\n /**\n * Whether to restore focus to the element that had focus before trap activated.\n * Default: true\n */\n restoreFocus?: boolean;\n /**\n * Initial focus target when trap activates.\n * - 'first': Focus first focusable element (default)\n * - 'container': Focus the container itself\n * - 'none': Skip initial focus browser handles it (e.g. autofocus attribute)\n * - CSS selector: Focus element matching selector\n * - HTMLElement: Focus this specific element\n */\n initialFocus?: 'first' | 'container' | 'none' | string | HTMLElement;\n}\n\nexport interface UseFocusTrapReturn {\n /**\n * Ref to the element that had focus before trap activated.\n * Useful for manual focus restoration if needed.\n */\n triggerRef: React.MutableRefObject<HTMLElement | null>;\n}\n\n/**\n * Hook to trap focus within a container (for modals, dialogs, drawers).\n * \n * Implements WCAG 2.1 focus trap pattern:\n * - Moves focus into container on activation\n * - Wraps Tab/Shift+Tab navigation within container\n * - Restores focus to trigger element on deactivation\n * - Safety net: catches focus escaping via other means\n * \n * Note: For Escape key handling, use `useDismissOnEscape` hook separately.\n * This keeps focus trap (accessibility) separate from Escape handling (UX).\n * \n * @example\n * ```tsx\n * const MyModal = ({ isOpen, onClose }) => {\n * const containerRef = useRef<HTMLDivElement>(null);\n * \n * // Escape handling (UX)\n * useDismissOnEscape({\n * containerRef,\n * onDismiss: onClose,\n * enabled: isOpen\n * });\n * \n * // Focus trap (accessibility)\n * const { triggerRef } = useFocusTrap({\n * enabled: isOpen,\n * containerRef,\n * restoreFocus: true\n * });\n * \n * return (\n * <div ref={containerRef}>\n * <button>First</button>\n * <button>Second</button>\n * </div>\n * );\n * };\n * ```\n */\n/**\n * Resolve the initial focus target based on the initialFocus option.\n */\nfunction resolveInitialFocusTarget(\n container: HTMLElement,\n initialFocus: 'first' | 'container' | 'none' | string | HTMLElement\n): HTMLElement | null {\n if (initialFocus === 'none') return null;\n if (initialFocus === 'first') {\n return getFirstFocusableElement({ container }) || container;\n }\n if (initialFocus === 'container') {\n return container;\n }\n if (typeof initialFocus === 'string') {\n return container.querySelector<HTMLElement>(initialFocus);\n }\n if (initialFocus instanceof HTMLElement) {\n return initialFocus;\n }\n return null;\n}\n\nexport function useFocusTrap<T extends HTMLElement = HTMLElement>({\n enabled,\n containerRef,\n restoreFocus = true,\n initialFocus = 'first',\n}: UseFocusTrapOptions<T>): UseFocusTrapReturn {\n const triggerRef = useRef<HTMLElement | null>(null);\n const lastFocusedInContainer = useRef<HTMLElement | null>(null);\n\n // Focus management: save trigger, move focus into container on activate, restore on deactivate\n useLayoutEffect(() => {\n if (!enabled) {\n // Restore focus to trigger when trap deactivates\n if (restoreFocus && triggerRef.current) {\n requestAnimationFrame(() => {\n triggerRef.current?.focus();\n triggerRef.current = null;\n });\n }\n return;\n }\n\n const container = containerRef.current;\n if (!container) return;\n\n // Save the element that had focus before trap activated\n triggerRef.current = document.activeElement as HTMLElement;\n\n // Focus initial target\n requestAnimationFrame(() => {\n resolveInitialFocusTarget(container, initialFocus)?.focus();\n });\n }, [enabled, containerRef, restoreFocus, initialFocus]);\n\n // Focus trap: Tab wrapping (only when enabled)\n useLayoutEffect(() => {\n if (!enabled) return;\n \n const container = containerRef.current;\n if (!container) return;\n\n const handleKeyDown = (e: KeyboardEvent) => {\n // Tab wrapping\n if (e.key === 'Tab') {\n const focusables = getFocusableElements({ container });\n\n if (focusables.length === 0) {\n e.preventDefault();\n container.focus();\n return;\n }\n\n const first = focusables[0];\n const last = focusables[focusables.length - 1];\n const activeElement = document.activeElement;\n\n if (e.shiftKey && activeElement === first) {\n e.preventDefault();\n last.focus();\n } else if (!e.shiftKey && activeElement === last) {\n e.preventDefault();\n first.focus();\n }\n }\n };\n\n document.addEventListener('keydown', handleKeyDown, true);\n return () => document.removeEventListener('keydown', handleKeyDown, true);\n }, [enabled, containerRef]);\n\n // Focus trap safety net: catch focus escaping\n useLayoutEffect(() => {\n if (!enabled) return;\n \n const container = containerRef.current;\n if (!container) return;\n\n const handleFocusIn = (e: FocusEvent) => {\n const target = e.target as Node;\n \n if (container.contains(target)) {\n lastFocusedInContainer.current = target as HTMLElement;\n } else {\n // Focus escaped - redirect back\n const fallback = lastFocusedInContainer.current \n || getFirstFocusableElement({ container }) \n || container;\n fallback.focus();\n }\n };\n\n document.addEventListener('focusin', handleFocusIn, true);\n return () => document.removeEventListener('focusin', handleFocusIn, true);\n }, [enabled, containerRef]);\n\n return { triggerRef };\n}\n"],"names":["useRef","useLayoutEffect","getFirstFocusableElement","getFocusableElements","resolveInitialFocusTarget","container","initialFocus","querySelector","HTMLElement","useFocusTrap","enabled","containerRef","restoreFocus","triggerRef","lastFocusedInContainer","current","requestAnimationFrame","focus","document","activeElement","handleKeyDown","e","key","focusables","length","preventDefault","first","last","shiftKey","addEventListener","removeEventListener","handleFocusIn","target","contains"],"mappings":"AA+EA,SAAA,UAAAA,GAAA,mBAAAC,SAAA;AAAA,SAAA,4BAAAC,GAAA,wBAAAC,SAAA;AAAA,SAASC,EACPC,GACAC,GACoB;AACpB,SAAIA,MAAiB,SAAe,OAChCA,MAAiB,UACZJ,EAAyB;AAAA,IAAEG,WAAAA;AAAAA,EAAAA,CAAW,KAAKA,IAEhDC,MAAiB,cACZD,IAEL,OAAOC,KAAiB,WACnBD,EAAUE,cAA2BD,CAAY,IAEtDA,aAAwBE,cACnBF,IAEF;AACT;AAEO,SAASG,EAAkD;AAAA,EAChEC,SAAAA;AAAAA,EACAC,cAAAA;AAAAA,EACAC,cAAAA,IAAe;AAAA,EACfN,cAAAA,IAAe;AACO,GAAuB;AAC7C,QAAMO,IAAab,EAA2B,IAAI,GAC5Cc,IAAyBd,EAA2B,IAAI;AAG9DC,SAAAA,EAAgB,MAAM;AACpB,QAAI,CAACS,GAAS;AAEZ,MAAIE,KAAgBC,EAAWE,WAC7BC,sBAAsB,MAAM;AAC1BH,QAAAA,EAAWE,SAASE,MAAAA,GACpBJ,EAAWE,UAAU;AAAA,MACvB,CAAC;AAEH;AAAA,IACF;AAEA,UAAMV,IAAYM,EAAaI;AAC/B,IAAKV,MAGLQ,EAAWE,UAAUG,SAASC,eAG9BH,sBAAsB,MAAM;AAC1BZ,MAAAA,EAA0BC,GAAWC,CAAY,GAAGW,MAAAA;AAAAA,IACtD,CAAC;AAAA,EACH,GAAG,CAACP,GAASC,GAAcC,GAAcN,CAAY,CAAC,GAGtDL,EAAgB,MAAM;AACpB,QAAI,CAACS,EAAS;AAEd,UAAML,IAAYM,EAAaI;AAC/B,QAAI,CAACV,EAAW;AAEhB,UAAMe,IAAgBA,CAACC,MAAqB;AAE1C,UAAIA,EAAEC,QAAQ,OAAO;AACnB,cAAMC,IAAapB,EAAqB;AAAA,UAAEE,WAAAA;AAAAA,QAAAA,CAAW;AAErD,YAAIkB,EAAWC,WAAW,GAAG;AAC3BH,UAAAA,EAAEI,eAAAA,GACFpB,EAAUY,MAAAA;AACV;AAAA,QACF;AAEA,cAAMS,IAAQH,EAAW,CAAC,GACpBI,IAAOJ,EAAWA,EAAWC,SAAS,CAAC,GACvCL,IAAgBD,SAASC;AAE/B,QAAIE,EAAEO,YAAYT,MAAkBO,KAClCL,EAAEI,eAAAA,GACFE,EAAKV,MAAAA,KACI,CAACI,EAAEO,YAAYT,MAAkBQ,MAC1CN,EAAEI,eAAAA,GACFC,EAAMT,MAAAA;AAAAA,MAEV;AAAA,IACF;AAEAC,oBAASW,iBAAiB,WAAWT,GAAe,EAAI,GACjD,MAAMF,SAASY,oBAAoB,WAAWV,GAAe,EAAI;AAAA,EAC1E,GAAG,CAACV,GAASC,CAAY,CAAC,GAG1BV,EAAgB,MAAM;AACpB,QAAI,CAACS,EAAS;AAEd,UAAML,IAAYM,EAAaI;AAC/B,QAAI,CAACV,EAAW;AAEhB,UAAM0B,IAAgBA,CAACV,MAAkB;AACvC,YAAMW,IAASX,EAAEW;AAEjB,MAAI3B,EAAU4B,SAASD,CAAM,IAC3BlB,EAAuBC,UAAUiB,KAGhBlB,EAAuBC,WACnCb,EAAyB;AAAA,QAAEG,WAAAA;AAAAA,MAAAA,CAAW,KACtCA,GACIY,MAAAA;AAAAA,IAEb;AAEAC,oBAASW,iBAAiB,WAAWE,GAAe,EAAI,GACjD,MAAMb,SAASY,oBAAoB,WAAWC,GAAe,EAAI;AAAA,EAC1E,GAAG,CAACrB,GAASC,CAAY,CAAC,GAEnB;AAAA,IAAEE,YAAAA;AAAAA,EAAAA;AACX;"}
package/dist/index230.js CHANGED
@@ -1,57 +1,25 @@
1
- import { useState as m, useEffect as w, useCallback as b } from "react";
2
- import { useScrollActiveIntoView as x } from "./index231.js";
3
- function E({
4
- items: u,
5
- isOpen: t,
6
- onSelect: o,
7
- onClose: c,
8
- onOpen: l,
9
- loop: i = !0,
10
- disabled: h = !1,
11
- listboxRef: k,
12
- optionSelector: g = '[role="option"]'
1
+ const l = ["button:not([disabled])", "[href]", "input:not([disabled])", "select:not([disabled])", "textarea:not([disabled])", '[tabindex]:not([tabindex="-1"]):not([disabled])', '[contenteditable="true"]'].join(", "), a = [l, '[role="menuitem"]', '[role="option"]', '[role="menuitemcheckbox"]', '[role="menuitemradio"]'].join(", ");
2
+ function u({
3
+ container: e,
4
+ includeRoles: t = !1,
5
+ additionalSelectors: r = [],
6
+ filterHidden: s = !1
13
7
  }) {
14
- const [f, a] = m(-1);
15
- w(() => {
16
- t || a(-1);
17
- }, [t]), x({
18
- containerRef: k,
19
- activeIndex: f,
20
- itemSelector: g,
21
- enabled: t
22
- });
23
- const D = b((r) => {
24
- if (h) {
25
- r.key === "Escape" && t && (r.preventDefault(), c());
26
- return;
27
- }
28
- const e = u.length;
29
- switch (r.key) {
30
- case "ArrowDown":
31
- r.preventDefault(), !t && e > 0 ? (l?.(), a(0)) : t && e > 0 && a((n) => i ? (n + 1) % e : Math.min(n + 1, e - 1));
32
- break;
33
- case "ArrowUp":
34
- r.preventDefault(), t && e > 0 && a((n) => n === -1 ? e - 1 : i ? (n - 1 + e) % e : Math.max(n - 1, 0));
35
- break;
36
- case "Enter":
37
- t && f >= 0 && u[f] && (r.preventDefault(), o(u[f], f), a(-1));
38
- break;
39
- case "Escape":
40
- t && (r.preventDefault(), c(), a(-1));
41
- break;
42
- case "Tab":
43
- t && (c(), a(-1));
44
- break;
45
- }
46
- }, [h, u, t, f, o, c, l, i]), d = b((r, e) => `${r}-option-${e}`, []);
47
- return {
48
- highlightedIndex: f,
49
- setHighlightedIndex: a,
50
- handleKeyDown: D,
51
- getOptionId: d
52
- };
8
+ if (!e) return [];
9
+ const d = [t ? a : l, ...r].filter(Boolean).join(", "), i = Array.from(e.querySelectorAll(d));
10
+ return s ? i.filter((n) => {
11
+ const o = window.getComputedStyle(n);
12
+ return o.display !== "none" && o.visibility !== "hidden" && o.opacity !== "0" && !n.hasAttribute("hidden") && n.offsetWidth > 0 && n.offsetHeight > 0;
13
+ }) : i;
14
+ }
15
+ function c(e) {
16
+ const t = u(e);
17
+ return t.length > 0 ? t[0] : null;
53
18
  }
54
19
  export {
55
- E as useComboboxNavigation
20
+ l as FOCUSABLE_SELECTOR,
21
+ a as FOCUSABLE_WITH_ROLES_SELECTOR,
22
+ c as getFirstFocusableElement,
23
+ u as getFocusableElements
56
24
  };
57
25
  //# sourceMappingURL=index230.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index230.js","sources":["../src/utils/a11y/useComboboxNavigation.ts"],"sourcesContent":["import { useCallback, useState, useEffect } from 'react';\nimport type { RefObject } from 'react';\nimport { useScrollActiveIntoView } from './useScrollActiveIntoView';\n\nexport interface UseComboboxNavigationOptions<T = any> {\n /**\n * Array of items to navigate through\n */\n items: T[];\n \n /**\n * Whether the dropdown is currently open\n */\n isOpen: boolean;\n \n /**\n * Callback when an item is selected (Enter key)\n */\n onSelect: (item: T, index: number) => void;\n \n /**\n * Callback to close the dropdown\n */\n onClose: () => void;\n \n /**\n * Optional: Callback to open the dropdown\n */\n onOpen?: () => void;\n \n /**\n * Whether to wrap around at the ends of the list.\n * Default: true\n */\n loop?: boolean;\n \n /**\n * Whether keyboard navigation is disabled\n * (e.g., for custom rendered content)\n */\n disabled?: boolean;\n \n /**\n * Ref to the listbox container for scroll management\n */\n listboxRef?: RefObject<HTMLElement | null>;\n \n /**\n * CSS selector for option elements (default: '[role=\"option\"]')\n */\n optionSelector?: string;\n}\n\nexport interface UseComboboxNavigationReturn {\n /**\n * Currently highlighted index (-1 if none)\n */\n highlightedIndex: number;\n \n /**\n * Set the highlighted index manually\n */\n setHighlightedIndex: (index: number | ((prev: number) => number)) => void;\n \n /**\n * Keyboard event handler for the combobox input\n */\n handleKeyDown: (e: React.KeyboardEvent) => void;\n \n /**\n * Generate stable ID for an option\n */\n getOptionId: (listboxId: string, index: number) => string;\n \n}\n\n/**\n * Hook for managing combobox keyboard navigation with aria-activedescendant.\n * \n * Implements WAI-ARIA 1.2 Combobox pattern:\n * - Arrow Up/Down to navigate options\n * - Enter to select highlighted option\n * - Escape to close dropdown\n * - Tab to close and move focus\n * - Auto-scrolls highlighted option into view\n * \n * @example\n * ```tsx\n * const { \n * highlightedIndex, \n * handleKeyDown, \n * getOptionId \n * } = useComboboxNavigation({\n * items: suggestions,\n * isOpen: isDropdownOpen,\n * onSelect: (item, idx) => handleSelect(item),\n * onClose: () => setIsOpen(false),\n * listboxRef\n * });\n * \n * <input\n * role=\"combobox\"\n * onKeyDown={handleKeyDown}\n * aria-activedescendant={highlightedIndex >= 0 ? getOptionId(listboxId, highlightedIndex) : undefined}\n * />\n * ```\n */\nexport function useComboboxNavigation<T = any>({\n items,\n isOpen,\n onSelect,\n onClose,\n onOpen,\n loop = true,\n disabled = false,\n listboxRef,\n optionSelector = '[role=\"option\"]'\n}: UseComboboxNavigationOptions<T>): UseComboboxNavigationReturn {\n const [highlightedIndex, setHighlightedIndex] = useState<number>(-1);\n \n // Reset highlighted index when dropdown closes\n useEffect(() => {\n if (!isOpen) {\n setHighlightedIndex(-1);\n }\n }, [isOpen]);\n \n // Auto-scroll highlighted item into view\n useScrollActiveIntoView({\n containerRef: listboxRef,\n activeIndex: highlightedIndex,\n itemSelector: optionSelector,\n enabled: isOpen\n });\n \n const handleKeyDown = useCallback(\n (e: React.KeyboardEvent) => {\n if (disabled) {\n // For disabled navigation, still handle Escape\n if (e.key === 'Escape' && isOpen) {\n e.preventDefault();\n onClose();\n }\n return;\n }\n \n const itemCount = items.length;\n \n switch (e.key) {\n case 'ArrowDown':\n e.preventDefault();\n if (!isOpen && itemCount > 0) {\n // Open dropdown and highlight first item\n onOpen?.();\n setHighlightedIndex(0);\n } else if (isOpen && itemCount > 0) {\n // Navigate down\n setHighlightedIndex((prev) => {\n if (loop) {\n return (prev + 1) % itemCount;\n }\n return Math.min(prev + 1, itemCount - 1);\n });\n }\n break;\n \n case 'ArrowUp':\n e.preventDefault();\n if (isOpen && itemCount > 0) {\n // Navigate up\n setHighlightedIndex((prev) => {\n // If nothing highlighted, go to last item\n if (prev === -1) {\n return itemCount - 1;\n }\n if (loop) {\n return (prev - 1 + itemCount) % itemCount;\n }\n return Math.max(prev - 1, 0);\n });\n }\n break;\n \n case 'Enter':\n if (isOpen && highlightedIndex >= 0 && items[highlightedIndex]) {\n e.preventDefault();\n onSelect(items[highlightedIndex], highlightedIndex);\n setHighlightedIndex(-1);\n }\n break;\n \n case 'Escape':\n if (isOpen) {\n e.preventDefault();\n onClose();\n setHighlightedIndex(-1);\n }\n break;\n \n case 'Tab':\n // Close dropdown on Tab (don't preventDefault - let focus move naturally)\n if (isOpen) {\n onClose();\n setHighlightedIndex(-1);\n }\n break;\n }\n },\n [disabled, items, isOpen, highlightedIndex, onSelect, onClose, onOpen, loop]\n );\n \n const getOptionId = useCallback(\n (listboxId: string, index: number) => `${listboxId}-option-${index}`,\n []\n );\n \n return {\n highlightedIndex,\n setHighlightedIndex,\n handleKeyDown,\n getOptionId\n };\n}\n"],"names":["useState","useEffect","useCallback","useScrollActiveIntoView","useComboboxNavigation","items","isOpen","onSelect","onClose","onOpen","loop","disabled","listboxRef","optionSelector","highlightedIndex","setHighlightedIndex","containerRef","activeIndex","itemSelector","enabled","handleKeyDown","e","key","preventDefault","itemCount","length","prev","Math","min","max","getOptionId","listboxId","index"],"mappings":"AA2GO,SAAA,YAAAA,GAAA,aAAAC,GAAA,eAAAC,SAAA;AAAA,SAAA,2BAAAC,SAAA;AAAA,SAASC,EAA+B;AAAA,EAC7CC,OAAAA;AAAAA,EACAC,QAAAA;AAAAA,EACAC,UAAAA;AAAAA,EACAC,SAAAA;AAAAA,EACAC,QAAAA;AAAAA,EACAC,MAAAA,IAAO;AAAA,EACPC,UAAAA,IAAW;AAAA,EACXC,YAAAA;AAAAA,EACAC,gBAAAA,IAAiB;AACc,GAAgC;AAC/D,QAAM,CAACC,GAAkBC,CAAmB,IAAIf,EAAiB,EAAE;AAGnEC,EAAAA,EAAU,MAAM;AACd,IAAKK,KACHS,EAAoB,EAAE;AAAA,EAE1B,GAAG,CAACT,CAAM,CAAC,GAGXH,EAAwB;AAAA,IACtBa,cAAcJ;AAAAA,IACdK,aAAaH;AAAAA,IACbI,cAAcL;AAAAA,IACdM,SAASb;AAAAA,EAAAA,CACV;AAED,QAAMc,IAAgBlB,EACpB,CAACmB,MAA2B;AAC1B,QAAIV,GAAU;AAEZ,MAAIU,EAAEC,QAAQ,YAAYhB,MACxBe,EAAEE,eAAAA,GACFf,EAAAA;AAEF;AAAA,IACF;AAEA,UAAMgB,IAAYnB,EAAMoB;AAExB,YAAQJ,EAAEC,KAAAA;AAAAA,MACR,KAAK;AACHD,QAAAA,EAAEE,eAAAA,GACE,CAACjB,KAAUkB,IAAY,KAEzBf,IAAAA,GACAM,EAAoB,CAAC,KACZT,KAAUkB,IAAY,KAE/BT,EAAqBW,CAAAA,MACfhB,KACMgB,IAAO,KAAKF,IAEfG,KAAKC,IAAIF,IAAO,GAAGF,IAAY,CAAC,CACxC;AAEH;AAAA,MAEF,KAAK;AACHH,QAAAA,EAAEE,eAAAA,GACEjB,KAAUkB,IAAY,KAExBT,EAAqBW,CAAAA,MAEfA,MAAS,KACJF,IAAY,IAEjBd,KACMgB,IAAO,IAAIF,KAAaA,IAE3BG,KAAKE,IAAIH,IAAO,GAAG,CAAC,CAC5B;AAEH;AAAA,MAEF,KAAK;AACH,QAAIpB,KAAUQ,KAAoB,KAAKT,EAAMS,CAAgB,MAC3DO,EAAEE,eAAAA,GACFhB,EAASF,EAAMS,CAAgB,GAAGA,CAAgB,GAClDC,EAAoB,EAAE;AAExB;AAAA,MAEF,KAAK;AACH,QAAIT,MACFe,EAAEE,eAAAA,GACFf,EAAAA,GACAO,EAAoB,EAAE;AAExB;AAAA,MAEF,KAAK;AAEH,QAAIT,MACFE,EAAAA,GACAO,EAAoB,EAAE;AAExB;AAAA,IAAA;AAAA,EAEN,GACA,CAACJ,GAAUN,GAAOC,GAAQQ,GAAkBP,GAAUC,GAASC,GAAQC,CAAI,CAC7E,GAEMoB,IAAc5B,EAClB,CAAC6B,GAAmBC,MAAkB,GAAGD,CAAS,WAAWC,CAAK,IAClE,CAAA,CACF;AAEA,SAAO;AAAA,IACLlB,kBAAAA;AAAAA,IACAC,qBAAAA;AAAAA,IACAK,eAAAA;AAAAA,IACAU,aAAAA;AAAAA,EAAAA;AAEJ;"}
1
+ {"version":3,"file":"index230.js","sources":["../src/utils/a11y/focusableElements.ts"],"sourcesContent":["/**\n * Utilities for finding focusable elements within a container.\n * \n * Used for focus management in modals, popovers, and other interactive overlays.\n */\n\n/**\n * Base selector for standard focusable elements.\n * Matches: buttons, links, inputs, selects, textareas, elements with tabindex >= 0, contenteditable.\n */\nexport const FOCUSABLE_SELECTOR = [\n 'button:not([disabled])',\n '[href]',\n 'input:not([disabled])',\n 'select:not([disabled])',\n 'textarea:not([disabled])',\n '[tabindex]:not([tabindex=\"-1\"]):not([disabled])',\n '[contenteditable=\"true\"]'\n].join(', ');\n\n/**\n * Extended selector that includes ARIA role-based focusable elements.\n * Useful for composite widgets like menus, listboxes, etc.\n */\nexport const FOCUSABLE_WITH_ROLES_SELECTOR = [\n FOCUSABLE_SELECTOR,\n '[role=\"menuitem\"]',\n '[role=\"option\"]',\n '[role=\"menuitemcheckbox\"]',\n '[role=\"menuitemradio\"]'\n].join(', ');\n\n/**\n * Options for getFocusableElements\n */\nexport interface GetFocusableElementsOptions {\n /**\n * Container element to search within. If null/undefined, returns empty array.\n */\n container: HTMLElement | null;\n /**\n * Whether to include role-based focusable elements (menuitem, option, etc.).\n * Default: false (uses base selector only)\n */\n includeRoles?: boolean;\n /**\n * Additional custom selectors to include.\n */\n additionalSelectors?: string[];\n /**\n * Whether to filter out hidden/invisible elements.\n * Default: false (returns all matching elements regardless of visibility)\n */\n filterHidden?: boolean;\n}\n\n/**\n * Get all focusable elements within a container.\n * \n * @example Basic usage (standard focusable elements)\n * ```ts\n * const focusables = getFocusableElements({ container: dialogRef.current });\n * focusables[0]?.focus(); // Focus first element\n * ```\n * \n * @example With role-based elements (for menus/listboxes)\n * ```ts\n * const focusables = getFocusableElements({ \n * container: menuRef.current,\n * includeRoles: true \n * });\n * ```\n * \n * @example With custom selectors\n * ```ts\n * const focusables = getFocusableElements({ \n * container: customWidgetRef.current,\n * additionalSelectors: ['[data-focusable=\"true\"]']\n * });\n * ```\n */\nexport function getFocusableElements({\n container,\n includeRoles = false,\n additionalSelectors = [],\n filterHidden = false\n}: GetFocusableElementsOptions): HTMLElement[] {\n if (!container) return [];\n\n const selector = [\n includeRoles ? FOCUSABLE_WITH_ROLES_SELECTOR : FOCUSABLE_SELECTOR,\n ...additionalSelectors\n ].filter(Boolean).join(', ');\n\n const elements = Array.from(container.querySelectorAll<HTMLElement>(selector));\n\n if (!filterHidden) return elements;\n\n // Filter out hidden/invisible elements\n return elements.filter((el) => {\n const style = window.getComputedStyle(el);\n return (\n style.display !== 'none' &&\n style.visibility !== 'hidden' &&\n style.opacity !== '0' &&\n !el.hasAttribute('hidden') &&\n el.offsetWidth > 0 &&\n el.offsetHeight > 0\n );\n });\n}\n\n/**\n * Get the first focusable element in a container.\n * Returns null if none found.\n */\nexport function getFirstFocusableElement(\n options: GetFocusableElementsOptions\n): HTMLElement | null {\n const focusables = getFocusableElements(options);\n return focusables.length > 0 ? focusables[0] : null;\n}\n\n/**\n * Get the last focusable element in a container.\n * Returns null if none found.\n */\nexport function getLastFocusableElement(\n options: GetFocusableElementsOptions\n): HTMLElement | null {\n const focusables = getFocusableElements(options);\n return focusables.length > 0 ? focusables[focusables.length - 1] : null;\n}\n"],"names":["FOCUSABLE_SELECTOR","join","FOCUSABLE_WITH_ROLES_SELECTOR","getFocusableElements","container","includeRoles","additionalSelectors","filterHidden","selector","filter","Boolean","elements","Array","from","querySelectorAll","el","style","window","getComputedStyle","display","visibility","opacity","hasAttribute","offsetWidth","offsetHeight","getFirstFocusableElement","options","focusables","length"],"mappings":"AAUO,MAAMA,IAAqB,CAChC,0BACA,UACA,yBACA,0BACA,4BACA,mDACA,0BAA0B,EAC1BC,KAAK,IAAI,GAMEC,IAAgC,CAC3CF,GACA,qBACA,mBACA,6BACA,wBAAwB,EACxBC,KAAK,IAAI;AAmDJ,SAASE,EAAqB;AAAA,EACnCC,WAAAA;AAAAA,EACAC,cAAAA,IAAe;AAAA,EACfC,qBAAAA,IAAsB,CAAA;AAAA,EACtBC,cAAAA,IAAe;AACY,GAAkB;AAC7C,MAAI,CAACH,EAAW,QAAO,CAAA;AAEvB,QAAMI,IAAW,CACfH,IAAeH,IAAgCF,GAC/C,GAAGM,CAAmB,EACtBG,OAAOC,OAAO,EAAET,KAAK,IAAI,GAErBU,IAAWC,MAAMC,KAAKT,EAAUU,iBAA8BN,CAAQ,CAAC;AAE7E,SAAKD,IAGEI,EAASF,OAAQM,CAAAA,MAAO;AAC7B,UAAMC,IAAQC,OAAOC,iBAAiBH,CAAE;AACxC,WACEC,EAAMG,YAAY,UAClBH,EAAMI,eAAe,YACrBJ,EAAMK,YAAY,OAClB,CAACN,EAAGO,aAAa,QAAQ,KACzBP,EAAGQ,cAAc,KACjBR,EAAGS,eAAe;AAAA,EAEtB,CAAC,IAbyBb;AAc5B;AAMO,SAASc,EACdC,GACoB;AACpB,QAAMC,IAAaxB,EAAqBuB,CAAO;AAC/C,SAAOC,EAAWC,SAAS,IAAID,EAAW,CAAC,IAAI;AACjD;"}
package/dist/index231.js CHANGED
@@ -1,22 +1,57 @@
1
- import { useEffect as s } from "react";
2
- const u = {
3
- block: "nearest"
4
- };
5
- function m({
6
- containerRef: t,
7
- activeIndex: o,
8
- itemSelector: r = '[role="option"]',
9
- enabled: c = !0,
10
- scrollOptions: e = u
1
+ import { useState as m, useEffect as w, useCallback as b } from "react";
2
+ import { useScrollActiveIntoView as x } from "./index232.js";
3
+ function E({
4
+ items: u,
5
+ isOpen: t,
6
+ onSelect: o,
7
+ onClose: c,
8
+ onOpen: l,
9
+ loop: i = !0,
10
+ disabled: h = !1,
11
+ listboxRef: k,
12
+ optionSelector: g = '[role="option"]'
11
13
  }) {
12
- s(() => {
13
- if (!c || o < 0 || !t?.current)
14
+ const [f, a] = m(-1);
15
+ w(() => {
16
+ t || a(-1);
17
+ }, [t]), x({
18
+ containerRef: k,
19
+ activeIndex: f,
20
+ itemSelector: g,
21
+ enabled: t
22
+ });
23
+ const D = b((r) => {
24
+ if (h) {
25
+ r.key === "Escape" && t && (r.preventDefault(), c());
14
26
  return;
15
- const n = t.current.querySelectorAll(r)[o];
16
- n && n.scrollIntoView(e);
17
- }, [o, t, r, c, e]);
27
+ }
28
+ const e = u.length;
29
+ switch (r.key) {
30
+ case "ArrowDown":
31
+ r.preventDefault(), !t && e > 0 ? (l?.(), a(0)) : t && e > 0 && a((n) => i ? (n + 1) % e : Math.min(n + 1, e - 1));
32
+ break;
33
+ case "ArrowUp":
34
+ r.preventDefault(), t && e > 0 && a((n) => n === -1 ? e - 1 : i ? (n - 1 + e) % e : Math.max(n - 1, 0));
35
+ break;
36
+ case "Enter":
37
+ t && f >= 0 && u[f] && (r.preventDefault(), o(u[f], f), a(-1));
38
+ break;
39
+ case "Escape":
40
+ t && (r.preventDefault(), c(), a(-1));
41
+ break;
42
+ case "Tab":
43
+ t && (c(), a(-1));
44
+ break;
45
+ }
46
+ }, [h, u, t, f, o, c, l, i]), d = b((r, e) => `${r}-option-${e}`, []);
47
+ return {
48
+ highlightedIndex: f,
49
+ setHighlightedIndex: a,
50
+ handleKeyDown: D,
51
+ getOptionId: d
52
+ };
18
53
  }
19
54
  export {
20
- m as useScrollActiveIntoView
55
+ E as useComboboxNavigation
21
56
  };
22
57
  //# sourceMappingURL=index231.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index231.js","sources":["../src/utils/a11y/useScrollActiveIntoView.ts"],"sourcesContent":["import { useEffect } from 'react';\nimport type { RefObject } from 'react';\n\nconst DEFAULT_SCROLL_OPTIONS: ScrollIntoViewOptions = { block: 'nearest' };\n\nexport interface UseScrollActiveIntoViewOptions {\n /**\n * Ref to the container element\n */\n containerRef?: RefObject<HTMLElement | null>;\n \n /**\n * Index of the currently active/highlighted item (-1 if none)\n */\n activeIndex: number;\n \n /**\n * CSS selector for item elements\n * Default: '[role=\"option\"]'\n */\n itemSelector?: string;\n \n /**\n * Whether scrolling is enabled\n * Default: true\n */\n enabled?: boolean;\n \n /**\n * ScrollIntoView options\n * Default: { block: 'nearest' }\n */\n scrollOptions?: ScrollIntoViewOptions;\n}\n\n/**\n * Hook to automatically scroll the active item into view.\n * \n * Useful for aria-activedescendant patterns where DOM focus stays\n * on the container (e.g., input field) but we need to visually show\n * which descendant option is logically active.\n * \n * Common use cases:\n * - Combobox dropdown options\n * - Menu items with virtual focus\n * - Grid cells with keyboard navigation\n * - Tree view items\n * - Listbox options\n * \n * @example\n * ```tsx\n * const [highlightedIndex, setHighlightedIndex] = useState(-1);\n * const listboxRef = useRef<HTMLDivElement>(null);\n * \n * useScrollActiveIntoView({\n * containerRef: listboxRef,\n * activeIndex: highlightedIndex,\n * itemSelector: '[role=\"option\"]'\n * });\n * \n * // Now when highlightedIndex changes, the item scrolls into view\n * ```\n * \n * @example Custom scroll behavior\n * ```tsx\n * useScrollActiveIntoView({\n * containerRef: menuRef,\n * activeIndex: activeMenuIndex,\n * itemSelector: '[role=\"menuitem\"]',\n * scrollOptions: { block: 'center', behavior: 'smooth' }\n * });\n * ```\n */\nexport function useScrollActiveIntoView({\n containerRef,\n activeIndex,\n itemSelector = '[role=\"option\"]',\n enabled = true,\n scrollOptions = DEFAULT_SCROLL_OPTIONS\n}: UseScrollActiveIntoViewOptions): void {\n useEffect(() => {\n // Early returns for disabled states\n if (!enabled || activeIndex < 0 || !containerRef?.current) {\n return;\n }\n \n const container = containerRef.current;\n const items = container.querySelectorAll(itemSelector);\n const activeItem = items[activeIndex] as HTMLElement;\n \n if (activeItem) {\n activeItem.scrollIntoView(scrollOptions);\n }\n }, [activeIndex, containerRef, itemSelector, enabled, scrollOptions]);\n}\n"],"names":["useEffect","DEFAULT_SCROLL_OPTIONS","block","useScrollActiveIntoView","containerRef","activeIndex","itemSelector","enabled","scrollOptions","current","activeItem","querySelectorAll","scrollIntoView"],"mappings":"AAGA,SAAA,aAAAA,SAAA;AAAA,MAAMC,IAAgD;AAAA,EAAEC,OAAO;AAAU;AAsElE,SAASC,EAAwB;AAAA,EACtCC,cAAAA;AAAAA,EACAC,aAAAA;AAAAA,EACAC,cAAAA,IAAe;AAAA,EACfC,SAAAA,IAAU;AAAA,EACVC,eAAAA,IAAgBP;AACc,GAAS;AACvCD,EAAAA,EAAU,MAAM;AAEd,QAAI,CAACO,KAAWF,IAAc,KAAK,CAACD,GAAcK;AAChD;AAKF,UAAMC,IAFYN,EAAaK,QACPE,iBAAiBL,CAAY,EAC5BD,CAAW;AAEpC,IAAIK,KACFA,EAAWE,eAAeJ,CAAa;AAAA,EAE3C,GAAG,CAACH,GAAaD,GAAcE,GAAcC,GAASC,CAAa,CAAC;AACtE;"}
1
+ {"version":3,"file":"index231.js","sources":["../src/utils/a11y/useComboboxNavigation.ts"],"sourcesContent":["import { useCallback, useState, useEffect } from 'react';\nimport type { RefObject } from 'react';\nimport { useScrollActiveIntoView } from './useScrollActiveIntoView';\n\nexport interface UseComboboxNavigationOptions<T = any> {\n /**\n * Array of items to navigate through\n */\n items: T[];\n \n /**\n * Whether the dropdown is currently open\n */\n isOpen: boolean;\n \n /**\n * Callback when an item is selected (Enter key)\n */\n onSelect: (item: T, index: number) => void;\n \n /**\n * Callback to close the dropdown\n */\n onClose: () => void;\n \n /**\n * Optional: Callback to open the dropdown\n */\n onOpen?: () => void;\n \n /**\n * Whether to wrap around at the ends of the list.\n * Default: true\n */\n loop?: boolean;\n \n /**\n * Whether keyboard navigation is disabled\n * (e.g., for custom rendered content)\n */\n disabled?: boolean;\n \n /**\n * Ref to the listbox container for scroll management\n */\n listboxRef?: RefObject<HTMLElement | null>;\n \n /**\n * CSS selector for option elements (default: '[role=\"option\"]')\n */\n optionSelector?: string;\n}\n\nexport interface UseComboboxNavigationReturn {\n /**\n * Currently highlighted index (-1 if none)\n */\n highlightedIndex: number;\n \n /**\n * Set the highlighted index manually\n */\n setHighlightedIndex: (index: number | ((prev: number) => number)) => void;\n \n /**\n * Keyboard event handler for the combobox input\n */\n handleKeyDown: (e: React.KeyboardEvent) => void;\n \n /**\n * Generate stable ID for an option\n */\n getOptionId: (listboxId: string, index: number) => string;\n \n}\n\n/**\n * Hook for managing combobox keyboard navigation with aria-activedescendant.\n * \n * Implements WAI-ARIA 1.2 Combobox pattern:\n * - Arrow Up/Down to navigate options\n * - Enter to select highlighted option\n * - Escape to close dropdown\n * - Tab to close and move focus\n * - Auto-scrolls highlighted option into view\n * \n * @example\n * ```tsx\n * const { \n * highlightedIndex, \n * handleKeyDown, \n * getOptionId \n * } = useComboboxNavigation({\n * items: suggestions,\n * isOpen: isDropdownOpen,\n * onSelect: (item, idx) => handleSelect(item),\n * onClose: () => setIsOpen(false),\n * listboxRef\n * });\n * \n * <input\n * role=\"combobox\"\n * onKeyDown={handleKeyDown}\n * aria-activedescendant={highlightedIndex >= 0 ? getOptionId(listboxId, highlightedIndex) : undefined}\n * />\n * ```\n */\nexport function useComboboxNavigation<T = any>({\n items,\n isOpen,\n onSelect,\n onClose,\n onOpen,\n loop = true,\n disabled = false,\n listboxRef,\n optionSelector = '[role=\"option\"]'\n}: UseComboboxNavigationOptions<T>): UseComboboxNavigationReturn {\n const [highlightedIndex, setHighlightedIndex] = useState<number>(-1);\n \n // Reset highlighted index when dropdown closes\n useEffect(() => {\n if (!isOpen) {\n setHighlightedIndex(-1);\n }\n }, [isOpen]);\n \n // Auto-scroll highlighted item into view\n useScrollActiveIntoView({\n containerRef: listboxRef,\n activeIndex: highlightedIndex,\n itemSelector: optionSelector,\n enabled: isOpen\n });\n \n const handleKeyDown = useCallback(\n (e: React.KeyboardEvent) => {\n if (disabled) {\n // For disabled navigation, still handle Escape\n if (e.key === 'Escape' && isOpen) {\n e.preventDefault();\n onClose();\n }\n return;\n }\n \n const itemCount = items.length;\n \n switch (e.key) {\n case 'ArrowDown':\n e.preventDefault();\n if (!isOpen && itemCount > 0) {\n // Open dropdown and highlight first item\n onOpen?.();\n setHighlightedIndex(0);\n } else if (isOpen && itemCount > 0) {\n // Navigate down\n setHighlightedIndex((prev) => {\n if (loop) {\n return (prev + 1) % itemCount;\n }\n return Math.min(prev + 1, itemCount - 1);\n });\n }\n break;\n \n case 'ArrowUp':\n e.preventDefault();\n if (isOpen && itemCount > 0) {\n // Navigate up\n setHighlightedIndex((prev) => {\n // If nothing highlighted, go to last item\n if (prev === -1) {\n return itemCount - 1;\n }\n if (loop) {\n return (prev - 1 + itemCount) % itemCount;\n }\n return Math.max(prev - 1, 0);\n });\n }\n break;\n \n case 'Enter':\n if (isOpen && highlightedIndex >= 0 && items[highlightedIndex]) {\n e.preventDefault();\n onSelect(items[highlightedIndex], highlightedIndex);\n setHighlightedIndex(-1);\n }\n break;\n \n case 'Escape':\n if (isOpen) {\n e.preventDefault();\n onClose();\n setHighlightedIndex(-1);\n }\n break;\n \n case 'Tab':\n // Close dropdown on Tab (don't preventDefault - let focus move naturally)\n if (isOpen) {\n onClose();\n setHighlightedIndex(-1);\n }\n break;\n }\n },\n [disabled, items, isOpen, highlightedIndex, onSelect, onClose, onOpen, loop]\n );\n \n const getOptionId = useCallback(\n (listboxId: string, index: number) => `${listboxId}-option-${index}`,\n []\n );\n \n return {\n highlightedIndex,\n setHighlightedIndex,\n handleKeyDown,\n getOptionId\n };\n}\n"],"names":["useState","useEffect","useCallback","useScrollActiveIntoView","useComboboxNavigation","items","isOpen","onSelect","onClose","onOpen","loop","disabled","listboxRef","optionSelector","highlightedIndex","setHighlightedIndex","containerRef","activeIndex","itemSelector","enabled","handleKeyDown","e","key","preventDefault","itemCount","length","prev","Math","min","max","getOptionId","listboxId","index"],"mappings":"AA2GO,SAAA,YAAAA,GAAA,aAAAC,GAAA,eAAAC,SAAA;AAAA,SAAA,2BAAAC,SAAA;AAAA,SAASC,EAA+B;AAAA,EAC7CC,OAAAA;AAAAA,EACAC,QAAAA;AAAAA,EACAC,UAAAA;AAAAA,EACAC,SAAAA;AAAAA,EACAC,QAAAA;AAAAA,EACAC,MAAAA,IAAO;AAAA,EACPC,UAAAA,IAAW;AAAA,EACXC,YAAAA;AAAAA,EACAC,gBAAAA,IAAiB;AACc,GAAgC;AAC/D,QAAM,CAACC,GAAkBC,CAAmB,IAAIf,EAAiB,EAAE;AAGnEC,EAAAA,EAAU,MAAM;AACd,IAAKK,KACHS,EAAoB,EAAE;AAAA,EAE1B,GAAG,CAACT,CAAM,CAAC,GAGXH,EAAwB;AAAA,IACtBa,cAAcJ;AAAAA,IACdK,aAAaH;AAAAA,IACbI,cAAcL;AAAAA,IACdM,SAASb;AAAAA,EAAAA,CACV;AAED,QAAMc,IAAgBlB,EACpB,CAACmB,MAA2B;AAC1B,QAAIV,GAAU;AAEZ,MAAIU,EAAEC,QAAQ,YAAYhB,MACxBe,EAAEE,eAAAA,GACFf,EAAAA;AAEF;AAAA,IACF;AAEA,UAAMgB,IAAYnB,EAAMoB;AAExB,YAAQJ,EAAEC,KAAAA;AAAAA,MACR,KAAK;AACHD,QAAAA,EAAEE,eAAAA,GACE,CAACjB,KAAUkB,IAAY,KAEzBf,IAAAA,GACAM,EAAoB,CAAC,KACZT,KAAUkB,IAAY,KAE/BT,EAAqBW,CAAAA,MACfhB,KACMgB,IAAO,KAAKF,IAEfG,KAAKC,IAAIF,IAAO,GAAGF,IAAY,CAAC,CACxC;AAEH;AAAA,MAEF,KAAK;AACHH,QAAAA,EAAEE,eAAAA,GACEjB,KAAUkB,IAAY,KAExBT,EAAqBW,CAAAA,MAEfA,MAAS,KACJF,IAAY,IAEjBd,KACMgB,IAAO,IAAIF,KAAaA,IAE3BG,KAAKE,IAAIH,IAAO,GAAG,CAAC,CAC5B;AAEH;AAAA,MAEF,KAAK;AACH,QAAIpB,KAAUQ,KAAoB,KAAKT,EAAMS,CAAgB,MAC3DO,EAAEE,eAAAA,GACFhB,EAASF,EAAMS,CAAgB,GAAGA,CAAgB,GAClDC,EAAoB,EAAE;AAExB;AAAA,MAEF,KAAK;AACH,QAAIT,MACFe,EAAEE,eAAAA,GACFf,EAAAA,GACAO,EAAoB,EAAE;AAExB;AAAA,MAEF,KAAK;AAEH,QAAIT,MACFE,EAAAA,GACAO,EAAoB,EAAE;AAExB;AAAA,IAAA;AAAA,EAEN,GACA,CAACJ,GAAUN,GAAOC,GAAQQ,GAAkBP,GAAUC,GAASC,GAAQC,CAAI,CAC7E,GAEMoB,IAAc5B,EAClB,CAAC6B,GAAmBC,MAAkB,GAAGD,CAAS,WAAWC,CAAK,IAClE,CAAA,CACF;AAEA,SAAO;AAAA,IACLlB,kBAAAA;AAAAA,IACAC,qBAAAA;AAAAA,IACAK,eAAAA;AAAAA,IACAU,aAAAA;AAAAA,EAAAA;AAEJ;"}
package/dist/index232.js CHANGED
@@ -1,13 +1,22 @@
1
- function r(t, i) {
2
- if (t == null) return {};
3
- var o = {};
4
- for (var e in t) if ({}.hasOwnProperty.call(t, e)) {
5
- if (i.indexOf(e) !== -1) continue;
6
- o[e] = t[e];
7
- }
8
- return o;
1
+ import { useEffect as s } from "react";
2
+ const u = {
3
+ block: "nearest"
4
+ };
5
+ function m({
6
+ containerRef: t,
7
+ activeIndex: o,
8
+ itemSelector: r = '[role="option"]',
9
+ enabled: c = !0,
10
+ scrollOptions: e = u
11
+ }) {
12
+ s(() => {
13
+ if (!c || o < 0 || !t?.current)
14
+ return;
15
+ const n = t.current.querySelectorAll(r)[o];
16
+ n && n.scrollIntoView(e);
17
+ }, [o, t, r, c, e]);
9
18
  }
10
19
  export {
11
- r as default
20
+ m as useScrollActiveIntoView
12
21
  };
13
22
  //# sourceMappingURL=index232.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index232.js","sources":["../node_modules/@babel/runtime/helpers/esm/objectWithoutPropertiesLoose.js"],"sourcesContent":["function _objectWithoutPropertiesLoose(r, e) {\n if (null == r) return {};\n var t = {};\n for (var n in r) if ({}.hasOwnProperty.call(r, n)) {\n if (-1 !== e.indexOf(n)) continue;\n t[n] = r[n];\n }\n return t;\n}\nexport { _objectWithoutPropertiesLoose as default };"],"names":["_objectWithoutPropertiesLoose","r","e","t","n"],"mappings":"AAAA,SAASA,EAA8BC,GAAGC,GAAG;AAC3C,MAAYD,KAAR,KAAW,QAAO,CAAA;AACtB,MAAIE,IAAI,CAAA;AACR,WAASC,KAAKH,EAAG,KAAI,CAAA,EAAG,eAAe,KAAKA,GAAGG,CAAC,GAAG;AACjD,QAAWF,EAAE,QAAQE,CAAC,MAAlB,GAAqB;AACzB,IAAAD,EAAEC,CAAC,IAAIH,EAAEG,CAAC;AAAA,EACZ;AACA,SAAOD;AACT;","x_google_ignoreList":[0]}
1
+ {"version":3,"file":"index232.js","sources":["../src/utils/a11y/useScrollActiveIntoView.ts"],"sourcesContent":["import { useEffect } from 'react';\nimport type { RefObject } from 'react';\n\nconst DEFAULT_SCROLL_OPTIONS: ScrollIntoViewOptions = { block: 'nearest' };\n\nexport interface UseScrollActiveIntoViewOptions {\n /**\n * Ref to the container element\n */\n containerRef?: RefObject<HTMLElement | null>;\n \n /**\n * Index of the currently active/highlighted item (-1 if none)\n */\n activeIndex: number;\n \n /**\n * CSS selector for item elements\n * Default: '[role=\"option\"]'\n */\n itemSelector?: string;\n \n /**\n * Whether scrolling is enabled\n * Default: true\n */\n enabled?: boolean;\n \n /**\n * ScrollIntoView options\n * Default: { block: 'nearest' }\n */\n scrollOptions?: ScrollIntoViewOptions;\n}\n\n/**\n * Hook to automatically scroll the active item into view.\n * \n * Useful for aria-activedescendant patterns where DOM focus stays\n * on the container (e.g., input field) but we need to visually show\n * which descendant option is logically active.\n * \n * Common use cases:\n * - Combobox dropdown options\n * - Menu items with virtual focus\n * - Grid cells with keyboard navigation\n * - Tree view items\n * - Listbox options\n * \n * @example\n * ```tsx\n * const [highlightedIndex, setHighlightedIndex] = useState(-1);\n * const listboxRef = useRef<HTMLDivElement>(null);\n * \n * useScrollActiveIntoView({\n * containerRef: listboxRef,\n * activeIndex: highlightedIndex,\n * itemSelector: '[role=\"option\"]'\n * });\n * \n * // Now when highlightedIndex changes, the item scrolls into view\n * ```\n * \n * @example Custom scroll behavior\n * ```tsx\n * useScrollActiveIntoView({\n * containerRef: menuRef,\n * activeIndex: activeMenuIndex,\n * itemSelector: '[role=\"menuitem\"]',\n * scrollOptions: { block: 'center', behavior: 'smooth' }\n * });\n * ```\n */\nexport function useScrollActiveIntoView({\n containerRef,\n activeIndex,\n itemSelector = '[role=\"option\"]',\n enabled = true,\n scrollOptions = DEFAULT_SCROLL_OPTIONS\n}: UseScrollActiveIntoViewOptions): void {\n useEffect(() => {\n // Early returns for disabled states\n if (!enabled || activeIndex < 0 || !containerRef?.current) {\n return;\n }\n \n const container = containerRef.current;\n const items = container.querySelectorAll(itemSelector);\n const activeItem = items[activeIndex] as HTMLElement;\n \n if (activeItem) {\n activeItem.scrollIntoView(scrollOptions);\n }\n }, [activeIndex, containerRef, itemSelector, enabled, scrollOptions]);\n}\n"],"names":["useEffect","DEFAULT_SCROLL_OPTIONS","block","useScrollActiveIntoView","containerRef","activeIndex","itemSelector","enabled","scrollOptions","current","activeItem","querySelectorAll","scrollIntoView"],"mappings":"AAGA,SAAA,aAAAA,SAAA;AAAA,MAAMC,IAAgD;AAAA,EAAEC,OAAO;AAAU;AAsElE,SAASC,EAAwB;AAAA,EACtCC,cAAAA;AAAAA,EACAC,aAAAA;AAAAA,EACAC,cAAAA,IAAe;AAAA,EACfC,SAAAA,IAAU;AAAA,EACVC,eAAAA,IAAgBP;AACc,GAAS;AACvCD,EAAAA,EAAU,MAAM;AAEd,QAAI,CAACO,KAAWF,IAAc,KAAK,CAACD,GAAcK;AAChD;AAKF,UAAMC,IAFYN,EAAaK,QACPE,iBAAiBL,CAAY,EAC5BD,CAAW;AAEpC,IAAIK,KACFA,EAAWE,eAAeJ,CAAa;AAAA,EAE3C,GAAG,CAACH,GAAaD,GAAcE,GAAcC,GAASC,CAAa,CAAC;AACtE;"}
package/dist/index233.js CHANGED
@@ -1,13 +1,13 @@
1
- function e() {
2
- return e = Object.assign ? Object.assign.bind() : function(t) {
3
- for (var n = 1; n < arguments.length; n++) {
4
- var a = arguments[n];
5
- for (var r in a) ({}).hasOwnProperty.call(a, r) && (t[r] = a[r]);
6
- }
7
- return t;
8
- }, e.apply(null, arguments);
1
+ function r(t, i) {
2
+ if (t == null) return {};
3
+ var o = {};
4
+ for (var e in t) if ({}.hasOwnProperty.call(t, e)) {
5
+ if (i.indexOf(e) !== -1) continue;
6
+ o[e] = t[e];
7
+ }
8
+ return o;
9
9
  }
10
10
  export {
11
- e as default
11
+ r as default
12
12
  };
13
13
  //# sourceMappingURL=index233.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index233.js","sources":["../node_modules/@babel/runtime/helpers/esm/extends.js"],"sourcesContent":["function _extends() {\n return _extends = Object.assign ? Object.assign.bind() : function (n) {\n for (var e = 1; e < arguments.length; e++) {\n var t = arguments[e];\n for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]);\n }\n return n;\n }, _extends.apply(null, arguments);\n}\nexport { _extends as default };"],"names":["_extends","n","e","t"],"mappings":"AAAA,SAASA,IAAW;AAClB,SAAOA,IAAW,OAAO,SAAS,OAAO,OAAO,KAAI,IAAK,SAAUC,GAAG;AACpE,aAASC,IAAI,GAAGA,IAAI,UAAU,QAAQA,KAAK;AACzC,UAAIC,IAAI,UAAUD,CAAC;AACnB,eAAS,KAAKC,EAAG,EAAC,CAAA,GAAI,eAAe,KAAKA,GAAG,CAAC,MAAMF,EAAE,CAAC,IAAIE,EAAE,CAAC;AAAA,IAChE;AACA,WAAOF;AAAA,EACT,GAAGD,EAAS,MAAM,MAAM,SAAS;AACnC;","x_google_ignoreList":[0]}
1
+ {"version":3,"file":"index233.js","sources":["../node_modules/@babel/runtime/helpers/esm/objectWithoutPropertiesLoose.js"],"sourcesContent":["function _objectWithoutPropertiesLoose(r, e) {\n if (null == r) return {};\n var t = {};\n for (var n in r) if ({}.hasOwnProperty.call(r, n)) {\n if (-1 !== e.indexOf(n)) continue;\n t[n] = r[n];\n }\n return t;\n}\nexport { _objectWithoutPropertiesLoose as default };"],"names":["_objectWithoutPropertiesLoose","r","e","t","n"],"mappings":"AAAA,SAASA,EAA8BC,GAAGC,GAAG;AAC3C,MAAYD,KAAR,KAAW,QAAO,CAAA;AACtB,MAAIE,IAAI,CAAA;AACR,WAASC,KAAKH,EAAG,KAAI,CAAA,EAAG,eAAe,KAAKA,GAAGG,CAAC,GAAG;AACjD,QAAWF,EAAE,QAAQE,CAAC,MAAlB,GAAqB;AACzB,IAAAD,EAAEC,CAAC,IAAIH,EAAEG,CAAC;AAAA,EACZ;AACA,SAAOD;AACT;","x_google_ignoreList":[0]}
package/dist/index234.js CHANGED
@@ -1,8 +1,13 @@
1
- import e from "./index237.js";
2
- function p(o, t) {
3
- o.prototype = Object.create(t.prototype), o.prototype.constructor = o, e(o, t);
1
+ function e() {
2
+ return e = Object.assign ? Object.assign.bind() : function(t) {
3
+ for (var n = 1; n < arguments.length; n++) {
4
+ var a = arguments[n];
5
+ for (var r in a) ({}).hasOwnProperty.call(a, r) && (t[r] = a[r]);
6
+ }
7
+ return t;
8
+ }, e.apply(null, arguments);
4
9
  }
5
10
  export {
6
- p as default
11
+ e as default
7
12
  };
8
13
  //# sourceMappingURL=index234.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index234.js","sources":["../node_modules/@babel/runtime/helpers/esm/inheritsLoose.js"],"sourcesContent":["import setPrototypeOf from \"./setPrototypeOf.js\";\nfunction _inheritsLoose(t, o) {\n t.prototype = Object.create(o.prototype), t.prototype.constructor = t, setPrototypeOf(t, o);\n}\nexport { _inheritsLoose as default };"],"names":["_setPrototypeOf","_inheritsLoose","t","o","setPrototypeOf"],"mappings":"AACA,OAAAA,OAAA;AAAA,SAASC,EAAeC,GAAGC,GAAG;AAC5B,EAAAD,EAAE,YAAY,OAAO,OAAOC,EAAE,SAAS,GAAGD,EAAE,UAAU,cAAcA,GAAGE,EAAeF,GAAGC,CAAC;AAC5F;","x_google_ignoreList":[0]}
1
+ {"version":3,"file":"index234.js","sources":["../node_modules/@babel/runtime/helpers/esm/extends.js"],"sourcesContent":["function _extends() {\n return _extends = Object.assign ? Object.assign.bind() : function (n) {\n for (var e = 1; e < arguments.length; e++) {\n var t = arguments[e];\n for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]);\n }\n return n;\n }, _extends.apply(null, arguments);\n}\nexport { _extends as default };"],"names":["_extends","n","e","t"],"mappings":"AAAA,SAASA,IAAW;AAClB,SAAOA,IAAW,OAAO,SAAS,OAAO,OAAO,KAAI,IAAK,SAAUC,GAAG;AACpE,aAASC,IAAI,GAAGA,IAAI,UAAU,QAAQA,KAAK;AACzC,UAAIC,IAAI,UAAUD,CAAC;AACnB,eAAS,KAAKC,EAAG,EAAC,CAAA,GAAI,eAAe,KAAKA,GAAG,CAAC,MAAMF,EAAE,CAAC,IAAIE,EAAE,CAAC;AAAA,IAChE;AACA,WAAOF;AAAA,EACT,GAAGD,EAAS,MAAM,MAAM,SAAS;AACnC;","x_google_ignoreList":[0]}
package/dist/index235.js CHANGED
@@ -1,173 +1,8 @@
1
- import { __spreadArray as D } from "./index238.js";
2
- import { parse as ut } from "./index239.js";
3
- var g = /* @__PURE__ */ new Map(), Y = function(t) {
4
- return t.cloneNode(!0);
5
- }, z = function() {
6
- return window.location.protocol === "file:";
7
- }, Z = function(t, o, n) {
8
- var e = new XMLHttpRequest();
9
- e.onreadystatechange = function() {
10
- try {
11
- if (!/\.svg/i.test(t) && e.readyState === 2) {
12
- var s = e.getResponseHeader("Content-Type");
13
- if (!s)
14
- throw new Error("Content type not found");
15
- var i = ut(s).type;
16
- if (!(i === "image/svg+xml" || i === "text/plain"))
17
- throw new Error("Invalid content type: ".concat(i));
18
- }
19
- if (e.readyState === 4) {
20
- if (e.status === 404 || e.responseXML === null)
21
- throw new Error(z() ? "Note: SVG injection ajax calls do not work locally without adjusting security settings in your browser. Or consider using a local webserver." : "Unable to load SVG file: " + t);
22
- if (e.status === 200 || z() && e.status === 0)
23
- n(null, e);
24
- else
25
- throw new Error("There was a problem injecting the SVG: " + e.status + " " + e.statusText);
26
- }
27
- } catch (a) {
28
- if (e.abort(), a instanceof Error)
29
- n(a, e);
30
- else
31
- throw a;
32
- }
33
- }, e.open("GET", t), e.withCredentials = o, e.overrideMimeType && e.overrideMimeType("text/xml"), e.send();
34
- }, v = {}, B = function(t, o) {
35
- v[t] = v[t] || [], v[t].push(o);
36
- }, ft = function(t) {
37
- for (var o = function(i, a) {
38
- setTimeout(function() {
39
- if (Array.isArray(v[t])) {
40
- var u = g.get(t), p = v[t][i];
41
- u instanceof SVGSVGElement && p(null, Y(u)), u instanceof Error && p(u), i === v[t].length - 1 && delete v[t];
42
- }
43
- }, 0);
44
- }, n = 0, e = v[t].length; n < e; n++)
45
- o(n);
46
- }, lt = function(t, o, n) {
47
- if (g.has(t)) {
48
- var e = g.get(t);
49
- if (e === void 0) {
50
- B(t, n);
51
- return;
52
- }
53
- if (e instanceof SVGSVGElement) {
54
- n(null, Y(e));
55
- return;
56
- }
57
- }
58
- g.set(t, void 0), B(t, n), Z(t, o, function(s, i) {
59
- var a;
60
- s ? g.set(t, s) : ((a = i.responseXML) === null || a === void 0 ? void 0 : a.documentElement) instanceof SVGSVGElement && g.set(t, i.responseXML.documentElement), ft(t);
61
- });
62
- }, ct = function(t, o, n) {
63
- Z(t, o, function(e, s) {
64
- var i;
65
- e ? n(e) : ((i = s.responseXML) === null || i === void 0 ? void 0 : i.documentElement) instanceof SVGSVGElement && n(null, s.responseXML.documentElement);
66
- });
67
- }, dt = 0, vt = function() {
68
- return ++dt;
69
- }, l = [], J = {}, pt = "http://www.w3.org/2000/svg", F = "http://www.w3.org/1999/xlink", K = function(t, o, n, e, s, i, a) {
70
- var u = t.getAttribute("data-src") || t.getAttribute("src");
71
- if (!u) {
72
- a(new Error("Invalid data-src or src attribute"));
73
- return;
74
- }
75
- if (l.indexOf(t) !== -1) {
76
- l.splice(l.indexOf(t), 1), t = null;
77
- return;
78
- }
79
- l.push(t), t.setAttribute("src", "");
80
- var p = e ? lt : ct;
81
- p(u, s, function(j, r) {
82
- if (!r) {
83
- l.splice(l.indexOf(t), 1), t = null, a(j);
84
- return;
85
- }
86
- var w = t.getAttribute("id");
87
- w && r.setAttribute("id", w);
88
- var S = t.getAttribute("title");
89
- S && r.setAttribute("title", S);
90
- var E = t.getAttribute("width");
91
- E && r.setAttribute("width", E);
92
- var y = t.getAttribute("height");
93
- y && r.setAttribute("height", y);
94
- var G = Array.from(new Set(D(D(D([], (r.getAttribute("class") || "").split(" "), !0), ["injected-svg"], !1), (t.getAttribute("class") || "").split(" "), !0))).join(" ").trim();
95
- r.setAttribute("class", G);
96
- var b = t.getAttribute("style");
97
- b && r.setAttribute("style", b), r.setAttribute("data-src", u);
98
- var R = [].filter.call(t.attributes, function(f) {
99
- return /^data-\w[\w-]*$/.test(f.name);
100
- });
101
- if (Array.prototype.forEach.call(R, function(f) {
102
- f.name && f.value && r.setAttribute(f.name, f.value);
103
- }), n) {
104
- var h = {
105
- clipPath: ["clip-path"],
106
- "color-profile": ["color-profile"],
107
- cursor: ["cursor"],
108
- filter: ["filter"],
109
- linearGradient: ["fill", "stroke"],
110
- marker: ["marker", "marker-start", "marker-mid", "marker-end"],
111
- mask: ["mask"],
112
- path: [],
113
- pattern: ["fill", "stroke"],
114
- radialGradient: ["fill", "stroke"]
115
- }, C, d, m, T, k;
116
- Object.keys(h).forEach(function(f) {
117
- C = f, m = h[f], d = r.querySelectorAll(C + "[id]");
118
- for (var nt = function(I, mt) {
119
- T = d[I].id, k = T + "-" + vt();
120
- var M;
121
- Array.prototype.forEach.call(m, function(W) {
122
- M = r.querySelectorAll("[" + W + '*="' + T + '"]');
123
- for (var O = 0, st = M.length; O < st; O++) {
124
- var $ = M[O].getAttribute(W);
125
- $ && !$.match(new RegExp('url\\("?#' + T + '"?\\)')) || M[O].setAttribute(W, "url(#" + k + ")");
126
- }
127
- });
128
- for (var U = r.querySelectorAll("[*|href]"), H = [], N = 0, at = U.length; N < at; N++) {
129
- var P = U[N].getAttributeNS(F, "href");
130
- P && P.toString() === "#" + d[I].id && H.push(U[N]);
131
- }
132
- for (var Q = 0, ot = H.length; Q < ot; Q++)
133
- H[Q].setAttributeNS(F, "href", "#" + k);
134
- d[I].id = k;
135
- }, _ = 0, it = d.length; _ < it; _++)
136
- nt(_);
137
- });
138
- }
139
- r.removeAttribute("xmlns:a");
140
- for (var x = r.querySelectorAll("script"), L = [], V, q, A = 0, tt = x.length; A < tt; A++)
141
- q = x[A].getAttribute("type"), (!q || q === "application/ecmascript" || q === "application/javascript" || q === "text/javascript") && (V = x[A].innerText || x[A].textContent, V && L.push(V), r.removeChild(x[A]));
142
- if (L.length > 0 && (o === "always" || o === "once" && !J[u])) {
143
- for (var X = 0, et = L.length; X < et; X++)
144
- new Function(L[X])(window);
145
- J[u] = !0;
146
- }
147
- var rt = r.querySelectorAll("style");
148
- if (Array.prototype.forEach.call(rt, function(f) {
149
- f.textContent += "";
150
- }), r.setAttribute("xmlns", pt), r.setAttribute("xmlns:xlink", F), i(r), !t.parentNode) {
151
- l.splice(l.indexOf(t), 1), t = null, a(new Error("Parent node is null"));
152
- return;
153
- }
154
- t.parentNode.replaceChild(r, t), l.splice(l.indexOf(t), 1), t = null, a(null, r);
155
- });
156
- }, wt = function(t, o) {
157
- var n = o === void 0 ? {} : o, e = n.afterAll, s = e === void 0 ? function() {
158
- } : e, i = n.afterEach, a = i === void 0 ? function() {
159
- } : i, u = n.beforeEach, p = u === void 0 ? function() {
160
- } : u, j = n.cacheRequests, r = j === void 0 ? !0 : j, w = n.evalScripts, S = w === void 0 ? "never" : w, E = n.httpRequestWithCredentials, y = E === void 0 ? !1 : E, G = n.renumerateIRIElements, b = G === void 0 ? !0 : G;
161
- if (t && "length" in t)
162
- for (var R = 0, h = 0, C = t.length; h < C; h++)
163
- K(t[h], S, b, r, y, p, function(d, m) {
164
- a(d, m), t && "length" in t && t.length === ++R && s(R);
165
- });
166
- else t ? K(t, S, b, r, y, p, function(d, m) {
167
- a(d, m), s(1), t = null;
168
- }) : s(0);
169
- };
1
+ import e from "./index238.js";
2
+ function p(o, t) {
3
+ o.prototype = Object.create(t.prototype), o.prototype.constructor = o, e(o, t);
4
+ }
170
5
  export {
171
- wt as SVGInjector
6
+ p as default
172
7
  };
173
8
  //# sourceMappingURL=index235.js.map