@k2b/ui 0.6.0 → 0.6.2
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/browser/feedback/toast.js +9 -5
- package/dist/browser/feedback/toast.js.map +1 -1
- package/dist/browser/layout/BottomSheet.js +10 -3
- package/dist/browser/layout/BottomSheet.js.map +1 -1
- package/dist/ssr/feedback/toast.js +9 -5
- package/dist/ssr/feedback/toast.js.map +1 -1
- package/dist/ssr/layout/BottomSheet.js +10 -3
- package/dist/ssr/layout/BottomSheet.js.map +1 -1
- package/dist/styles.css +1 -1
- package/dist/types/layout/BottomSheet.d.ts +1 -1
- package/package.json +1 -1
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { getK2bPortalRoot } from "../internal/portal";
|
|
2
|
+
import { resolveUiMessages } from "../intl/messages";
|
|
2
3
|
const DEFAULT_DURATION_MS = 3000;
|
|
3
4
|
const MAX_VISIBLE_TOASTS = 5;
|
|
4
5
|
const ANIMATION_MS = 200;
|
|
@@ -8,19 +9,22 @@ const VARIANT_STYLES = {
|
|
|
8
9
|
default: {
|
|
9
10
|
tone: "info",
|
|
10
11
|
iconClass: "ti-info-circle",
|
|
11
|
-
|
|
12
|
+
titleKey: "info"
|
|
12
13
|
},
|
|
13
14
|
success: {
|
|
14
15
|
tone: "success",
|
|
15
16
|
iconClass: "ti-check",
|
|
16
|
-
|
|
17
|
+
titleKey: "success"
|
|
17
18
|
},
|
|
18
19
|
error: {
|
|
19
20
|
tone: "danger",
|
|
20
21
|
iconClass: "ti-x",
|
|
21
|
-
|
|
22
|
+
titleKey: "error"
|
|
22
23
|
}
|
|
23
24
|
};
|
|
25
|
+
|
|
26
|
+
/** Default titles follow the document locale, like the other imperative `@k2b/ui` surfaces. */
|
|
27
|
+
const defaultTitle = variant => resolveUiMessages()[VARIANT_STYLES[variant].titleKey];
|
|
24
28
|
const normalizedIconClass = iconClass => {
|
|
25
29
|
const tokens = iconClass.split(/\s+/).filter(Boolean).filter(token => token !== "ti");
|
|
26
30
|
return ["ti", ...tokens].join(" ");
|
|
@@ -124,7 +128,7 @@ const showToast = (description, options) => {
|
|
|
124
128
|
applyLiveRegion(contentElement, currentVariant);
|
|
125
129
|
const titleElement = document.createElement("div");
|
|
126
130
|
titleElement.className = "k2b-toast__title";
|
|
127
|
-
titleElement.textContent = options?.title ??
|
|
131
|
+
titleElement.textContent = options?.title ?? defaultTitle(currentVariant);
|
|
128
132
|
const descriptionElement = document.createElement("div");
|
|
129
133
|
descriptionElement.className = "k2b-toast__description";
|
|
130
134
|
descriptionElement.textContent = description;
|
|
@@ -219,7 +223,7 @@ const showToast = (description, options) => {
|
|
|
219
223
|
if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, "title")) {
|
|
220
224
|
titleElement.textContent = nextOptions.title ?? "";
|
|
221
225
|
} else if (variantChanged) {
|
|
222
|
-
titleElement.textContent =
|
|
226
|
+
titleElement.textContent = defaultTitle(currentVariant);
|
|
223
227
|
}
|
|
224
228
|
if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, "action")) renderAction(nextOptions.action);
|
|
225
229
|
if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, "duration")) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["feedback/toast.ts"],"sourcesContent":["import { getK2bPortalRoot } from \"../internal/portal\";\n\nexport type ToastVariant = \"default\" | \"success\" | \"error\";\n\nexport type ToastAction = {\n label: string;\n} & ({ href: string } | { onClick: () => void });\n\nexport type ToastOptions = {\n variant?: ToastVariant;\n duration?: number;\n iconClass?: string;\n title?: string;\n action?: ToastAction | null;\n /** Fraction from 0 to 1, or an indeterminate activity indicator. null removes it. */\n progress?: number | \"indeterminate\" | null;\n dismissLabel?: string;\n};\n\nexport type ToastHandle = {\n dismiss: () => void;\n update: (description: string, options?: ToastOptions) => void;\n};\n\nexport interface ToastFn {\n (description: string, options?: ToastOptions): ToastHandle;\n success: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n error: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n dismissAll: () => void;\n}\n\nconst DEFAULT_DURATION_MS = 3000;\nconst MAX_VISIBLE_TOASTS = 5;\nconst ANIMATION_MS = 200;\nexport const K2B_TOAST_CONTAINER_ID = \"k2b-ui-toast-container\";\nconst CONTAINER_ATTRIBUTE = \"data-k2b-toast-container\";\n\ntype VariantStyle = {\n tone: \"info\" | \"success\" | \"danger\";\n iconClass: string;\n defaultTitle: string;\n};\n\nconst VARIANT_STYLES: Record<ToastVariant, VariantStyle> = {\n default: {\n tone: \"info\",\n iconClass: \"ti-info-circle\",\n defaultTitle: \"Info\",\n },\n success: {\n tone: \"success\",\n iconClass: \"ti-check\",\n defaultTitle: \"Success\",\n },\n error: {\n tone: \"danger\",\n iconClass: \"ti-x\",\n defaultTitle: \"Error\",\n },\n};\n\nconst normalizedIconClass = (iconClass: string): string => {\n const tokens = iconClass\n .split(/\\s+/)\n .filter(Boolean)\n .filter((token) => token !== \"ti\");\n return [\"ti\", ...tokens].join(\" \");\n};\n\nconst applyIconClass = (icon: HTMLElement, iconClass: string): void => {\n icon.className = normalizedIconClass(iconClass);\n};\n\nconst applyLiveRegion = (element: HTMLElement, variant: ToastVariant): void => {\n const isError = variant === \"error\";\n element.setAttribute(\"role\", isError ? \"alert\" : \"status\");\n element.setAttribute(\"aria-live\", isError ? \"assertive\" : \"polite\");\n element.setAttribute(\"aria-atomic\", \"true\");\n};\n\nconst liveToasts = new Set<ToastHandle>();\n\nconst ensureContainer = (): HTMLElement | null => {\n if (typeof document === \"undefined\") return null;\n const root = getK2bPortalRoot();\n let container = root.querySelector<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`);\n if (container) return container;\n\n container = document.createElement(\"div\");\n container.id = K2B_TOAST_CONTAINER_ID;\n container.setAttribute(CONTAINER_ATTRIBUTE, \"\");\n container.setAttribute(\"popover\", \"manual\");\n // Keep the source rail geometry inline: it must defeat UA popover defaults\n // even when a consumer has not loaded the optional package stylesheet yet.\n container.style.cssText =\n \"position:fixed;top:auto;left:auto;bottom:env(safe-area-inset-bottom,0px);right:env(safe-area-inset-right,0px);\" +\n \"z-index:50;box-sizing:border-box;display:flex;flex-direction:column;gap:0.5rem;\" +\n \"width:min(22rem,calc(100vw - env(safe-area-inset-left,0px) - env(safe-area-inset-right,0px)));\" +\n \"height:auto;max-width:100vw;\" +\n \"max-height:calc(100dvh - env(safe-area-inset-top,0px) - env(safe-area-inset-bottom,0px));\" +\n \"margin:0;padding:1rem;border:0;background:transparent;overflow-x:hidden;overflow-y:auto;overscroll-behavior:contain;\" +\n \"pointer-events:none;\";\n root.appendChild(container);\n return container;\n};\n\nconst promoteToTopLayer = (container: HTMLElement): HTMLElement => {\n if (typeof container.showPopover !== \"function\" || !container.isConnected) return container;\n let active = container;\n try {\n if (container.matches(\":popover-open\") || document.querySelector(\"dialog:modal\")) {\n const next = container.cloneNode(false) as HTMLElement;\n while (container.firstChild) next.appendChild(container.firstChild);\n const root = container.parentElement ?? getK2bPortalRoot();\n container.remove();\n root.appendChild(next);\n active = next;\n }\n if (!active.matches(\":popover-open\")) active.showPopover();\n } catch {\n active.removeAttribute(\"popover\");\n }\n return active;\n};\n\n/** Close every empty rail so an emptied container does not linger in the top\n * layer. Rails are resolved at call time on purpose: `promoteToTopLayer`\n * swaps the element for a fresh clone, so a container captured when the toast\n * was created can already be detached by the time the toast is dismissed. */\nconst hideEmptyContainers = (): void => {\n if (typeof document === \"undefined\") return;\n for (const container of Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`))) {\n if (container.childElementCount > 0 || typeof container.hidePopover !== \"function\") continue;\n try {\n if (container.matches(\":popover-open\")) container.hidePopover();\n } catch {\n // Already hidden or disconnected.\n }\n }\n};\n\nconst renderLead = (lead: HTMLElement, variant: ToastVariant, iconClassOverride?: string): HTMLElement => {\n const style = VARIANT_STYLES[variant];\n lead.replaceChildren();\n lead.className = \"k2b-toast__icon\";\n lead.dataset.tone = style.tone;\n const icon = document.createElement(\"i\");\n applyIconClass(icon, iconClassOverride ?? style.iconClass);\n icon.setAttribute(\"aria-hidden\", \"true\");\n lead.appendChild(icon);\n return icon;\n};\n\nconst showToast = (description: string, options?: ToastOptions): ToastHandle => {\n const initialContainer = ensureContainer();\n if (!initialContainer) {\n const noop = () => {};\n return { dismiss: noop, update: noop };\n }\n\n let dismissed = false;\n let dismissTimer: ReturnType<typeof setTimeout> | null = null;\n let currentVariant: ToastVariant = options?.variant ?? \"default\";\n let currentProgress = options?.progress ?? null;\n let currentDuration = options?.duration ?? DEFAULT_DURATION_MS;\n let remainingDuration = currentDuration;\n let timerStartedAt = 0;\n let pausedByPointer = false;\n let pausedByFocus = false;\n\n const toastElement = document.createElement(\"div\");\n toastElement.className = \"k2b-toast\";\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n toastElement.dataset.k2bToast = \"\";\n\n const leadElement = document.createElement(\"div\");\n let leadIconElement = renderLead(leadElement, currentVariant, options?.iconClass);\n\n const contentElement = document.createElement(\"div\");\n contentElement.className = \"k2b-toast__content\";\n applyLiveRegion(contentElement, currentVariant);\n\n const titleElement = document.createElement(\"div\");\n titleElement.className = \"k2b-toast__title\";\n titleElement.textContent = options?.title ?? VARIANT_STYLES[currentVariant].defaultTitle;\n const descriptionElement = document.createElement(\"div\");\n descriptionElement.className = \"k2b-toast__description\";\n descriptionElement.textContent = description;\n contentElement.append(titleElement, descriptionElement);\n\n const closeButton = document.createElement(\"button\");\n closeButton.type = \"button\";\n closeButton.className = \"k2b-toast__close\";\n closeButton.setAttribute(\"aria-label\", options?.dismissLabel ?? \"Dismiss notification\");\n const closeIcon = document.createElement(\"i\");\n closeIcon.className = \"ti ti-x\";\n closeIcon.setAttribute(\"aria-hidden\", \"true\");\n closeButton.appendChild(closeIcon);\n\n toastElement.append(leadElement, contentElement, closeButton);\n\n const clearDismissTimer = () => {\n if (dismissTimer === null) return;\n clearTimeout(dismissTimer);\n dismissTimer = null;\n };\n\n const pauseDismissTimer = () => {\n if (dismissTimer === null) return;\n remainingDuration = Math.max(0, remainingDuration - (Date.now() - timerStartedAt));\n clearDismissTimer();\n };\n\n const resumeDismissTimer = () => {\n if (dismissed || currentProgress !== null || currentDuration === 0 || remainingDuration <= 0 || pausedByPointer || pausedByFocus)\n return;\n clearDismissTimer();\n timerStartedAt = Date.now();\n dismissTimer = setTimeout(() => dismiss(), remainingDuration);\n };\n\n const resetDismissTimer = (duration: number) => {\n clearDismissTimer();\n currentDuration = duration;\n remainingDuration = duration;\n resumeDismissTimer();\n };\n\n const dismiss = () => {\n if (dismissed) return;\n dismissed = true;\n clearDismissTimer();\n liveToasts.delete(handle);\n toastElement.dataset.closing = \"true\";\n setTimeout(() => {\n toastElement.remove();\n hideEmptyContainers();\n }, ANIMATION_MS);\n };\n\n const progressElement = document.createElement(\"progress\");\n progressElement.className = \"k2b-toast__progress\";\n progressElement.max = 1;\n const renderProgress = () => {\n progressElement.hidden = currentProgress === null;\n progressElement.setAttribute(\"aria-label\", titleElement.textContent || descriptionElement.textContent || \"\");\n if (typeof currentProgress === \"number\")\n progressElement.value = Number.isFinite(currentProgress) ? Math.max(0, Math.min(1, currentProgress)) : 0;\n else progressElement.removeAttribute(\"value\");\n };\n contentElement.append(progressElement);\n renderProgress();\n let actionElement: HTMLAnchorElement | HTMLButtonElement | null = null;\n const renderAction = (action: ToastAction | null | undefined) => {\n actionElement?.remove();\n actionElement = null;\n if (!action) return;\n if (\"href\" in action) {\n const link = document.createElement(\"a\");\n link.href = action.href;\n actionElement = link;\n } else {\n const button = document.createElement(\"button\");\n button.type = \"button\";\n actionElement = button;\n }\n actionElement.className = \"k2b-toast__action\";\n actionElement.textContent = action.label;\n actionElement.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n if (\"onClick\" in action) action.onClick();\n else dismiss();\n });\n contentElement.appendChild(actionElement);\n };\n renderAction(options?.action);\n\n const update = (nextDescription: string, nextOptions?: ToastOptions) => {\n if (dismissed) return;\n descriptionElement.textContent = nextDescription;\n\n const variantChanged = nextOptions?.variant !== undefined && nextOptions.variant !== currentVariant;\n if (variantChanged) {\n currentVariant = nextOptions.variant!;\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n leadIconElement = renderLead(leadElement, currentVariant, nextOptions.iconClass);\n applyLiveRegion(contentElement, currentVariant);\n } else if (nextOptions?.iconClass !== undefined) {\n applyIconClass(leadIconElement, nextOptions.iconClass);\n }\n\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"title\")) {\n titleElement.textContent = nextOptions.title ?? \"\";\n } else if (variantChanged) {\n titleElement.textContent = VARIANT_STYLES[currentVariant].defaultTitle;\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"action\")) renderAction(nextOptions.action);\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"duration\")) {\n currentDuration = nextOptions.duration ?? DEFAULT_DURATION_MS;\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"progress\")) currentProgress = nextOptions.progress ?? null;\n if (nextOptions?.dismissLabel) closeButton.setAttribute(\"aria-label\", nextOptions.dismissLabel);\n renderProgress();\n resetDismissTimer(currentDuration);\n };\n\n toastElement.addEventListener(\"click\", () => {\n if (currentProgress === null) dismiss();\n });\n closeButton.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n dismiss();\n });\n toastElement.addEventListener(\"pointerenter\", () => {\n pausedByPointer = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"pointerleave\", () => {\n pausedByPointer = false;\n resumeDismissTimer();\n });\n toastElement.addEventListener(\"focusin\", () => {\n pausedByFocus = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"focusout\", (event) => {\n if (toastElement.contains(event.relatedTarget as Node | null)) return;\n pausedByFocus = false;\n resumeDismissTimer();\n });\n\n const handle: ToastHandle = { dismiss, update };\n liveToasts.add(handle);\n if (liveToasts.size > MAX_VISIBLE_TOASTS) liveToasts.values().next().value?.dismiss();\n promoteToTopLayer(initialContainer).appendChild(toastElement);\n requestAnimationFrame(() => {\n if (!dismissed) toastElement.dataset.open = \"true\";\n });\n resetDismissTimer(currentDuration);\n return handle;\n};\n\nexport const isPointInsideToast = (x: number, y: number): boolean => {\n if (typeof document === \"undefined\") return false;\n const containers = Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`));\n for (const container of containers) {\n for (const child of Array.from(container.children)) {\n const rect = child.getBoundingClientRect();\n if (x >= rect.left && x <= rect.right && y >= rect.top && y <= rect.bottom) return true;\n }\n }\n return false;\n};\n\nconst toastFn = ((description: string, options?: ToastOptions) => showToast(description, options)) as ToastFn;\ntoastFn.success = (description, options) => showToast(description, { ...options, variant: \"success\" });\ntoastFn.error = (description, options) => showToast(description, { ...options, variant: \"error\" });\ntoastFn.dismissAll = () => {\n for (const handle of Array.from(liveToasts)) handle.dismiss();\n};\n\nexport const toast: ToastFn = toastFn;\n"],"mappings":"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","ignoreList":[]}
|
|
1
|
+
{"version":3,"names":[],"sources":["feedback/toast.ts"],"sourcesContent":["import { getK2bPortalRoot } from \"../internal/portal\";\nimport { resolveUiMessages } from \"../intl/messages\";\n\nexport type ToastVariant = \"default\" | \"success\" | \"error\";\n\nexport type ToastAction = {\n label: string;\n} & ({ href: string } | { onClick: () => void });\n\nexport type ToastOptions = {\n variant?: ToastVariant;\n duration?: number;\n iconClass?: string;\n title?: string;\n action?: ToastAction | null;\n /** Fraction from 0 to 1, or an indeterminate activity indicator. null removes it. */\n progress?: number | \"indeterminate\" | null;\n dismissLabel?: string;\n};\n\nexport type ToastHandle = {\n dismiss: () => void;\n update: (description: string, options?: ToastOptions) => void;\n};\n\nexport interface ToastFn {\n (description: string, options?: ToastOptions): ToastHandle;\n success: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n error: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n dismissAll: () => void;\n}\n\nconst DEFAULT_DURATION_MS = 3000;\nconst MAX_VISIBLE_TOASTS = 5;\nconst ANIMATION_MS = 200;\nexport const K2B_TOAST_CONTAINER_ID = \"k2b-ui-toast-container\";\nconst CONTAINER_ATTRIBUTE = \"data-k2b-toast-container\";\n\ntype VariantStyle = {\n tone: \"info\" | \"success\" | \"danger\";\n iconClass: string;\n titleKey: \"info\" | \"success\" | \"error\";\n};\n\nconst VARIANT_STYLES: Record<ToastVariant, VariantStyle> = {\n default: {\n tone: \"info\",\n iconClass: \"ti-info-circle\",\n titleKey: \"info\",\n },\n success: {\n tone: \"success\",\n iconClass: \"ti-check\",\n titleKey: \"success\",\n },\n error: {\n tone: \"danger\",\n iconClass: \"ti-x\",\n titleKey: \"error\",\n },\n};\n\n/** Default titles follow the document locale, like the other imperative `@k2b/ui` surfaces. */\nconst defaultTitle = (variant: ToastVariant): string => resolveUiMessages()[VARIANT_STYLES[variant].titleKey];\n\nconst normalizedIconClass = (iconClass: string): string => {\n const tokens = iconClass\n .split(/\\s+/)\n .filter(Boolean)\n .filter((token) => token !== \"ti\");\n return [\"ti\", ...tokens].join(\" \");\n};\n\nconst applyIconClass = (icon: HTMLElement, iconClass: string): void => {\n icon.className = normalizedIconClass(iconClass);\n};\n\nconst applyLiveRegion = (element: HTMLElement, variant: ToastVariant): void => {\n const isError = variant === \"error\";\n element.setAttribute(\"role\", isError ? \"alert\" : \"status\");\n element.setAttribute(\"aria-live\", isError ? \"assertive\" : \"polite\");\n element.setAttribute(\"aria-atomic\", \"true\");\n};\n\nconst liveToasts = new Set<ToastHandle>();\n\nconst ensureContainer = (): HTMLElement | null => {\n if (typeof document === \"undefined\") return null;\n const root = getK2bPortalRoot();\n let container = root.querySelector<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`);\n if (container) return container;\n\n container = document.createElement(\"div\");\n container.id = K2B_TOAST_CONTAINER_ID;\n container.setAttribute(CONTAINER_ATTRIBUTE, \"\");\n container.setAttribute(\"popover\", \"manual\");\n // Keep the source rail geometry inline: it must defeat UA popover defaults\n // even when a consumer has not loaded the optional package stylesheet yet.\n container.style.cssText =\n \"position:fixed;top:auto;left:auto;bottom:env(safe-area-inset-bottom,0px);right:env(safe-area-inset-right,0px);\" +\n \"z-index:50;box-sizing:border-box;display:flex;flex-direction:column;gap:0.5rem;\" +\n \"width:min(22rem,calc(100vw - env(safe-area-inset-left,0px) - env(safe-area-inset-right,0px)));\" +\n \"height:auto;max-width:100vw;\" +\n \"max-height:calc(100dvh - env(safe-area-inset-top,0px) - env(safe-area-inset-bottom,0px));\" +\n \"margin:0;padding:1rem;border:0;background:transparent;overflow-x:hidden;overflow-y:auto;overscroll-behavior:contain;\" +\n \"pointer-events:none;\";\n root.appendChild(container);\n return container;\n};\n\nconst promoteToTopLayer = (container: HTMLElement): HTMLElement => {\n if (typeof container.showPopover !== \"function\" || !container.isConnected) return container;\n let active = container;\n try {\n if (container.matches(\":popover-open\") || document.querySelector(\"dialog:modal\")) {\n const next = container.cloneNode(false) as HTMLElement;\n while (container.firstChild) next.appendChild(container.firstChild);\n const root = container.parentElement ?? getK2bPortalRoot();\n container.remove();\n root.appendChild(next);\n active = next;\n }\n if (!active.matches(\":popover-open\")) active.showPopover();\n } catch {\n active.removeAttribute(\"popover\");\n }\n return active;\n};\n\n/** Close every empty rail so an emptied container does not linger in the top\n * layer. Rails are resolved at call time on purpose: `promoteToTopLayer`\n * swaps the element for a fresh clone, so a container captured when the toast\n * was created can already be detached by the time the toast is dismissed. */\nconst hideEmptyContainers = (): void => {\n if (typeof document === \"undefined\") return;\n for (const container of Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`))) {\n if (container.childElementCount > 0 || typeof container.hidePopover !== \"function\") continue;\n try {\n if (container.matches(\":popover-open\")) container.hidePopover();\n } catch {\n // Already hidden or disconnected.\n }\n }\n};\n\nconst renderLead = (lead: HTMLElement, variant: ToastVariant, iconClassOverride?: string): HTMLElement => {\n const style = VARIANT_STYLES[variant];\n lead.replaceChildren();\n lead.className = \"k2b-toast__icon\";\n lead.dataset.tone = style.tone;\n const icon = document.createElement(\"i\");\n applyIconClass(icon, iconClassOverride ?? style.iconClass);\n icon.setAttribute(\"aria-hidden\", \"true\");\n lead.appendChild(icon);\n return icon;\n};\n\nconst showToast = (description: string, options?: ToastOptions): ToastHandle => {\n const initialContainer = ensureContainer();\n if (!initialContainer) {\n const noop = () => {};\n return { dismiss: noop, update: noop };\n }\n\n let dismissed = false;\n let dismissTimer: ReturnType<typeof setTimeout> | null = null;\n let currentVariant: ToastVariant = options?.variant ?? \"default\";\n let currentProgress = options?.progress ?? null;\n let currentDuration = options?.duration ?? DEFAULT_DURATION_MS;\n let remainingDuration = currentDuration;\n let timerStartedAt = 0;\n let pausedByPointer = false;\n let pausedByFocus = false;\n\n const toastElement = document.createElement(\"div\");\n toastElement.className = \"k2b-toast\";\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n toastElement.dataset.k2bToast = \"\";\n\n const leadElement = document.createElement(\"div\");\n let leadIconElement = renderLead(leadElement, currentVariant, options?.iconClass);\n\n const contentElement = document.createElement(\"div\");\n contentElement.className = \"k2b-toast__content\";\n applyLiveRegion(contentElement, currentVariant);\n\n const titleElement = document.createElement(\"div\");\n titleElement.className = \"k2b-toast__title\";\n titleElement.textContent = options?.title ?? defaultTitle(currentVariant);\n const descriptionElement = document.createElement(\"div\");\n descriptionElement.className = \"k2b-toast__description\";\n descriptionElement.textContent = description;\n contentElement.append(titleElement, descriptionElement);\n\n const closeButton = document.createElement(\"button\");\n closeButton.type = \"button\";\n closeButton.className = \"k2b-toast__close\";\n closeButton.setAttribute(\"aria-label\", options?.dismissLabel ?? \"Dismiss notification\");\n const closeIcon = document.createElement(\"i\");\n closeIcon.className = \"ti ti-x\";\n closeIcon.setAttribute(\"aria-hidden\", \"true\");\n closeButton.appendChild(closeIcon);\n\n toastElement.append(leadElement, contentElement, closeButton);\n\n const clearDismissTimer = () => {\n if (dismissTimer === null) return;\n clearTimeout(dismissTimer);\n dismissTimer = null;\n };\n\n const pauseDismissTimer = () => {\n if (dismissTimer === null) return;\n remainingDuration = Math.max(0, remainingDuration - (Date.now() - timerStartedAt));\n clearDismissTimer();\n };\n\n const resumeDismissTimer = () => {\n if (dismissed || currentProgress !== null || currentDuration === 0 || remainingDuration <= 0 || pausedByPointer || pausedByFocus)\n return;\n clearDismissTimer();\n timerStartedAt = Date.now();\n dismissTimer = setTimeout(() => dismiss(), remainingDuration);\n };\n\n const resetDismissTimer = (duration: number) => {\n clearDismissTimer();\n currentDuration = duration;\n remainingDuration = duration;\n resumeDismissTimer();\n };\n\n const dismiss = () => {\n if (dismissed) return;\n dismissed = true;\n clearDismissTimer();\n liveToasts.delete(handle);\n toastElement.dataset.closing = \"true\";\n setTimeout(() => {\n toastElement.remove();\n hideEmptyContainers();\n }, ANIMATION_MS);\n };\n\n const progressElement = document.createElement(\"progress\");\n progressElement.className = \"k2b-toast__progress\";\n progressElement.max = 1;\n const renderProgress = () => {\n progressElement.hidden = currentProgress === null;\n progressElement.setAttribute(\"aria-label\", titleElement.textContent || descriptionElement.textContent || \"\");\n if (typeof currentProgress === \"number\")\n progressElement.value = Number.isFinite(currentProgress) ? Math.max(0, Math.min(1, currentProgress)) : 0;\n else progressElement.removeAttribute(\"value\");\n };\n contentElement.append(progressElement);\n renderProgress();\n let actionElement: HTMLAnchorElement | HTMLButtonElement | null = null;\n const renderAction = (action: ToastAction | null | undefined) => {\n actionElement?.remove();\n actionElement = null;\n if (!action) return;\n if (\"href\" in action) {\n const link = document.createElement(\"a\");\n link.href = action.href;\n actionElement = link;\n } else {\n const button = document.createElement(\"button\");\n button.type = \"button\";\n actionElement = button;\n }\n actionElement.className = \"k2b-toast__action\";\n actionElement.textContent = action.label;\n actionElement.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n if (\"onClick\" in action) action.onClick();\n else dismiss();\n });\n contentElement.appendChild(actionElement);\n };\n renderAction(options?.action);\n\n const update = (nextDescription: string, nextOptions?: ToastOptions) => {\n if (dismissed) return;\n descriptionElement.textContent = nextDescription;\n\n const variantChanged = nextOptions?.variant !== undefined && nextOptions.variant !== currentVariant;\n if (variantChanged) {\n currentVariant = nextOptions.variant!;\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n leadIconElement = renderLead(leadElement, currentVariant, nextOptions.iconClass);\n applyLiveRegion(contentElement, currentVariant);\n } else if (nextOptions?.iconClass !== undefined) {\n applyIconClass(leadIconElement, nextOptions.iconClass);\n }\n\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"title\")) {\n titleElement.textContent = nextOptions.title ?? \"\";\n } else if (variantChanged) {\n titleElement.textContent = defaultTitle(currentVariant);\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"action\")) renderAction(nextOptions.action);\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"duration\")) {\n currentDuration = nextOptions.duration ?? DEFAULT_DURATION_MS;\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"progress\")) currentProgress = nextOptions.progress ?? null;\n if (nextOptions?.dismissLabel) closeButton.setAttribute(\"aria-label\", nextOptions.dismissLabel);\n renderProgress();\n resetDismissTimer(currentDuration);\n };\n\n toastElement.addEventListener(\"click\", () => {\n if (currentProgress === null) dismiss();\n });\n closeButton.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n dismiss();\n });\n toastElement.addEventListener(\"pointerenter\", () => {\n pausedByPointer = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"pointerleave\", () => {\n pausedByPointer = false;\n resumeDismissTimer();\n });\n toastElement.addEventListener(\"focusin\", () => {\n pausedByFocus = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"focusout\", (event) => {\n if (toastElement.contains(event.relatedTarget as Node | null)) return;\n pausedByFocus = false;\n resumeDismissTimer();\n });\n\n const handle: ToastHandle = { dismiss, update };\n liveToasts.add(handle);\n if (liveToasts.size > MAX_VISIBLE_TOASTS) liveToasts.values().next().value?.dismiss();\n promoteToTopLayer(initialContainer).appendChild(toastElement);\n requestAnimationFrame(() => {\n if (!dismissed) toastElement.dataset.open = \"true\";\n });\n resetDismissTimer(currentDuration);\n return handle;\n};\n\nexport const isPointInsideToast = (x: number, y: number): boolean => {\n if (typeof document === \"undefined\") return false;\n const containers = Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`));\n for (const container of containers) {\n for (const child of Array.from(container.children)) {\n const rect = child.getBoundingClientRect();\n if (x >= rect.left && x <= rect.right && y >= rect.top && y <= rect.bottom) return true;\n }\n }\n return false;\n};\n\nconst toastFn = ((description: string, options?: ToastOptions) => showToast(description, options)) as ToastFn;\ntoastFn.success = (description, options) => showToast(description, { ...options, variant: \"success\" });\ntoastFn.error = (description, options) => showToast(description, { ...options, variant: \"error\" });\ntoastFn.dismissAll = () => {\n for (const handle of Array.from(liveToasts)) handle.dismiss();\n};\n\nexport const toast: ToastFn = toastFn;\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -12,9 +12,16 @@ import { Show } from "solid-js";
|
|
|
12
12
|
import { useUiMessages } from "../intl/messages";
|
|
13
13
|
import PanelDialog from "./PanelDialog";
|
|
14
14
|
|
|
15
|
-
/** Initial focus goes to the first input of the top sheet
|
|
16
|
-
*
|
|
17
|
-
|
|
15
|
+
/** Initial focus goes to the first input of the top sheet, otherwise to the
|
|
16
|
+
* dialog element itself. Native `showModal()` focuses the first focusable
|
|
17
|
+
* descendant, which is the drag handle; iOS shows a ring for that programmatic
|
|
18
|
+
* focus, so the sheet moves it to the ring-less dialog before the next paint. */
|
|
19
|
+
const sheetInitialFocus = dialog => {
|
|
20
|
+
const input = dialog.lastElementChild?.querySelector("input:not([type='hidden']):not([disabled]), textarea:not([disabled]), select:not([disabled]), [role='combobox']:not([disabled]):not([aria-disabled='true'])");
|
|
21
|
+
if (input) return input;
|
|
22
|
+
dialog.tabIndex = -1;
|
|
23
|
+
return dialog;
|
|
24
|
+
};
|
|
18
25
|
export const bottomSheetOptions = {
|
|
19
26
|
panelClassName: "k2b-dialog k2b-bottom-sheet-frame",
|
|
20
27
|
contentClassName: "k2b-panel-dialog-viewport k2b-bottom-sheet-viewport",
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["layout/BottomSheet.tsx"],"sourcesContent":["import { type JSX, Show } from \"solid-js\";\nimport type { OpenDialogOptions } from \"../feedback/dialog-core\";\nimport { useUiMessages } from \"../intl/messages\";\nimport PanelDialog from \"./PanelDialog\";\n\n/** Initial focus goes to the first input of the top sheet
|
|
1
|
+
{"version":3,"names":[],"sources":["layout/BottomSheet.tsx"],"sourcesContent":["import { type JSX, Show } from \"solid-js\";\nimport type { OpenDialogOptions } from \"../feedback/dialog-core\";\nimport { useUiMessages } from \"../intl/messages\";\nimport PanelDialog from \"./PanelDialog\";\n\n/** Initial focus goes to the first input of the top sheet, otherwise to the\n * dialog element itself. Native `showModal()` focuses the first focusable\n * descendant, which is the drag handle; iOS shows a ring for that programmatic\n * focus, so the sheet moves it to the ring-less dialog before the next paint. */\nconst sheetInitialFocus = (dialog: HTMLDialogElement): HTMLElement => {\n const input = dialog.lastElementChild?.querySelector<HTMLElement>(\n \"input:not([type='hidden']):not([disabled]), textarea:not([disabled]), select:not([disabled]), [role='combobox']:not([disabled]):not([aria-disabled='true'])\",\n );\n if (input) return input;\n dialog.tabIndex = -1;\n return dialog;\n};\n\nexport const bottomSheetOptions = {\n panelClassName: \"k2b-dialog k2b-bottom-sheet-frame\",\n contentClassName: \"k2b-panel-dialog-viewport k2b-bottom-sheet-viewport\",\n initialFocus: sheetInitialFocus,\n} satisfies OpenDialogOptions;\n\nexport type BottomSheetProps = {\n children: JSX.Element;\n /** Pass dialogCore's render context requestDismiss, never the completion callback. */\n onDismiss: () => void | Promise<void>;\n dismissDisabled?: boolean;\n dismissLabel?: string;\n handle?: boolean;\n};\n\nfunction BottomSheetRoot(props: BottomSheetProps) {\n const messages = useUiMessages();\n let pointer: { id: number; y: number } | undefined;\n let suppressClick = false;\n const dismiss = () => {\n if (!props.dismissDisabled) void props.onDismiss();\n };\n return (\n <PanelDialog>\n <Show when={props.handle !== false}>\n <button\n type=\"button\"\n class=\"k2b-bottom-sheet__handle\"\n aria-label={props.dismissLabel ?? messages().close}\n disabled={props.dismissDisabled}\n onPointerDown={(event) => {\n if (!event.isPrimary || event.button !== 0 || props.dismissDisabled) return;\n suppressClick = false;\n pointer = { id: event.pointerId, y: event.clientY };\n event.currentTarget.setPointerCapture(event.pointerId);\n }}\n onPointerUp={(event) => {\n if (pointer?.id !== event.pointerId) return;\n const distance = event.clientY - pointer.y;\n pointer = undefined;\n // A drag must not turn into a second dismiss request through click.\n suppressClick = Math.abs(distance) > 8;\n if (distance > 60) dismiss();\n }}\n onPointerCancel={() => {\n pointer = undefined;\n suppressClick = true;\n }}\n onLostPointerCapture={() => {\n if (pointer) {\n pointer = undefined;\n suppressClick = true;\n }\n }}\n onClick={(event) => {\n if (event.detail !== 0 && suppressClick) {\n suppressClick = false;\n return;\n }\n dismiss();\n }}\n >\n <span aria-hidden=\"true\" />\n </button>\n </Show>\n {props.children}\n </PanelDialog>\n );\n}\n\n/** Bottom-edge presentation; dialogCore continues to own all modal state. */\nconst BottomSheet = Object.assign(BottomSheetRoot, {\n Header: PanelDialog.Header,\n Body: PanelDialog.Body,\n Footer: PanelDialog.Footer,\n Section: PanelDialog.Section,\n Tabs: PanelDialog.Tabs,\n});\nexport default BottomSheet;\n"],"mappings":";;;;;;;;;;AAAA,SAAmB,IAAI,QAAQ,UAAU;AAEzC,SAAS,aAAa,QAAQ,kBAAkB;AAChD,OAAO,WAAW,MAAM,eAAe;;AAEvC;AACA;AACA;AACA;AACA,MAAM,iBAAiB,GAAI,MAAyB,IAAkB;EACpE,MAAM,KAAK,GAAG,MAAM,CAAC,gBAAgB,EAAE,aAAa,CAClD,6JACF,CAAC;EACD,IAAI,KAAK,EAAE,OAAO,KAAK;EACvB,MAAM,CAAC,QAAQ,GAAG,CAAC,CAAC;EACpB,OAAO,MAAM;AACf,CAAC;AAED,OAAO,MAAM,kBAAkB,GAAG;EAChC,cAAc,EAAE,mCAAmC;EACnD,gBAAgB,EAAE,qDAAqD;EACvE,YAAY,EAAE;AAChB,CAA6B;AAW7B,SAAS,eAAe,CAAC,KAAuB,EAAE;EAChD,MAAM,QAAQ,GAAG,aAAa,CAAC,CAAC;EAChC,IAAI,OAA8C;EAClD,IAAI,aAAa,GAAG,KAAK;EACzB,MAAM,OAAO,GAAG,MAAM;IACpB,IAAI,CAAC,KAAK,CAAC,eAAe,EAAE,KAAK,KAAK,CAAC,SAAS,CAAC,CAAC;EACpD,CAAC;EACD,yBACG,WAAW;IAAA;MAAA,0BACT,IAAI;QAAA,IAAC,IAAI;UAAA,OAAE,KAAK,CAAC,MAAM,KAAK,KAAK;QAAA;QAAA;UAAA;UAAA,eA8BpB,KAAK,IAAK;YAClB,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,IAAI,aAAa,EAAE;cACvC,aAAa,GAAG,KAAK;cACrB;YACF;YACA,OAAO,CAAC,CAAC;UACX,CAAC;UAAA,4CAZqB,MAAM;YAC1B,IAAI,OAAO,EAAE;cACX,OAAO,GAAG,SAAS;cACnB,aAAa,GAAG,IAAI;YACtB;UACF,CAAC;UAAA,uCATgB,MAAM;YACrB,OAAO,GAAG,SAAS;YACnB,aAAa,GAAG,IAAI;UACtB,CAAC;UAAA,mBAXa,KAAK,IAAK;YACtB,IAAI,OAAO,EAAE,EAAE,KAAK,KAAK,CAAC,SAAS,EAAE;YACrC,MAAM,QAAQ,GAAG,KAAK,CAAC,OAAO,GAAG,OAAO,CAAC,CAAC;YAC1C,OAAO,GAAG,SAAS;YACnB;YACA,aAAa,GAAG,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC;YACtC,IAAI,QAAQ,GAAG,EAAE,EAAE,OAAO,CAAC,CAAC;UAC9B,CAAC;UAAA,qBAbe,KAAK,IAAK;YACxB,IAAI,CAAC,KAAK,CAAC,SAAS,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,IAAI,KAAK,CAAC,eAAe,EAAE;YACrE,aAAa,GAAG,KAAK;YACrB,OAAO,GAAG;cAAE,EAAE,EAAE,KAAK,CAAC,SAAS;cAAE,CAAC,EAAE,KAAK,CAAC;YAAQ,CAAC;YACnD,KAAK,CAAC,aAAa,CAAC,iBAAiB,CAAC,KAAK,CAAC,SAAS,CAAC;UACxD,CAAC;UAAA;YAAA,UAPW,KAAK,CAAC,YAAY,IAAI,QAAQ,CAAC,CAAC,CAAC,KAAK;cAAA,OACxC,KAAK,CAAC,eAAe;YAAA;YAAA;YAAA;UAAA;YAAA;YAAA;UAAA;UAAA;UAAA;QAAA;MAAA,iBAoClC,KAAK,CAAC,QAAQ;IAAA;EAAA;AAGrB;;AAEA;AACA,MAAM,WAAW,GAAG,MAAM,CAAC,MAAM,CAAC,eAAe,EAAE;EACjD,MAAM,EAAE,WAAW,CAAC,MAAM;EAC1B,IAAI,EAAE,WAAW,CAAC,IAAI;EACtB,MAAM,EAAE,WAAW,CAAC,MAAM;EAC1B,OAAO,EAAE,WAAW,CAAC,OAAO;EAC5B,IAAI,EAAE,WAAW,CAAC;AACpB,CAAC,CAAC;AACF,eAAe,WAAW;AAAC","ignoreList":[]}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { getK2bPortalRoot } from "../internal/portal";
|
|
2
|
+
import { resolveUiMessages } from "../intl/messages";
|
|
2
3
|
const DEFAULT_DURATION_MS = 3000;
|
|
3
4
|
const MAX_VISIBLE_TOASTS = 5;
|
|
4
5
|
const ANIMATION_MS = 200;
|
|
@@ -8,19 +9,22 @@ const VARIANT_STYLES = {
|
|
|
8
9
|
default: {
|
|
9
10
|
tone: "info",
|
|
10
11
|
iconClass: "ti-info-circle",
|
|
11
|
-
|
|
12
|
+
titleKey: "info"
|
|
12
13
|
},
|
|
13
14
|
success: {
|
|
14
15
|
tone: "success",
|
|
15
16
|
iconClass: "ti-check",
|
|
16
|
-
|
|
17
|
+
titleKey: "success"
|
|
17
18
|
},
|
|
18
19
|
error: {
|
|
19
20
|
tone: "danger",
|
|
20
21
|
iconClass: "ti-x",
|
|
21
|
-
|
|
22
|
+
titleKey: "error"
|
|
22
23
|
}
|
|
23
24
|
};
|
|
25
|
+
|
|
26
|
+
/** Default titles follow the document locale, like the other imperative `@k2b/ui` surfaces. */
|
|
27
|
+
const defaultTitle = variant => resolveUiMessages()[VARIANT_STYLES[variant].titleKey];
|
|
24
28
|
const normalizedIconClass = iconClass => {
|
|
25
29
|
const tokens = iconClass.split(/\s+/).filter(Boolean).filter(token => token !== "ti");
|
|
26
30
|
return ["ti", ...tokens].join(" ");
|
|
@@ -124,7 +128,7 @@ const showToast = (description, options) => {
|
|
|
124
128
|
applyLiveRegion(contentElement, currentVariant);
|
|
125
129
|
const titleElement = document.createElement("div");
|
|
126
130
|
titleElement.className = "k2b-toast__title";
|
|
127
|
-
titleElement.textContent = options?.title ??
|
|
131
|
+
titleElement.textContent = options?.title ?? defaultTitle(currentVariant);
|
|
128
132
|
const descriptionElement = document.createElement("div");
|
|
129
133
|
descriptionElement.className = "k2b-toast__description";
|
|
130
134
|
descriptionElement.textContent = description;
|
|
@@ -219,7 +223,7 @@ const showToast = (description, options) => {
|
|
|
219
223
|
if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, "title")) {
|
|
220
224
|
titleElement.textContent = nextOptions.title ?? "";
|
|
221
225
|
} else if (variantChanged) {
|
|
222
|
-
titleElement.textContent =
|
|
226
|
+
titleElement.textContent = defaultTitle(currentVariant);
|
|
223
227
|
}
|
|
224
228
|
if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, "action")) renderAction(nextOptions.action);
|
|
225
229
|
if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, "duration")) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["feedback/toast.ts"],"sourcesContent":["import { getK2bPortalRoot } from \"../internal/portal\";\n\nexport type ToastVariant = \"default\" | \"success\" | \"error\";\n\nexport type ToastAction = {\n label: string;\n} & ({ href: string } | { onClick: () => void });\n\nexport type ToastOptions = {\n variant?: ToastVariant;\n duration?: number;\n iconClass?: string;\n title?: string;\n action?: ToastAction | null;\n /** Fraction from 0 to 1, or an indeterminate activity indicator. null removes it. */\n progress?: number | \"indeterminate\" | null;\n dismissLabel?: string;\n};\n\nexport type ToastHandle = {\n dismiss: () => void;\n update: (description: string, options?: ToastOptions) => void;\n};\n\nexport interface ToastFn {\n (description: string, options?: ToastOptions): ToastHandle;\n success: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n error: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n dismissAll: () => void;\n}\n\nconst DEFAULT_DURATION_MS = 3000;\nconst MAX_VISIBLE_TOASTS = 5;\nconst ANIMATION_MS = 200;\nexport const K2B_TOAST_CONTAINER_ID = \"k2b-ui-toast-container\";\nconst CONTAINER_ATTRIBUTE = \"data-k2b-toast-container\";\n\ntype VariantStyle = {\n tone: \"info\" | \"success\" | \"danger\";\n iconClass: string;\n defaultTitle: string;\n};\n\nconst VARIANT_STYLES: Record<ToastVariant, VariantStyle> = {\n default: {\n tone: \"info\",\n iconClass: \"ti-info-circle\",\n defaultTitle: \"Info\",\n },\n success: {\n tone: \"success\",\n iconClass: \"ti-check\",\n defaultTitle: \"Success\",\n },\n error: {\n tone: \"danger\",\n iconClass: \"ti-x\",\n defaultTitle: \"Error\",\n },\n};\n\nconst normalizedIconClass = (iconClass: string): string => {\n const tokens = iconClass\n .split(/\\s+/)\n .filter(Boolean)\n .filter((token) => token !== \"ti\");\n return [\"ti\", ...tokens].join(\" \");\n};\n\nconst applyIconClass = (icon: HTMLElement, iconClass: string): void => {\n icon.className = normalizedIconClass(iconClass);\n};\n\nconst applyLiveRegion = (element: HTMLElement, variant: ToastVariant): void => {\n const isError = variant === \"error\";\n element.setAttribute(\"role\", isError ? \"alert\" : \"status\");\n element.setAttribute(\"aria-live\", isError ? \"assertive\" : \"polite\");\n element.setAttribute(\"aria-atomic\", \"true\");\n};\n\nconst liveToasts = new Set<ToastHandle>();\n\nconst ensureContainer = (): HTMLElement | null => {\n if (typeof document === \"undefined\") return null;\n const root = getK2bPortalRoot();\n let container = root.querySelector<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`);\n if (container) return container;\n\n container = document.createElement(\"div\");\n container.id = K2B_TOAST_CONTAINER_ID;\n container.setAttribute(CONTAINER_ATTRIBUTE, \"\");\n container.setAttribute(\"popover\", \"manual\");\n // Keep the source rail geometry inline: it must defeat UA popover defaults\n // even when a consumer has not loaded the optional package stylesheet yet.\n container.style.cssText =\n \"position:fixed;top:auto;left:auto;bottom:env(safe-area-inset-bottom,0px);right:env(safe-area-inset-right,0px);\" +\n \"z-index:50;box-sizing:border-box;display:flex;flex-direction:column;gap:0.5rem;\" +\n \"width:min(22rem,calc(100vw - env(safe-area-inset-left,0px) - env(safe-area-inset-right,0px)));\" +\n \"height:auto;max-width:100vw;\" +\n \"max-height:calc(100dvh - env(safe-area-inset-top,0px) - env(safe-area-inset-bottom,0px));\" +\n \"margin:0;padding:1rem;border:0;background:transparent;overflow-x:hidden;overflow-y:auto;overscroll-behavior:contain;\" +\n \"pointer-events:none;\";\n root.appendChild(container);\n return container;\n};\n\nconst promoteToTopLayer = (container: HTMLElement): HTMLElement => {\n if (typeof container.showPopover !== \"function\" || !container.isConnected) return container;\n let active = container;\n try {\n if (container.matches(\":popover-open\") || document.querySelector(\"dialog:modal\")) {\n const next = container.cloneNode(false) as HTMLElement;\n while (container.firstChild) next.appendChild(container.firstChild);\n const root = container.parentElement ?? getK2bPortalRoot();\n container.remove();\n root.appendChild(next);\n active = next;\n }\n if (!active.matches(\":popover-open\")) active.showPopover();\n } catch {\n active.removeAttribute(\"popover\");\n }\n return active;\n};\n\n/** Close every empty rail so an emptied container does not linger in the top\n * layer. Rails are resolved at call time on purpose: `promoteToTopLayer`\n * swaps the element for a fresh clone, so a container captured when the toast\n * was created can already be detached by the time the toast is dismissed. */\nconst hideEmptyContainers = (): void => {\n if (typeof document === \"undefined\") return;\n for (const container of Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`))) {\n if (container.childElementCount > 0 || typeof container.hidePopover !== \"function\") continue;\n try {\n if (container.matches(\":popover-open\")) container.hidePopover();\n } catch {\n // Already hidden or disconnected.\n }\n }\n};\n\nconst renderLead = (lead: HTMLElement, variant: ToastVariant, iconClassOverride?: string): HTMLElement => {\n const style = VARIANT_STYLES[variant];\n lead.replaceChildren();\n lead.className = \"k2b-toast__icon\";\n lead.dataset.tone = style.tone;\n const icon = document.createElement(\"i\");\n applyIconClass(icon, iconClassOverride ?? style.iconClass);\n icon.setAttribute(\"aria-hidden\", \"true\");\n lead.appendChild(icon);\n return icon;\n};\n\nconst showToast = (description: string, options?: ToastOptions): ToastHandle => {\n const initialContainer = ensureContainer();\n if (!initialContainer) {\n const noop = () => {};\n return { dismiss: noop, update: noop };\n }\n\n let dismissed = false;\n let dismissTimer: ReturnType<typeof setTimeout> | null = null;\n let currentVariant: ToastVariant = options?.variant ?? \"default\";\n let currentProgress = options?.progress ?? null;\n let currentDuration = options?.duration ?? DEFAULT_DURATION_MS;\n let remainingDuration = currentDuration;\n let timerStartedAt = 0;\n let pausedByPointer = false;\n let pausedByFocus = false;\n\n const toastElement = document.createElement(\"div\");\n toastElement.className = \"k2b-toast\";\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n toastElement.dataset.k2bToast = \"\";\n\n const leadElement = document.createElement(\"div\");\n let leadIconElement = renderLead(leadElement, currentVariant, options?.iconClass);\n\n const contentElement = document.createElement(\"div\");\n contentElement.className = \"k2b-toast__content\";\n applyLiveRegion(contentElement, currentVariant);\n\n const titleElement = document.createElement(\"div\");\n titleElement.className = \"k2b-toast__title\";\n titleElement.textContent = options?.title ?? VARIANT_STYLES[currentVariant].defaultTitle;\n const descriptionElement = document.createElement(\"div\");\n descriptionElement.className = \"k2b-toast__description\";\n descriptionElement.textContent = description;\n contentElement.append(titleElement, descriptionElement);\n\n const closeButton = document.createElement(\"button\");\n closeButton.type = \"button\";\n closeButton.className = \"k2b-toast__close\";\n closeButton.setAttribute(\"aria-label\", options?.dismissLabel ?? \"Dismiss notification\");\n const closeIcon = document.createElement(\"i\");\n closeIcon.className = \"ti ti-x\";\n closeIcon.setAttribute(\"aria-hidden\", \"true\");\n closeButton.appendChild(closeIcon);\n\n toastElement.append(leadElement, contentElement, closeButton);\n\n const clearDismissTimer = () => {\n if (dismissTimer === null) return;\n clearTimeout(dismissTimer);\n dismissTimer = null;\n };\n\n const pauseDismissTimer = () => {\n if (dismissTimer === null) return;\n remainingDuration = Math.max(0, remainingDuration - (Date.now() - timerStartedAt));\n clearDismissTimer();\n };\n\n const resumeDismissTimer = () => {\n if (dismissed || currentProgress !== null || currentDuration === 0 || remainingDuration <= 0 || pausedByPointer || pausedByFocus)\n return;\n clearDismissTimer();\n timerStartedAt = Date.now();\n dismissTimer = setTimeout(() => dismiss(), remainingDuration);\n };\n\n const resetDismissTimer = (duration: number) => {\n clearDismissTimer();\n currentDuration = duration;\n remainingDuration = duration;\n resumeDismissTimer();\n };\n\n const dismiss = () => {\n if (dismissed) return;\n dismissed = true;\n clearDismissTimer();\n liveToasts.delete(handle);\n toastElement.dataset.closing = \"true\";\n setTimeout(() => {\n toastElement.remove();\n hideEmptyContainers();\n }, ANIMATION_MS);\n };\n\n const progressElement = document.createElement(\"progress\");\n progressElement.className = \"k2b-toast__progress\";\n progressElement.max = 1;\n const renderProgress = () => {\n progressElement.hidden = currentProgress === null;\n progressElement.setAttribute(\"aria-label\", titleElement.textContent || descriptionElement.textContent || \"\");\n if (typeof currentProgress === \"number\")\n progressElement.value = Number.isFinite(currentProgress) ? Math.max(0, Math.min(1, currentProgress)) : 0;\n else progressElement.removeAttribute(\"value\");\n };\n contentElement.append(progressElement);\n renderProgress();\n let actionElement: HTMLAnchorElement | HTMLButtonElement | null = null;\n const renderAction = (action: ToastAction | null | undefined) => {\n actionElement?.remove();\n actionElement = null;\n if (!action) return;\n if (\"href\" in action) {\n const link = document.createElement(\"a\");\n link.href = action.href;\n actionElement = link;\n } else {\n const button = document.createElement(\"button\");\n button.type = \"button\";\n actionElement = button;\n }\n actionElement.className = \"k2b-toast__action\";\n actionElement.textContent = action.label;\n actionElement.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n if (\"onClick\" in action) action.onClick();\n else dismiss();\n });\n contentElement.appendChild(actionElement);\n };\n renderAction(options?.action);\n\n const update = (nextDescription: string, nextOptions?: ToastOptions) => {\n if (dismissed) return;\n descriptionElement.textContent = nextDescription;\n\n const variantChanged = nextOptions?.variant !== undefined && nextOptions.variant !== currentVariant;\n if (variantChanged) {\n currentVariant = nextOptions.variant!;\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n leadIconElement = renderLead(leadElement, currentVariant, nextOptions.iconClass);\n applyLiveRegion(contentElement, currentVariant);\n } else if (nextOptions?.iconClass !== undefined) {\n applyIconClass(leadIconElement, nextOptions.iconClass);\n }\n\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"title\")) {\n titleElement.textContent = nextOptions.title ?? \"\";\n } else if (variantChanged) {\n titleElement.textContent = VARIANT_STYLES[currentVariant].defaultTitle;\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"action\")) renderAction(nextOptions.action);\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"duration\")) {\n currentDuration = nextOptions.duration ?? DEFAULT_DURATION_MS;\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"progress\")) currentProgress = nextOptions.progress ?? null;\n if (nextOptions?.dismissLabel) closeButton.setAttribute(\"aria-label\", nextOptions.dismissLabel);\n renderProgress();\n resetDismissTimer(currentDuration);\n };\n\n toastElement.addEventListener(\"click\", () => {\n if (currentProgress === null) dismiss();\n });\n closeButton.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n dismiss();\n });\n toastElement.addEventListener(\"pointerenter\", () => {\n pausedByPointer = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"pointerleave\", () => {\n pausedByPointer = false;\n resumeDismissTimer();\n });\n toastElement.addEventListener(\"focusin\", () => {\n pausedByFocus = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"focusout\", (event) => {\n if (toastElement.contains(event.relatedTarget as Node | null)) return;\n pausedByFocus = false;\n resumeDismissTimer();\n });\n\n const handle: ToastHandle = { dismiss, update };\n liveToasts.add(handle);\n if (liveToasts.size > MAX_VISIBLE_TOASTS) liveToasts.values().next().value?.dismiss();\n promoteToTopLayer(initialContainer).appendChild(toastElement);\n requestAnimationFrame(() => {\n if (!dismissed) toastElement.dataset.open = \"true\";\n });\n resetDismissTimer(currentDuration);\n return handle;\n};\n\nexport const isPointInsideToast = (x: number, y: number): boolean => {\n if (typeof document === \"undefined\") return false;\n const containers = Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`));\n for (const container of containers) {\n for (const child of Array.from(container.children)) {\n const rect = child.getBoundingClientRect();\n if (x >= rect.left && x <= rect.right && y >= rect.top && y <= rect.bottom) return true;\n }\n }\n return false;\n};\n\nconst toastFn = ((description: string, options?: ToastOptions) => showToast(description, options)) as ToastFn;\ntoastFn.success = (description, options) => showToast(description, { ...options, variant: \"success\" });\ntoastFn.error = (description, options) => showToast(description, { ...options, variant: \"error\" });\ntoastFn.dismissAll = () => {\n for (const handle of Array.from(liveToasts)) handle.dismiss();\n};\n\nexport const toast: ToastFn = toastFn;\n"],"mappings":"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","ignoreList":[]}
|
|
1
|
+
{"version":3,"names":[],"sources":["feedback/toast.ts"],"sourcesContent":["import { getK2bPortalRoot } from \"../internal/portal\";\nimport { resolveUiMessages } from \"../intl/messages\";\n\nexport type ToastVariant = \"default\" | \"success\" | \"error\";\n\nexport type ToastAction = {\n label: string;\n} & ({ href: string } | { onClick: () => void });\n\nexport type ToastOptions = {\n variant?: ToastVariant;\n duration?: number;\n iconClass?: string;\n title?: string;\n action?: ToastAction | null;\n /** Fraction from 0 to 1, or an indeterminate activity indicator. null removes it. */\n progress?: number | \"indeterminate\" | null;\n dismissLabel?: string;\n};\n\nexport type ToastHandle = {\n dismiss: () => void;\n update: (description: string, options?: ToastOptions) => void;\n};\n\nexport interface ToastFn {\n (description: string, options?: ToastOptions): ToastHandle;\n success: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n error: (description: string, options?: Omit<ToastOptions, \"variant\">) => ToastHandle;\n dismissAll: () => void;\n}\n\nconst DEFAULT_DURATION_MS = 3000;\nconst MAX_VISIBLE_TOASTS = 5;\nconst ANIMATION_MS = 200;\nexport const K2B_TOAST_CONTAINER_ID = \"k2b-ui-toast-container\";\nconst CONTAINER_ATTRIBUTE = \"data-k2b-toast-container\";\n\ntype VariantStyle = {\n tone: \"info\" | \"success\" | \"danger\";\n iconClass: string;\n titleKey: \"info\" | \"success\" | \"error\";\n};\n\nconst VARIANT_STYLES: Record<ToastVariant, VariantStyle> = {\n default: {\n tone: \"info\",\n iconClass: \"ti-info-circle\",\n titleKey: \"info\",\n },\n success: {\n tone: \"success\",\n iconClass: \"ti-check\",\n titleKey: \"success\",\n },\n error: {\n tone: \"danger\",\n iconClass: \"ti-x\",\n titleKey: \"error\",\n },\n};\n\n/** Default titles follow the document locale, like the other imperative `@k2b/ui` surfaces. */\nconst defaultTitle = (variant: ToastVariant): string => resolveUiMessages()[VARIANT_STYLES[variant].titleKey];\n\nconst normalizedIconClass = (iconClass: string): string => {\n const tokens = iconClass\n .split(/\\s+/)\n .filter(Boolean)\n .filter((token) => token !== \"ti\");\n return [\"ti\", ...tokens].join(\" \");\n};\n\nconst applyIconClass = (icon: HTMLElement, iconClass: string): void => {\n icon.className = normalizedIconClass(iconClass);\n};\n\nconst applyLiveRegion = (element: HTMLElement, variant: ToastVariant): void => {\n const isError = variant === \"error\";\n element.setAttribute(\"role\", isError ? \"alert\" : \"status\");\n element.setAttribute(\"aria-live\", isError ? \"assertive\" : \"polite\");\n element.setAttribute(\"aria-atomic\", \"true\");\n};\n\nconst liveToasts = new Set<ToastHandle>();\n\nconst ensureContainer = (): HTMLElement | null => {\n if (typeof document === \"undefined\") return null;\n const root = getK2bPortalRoot();\n let container = root.querySelector<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`);\n if (container) return container;\n\n container = document.createElement(\"div\");\n container.id = K2B_TOAST_CONTAINER_ID;\n container.setAttribute(CONTAINER_ATTRIBUTE, \"\");\n container.setAttribute(\"popover\", \"manual\");\n // Keep the source rail geometry inline: it must defeat UA popover defaults\n // even when a consumer has not loaded the optional package stylesheet yet.\n container.style.cssText =\n \"position:fixed;top:auto;left:auto;bottom:env(safe-area-inset-bottom,0px);right:env(safe-area-inset-right,0px);\" +\n \"z-index:50;box-sizing:border-box;display:flex;flex-direction:column;gap:0.5rem;\" +\n \"width:min(22rem,calc(100vw - env(safe-area-inset-left,0px) - env(safe-area-inset-right,0px)));\" +\n \"height:auto;max-width:100vw;\" +\n \"max-height:calc(100dvh - env(safe-area-inset-top,0px) - env(safe-area-inset-bottom,0px));\" +\n \"margin:0;padding:1rem;border:0;background:transparent;overflow-x:hidden;overflow-y:auto;overscroll-behavior:contain;\" +\n \"pointer-events:none;\";\n root.appendChild(container);\n return container;\n};\n\nconst promoteToTopLayer = (container: HTMLElement): HTMLElement => {\n if (typeof container.showPopover !== \"function\" || !container.isConnected) return container;\n let active = container;\n try {\n if (container.matches(\":popover-open\") || document.querySelector(\"dialog:modal\")) {\n const next = container.cloneNode(false) as HTMLElement;\n while (container.firstChild) next.appendChild(container.firstChild);\n const root = container.parentElement ?? getK2bPortalRoot();\n container.remove();\n root.appendChild(next);\n active = next;\n }\n if (!active.matches(\":popover-open\")) active.showPopover();\n } catch {\n active.removeAttribute(\"popover\");\n }\n return active;\n};\n\n/** Close every empty rail so an emptied container does not linger in the top\n * layer. Rails are resolved at call time on purpose: `promoteToTopLayer`\n * swaps the element for a fresh clone, so a container captured when the toast\n * was created can already be detached by the time the toast is dismissed. */\nconst hideEmptyContainers = (): void => {\n if (typeof document === \"undefined\") return;\n for (const container of Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`))) {\n if (container.childElementCount > 0 || typeof container.hidePopover !== \"function\") continue;\n try {\n if (container.matches(\":popover-open\")) container.hidePopover();\n } catch {\n // Already hidden or disconnected.\n }\n }\n};\n\nconst renderLead = (lead: HTMLElement, variant: ToastVariant, iconClassOverride?: string): HTMLElement => {\n const style = VARIANT_STYLES[variant];\n lead.replaceChildren();\n lead.className = \"k2b-toast__icon\";\n lead.dataset.tone = style.tone;\n const icon = document.createElement(\"i\");\n applyIconClass(icon, iconClassOverride ?? style.iconClass);\n icon.setAttribute(\"aria-hidden\", \"true\");\n lead.appendChild(icon);\n return icon;\n};\n\nconst showToast = (description: string, options?: ToastOptions): ToastHandle => {\n const initialContainer = ensureContainer();\n if (!initialContainer) {\n const noop = () => {};\n return { dismiss: noop, update: noop };\n }\n\n let dismissed = false;\n let dismissTimer: ReturnType<typeof setTimeout> | null = null;\n let currentVariant: ToastVariant = options?.variant ?? \"default\";\n let currentProgress = options?.progress ?? null;\n let currentDuration = options?.duration ?? DEFAULT_DURATION_MS;\n let remainingDuration = currentDuration;\n let timerStartedAt = 0;\n let pausedByPointer = false;\n let pausedByFocus = false;\n\n const toastElement = document.createElement(\"div\");\n toastElement.className = \"k2b-toast\";\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n toastElement.dataset.k2bToast = \"\";\n\n const leadElement = document.createElement(\"div\");\n let leadIconElement = renderLead(leadElement, currentVariant, options?.iconClass);\n\n const contentElement = document.createElement(\"div\");\n contentElement.className = \"k2b-toast__content\";\n applyLiveRegion(contentElement, currentVariant);\n\n const titleElement = document.createElement(\"div\");\n titleElement.className = \"k2b-toast__title\";\n titleElement.textContent = options?.title ?? defaultTitle(currentVariant);\n const descriptionElement = document.createElement(\"div\");\n descriptionElement.className = \"k2b-toast__description\";\n descriptionElement.textContent = description;\n contentElement.append(titleElement, descriptionElement);\n\n const closeButton = document.createElement(\"button\");\n closeButton.type = \"button\";\n closeButton.className = \"k2b-toast__close\";\n closeButton.setAttribute(\"aria-label\", options?.dismissLabel ?? \"Dismiss notification\");\n const closeIcon = document.createElement(\"i\");\n closeIcon.className = \"ti ti-x\";\n closeIcon.setAttribute(\"aria-hidden\", \"true\");\n closeButton.appendChild(closeIcon);\n\n toastElement.append(leadElement, contentElement, closeButton);\n\n const clearDismissTimer = () => {\n if (dismissTimer === null) return;\n clearTimeout(dismissTimer);\n dismissTimer = null;\n };\n\n const pauseDismissTimer = () => {\n if (dismissTimer === null) return;\n remainingDuration = Math.max(0, remainingDuration - (Date.now() - timerStartedAt));\n clearDismissTimer();\n };\n\n const resumeDismissTimer = () => {\n if (dismissed || currentProgress !== null || currentDuration === 0 || remainingDuration <= 0 || pausedByPointer || pausedByFocus)\n return;\n clearDismissTimer();\n timerStartedAt = Date.now();\n dismissTimer = setTimeout(() => dismiss(), remainingDuration);\n };\n\n const resetDismissTimer = (duration: number) => {\n clearDismissTimer();\n currentDuration = duration;\n remainingDuration = duration;\n resumeDismissTimer();\n };\n\n const dismiss = () => {\n if (dismissed) return;\n dismissed = true;\n clearDismissTimer();\n liveToasts.delete(handle);\n toastElement.dataset.closing = \"true\";\n setTimeout(() => {\n toastElement.remove();\n hideEmptyContainers();\n }, ANIMATION_MS);\n };\n\n const progressElement = document.createElement(\"progress\");\n progressElement.className = \"k2b-toast__progress\";\n progressElement.max = 1;\n const renderProgress = () => {\n progressElement.hidden = currentProgress === null;\n progressElement.setAttribute(\"aria-label\", titleElement.textContent || descriptionElement.textContent || \"\");\n if (typeof currentProgress === \"number\")\n progressElement.value = Number.isFinite(currentProgress) ? Math.max(0, Math.min(1, currentProgress)) : 0;\n else progressElement.removeAttribute(\"value\");\n };\n contentElement.append(progressElement);\n renderProgress();\n let actionElement: HTMLAnchorElement | HTMLButtonElement | null = null;\n const renderAction = (action: ToastAction | null | undefined) => {\n actionElement?.remove();\n actionElement = null;\n if (!action) return;\n if (\"href\" in action) {\n const link = document.createElement(\"a\");\n link.href = action.href;\n actionElement = link;\n } else {\n const button = document.createElement(\"button\");\n button.type = \"button\";\n actionElement = button;\n }\n actionElement.className = \"k2b-toast__action\";\n actionElement.textContent = action.label;\n actionElement.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n if (\"onClick\" in action) action.onClick();\n else dismiss();\n });\n contentElement.appendChild(actionElement);\n };\n renderAction(options?.action);\n\n const update = (nextDescription: string, nextOptions?: ToastOptions) => {\n if (dismissed) return;\n descriptionElement.textContent = nextDescription;\n\n const variantChanged = nextOptions?.variant !== undefined && nextOptions.variant !== currentVariant;\n if (variantChanged) {\n currentVariant = nextOptions.variant!;\n toastElement.dataset.tone = VARIANT_STYLES[currentVariant].tone;\n leadIconElement = renderLead(leadElement, currentVariant, nextOptions.iconClass);\n applyLiveRegion(contentElement, currentVariant);\n } else if (nextOptions?.iconClass !== undefined) {\n applyIconClass(leadIconElement, nextOptions.iconClass);\n }\n\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"title\")) {\n titleElement.textContent = nextOptions.title ?? \"\";\n } else if (variantChanged) {\n titleElement.textContent = defaultTitle(currentVariant);\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"action\")) renderAction(nextOptions.action);\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"duration\")) {\n currentDuration = nextOptions.duration ?? DEFAULT_DURATION_MS;\n }\n if (nextOptions && Object.prototype.hasOwnProperty.call(nextOptions, \"progress\")) currentProgress = nextOptions.progress ?? null;\n if (nextOptions?.dismissLabel) closeButton.setAttribute(\"aria-label\", nextOptions.dismissLabel);\n renderProgress();\n resetDismissTimer(currentDuration);\n };\n\n toastElement.addEventListener(\"click\", () => {\n if (currentProgress === null) dismiss();\n });\n closeButton.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n dismiss();\n });\n toastElement.addEventListener(\"pointerenter\", () => {\n pausedByPointer = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"pointerleave\", () => {\n pausedByPointer = false;\n resumeDismissTimer();\n });\n toastElement.addEventListener(\"focusin\", () => {\n pausedByFocus = true;\n pauseDismissTimer();\n });\n toastElement.addEventListener(\"focusout\", (event) => {\n if (toastElement.contains(event.relatedTarget as Node | null)) return;\n pausedByFocus = false;\n resumeDismissTimer();\n });\n\n const handle: ToastHandle = { dismiss, update };\n liveToasts.add(handle);\n if (liveToasts.size > MAX_VISIBLE_TOASTS) liveToasts.values().next().value?.dismiss();\n promoteToTopLayer(initialContainer).appendChild(toastElement);\n requestAnimationFrame(() => {\n if (!dismissed) toastElement.dataset.open = \"true\";\n });\n resetDismissTimer(currentDuration);\n return handle;\n};\n\nexport const isPointInsideToast = (x: number, y: number): boolean => {\n if (typeof document === \"undefined\") return false;\n const containers = Array.from(document.querySelectorAll<HTMLElement>(`[${CONTAINER_ATTRIBUTE}]`));\n for (const container of containers) {\n for (const child of Array.from(container.children)) {\n const rect = child.getBoundingClientRect();\n if (x >= rect.left && x <= rect.right && y >= rect.top && y <= rect.bottom) return true;\n }\n }\n return false;\n};\n\nconst toastFn = ((description: string, options?: ToastOptions) => showToast(description, options)) as ToastFn;\ntoastFn.success = (description, options) => showToast(description, { ...options, variant: \"success\" });\ntoastFn.error = (description, options) => showToast(description, { ...options, variant: \"error\" });\ntoastFn.dismissAll = () => {\n for (const handle of Array.from(liveToasts)) handle.dismiss();\n};\n\nexport const toast: ToastFn = toastFn;\n"],"mappings":"AAAA,SAAS,gBAAgB,QAAQ,oBAAoB;AACrD,SAAS,iBAAiB,QAAQ,kBAAkB;AA+BpD,MAAM,mBAAmB,GAAG,IAAI;AAChC,MAAM,kBAAkB,GAAG,CAAC;AAC5B,MAAM,YAAY,GAAG,GAAG;AACxB,OAAO,MAAM,sBAAsB,GAAG,wBAAwB;AAC9D,MAAM,mBAAmB,GAAG,0BAA0B;AAQtD,MAAM,cAAkD,GAAG;EACzD,OAAO,EAAE;IACP,IAAI,EAAE,MAAM;IACZ,SAAS,EAAE,gBAAgB;IAC3B,QAAQ,EAAE;EACZ,CAAC;EACD,OAAO,EAAE;IACP,IAAI,EAAE,SAAS;IACf,SAAS,EAAE,UAAU;IACrB,QAAQ,EAAE;EACZ,CAAC;EACD,KAAK,EAAE;IACL,IAAI,EAAE,QAAQ;IACd,SAAS,EAAE,MAAM;IACjB,QAAQ,EAAE;EACZ;AACF,CAAC;;AAED;AACA,MAAM,YAAY,GAAI,OAAqB,IAAa,iBAAiB,CAAC,CAAC,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,QAAQ,CAAC;AAE7G,MAAM,mBAAmB,GAAI,SAAiB,IAAa;EACzD,MAAM,MAAM,GAAG,SAAS,CACrB,KAAK,CAAC,KAAK,CAAC,CACZ,MAAM,CAAC,OAAO,CAAC,CACf,MAAM,CAAE,KAAK,IAAK,KAAK,KAAK,IAAI,CAAC;EACpC,OAAO,CAAC,IAAI,EAAE,GAAG,MAAM,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC;AACpC,CAAC;AAED,MAAM,cAAc,GAAG,CAAC,IAAiB,EAAE,SAAiB,KAAW;EACrE,IAAI,CAAC,SAAS,GAAG,mBAAmB,CAAC,SAAS,CAAC;AACjD,CAAC;AAED,MAAM,eAAe,GAAG,CAAC,OAAoB,EAAE,OAAqB,KAAW;EAC7E,MAAM,OAAO,GAAG,OAAO,KAAK,OAAO;EACnC,OAAO,CAAC,YAAY,CAAC,MAAM,EAAE,OAAO,GAAG,OAAO,GAAG,QAAQ,CAAC;EAC1D,OAAO,CAAC,YAAY,CAAC,WAAW,EAAE,OAAO,GAAG,WAAW,GAAG,QAAQ,CAAC;EACnE,OAAO,CAAC,YAAY,CAAC,aAAa,EAAE,MAAM,CAAC;AAC7C,CAAC;AAED,MAAM,UAAU,GAAG,IAAI,GAAG,CAAc,CAAC;AAEzC,MAAM,eAAe,GAAG,MAA0B;EAChD,IAAI,OAAO,QAAQ,KAAK,WAAW,EAAE,OAAO,IAAI;EAChD,MAAM,IAAI,GAAG,gBAAgB,CAAC,CAAC;EAC/B,IAAI,SAAS,GAAG,IAAI,CAAC,aAAa,CAAc,IAAI,mBAAmB,GAAG,CAAC;EAC3E,IAAI,SAAS,EAAE,OAAO,SAAS;EAE/B,SAAS,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;EACzC,SAAS,CAAC,EAAE,GAAG,sBAAsB;EACrC,SAAS,CAAC,YAAY,CAAC,mBAAmB,EAAE,EAAE,CAAC;EAC/C,SAAS,CAAC,YAAY,CAAC,SAAS,EAAE,QAAQ,CAAC;EAC3C;EACA;EACA,SAAS,CAAC,KAAK,CAAC,OAAO,GACrB,gHAAgH,GAChH,iFAAiF,GACjF,gGAAgG,GAChG,8BAA8B,GAC9B,2FAA2F,GAC3F,sHAAsH,GACtH,sBAAsB;EACxB,IAAI,CAAC,WAAW,CAAC,SAAS,CAAC;EAC3B,OAAO,SAAS;AAClB,CAAC;AAED,MAAM,iBAAiB,GAAI,SAAsB,IAAkB;EACjE,IAAI,OAAO,SAAS,CAAC,WAAW,KAAK,UAAU,IAAI,CAAC,SAAS,CAAC,WAAW,EAAE,OAAO,SAAS;EAC3F,IAAI,MAAM,GAAG,SAAS;EACtB,IAAI;IACF,IAAI,SAAS,CAAC,OAAO,CAAC,eAAe,CAAC,IAAI,QAAQ,CAAC,aAAa,CAAC,cAAc,CAAC,EAAE;MAChF,MAAM,IAAI,GAAG,SAAS,CAAC,SAAS,CAAC,KAAK,CAAgB;MACtD,OAAO,SAAS,CAAC,UAAU,EAAE,IAAI,CAAC,WAAW,CAAC,SAAS,CAAC,UAAU,CAAC;MACnE,MAAM,IAAI,GAAG,SAAS,CAAC,aAAa,IAAI,gBAAgB,CAAC,CAAC;MAC1D,SAAS,CAAC,MAAM,CAAC,CAAC;MAClB,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC;MACtB,MAAM,GAAG,IAAI;IACf;IACA,IAAI,CAAC,MAAM,CAAC,OAAO,CAAC,eAAe,CAAC,EAAE,MAAM,CAAC,WAAW,CAAC,CAAC;EAC5D,CAAC,CAAC,MAAM;IACN,MAAM,CAAC,eAAe,CAAC,SAAS,CAAC;EACnC;EACA,OAAO,MAAM;AACf,CAAC;;AAED;AACA;AACA;AACA;AACA,MAAM,mBAAmB,GAAG,MAAY;EACtC,IAAI,OAAO,QAAQ,KAAK,WAAW,EAAE;EACrC,KAAK,MAAM,SAAS,IAAI,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,gBAAgB,CAAc,IAAI,mBAAmB,GAAG,CAAC,CAAC,EAAE;IACtG,IAAI,SAAS,CAAC,iBAAiB,GAAG,CAAC,IAAI,OAAO,SAAS,CAAC,WAAW,KAAK,UAAU,EAAE;IACpF,IAAI;MACF,IAAI,SAAS,CAAC,OAAO,CAAC,eAAe,CAAC,EAAE,SAAS,CAAC,WAAW,CAAC,CAAC;IACjE,CAAC,CAAC,MAAM;MACN;IAAA;EAEJ;AACF,CAAC;AAED,MAAM,UAAU,GAAG,CAAC,IAAiB,EAAE,OAAqB,EAAE,iBAA0B,KAAkB;EACxG,MAAM,KAAK,GAAG,cAAc,CAAC,OAAO,CAAC;EACrC,IAAI,CAAC,eAAe,CAAC,CAAC;EACtB,IAAI,CAAC,SAAS,GAAG,iBAAiB;EAClC,IAAI,CAAC,OAAO,CAAC,IAAI,GAAG,KAAK,CAAC,IAAI;EAC9B,MAAM,IAAI,GAAG,QAAQ,CAAC,aAAa,CAAC,GAAG,CAAC;EACxC,cAAc,CAAC,IAAI,EAAE,iBAAiB,IAAI,KAAK,CAAC,SAAS,CAAC;EAC1D,IAAI,CAAC,YAAY,CAAC,aAAa,EAAE,MAAM,CAAC;EACxC,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC;EACtB,OAAO,IAAI;AACb,CAAC;AAED,MAAM,SAAS,GAAG,CAAC,WAAmB,EAAE,OAAsB,KAAkB;EAC9E,MAAM,gBAAgB,GAAG,eAAe,CAAC,CAAC;EAC1C,IAAI,CAAC,gBAAgB,EAAE;IACrB,MAAM,IAAI,GAAG,MAAM,CAAC,CAAC;IACrB,OAAO;MAAE,OAAO,EAAE,IAAI;MAAE,MAAM,EAAE;IAAK,CAAC;EACxC;EAEA,IAAI,SAAS,GAAG,KAAK;EACrB,IAAI,YAAkD,GAAG,IAAI;EAC7D,IAAI,cAA4B,GAAG,OAAO,EAAE,OAAO,IAAI,SAAS;EAChE,IAAI,eAAe,GAAG,OAAO,EAAE,QAAQ,IAAI,IAAI;EAC/C,IAAI,eAAe,GAAG,OAAO,EAAE,QAAQ,IAAI,mBAAmB;EAC9D,IAAI,iBAAiB,GAAG,eAAe;EACvC,IAAI,cAAc,GAAG,CAAC;EACtB,IAAI,eAAe,GAAG,KAAK;EAC3B,IAAI,aAAa,GAAG,KAAK;EAEzB,MAAM,YAAY,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;EAClD,YAAY,CAAC,SAAS,GAAG,WAAW;EACpC,YAAY,CAAC,OAAO,CAAC,IAAI,GAAG,cAAc,CAAC,cAAc,CAAC,CAAC,IAAI;EAC/D,YAAY,CAAC,OAAO,CAAC,QAAQ,GAAG,EAAE;EAElC,MAAM,WAAW,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;EACjD,IAAI,eAAe,GAAG,UAAU,CAAC,WAAW,EAAE,cAAc,EAAE,OAAO,EAAE,SAAS,CAAC;EAEjF,MAAM,cAAc,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;EACpD,cAAc,CAAC,SAAS,GAAG,oBAAoB;EAC/C,eAAe,CAAC,cAAc,EAAE,cAAc,CAAC;EAE/C,MAAM,YAAY,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;EAClD,YAAY,CAAC,SAAS,GAAG,kBAAkB;EAC3C,YAAY,CAAC,WAAW,GAAG,OAAO,EAAE,KAAK,IAAI,YAAY,CAAC,cAAc,CAAC;EACzE,MAAM,kBAAkB,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;EACxD,kBAAkB,CAAC,SAAS,GAAG,wBAAwB;EACvD,kBAAkB,CAAC,WAAW,GAAG,WAAW;EAC5C,cAAc,CAAC,MAAM,CAAC,YAAY,EAAE,kBAAkB,CAAC;EAEvD,MAAM,WAAW,GAAG,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC;EACpD,WAAW,CAAC,IAAI,GAAG,QAAQ;EAC3B,WAAW,CAAC,SAAS,GAAG,kBAAkB;EAC1C,WAAW,CAAC,YAAY,CAAC,YAAY,EAAE,OAAO,EAAE,YAAY,IAAI,sBAAsB,CAAC;EACvF,MAAM,SAAS,GAAG,QAAQ,CAAC,aAAa,CAAC,GAAG,CAAC;EAC7C,SAAS,CAAC,SAAS,GAAG,SAAS;EAC/B,SAAS,CAAC,YAAY,CAAC,aAAa,EAAE,MAAM,CAAC;EAC7C,WAAW,CAAC,WAAW,CAAC,SAAS,CAAC;EAElC,YAAY,CAAC,MAAM,CAAC,WAAW,EAAE,cAAc,EAAE,WAAW,CAAC;EAE7D,MAAM,iBAAiB,GAAG,MAAM;IAC9B,IAAI,YAAY,KAAK,IAAI,EAAE;IAC3B,YAAY,CAAC,YAAY,CAAC;IAC1B,YAAY,GAAG,IAAI;EACrB,CAAC;EAED,MAAM,iBAAiB,GAAG,MAAM;IAC9B,IAAI,YAAY,KAAK,IAAI,EAAE;IAC3B,iBAAiB,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,iBAAiB,IAAI,IAAI,CAAC,GAAG,CAAC,CAAC,GAAG,cAAc,CAAC,CAAC;IAClF,iBAAiB,CAAC,CAAC;EACrB,CAAC;EAED,MAAM,kBAAkB,GAAG,MAAM;IAC/B,IAAI,SAAS,IAAI,eAAe,KAAK,IAAI,IAAI,eAAe,KAAK,CAAC,IAAI,iBAAiB,IAAI,CAAC,IAAI,eAAe,IAAI,aAAa,EAC9H;IACF,iBAAiB,CAAC,CAAC;IACnB,cAAc,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC;IAC3B,YAAY,GAAG,UAAU,CAAC,MAAM,OAAO,CAAC,CAAC,EAAE,iBAAiB,CAAC;EAC/D,CAAC;EAED,MAAM,iBAAiB,GAAI,QAAgB,IAAK;IAC9C,iBAAiB,CAAC,CAAC;IACnB,eAAe,GAAG,QAAQ;IAC1B,iBAAiB,GAAG,QAAQ;IAC5B,kBAAkB,CAAC,CAAC;EACtB,CAAC;EAED,MAAM,OAAO,GAAG,MAAM;IACpB,IAAI,SAAS,EAAE;IACf,SAAS,GAAG,IAAI;IAChB,iBAAiB,CAAC,CAAC;IACnB,UAAU,CAAC,MAAM,CAAC,MAAM,CAAC;IACzB,YAAY,CAAC,OAAO,CAAC,OAAO,GAAG,MAAM;IACrC,UAAU,CAAC,MAAM;MACf,YAAY,CAAC,MAAM,CAAC,CAAC;MACrB,mBAAmB,CAAC,CAAC;IACvB,CAAC,EAAE,YAAY,CAAC;EAClB,CAAC;EAED,MAAM,eAAe,GAAG,QAAQ,CAAC,aAAa,CAAC,UAAU,CAAC;EAC1D,eAAe,CAAC,SAAS,GAAG,qBAAqB;EACjD,eAAe,CAAC,GAAG,GAAG,CAAC;EACvB,MAAM,cAAc,GAAG,MAAM;IAC3B,eAAe,CAAC,MAAM,GAAG,eAAe,KAAK,IAAI;IACjD,eAAe,CAAC,YAAY,CAAC,YAAY,EAAE,YAAY,CAAC,WAAW,IAAI,kBAAkB,CAAC,WAAW,IAAI,EAAE,CAAC;IAC5G,IAAI,OAAO,eAAe,KAAK,QAAQ,EACrC,eAAe,CAAC,KAAK,GAAG,MAAM,CAAC,QAAQ,CAAC,eAAe,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,eAAe,CAAC,CAAC,GAAG,CAAC,CAAC,KACtG,eAAe,CAAC,eAAe,CAAC,OAAO,CAAC;EAC/C,CAAC;EACD,cAAc,CAAC,MAAM,CAAC,eAAe,CAAC;EACtC,cAAc,CAAC,CAAC;EAChB,IAAI,aAA2D,GAAG,IAAI;EACtE,MAAM,YAAY,GAAI,MAAsC,IAAK;IAC/D,aAAa,EAAE,MAAM,CAAC,CAAC;IACvB,aAAa,GAAG,IAAI;IACpB,IAAI,CAAC,MAAM,EAAE;IACb,IAAI,MAAM,IAAI,MAAM,EAAE;MACpB,MAAM,IAAI,GAAG,QAAQ,CAAC,aAAa,CAAC,GAAG,CAAC;MACxC,IAAI,CAAC,IAAI,GAAG,MAAM,CAAC,IAAI;MACvB,aAAa,GAAG,IAAI;IACtB,CAAC,MAAM;MACL,MAAM,MAAM,GAAG,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC;MAC/C,MAAM,CAAC,IAAI,GAAG,QAAQ;MACtB,aAAa,GAAG,MAAM;IACxB;IACA,aAAa,CAAC,SAAS,GAAG,mBAAmB;IAC7C,aAAa,CAAC,WAAW,GAAG,MAAM,CAAC,KAAK;IACxC,aAAa,CAAC,gBAAgB,CAAC,OAAO,EAAG,KAAK,IAAK;MACjD,KAAK,CAAC,eAAe,CAAC,CAAC;MACvB,IAAI,SAAS,IAAI,MAAM,EAAE,MAAM,CAAC,OAAO,CAAC,CAAC,CAAC,KACrC,OAAO,CAAC,CAAC;IAChB,CAAC,CAAC;IACF,cAAc,CAAC,WAAW,CAAC,aAAa,CAAC;EAC3C,CAAC;EACD,YAAY,CAAC,OAAO,EAAE,MAAM,CAAC;EAE7B,MAAM,MAAM,GAAG,CAAC,eAAuB,EAAE,WAA0B,KAAK;IACtE,IAAI,SAAS,EAAE;IACf,kBAAkB,CAAC,WAAW,GAAG,eAAe;IAEhD,MAAM,cAAc,GAAG,WAAW,EAAE,OAAO,KAAK,SAAS,IAAI,WAAW,CAAC,OAAO,KAAK,cAAc;IACnG,IAAI,cAAc,EAAE;MAClB,cAAc,GAAG,WAAW,CAAC,OAAQ;MACrC,YAAY,CAAC,OAAO,CAAC,IAAI,GAAG,cAAc,CAAC,cAAc,CAAC,CAAC,IAAI;MAC/D,eAAe,GAAG,UAAU,CAAC,WAAW,EAAE,cAAc,EAAE,WAAW,CAAC,SAAS,CAAC;MAChF,eAAe,CAAC,cAAc,EAAE,cAAc,CAAC;IACjD,CAAC,MAAM,IAAI,WAAW,EAAE,SAAS,KAAK,SAAS,EAAE;MAC/C,cAAc,CAAC,eAAe,EAAE,WAAW,CAAC,SAAS,CAAC;IACxD;IAEA,IAAI,WAAW,IAAI,MAAM,CAAC,SAAS,CAAC,cAAc,CAAC,IAAI,CAAC,WAAW,EAAE,OAAO,CAAC,EAAE;MAC7E,YAAY,CAAC,WAAW,GAAG,WAAW,CAAC,KAAK,IAAI,EAAE;IACpD,CAAC,MAAM,IAAI,cAAc,EAAE;MACzB,YAAY,CAAC,WAAW,GAAG,YAAY,CAAC,cAAc,CAAC;IACzD;IACA,IAAI,WAAW,IAAI,MAAM,CAAC,SAAS,CAAC,cAAc,CAAC,IAAI,CAAC,WAAW,EAAE,QAAQ,CAAC,EAAE,YAAY,CAAC,WAAW,CAAC,MAAM,CAAC;IAChH,IAAI,WAAW,IAAI,MAAM,CAAC,SAAS,CAAC,cAAc,CAAC,IAAI,CAAC,WAAW,EAAE,UAAU,CAAC,EAAE;MAChF,eAAe,GAAG,WAAW,CAAC,QAAQ,IAAI,mBAAmB;IAC/D;IACA,IAAI,WAAW,IAAI,MAAM,CAAC,SAAS,CAAC,cAAc,CAAC,IAAI,CAAC,WAAW,EAAE,UAAU,CAAC,EAAE,eAAe,GAAG,WAAW,CAAC,QAAQ,IAAI,IAAI;IAChI,IAAI,WAAW,EAAE,YAAY,EAAE,WAAW,CAAC,YAAY,CAAC,YAAY,EAAE,WAAW,CAAC,YAAY,CAAC;IAC/F,cAAc,CAAC,CAAC;IAChB,iBAAiB,CAAC,eAAe,CAAC;EACpC,CAAC;EAED,YAAY,CAAC,gBAAgB,CAAC,OAAO,EAAE,MAAM;IAC3C,IAAI,eAAe,KAAK,IAAI,EAAE,OAAO,CAAC,CAAC;EACzC,CAAC,CAAC;EACF,WAAW,CAAC,gBAAgB,CAAC,OAAO,EAAG,KAAK,IAAK;IAC/C,KAAK,CAAC,eAAe,CAAC,CAAC;IACvB,OAAO,CAAC,CAAC;EACX,CAAC,CAAC;EACF,YAAY,CAAC,gBAAgB,CAAC,cAAc,EAAE,MAAM;IAClD,eAAe,GAAG,IAAI;IACtB,iBAAiB,CAAC,CAAC;EACrB,CAAC,CAAC;EACF,YAAY,CAAC,gBAAgB,CAAC,cAAc,EAAE,MAAM;IAClD,eAAe,GAAG,KAAK;IACvB,kBAAkB,CAAC,CAAC;EACtB,CAAC,CAAC;EACF,YAAY,CAAC,gBAAgB,CAAC,SAAS,EAAE,MAAM;IAC7C,aAAa,GAAG,IAAI;IACpB,iBAAiB,CAAC,CAAC;EACrB,CAAC,CAAC;EACF,YAAY,CAAC,gBAAgB,CAAC,UAAU,EAAG,KAAK,IAAK;IACnD,IAAI,YAAY,CAAC,QAAQ,CAAC,KAAK,CAAC,aAA4B,CAAC,EAAE;IAC/D,aAAa,GAAG,KAAK;IACrB,kBAAkB,CAAC,CAAC;EACtB,CAAC,CAAC;EAEF,MAAM,MAAmB,GAAG;IAAE,OAAO;IAAE;EAAO,CAAC;EAC/C,UAAU,CAAC,GAAG,CAAC,MAAM,CAAC;EACtB,IAAI,UAAU,CAAC,IAAI,GAAG,kBAAkB,EAAE,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC;EACrF,iBAAiB,CAAC,gBAAgB,CAAC,CAAC,WAAW,CAAC,YAAY,CAAC;EAC7D,qBAAqB,CAAC,MAAM;IAC1B,IAAI,CAAC,SAAS,EAAE,YAAY,CAAC,OAAO,CAAC,IAAI,GAAG,MAAM;EACpD,CAAC,CAAC;EACF,iBAAiB,CAAC,eAAe,CAAC;EAClC,OAAO,MAAM;AACf,CAAC;AAED,OAAO,MAAM,kBAAkB,GAAG,CAAC,CAAS,EAAE,CAAS,KAAc;EACnE,IAAI,OAAO,QAAQ,KAAK,WAAW,EAAE,OAAO,KAAK;EACjD,MAAM,UAAU,GAAG,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,gBAAgB,CAAc,IAAI,mBAAmB,GAAG,CAAC,CAAC;EACjG,KAAK,MAAM,SAAS,IAAI,UAAU,EAAE;IAClC,KAAK,MAAM,KAAK,IAAI,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,EAAE;MAClD,MAAM,IAAI,GAAG,KAAK,CAAC,qBAAqB,CAAC,CAAC;MAC1C,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,IAAI,CAAC,KAAK,IAAI,CAAC,IAAI,IAAI,CAAC,GAAG,IAAI,CAAC,IAAI,IAAI,CAAC,MAAM,EAAE,OAAO,IAAI;IACzF;EACF;EACA,OAAO,KAAK;AACd,CAAC;AAED,MAAM,OAAO,GAAI,CAAC,WAAmB,EAAE,OAAsB,KAAK,SAAS,CAAC,WAAW,EAAE,OAAO,CAAa;AAC7G,OAAO,CAAC,OAAO,GAAG,CAAC,WAAW,EAAE,OAAO,KAAK,SAAS,CAAC,WAAW,EAAE;EAAE,GAAG,OAAO;EAAE,OAAO,EAAE;AAAU,CAAC,CAAC;AACtG,OAAO,CAAC,KAAK,GAAG,CAAC,WAAW,EAAE,OAAO,KAAK,SAAS,CAAC,WAAW,EAAE;EAAE,GAAG,OAAO;EAAE,OAAO,EAAE;AAAQ,CAAC,CAAC;AAClG,OAAO,CAAC,UAAU,GAAG,MAAM;EACzB,KAAK,MAAM,MAAM,IAAI,KAAK,CAAC,IAAI,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC,OAAO,CAAC,CAAC;AAC/D,CAAC;AAED,OAAO,MAAM,KAAc,GAAG,OAAO","ignoreList":[]}
|
|
@@ -7,9 +7,16 @@ import { Show } from "solid-js";
|
|
|
7
7
|
import { useUiMessages } from "../intl/messages";
|
|
8
8
|
import PanelDialog from "./PanelDialog";
|
|
9
9
|
|
|
10
|
-
/** Initial focus goes to the first input of the top sheet
|
|
11
|
-
*
|
|
12
|
-
|
|
10
|
+
/** Initial focus goes to the first input of the top sheet, otherwise to the
|
|
11
|
+
* dialog element itself. Native `showModal()` focuses the first focusable
|
|
12
|
+
* descendant, which is the drag handle; iOS shows a ring for that programmatic
|
|
13
|
+
* focus, so the sheet moves it to the ring-less dialog before the next paint. */
|
|
14
|
+
const sheetInitialFocus = dialog => {
|
|
15
|
+
const input = dialog.lastElementChild?.querySelector("input:not([type='hidden']):not([disabled]), textarea:not([disabled]), select:not([disabled]), [role='combobox']:not([disabled]):not([aria-disabled='true'])");
|
|
16
|
+
if (input) return input;
|
|
17
|
+
dialog.tabIndex = -1;
|
|
18
|
+
return dialog;
|
|
19
|
+
};
|
|
13
20
|
export const bottomSheetOptions = {
|
|
14
21
|
panelClassName: "k2b-dialog k2b-bottom-sheet-frame",
|
|
15
22
|
contentClassName: "k2b-panel-dialog-viewport k2b-bottom-sheet-viewport",
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":[],"sources":["layout/BottomSheet.tsx"],"sourcesContent":["import { type JSX, Show } from \"solid-js\";\nimport type { OpenDialogOptions } from \"../feedback/dialog-core\";\nimport { useUiMessages } from \"../intl/messages\";\nimport PanelDialog from \"./PanelDialog\";\n\n/** Initial focus goes to the first input of the top sheet
|
|
1
|
+
{"version":3,"names":[],"sources":["layout/BottomSheet.tsx"],"sourcesContent":["import { type JSX, Show } from \"solid-js\";\nimport type { OpenDialogOptions } from \"../feedback/dialog-core\";\nimport { useUiMessages } from \"../intl/messages\";\nimport PanelDialog from \"./PanelDialog\";\n\n/** Initial focus goes to the first input of the top sheet, otherwise to the\n * dialog element itself. Native `showModal()` focuses the first focusable\n * descendant, which is the drag handle; iOS shows a ring for that programmatic\n * focus, so the sheet moves it to the ring-less dialog before the next paint. */\nconst sheetInitialFocus = (dialog: HTMLDialogElement): HTMLElement => {\n const input = dialog.lastElementChild?.querySelector<HTMLElement>(\n \"input:not([type='hidden']):not([disabled]), textarea:not([disabled]), select:not([disabled]), [role='combobox']:not([disabled]):not([aria-disabled='true'])\",\n );\n if (input) return input;\n dialog.tabIndex = -1;\n return dialog;\n};\n\nexport const bottomSheetOptions = {\n panelClassName: \"k2b-dialog k2b-bottom-sheet-frame\",\n contentClassName: \"k2b-panel-dialog-viewport k2b-bottom-sheet-viewport\",\n initialFocus: sheetInitialFocus,\n} satisfies OpenDialogOptions;\n\nexport type BottomSheetProps = {\n children: JSX.Element;\n /** Pass dialogCore's render context requestDismiss, never the completion callback. */\n onDismiss: () => void | Promise<void>;\n dismissDisabled?: boolean;\n dismissLabel?: string;\n handle?: boolean;\n};\n\nfunction BottomSheetRoot(props: BottomSheetProps) {\n const messages = useUiMessages();\n let pointer: { id: number; y: number } | undefined;\n let suppressClick = false;\n const dismiss = () => {\n if (!props.dismissDisabled) void props.onDismiss();\n };\n return (\n <PanelDialog>\n <Show when={props.handle !== false}>\n <button\n type=\"button\"\n class=\"k2b-bottom-sheet__handle\"\n aria-label={props.dismissLabel ?? messages().close}\n disabled={props.dismissDisabled}\n onPointerDown={(event) => {\n if (!event.isPrimary || event.button !== 0 || props.dismissDisabled) return;\n suppressClick = false;\n pointer = { id: event.pointerId, y: event.clientY };\n event.currentTarget.setPointerCapture(event.pointerId);\n }}\n onPointerUp={(event) => {\n if (pointer?.id !== event.pointerId) return;\n const distance = event.clientY - pointer.y;\n pointer = undefined;\n // A drag must not turn into a second dismiss request through click.\n suppressClick = Math.abs(distance) > 8;\n if (distance > 60) dismiss();\n }}\n onPointerCancel={() => {\n pointer = undefined;\n suppressClick = true;\n }}\n onLostPointerCapture={() => {\n if (pointer) {\n pointer = undefined;\n suppressClick = true;\n }\n }}\n onClick={(event) => {\n if (event.detail !== 0 && suppressClick) {\n suppressClick = false;\n return;\n }\n dismiss();\n }}\n >\n <span aria-hidden=\"true\" />\n </button>\n </Show>\n {props.children}\n </PanelDialog>\n );\n}\n\n/** Bottom-edge presentation; dialogCore continues to own all modal state. */\nconst BottomSheet = Object.assign(BottomSheetRoot, {\n Header: PanelDialog.Header,\n Body: PanelDialog.Body,\n Footer: PanelDialog.Footer,\n Section: PanelDialog.Section,\n Tabs: PanelDialog.Tabs,\n});\nexport default BottomSheet;\n"],"mappings":";;;;;AAAA,SAAmB,IAAI,QAAQ,UAAU;AAEzC,SAAS,aAAa,QAAQ,kBAAkB;AAChD,OAAO,WAAW,MAAM,eAAe;;AAEvC;AACA;AACA;AACA;AACA,MAAM,iBAAiB,GAAI,MAAyB,IAAkB;EACpE,MAAM,KAAK,GAAG,MAAM,CAAC,gBAAgB,EAAE,aAAa,CAClD,6JACF,CAAC;EACD,IAAI,KAAK,EAAE,OAAO,KAAK;EACvB,MAAM,CAAC,QAAQ,GAAG,CAAC,CAAC;EACpB,OAAO,MAAM;AACf,CAAC;AAED,OAAO,MAAM,kBAAkB,GAAG;EAChC,cAAc,EAAE,mCAAmC;EACnD,gBAAgB,EAAE,qDAAqD;EACvE,YAAY,EAAE;AAChB,CAA6B;AAW7B,SAAS,eAAe,CAAC,KAAuB,EAAE;EAChD,MAAM,QAAQ,GAAG,aAAa,CAAC,CAAC;EAChC,IAAI,OAA8C;EAClD,IAAI,aAAa,GAAG,KAAK;EACzB,MAAM,OAAO,GAAG,MAAM;IACpB,IAAI,CAAC,KAAK,CAAC,eAAe,EAAE,KAAK,KAAK,CAAC,SAAS,CAAC,CAAC;EACpD,CAAC;EACD,yBACG,WAAW;IAAA;MAAA,0BACT,IAAI;QAAA,IAAC,IAAI;UAAA,OAAE,KAAK,CAAC,MAAM,KAAK,KAAK;QAAA;QAAA;UAAA,2DAIlB,KAAK,CAAC,YAAY,IAAI,QAAQ,CAAC,CAAC,CAAC,KAAK,4CACxC,KAAK,CAAC,eAAe;QAAA;MAAA,IAoClC,KAAK,CAAC,QAAQ;IAAA;EAAA;AAGrB;;AAEA;AACA,MAAM,WAAW,GAAG,MAAM,CAAC,MAAM,CAAC,eAAe,EAAE;EACjD,MAAM,EAAE,WAAW,CAAC,MAAM;EAC1B,IAAI,EAAE,WAAW,CAAC,IAAI;EACtB,MAAM,EAAE,WAAW,CAAC,MAAM;EAC1B,OAAO,EAAE,WAAW,CAAC,OAAO;EAC5B,IAAI,EAAE,WAAW,CAAC;AACpB,CAAC,CAAC;AACF,eAAe,WAAW","ignoreList":[]}
|