@domphy/ui 0.20.0 → 0.20.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/core-theme-ui.global.js +1 -1
- package/dist/core-theme-ui.global.js.map +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/package.json +15 -9
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/global.ts","../../core/src/constants/BooleanAttributes.ts","../../core/src/constants/CamelAttributes.ts","../../core/src/constants/HtmlAttributeNames.ts","../../core/src/constants/HtmlTags.ts","../../core/src/constants/PrefixCSS.ts","../../core/src/constants/SvgTags.ts","../../core/src/constants/VoidTags.ts","../../core/src/config.ts","../../core/src/types/EventProperties.ts","../../core/src/classes/Collector.ts","../../core/src/classes/Notifier.ts","../../core/src/classes/State.ts","../../core/src/utils.ts","../../core/src/helpers.ts","../../core/src/classes/ElementAttribute.ts","../../core/src/classes/AttributeList.ts","../../core/src/dev.ts","../../core/src/classes/StyleProperty.ts","../../core/src/classes/StyleRule.ts","../../core/src/classes/StyleList.ts","../../core/src/classes/ElementNode.ts","../../core/src/classes/TextNode.ts","../../core/src/classes/ElementList.ts","../../core/src/classes/Reactive.ts","../../core/src/classes/RecordState.ts","../../theme/src/light.ts","../../theme/src/theme.ts","../../theme/src/density.ts","../../theme/src/generate.ts","../../theme/src/size.ts","../../theme/src/tone.ts","../../palette/src/utils.ts","../../palette/src/Swatch.ts","../../palette/src/Ramp.ts","../../palette/src/Palette.ts","../../palette/src/Generator.ts","../src/index.ts","../src/patches/abbreviation.ts","../src/patches/accordion.ts","../src/patches/alert.ts","../src/patches/avatar.ts","../src/patches/badge.ts","../src/patches/blockquote.ts","../src/patches/breadcrumb.ts","../src/patches/breadcrumbEllipsis.ts","../src/utils/buttonSize.ts","../src/utils/focusRing.ts","../src/patches/buttonGhost.ts","../src/patches/button.ts","../src/patches/buttonSwitch.ts","../src/patches/card.ts","../src/patches/code.ts","../src/utils/elevation.ts","../../floating/src/utils/index.ts","../../floating/src/core/computeCoordsFromPlacement.ts","../../floating/src/core/detectOverflow.ts","../../floating/src/core/computePosition.ts","../../floating/src/core/middleware/arrow.ts","../../floating/src/core/middleware/autoPlacement.ts","../../floating/src/core/middleware/flip.ts","../../floating/src/core/middleware/hide.ts","../../floating/src/core/middleware/inline.ts","../../floating/src/core/constants.ts","../../floating/src/core/middleware/offset.ts","../../floating/src/core/middleware/shift.ts","../../floating/src/core/middleware/size.ts","../../floating/src/utils/dom.ts","../../floating/src/dom/utils/getCssDimensions.ts","../../floating/src/dom/utils/unwrapElement.ts","../../floating/src/dom/platform/getScale.ts","../../floating/src/dom/utils/getVisualOffsets.ts","../../floating/src/dom/utils/getBoundingClientRect.ts","../../floating/src/dom/utils/getWindowScrollBarX.ts","../../floating/src/dom/utils/getHTMLOffset.ts","../../floating/src/dom/platform/convertOffsetParentRelativeRectToViewportRelativeRect.ts","../../floating/src/dom/platform/getClientRects.ts","../../floating/src/dom/utils/getDocumentRect.ts","../../floating/src/dom/utils/getViewportRect.ts","../../floating/src/dom/platform/getClippingRect.ts","../../floating/src/dom/platform/getDimensions.ts","../../floating/src/dom/utils/getRectRelativeToOffsetParent.ts","../../floating/src/dom/utils/isStaticPositioned.ts","../../floating/src/dom/platform/getOffsetParent.ts","../../floating/src/dom/platform/getElementRects.ts","../../floating/src/dom/platform/isRTL.ts","../../floating/src/dom/platform.ts","../../floating/src/dom/utils/rectsAreEqual.ts","../../floating/src/dom/autoUpdate.ts","../../floating/src/dom/createFloating.ts","../../floating/src/dom/middleware.ts","../../floating/src/dom/index.ts","../src/utils/floating.ts","../src/patches/tag.ts","../src/patches/combobox.ts","../src/patches/command.ts","../src/patches/datePicker.ts","../src/patches/descriptionList.ts","../src/patches/details.ts","../src/utils/scrollLock.ts","../src/patches/dialog.ts","../src/patches/divider.ts","../src/patches/drawer.ts","../src/patches/emphasis.ts","../src/patches/empty.ts","../src/patches/errorBoundary.ts","../src/patches/fab.ts","../src/patches/figure.ts","../src/patches/formGroup.ts","../src/patches/heading.ts","../src/patches/horizontalRule.ts","../src/patches/icon.ts","../src/patches/image.ts","../src/patches/inputCheckbox.ts","../src/patches/inputColor.ts","../src/patches/inputDateTime.ts","../src/patches/inputFile.ts","../src/patches/inputNumber.ts","../src/patches/inputPassword.ts","../src/patches/inputOTP.ts","../src/patches/inputRadio.ts","../src/patches/inputRange.ts","../src/patches/inputSearch.ts","../src/patches/inputSwitch.ts","../src/patches/inputText.ts","../src/patches/keyboard.ts","../src/patches/label.ts","../src/patches/link.ts","../src/patches/linkButton.ts","../src/patches/list.ts","../src/patches/mark.ts","../src/patches/menu.ts","../src/patches/motion.ts","../src/patches/orderedList.ts","../src/patches/pagination.ts","../src/patches/panelSection.ts","../src/patches/paragraph.ts","../src/patches/popover.ts","../src/patches/popoverArrow.ts","../src/patches/preformated.ts","../src/patches/progress.ts","../src/patches/rating.ts","../src/patches/ringProgress.ts","../src/patches/row.ts","../src/patches/scrollArea.ts","../src/patches/segmented.ts","../src/patches/select.ts","../src/patches/selectBox.ts","../src/patches/selectItem.ts","../src/patches/selectList.ts","../src/patches/skeleton.ts","../src/patches/small.ts","../src/patches/spinner.ts","../src/patches/splitter.ts","../src/patches/stack.ts","../src/patches/steps.ts","../src/patches/strong.ts","../src/patches/subscript.ts","../src/patches/superscript.ts","../src/patches/table.ts","../src/patches/tabs.ts","../src/patches/textarea.ts","../src/patches/timeline.ts","../src/patches/toast.ts","../src/patches/toggleGroup.ts","../src/patches/toolbar.ts","../src/patches/tooltip.ts","../src/patches/transitionGroup.ts","../src/patches/unorderedList.ts"],"sourcesContent":["export * as core from \"@domphy/core\";\nexport * as theme from \"@domphy/theme\";\nexport * as ui from \"./index.js\";\n","export const BooleanAttributes = [\n \"allowFullScreen\",\n \"async\",\n \"autoFocus\",\n \"autoPlay\",\n \"checked\",\n \"compact\",\n \"contentEditable\",\n \"controls\",\n \"declare\",\n \"default\",\n \"defer\",\n \"disabled\",\n \"formNoValidate\",\n \"hidden\",\n \"isMap\",\n \"itemScope\",\n \"loop\",\n \"multiple\",\n \"muted\",\n \"noHref\",\n \"noShade\",\n \"noValidate\",\n \"open\",\n \"playsInline\",\n \"readonly\",\n \"required\",\n \"reversed\",\n \"scoped\",\n \"selected\",\n \"sortable\",\n \"trueSpeed\",\n \"typeMustMatch\",\n \"wmode\",\n \"spellCheck\",\n \"inert\",\n \"download\",\n \"noModule\",\n \"paused\",\n \"autoPictureInPicture\",\n] as const;\n","export const CamelAttributes: string[] = [\n \"viewBox\",\n \"preserveAspectRatio\",\n \"gradientTransform\",\n \"gradientUnits\",\n \"spreadMethod\",\n \"markerStart\",\n \"markerMid\",\n \"markerEnd\",\n \"markerHeight\",\n \"markerWidth\",\n \"markerUnits\",\n \"refX\",\n \"refY\",\n \"patternContentUnits\",\n \"patternTransform\",\n \"patternUnits\",\n \"filterUnits\",\n \"primitiveUnits\",\n \"kernelUnitLength\",\n \"clipPathUnits\",\n \"maskContentUnits\",\n \"maskUnits\",\n \"baseFrequency\",\n \"numOctaves\",\n \"xChannelSelector\",\n \"yChannelSelector\",\n \"stdDeviation\",\n \"colorInterpolationFilters\",\n \"pathLength\",\n] as const;\n","// Multi-word HTML/global attribute names whose real DOM content-attribute\n// spelling is either a plain lowercase concatenation (no hyphen at all, e.g.\n// autoFocus -> autofocus, tabIndex -> tabindex) or an outright rename\n// (htmlFor -> for). The generic camelToKebab() helper only knows how to\n// insert a hyphen before every capital letter, so it cannot produce these —\n// it is only correct for the small set of HTML attributes whose real name IS\n// genuinely hyphenated (http-equiv, accept-charset) and for aria-*/data-*,\n// which follow that same hyphenated convention.\n//\n// ElementAttribute's constructor checks this map before falling back to\n// camelToKebab(), so any camelCase key NOT listed here (including custom\n// attributes such as web-component props, e.g. myWidgetProp) still gets the\n// previous kebab-case treatment unchanged.\nexport const HtmlAttributeNames: Record<string, string> = {\n // Rename, not just a case change.\n htmlFor: \"for\",\n\n // Boolean HTML attributes (BooleanAttributes.ts) with camelCase humps.\n allowFullScreen: \"allowfullscreen\",\n autoFocus: \"autofocus\",\n autoPlay: \"autoplay\",\n contentEditable: \"contenteditable\",\n formNoValidate: \"formnovalidate\",\n isMap: \"ismap\",\n itemScope: \"itemscope\",\n noHref: \"nohref\",\n noShade: \"noshade\",\n noValidate: \"novalidate\",\n playsInline: \"playsinline\",\n trueSpeed: \"truespeed\",\n typeMustMatch: \"typemustmatch\",\n spellCheck: \"spellcheck\",\n noModule: \"nomodule\",\n autoPictureInPicture: \"autopictureinpicture\",\n\n // Enumerated (yes/no, on/off) attributes.\n autoCapitalize: \"autocapitalize\",\n\n // Other global attributes.\n accessKey: \"accesskey\",\n enterKeyHint: \"enterkeyhint\",\n inputMode: \"inputmode\",\n itemId: \"itemid\",\n itemProp: \"itemprop\",\n itemRef: \"itemref\",\n itemType: \"itemtype\",\n tabIndex: \"tabindex\",\n writingSuggestions: \"writingsuggestions\",\n\n // Common non-boolean multi-word HTML attributes.\n charSet: \"charset\",\n hrefLang: \"hreflang\",\n crossOrigin: \"crossorigin\",\n aLink: \"alink\",\n bgColor: \"bgcolor\",\n vLink: \"vlink\",\n formAction: \"formaction\",\n formEncType: \"formenctype\",\n formMethod: \"formmethod\",\n formTarget: \"formtarget\",\n popoverTarget: \"popovertarget\",\n popoverTargetAction: \"popovertargetaction\",\n allowPaymentRequest: \"allowpaymentrequest\",\n allowUserMedia: \"allowusermedia\",\n frameBorder: \"frameborder\",\n longDesc: \"longdesc\",\n marginHeight: \"marginheight\",\n marginWidth: \"marginwidth\",\n referrerPolicy: \"referrerpolicy\",\n srcDoc: \"srcdoc\",\n hSpace: \"hspace\",\n fetchPriority: \"fetchpriority\",\n srcSet: \"srcset\",\n srcLang: \"srclang\",\n useMap: \"usemap\",\n vSpace: \"vspace\",\n dirName: \"dirname\",\n imageSizes: \"imagesizes\",\n imageSrcSet: \"imagesrcset\",\n classId: \"classid\",\n codeBase: \"codebase\",\n codeType: \"codetype\",\n valueType: \"valuetype\",\n shadowRootClonable: \"shadowrootclonable\",\n shadowRootDelegatesFocus: \"shadowrootdelegatesfocus\",\n shadowRootMode: \"shadowrootmode\",\n colSpan: \"colspan\",\n rowSpan: \"rowspan\",\n noWrap: \"nowrap\",\n vAlign: \"valign\",\n charOff: \"charoff\",\n maxLength: \"maxlength\",\n minLength: \"minlength\",\n autoComplete: \"autocomplete\",\n encType: \"enctype\",\n dateTime: \"datetime\",\n};\n","export const HtmlTags = [\n \"a\",\n \"abbr\",\n \"address\",\n \"article\",\n \"aside\",\n \"audio\",\n \"b\",\n \"base\",\n \"blockquote\",\n \"br\",\n \"button\",\n \"canvas\",\n \"caption\",\n \"cite\",\n \"code\",\n \"col\",\n \"colgroup\",\n \"data\",\n \"datalist\",\n \"dd\",\n \"del\",\n \"details\",\n \"dfn\",\n \"dialog\",\n \"div\",\n \"dl\",\n \"dt\",\n \"em\",\n \"fieldset\",\n \"figcaption\",\n \"figure\",\n \"footer\",\n \"form\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"header\",\n \"hgroup\",\n \"i\",\n \"iframe\",\n \"img\",\n \"input\",\n \"ins\",\n \"kbd\",\n \"label\",\n \"legend\",\n \"li\",\n \"main\",\n \"map\",\n \"mark\",\n \"meta\",\n \"meter\",\n \"nav\",\n \"noscript\",\n \"object\",\n \"ol\",\n \"optgroup\",\n \"option\",\n \"output\",\n \"p\",\n \"param\",\n \"picture\",\n \"pre\",\n \"progress\",\n \"q\",\n \"rp\",\n \"rt\",\n \"ruby\",\n \"s\",\n \"samp\",\n \"section\",\n \"select\",\n \"slot\",\n \"small\",\n \"source\",\n \"span\",\n \"strong\",\n \"sub\",\n \"summary\",\n \"sup\",\n \"table\",\n \"tbody\",\n \"td\",\n \"template\",\n \"textarea\",\n \"tfoot\",\n \"th\",\n \"thead\",\n \"time\",\n \"title\",\n \"tr\",\n \"track\",\n \"u\",\n \"ul\",\n \"var\",\n \"video\",\n \"wbr\",\n \"bdi\",\n \"bdo\",\n \"math\",\n \"menu\",\n \"search\",\n \"area\",\n \"embed\",\n \"hr\",\n \"animate\",\n \"animateMotion\",\n \"animateTransform\",\n \"circle\",\n \"clipPath\",\n \"cursor\",\n \"defs\",\n \"desc\",\n \"ellipse\",\n \"feBlend\",\n \"feColorMatrix\",\n \"feComponentTransfer\",\n \"feComposite\",\n \"feConvolveMatrix\",\n \"feDiffuseLighting\",\n \"feDisplacementMap\",\n \"feDistantLight\",\n \"feDropShadow\",\n \"feFlood\",\n \"feFuncA\",\n \"feFuncB\",\n \"feFuncG\",\n \"feFuncR\",\n \"feGaussianBlur\",\n \"feImage\",\n \"feMerge\",\n \"feMergeNode\",\n \"feMorphology\",\n \"feOffset\",\n \"fePointLight\",\n \"feSpecularLighting\",\n \"feSpotLight\",\n \"feTile\",\n \"feTurbulence\",\n \"filter\",\n \"foreignObject\",\n \"g\",\n \"image\",\n \"line\",\n \"linearGradient\",\n \"marker\",\n \"mask\",\n \"metadata\",\n \"mpath\",\n \"path\",\n \"pattern\",\n \"polygon\",\n \"polyline\",\n \"prefetch\",\n \"radialGradient\",\n \"rect\",\n \"set\",\n \"solidColor\",\n \"stop\",\n \"svg\",\n \"switch\",\n \"symbol\",\n \"tbreak\",\n \"text\",\n \"textPath\",\n \"tspan\",\n \"use\",\n \"view\",\n];\n","//browserslist query \"> 0.1%, not dead\"\nexport const PrefixCSS: Record<string, string[]> = {\n transform: [\"webkit\", \"ms\"],\n transition: [\"webkit\", \"ms\"],\n animation: [\"webkit\"],\n userSelect: [\"webkit\", \"ms\"],\n flexDirection: [\"webkit\", \"ms\"],\n flexWrap: [\"webkit\", \"ms\"],\n justifyContent: [\"webkit\", \"ms\"],\n alignItems: [\"webkit\", \"ms\"],\n alignSelf: [\"webkit\", \"ms\"],\n order: [\"webkit\", \"ms\"],\n flexGrow: [\"webkit\", \"ms\"],\n flexShrink: [\"webkit\", \"ms\"],\n flexBasis: [\"webkit\", \"ms\"],\n columns: [\"webkit\"],\n columnCount: [\"webkit\"],\n columnGap: [\"webkit\"],\n columnRule: [\"webkit\"],\n columnWidth: [\"webkit\"],\n boxSizing: [\"webkit\"],\n appearance: [\"webkit\", \"moz\"],\n filter: [\"webkit\"],\n backdropFilter: [\"webkit\"],\n clipPath: [\"webkit\"],\n mask: [\"webkit\"],\n maskImage: [\"webkit\"],\n textSizeAdjust: [\"webkit\", \"ms\"],\n hyphens: [\"webkit\", \"ms\"],\n writingMode: [\"webkit\", \"ms\"],\n gridTemplateColumns: [\"ms\"],\n gridTemplateRows: [\"ms\"],\n gridAutoColumns: [\"ms\"],\n gridAutoRows: [\"ms\"],\n gridColumn: [\"ms\"],\n gridRow: [\"ms\"],\n marginInlineStart: [\"webkit\"],\n marginInlineEnd: [\"webkit\"],\n paddingInlineStart: [\"webkit\"],\n paddingInlineEnd: [\"webkit\"],\n minInlineSize: [\"webkit\"],\n maxInlineSize: [\"webkit\"],\n minBlockSize: [\"webkit\"],\n maxBlockSize: [\"webkit\"],\n inlineSize: [\"webkit\"],\n blockSize: [\"webkit\"],\n tabSize: [\"moz\"],\n overscrollBehavior: [\"webkit\", \"ms\"],\n touchAction: [\"ms\"],\n resize: [\"webkit\"],\n printColorAdjust: [\"webkit\"],\n backgroundClip: [\"webkit\"],\n boxDecorationBreak: [\"webkit\"],\n overflowScrolling: [\"webkit\"],\n};\n","export const SvgTags = [\n \"svg\",\n \"circle\",\n \"path\",\n \"rect\",\n \"ellipse\",\n \"line\",\n \"polyline\",\n \"polygon\",\n \"g\",\n \"defs\",\n \"use\",\n \"symbol\",\n \"linearGradient\",\n \"radialGradient\",\n \"stop\",\n \"clipPath\",\n \"mask\",\n \"filter\",\n \"text\",\n \"tspan\",\n \"textPath\",\n \"image\",\n \"pattern\",\n \"marker\",\n \"animate\",\n \"animateTransform\",\n \"animateMotion\",\n \"feGaussianBlur\",\n \"feComposite\",\n \"feColorMatrix\",\n \"feMerge\",\n \"feMergeNode\",\n \"feOffset\",\n \"feFlood\",\n \"feBlend\",\n \"feTurbulence\",\n \"feDisplacementMap\",\n \"feComponentTransfer\",\n \"feFuncR\",\n \"feFuncG\",\n \"feFuncB\",\n \"feFuncA\",\n \"foreignObject\",\n];\n","export const VoidTags = [\n \"area\",\n \"base\",\n \"br\",\n \"col\",\n \"embed\",\n \"hr\",\n \"img\",\n \"input\",\n \"link\",\n \"meta\",\n \"source\",\n \"track\",\n \"wbr\",\n] as const;\n\nexport type VoidTagName = (typeof VoidTags)[number];\n","interface DomphyConfig {\n cspNonce?: string;\n}\n\nconst _config: DomphyConfig = {};\n\nexport function configure(options: Partial<DomphyConfig>): void {\n Object.assign(_config, options);\n}\n\nexport function getConfig(): Readonly<DomphyConfig> {\n return _config;\n}\n","export const EventProperties = [\n \"onAbort\",\n \"onAuxClick\",\n \"onBeforeMatch\",\n \"onBeforeToggle\",\n \"onBlur\",\n \"onCancel\",\n \"onCanPlay\",\n \"onCanPlayThrough\",\n \"onChange\",\n \"onClick\",\n \"onClose\",\n \"onContextLost\",\n \"onContextMenu\",\n \"onContextRestored\",\n \"onCopy\",\n \"onCueChange\",\n \"onCut\",\n \"onDblClick\",\n \"onDrag\",\n \"onDragEnd\",\n \"onDragEnter\",\n \"onDragLeave\",\n \"onDragOver\",\n \"onDragStart\",\n \"onDrop\",\n \"onDurationChange\",\n \"onEmptied\",\n \"onEnded\",\n \"onError\",\n \"onFocus\",\n \"onFormData\",\n \"onInput\",\n \"onInvalid\",\n \"onKeyDown\",\n \"onKeyPress\",\n \"onKeyUp\",\n \"onLoad\",\n \"onLoadedData\",\n \"onLoadedMetadata\",\n \"onLoadStart\",\n \"onMouseDown\",\n \"onMouseEnter\",\n \"onMouseLeave\",\n \"onMouseMove\",\n \"onMouseOut\",\n \"onMouseOver\",\n \"onMouseUp\",\n \"onPaste\",\n \"onPause\",\n \"onPlay\",\n \"onPlaying\",\n \"onProgress\",\n \"onRateChange\",\n \"onReset\",\n \"onResize\",\n \"onScroll\",\n \"onScrollEnd\",\n \"onSecurityPolicyViolation\",\n \"onSeeked\",\n \"onSeeking\",\n \"onSelect\",\n \"onSlotChange\",\n \"onStalled\",\n \"onSubmit\",\n \"onSuspend\",\n \"onTimeUpdate\",\n \"onToggle\",\n \"onVolumeChange\",\n \"onWaiting\",\n \"onWheel\",\n \"onTouchStart\",\n \"onTouchMove\",\n \"onTouchEnd\",\n \"onTouchCancel\",\n \"onPointerDown\",\n \"onPointerMove\",\n \"onPointerUp\",\n \"onPointerCancel\",\n \"onPointerEnter\",\n \"onPointerLeave\",\n \"onPointerOver\",\n \"onPointerOut\",\n \"onGotPointerCapture\",\n \"onLostPointerCapture\",\n \"onCompositionStart\",\n \"onCompositionUpdate\",\n \"onCompositionEnd\",\n \"onTransitionEnd\",\n \"onTransitionStart\",\n \"onAnimationStart\",\n \"onAnimationEnd\",\n \"onAnimationIteration\",\n \"onFullscreenChange\",\n \"onFullscreenError\",\n \"onFocusIn\",\n \"onFocusOut\",\n] as const;\n\nexport const eventNameMap = EventProperties.reduce(\n (acc, ev) => {\n const key = ev.slice(2).toLowerCase() as keyof HTMLElementEventMap;\n acc[key] = ev;\n return acc;\n },\n {} as Partial<\n Record<keyof HTMLElementEventMap, (typeof EventProperties)[number]>\n >,\n);\n","import type { Handler } from \"../types.js\";\n\n// A Collector is the bridge between auto-tracked reads (State.get / RecordState.get\n// called WITHOUT an explicit listener) and the existing Notifier subscription model.\n//\n// When a Collector is active and a reactive source is read, the source subscribes\n// the Collector's `handler` to its Notifier exactly as it would any other listener.\n// The Notifier hands back a `release` callback through `handler.onSubscribe`; the\n// Collector records every release it receives so the whole dependency set can be\n// torn down at once on the next re-run (effect/computed) or on dispose. This reuses\n// Notifier's subscribe/notify/flush and `_chain` cycle detection — there is no\n// parallel reactivity system.\nexport class Collector {\n // The function the Notifier actually stores as a listener. Invoked (via the\n // Notifier flush) whenever any tracked dependency changes.\n readonly handler: Handler;\n // Release callbacks for the dependencies subscribed during the current run.\n private _releases: Set<() => void> = new Set();\n\n constructor(onDependencyChange: () => void) {\n const handler = (() => onDependencyChange()) as Handler;\n // Notifier.addListener calls onSubscribe(release) right after adding the\n // listener. Record the release so we can drop this exact subscription later.\n handler.onSubscribe = (release: () => void) => {\n this._releases.add(release);\n };\n this.handler = handler;\n }\n\n // Release every dependency subscribed since the last reset. Called before a\n // re-run (so stale deps are dropped and only freshly read deps remain) and on\n // dispose (so nothing is left subscribed).\n reset(): void {\n for (const release of this._releases) release();\n this._releases.clear();\n }\n\n get dependencyCount(): number {\n return this._releases.size;\n }\n}\n\n// Stack of active collectors. A stack (not a single slot) so nested reactive\n// computations compose: a `computed` read inside an `effect` pushes its own\n// collector while running, then pops, restoring the effect as the active one.\nconst COLLECTOR_STACK: Collector[] = [];\n\n// Depth of active `untrack` regions. While > 0, reads do NOT register into the\n// active collector even though one is on the stack.\nlet UNTRACK_DEPTH = 0;\n\n// The collector that auto-tracked reads should subscribe to right now, or null\n// when tracking is suppressed (inside untrack) or no computation is running.\nexport function activeCollector(): Collector | null {\n if (UNTRACK_DEPTH > 0) return null;\n return COLLECTOR_STACK.length\n ? COLLECTOR_STACK[COLLECTOR_STACK.length - 1]\n : null;\n}\n\n// Run `fn` with `collector` active, guaranteeing the stack is restored even if\n// `fn` throws.\nexport function runWithCollector<T>(collector: Collector, fn: () => T): T {\n COLLECTOR_STACK.push(collector);\n try {\n return fn();\n } finally {\n COLLECTOR_STACK.pop();\n }\n}\n\n// Run `fn` with tracking suppressed; reads inside register nowhere.\nexport function runUntracked<T>(fn: () => T): T {\n UNTRACK_DEPTH++;\n try {\n return fn();\n } finally {\n UNTRACK_DEPTH--;\n }\n}\n","import type { Handler } from \"../types.js\";\n\ntype ChainEntry = [notifier: Notifier, event: string];\n\n// Shared across all instances to track the flush chain for circular detection.\nlet _chain: ChainEntry[] = [];\n\n// Microtask scheduler. Older embedded Chromium runtimes (SketchUp 2020 /\n// 2021.0 ship CEF 64) predate `queueMicrotask` (added in Chrome 71). A\n// resolved Promise's `.then` runs as a microtask in the same checkpoint, so\n// it is the standard fallback. The `.catch` mimics `queueMicrotask`'s\n// behaviour of surfacing thrown errors to the global error handler rather\n// than silently becoming an unhandled-rejection.\nexport const _microtask: (cb: () => void) => void =\n typeof queueMicrotask === \"function\"\n ? queueMicrotask\n : (cb) => {\n Promise.resolve()\n .then(cb)\n .catch((e) => {\n setTimeout(() => {\n throw e;\n }, 0);\n });\n };\n\n// Cap on self-re-notifications within one settle burst. A converging update\n// (clamp/normalize) reaches a fixpoint in a pass or two; anything beyond this is\n// a genuinely diverging self-feedback loop and is stopped like a cycle.\nconst SELF_NOTIFY_CAP = 100;\n\n// Batching: while `_batchDepth > 0`, every `notify` records its pending entry as\n// usual but does NOT schedule a flush. Notifiers that received writes during the\n// batch are collected in `_batchedNotifiers`; when the outermost batch ends they\n// are scheduled together, so the whole batch coalesces into a SINGLE microtask\n// flush instead of one per write. This composes with the existing per-event\n// `_pending` coalescing (repeated writes to the same event still collapse to one\n// entry) without ever double-flushing.\nlet _batchDepth = 0;\nlet _batchedNotifiers: Set<Notifier> = new Set();\n\n// Every Notifier with a flush scheduled but not yet run. flushSync() drains this\n// to apply pending state-change notifications synchronously (see\n// flushPendingNotifiers); normal operation still flushes via the microtask.\nconst _scheduledNotifiers: Set<Notifier> = new Set();\n\n// Run `fn`, deferring all flushes triggered inside it into one flush afterwards.\n// Nested batches collapse into the outermost one. Reentrant-safe: the stack is\n// restored and the batched set is flushed even if `fn` throws.\nexport function runBatched<T>(fn: () => T): T {\n _batchDepth++;\n try {\n return fn();\n } finally {\n _batchDepth--;\n if (_batchDepth === 0) {\n const notifiers = _batchedNotifiers;\n _batchedNotifiers = new Set();\n for (const notifier of notifiers) notifier._scheduleFlush();\n }\n }\n}\n\nexport class Notifier {\n // `Object.create(null)` avoids inheriting Object.prototype (`constructor`,\n // `toString`, `hasOwnProperty`, `__proto__`, ...): a plain `{}` would resolve\n // `this._listeners[event]` to an inherited value for those event names,\n // which is truthy but not a Set, crashing `.has`/`.add` on first subscribe.\n private _listeners: Record<string, Set<Handler>> | null = Object.create(\n null,\n );\n private _pending: Map<string, { args: unknown[]; chain: ChainEntry[] }> =\n new Map();\n private _scheduled = false;\n // Args currently being delivered per event (used to detect a self-update fixpoint).\n private _flushing: Map<string, unknown[]> = new Map();\n // Self-re-notification depth in the current settle burst (runaway guard).\n private _selfDepth = 0;\n\n _dispose(): void {\n if (this._listeners) {\n for (const event in this._listeners) {\n this._listeners[event].clear();\n }\n }\n this._listeners = null;\n }\n\n addListener(event: string, listener: Handler): () => void {\n if (!this._listeners) return () => {};\n\n if (typeof event !== \"string\" || typeof listener !== \"function\") {\n throw new Error(\n \"Event name must be a string, listener must be a function\",\n );\n }\n\n if (!this._listeners[event]) {\n this._listeners[event] = new Set();\n }\n\n const release = () => this.removeListener(event, listener);\n\n if (this._listeners[event].has(listener)) return release;\n\n this._listeners[event].add(listener);\n if (typeof listener.onSubscribe === \"function\") {\n listener.onSubscribe(release);\n }\n\n return release;\n }\n\n removeListener(event: string, listener: Handler): void {\n if (!this._listeners) return;\n\n const listeners = this._listeners[event];\n if (listeners && listeners.has(listener)) {\n listeners.delete(listener);\n if (listeners.size === 0) {\n delete this._listeners[event];\n }\n }\n }\n\n // Number of listeners subscribed to an event. Used by `computed` to stay lazy:\n // an unobserved computed only marks itself dirty on a dependency change and\n // defers recomputation until the next read.\n listenerCount(event: string): number {\n return this._listeners?.[event]?.size ?? 0;\n }\n\n notify(event: string, ...args: unknown[]): void {\n if (!this._listeners) return;\n if (!this._listeners[event]) return;\n\n // A listener that re-sets its OWN state mid-flush shows up as [this,event] at\n // the TOP of the chain. That is a converging self-update (clamp/normalize),\n // not a cross-state cycle — let it re-propagate with a fresh chain. A deeper\n // match (intervening notifiers) is a real cycle and is still rejected.\n const top = _chain.length ? _chain[_chain.length - 1] : null;\n const selfReentry = !!top && top[0] === this && top[1] === event;\n\n if (selfReentry) {\n const inflight = this._flushing.get(event);\n // Same value as the one being delivered → fixpoint reached, stop quietly.\n if (inflight && inflight[0] === args[0]) return;\n if (this._selfDepth >= SELF_NOTIFY_CAP) {\n console.error(\n `[Domphy] Runaway self-update on \"${event}\" — stopped after ${SELF_NOTIFY_CAP} iterations`,\n );\n return;\n }\n this._selfDepth++;\n this._pending.set(event, { args, chain: [] });\n } else {\n if (this._isCircular(event)) return;\n this._pending.set(event, { args, chain: [..._chain] });\n }\n\n // While batching, defer scheduling: just remember this notifier has pending\n // work so the outermost batch can flush it once. Outside a batch, schedule\n // the microtask flush immediately as before.\n if (_batchDepth > 0) {\n _batchedNotifiers.add(this);\n } else {\n this._scheduleFlush();\n }\n }\n\n // Schedule the microtask flush if one is not already pending. Idempotent, so a\n // batch flushing many notifiers (and concurrent direct notifies) never queues\n // two flushes for the same instance.\n _scheduleFlush(): void {\n if (this._scheduled) return;\n this._scheduled = true;\n _scheduledNotifiers.add(this);\n _microtask(() => this._flushAll());\n }\n\n private _isCircular(event: string): boolean {\n const idx = _chain.findIndex(([n, e]) => n === this && e === event);\n if (idx === -1) return false;\n\n const names = [..._chain.slice(idx).map(([, e]) => e), event];\n console.error(\n `[Domphy] Circular dependency detected:\\n ${names.join(\" → \")}`,\n );\n return true;\n }\n\n _flushAll(): void {\n this._scheduled = false;\n _scheduledNotifiers.delete(this);\n const pending = this._pending;\n this._pending = new Map();\n\n for (const [event, { args, chain }] of pending) {\n _chain = chain;\n this._flush(event, args);\n }\n _chain = [];\n // Burst settled (no self-update re-queued anything) → reset the runaway guard.\n if (this._pending.size === 0) this._selfDepth = 0;\n }\n\n private _flush(event: string, args: unknown[]): void {\n if (!this._listeners) return;\n const listeners = this._listeners[event];\n if (!listeners) return;\n\n _chain.push([this, event]);\n this._flushing.set(event, args);\n\n for (const listener of [...listeners]) {\n if (!listeners.has(listener)) continue;\n try {\n listener(...args);\n } catch (e) {\n console.error(e);\n }\n }\n\n this._flushing.delete(event);\n _chain.pop();\n }\n}\n\n// True when any Notifier has a flush scheduled but not yet run. flushSync() uses\n// this to decide whether more synchronous draining is needed.\nexport function hasPendingNotifiers(): boolean {\n return _scheduledNotifiers.size > 0;\n}\n\n// Synchronously run every scheduled Notifier flush, including notifiers\n// scheduled while draining (a listener that writes another state re-schedules\n// its own Notifier). Driven by flushSync() alongside the reaction queue.\nexport function flushPendingNotifiers(): void {\n let guard = 0;\n while (_scheduledNotifiers.size > 0) {\n if (guard++ > 10000) {\n console.error(\"[Domphy] flushSync: notifier queue did not settle\");\n break;\n }\n const notifiers = [..._scheduledNotifiers];\n _scheduledNotifiers.clear();\n for (const notifier of notifiers) notifier._flushAll();\n }\n}\n","import type { Handler } from \"../types.js\";\nimport { activeCollector } from \"./Collector.js\";\nimport { Notifier } from \"./Notifier.js\";\n\nexport type ValueListener<T> = ((_value: T) => void) & Handler;\nexport type ReadableState<T> = {\n readonly _isState: true;\n get(listener?: ValueListener<T>): T;\n};\nexport type ValueOrState<T> = T | State<T> | ReadableState<T>;\n\nexport class State<T> {\n readonly _isState = true;\n private _value: T;\n readonly initialValue: T;\n private _notifier: Notifier | null = new Notifier();\n\n constructor(\n initialValue: T,\n readonly name: string = typeof initialValue,\n ) {\n this.initialValue = initialValue;\n this._value = initialValue;\n }\n\n get(listener?: ValueListener<T>): T {\n if (listener) {\n this.addListener(listener);\n } else {\n // Auto-tracking: with no explicit listener, subscribe the active collector\n // (a running computed/effect) so it re-runs when this state changes. When\n // no collector is active the read is a plain, untracked value read — the\n // original behavior is preserved exactly.\n const collector = activeCollector();\n if (collector) this.addListener(collector.handler as ValueListener<T>);\n }\n return this._value;\n }\n\n set(newValue: T): void {\n if (!this._notifier) return;\n this._value = newValue;\n this._notifier.notify(this.name, newValue);\n }\n\n reset(): void {\n this.set(this.initialValue);\n }\n\n addListener(listener: ValueListener<T>): () => void {\n if (!this._notifier) return () => {};\n return this._notifier.addListener(this.name, listener);\n }\n\n removeListener(listener: ValueListener<T>): void {\n if (!this._notifier) return;\n this._notifier.removeListener(this.name, listener);\n }\n\n _dispose(): void {\n if (this._notifier) {\n this._notifier._dispose();\n this._notifier = null;\n }\n }\n}\n","import { type ReadableState, State, type ValueListener } from \"./classes/State.js\";\nimport { addEvent, addHook, deepClone } from \"./helpers.js\";\nimport type {\n BehaviorAttach,\n DomphyElement,\n EventName,\n Handler,\n HookMap,\n PartialElement,\n} from \"./types.js\";\n\nexport function merge(\n source: Record<string, any> = {},\n target: Record<string, any> = {},\n): Record<string, any> {\n const comma = [\n \"animation\",\n \"transition\",\n \"boxShadow\",\n \"textShadow\",\n \"background\",\n \"fontFamily\",\n ];\n const space = [\"class\", \"rel\", \"transform\", \"acceptCharset\", \"sandbox\"];\n const adjacent = [\"content\"];\n if (\n Object.prototype.toString.call(target) === \"[object Object]\" &&\n Object.getPrototypeOf(target) === Object.prototype\n ) {\n // plainjs not class instance\n target = deepClone(target);\n }\n\n for (const key in target) {\n const value = target[key];\n if (value === undefined || value === null || value === \"\") continue;\n\n if (typeof value === \"object\" && !Array.isArray(value)) {\n if (typeof source[key] === \"object\") {\n source[key] = merge(source[key], value);\n } else {\n source[key] = value;\n }\n } else {\n if (comma.includes(key)) {\n if (typeof source[key] === \"function\" || typeof value === \"function\") {\n const old = source[key];\n source[key] = (listener: Handler) => {\n const val1 = typeof old === \"function\" ? old(listener) : old;\n const val2 = typeof value === \"function\" ? value(listener) : value;\n return [val1, val2].filter((e) => e).join(\", \");\n };\n } else {\n source[key] = [source[key], value].filter((e) => e).join(\", \");\n }\n } else if (adjacent.includes(key)) {\n if (typeof source[key] === \"function\" || typeof value === \"function\") {\n const old = source[key];\n source[key] = (listener: Handler) => {\n const val1 = typeof old === \"function\" ? old(listener) : old;\n const val2 = typeof value === \"function\" ? value(listener) : value;\n return [val1, val2].filter((e) => e).join(\"\");\n };\n } else {\n source[key] = [source[key], value].filter((e) => e).join(\"\");\n }\n } else if (space.includes(key)) {\n if (typeof source[key] === \"function\" || typeof value === \"function\") {\n const old = source[key];\n source[key] = (listener: Handler) => {\n const val1 = typeof old === \"function\" ? old(listener) : old;\n const val2 = typeof value === \"function\" ? value(listener) : value;\n return [val1, val2].filter((e) => e).join(\" \");\n };\n } else {\n source[key] = [source[key], value].filter((e) => e).join(\" \");\n }\n } else if (key.startsWith(\"on\")) {\n const name = key.replace(\"on\", \"\").toLowerCase() as EventName;\n addEvent(source as DomphyElement, name, value);\n } else if (key.startsWith(\"_on\")) {\n const name = key.replace(\"_on\", \"\") as keyof HookMap;\n addHook(source as DomphyElement, name, value);\n } else {\n source[key] = value;\n }\n }\n }\n return source;\n}\n\nexport function hashString(str: string = \"\"): string {\n let hash = 0x811c9dc5; // FNV-1a 32-bit offset basis\n for (let i = 0; i < str.length; i++) {\n hash ^= str.charCodeAt(i);\n hash = (hash * 0x01000193) >>> 0; // FNV prime, keep 32-bit unsigned\n }\n return String.fromCharCode(97 + (hash % 26)) + hash.toString(16);\n}\n\n// Normalizes `val` into a State-like object exposing `.get()`.\n//\n// WARNING: if `val` is already a State or any ReadableState (including the\n// output of `readonly()`/`computed()`), it is returned UNCHANGED — even\n// though the return type says `State<T>`. A ReadableState that isn't\n// actually a `State` instance has no `.set()` method at runtime; calling\n// `.set()` on the value returned by `toState()` is only safe when you know\n// `val` was not already a read-only source. This is by design — a\n// read-only source must stay read-only — so `toState` never fabricates a\n// `.set()`. Callers that need to write must either accept a plain value (so\n// `toState` allocates a fresh, writable `State`) or check `isState`/inspect\n// the source before calling `.set()`.\nexport function toState<T>(\n val: T | State<T> | ReadableState<T>,\n name?: string,\n): State<T> {\n return val instanceof State || (val as any)?._isState\n ? (val as State<T>)\n : new State<T>(val as T, name);\n}\n\n// Returns true when `value` is a State or any ReadableState (including\n// Computed<T>). Use this as a type guard when writing utilities that accept\n// either a raw value or a reactive source.\n//\n// function bindOrUse<T>(src: T | ReadableState<T>) {\n// if (isState(src)) return src.get()\n// return src\n// }\nexport function isState<T = unknown>(value: unknown): value is ReadableState<T> {\n return (\n typeof value === \"object\" &&\n value !== null &&\n (value as any)._isState === true\n );\n}\n\n// Wraps a State or ReadableState in a read-only view. The returned object exposes\n// only `.get()` — callers cannot call `.set()`. Useful for exposing internal\n// state from a module or factory without granting write access.\n//\n// const _count = toState(0)\n// export const count = readonly(_count) // consumers can read, not write\n// export const increment = () => _count.set(_count.get() + 1)\nexport function readonly<T>(source: ReadableState<T>): ReadableState<T> {\n return {\n _isState: true as const,\n get(listener?: ValueListener<T>): T {\n return source.get(listener);\n },\n };\n}\n\n// Declares a per-node behavior (Svelte-action-like) inside a patch factory.\n// `attach` runs once for the real DOM node the returned partial lands on, no\n// matter how many times the factory itself is re-invoked by a reactive\n// parent; every later call routes its `props` into the SAME instance via\n// `update()` instead of creating a new, disconnected one. Compose with other\n// patch fields normally (spread, `merge()`, or via `$`):\n//\n// function draggable(props: { onMove(dx: number, dy: number): void }) {\n// return behavior(\"draggable\", (node, props) => {\n// const onPointerMove = (e: PointerEvent) => props.onMove(e.movementX, e.movementY)\n// node.domElement!.addEventListener(\"pointermove\", onPointerMove)\n// return {\n// update: (next) => { props = next },\n// destroy: () => node.domElement!.removeEventListener(\"pointermove\", onPointerMove),\n// }\n// }, props)\n// }\n//\n// `key` must be unique per concern on one element (not per patch instance) —\n// two DIFFERENT patches sharing an element (e.g. a tooltip AND a popover on\n// the same button) should use distinct keys so their instances stay\n// independent; re-declaring the SAME key from a later generation is exactly\n// the \"route props into the existing instance\" case this exists for.\nexport function behavior<P>(\n key: string,\n attach: BehaviorAttach<P>,\n props: P,\n): PartialElement {\n return { _behaviors: { [key]: { attach, props } } };\n}\n","import type { ElementNode } from \"./classes/ElementNode.js\";\nimport { getConfig } from \"./config.js\";\nimport { HtmlTags } from \"./constants/HtmlTags.js\";\nimport { eventNameMap } from \"./types/EventProperties.js\";\nimport type {\n DomphyElement,\n HookMap,\n PartialElement,\n TagName,\n} from \"./types.js\";\nimport { merge } from \"./utils.js\";\n\nexport function addHook<K extends keyof HookMap>(\n partial: PartialElement,\n hookName: K,\n handler: HookMap[K],\n): void {\n const hookProperty = `_on${hookName}` as keyof PartialElement;\n const current = partial[hookProperty];\n\n if (typeof current === \"function\") {\n (partial as any)[hookProperty] = (...args: any[]) => {\n (current as Function)(...args);\n (handler as Function)(...args);\n };\n } else {\n (partial as any)[hookProperty] = handler;\n }\n}\n\nexport function addEvent<K extends keyof HTMLElementEventMap>(\n attributes: PartialElement,\n eventName: K,\n handler: (event: HTMLElementEventMap[K], node: ElementNode) => void,\n): void {\n const eventProperty = eventNameMap[eventName];\n if (!eventProperty) {\n throw Error(`invalid event name \"${eventName}\"`);\n }\n const current = (attributes as any)[eventProperty];\n\n if (typeof current === \"function\") {\n (attributes as any)[eventProperty] = (\n event: HTMLElementEventMap[K],\n node: ElementNode,\n ) => {\n current(event, node);\n handler(event, node);\n };\n } else {\n (attributes as any)[eventProperty] = handler;\n }\n}\n\nexport function deepClone(value: any, seen = new WeakMap()): any {\n if (value === null || typeof value !== \"object\") return value;\n if (typeof value === \"function\") return value;\n if (seen.has(value)) return seen.get(value);\n\n let clone: any;\n\n if (Array.isArray(value)) {\n clone = [];\n seen.set(value, clone);\n for (const v of value) clone.push(deepClone(v, seen));\n return clone;\n }\n\n // These built-in types must be checked BEFORE the class-instance bailout\n // below, otherwise their prototype (not Object.prototype) makes the\n // bailout return them by reference and these branches become dead code.\n if (value instanceof Date) return new Date(value);\n if (value instanceof RegExp) return new RegExp(value);\n if (value instanceof Map) {\n clone = new Map();\n seen.set(value, clone);\n for (const [k, v] of value)\n clone.set(deepClone(k, seen), deepClone(v, seen));\n return clone;\n }\n if (value instanceof Set) {\n clone = new Set();\n seen.set(value, clone);\n for (const v of value) clone.add(deepClone(v, seen));\n return clone;\n }\n if (ArrayBuffer.isView(value)) {\n return new (value as any).constructor(value);\n }\n if (value instanceof ArrayBuffer) {\n return value.slice(0);\n }\n\n const proto = Object.getPrototypeOf(value);\n if (proto !== Object.prototype) return value; // ignore class instance (State, ElementNode, ...)\n\n clone = Object.create(proto);\n seen.set(value, clone);\n\n for (const key of Reflect.ownKeys(value)) {\n clone[key] = deepClone(value[key], seen);\n }\n\n return clone;\n}\n\nexport function validate(\n element: DomphyElement | PartialElement,\n asPartial = false,\n): boolean {\n if (Object.prototype.toString.call(element) !== \"[object Object]\") {\n throw Error(`typeof ${element} is invalid DomphyElement`);\n }\n const keys = Object.keys(element);\n if (keys.length === 0 && !asPartial) {\n throw Error(\"element object has no tag key\");\n }\n for (let i = 0; i < keys.length; i++) {\n const key = keys[i];\n const val = element[key as keyof typeof element];\n if (i === 0 && !HtmlTags.includes(key) && !asPartial) {\n throw Error(`key ${key} is not valid HTML tag name`);\n } else if (\n key === \"style\" &&\n val &&\n Object.prototype.toString.call(val) !== \"[object Object]\"\n ) {\n throw Error(`\"style\" must be a object`);\n } else if (key === \"$\") {\n element.$!.forEach((v) => validate(v as PartialElement, true));\n } else if (key.startsWith(\"_on\") && typeof val !== \"function\") {\n throw Error(`hook ${key} value \"${val}\" must be a function `);\n } else if (key.startsWith(\"on\") && typeof val !== \"function\") {\n throw Error(`event ${key} value \"${val}\" must be a function `);\n } else if (key === \"_portal\" && typeof val !== \"function\") {\n throw Error(`\"_portal\" must be a function return HTMLElement`);\n } else if (\n key === \"_context\" &&\n Object.prototype.toString.call(val) !== \"[object Object]\"\n ) {\n throw Error(`\"_context\" must be a object`);\n } else if (\n key === \"_metadata\" &&\n Object.prototype.toString.call(val) !== \"[object Object]\"\n ) {\n throw Error(`\"_metadata\" must be a object`);\n } else if (\n key === \"_key\" &&\n typeof val !== \"string\" &&\n typeof val !== \"number\"\n ) {\n throw Error(`\"_key\" must be a string or number`);\n }\n }\n return true;\n}\n\nexport function isHTML(str: string): boolean {\n // `s` (dotAll) flag: `.` must also match newlines, otherwise a paired-tag\n // string with content spanning multiple lines (e.g. \"<div>\\nfoo\\n</div>\")\n // fails to match and falls through to the plain-text/escaped path.\n return /<([a-z][\\w-]*)(\\s[^>]*)?>.*<\\/\\1>|<([a-z][\\w-]*)(\\s[^>]*)?\\/>/is.test(\n str.trim(),\n );\n}\n\n// Strip <script> elements, event-handler attributes, and javascript: URLs\n// from an HTML string. Works in both SSR (no DOM) and client contexts. Not a\n// full sanitizer — it removes the most common XSS vectors so user-generated\n// strings passed as inline HTML content can't execute arbitrary code.\nexport function sanitizeHTMLString(html: string): string {\n // Remove <script>...</script> elements entirely (paired form), including\n // multi-line bodies. Case-insensitive: the tag name is case-insensitive.\n let result = html.replace(/<script\\b[^>]*>[\\s\\S]*?<\\/script\\s*>/gi, \"\");\n // Self-closing form (e.g. <script src=\"evil.js\"/>) — not valid HTML5 but\n // strip it defensively before the unclosed catch-all below, otherwise the\n // catch-all would swallow everything after it too.\n result = result.replace(/<script\\b[^>]*\\/>/gi, \"\");\n // Unclosed form (opening tag with no matching </script>) — strip from the\n // tag to the end of the string since the real extent is unknowable.\n result = result.replace(/<script\\b[^>]*>[\\s\\S]*$/gi, \"\");\n // Remove on* event handler attributes (onclick, onerror, onload, …).\n // Case-insensitive: HTML attribute names are case-insensitive, so\n // ONERROR=/OnClick= must be stripped too, not just lowercase.\n result = result.replace(\n /\\s+on[a-zA-Z][\\w-]*\\s*=\\s*(?:\"[^\"]*\"|'[^']*'|[^\\s>]*)/gi,\n \"\",\n );\n // Also strip on* when preceded by \"/\" (e.g. <svg/onload=…>)\n result = result.replace(\n /\\/on[a-zA-Z][\\w-]*\\s*=\\s*(?:\"[^\"]*\"|'[^']*'|[^\\s>]*)/gi,\n \"/\",\n );\n // Neutralise javascript: scheme in URL attributes\n result = result.replace(\n /((?:href|src|action|formaction)\\s*=\\s*)([\"']?)[\\s]*javascript:[^\"'\\s>]*/gi,\n \"$1$2#\",\n );\n return result;\n}\n\nexport function escapeHTML(str: string): string {\n return str\n .replace(/&/g, \"&\")\n .replace(/</g, \"<\")\n .replace(/>/g, \">\")\n .replace(/\"/g, \""\")\n .replace(/'/g, \"'\");\n}\n\nexport function addClass(element: PartialElement, className: string): void {\n if (typeof element.class === \"function\") {\n const reactive = element.class;\n element.class = (listener) => `${String(reactive(listener))} ${className}`;\n } else {\n const current = element.class || \"\";\n const split = String(current).split(\" \");\n split.push(className);\n element.class = split.filter((e) => e).join(\" \");\n }\n}\n\nexport function removeClass(element: PartialElement, className: string): void {\n if (typeof element.class === \"function\") {\n const reactive = element.class;\n element.class = (listener) => {\n const split = String(reactive(listener)).split(\" \");\n return split.filter((e) => e !== className).join(\" \");\n };\n } else {\n // Normalize BEFORE stringifying, otherwise a missing `class` stringifies\n // to the literal \"undefined\" and pollutes the resulting class list.\n element.class ||= \"\";\n const split = String(element.class).split(\" \");\n element.class = split.filter((e) => e !== className).join(\" \");\n }\n}\n\nexport function toggleClass(element: PartialElement, className: string): void {\n if (typeof element.class === \"function\") {\n const reactive = element.class;\n element.class = (listener) => {\n const split = String(reactive(listener)).split(\" \");\n return split.includes(className)\n ? split.filter((e) => e !== className).join(\" \")\n : split.concat([className]).join(\" \");\n };\n } else {\n // Normalize BEFORE stringifying, otherwise a missing `class` stringifies\n // to the literal \"undefined\" and pollutes the resulting class list.\n element.class ||= \"\";\n const split = String(element.class).split(\" \");\n element.class = split.includes(className)\n ? split.filter((e) => e !== className).join(\" \")\n : split.concat([className]).join(\" \");\n }\n}\n\nexport function getTagName(element: DomphyElement): TagName | undefined {\n return Object.keys(element).find((e) => HtmlTags.includes(e)) as\n | TagName\n | undefined;\n}\n\nexport function camelToKebab(str: string): string {\n return str.replace(/([a-z0-9])([A-Z])/g, \"$1-$2\").toLowerCase();\n}\n\nexport function selectorSplitter(selectors: string) {\n if (selectors.indexOf(\"@\") === 0) {\n return [selectors];\n }\n var splitted = [];\n var parens = 0;\n var angulars = 0;\n var soFar = \"\";\n for (var i = 0, len = selectors.length; i < len; i++) {\n var char = selectors[i];\n if (char === \"(\") {\n parens += 1;\n } else if (char === \")\") {\n parens -= 1;\n } else if (char === \"[\") {\n angulars += 1;\n } else if (char === \"]\") {\n angulars -= 1;\n } else if (char === \",\") {\n if (!parens && !angulars) {\n splitted.push(soFar.trim());\n soFar = \"\";\n continue;\n }\n }\n soFar += char;\n }\n splitted.push(soFar.trim());\n return splitted;\n}\n\nexport function normalizeSelectorKey(selectorText: string): string {\n const text = selectorText.trim();\n // At-rule headers (@media, @keyframes, @supports...) are matched\n // whitespace-insensitive because CSSOM reformats them unpredictably.\n if (text.startsWith(\"@\")) return text.replace(/\\s+/g, \"\");\n return text\n .replace(/\\s*([>+~,])\\s*/g, \"$1\") // tighten combinators and selector lists\n .replace(/\\s+/g, \" \") // collapse descendant-combinator whitespace\n .replace(/\\(\\s*odd\\s*\\)/g, \"(2n+1)\") // CSSOM serializes :nth-child(odd) as (2n+1)\n .replace(/\\(\\s*even\\s*\\)/g, \"(2n)\")\n .trim();\n}\n\nexport function collectCSSRules(\n rules: CSSRuleList,\n map: Map<string, CSSRule>,\n): Map<string, CSSRule> {\n for (let i = 0; i < rules.length; i++) {\n const rule = rules[i] as any;\n let key: string | null = null;\n if (typeof rule.selectorText === \"string\") {\n key = normalizeSelectorKey(rule.selectorText);\n } else if (\n typeof rule.cssText === \"string\" &&\n rule.cssText.startsWith(\"@\")\n ) {\n key = normalizeSelectorKey(rule.cssText.split(\"{\")[0]);\n }\n if (key && !map.has(key)) map.set(key, rule as CSSRule);\n }\n return map;\n}\n\nexport function ensureDomStyle(\n styleParent: HTMLHeadElement | ShadowRoot,\n nonce?: string,\n): HTMLStyleElement {\n let domStyle = styleParent.querySelector(\n \"#domphy-style\",\n ) as HTMLStyleElement | null;\n\n if (!domStyle) {\n domStyle = document.createElement(\"style\");\n domStyle.id = \"domphy-style\";\n const resolvedNonce = nonce ?? getConfig().cspNonce;\n if (resolvedNonce) domStyle.nonce = resolvedNonce;\n styleParent.appendChild(domStyle);\n }\n\n if (domStyle.dataset.domphyBase !== \"true\") {\n domStyle.sheet?.insertRule(\"[hidden] { display: none !important; }\", 0);\n domStyle.dataset.domphyBase = \"true\";\n }\n\n return domStyle;\n}\n\nexport const mergePartial = (\n partial: PartialElement | DomphyElement,\n): typeof partial => {\n if (Array.isArray(partial.$)) {\n const part: typeof partial = {};\n partial.$.forEach((p) => merge(part, mergePartial(p)));\n delete partial.$;\n merge(part, partial); // native win\n\n return part;\n } else {\n return partial;\n }\n};\n","import {\n BooleanAttributes,\n CamelAttributes,\n HtmlAttributeNames,\n} from \"../constants.js\";\nimport { camelToKebab, escapeHTML } from \"../helpers.js\";\nimport type { AttributeValue } from \"../types.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\nimport { Notifier } from \"./Notifier.js\";\n\n// Enumerated (not boolean) HTML attributes whose missing-value default is the\n// truthy state — unlike BooleanAttributes, omitting them does NOT mean \"off\",\n// so a `true`/`false` input must map to the real keyword instead of being\n// dropped from the DOM.\nconst EnumeratedBooleanAttributes: Record<string, readonly [string, string]> =\n {\n translate: [\"yes\", \"no\"],\n autoCapitalize: [\"on\", \"off\"],\n };\n\nexport class ElementAttribute {\n readonly name: string;\n readonly isBoolean: boolean;\n private readonly enumeratedBoolean?: readonly [string, string];\n value: any;\n // The value exactly as declared by the caller, kept verbatim (a reactive\n // function stays a function here) — unlike `value`, which always holds the\n // current RESOLVED primitive. AttributeList.addClass() reads this to detect\n // whether the existing \"class\" binding is reactive and, if so, to compose\n // with the original function instead of freezing at its last-resolved\n // string.\n declaredValue: AttributeValue = undefined;\n parent: ElementNode;\n _notifier = new Notifier();\n // Release handles for the reactive listener's state subscriptions, so a\n // re-set (e.g. patch() replacing a reactive value) can drop the old listener\n // instead of leaking it on the long-lived State until node removal.\n private _releases: (() => void)[] = [];\n // Whether the BeforeRemove hook that drains _releases has been registered.\n // It must register at most ONCE per attribute: patch() re-sets every\n // reactive attribute on every reuse, and ElementNode.addHook COMPOSES hooks,\n // so an unguarded registration would grow the node's BeforeRemove chain by\n // one closure per subscription per patch for the node's whole life.\n private _removeHooked = false;\n\n constructor(name: string, value: any, parent: any) {\n this.parent = parent;\n this.isBoolean = (BooleanAttributes as readonly string[]).includes(name);\n this.enumeratedBoolean = EnumeratedBooleanAttributes[name];\n if (CamelAttributes.includes(name)) {\n this.name = name;\n } else if (Object.hasOwn(HtmlAttributeNames, name)) {\n this.name = HtmlAttributeNames[name];\n } else {\n this.name = camelToKebab(name);\n }\n this.value = undefined;\n this.set(value);\n }\n\n private normalize(value: any): any {\n if (this.enumeratedBoolean && typeof value === \"boolean\") {\n return value ? this.enumeratedBoolean[0] : this.enumeratedBoolean[1];\n }\n return value;\n }\n\n render(): void {\n if (!this.parent || !this.parent.domElement) return;\n const domElement = this.parent.domElement;\n\n const mutateAttrs = [\"value\"];\n if (this.isBoolean) {\n if (this.value === false || this.value == null) {\n domElement.removeAttribute(this.name);\n } else {\n domElement.setAttribute(\n this.name,\n this.value === true ? \"\" : this.value,\n );\n }\n } else if (this.value == null) {\n domElement.removeAttribute(this.name);\n } else if (mutateAttrs.includes(this.name)) {\n (domElement as any)[this.name] = this.value;\n } else {\n domElement.setAttribute(this.name, this.value);\n }\n }\n\n set(value: AttributeValue): void {\n const prev = this.value;\n this.declaredValue = value;\n\n // Drop any previous reactive subscription before (re)binding.\n if (this._releases.length) {\n for (const release of this._releases) release();\n this._releases = [];\n }\n\n if (value == null) {\n this.value = null;\n } else if (typeof value === \"function\") {\n let listener: any = () => {\n if (!this.parent || this.parent._disposed) return;\n const p = this.value;\n // Re-pass `listener` so states read only on a later run (conditional\n // dependencies) get subscribed too — matching children/style paths.\n this.value = this.isBoolean\n ? Boolean((value as Function)(listener))\n : this.normalize((value as Function)(listener));\n this.render();\n if (p !== this.value) this._notifier.notify(this.name, this.value);\n };\n\n listener.elementNode = this.parent!;\n listener.debug = `class:${this.parent?.tagName}_${this.parent?.nodeId} attribute:${this.name}`;\n\n listener.onSubscribe = (release: () => void) => {\n this._releases.push(release);\n // One hook per attribute (see _removeHooked) — it drains whatever the\n // CURRENT release list holds at removal time, so a single registration\n // covers every later re-set/subscription.\n if (this.parent && !this._removeHooked) {\n this._removeHooked = true;\n this.parent.addHook(\"BeforeRemove\", () => {\n for (const releaseSubscription of this._releases) {\n releaseSubscription();\n }\n this._releases = [];\n listener = null;\n });\n }\n };\n\n this.value = this.isBoolean\n ? Boolean(value(listener))\n : this.normalize(value(listener));\n } else {\n this.value = this.isBoolean ? Boolean(value) : this.normalize(value);\n }\n\n this.render();\n if (prev !== this.value) this._notifier.notify(this.name, this.value);\n }\n\n addListener(callback: (value: any) => void): void {\n const handler = callback as any;\n handler.onSubscribe = (release: () => void) =>\n this.parent?.addHook(\"BeforeRemove\", release);\n this._notifier.addListener(this.name, handler);\n }\n\n remove(): void {\n if (this.parent && this.parent.attributes) {\n this.parent.attributes.remove(this.name);\n }\n this._dispose();\n }\n\n _dispose(): void {\n // Release state subscriptions immediately — an attribute removed\n // individually (AttributeList.remove) must not stay subscribed until the\n // whole node's eventual removal.\n for (const releaseSubscription of this._releases) releaseSubscription();\n this._releases = [];\n this._notifier._dispose();\n this.value = null;\n this.parent = null as any;\n }\n\n generateHTML(): string {\n const { name, value } = this;\n if (this.isBoolean) {\n return value ? `${name}` : \"\";\n }\n // Match render()'s live-DOM behavior (removeAttribute on null/undefined):\n // an attribute whose reactive value resolves to null/undefined is OMITTED,\n // not stringified as the literal text \"null\"/\"undefined\" — that literal\n // text is a real value to a screen reader (e.g. any non-token\n // aria-current is read as \"true\"), so it must never be emitted.\n if (value == null) return \"\";\n const val = Array.isArray(value) ? JSON.stringify(value) : value;\n return `${name}=\"${escapeHTML(String(val))}\"`;\n }\n}\n","import { BooleanAttributes } from \"../constants.js\";\nimport type { AttributeValue, Listener } from \"../types.js\";\nimport { ElementAttribute } from \"./ElementAttribute.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\n\nexport class AttributeList {\n items: Record<string, ElementAttribute> | null = {};\n parent: ElementNode | null;\n\n constructor(parent: ElementNode) {\n this.parent = parent;\n }\n\n generateHTML(): string {\n if (!this.items) return \"\";\n const str = Object.values(this.items)\n .map((attr) => attr.generateHTML())\n .filter(Boolean) // an omitted (null/undefined-valued) attribute emits \"\"\n .join(\" \");\n return str ? ` ${str}` : \"\";\n }\n\n get(name: string): any {\n if (!this.items) return undefined;\n return this.items[name]?.value;\n }\n\n set(name: string, value: AttributeValue): void {\n if (!this.items || !this.parent) return;\n if (this.items[name]) {\n this.items[name].set(value);\n } else {\n this.items[name] = new ElementAttribute(name, value, this.parent);\n }\n }\n\n addListener(name: string, callback: (value: string | number) => void): void {\n if (this.has(name)) {\n this.items![name].addListener(callback);\n }\n }\n\n has(name: string): boolean {\n if (!this.items) return false;\n return Object.hasOwn(this.items, name);\n }\n\n remove(name: string): void {\n if (!this.items) return;\n\n // Resolve the canonical DOM-facing name (e.g. \"ariaCurrent\" -> \"aria-current\")\n // BEFORE disposing the ElementAttribute — removeAttribute() must use the\n // same name render()/setAttribute() used, or the real DOM attribute is\n // left stuck forever for any name camelToKebab()/HtmlAttributeNames changed.\n const domName = this.items[name]?.name ?? name;\n\n if (this.items[name]) {\n this.items[name]._dispose();\n delete this.items[name];\n }\n\n if (\n this.parent &&\n this.parent.domElement &&\n this.parent.domElement instanceof Element\n ) {\n this.parent.domElement.removeAttribute(domName);\n }\n }\n\n _dispose(): void {\n if (this.items) {\n for (const key in this.items) {\n this.items[key]._dispose();\n }\n }\n this.items = null;\n this.parent = null;\n }\n\n toggle(name: string, force?: boolean): void {\n if (\n !BooleanAttributes.includes(name as (typeof BooleanAttributes)[number])\n ) {\n throw Error(`${name} is not a boolean attribute`);\n }\n if (force === true) {\n this.set(name, true);\n } else if (force === false) {\n this.remove(name);\n } else {\n this.has(name) ? this.remove(name) : this.set(name, true);\n }\n }\n\n addClass(className: string | ((listener: Listener) => string)): void {\n if (!className) return;\n if (typeof className !== \"string\" && typeof className !== \"function\") return;\n\n const add = (classes: string, newClass: string) => {\n const list = (classes || \"\").split(\" \").filter((e: string) => e);\n !list.includes(newClass) && list.push(newClass);\n return list.join(\" \");\n };\n\n // Read the declared value (not the resolved `.value`) to detect whether\n // the existing \"class\" binding is reactive — ElementAttribute.set()\n // always invokes a function value immediately and stores only the\n // resolved string as `.value`, so `.get(\"class\")` can never itself be a\n // function; `declaredValue` preserves the original reactive function.\n const declared = this.items?.[\"class\"]?.declaredValue;\n const currentIsFn = typeof declared === \"function\";\n const current = currentIsFn ? declared : this.get(\"class\");\n const nextIsFn = typeof className === \"function\";\n\n // Neither side is reactive — merge as a plain string, same as before.\n if (!currentIsFn && !nextIsFn) {\n this.set(\"class\", add(current, className as string));\n return;\n }\n\n // Either side is reactive: the merged class must itself be a function so\n // it re-resolves on every listener tick, threading the SAME listener\n // through both sides so each one's own state dependencies (if any) are\n // tracked. Calling a reactive side with no listener (the previous bug\n // here) both breaks its dependency tracking and, at the ElementNode.merge\n // call site, silently drops the auto-generated per-node style class —\n // the element's own `style: {}` object then never reaches the DOM.\n this.set(\"class\", (listener: Listener) =>\n add(\n currentIsFn ? (current as (l: Listener) => string)(listener) : current,\n nextIsFn\n ? (className as (l: Listener) => string)(listener)\n : (className as string),\n ),\n );\n }\n\n hasClass(className: string): boolean {\n if (!className || typeof className !== \"string\") return false;\n const current = this.get(\"class\") || \"\";\n const list = current.split(\" \").filter((e: string) => e);\n return list.includes(className);\n }\n\n toggleClass(className: string): void {\n if (!className || typeof className !== \"string\") return;\n this.hasClass(className)\n ? this.removeClass(className)\n : this.addClass(className);\n }\n\n removeClass(className: string): void {\n if (!className || typeof className !== \"string\") return;\n const current = this.get(\"class\") || \"\";\n const list: string[] = current.split(\" \").filter((e: string) => e);\n const updated = list.filter((cls) => cls !== className);\n updated.length > 0\n ? this.set(\"class\", updated.join(\" \"))\n : this.remove(\"class\");\n }\n\n replaceClass(oldClass: string, newClass: string): void {\n if (\n !oldClass ||\n !newClass ||\n typeof oldClass !== \"string\" ||\n typeof newClass !== \"string\"\n )\n return;\n if (this.hasClass(oldClass)) {\n this.removeClass(oldClass);\n this.addClass(newClass);\n }\n }\n}\n","declare const process: { env: Record<string, string | undefined> } | undefined;\n\n// Dev-only warning guard. A consumer bundler (Vite / webpack / esbuild)\n// statically replaces `process.env.NODE_ENV`, so production builds fold this to\n// `false` and tree-shake the guarded warnings out entirely. The `typeof process`\n// check keeps the IIFE/CDN build (and embedded runtimes such as SketchUp's CEF,\n// which have no `process`) from throwing at load time — there it stays `false`,\n// so warnings simply never fire. In a bundler's dev mode (or a test runner where\n// NODE_ENV is \"test\"/unset) it is `true`, surfacing the warnings during\n// development without any runtime cost in production.\nexport const __DEV__: boolean =\n typeof process !== \"undefined\" &&\n process.env != null &&\n process.env.NODE_ENV !== \"production\";\n","import { PrefixCSS } from \"../constants.js\";\nimport { camelToKebab } from \"../helpers.js\";\nimport type { Listener, StyleValue } from \"../types.js\";\nimport type { StyleRule } from \"./StyleRule.js\";\n\nexport class StyleProperty {\n name: string;\n cssName: string;\n value: StyleValue = \"\";\n parentRule: StyleRule;\n // Release handles for the reactive listener's state subscriptions, so a\n // re-set (e.g. StyleList.patchCSS() replacing a reactive value on a reused\n // node) can drop the old listener(s) instead of leaking them on the\n // long-lived State(s) until node removal. A single reactive style function\n // can subscribe to MULTIPLE states in one evaluation (e.g.\n // `transform: (l) => \\`translate(${x.get(l)}px, ${y.get(l)}px)\\``), so\n // onSubscribe can fire more than once per set() call -- every release must\n // be kept, not just the last one. Mirrors ElementAttribute's `_releases`\n // array pattern.\n private _releases: (() => void)[] = [];\n\n constructor(name: string, value: StyleValue, parentRule: StyleRule) {\n this.name = name;\n // CSS custom properties (`--fooBar`) are case-sensitive and never\n // kebab-cased by the platform itself — running one through\n // camelToKebab() would mangle it (e.g. \"--siteHeaderHeight\" ->\n // \"--site-header-height\"), silently breaking every `var(--siteHeaderHeight)`\n // reference elsewhere in the same style tree.\n this.cssName = name.startsWith(\"--\") ? name : camelToKebab(name);\n this.parentRule = parentRule;\n this.set(value);\n }\n\n _domUpdate(): void {\n if (!this.parentRule) return;\n const domRule = this.parentRule.domRule;\n\n if (domRule && (domRule as CSSStyleRule).style) {\n const style: CSSStyleDeclaration = (domRule as CSSStyleRule).style;\n style.setProperty(this.cssName, String(this.value));\n\n if (PrefixCSS[this.name]) {\n PrefixCSS[this.name].forEach((prefix) => {\n style.setProperty(`-${prefix}-${this.cssName}`, String(this.value));\n });\n }\n }\n }\n _dispose(): void {\n if (this._releases.length) {\n for (const release of this._releases) release();\n this._releases = [];\n }\n this.value = \"\";\n this.parentRule = null as any;\n }\n\n set(value: StyleValue): void {\n // Drop any previous reactive subscription(s) before (re)binding.\n if (this._releases.length) {\n for (const release of this._releases) release();\n this._releases = [];\n }\n\n if (typeof value === \"function\") {\n let listener = (() => {\n if (!this.parentRule || this.parentRule.parentNode?._disposed) return;\n this.value = value(listener);\n this._domUpdate();\n }) as unknown as Listener;\n\n listener.onSubscribe = (release: () => void) => {\n this._releases.push(release);\n };\n\n listener.elementNode = this.parentRule!.root!;\n listener.debug = `class:${this.parentRule?.root?.tagName}_${this.parentRule?.root?.nodeId} style:${this.name}`;\n this.value = value(listener);\n } else {\n this.value = value;\n }\n\n this._domUpdate();\n }\n\n remove(): void {\n if (!this.parentRule) return;\n\n if (this.parentRule.domRule instanceof CSSStyleRule) {\n const domStyle = this.parentRule.domRule.style;\n domStyle.removeProperty(this.cssName);\n\n if (PrefixCSS[this.name]) {\n PrefixCSS[this.name].forEach((prefix) => {\n domStyle.removeProperty(`-${prefix}-${this.cssName}`);\n });\n }\n }\n delete this.parentRule.styleBlock![this.name];\n this._dispose();\n }\n\n cssText(): string {\n let str = `${this.cssName}: ${this.value}`;\n if (PrefixCSS[this.name]) {\n PrefixCSS[this.name].forEach((prefix) => {\n str += `; -${prefix}-${this.cssName}: ${this.value}`;\n });\n }\n return str;\n }\n}\n","import type { ElementNode } from \"./ElementNode.js\";\nimport { StyleList } from \"./StyleList.js\";\nimport { StyleProperty } from \"./StyleProperty.js\";\n\nexport class StyleRule {\n selectorText: string;\n domRule: CSSRule | CSSMediaRule | CSSKeyframesRule | null = null;\n styleList: StyleList | null;\n styleBlock: Record<string, StyleProperty> | null = {};\n parent: StyleRule | ElementNode | null;\n\n constructor(selectorText: string, parent: StyleRule | ElementNode) {\n this.selectorText = selectorText;\n this.styleList = new StyleList(this);\n this.parent = parent;\n }\n\n _dispose(): void {\n if (this.styleBlock) {\n for (const prop of Object.values(this.styleBlock)) {\n prop._dispose();\n }\n }\n\n if (this.styleList) {\n this.styleList._dispose();\n }\n\n this.styleBlock = null;\n this.styleList = null;\n this.domRule = null;\n this.parent = null;\n }\n\n get root() {\n let node = this.parent;\n while (node instanceof StyleRule) {\n node = node.parent;\n }\n return node;\n }\n\n get parentNode(): ElementNode | null {\n let root: any = this.parent;\n while (root && root instanceof StyleRule) {\n root = root.parent;\n }\n return root as ElementNode;\n }\n\n insertStyle(name: string, val: any): void {\n if (!this.styleBlock) return;\n if (this.styleBlock[name]) {\n this.styleBlock[name].set(val);\n } else {\n this.styleBlock[name] = new StyleProperty(name, val, this);\n }\n }\n\n removeStyle(name: string): void {\n if (!this.styleBlock) return;\n if (this.styleBlock[name]) {\n this.styleBlock[name].remove();\n }\n }\n\n cssText(): string {\n if (!this.styleBlock || !this.styleList) return \"\";\n const styleStr = Object.values(this.styleBlock)\n .map((decl) => decl.cssText())\n .join(\";\");\n const nested = this.styleList.cssText();\n return `${this.selectorText} { ${styleStr} ${nested} } `;\n }\n\n mount(domRule: CSSRule | CSSKeyframesRule): void {\n if (!domRule || !this.styleList) return;\n this.domRule = domRule;\n if (\"cssRules\" in domRule) {\n this.styleList.mount(domRule.cssRules as CSSRuleList);\n }\n }\n\n remove(): void {\n if (this.domRule && this.domRule.parentStyleSheet) {\n const sheet = this.domRule.parentStyleSheet;\n const rules = sheet.cssRules;\n for (let i = 0; i < rules.length; i++) {\n if (rules[i] === this.domRule) {\n sheet.deleteRule(i);\n break;\n }\n }\n }\n this._dispose();\n }\n\n render(domSheet: CSSStyleSheet | CSSGroupingRule) {\n if (!this.styleBlock || !this.styleList) return;\n const styleStr = Object.values(this.styleBlock)\n .map((decl) => decl.cssText())\n .join(\";\");\n try {\n if (!this.selectorText.startsWith(\"@\")) {\n const css = `${this.selectorText} { ${styleStr} }`;\n const index = domSheet.insertRule(css, domSheet.cssRules.length);\n const domRule = domSheet.cssRules[index];\n if (domRule && \"selectorText\" in domRule) {\n this.mount(domRule);\n }\n } else if (\n /^@(media|supports|container|layer)\\b/.test(this.selectorText)\n ) {\n const index = domSheet.insertRule(\n `${this.selectorText} {}`,\n domSheet.cssRules.length,\n );\n const domRule = domSheet.cssRules[index];\n if (\"cssRules\" in domRule) {\n this.mount(domRule as CSSGroupingRule);\n this.styleList.render(domRule as CSSGroupingRule);\n }\n } else if (\n this.selectorText.startsWith(\"@keyframes\") ||\n this.selectorText.startsWith(\"@font-face\")\n ) {\n const css = this.cssText();\n const index = domSheet.insertRule(css, domSheet.cssRules.length);\n const domRule = domSheet.cssRules[index];\n this.mount(domRule);\n }\n } catch (err) {\n console.warn(\"Failed to insert rule:\", this.selectorText, err);\n }\n }\n}\n","import { normalizeSelectorKey, selectorSplitter } from \"../helpers.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\nimport { StyleRule } from \"./StyleRule.js\";\n\nexport class StyleList {\n parent: StyleRule | ElementNode | null;\n items: StyleRule[] = [];\n domStyle: HTMLStyleElement | null = null;\n\n constructor(parent: StyleRule | ElementNode) {\n this.parent = parent;\n }\n\n get parentNode(): ElementNode | null {\n let root: any = this.parent;\n while (root && root instanceof StyleRule) {\n root = root.parent;\n }\n return root as ElementNode;\n }\n\n addCSS(obj: Record<string, any>, parentSelector: string = \"\"): void {\n if (!this.items || !this.parent) return;\n const basic: Record<string, any> = {};\n // Conditional at-rules (@media/@container/@supports/@layer) must be inserted\n // AFTER the base property block so that same-specificity rules in the at-rule\n // override the base when the condition matches (later rules win in the cascade).\n const conditionalRules: StyleRule[] = [];\n\n function getSelector(selector: string, prev: string): string {\n return selector.startsWith(\"&\")\n ? `${prev}${selector.slice(1)}`\n : `${prev} ${selector}`;\n }\n\n for (const selector in obj) {\n const value = obj[selector];\n const splitKeys = selectorSplitter(selector);\n for (const key of splitKeys) {\n const currentSelector = getSelector(key, parentSelector);\n if (/^@(container|layer|supports|media)\\b/.test(key)) {\n if (typeof value === \"object\" && value != null) {\n const rule = new StyleRule(key, this.parent);\n rule.styleList!.addCSS(value, parentSelector);\n conditionalRules.push(rule);\n }\n } else if (key.startsWith(\"@keyframes\")) {\n const rule = new StyleRule(key, this.parent);\n rule.styleList!.addCSS(value, \"\");\n this.items.push(rule);\n } else if (key.startsWith(\"@font-face\")) {\n const rule = new StyleRule(key, this.parent);\n for (const k in value) rule.insertStyle(k, value[k]);\n this.items.push(rule);\n } else if (typeof value === \"object\" && value != null) {\n const rule = new StyleRule(currentSelector, this.parent);\n this.items.push(rule);\n for (const [k, v] of Object.entries(value)) {\n if (typeof v === \"object\" && v != null) {\n // A further-nested selector block (whether it starts with '&'\n // or is a plain descendant selector like \".icon\") must be\n // flattened as a sibling rule at THIS level, not re-processed\n // as a rule nested inside `rule` -- `rule.styleList` is never\n // rendered for a plain (non-@) selector (see StyleRule.render()),\n // so inserting there silently drops the rule from the live\n // stylesheet on client render, and re-running addCSS against the\n // same already-fully-resolved `newSelector` duplicated the\n // selector text inside itself. `getSelector` already joins `k`\n // onto `currentSelector` correctly for both cases (concat for\n // '&', descendant-space otherwise), so both cases resolve the\n // same way: recurse on `this` with the fully-resolved selector.\n const newSelector = getSelector(k, currentSelector);\n this.addCSS(v, newSelector);\n } else {\n rule.insertStyle(k, v);\n }\n }\n } else {\n basic[key] = value;\n }\n }\n }\n\n if (Object.keys(basic).length) {\n const rule = new StyleRule(parentSelector, this.parent);\n for (const key in basic) rule.insertStyle(key, basic[key]);\n this.items.push(rule);\n }\n\n for (const rule of conditionalRules) {\n this.items.push(rule);\n }\n }\n\n cssText(): string {\n if (!this.items) return \"\";\n return this.items.map((rule) => rule.cssText()).join(\"\");\n }\n\n // Reconcile this node's own FLAT (non-selector, non-at-rule) style properties\n // in place: update/add properties present in `obj`, remove properties that\n // were present before and are gone now. Used by ElementNode.patch() when list\n // reconciliation reuses a live node, so a freshly-computed static style object\n // (e.g. from a factory function like `FilterButton(...)` called again with new\n // args) actually reaches the DOM instead of being silently dropped — `addCSS`\n // itself is append-only and would duplicate CSSOM rules if called again.\n //\n // Nested selector blocks (&:hover, @media/@supports/@container/@layer,\n // @keyframes, @font-face) are NOT reconciled here — they are set once at\n // construction and assumed stable across reuse. A value that must change\n // after construction under a nested selector needs its own reactive function\n // (`color: (l) => …`), same as it already did before this method existed.\n patchCSS(obj: Record<string, any>, parentSelector: string = \"\"): void {\n if (!this.items || !this.parent) return;\n\n const basic: Record<string, any> = {};\n for (const key in obj) {\n const value = obj[key];\n if (typeof value === \"object\" && value != null) continue; // nested/@rule block\n basic[key] = value;\n }\n\n let rule = this.items.find((r) => r.selectorText === parentSelector);\n if (!rule) {\n rule = new StyleRule(parentSelector, this.parent);\n this.items.push(rule);\n }\n\n const seen = new Set(Object.keys(basic));\n for (const key in basic) rule.insertStyle(key, basic[key]);\n\n if (rule.styleBlock) {\n for (const existingKey of Object.keys(rule.styleBlock)) {\n if (!seen.has(existingKey)) rule.removeStyle(existingKey);\n }\n }\n\n // A brand-new rule has no live CSSOM binding yet — insert it now if this\n // node is already mounted (addCSS's construction-time path relies on a\n // single later styles.render() call that already ran for a reused node).\n const sheet = this.domStyle?.sheet;\n if (!rule.domRule && sheet) rule.render(sheet);\n }\n\n insertRule(selector: string): StyleRule {\n if (!this.items || !this.parent) return null as any;\n let rule = this.items.find((rule) => rule.selectorText === selector);\n if (!rule) {\n rule = new StyleRule(selector, this.parent);\n this.items.push(rule);\n }\n return rule;\n }\n\n hydrate(domRuleMap: Map<string, CSSRule>): void {\n if (!this.items) return;\n for (const rule of this.items) {\n const domRule = domRuleMap.get(normalizeSelectorKey(rule.selectorText));\n if (domRule) rule.mount(domRule as CSSRule);\n }\n }\n\n mount(domRuleList: CSSRuleList): void {\n if (!this.items) return;\n if (!domRuleList) throw Error(\"Require domRuleList argument\");\n let wrongCount = 0;\n const fixOddEven = (css: string) =>\n css.replace(\"(odd)\", \"(2n+1)\").replace(\"(even)\", \"(2n)\");\n\n this.items.forEach((rule, i) => {\n const index = i - wrongCount;\n const domRule = domRuleList[index];\n if (!domRule) return;\n if (\n rule.selectorText.startsWith(\"@\") &&\n domRule instanceof CSSKeyframesRule\n ) {\n rule.mount(domRule);\n } else if (\"keyText\" in domRule) {\n rule.mount(domRule);\n } else if (\"selectorText\" in domRule) {\n if (domRule.selectorText !== fixOddEven(rule.selectorText)) {\n wrongCount += 1;\n } else {\n rule.mount(domRule);\n }\n } else if (\"cssRules\" in domRule) {\n rule.mount(domRule as CSSMediaRule);\n }\n });\n }\n\n render(dom: HTMLStyleElement | CSSGroupingRule) {\n if (dom instanceof HTMLStyleElement) {\n this.domStyle = dom;\n this.items.forEach((rule) => rule.render(dom.sheet!));\n } else if (dom instanceof CSSGroupingRule) {\n this.items.forEach((rule) => rule.render(dom));\n }\n }\n\n _dispose(): void {\n if (this.items) {\n for (let i = 0; i < this.items.length; i++) {\n this.items[i]._dispose();\n }\n }\n\n this.items = [];\n this.parent = null;\n this.domStyle = null;\n }\n}\n","import { SvgTags, VoidTags } from \"../constants.js\";\nimport { __DEV__ } from \"../dev.js\";\nimport {\n collectCSSRules,\n deepClone,\n ensureDomStyle,\n getTagName,\n mergePartial,\n validate,\n} from \"../helpers.js\";\nimport type {\n BehaviorInstance,\n BehaviorSpec,\n DomphyElement,\n EventName,\n HookMap,\n Listener,\n PartialElement,\n TagName,\n} from \"../types.js\";\nimport { hashString, merge } from \"../utils.js\";\nimport { AttributeList } from \"./AttributeList.js\";\nimport { ElementList } from \"./ElementList.js\";\nimport { StyleList } from \"./StyleList.js\";\n\nexport class ElementNode {\n _disposed = false;\n _beforeRemoveFired = false;\n // True when inserted imperatively (a direct children.insert() by app/patch\n // code, e.g. a floating panel or an _onInit-inserted subtree) rather than by\n // declared-inputs reconciliation — see ElementList.update()/insert().\n _imperative = false;\n type = \"ElementNode\";\n parent: ElementNode | null = null;\n _childrenRelease?: () => void;\n // Whether the BeforeRemove hook that releases `_childrenRelease` has been\n // registered for this node. It must register at most ONCE per node: patch()\n // re-runs _setupFunctionChildren on every reuse, and addHook COMPOSES hooks,\n // so an unguarded registration would grow the hook chain by one closure per\n // patch for the node's whole life.\n _childrenReleaseHooked = false;\n _portal?: (root: ElementNode) => HTMLElement;\n // Per-node behavior contract (see `behavior()` in utils.ts). Attached\n // instances, keyed the same as their declaring `_behaviors` record.\n _behaviorInstances = new Map<string, BehaviorInstance>();\n // Specs declared before the DOM element exists (construction-time merge()),\n // held until the Mount hook can actually attach them.\n _pendingBehaviors = new Map<string, BehaviorSpec>();\n _behaviorMountHooked = false;\n _behaviorTeardownHooked = false;\n tagName: TagName;\n children = new ElementList(this);\n styles = new StyleList(this);\n attributes = new AttributeList(this);\n domElement?: HTMLElement | null = null;\n _hooks: HookMap = {};\n _events?:\n | { [K in EventName]?: (event: Event, node: ElementNode) => void }\n | null = null;\n _boundEvents = new Set<EventName>();\n _context?: Record<string, any> = {};\n _metadata?: Record<string, any> = {};\n key?: string | number | null = null;\n nodeId: string;\n\n constructor(\n domphyElement: DomphyElement,\n _parent: ElementNode | null = null,\n index = 0,\n ) {\n domphyElement = deepClone(domphyElement);\n validate(domphyElement);\n domphyElement.style = domphyElement.style || {};\n this.parent = _parent;\n this.tagName = getTagName(domphyElement) as TagName;\n domphyElement = mergePartial(domphyElement) as DomphyElement;\n\n this.key = (domphyElement as any)._key ?? null;\n this._context = domphyElement._context || {};\n this._metadata = domphyElement._metadata || {};\n\n const tempPath = `${this.parent?.nodeId}.${index}`;\n const str = JSON.stringify(domphyElement.style || {}, (_k, v) =>\n typeof v === \"function\" ? tempPath : v,\n );\n this.nodeId = hashString(tempPath + str);\n\n this.attributes!.addClass(`${this.tagName}_${this.nodeId}`);\n if (domphyElement._onSchedule)\n domphyElement._onSchedule(this, domphyElement);\n\n this.merge(domphyElement);\n\n const children = (domphyElement as any)[this.tagName];\n\n if (children != null) {\n if (typeof children === \"function\") {\n this._setupFunctionChildren(children);\n } else {\n this.children!.update(Array.isArray(children) ? children : [children]);\n }\n }\n this._hooks.Init && this._hooks.Init(this);\n }\n\n _setupFunctionChildren(fn: (listener: any) => any): void {\n let listener: any = () => {\n if (this._disposed) return;\n try {\n const input = fn(listener);\n this.children!.update(Array.isArray(input) ? input : [input]);\n } catch (error) {\n this._handleError(error);\n }\n };\n listener!.elementNode = this;\n listener!.debug = `class:${this.tagName}_${this.nodeId} children`;\n // onSubscribe fires once per Notifier the listener subscribes to — a\n // children function reading N states yields N release handles. Keeping\n // only the last one leaked the others: the stale subscriptions kept\n // re-running an OLD generation's closure after patch() re-setup.\n const releases: Array<() => void> = [];\n listener!.onSubscribe = (release: () => void) => {\n releases.push(release);\n this._childrenRelease = () => {\n for (const releaseSubscription of releases) releaseSubscription();\n releases.length = 0;\n listener = null;\n };\n // Register the releasing hook once per NODE, not once per subscription\n // or per patch() re-setup — addHook composes, so repeats would grow the\n // BeforeRemove chain unboundedly on frequently re-rendered nodes. The\n // hook body reads the CURRENT _childrenRelease dynamically, so one\n // registration covers every later re-setup.\n if (!this._childrenReleaseHooked) {\n this._childrenReleaseHooked = true;\n this.addHook(\"BeforeRemove\", () => {\n this._childrenRelease?.();\n this._childrenRelease = undefined;\n });\n }\n };\n listener();\n }\n\n _createDOMNode() {\n const svgNamespace = \"http://www.w3.org/2000/svg\";\n const node = SvgTags.includes(this.tagName)\n ? document.createElementNS(svgNamespace, this.tagName)\n : document.createElement(this.tagName);\n\n this.domElement = node as HTMLElement;\n\n if (this._events) {\n for (const key in this._events) this._bindEvent(key as EventName);\n }\n\n if (this.attributes) {\n Object.values(this.attributes.items!).forEach((attr) => attr.render());\n }\n return node;\n }\n\n // Bind a DOM listener that dispatches LIVE from this._events, so patch() can\n // swap the handler (e.g. a list item's onClick closure after its data changes)\n // without detaching/reattaching the DOM listener.\n _bindEvent(eventName: EventName): void {\n if (!this.domElement || this._boundEvents.has(eventName)) return;\n this._boundEvents.add(eventName);\n let fn: any = (event: Event) => this._events?.[eventName]?.(event, this);\n this.domElement.addEventListener(eventName, fn);\n this.addHook(\"BeforeRemove\", (n) => {\n n.domElement?.removeEventListener(eventName, fn);\n fn = null;\n });\n }\n\n _dispose(): void {\n if (this._disposed) return;\n this._disposed = true;\n\n // Fire BeforeRemove so reactive-listener releases (registered as BeforeRemove\n // hooks via onSubscribe) actually run for this node. Descendants are torn\n // down through this recursive _dispose — not through ElementList.remove — so\n // without this their subscriptions to long-lived State/RecordState leak.\n // Skip if the async-removal path in ElementList already fired it.\n if (!this._beforeRemoveFired) {\n this._beforeRemoveFired = true;\n this._hooks.BeforeRemove?.(this, () => {});\n }\n\n if (this.children) {\n this.children._dispose();\n }\n\n if (this.styles) {\n this.styles.items!.forEach((rule) => rule.remove());\n this.styles._dispose();\n }\n\n if (this.attributes) {\n this.attributes._dispose();\n }\n\n // _onRemove fires for every node in the subtree, not just the directly-removed one.\n this._hooks.Remove?.(this);\n\n this.domElement = null;\n this._hooks = {};\n this._events = null;\n this._context = {};\n this._metadata = {};\n this.parent = null;\n }\n merge(part: PartialElement) {\n merge(this._context, part._context);\n merge(this._metadata, part._metadata);\n this._processBehaviors(part._behaviors);\n\n const keys = Object.keys(part);\n for (let i = 0; i < keys.length; i++) {\n const originalKey = keys[i];\n const value = (part as any)[originalKey];\n if (\n [\n \"$\",\n \"_onSchedule\",\n \"_key\",\n \"_context\",\n \"_metadata\",\n \"_behaviors\",\n \"style\",\n this.tagName,\n ].includes(originalKey)\n ) {\n } else if (\n [\n \"_onInit\",\n \"_onInsert\",\n \"_onMount\",\n \"_onBeforeUpdate\",\n \"_onUpdate\",\n \"_onBeforeRemove\",\n \"_onRemove\",\n \"_onError\",\n ].includes(originalKey)\n ) {\n this.addHook(originalKey.substring(3) as keyof HookMap, value);\n } else if (originalKey.startsWith(\"on\")) {\n this.addEvent(\n originalKey.substring(2).toLowerCase() as EventName,\n value,\n );\n } else if (originalKey === \"_portal\") {\n this._portal = value;\n } else if (originalKey === \"class\") {\n // A `class` must MERGE with (not replace) the auto-generated per-node\n // style class set at construction (line ~67) — replacing it outright\n // orphans this element's own `style: {}` object, since the CSS rule\n // is scoped to that auto class name. This applies to string/function\n // values (via AttributeList.addClass) AND to a nullish value (e.g. an\n // element passing through `class: props.className` with `className`\n // left unset) — the latter must be a no-op, NOT fall through to the\n // generic `attributes.set(\"class\", undefined)` below, which clears\n // the attribute and silently drops the auto class token.\n if (typeof value === \"string\" || typeof value === \"function\") {\n this.attributes!.addClass(value);\n }\n } else {\n this.attributes!.set(originalKey, value);\n }\n }\n if (part.style) {\n this.styles.addCSS(\n part.style || {},\n `.${`${this.tagName}_${this.nodeId}`}`,\n );\n }\n }\n\n // Update this live node IN PLACE from a fresh element description, preserving\n // its DOM element (and thus focus/scroll/selection/uncontrolled value) and its\n // children's identity. Used by list reconciliation to reuse a node by key\n // (keyed) or position (unkeyed) while reflecting new data, instead of\n // destroying and recreating the DOM. Flat style properties ARE reconciled (see\n // styles.patchCSS below) — a reused node's newly-computed static style must\n // reach the DOM, e.g. a factory function like `FilterButton(label, active,\n // onClick)` called again with new args from a reactive parent. Nested selector\n // blocks (&:hover, @media, …) are NOT reconciled — set once at construction,\n // assumed stable across reuse. Lifecycle hooks are NOT re-run (reused items\n // share structure; hooks already ran). Reactive content (a function child)\n // keeps its own listener and is left untouched.\n patch(rawElement: DomphyElement): void {\n let element: any = deepClone(rawElement);\n element.style = element.style || {};\n element = mergePartial(element);\n\n // Children / content — recurse so grandchildren are reused/patched too.\n // Reactive function always wins: release old binding and re-setup with the\n // new closure so the node reflects the new data source, not the stale one.\n // Nullish content means \"no children declared\" — same as the constructor —\n // NOT \"remove all children\". Treating it as [] here used to wipe children\n // that a patch inserted imperatively (node.children.insert in _onInit, e.g.\n // selectBox/combobox's inner tag list + input) on every ancestor re-render,\n // since lifecycle hooks don't re-run on a reused node to put them back.\n const content = element[this.tagName];\n if (typeof content === \"function\") {\n this._childrenRelease?.();\n this._childrenRelease = undefined;\n this._setupFunctionChildren(content);\n } else if (content != null) {\n const next = Array.isArray(content) ? content : [content];\n this.children.update(next, !!this.domElement, true);\n }\n\n if (element._context) merge(this._context, element._context);\n if (element._metadata) merge(this._metadata, element._metadata);\n this._processBehaviors(element._behaviors);\n\n this.styles.patchCSS(element.style || {}, `.${this.tagName}_${this.nodeId}`);\n\n // Rebuild attributes and events. Events are replaced (live dispatch in\n // _bindEvent reads this._events, so swapping the map is enough); attributes\n // present before but absent now are removed; the auto scope class is kept.\n const autoClass = `${this.tagName}_${this.nodeId}`;\n const reserved = [\n \"$\",\n \"_onSchedule\",\n \"_key\",\n \"_context\",\n \"_metadata\",\n \"_behaviors\",\n \"style\",\n this.tagName,\n ];\n const hookKeys = [\n \"_onInit\",\n \"_onInsert\",\n \"_onMount\",\n \"_onBeforeUpdate\",\n \"_onUpdate\",\n \"_onBeforeRemove\",\n \"_onRemove\",\n \"_onError\",\n ];\n const keep = new Set<string>([\"class\"]);\n let userClass: string | ((listener: Listener) => string) | null = null;\n\n this._events = {};\n for (const key of Object.keys(element)) {\n if (reserved.includes(key) || hookKeys.includes(key) || key === \"_portal\")\n continue;\n const value = element[key];\n if (key.startsWith(\"on\") && typeof value === \"function\") {\n this.addEvent(key.substring(2).toLowerCase() as EventName, value);\n } else if (\n key === \"class\" &&\n (typeof value === \"string\" || typeof value === \"function\")\n ) {\n userClass = value;\n } else {\n this.attributes!.set(key, value);\n keep.add(key);\n }\n }\n\n // A reactive userClass must stay reactive here too — a plain string\n // combine (as if it were static) would freeze it at whatever the\n // function happened to return on this one patch call, and never update\n // again since patch() doesn't re-run per listener tick.\n if (typeof userClass === \"function\") {\n const userClassFn = userClass;\n this.attributes!.set(\n \"class\",\n (listener: Listener) => `${autoClass} ${userClassFn(listener)}`,\n );\n } else {\n this.attributes!.set(\n \"class\",\n userClass ? `${autoClass} ${userClass}` : autoClass,\n );\n }\n\n if (this.attributes!.items) {\n for (const name of Object.keys(this.attributes!.items)) {\n if (!keep.has(name)) this.attributes!.remove(name);\n }\n }\n\n if (this._events) {\n for (const key in this._events) this._bindEvent(key as EventName);\n }\n }\n\n // Walk ancestors to find the nearest Error hook. The boundary node receives\n // the error and a `reset` callback that clears its children (allowing it to\n // re-render with fresh data or a fallback). If no handler is found, log to\n // console so errors in reactive children are never silently swallowed.\n _handleError(error: unknown): void {\n let node: ElementNode | null = this;\n while (node) {\n if (node._hooks.Error) {\n const boundary = node;\n node._hooks.Error(boundary, error, () => {\n boundary.children.update([]);\n });\n return;\n }\n node = node.parent;\n }\n console.error(\"[Domphy] Unhandled error in reactive child:\", error);\n }\n\n addEvent(\n name: EventName,\n callback: (event: Event, node: ElementNode) => void,\n ): void {\n this._events = this._events || {};\n\n const current = this._events[name];\n if (typeof current === \"function\") {\n this._events[name] = (event: Event, node: ElementNode) => {\n current!(event, node);\n callback(event, node);\n };\n } else {\n this._events[name] = callback;\n }\n }\n\n addHook<K extends keyof HookMap>(name: K, callback: HookMap[K]): void {\n const current = this._hooks[name];\n\n if (typeof current === \"function\") {\n const composed = ((...args: any[]) => {\n (current as Function)(...args);\n (callback as Function)(...args);\n }) as HookMap[K];\n // Preserve the maximum declared arity across composed hooks. Removal logic\n // inspects BeforeRemove.length (>= 2 means the hook owns `done()`, e.g. an\n // exit animation); a naive (...args) wrapper would report 0 and break that.\n try {\n Object.defineProperty(composed, \"length\", {\n value: Math.max(\n (current as Function).length,\n (callback as Function).length,\n ),\n configurable: true,\n });\n } catch {\n /* length non-configurable on some engines — best effort */\n }\n this._hooks[name] = composed;\n } else {\n this._hooks[name] = callback;\n }\n }\n getRoot(): ElementNode {\n let root: ElementNode = this;\n while (root && root instanceof ElementNode && root.parent) {\n root = root.parent;\n }\n return root;\n }\n\n // Route a `_behaviors` record declared by THIS generation's PartialElement\n // into their per-node instances: an already-attached key gets its fresh\n // `props` forwarded via update() (the cross-generation fix — the instance,\n // not the closure that declared it, is what persists); a not-yet-attached\n // key attaches immediately if the DOM element already exists (the patch()/\n // reused-node path), or is queued for the node's one-time Mount hook\n // (the merge()/construction path, where domElement doesn't exist yet).\n _processBehaviors(behaviors?: Record<string, BehaviorSpec>): void {\n if (!behaviors) return;\n for (const key of Object.keys(behaviors)) {\n const spec = behaviors[key];\n const instance = this._behaviorInstances.get(key);\n if (instance) {\n instance.update?.(spec.props);\n } else if (this.domElement) {\n this._attachBehaviorNow(key, spec);\n } else {\n this._pendingBehaviors.set(key, spec);\n this._ensureBehaviorMountHook();\n }\n }\n }\n\n _attachBehaviorNow(key: string, spec: BehaviorSpec): void {\n const instance = spec.attach(this, spec.props) || {};\n this._behaviorInstances.set(key, instance);\n this._ensureBehaviorTeardownHook();\n }\n\n // Registered at most once per node (Mount itself only ever fires once per\n // real DOM node) — flushes whatever was queued by merge() at construction,\n // by then reading domElement/getRoot() safely.\n _ensureBehaviorMountHook(): void {\n if (this._behaviorMountHooked) return;\n this._behaviorMountHooked = true;\n this.addHook(\"Mount\", () => {\n if (this._pendingBehaviors.size === 0) return;\n const pending = this._pendingBehaviors;\n this._pendingBehaviors = new Map();\n pending.forEach((spec, key) => this._attachBehaviorNow(key, spec));\n });\n }\n\n // Registered at most once per node — addHook COMPOSES, so a per-attach\n // registration would grow the BeforeRemove chain by one closure per\n // behavior key. The body reads the CURRENT instance map dynamically, so\n // one registration covers every key attached over the node's whole life.\n _ensureBehaviorTeardownHook(): void {\n if (this._behaviorTeardownHooked) return;\n this._behaviorTeardownHooked = true;\n this.addHook(\"BeforeRemove\", () => {\n this._behaviorInstances.forEach((instance) => instance.destroy?.());\n this._behaviorInstances.clear();\n });\n }\n\n // Look up a behavior instance by key, walking up from this node through its\n // ancestors (same pattern as getContext/getMetadata) — a behavior is\n // declared on the element that owns the concern (e.g. a combobox's outer\n // anchor), but the event that needs it often fires on a DESCENDANT (e.g.\n // the combobox's inner input on focus). Returns undefined if the key was\n // never declared on this node or an ancestor, or was declared but hasn't\n // attached yet (construction-time, pre-Mount).\n getBehavior<T extends BehaviorInstance = BehaviorInstance>(\n key: string,\n ): T | undefined {\n let node: ElementNode | null = this;\n while (node) {\n const instance = node._behaviorInstances.get(key);\n if (instance) return instance as T;\n node = node.parent;\n }\n return undefined;\n }\n\n getContext(name: string): any {\n let node: ElementNode | null = this;\n while (node && (!node._context || !Object.hasOwn(node._context, name))) {\n node = node.parent;\n }\n return node && node._context ? node._context[name] : undefined;\n }\n\n setContext(name: string, value: any) {\n this._context = this._context || {};\n this._context[name] = value;\n }\n\n getMetadata(name: string): any {\n return this._metadata ? this._metadata[name] : undefined;\n }\n\n setMetadata(key: string, value: any) {\n this._metadata = this._metadata || {};\n this._metadata[key] = value;\n }\n\n generateCSS(): string {\n if (!this.styles || !this.children) return \"\";\n let css = this.styles.cssText();\n css += this.children.items\n .map((child) => (child instanceof ElementNode ? child.generateCSS() : \"\"))\n .join(\"\");\n return css;\n }\n\n generateHTML(): string {\n if (!this.children || !this.attributes) return \"\";\n const attributes = this.attributes.generateHTML();\n // Void elements must not emit a closing tag — `<br></br>` is parsed by the\n // HTML tokenizer as two <br>, which corrupts hydration child alignment.\n if ((VoidTags as readonly string[]).includes(this.tagName)) {\n return `<${this.tagName}${attributes}>`;\n }\n const content = this.children.generateHTML();\n return `<${this.tagName}${attributes}>${content}</${this.tagName}>`;\n }\n\n mount(domElement: HTMLElement, domStyle?: HTMLStyleElement): void {\n if (!domElement) throw new Error(\"Missing dom node on bind\");\n if (\n __DEV__ &&\n !domStyle &&\n this.parent === null &&\n domElement.childNodes.length > 0\n ) {\n console.warn(\n \"[Domphy] mount() was called without a style element on already-rendered DOM. Reactive style updates after hydration will be dropped — pass the server-rendered <style> element as the second argument to mount().\",\n );\n }\n this.domElement = domElement;\n\n if (this._events) {\n for (const key in this._events) this._bindEvent(key as EventName);\n }\n\n if (this.children) {\n this.children.items.forEach((child, i) => {\n const childNode = domElement.childNodes[i];\n if (!childNode) return;\n if (child instanceof ElementNode) {\n child.mount(childNode as HTMLElement);\n } else {\n // Bind the server-rendered text/inline-HTML node so that reactive\n // child updates after hydration can locate and replace it.\n child.domText = childNode;\n }\n });\n }\n\n // Attach reactive style declarations to the server-rendered stylesheet so\n // post-hydration updates mutate the existing CSSOM rules instead of being\n // silently dropped (StyleProperty._domUpdate needs a bound domRule). Done\n // once from the call that received the style element, walking the whole\n // subtree because per-node selectors are globally unique.\n if (domStyle) {\n const sheet = domStyle.sheet;\n if (sheet)\n this._hydrateStyles(collectCSSRules(sheet.cssRules, new Map()));\n }\n\n this._hooks.Mount && this._hooks.Mount(this);\n }\n\n _hydrateStyles(domRuleMap: Map<string, CSSRule>): void {\n this.styles?.hydrate(domRuleMap);\n if (this.children) {\n for (const child of this.children.items) {\n if (child instanceof ElementNode) child._hydrateStyles(domRuleMap);\n }\n }\n }\n\n render(\n domElement: HTMLElement | SVGElement | DocumentFragment,\n ): HTMLElement | SVGElement {\n const newNode = this._createDOMNode();\n domElement.appendChild(newNode);\n this._hooks.Mount && this._hooks.Mount(this);\n let domStyle = this.getRoot().styles.domStyle;\n const root = domElement.getRootNode();\n const styleParent = root instanceof ShadowRoot ? root : document.head;\n domStyle ||= ensureDomStyle(styleParent);\n this.styles.render(domStyle as HTMLStyleElement);\n this.children.items.forEach((child) => {\n if (child instanceof ElementNode && child._portal) {\n const dom = child._portal!(this.getRoot());\n dom && child.render(dom);\n } else {\n child.render(newNode);\n }\n });\n return newNode;\n }\n\n remove() {\n if (this.parent) {\n this.parent.children.remove(this);\n } else {\n // Root removal must also run BeforeRemove/Remove (and release reactive\n // subscriptions across the whole tree via _dispose), honoring async done().\n const done = () => {\n this.domElement?.remove();\n this._dispose();\n };\n if (this._hooks.BeforeRemove && this.domElement) {\n let called = false;\n const once = () => {\n if (!called) {\n called = true;\n done();\n }\n };\n // Capture the hook reference (and thus its arity) before calling it — a\n // synchronous 2-arg hook (e.g. `motion()` with no `exit` frame) may call\n // `once()` inline, which runs `done()` -> `_dispose()` -> clears\n // `this._hooks` to `{}` before this line would otherwise re-read it.\n const beforeRemoveHook = this._hooks.BeforeRemove;\n this._beforeRemoveFired = true;\n beforeRemoveHook(this, once);\n if ((beforeRemoveHook as Function).length < 2 && !called) once();\n else if (__DEV__ && !called) {\n setTimeout(() => {\n if (!called)\n console.warn(\n \"[Domphy] _onBeforeRemove declared a `done` parameter but did not call it within 5s — the element will stay in the DOM. Call done() when cleanup finishes.\",\n );\n }, 5000);\n }\n } else {\n done();\n }\n }\n }\n}\n","import { escapeHTML, isHTML, sanitizeHTMLString } from \"../helpers.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\n\nexport class TextNode {\n type = \"TextNode\";\n // True when inserted imperatively (a direct children.insert()) rather than\n // by declared-inputs reconciliation — see ElementList.update()/insert().\n _imperative = false;\n parent: ElementNode;\n text: string;\n domText?: ChildNode;\n\n constructor(textContent: string | number, parent: ElementNode) {\n this.parent = parent;\n this.text = textContent === \"\" ? \"\\u200B\" : String(textContent);\n }\n _createDOMNode() {\n let newNode: ChildNode;\n if (isHTML(this.text)) {\n const tpl = document.createElement(\"template\");\n tpl.innerHTML = this.text.trim();\n // Strip event-handler attributes and javascript: URLs from all elements.\n tpl.content.querySelectorAll(\"*\").forEach((el) => {\n for (const attr of Array.from(el.attributes)) {\n if (/^on/i.test(attr.name)) {\n el.removeAttribute(attr.name);\n } else if (\n /^(?:href|src|action|formaction)$/i.test(attr.name) &&\n /^\\s*javascript:/i.test(attr.value)\n ) {\n el.setAttribute(attr.name, \"#\");\n }\n }\n });\n newNode = tpl.content.firstChild || document.createTextNode(\"\");\n } else {\n newNode = document.createTextNode(this.text);\n }\n this.domText = newNode;\n return newNode;\n }\n\n // Update the text content in place. When the node is a plain DOM text node and\n // stays plain text, mutate `nodeValue` directly (cheap, preserves the node) —\n // this is what lets reactive text like `(l) => \"Count: \" + n.get(l)` patch the\n // existing text node instead of recreating it every change. Crossing the\n // plain/inline-HTML boundary (or a non-text node) rebuilds the node.\n setText(textContent: string | number): void {\n const next =\n textContent === \"\" ? String.fromCharCode(0x200b) : String(textContent);\n if (next === this.text && this.domText) return;\n const wasHTML = isHTML(this.text);\n this.text = next;\n if (!this.domText) return;\n if (!wasHTML && !isHTML(next) && this.domText.nodeType === 3) {\n this.domText.nodeValue = next;\n return;\n }\n const old = this.domText;\n const fresh = this._createDOMNode();\n old.parentNode?.replaceChild(fresh, old);\n }\n\n _dispose(): void {\n this.domText = undefined;\n this.text = \"\";\n }\n\n generateHTML(): string {\n if (this.text === \"\\u200B\") return \"​\";\n // Mirror _createDOMNode: a single-root HTML string is intentional inline\n // HTML, anything else is plain text and must be escaped so the server\n // output is XSS-safe and parses back to the same text node the client\n // builds (otherwise hydration child alignment drifts).\n return isHTML(this.text)\n ? sanitizeHTMLString(this.text)\n : escapeHTML(this.text);\n }\n\n render(domText: ChildNode | DocumentFragment | HTMLElement): void {\n const newNode = this._createDOMNode();\n domText.appendChild(newNode);\n }\n}\n","import { __DEV__ } from \"../dev.js\";\nimport { ensureDomStyle, getTagName } from \"../helpers.js\";\nimport type { DomphyElement } from \"../types.js\";\nimport { ElementNode } from \"./ElementNode.js\";\nimport { TextNode } from \"./TextNode.js\";\n\ntype ElementInput = DomphyElement | null | undefined | number | string;\ntype NodeItem = ElementNode | TextNode;\n\n// DEV-only: call-sites that have already emitted the missing-`_key` reactive-list\n// warning, so it fires at most once per site instead of every reactive frame.\n// Keyed by the owner node's stable nodeId (same call-site → same id).\nconst _warnedKeylessSites = new Set<string>();\n\n// Test-only: clear the once-per-site throttle so each test starts clean.\nexport function _resetKeylessWarnings(): void {\n _warnedKeylessSites.clear();\n}\n\nexport class ElementList {\n items: NodeItem[] = [];\n owner: ElementNode;\n _nextKey: number = 0;\n\n constructor(parent: ElementNode) {\n this.owner = parent;\n }\n\n _createNode(element: ElementInput | DomphyElement): NodeItem {\n return typeof element === \"object\" && element !== null\n ? new ElementNode(element, this.owner, this._nextKey++)\n : new TextNode(element == null ? \"\" : String(element), this.owner);\n }\n\n // Resolve the first item at or after `index` whose DOM node is an ACTUAL\n // child of the owner's DOM element, for use as an insertBefore reference.\n // The logical `items` array and the real DOM child list diverge: a portal\n // item occupies a logical slot while its DOM lives wherever _portal() routed\n // it, so a positional `childNodes[i]` (or a blind `items[i].domElement`)\n // reference either points outside the owner (insertBefore throws\n // NotFoundError) or drifts by the number of preceding portals (silently\n // misplacing the node). Returns null when no such item exists (append).\n _domReferenceAfter(index: number): Node | null {\n const dom = this.owner.domElement;\n if (!dom) return null;\n for (let i = index; i < this.items.length; i++) {\n const item = this.items[i];\n const el = item instanceof ElementNode ? item.domElement : item.domText;\n if (el && el.parentNode === dom) return el;\n }\n return null;\n }\n\n _moveDomElement(node: NodeItem, index: number) {\n if (!this.owner || !this.owner.domElement) return;\n const dom = this.owner.domElement;\n\n const el = node instanceof ElementNode ? node.domElement : node.domText;\n if (!el) return;\n // `el` still occupies its old DOM slot when this runs, so a positional\n // `childNodes[index]` reference is off by one for a forward move. Reference\n // the node that should FOLLOW `el` in the new logical order by identity\n // instead — direction-agnostic and correct for forward and backward moves\n // (and for a move to the last slot, where there is no following node).\n const ref = this._domReferenceAfter(index + 1);\n if (el !== ref) dom.insertBefore(el, ref);\n }\n\n _swapDomElement(aNode: NodeItem, bNode: NodeItem) {\n if (!this.owner || !this.owner.domElement) return;\n const parent = this.owner.domElement;\n\n const a = aNode instanceof ElementNode ? aNode.domElement : aNode.domText;\n const b = bNode instanceof ElementNode ? bNode.domElement : bNode.domText;\n if (!a || !b) return;\n\n const aNext = a.nextSibling;\n const bNext = b.nextSibling;\n\n parent.insertBefore(a, bNext);\n parent.insertBefore(b, aNext);\n }\n\n update(inputs: ElementInput[], updateDom = true, silent = false): void {\n // Imperatively-inserted nodes (a direct children.insert() by app/patch\n // code — e.g. a floating panel portaled under the root, or selectBox's\n // inner tag list) are NOT part of the declared `inputs` and must survive\n // reconciliation: from this method's point of view they'd otherwise be\n // indistinguishable from stale leftovers and get pruned by the extras\n // cleanup below on the very next unrelated re-render. Park them at the\n // logical tail so positional reuse and the extras slice only ever see\n // declared nodes (their real DOM position is untouched — logical order is\n // an internal bookkeeping detail for them).\n if (this.items.some((item) => item._imperative)) {\n const declared = this.items.filter((item) => !item._imperative);\n const imperative = this.items.filter((item) => item._imperative);\n this.items = declared.concat(imperative);\n }\n\n const oldItems = this.items.slice(); // snapshot for cleanup\n\n // Keyed lookup from old list. Skip imperative nodes (never reconciled) and\n // nodes whose async removal is still in flight (_beforeRemoveFired — an\n // exit animation awaiting done()): \"resurrecting\" a mid-removal node by\n // key would let the original deferred done() later rip the reused node out\n // of the live list and dispose it. A re-added key gets a FRESH node while\n // the old one finishes exiting.\n const keyed = new Map<string | number, NodeItem>();\n for (const item of oldItems) {\n if (\n item instanceof ElementNode &&\n item.key !== null &&\n item.key !== undefined &&\n !item._imperative &&\n !item._beforeRemoveFired\n ) {\n keyed.set(item.key, item);\n }\n }\n\n if (!silent && this.owner.domElement)\n this.owner._hooks?.BeforeUpdate?.(this.owner, inputs);\n\n const oldSet = new Set<NodeItem>(oldItems);\n const claimed = new Set<NodeItem>();\n\n // DEV-only footgun detection (warn-only — does NOT change reconciliation).\n // An unkeyed list that grows or shrinks may pair the wrong node with the\n // wrong data slot (DOM ordering issue). A fixed-length unkeyed list is safe.\n let unkeyedObjectInputs = 0;\n const lengthChanged =\n __DEV__ && oldItems.length > 0\n ? inputs.length !== oldItems.length\n : false;\n\n // build target order using existing ops (mutating this.items)\n for (let i = 0; i < inputs.length; i++) {\n const input = inputs[i];\n const isObj = typeof input === \"object\" && input !== null;\n const key = isObj ? (input as any)._key : undefined;\n const tag = isObj ? getTagName(input as DomphyElement) : undefined;\n if (__DEV__ && isObj && key === undefined) unkeyedObjectInputs++;\n\n // Keyed reuse: same key + same tag → reuse the node and patch it in place\n // (preserves DOM identity/state while reflecting new data).\n if (key !== undefined) {\n const reused = keyed.get(key);\n if (reused instanceof ElementNode && reused.tagName === tag) {\n keyed.delete(key);\n const cur = this.items.indexOf(reused);\n if (cur !== i && cur >= 0) {\n const isPortal = !!reused._portal;\n this.move(cur, i, isPortal ? false : updateDom, true);\n }\n reused.parent = this.owner as any;\n reused.patch(input as DomphyElement);\n claimed.add(reused);\n continue;\n }\n // key present but no tag-compatible match → fall through to insert; any\n // stale keyed node keeps its slot in `keyed` and is removed below.\n } else if (isObj) {\n // Unkeyed positional reuse: reuse the old unkeyed element already sitting\n // at this slot if its tag matches — this is what preserves focus, scroll,\n // selection, IME and uncontrolled input values across plain list updates.\n const at = this.items[i];\n if (\n at instanceof ElementNode &&\n at.key == null &&\n at.tagName === tag &&\n oldSet.has(at) &&\n !claimed.has(at) &&\n !at._imperative &&\n !at._beforeRemoveFired\n ) {\n at.parent = this.owner as any;\n at.patch(input as DomphyElement);\n claimed.add(at);\n continue;\n }\n } else {\n // Text positional reuse: a string/number at this slot whose old node is a\n // TextNode is patched in place (mutate nodeValue) instead of recreating\n // the DOM text node — this keeps reactive text like `(l) => \"n:\" +\n // s.get(l)` cheap and stable across updates.\n const at = this.items[i];\n if (\n at instanceof TextNode &&\n oldSet.has(at) &&\n !claimed.has(at) &&\n !at._imperative\n ) {\n at.setText(input == null ? \"\" : (input as string | number));\n claimed.add(at);\n continue;\n }\n }\n\n claimed.add(this.insert(input, i, updateDom, true, true));\n }\n\n // Remove leftover nodes beyond the new length. Iterate a SNAPSHOT (not a\n // `while length > inputs.length` loop): a removal may defer (async exit\n // animation), leaving the node in `items`, so a length-based loop would spin.\n // Imperative nodes (parked at the tail above) are exempt — they are managed\n // by whoever inserted them, not by this declared-inputs reconciliation.\n const extras = this.items.slice(inputs.length);\n for (const node of extras) {\n if (!node._imperative) this.remove(node, updateDom, true);\n }\n keyed.forEach((node) => this.remove(node, updateDom, true));\n\n // Warn (once per call-site) when an unkeyed list changes length — positional\n // reuse may pair the wrong DOM node with the wrong data slot (focus, scroll,\n // input value drift). A fixed-length unkeyed list never trips this.\n // Skips the first render (gated on oldItems.length > 0) and keyed lists.\n if (\n __DEV__ &&\n oldItems.length > 0 &&\n unkeyedObjectInputs > 0 &&\n lengthChanged\n ) {\n const siteId = this.owner.nodeId;\n if (!_warnedKeylessSites.has(siteId)) {\n _warnedKeylessSites.add(siteId);\n const msg = `[domphy] unkeyed list length changed — DOM nodes reused by position may not match their data slot (focus/scroll/input-value drift). Add _key to each item. (parent <${this.owner.tagName}>, ${unkeyedObjectInputs} unkeyed item${unkeyedObjectInputs === 1 ? \"\" : \"s\"})`;\n console.warn(msg);\n }\n }\n\n if (!silent) this.owner._hooks?.Update?.(this.owner);\n }\n\n insert(\n input: ElementInput,\n index?: number,\n updateDom = true,\n silent = false,\n declared = false,\n ): NodeItem {\n const length = this.items.length;\n const finalIndex =\n typeof index !== \"number\" ||\n Number.isNaN(index) ||\n index < 0 ||\n index > length\n ? length\n : index;\n const item = this._createNode(input);\n // A node inserted by anything other than update()'s declared-inputs\n // reconciliation (`declared` is only ever passed by update) is imperative:\n // reconciliation must neither positionally reuse it nor prune it as a\n // stale extra — see update().\n item._imperative = !declared;\n this.items.splice(finalIndex, 0, item);\n\n if (item instanceof ElementNode) {\n //Parent always insert/mount before children\n item._hooks.Insert && item._hooks.Insert(item);\n\n const domElement = this.owner.domElement;\n if (updateDom && domElement) {\n if (item._portal) {\n const domElement = item._portal!(this.owner.getRoot());\n domElement && item.render(domElement);\n } else {\n const domNode = item._createDOMNode();\n // Reference by logical successor, not childNodes[finalIndex] — a\n // portal item earlier in `items` has no DOM slot here, so a raw\n // positional index drifts and silently misplaces the new node.\n const ref = this._domReferenceAfter(finalIndex + 1);\n domElement.insertBefore(domNode, ref);\n const root = domElement.getRootNode();\n const styleParent = root instanceof ShadowRoot ? root : document.head;\n const domStyle = ensureDomStyle(styleParent);\n item.styles.render(domStyle as HTMLStyleElement);\n item._hooks.Mount && item._hooks.Mount(item);\n item.children.items.forEach((child) => {\n if (child instanceof ElementNode && child._portal) {\n const dom = child._portal!(child.getRoot());\n dom && child.render(dom);\n } else {\n child.render(domNode);\n }\n });\n }\n }\n } else {\n const domElement = this.owner.domElement;\n if (updateDom && domElement) {\n const domNode = item._createDOMNode();\n const ref = this._domReferenceAfter(finalIndex + 1);\n domElement.insertBefore(domNode, ref);\n }\n }\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n return item;\n }\n\n remove(item: NodeItem, updateDom = true, silent = false): void {\n const index = this.items.indexOf(item);\n if (index < 0) return;\n\n if (item instanceof ElementNode) {\n // Guard against re-entrant removal of a node whose (deferred) removal is\n // already in flight — otherwise update()'s extras + keyed passes could\n // fire its BeforeRemove/animation twice. Synchronous removals are already\n // guarded by the indexOf check above (the node is spliced before re-entry).\n if (item._beforeRemoveFired) return;\n const done = () => {\n const el = item.domElement;\n // Re-resolve position at completion time — a deferred (animated) removal\n // may run after other inserts/removes have shifted indices.\n const i = this.items.indexOf(item);\n if (i >= 0) this.items.splice(i, 1);\n updateDom && el && el.remove();\n item._dispose(); // _dispose fires Remove + releases subscriptions for the whole subtree\n };\n if (item._hooks.BeforeRemove && item.domElement) {\n let doneCalled = false;\n const onceDone = () => {\n if (!doneCalled) {\n doneCalled = true;\n done();\n }\n };\n // Capture the hook reference (and thus its arity) before calling it — a\n // synchronous 2-arg hook (e.g. `motion()` with no `exit` frame) may call\n // `onceDone()` inline, which runs `done()` -> `item._dispose()` -> clears\n // `item._hooks` to `{}` before this line would otherwise re-read it.\n const beforeRemoveHook = item._hooks.BeforeRemove;\n item._beforeRemoveFired = true; // prevent _dispose from re-firing BeforeRemove\n beforeRemoveHook(item, onceDone);\n // Auto-complete only for sync cleanup hooks. A hook that declares `done`\n // (arity >= 2, e.g. an exit animation) owns completion and defers removal.\n if ((beforeRemoveHook as Function).length < 2 && !doneCalled)\n onceDone();\n else if (__DEV__ && !doneCalled) {\n setTimeout(() => {\n if (!doneCalled)\n console.warn(\n \"[Domphy] _onBeforeRemove declared a `done` parameter (e.g. an exit animation) but did not call it within 5s — the element will stay in the DOM. Call done() when cleanup finishes.\",\n );\n }, 5000);\n }\n } else {\n done();\n }\n } else {\n const el = item.domText;\n this.items.splice(index, 1);\n updateDom && el && el.remove();\n item._dispose();\n }\n\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n clear(updateDom = true, silent = false): void {\n if (this.items.length === 0) return;\n const snapshot = this.items.slice();\n\n for (const item of snapshot) {\n this.remove(item, updateDom, true);\n }\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n _dispose(): void {\n this.items.forEach((child) => child._dispose());\n this.items = [];\n }\n\n swap(aIndex: number, bIndex: number, updateDom = true, silent = false) {\n if (\n aIndex < 0 ||\n bIndex < 0 ||\n aIndex >= this.items.length ||\n bIndex >= this.items.length ||\n aIndex === bIndex\n )\n return;\n\n const itemA = this.items[aIndex];\n const itemB = this.items[bIndex];\n\n this.items[aIndex] = itemB;\n this.items[bIndex] = itemA;\n\n if (updateDom) this._swapDomElement(itemA, itemB);\n\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n move(\n fromIndex: number,\n toIndex: number,\n updateDom = true,\n silent = false,\n ): void {\n if (\n fromIndex < 0 ||\n fromIndex >= this.items.length ||\n toIndex < 0 ||\n toIndex >= this.items.length ||\n fromIndex === toIndex\n )\n return;\n\n const item = this.items[fromIndex];\n\n this.items.splice(fromIndex, 1);\n this.items.splice(toIndex, 0, item);\n\n if (updateDom) this._moveDomElement(item, toIndex);\n\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n generateHTML(): string {\n let html = \"\";\n for (const item of this.items) html += item.generateHTML();\n return html;\n }\n}\n","import {\n activeCollector,\n Collector,\n runUntracked,\n runWithCollector,\n} from \"./Collector.js\";\nimport { __DEV__ } from \"../dev.js\";\nimport {\n _microtask,\n flushPendingNotifiers,\n hasPendingNotifiers,\n Notifier,\n runBatched,\n} from \"./Notifier.js\";\nimport type { ReadableState, ValueListener } from \"./State.js\";\n\n// Derived-reactivity layer built ON TOP of State/RecordState + Notifier. Nothing\n// here forks a parallel reactivity system: every dependency is tracked by\n// subscribing a Collector's handler through the same Notifier.addListener path a\n// plain `state.get(listener)` uses, and every downstream notification goes\n// through Notifier.notify (so `_chain` cycle detection still applies).\n\n// ----------------------------------------------------------------------------\n// Reaction scheduler\n// ----------------------------------------------------------------------------\n//\n// An effect/computed subscribes its Collector handler to EACH of its\n// dependencies' Notifiers. When several dependencies change in one tick (or in\n// one `batch`), each dependency Notifier flushes in its own microtask and would\n// invoke the handler once per dependency. To re-run a reaction at most ONCE per\n// burst, the handler does not run its work inline; it enqueues a deduplicated\n// job. A single microtask drains the queue, and jobs enqueued while draining\n// (e.g. a downstream computed reacting) are processed in the same drain — so a\n// `batch` of writes collapses into a single downstream flush.\n\n// Reuses the shared `_microtask` scheduler from Notifier (same `queueMicrotask`\n// fallback for older embedded Chromium runtimes that predate it).\n\nconst REACTION_QUEUE: Set<() => void> = new Set();\nlet reactionDrainScheduled = false;\n\nfunction scheduleReaction(job: () => void): void {\n REACTION_QUEUE.add(job);\n if (reactionDrainScheduled) return;\n reactionDrainScheduled = true;\n _microtask(drainReactions);\n}\n\nfunction drainReactions(): void {\n reactionDrainScheduled = false;\n // Drain in passes: a job may enqueue more jobs (a computed re-running pushes to\n // its downstream computeds). Process until the queue settles.\n while (REACTION_QUEUE.size > 0) {\n const jobs = [...REACTION_QUEUE];\n REACTION_QUEUE.clear();\n for (const job of jobs) {\n try {\n job();\n } catch (e) {\n console.error(\"[Domphy] Uncaught error in effect:\", e);\n }\n }\n }\n}\n\n// Synchronously flush all pending reactivity: state-change notifications (DOM\n// attribute/style bindings and computed/effect dependency signals) AND the\n// deduplicated effect/computed reaction queue. Alternates between the two\n// because a notifier flush can queue reactions and a reaction can write state\n// (which queues more notifier flushes); it loops until both settle. Useful in\n// tests and imperative code that must observe the DOM right after `.set()`\n// instead of waiting for the next microtask. Inside `batch()` it does not touch\n// the batched writes — those still flush when the batch ends.\nexport function flushSync(): void {\n let guard = 0;\n while (hasPendingNotifiers() || REACTION_QUEUE.size > 0) {\n if (guard++ > 10000) {\n console.error(\"[Domphy] flushSync did not settle\");\n break;\n }\n flushPendingNotifiers();\n drainReactions();\n }\n}\n\n// ----------------------------------------------------------------------------\n// Scopes\n// ----------------------------------------------------------------------------\n\n// Disposer registered to a scope. A computed/effect/listener created inside a\n// scope's `run` adds its teardown here so `stop()` can release the whole graph\n// of a removed subtree in one call.\ntype Disposer = () => void;\n\n// Stack of active scopes. Nested scopes register into the innermost one, and a\n// child scope is itself registered into its parent so stopping the parent stops\n// the child too.\nconst SCOPE_STACK: EffectScope[] = [];\n\nfunction activeScope(): EffectScope | null {\n return SCOPE_STACK.length ? SCOPE_STACK[SCOPE_STACK.length - 1] : null;\n}\n\nfunction registerDisposer(dispose: Disposer): void {\n const scope = activeScope();\n if (scope) scope._add(dispose);\n}\n\nexport interface EffectScopeHandle {\n // Run `fn` with this scope active; anything reactive created inside is owned\n // by the scope. Returns whatever `fn` returns.\n run<T>(fn: () => T): T;\n // Dispose everything created inside this scope (and inside nested scopes).\n stop(): void;\n}\n\nclass EffectScope implements EffectScopeHandle {\n private _disposers: Set<Disposer> = new Set();\n private _stopped = false;\n\n // Register a teardown owned by this scope. Called by effect/computed/listener\n // creation and by nested-scope creation.\n _add(dispose: Disposer): void {\n if (this._stopped) {\n // The scope is already stopped; tear the new resource down immediately so\n // a late creation cannot leak.\n dispose();\n return;\n }\n this._disposers.add(dispose);\n }\n\n run<T>(fn: () => T): T {\n if (this._stopped) {\n // The scope is already stopped: pushing it back onto SCOPE_STACK would\n // make every effect/computed created inside `fn` register into `_add`,\n // which disposes late resources immediately (see above) BEFORE their\n // first run — a permanently inert effect that never executes even once,\n // with no error or warning. Instead, run `fn` without pushing this scope\n // so any reactive resource created inside registers to whatever scope is\n // currently enclosing (or the global/no scope), staying disposable.\n if (__DEV__) {\n console.warn(\n \"[Domphy] effectScope.run() called after stop() — resources created inside are registered to the enclosing scope instead of this stopped one.\",\n );\n }\n return fn();\n }\n SCOPE_STACK.push(this);\n try {\n return fn();\n } finally {\n SCOPE_STACK.pop();\n }\n }\n\n stop(): void {\n if (this._stopped) return;\n this._stopped = true;\n for (const dispose of this._disposers) dispose();\n this._disposers.clear();\n }\n}\n\n// Create an effect scope. Used so a removed subtree can dispose its reactive\n// graph in one `stop()` call. Nested scopes are owned by the enclosing scope.\nexport function effectScope(): EffectScopeHandle {\n const scope = new EffectScope();\n registerDisposer(() => scope.stop());\n return scope;\n}\n\n// ----------------------------------------------------------------------------\n// Effect\n// ----------------------------------------------------------------------------\n\n// Run `fn` immediately, auto-tracking every reactive read inside it, and re-run\n// it whenever any tracked dependency changes. Returns a `dispose()` that releases\n// all current subscriptions. Each run re-collects dependencies, so reads no\n// longer reached (e.g. behind a branch) are dropped.\nexport function effect(fn: () => void): () => void {\n let disposed = false;\n // `running` guards against an effect whose `fn` writes a state it also reads,\n // which would otherwise re-enter `run` mid-run.\n let running = false;\n\n // A dependency changed: schedule a single deduplicated re-run. The job is the\n // SAME function reference each time, so the reaction queue's Set collapses\n // notifications from multiple dependencies (and from a batch) into one re-run.\n const job = (): void => {\n if (disposed) return;\n run();\n };\n const collector = new Collector(() => {\n if (disposed) return;\n scheduleReaction(job);\n });\n\n const run = (): void => {\n if (disposed || running) return;\n running = true;\n // Drop the previous run's dependencies so only deps read on THIS run remain\n // subscribed (stale-dep collection).\n collector.reset();\n try {\n runWithCollector(collector, fn);\n } finally {\n running = false;\n }\n };\n\n const dispose = (): void => {\n if (disposed) return;\n disposed = true;\n collector.reset();\n REACTION_QUEUE.delete(job);\n };\n\n registerDisposer(dispose);\n run(); // initial run is synchronous + immediate\n return dispose;\n}\n\n// ----------------------------------------------------------------------------\n// Computed\n// ----------------------------------------------------------------------------\n\n// Read-only, State-like derived value. Subscribe to it exactly like a State:\n// `c.get()` for the current value, `c.get(listener)` to be notified on change,\n// and inside an element `(l) => c.get(l)` to bind the DOM.\nexport interface Computed<T> {\n readonly _isState: true;\n // The computed's own Notifier (downstream subscriptions live here). Exposed,\n // like State._notifier, so subscription/leak inspection works uniformly.\n readonly _notifier: Notifier;\n get(listener?: ValueListener<T>): T;\n}\n\n// Lazy + cached derived value. `fn` is evaluated on first read and the result is\n// cached; it re-evaluates ONLY after a tracked dependency changes (a dirty flag),\n// never on every read. When a dependency changes, the computed recomputes and, if\n// the new value differs by `===` from the cached one, notifies its own\n// downstream listeners; an identical value short-circuits (no downstream churn).\nexport function computed<T>(fn: () => T): Computed<T> {\n // The computed publishes its own changes through a private Notifier (the same\n // machinery State uses), so anything subscribing to the computed participates\n // in the normal flush + cycle detection.\n const EVENT = \"computed\";\n const notifier = new Notifier();\n\n let cachedValue: T = undefined as unknown as T;\n let dirty = true;\n let hasValue = false;\n\n // A dependency changed: schedule a single deduplicated reaction. Marking dirty\n // is immediate (so a synchronous read after the change recomputes); the\n // observed-path recompute+notify is deferred to the drain so multiple changing\n // dependencies (and a batch) collapse into one recompute.\n const job = (): void => {\n if (!dirty) return;\n // If nothing is observing this computed, stay lazy — the next read recomputes.\n // If there ARE downstream listeners, recompute now to apply the equality\n // short-circuit and push the new value through this computed's own Notifier.\n if (notifier.listenerCount(EVENT) > 0) recomputeAndNotify();\n };\n const collector = new Collector(() => {\n if (dirty) return;\n dirty = true;\n scheduleReaction(job);\n });\n\n const recompute = (): void => {\n collector.reset();\n cachedValue = runWithCollector(collector, fn);\n dirty = false;\n hasValue = true;\n };\n\n const recomputeAndNotify = (): void => {\n const previous = cachedValue;\n const had = hasValue;\n recompute();\n // Equality short-circuit: an unchanged value must not notify downstream.\n if (had && cachedValue === previous) return;\n notifier.notify(EVENT, cachedValue);\n };\n\n const get = (listener?: ValueListener<T>): T => {\n if (listener) {\n notifier.addListener(EVENT, listener);\n } else {\n // Auto-tracking: reading a computed inside another computed/effect makes\n // the outer computation depend on this one. Reusing State's collector path\n // means a chain of computeds composes through one Notifier graph.\n const outer = activeCollector();\n if (outer) notifier.addListener(EVENT, outer.handler);\n }\n if (dirty) {\n // A dirty read while downstream listeners exist must notify them, not\n // just refresh the cache: a plain recompute() here flips `dirty` off, so\n // the queued job() becomes a no-op and already-subscribed listeners\n // (e.g. a DOM binding) would NEVER learn the value changed — any code\n // reading the computed between a dependency write and the reaction\n // drain (an untracked .get() in a state listener, or flushSync) would\n // permanently swallow the update. recomputeAndNotify keeps the equality\n // short-circuit, so an unchanged value still stays silent. The initial\n // lazy compute (hasValue === false) must NOT notify — subscribers\n // already receive the value as this call's return.\n if (hasValue && notifier.listenerCount(EVENT) > 0) recomputeAndNotify();\n else recompute();\n }\n return cachedValue;\n };\n\n const dispose = (): void => {\n collector.reset();\n REACTION_QUEUE.delete(job);\n notifier._dispose();\n };\n registerDisposer(dispose);\n\n return { _isState: true, _notifier: notifier, get } as Computed<T>;\n}\n\n// ----------------------------------------------------------------------------\n// batch / untrack\n// ----------------------------------------------------------------------------\n\n// Run `fn`, coalescing all State/RecordState/computed writes inside into a SINGLE\n// downstream flush after `fn` returns. Composes with the existing microtask flush\n// without double-flushing (see Notifier.runBatched). Returns `fn`'s result.\nexport function batch<T>(fn: () => T): T {\n return runBatched(fn);\n}\n\n// Run `fn` and return its result WITHOUT registering any reads into the currently\n// active collector. Useful to read a state inside an effect/computed without\n// making it a dependency.\nexport function untrack<T>(fn: () => T): T {\n return runUntracked(fn);\n}\n\n// ----------------------------------------------------------------------------\n// watch\n// ----------------------------------------------------------------------------\n\n// A reactive source for `watch`: a State/Computed (anything with `.get()`) or a\n// getter function. The latter composes multiple reads — `() => a.get() + b.get()`\n// — into a single watched expression.\nexport type WatchSource<T> = ReadableState<T> | (() => T);\n\nexport interface WatchOptions {\n // If true, invoke the callback immediately with the initial value (oldValue\n // will be `undefined` on that first call). Default: false.\n immediate?: boolean;\n}\n\n// Imperative watcher: tracks `source`, and whenever it produces a new value\n// (by `===` change) calls `callback(newValue, oldValue)`. The callback receives\n// both the new value and the previous one — which plain `effect` cannot provide.\n//\n// Returns a `dispose()` that stops watching and releases subscriptions.\n//\n// Examples:\n// const count = toState(0)\n// const stop = watch(count, (n, prev) => console.log(n, prev))\n// const stop2 = watch(() => a.get() + b.get(), (sum) => console.log(sum))\nexport function watch<T>(\n source: WatchSource<T>,\n callback: (newValue: T, oldValue: T | undefined) => void,\n options?: WatchOptions,\n): () => void {\n let oldValue: T | undefined = undefined;\n let firstRun = true;\n\n // `effect` runs synchronously on setup (initial collection), then re-runs\n // whenever a tracked dependency changes. We suppress the callback on the\n // first (setup) run unless `immediate` is set.\n return effect(() => {\n const newValue =\n typeof source === \"function\" ? source() : source.get();\n\n if (!firstRun || options?.immediate) {\n callback(newValue, oldValue);\n }\n\n oldValue = newValue;\n firstRun = false;\n });\n}\n\n// ----------------------------------------------------------------------------\n// nextTick\n// ----------------------------------------------------------------------------\n\n// Returns a Promise that resolves on the next microtask — after all currently\n// scheduled reactive effects/computed re-runs have been processed. Useful when\n// you need to read state or the DOM immediately AFTER a reactive update settles\n// without calling the synchronous (and potentially expensive) `flushSync()`.\n//\n// Optionally pass a callback to be invoked when the microtask fires:\n// await nextTick() // wait for reactive flush\n// nextTick(() => doSomething()) // callback style\nexport function nextTick(): Promise<void>;\nexport function nextTick(fn: () => void): Promise<void>;\nexport function nextTick(fn?: () => void): Promise<void> {\n // A resolved Promise's `.then` schedules a microtask via the same checkpoint\n // that `_microtask` uses internally, so it runs in the same microtask queue\n // position as scheduled effect re-runs — after them when called synchronously.\n return fn ? Promise.resolve().then(fn) : Promise.resolve();\n}\n","import { activeCollector } from \"./Collector.js\";\nimport { Notifier } from \"./Notifier.js\";\n\ntype Listener = (...args: any[]) => void;\n\nexport class RecordState<T extends Record<string, any> = Record<string, any>> {\n private _notifier = new Notifier();\n private _record: T;\n readonly initialRecord: T;\n\n constructor(record: T) {\n this.initialRecord = { ...record };\n this._record = { ...record };\n }\n\n get<K extends keyof T>(key: K, l?: Listener): T[K] {\n if (l) {\n this._notifier.addListener(key as string, l);\n } else {\n // Auto-tracking: with no explicit listener, subscribe the active\n // collector for THIS key so a running computed/effect re-runs only\n // when this specific key changes. With no collector active the read\n // is untracked — the original behavior is preserved exactly.\n const collector = activeCollector();\n if (collector)\n this._notifier.addListener(key as string, collector.handler);\n }\n return this._record[key];\n }\n\n set<K extends keyof T>(key: K, value: T[K]): void {\n this._record[key] = value;\n this._notifier.notify(key as string, value);\n }\n\n addListener<K extends keyof T>(key: K, fn: Listener): () => void {\n return this._notifier.addListener(key as string, fn);\n }\n\n removeListener<K extends keyof T>(key: K, fn: Listener): void {\n this._notifier.removeListener(key as string, fn);\n }\n\n reset<K extends keyof T>(key: K): void {\n this.set(key, this.initialRecord[key]);\n }\n\n _dispose(): void {\n this._notifier._dispose();\n }\n}\n","import type { ThemeInput } from \"./types.js\";\n\nconst light: ThemeInput = {\n direction: \"darken\",\n colors: {\n primary: [\n \"#ffffff\",\n \"#e3ecff\",\n \"#c6daff\",\n \"#aac8ff\",\n \"#8fb6ff\",\n \"#76a3ff\",\n \"#5f91fc\",\n \"#4a7ff4\",\n \"#386ee7\",\n \"#2a5ed7\",\n \"#1e4ec2\",\n \"#1440aa\",\n \"#0c3290\",\n \"#072674\",\n \"#041a57\",\n \"#020f38\",\n \"#010419\",\n \"#000000\",\n ],\n secondary: [\n \"#ffffff\",\n \"#fce6ea\",\n \"#faced6\",\n \"#f7b5c2\",\n \"#f29db0\",\n \"#ec859e\",\n \"#e36e8d\",\n \"#d8597d\",\n \"#ca456e\",\n \"#b93460\",\n \"#a42351\",\n \"#8e1643\",\n \"#770b36\",\n \"#5f0529\",\n \"#46031d\",\n \"#2d0210\",\n \"#130104\",\n \"#000000\",\n ],\n info: [\n \"#ffffff\",\n \"#dcf0f9\",\n \"#b7e1f6\",\n \"#90d2f1\",\n \"#6ac3eb\",\n \"#42b4e2\",\n \"#16a4d5\",\n \"#0094c4\",\n \"#0084b2\",\n \"#00739e\",\n \"#00638a\",\n \"#005476\",\n \"#004461\",\n \"#00354d\",\n \"#002638\",\n \"#001623\",\n \"#00070d\",\n \"#000000\",\n ],\n success: [\n \"#ffffff\",\n \"#e3f3dc\",\n \"#c6e8b8\",\n \"#a9dd94\",\n \"#8ed171\",\n \"#75c450\",\n \"#61b635\",\n \"#51a51f\",\n \"#429304\",\n \"#358100\",\n \"#2a7000\",\n \"#215f00\",\n \"#194d00\",\n \"#123c00\",\n \"#0b2b00\",\n \"#051a00\",\n \"#010900\",\n \"#000000\",\n ],\n warning: [\n \"#ffffff\",\n \"#ffeada\",\n \"#ffd3b3\",\n \"#ffbd8d\",\n \"#ffa96b\",\n \"#ff9853\",\n \"#ec8640\",\n \"#d77531\",\n \"#c16523\",\n \"#aa5718\",\n \"#944a0f\",\n \"#7e3d09\",\n \"#673106\",\n \"#512504\",\n \"#3b1a03\",\n \"#250e02\",\n \"#0e0401\",\n \"#000000\",\n ],\n attention: [\n \"#ffffff\",\n \"#ffeada\",\n \"#ffd3b3\",\n \"#ffbd8d\",\n \"#ffa96b\",\n \"#ff9853\",\n \"#ec8640\",\n \"#d77531\",\n \"#c16523\",\n \"#aa5718\",\n \"#944a0f\",\n \"#7e3d09\",\n \"#673106\",\n \"#512504\",\n \"#3b1a03\",\n \"#250e02\",\n \"#0e0401\",\n \"#000000\",\n ],\n error: [\n \"#ffffff\",\n \"#fce7e4\",\n \"#fbcfca\",\n \"#f8b7b0\",\n \"#f59f96\",\n \"#ef877e\",\n \"#e86f67\",\n \"#de5852\",\n \"#d3403e\",\n \"#c5282c\",\n \"#b30a1b\",\n \"#9e000b\",\n \"#860001\",\n \"#6c0000\",\n \"#510000\",\n \"#340000\",\n \"#170000\",\n \"#000000\",\n ],\n danger: [\n \"#ffffff\",\n \"#fce7e4\",\n \"#fbcfca\",\n \"#f8b7b0\",\n \"#f59f96\",\n \"#ef877e\",\n \"#e86f67\",\n \"#de5852\",\n \"#d3403e\",\n \"#c5282c\",\n \"#b30a1b\",\n \"#9e000b\",\n \"#860001\",\n \"#6c0000\",\n \"#510000\",\n \"#340000\",\n \"#170000\",\n \"#000000\",\n ],\n highlight: [\n \"#ffffff\",\n \"#f9f5cd\",\n \"#f4eb95\",\n \"#efe05a\",\n \"#e6d427\",\n \"#d3c100\",\n \"#bfad00\",\n \"#ab9b00\",\n \"#988900\",\n \"#857700\",\n \"#736600\",\n \"#615600\",\n \"#4f4600\",\n \"#3e3600\",\n \"#2c2700\",\n \"#1b1700\",\n \"#090700\",\n \"#000000\",\n ],\n neutral: [\n \"#ffffff\",\n \"#ededed\",\n \"#dbdbdb\",\n \"#cacaca\",\n \"#bababa\",\n \"#ababab\",\n \"#9b9b9b\",\n \"#8d8d8d\",\n \"#7e7e7e\",\n \"#707070\",\n \"#636363\",\n \"#565656\",\n \"#484848\",\n \"#383838\",\n \"#282828\",\n \"#181818\",\n \"#080808\",\n \"#000000\",\n ],\n },\n baseTones: {\n highlight: 5,\n warning: 6,\n attention: 6,\n error: 8,\n danger: 8,\n secondary: 8,\n primary: 9,\n info: 8,\n success: 8,\n neutral: 8,\n },\n fontSizes: [\n \"0.75rem\",\n \"0.875rem\",\n \"1rem\",\n \"1.25rem\",\n \"1.5625rem\",\n \"1.9375rem\",\n \"2.4375rem\",\n \"3.0625rem\",\n ],\n densities: [0.75, 1, 1.5, 2, 2.5],\n darkBias: 1,\n custom: {},\n};\n\nexport default light;\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport light from \"./light.js\";\nimport type { PartialThemeInput, ThemeInput, ThemeVars } from \"./types.js\";\n\n// JSON clone (not structuredClone) so the build runs in older embedded\n// browsers like SketchUp 2022's CEF, which predates Chromium 98.\n// ThemeInput is plain JSON (no Map/Set/Date/typed arrays).\nconst clone = <T>(v: T): T => JSON.parse(JSON.stringify(v));\n\n// Custom-token keys may contain CSS-illegal characters (e.g. \"radius/sm/lg\").\n// Map every illegal char to \"_\" so the declared property name and the var()\n// reference always agree and stay valid CSS.\nconst escapeKey = (k: string): string => k.replace(/[^a-zA-Z0-9_-]/g, \"_\");\n\nconst themes: Record<string, ThemeInput> = {\n light: clone(light),\n dark: createDark(light),\n};\n\n// Memo caches. themeVars() depends only on the theme STRUCTURE (color names,\n// tone steps, custom keys) — it emits `var(--…)` references, never resolved\n// values — so its result is stable until setTheme() changes that structure.\n// themeTokens() returns resolved values per theme, cached per name. Both are\n// invalidated in setTheme(). Callers must treat the returned objects as\n// read-only (they are shared).\nlet _themeVarsCache: ThemeVars | null = null;\nconst _themeTokensCache = new Map<string, Record<string, any>>();\n\nfunction colorSteps(input: ThemeInput): number {\n const firstColor = Object.keys(input.colors)[0];\n return firstColor ? input.colors[firstColor].length : 0;\n}\n\n// --- Validation ---\n\nfunction validateTheme(partial: PartialThemeInput): void {\n for (const key in partial) {\n if (!Object.keys(light).includes(key as keyof ThemeInput)) {\n throw new Error(`Invalid key: ${key}`);\n }\n }\n if (partial.fontSizes && !Array.isArray(partial.fontSizes)) {\n throw new Error(`fontSize must be array of string`);\n }\n if (partial.densities) {\n if (\n !Array.isArray(partial.densities) ||\n partial.densities.some((v) => typeof v !== \"number\")\n ) {\n throw new Error(`densities must be array of number`);\n }\n }\n if (\"custom\" in partial) {\n const custom = partial.custom!;\n if (typeof custom !== \"object\" || custom === null) {\n throw new Error(`Invalid custom property: must be an object`);\n }\n }\n if (\"colors\" in partial) {\n const colors = partial.colors!;\n const valid =\n typeof colors === \"object\" &&\n colors !== null &&\n Object.values(colors).every(\n (v) => Array.isArray(v) && v.every((c) => typeof c === \"string\"),\n );\n if (!valid) {\n throw new Error(`colors must be an object of string[]`);\n }\n }\n if (\"baseTones\" in partial) {\n const baseTones = partial.baseTones!;\n const valid =\n typeof baseTones === \"object\" &&\n baseTones !== null &&\n Object.values(baseTones).every((v) => typeof v === \"number\");\n if (!valid) {\n throw new Error(`baseTones must be an object of number`);\n }\n }\n if (\"direction\" in partial) {\n if (partial.direction !== \"lighten\" && partial.direction !== \"darken\") {\n throw new Error(`direction must be \"lighten\" or \"darken\"`);\n }\n }\n}\n\n// --- Deep Merge ---\n\nfunction deepMerge(target: any, source: any): void {\n // Guard against prototype pollution: a JSON.parse'd payload (e.g. a custom\n // theme loaded from an API response) can carry an own enumerable\n // \"__proto__\" key, which `for...in` picks up unlike object-literal syntax.\n // Must run at every recursion depth — the key can appear inside any\n // nested Record-typed field (custom, colors, baseTones), not just the top.\n for (const key of Object.keys(source)) {\n if (key === \"__proto__\" || key === \"constructor\" || key === \"prototype\") {\n continue;\n }\n if (\n source[key] &&\n typeof source[key] === \"object\" &&\n !Array.isArray(source[key])\n ) {\n target[key] ??= {};\n deepMerge(target[key], source[key]);\n } else {\n target[key] = source[key];\n }\n }\n}\n\n// --- Builders (pure functions) ---\n\nfunction buildThemeCSS(name: string, input: ThemeInput): string {\n const styles: Record<string, string | number> = {};\n const toneSteps = colorSteps(input);\n\n for (const key in input) {\n const value = input[key as keyof ThemeInput];\n\n if (key === \"colors\") {\n for (const colorName in input.colors) {\n [...Array(toneSteps).keys()].forEach(\n (i) => (styles[`--${colorName}-${i}`] = input.colors[colorName][i]),\n );\n }\n } else if (key === \"fontSizes\") {\n [...Array(8).keys()].forEach(\n (i) => (styles[`--fontSize-${i}`] = input.fontSizes[i]),\n );\n } else if (key === \"custom\") {\n if (value && typeof value === \"object\") {\n for (const k in value as Record<string, string>) {\n styles[`--custom-${escapeKey(k)}`] = (\n value as Record<string, string>\n )[k];\n }\n }\n }\n // densities / baseTones / direction / darkBias are not CSS custom properties\n }\n\n let text = \"\";\n for (const prop in styles) {\n text += ` ${prop}: ${styles[prop]};\\n`;\n }\n return `[data-theme=\"${name}\"] {\\n${text}}`;\n}\n\n// --- Public API ---\n\nexport function getTheme(name: string): ThemeInput {\n if (!themes[name]) throw Error(`Theme \"${name}\" not found`);\n return themes[name];\n}\n\nexport function setTheme(name: string, input: PartialThemeInput): void {\n validateTheme(input);\n if (!themes[name]) themes[name] = clone(light);\n deepMerge(themes[name], input);\n // Structure/values may have changed → drop memoized derivations.\n _themeVarsCache = null;\n _themeTokensCache.clear();\n}\n\nfunction createDark(source: ThemeInput): ThemeInput {\n const dark = clone(source);\n dark.direction = \"lighten\";\n for (const name in dark.colors) {\n dark.colors[name].reverse();\n dark.baseTones[name] = dark.colors[name].length - 1 - dark.baseTones[name];\n }\n return dark;\n}\n\nexport function themeTokens(name: string): Record<string, any> {\n const cached = _themeTokensCache.get(name);\n if (cached) return cached;\n const input = getTheme(name);\n const toneSteps = colorSteps(input);\n const tokens: Record<string, any> = {};\n\n for (const key in input) {\n const value = input[key as keyof ThemeInput];\n\n if (key === \"colors\") {\n for (const name in input.colors) {\n const colorTones = {} as Partial<Record<number, string>>;\n [...Array(toneSteps).keys()].forEach(\n (i) => (colorTones[i] = input.colors[name][i]),\n );\n tokens[name] = colorTones as Record<number, string>;\n }\n } else if (key === \"fontSizes\") {\n tokens.fontSizes = input.fontSizes;\n } else if (key === \"densities\") {\n tokens.densities = input.densities;\n } else if (key === \"custom\") {\n tokens.custom = {};\n if (value && typeof value === \"object\") {\n for (const k in value as Record<string, string>) {\n tokens.custom[k] = (value as Record<string, string>)[k];\n }\n }\n }\n // baseTones / direction / darkBias are metadata — reachable via getTheme(), not tokens\n }\n\n _themeTokensCache.set(name, tokens);\n return tokens;\n}\n\nexport function themeVars(): ThemeVars {\n if (_themeVarsCache) return _themeVarsCache;\n const input = getTheme(\"light\");\n const toneSteps = colorSteps(input);\n const theme = {} as ThemeVars;\n\n for (const key in input) {\n const value = input[key as keyof ThemeInput];\n\n if (key === \"colors\") {\n for (const name in input.colors) {\n const colorTones = {} as Partial<Record<number, string>>;\n [...Array(toneSteps).keys()].forEach(\n (i) => (colorTones[i] = `var(--${name}-${i})`),\n );\n theme[name] = colorTones as Record<number, string>;\n }\n } else if (key === \"fontSizes\") {\n theme.fontSizes = [...Array(8).keys()].map((i) => `var(--fontSize-${i})`);\n } else if (key === \"custom\") {\n theme.custom = {} as Record<string, string>;\n if (value && typeof value === \"object\") {\n for (const k in value as Record<string, string>) {\n theme.custom[k] = `var(--custom-${escapeKey(k)})`;\n }\n }\n }\n // densities / baseTones / direction / darkBias are not exposed as CSS vars\n }\n\n _themeVarsCache = theme;\n return theme;\n}\n\nexport function themeCSS(): string {\n return Object.entries(themes)\n .map(([name, input]) => buildThemeCSS(name, input))\n .join(\"\\n\");\n}\n\nexport function themeApply(el?: HTMLStyleElement): void {\n if (typeof document === \"undefined\") return;\n if (el) {\n el.textContent = themeCSS();\n return;\n } else {\n el =\n (document.getElementById(\"domphy-themes\") as HTMLStyleElement) ??\n Object.assign(document.createElement(\"style\"), { id: \"domphy-themes\" });\n el.textContent = themeCSS();\n document.head.appendChild(el);\n }\n}\n\nexport function themeSpacing(n: number) {\n return `calc(${n / 4}em)`;\n}\n\n// Fluid spacing using CSS clamp(). Returns a value that scales linearly\n// between themeSpacing(min) and themeSpacing(max) across a viewport width\n// range (default 320px → 1280px). Use for structural spacing that should\n// grow with the viewport — not for bounded-control padding (use density for that).\n//\n// Example: themeFluidSpacing(4, 16) → \"clamp(1em, 0.3125vw, 4em)\"\n// (1em at 320px viewport, 4em at 1280px, scales linearly between)\nexport function themeFluidSpacing(\n min: number,\n max: number,\n viewportMin = 320,\n viewportMax = 1280,\n): string {\n const minEm = min / 4;\n const maxEm = max / 4;\n const slope = ((maxEm - minEm) / (viewportMax - viewportMin)) * 100;\n const intercept = minEm - (slope * viewportMin) / 100;\n const interceptRounded = parseFloat(intercept.toFixed(4));\n const preferred =\n interceptRounded === 0\n ? `${slope.toFixed(4)}vw`\n : `${intercept.toFixed(4)}em + ${slope.toFixed(4)}vw`;\n return `clamp(${minEm}em, ${preferred}, ${maxEm}em)`;\n}\n\n// System theme detection helper. Reads window.matchMedia and/or a saved\n// localStorage preference, sets data-theme on targetEl (default: <html>),\n// then listens for OS-level changes. Returns a cleanup function.\n//\n// Usage:\n// const cleanup = applySystemTheme() // one-liner on client startup\n// const cleanup = applySystemTheme(document.documentElement, { storageKey: \"my-theme\" })\n//\n// When the user manually changes the theme, call:\n// localStorage.setItem(storageKey, \"dark\") // applySystemTheme will honour it on reload\n// element.setAttribute(\"data-theme\", \"dark\") // update DOM immediately\n//\n// For SSR: call only on the client (typeof window !== \"undefined\").\nexport function applySystemTheme(\n targetEl: Element = document.documentElement,\n options: {\n /** Persist the resolved theme in localStorage so it survives reloads. Default: true. */\n persist?: boolean;\n /** localStorage key. Default: \"dp-theme\". */\n storageKey?: string;\n } = {},\n): () => void {\n const { persist = true, storageKey = \"dp-theme\" } = options;\n\n const resolve = (): \"light\" | \"dark\" => {\n if (persist) {\n const saved = localStorage.getItem(storageKey);\n if (saved === \"light\" || saved === \"dark\") return saved;\n }\n return window.matchMedia(\"(prefers-color-scheme: dark)\").matches\n ? \"dark\"\n : \"light\";\n };\n\n targetEl.setAttribute(\"data-theme\", resolve());\n\n const mql = window.matchMedia(\"(prefers-color-scheme: dark)\");\n const handler = (event: MediaQueryListEvent) => {\n // Only follow the OS change when there is no user-saved preference.\n if (!persist || !localStorage.getItem(storageKey)) {\n targetEl.setAttribute(\"data-theme\", event.matches ? \"dark\" : \"light\");\n }\n };\n mql.addEventListener(\"change\", handler);\n\n return () => mql.removeEventListener(\"change\", handler);\n}\n\nexport function themeName(object: ElementNode | Listener) {\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataTheme\"))) {\n node = node.parent as ElementNode;\n }\n\n let themeName = \"light\";\n\n if (node && node.attributes && node.attributes.has(\"dataTheme\")) {\n themeName = node.attributes.get(\"dataTheme\");\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataTheme\", object);\n }\n return themeName;\n}\n\n// The 10 semantic roles every built-in theme (light/dark) ships — single source\n// of truth for both the runtime list (icons, docs demos, e.g. ThemeBuilder's\n// color-picker sidebar) and the ColorRole type below. `ThemeInput.colors` stays\n// a plain string-indexed record (custom themes may register their own role\n// names via setTheme/generateTheme), so this is deliberately NOT presented as\n// an exhaustive runtime constraint anywhere it's consumed.\nexport const COLOR_ROLES = [\n \"neutral\",\n \"primary\",\n \"secondary\",\n \"info\",\n \"success\",\n \"warning\",\n \"attention\",\n \"error\",\n \"danger\",\n \"highlight\",\n] as const;\n\nexport type ColorRole = (typeof COLOR_ROLES)[number];\n\n// `ColorRole | (string & {})` — NOT plain `string` and NOT a strict `ColorRole`\n// union. `ThemeInput.colors` being a generic Record (see above) means a strict\n// union would reject valid custom-role code. But every prior version of this\n// type (`keyof ThemeInput[\"colors\"]`, which TS widens to plain `string` for a\n// generic Record) gave editors/AI codegen ZERO signal about the 10 built-in\n// role names — a typo'd role (e.g. \"accent\", not a real role) type-checked fine\n// and only surfaced as an unhandled runtime throw from themeColor(). The\n// `string & {}` branch preserves full acceptance of arbitrary custom-role\n// strings while `ColorRole` still ranks first in autocomplete/hover — this is\n// the standard \"loose autocomplete\" pattern (TS does not support \"reject unknown\n// literals but allow an explicit escape hatch\" any more precisely than this).\nexport type ThemeColor = ColorRole | (string & {});\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport { getTheme, themeName } from \"./theme.js\";\n\nconst ElementDensities = [\"inherit\"];\n\n[...Array(5).keys()].forEach((i) => {\n ElementDensities.push(`decrease-${i}`);\n ElementDensities.push(`increase-${i}`);\n});\n\nexport type ElementDensity = (typeof ElementDensities)[number];\n\nfunction offsetDensity(\n origin: number,\n density: ElementDensity = \"inherit\",\n): number {\n if (!ElementDensities.includes(density!)) {\n throw Error(`density name \"${density}\" invalid`);\n }\n let resultDensity: number;\n if (density === \"inherit\") {\n resultDensity = origin as number;\n } else if (density?.startsWith(\"increase-\")) {\n const offset = parseInt(density.replace(\"increase-\", \"\"), 10);\n resultDensity = origin + offset;\n } else if (density?.startsWith(\"decrease-\")) {\n const offset = parseInt(density.replace(\"decrease-\", \"\"), 10);\n resultDensity = origin - offset;\n } else {\n resultDensity = origin;\n }\n return Math.max(0, Math.min(4, resultDensity));\n}\n\nfunction contextDensity(object: ElementNode | Listener | null): number {\n if (!object) return 2;\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataDensity\"))) {\n node = node.parent as ElementNode;\n }\n\n let density = 2;\n\n if (node && node.attributes && node.attributes.has(\"dataDensity\")) {\n density = offsetDensity(density, node.attributes.get(\"dataDensity\"));\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataDensity\", object);\n }\n return density;\n}\n\nexport function themeDensity(object: ElementNode | Listener | null): number {\n const index = contextDensity(object);\n return getTheme(object ? themeName(object) : \"light\").densities[index];\n}\n","import { calcDeltaE2000, generateRamp, hexToRgb, rgbToLab } from \"@domphy/palette\";\nimport type { PartialThemeInput, ThemeInput } from \"./types.js\";\n\nexport type GenerateThemeOptions = {\n /** Ramp length. Must match `@domphy/theme`'s tone scale (18 steps: shift-0..shift-17). */\n steps?: number;\n direction?: ThemeInput[\"direction\"];\n fontSizes?: string[];\n densities?: number[];\n darkBias?: number;\n custom?: Record<string, string | number>;\n};\n\nconst DEFAULT_FONT_SIZES = [\n \"0.75rem\",\n \"0.875rem\",\n \"1rem\",\n \"1.25rem\",\n \"1.5625rem\",\n \"1.9375rem\",\n \"2.4375rem\",\n \"3.0625rem\",\n];\nconst DEFAULT_DENSITIES = [0.75, 1, 1.5, 2, 2.5];\n\n// The step whose color is perceptually closest (CIEDE2000) to the caller's\n// original base color — the ramp's \"base tone\" is not always the mathematical\n// center, since the warp curve does not distribute steps symmetrically.\nfunction nearestStepIndex(ramp: string[], baseHex: string): number {\n const baseLab = rgbToLab(hexToRgb(baseHex));\n let best = 0;\n let bestDist = Infinity;\n for (let i = 0; i < ramp.length; i++) {\n const dist = calcDeltaE2000(baseLab, rgbToLab(hexToRgb(ramp[i])));\n if (dist < bestDist) {\n bestDist = dist;\n best = i;\n }\n }\n return best;\n}\n\n/**\n * Generate a complete `ThemeInput` from one base hex color per semantic role,\n * using `@domphy/palette`'s `generateRamp` (Oklab, WCAG-span-optimized) for\n * every color family. Each family's `baseTones` entry is the step nearest\n * (CIEDE2000) to the caller's original input, so `themeColor(l, \"base\", name)`\n * still resolves to (approximately) the exact brand color that was passed in.\n *\n * ```ts\n * const theme = generateTheme({\n * primary: \"#4a7ff4\",\n * secondary: \"#d8597d\",\n * neutral: \"#8d8d8d\",\n * })\n * ```\n *\n * Roles not passed are simply absent from the result — merge with an existing\n * `ThemeInput`/`PartialThemeInput` (e.g. spread over `light` from\n * `@domphy/theme`) to fill in the rest.\n */\nexport function generateTheme(\n baseColors: Record<string, string>,\n options: GenerateThemeOptions = {},\n): PartialThemeInput {\n const steps = options.steps ?? 18;\n const colors: Record<string, string[]> = {};\n const baseTones: Record<string, number> = {};\n\n for (const [name, hex] of Object.entries(baseColors)) {\n const ramp = generateRamp(hex, steps);\n colors[name] = ramp;\n baseTones[name] = nearestStepIndex(ramp, hex);\n }\n\n return {\n direction: options.direction ?? \"darken\",\n colors,\n baseTones,\n fontSizes: options.fontSizes ?? DEFAULT_FONT_SIZES,\n densities: options.densities ?? DEFAULT_DENSITIES,\n darkBias: options.darkBias ?? 1,\n custom: options.custom ?? {},\n };\n}\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport { themeVars } from \"./theme.js\";\n\nconst ElementSizes = [\"inherit\"];\n\n[...Array(8).keys()].forEach((i) => {\n ElementSizes.push(`decrease-${i}`);\n ElementSizes.push(`increase-${i}`);\n});\n\nexport type ElementSize = (typeof ElementSizes)[number];\n\nfunction offsetSize(origin: number, size: ElementSize = \"inherit\"): number {\n if (!ElementSizes.includes(size!)) {\n throw Error(`size name \"${size}\" invalid`);\n }\n let resultSize: number;\n if (size === \"inherit\") {\n resultSize = origin as number;\n } else if (size?.startsWith(\"increase-\")) {\n const offset = parseInt(size.replace(\"increase-\", \"\"), 10);\n resultSize = origin + offset;\n } else if (size?.startsWith(\"decrease-\")) {\n const offset = parseInt(size.replace(\"decrease-\", \"\"), 10);\n resultSize = origin - offset;\n } else {\n resultSize = origin;\n }\n return Math.max(0, Math.min(7, resultSize));\n}\n\nfunction contextSize(object: ElementNode | Listener | null): number {\n if (!object) return 2;\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataSize\"))) {\n node = node.parent as ElementNode;\n }\n\n let size = 2;\n\n if (node && node.attributes && node.attributes.has(\"dataSize\")) {\n size = offsetSize(size, node.attributes.get(\"dataSize\"));\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataSize\", object);\n }\n return size;\n}\n\nexport function themeSize(\n object: ElementNode | Listener,\n size: ElementSize = \"inherit\",\n): string {\n const index = offsetSize(contextSize(object), size);\n return themeVars().fontSizes[index];\n}\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport light from \"./light.js\";\nimport { getTheme, themeName, themeTokens, themeVars } from \"./theme.js\";\n\nconst TONE_STEPS = light.colors.neutral.length;\n\n// Semantic tone aliases, resolved through the shift-N machinery below so they\n// stay context-aware (dataTone) and correct in both light and dark themes.\n// Mapping derived from stock @domphy/ui patch usage (packages/ui/src/patches)\n// and cross-checked against consumer usage frequency:\n// surface -> shift-1 subtle raised background (e.g. inputFile drop zone)\n// hover -> shift-2 hover/active background (e.g. button, menu, list)\n// border -> shift-3 subtle hairline divider (e.g. card footer separator)\n// border-strong -> shift-4 control outline (e.g. button, input, card boundary)\n// muted -> shift-8 secondary/disabled text\n// text -> shift-9 default/primary text\nconst ToneAliases: Record<string, string> = {\n surface: \"shift-1\",\n hover: \"shift-2\",\n border: \"shift-3\",\n \"border-strong\": \"shift-4\",\n muted: \"shift-8\",\n text: \"shift-9\",\n};\n\n// Exported as a value (not just a type) so tooling — @domphy/doctor, the MCP\n// server, generated `tones.json` — can validate tone names without parsing TS.\nexport const ElementTones = [\"inherit\", \"base\", ...Object.keys(ToneAliases)];\n\n[...Array(TONE_STEPS).keys()].forEach((i) => {\n ElementTones.push(`decrease-${i}`);\n ElementTones.push(`increase-${i}`);\n ElementTones.push(`shift-${i}`);\n});\n\nexport type ElementTone = (typeof ElementTones)[number];\n\nfunction adjustTone(tone: number, level: number): number {\n if (tone < 0 || tone > TONE_STEPS - 1) return tone;\n let newIndex = tone + level;\n newIndex = Math.max(0, Math.min(TONE_STEPS - 1, newIndex));\n return newIndex;\n}\n\nfunction shiftTone(tone: number, level: number): number {\n if (tone < 0 || tone > TONE_STEPS - 1) return tone;\n const midpoint = Math.floor((TONE_STEPS - 1) / 2);\n let newIndex = tone <= midpoint ? tone + level : tone - level;\n // Clamp overshoot to the near boundary. (Negating an out-of-range index, as\n // a prior version did, flips it to the opposite extreme — e.g. shift past\n // the dark end would land on the lightest tone.)\n newIndex = Math.max(0, Math.min(TONE_STEPS - 1, newIndex));\n return newIndex;\n}\n\nfunction offsetTone(originTone: number, tone: ElementTone = \"inherit\"): number {\n if (typeof tone === \"number\") return tone;\n\n if (tone === \"inherit\") return originTone;\n\n if (!ElementTones.includes(tone!)) {\n throw Error(`tone name \"${tone}\" invalid`);\n }\n\n if (tone in ToneAliases) {\n tone = ToneAliases[tone];\n }\n\n if (tone.startsWith(\"increase-\")) {\n const offset = parseInt(tone.replace(\"increase-\", \"\"), 10);\n return adjustTone(originTone, offset);\n } else if (tone.startsWith(\"decrease-\")) {\n const offset = parseInt(tone.replace(\"decrease-\", \"\"), 10);\n return adjustTone(originTone, -offset);\n } else if (tone.startsWith(\"shift-\")) {\n const offset = parseInt(tone.replace(\"shift-\", \"\"), 10);\n return shiftTone(originTone, offset);\n } else {\n return originTone;\n }\n}\n\nfunction contextTone(object: ElementNode | Listener | null): number {\n if (!object) return 0;\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataTone\"))) {\n node = node.parent as ElementNode;\n }\n\n let tone = 0;\n\n if (node && node.attributes && node.attributes.has(\"dataTone\")) {\n tone = offsetTone(tone, node.attributes.get(\"dataTone\"));\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataTone\", object);\n }\n return tone;\n}\n\nfunction _themeTone(\n object: ElementNode | Listener,\n tone: ElementTone = \"inherit\",\n): number {\n return offsetTone(contextTone(object), tone);\n}\n\nfunction biasContext(context: number, direction: string, bias: number): number {\n if (bias <= 0) return context;\n if (direction === \"lighten\" && context === 0) return bias;\n if (direction === \"darken\" && context === TONE_STEPS - 1)\n return TONE_STEPS - 1 - bias;\n return context;\n}\n\nexport function themeColor(\n object: ElementNode | Listener | null,\n tone: ElementTone = \"inherit\",\n color: string = \"inherit\",\n): string {\n const themeColor = color === \"inherit\" ? \"neutral\" : color;\n\n if (!object) {\n // No node context implies the light theme (themeVars reads getTheme(\"light\")).\n const colors = themeVars()[themeColor];\n if (!colors) {\n throw Error(`color \"${themeColor}\" not found on theme \"light\"`);\n }\n if (tone === \"base\") return colors[getTheme(\"light\").baseTones[themeColor]];\n return colors[offsetTone(0, tone)];\n }\n\n const name = themeName(object);\n let resultTone: number;\n if (tone === \"base\") {\n resultTone = getTheme(name).baseTones[themeColor];\n } else {\n const theme = getTheme(name);\n const context = biasContext(\n contextTone(object),\n theme.direction,\n theme.darkBias,\n );\n resultTone = offsetTone(context, tone);\n }\n const colors = themeVars()[themeColor];\n if (!colors) {\n throw Error(`color \"${themeColor}\" not found on theme \"${name}\"`);\n }\n const resultColor = colors[resultTone];\n\n return resultColor;\n}\n\nexport function themeColorToken(\n object: ElementNode | Listener | null,\n tone: ElementTone = \"inherit\",\n color: string = \"inherit\",\n): string {\n const colorName = color === \"inherit\" ? \"neutral\" : color;\n const name = object ? themeName(object as ElementNode | Listener) : \"light\";\n const tokens = themeTokens(name);\n const colorTokens = tokens[colorName];\n if (!colorTokens) {\n throw Error(`color \"${colorName}\" not found on theme \"${name}\"`);\n }\n\n if (!object) {\n if (tone === \"base\")\n return colorTokens[getTheme(\"light\").baseTones[colorName]];\n return colorTokens[offsetTone(0, tone)];\n }\n\n let resultTone: number;\n if (tone === \"base\") {\n resultTone = getTheme(name).baseTones[colorName];\n } else {\n const theme = getTheme(name);\n const context = biasContext(\n contextTone(object),\n theme.direction,\n theme.darkBias,\n );\n resultTone = offsetTone(context, tone);\n }\n\n return colorTokens[resultTone];\n}\n","/** Gamma-encode linear RGB (0-1) to 8-bit sRGB channels (0-255). */\nconst lrgbToSrgb = (rgb: number[]) => {\n const toSRGB = (c: number) => {\n const clamped = Math.max(0, Math.min(1, c));\n const s = clamped <= 0.0031308 ? 12.92 * clamped : 1.055 * Math.pow(clamped, 1 / 2.4) - 0.055;\n return Math.max(0, Math.min(255, Math.round(s * 255)));\n };\n return rgb.map(toSRGB);\n}\n\nconst srgbToLrgb = (rgb: number[]) => {\n const toLRGB = (c: number) => (c > 0.04045 ? Math.pow((c + 0.055) / 1.055, 2.4) : c / 12.92);\n return rgb.map(toLRGB);\n}\n\n/** Convert linear RGB to sRGB Hex string. */\nexport const rgbToHex = (rgb: number[]): string => {\n\n let [r, g, b] = lrgbToSrgb(rgb) as any[]\n r = r.toString(16).padStart(2, \"0\");\n g = g.toString(16).padStart(2, \"0\");\n b = b.toString(16).padStart(2, \"0\");\n return `#${r}${g}${b}`;\n};\n\n/** Convert sRGB Hex string to linear RGB. */\nexport const hexToRgb = (hex: string): number[] => {\n const r = parseInt(hex.slice(1, 3), 16) / 255;\n const g = parseInt(hex.slice(3, 5), 16) / 255;\n const b = parseInt(hex.slice(5, 7), 16) / 255;\n\n return srgbToLrgb([r, g, b])\n};\n\n/** Converts linear RGB to Oklab color space. */\n/** Specification: Björn Ottosson (2020). */\nexport const rgbToOklab = (rgb: number[]): number[] => {\n const l = 0.4122214708 * rgb[0] + 0.5363325363 * rgb[1] + 0.0514459929 * rgb[2];\n const m = 0.2119034982 * rgb[0] + 0.6806995451 * rgb[1] + 0.1073969566 * rgb[2];\n const s = 0.0883024619 * rgb[0] + 0.2817188376 * rgb[1] + 0.6299787005 * rgb[2];\n const l_ = Math.cbrt(l), m_ = Math.cbrt(m), s_ = Math.cbrt(s);\n return [\n 0.2104542553 * l_ + 0.793617785 * m_ - 0.0040720468 * s_,\n 1.9779984951 * l_ - 2.428592205 * m_ + 0.4505937099 * s_,\n 0.0259040371 * l_ + 0.7827717662 * m_ - 0.808675766 * s_\n ];\n};\n\n/** Converts Oklab color space to linear RGB. */\n/** Specification: Björn Ottosson (2020). */\nexport const oklabToRgb = (lab: number[]): number[] => {\n const [L, a, b] = lab;\n const l_ = L + 0.3963377774 * a + 0.2158037573 * b;\n const m_ = L - 0.1055613458 * a - 0.0638541728 * b;\n const s_ = L - 0.0894841775 * a - 1.291485548 * b;\n const l = l_ * l_ * l_, m = m_ * m_ * m_, s = s_ * s_ * s_;\n return [\n 4.0767416621 * l - 3.3077115913 * m + 0.2309699292 * s,\n -1.2684380046 * l + 2.6097574011 * m - 0.3413193965 * s,\n -0.0041960863 * l - 0.7034186147 * m + 1.707614701 * s\n ];\n};\n\n/** Calculate Equivalent Achromatic Lightness (L_EAL) using High et al. (2023). */\nexport const toLightnessEAL = (lab: number[]): number => {\n const [L, a, b] = lab;\n const C = Math.sqrt(a * a + b * b);\n const hRad = Math.atan2(b, a);\n const hDeg = (hRad * 180 / Math.PI + 360) % 360;\n\n const k1 = 0.1644, k2 = 0.0603, k3 = 0.1307, k4 = 0.0060;\n const fBYh = k1 * Math.abs(Math.sin(((hDeg - 90) / 2) * (Math.PI / 180))) + k2;\n\n let fRh = 0;\n if (hDeg <= 90 || hDeg >= 270) {\n fRh = k3 * Math.abs(Math.cos(hDeg * (Math.PI / 180))) + k4;\n }\n return L + (fBYh + fRh) * C;\n};\n\n/** Reverse L_EAL to get CIELAB Lightness (L). */\nexport const fromLightnessEAL = (brightness: number, lab: number[]): number => {\n const [, a, b] = lab;\n const C = Math.sqrt(a * a + b * b);\n const hRad = Math.atan2(b, a);\n const hDeg = (hRad * 180 / Math.PI + 360) % 360;\n\n const k1 = 0.1644, k2 = 0.0603, k3 = 0.1307, k4 = 0.0060;\n const fBYh = k1 * Math.abs(Math.sin(((hDeg - 90) / 2) * (Math.PI / 180))) + k2;\n\n let fRh = 0;\n if (hDeg <= 90 || hDeg >= 270) {\n fRh = k3 * Math.abs(Math.cos(hDeg * (Math.PI / 180))) + k4;\n }\n return Math.max(0, brightness - (fBYh + fRh) * C);\n};\n\n\n/** Convert LCH to CIELAB coordinates. */\nexport const lchToLab = (lch: number[]): number[] => {\n const [L, C, h] = lch;\n const hRad = (h * Math.PI) / 180;\n return [L, C * Math.cos(hRad), C * Math.sin(hRad)];\n};\n\n/** Convert linear sRGB to CIELAB (D65) */\nexport const rgbToLab = (rgb: number[]): number[] => {\n const [r, g, b] = rgb;\n\n // sRGB → XYZ (D65)\n const x = 0.4124564 * r + 0.3575761 * g + 0.1804375 * b;\n const y = 0.2126729 * r + 0.7151522 * g + 0.0721750 * b;\n const z = 0.0193339 * r + 0.1191920 * g + 0.9503041 * b;\n\n // D65 reference white\n const Xn = 0.95047;\n const Yn = 1.00000;\n const Zn = 1.08883;\n\n const f = (t: number) =>\n t > 0.008856 ? Math.cbrt(t) : (7.787 * t + 16 / 116);\n\n const fx = f(x / Xn);\n const fy = f(y / Yn);\n const fz = f(z / Zn);\n\n return [\n 116 * fy - 16,\n 500 * (fx - fy),\n 200 * (fy - fz),\n ];\n};\n\n/** Convert CIELAB (D65) to linear sRGB */\nexport const labToRgb = (lab: number[]): number[] => {\n const [L, a, b] = lab;\n\n const fy = (L + 16) / 116;\n const fx = a / 500 + fy;\n const fz = fy - b / 200;\n\n const fInv = (t: number) =>\n t ** 3 > 0.008856 ? t ** 3 : (t - 16 / 116) / 7.787;\n\n // D65 reference white\n const Xn = 0.95047;\n const Yn = 1.00000;\n const Zn = 1.08883;\n\n const x = fInv(fx) * Xn;\n const y = fInv(fy) * Yn;\n const z = fInv(fz) * Zn;\n\n // XYZ (D65) → sRGB\n return [\n 3.2404542 * x - 1.5371385 * y - 0.4985314 * z,\n -0.9692660 * x + 1.8760108 * y + 0.0415560 * z,\n 0.0556434 * x - 0.2040259 * y + 1.0572252 * z,\n ];\n};\n\n/** Convert CIELAB to LCH coordinates. */\nexport const labToLch = (lab: number[]): number[] => {\n const [L, a, b] = lab;\n const C = Math.sqrt(a * a + b * b);\n if (C < 0.0001) return [L, 0, 0];\n\n const hRad = Math.atan2(b, a);\n let hDeg = (hRad * 180 / Math.PI + 360) % 360;\n if (hDeg >= 359.9999) hDeg = 0;\n\n return [L, C, hDeg];\n};\n/** Calculate color difference using CIEDE2000 formula. */\nexport const calcDeltaE2000 = (lab1: number[], lab2: number[]): number => {\n const [L1, a1, b1] = lab1, [L2, a2, b2] = lab2;\n const avgL = (L1 + L2) / 2;\n const C1 = Math.sqrt(a1 * a1 + b1 * b1), C2 = Math.sqrt(a2 * a2 + b2 * b2);\n const avgC = (C1 + C2) / 2;\n const G = 0.5 * (1 - Math.sqrt(Math.pow(avgC, 7) / (Math.pow(avgC, 7) + Math.pow(25, 7))));\n const a1p = a1 * (1 + G), a2p = a2 * (1 + G);\n const C1p = Math.sqrt(a1p * a1p + b1 * b1), C2p = Math.sqrt(a2p * a2p + b2 * b2);\n const avgCp = (C1p + C2p) / 2;\n const h1p = Math.atan2(b1, a1p) * 180 / Math.PI + (Math.atan2(b1, a1p) < 0 ? 360 : 0);\n const h2p = Math.atan2(b2, a2p) * 180 / Math.PI + (Math.atan2(b2, a2p) < 0 ? 360 : 0);\n let dhp = h2p - h1p;\n if (Math.abs(dhp) > 180) dhp += (h2p <= h1p ? 360 : -360);\n const avgHp = Math.abs(h1p - h2p) > 180 ? (h1p + h2p + 360) / 2 : (h1p + h2p) / 2;\n const T = 1 - 0.17 * Math.cos((avgHp - 30) * Math.PI / 180) + 0.24 * Math.cos(2 * avgHp * Math.PI / 180) + 0.32 * Math.cos((3 * avgHp + 6) * Math.PI / 180) - 0.2 * Math.cos((4 * avgHp - 63) * Math.PI / 180);\n const dLp = L2 - L1, dCp = C2p - C1p;\n const dHp = 2 * Math.sqrt(C1p * C2p) * Math.sin(dhp / 2 * Math.PI / 180);\n const SL = 1 + (0.015 * Math.pow(avgL - 50, 2)) / Math.sqrt(20 + Math.pow(avgL - 50, 2));\n const SC = 1 + 0.045 * avgCp, SH = 1 + 0.015 * avgCp * T;\n const dtheta = 30 * Math.exp(-Math.pow((avgHp - 275) / 25, 2));\n const RC = 2 * Math.sqrt(Math.pow(avgCp, 7) / (Math.pow(avgCp, 7) + Math.pow(25, 7)));\n const RT = -RC * Math.sin(2 * dtheta * Math.PI / 180);\n return Math.sqrt(Math.pow(dLp / SL, 2) + Math.pow(dCp / SC, 2) + Math.pow(dHp / SH, 2) + RT * (dCp / SC) * (dHp / SH));\n};\n\n/** Convert CSS rgb() string to linear RGB. */\nexport const cssRgbToRgb = (css: string): number[] => {\n const m = css.match(/\\d+(\\.\\d+)?/g);\n if (!m || m.length < 3) throw new Error(\"Invalid CSS rgb()\");\n\n const toLinear = (c: number) => {\n const v = c / 255;\n return v <= 0.04045 ? v / 12.92 : Math.pow((v + 0.055) / 1.055, 2.4);\n };\n return [toLinear(Number(m[0])), toLinear(Number(m[1])), toLinear(Number(m[2]))];\n};\n\n\n\n/**\n * Create a Monotone Cubic Hermite Interpolator.\n * Ensures monotonicity is preserved between points.\n * Fritsch, F. N., & Carlson, R. E. (1980). Monotone piecewise cubic interpolation. *SIAM Journal on Numerical Analysis*, 17(2), 238–246.\n */\n\nexport const createMonotone = (points: number[][]) => {\n if (points.length < 1) return (_t: number) => 0;\n\n const sorted = [...points].sort((a, b) => a[0] - b[0]);\n const uniquePoints: number[][] = [];\n\n for (let i = 0; i < sorted.length; i++) {\n if (i === 0 || sorted[i][0] !== sorted[i - 1][0]) {\n uniquePoints.push(sorted[i]);\n }\n }\n\n const n = uniquePoints.length;\n if (n === 1) return (_t: number) => uniquePoints[0][1];\n\n const x = uniquePoints.map(p => p[0]);\n const y = uniquePoints.map(p => p[1]);\n const h: number[] = [];\n const secants: number[] = [];\n\n for (let i = 0; i < n - 1; i++) {\n h[i] = x[i + 1] - x[i];\n secants[i] = (y[i + 1] - y[i]) / h[i];\n }\n\n const m: number[] = new Array(n);\n m[0] = secants[0];\n m[n - 1] = secants[n - 2];\n\n for (let i = 1; i < n - 1; i++) {\n const d0 = secants[i - 1];\n const d1 = secants[i];\n if (d0 * d1 <= 0) {\n m[i] = 0;\n } else {\n const alpha = (1 + h[i] / (h[i - 1] + h[i])) / 3;\n m[i] = (d0 * d1) / ((1 - alpha) * d0 + alpha * d1);\n }\n }\n\n return (t: number): number => {\n if (t <= x[0]) return y[0];\n if (t >= x[n - 1]) return y[n - 1];\n\n let low = 0;\n let high = n - 2;\n let i = 0;\n while (low <= high) {\n const mid = Math.floor((low + high) / 2);\n if (t >= x[mid] && t <= x[mid + 1]) {\n i = mid;\n break;\n }\n if (t < x[mid]) high = mid - 1;\n else low = mid + 1;\n }\n\n const dx = h[i];\n const s = (t - x[i]) / dx;\n const s2 = s * s;\n const s3 = s2 * s;\n const m0 = m[i] * dx;\n const m1 = m[i + 1] * dx;\n\n return (2 * s3 - 3 * s2 + 1) * y[i] +\n (s3 - 2 * s2 + s) * m0 +\n (-2 * s3 + 3 * s2) * y[i + 1] +\n (s3 - s2) * m1;\n };\n};\n\n/** Calculate Root Mean Square (RMS) of an array. */\nexport function rootMeanSquare(values: number[]): number {\n const n = values.length;\n if (n === 0) return 0;\n\n let sumSq = 0;\n for (let i = 0; i < n; i++) {\n sumSq += values[i] * values[i];\n }\n return Math.sqrt(sumSq / n);\n}\n\n/** Calculate min, max, and average of an array. */\nexport const calcStatistics = (array: number[]) => {\n const n = array.length;\n if (n === 0) return { min: 0, max: 0, avg: 0 };\n\n let min = array[0];\n let max = array[0];\n let sum = 0;\n\n for (let i = 0; i < n; i++) {\n const v = array[i];\n if (v < min) min = v;\n if (v > max) max = v;\n sum += v;\n }\n\n return { min, max, avg: sum / n };\n};\n\n/** Calculate geometric mean score (0-100) from metrics. */\nexport const calcScore = (metrics: number[]): number => {\n const n = metrics.length;\n if (n === 0) return 0;\n\n const eps = 1e-6;\n const product = metrics.reduce((acc, score) => acc * (score + eps), 1);\n const globalScore = Math.pow(product, 1 / n);\n const result = Math.max(0, Math.min(1, globalScore));\n return parseFloat((result * 100).toFixed(2));\n};\n\n/**\n * Compute WCAG 2.1 contrast ratio between two hex colors.\n * Returns a value >= 1. Passes WCAG AA at >= 4.5, AAA at >= 7.\n */\nexport const contrastRatio = (hex1: string, hex2: string): number => {\n const [r1, g1, b1] = hexToRgb(hex1);\n const [r2, g2, b2] = hexToRgb(hex2);\n const l1 = 0.2126 * r1 + 0.7152 * g1 + 0.0722 * b1;\n const l2 = 0.2126 * r2 + 0.7152 * g2 + 0.0722 * b2;\n const lighter = Math.max(l1, l2);\n const darker = Math.min(l1, l2);\n return (lighter + 0.05) / (darker + 0.05);\n};\n\n/**\n * Mix two hex colors. `ratio` controls how much of the second color is used\n * (0 = all hex1, 1 = all hex2, default 0.5). Interpolation happens in\n * the given `space` — defaults to `oklab` (perceptually uniform).\n */\nexport const mix = (\n hex1: string,\n hex2: string,\n ratio = 0.5,\n space: 'oklab' | 'lab' | 'rgb' = 'oklab'\n): string => {\n const t = Math.max(0, Math.min(1, ratio));\n const rgb1 = hexToRgb(hex1);\n const rgb2 = hexToRgb(hex2);\n\n if (space === 'rgb') {\n return rgbToHex(rgb1.map((c, i) => c + t * (rgb2[i] - c)));\n }\n\n if (space === 'lab') {\n const lab1 = rgbToLab(rgb1);\n const lab2 = rgbToLab(rgb2);\n return rgbToHex(labToRgb(lab1.map((c, i) => c + t * (lab2[i] - c))));\n }\n\n // Default: oklab\n const ok1 = rgbToOklab(rgb1);\n const ok2 = rgbToOklab(rgb2);\n return rgbToHex(oklabToRgb(ok1.map((c, i) => c + t * (ok2[i] - c))));\n};\n\n/**\n * Generate a `steps`-step gradient across `colors` (2 or more anchors).\n * Interpolation is in Oklab for perceptual uniformity.\n * Returns hex strings from the first to the last anchor.\n */\nexport const scale = (colors: string[], steps: number): string[] => {\n if (colors.length < 2) throw new Error(\"scale() requires at least 2 colors\");\n if (steps < 1) return [];\n if (steps === 1) return [colors[0]];\n\n const oklabs = colors.map(hex => rgbToOklab(hexToRgb(hex)));\n const segments = oklabs.length - 1;\n const result: string[] = [];\n\n for (let i = 0; i < steps; i++) {\n const t = i / (steps - 1);\n const pos = t * segments;\n const seg = Math.min(Math.floor(pos), segments - 1);\n const localT = pos - seg;\n const ok1 = oklabs[seg];\n const ok2 = oklabs[seg + 1];\n result.push(rgbToHex(oklabToRgb(ok1.map((c, j) => c + localT * (ok2[j] - c)))));\n }\n\n return result;\n};\n","import { hexToRgb, labToLch, rgbToLab, toLightnessEAL } from \"./utils\";\n\nexport class Swatch {\n readonly hex: string;\n\n constructor(hex: string) {\n this.hex = hex;\n }\n\n get rgb() {\n return hexToRgb(this.hex);\n }\n\n get lab() {\n return rgbToLab(this.rgb);\n }\n\n get lch() {\n return labToLch(this.lab);\n }\n\n get lightness() {\n // Equivalent Achromatic Lightness (High et al., 2023). Delegates to the\n // shared toLightnessEAL() so the formula lives in exactly one place.\n return toLightnessEAL(this.lab);\n }\n\n get chroma() {\n return this.lch[1];\n }\n\n get hue() {\n return this.lch[2];\n }\n\n get luminance() {\n const [r, g, b] = this.rgb;\n return 0.2126 * r + 0.7152 * g + 0.0722 * b;\n }\n}\n","import { Swatch } from \"./Swatch\";\nimport { calcDeltaE2000, calcScore, createMonotone } from \"./utils\";\n\nexport type ContrastValue = {\n efficiency: number;\n target: number;\n span: number;\n value: number;\n};\n\nexport type WcagContrasts = Record<30 | 45 | 70, ContrastValue>;\nexport type ApcaContrasts = Record<45 | 60 | 75, ContrastValue>;\n\nexport class Ramp {\n swatches: Swatch[];\n name: string;\n\n constructor(colors: string[] = [], name = \"brand\") {\n this.swatches = colors.map((hex) => new Swatch(hex));\n this.name = name;\n }\n\n get colors() {\n return this.swatches.map((swatch) => swatch.hex);\n }\n\n get peakChroma() {\n const colors = this.colors.slice(2, -2);\n let bestHex = \"\";\n let bestChroma = -Infinity;\n\n for (const hex of colors) {\n const swatch = new Swatch(hex);\n if (swatch.chroma > bestChroma) {\n bestChroma = swatch.chroma;\n bestHex = hex;\n }\n }\n if (bestChroma < 6) return this.colors[Math.ceil(this.steps / 2)];\n\n return bestHex;\n }\n\n get steps() {\n return this.colors.length;\n }\n\n get baseColor() {\n if (this.colors.length === 0) return \"\";\n return this.peakChroma || this.colors[Math.floor(this.colors.length / 2)];\n }\n\n get baseIndex() {\n if (this.colors.length === 0) return -1;\n return this.colors.findIndex((hex) => hex.toLowerCase() === this.baseColor.toLowerCase());\n }\n\n get wcag(): WcagContrasts {\n const swatches = this.swatches;\n const total = swatches.length;\n const maxGap = total - 1;\n const contrasts = {} as WcagContrasts;\n\n if (total <= 1) {\n for (const level of [30, 45, 70] as const) {\n contrasts[level] = { efficiency: 1, target: level / 10, span: 0, value: 0 };\n }\n return contrasts;\n }\n\n for (const level of [30, 45, 70] as const) {\n const target = level / 10;\n let span = maxGap;\n let value = 0;\n\n for (let k = 1; k < total; k++) {\n let currentKMin = Infinity;\n\n for (let i = 0; i < total - k; i++) {\n const l1 = swatches[i].luminance;\n const l2 = swatches[i + k].luminance;\n const result = (Math.max(l1, l2) + 0.05) / (Math.min(l1, l2) + 0.05);\n if (result < currentKMin) currentKMin = result;\n }\n\n if (currentKMin >= target) {\n span = k;\n value = currentKMin;\n break;\n }\n\n if (k === maxGap) value = currentKMin;\n }\n\n contrasts[level] = {\n efficiency: span / maxGap,\n target,\n span,\n value,\n };\n }\n\n return contrasts;\n }\n\n get apca(): ApcaContrasts {\n const swatches = this.swatches;\n const total = swatches.length;\n const maxGap = total - 1;\n const contrasts = {} as ApcaContrasts;\n\n if (total <= 1) {\n for (const level of [45, 60, 75] as const) {\n contrasts[level] = { efficiency: 1, target: level, span: 0, value: 0 };\n }\n return contrasts;\n }\n\n const apcaContrast = (yText: number, yBg: number) => {\n const Bc = 0.022, Bl = 1.414;\n const txt = yText < Bc ? yText + Math.pow(Bc - yText, Bl) : yText;\n const bg = yBg < Bc ? yBg + Math.pow(Bc - yBg, Bl) : yBg;\n\n let lc = bg >= txt\n ? (Math.pow(bg, 0.56) - Math.pow(txt, 0.57)) * 114\n : (Math.pow(bg, 0.65) - Math.pow(txt, 0.62)) * 114;\n\n if (Math.abs(lc) < 10) return 0;\n lc = lc > 0 ? lc - 2.7 : lc + 2.7;\n return Math.round(lc);\n };\n\n for (const level of [45, 60, 75] as const) {\n const target = level;\n let span = maxGap;\n let value = 0;\n\n for (let k = 1; k < total; k++) {\n let currentKMin = Infinity;\n\n for (let i = 0; i < total - k; i++) {\n const bg = swatches[i].luminance > swatches[i + k].luminance ? swatches[i].luminance : swatches[i + k].luminance;\n const text = swatches[i].luminance > swatches[i + k].luminance ? swatches[i + k].luminance : swatches[i].luminance;\n const result = Math.abs(apcaContrast(text, bg));\n if (result < currentKMin) currentKMin = result;\n }\n\n if (currentKMin >= target) {\n span = k;\n value = currentKMin;\n break;\n }\n\n if (k === maxGap) value = currentKMin;\n }\n\n contrasts[level] = {\n efficiency: span / maxGap,\n target,\n span,\n value,\n };\n }\n\n return contrasts;\n }\n\n get deltaECurve() {\n const values = [0];\n\n for (let i = 1; i < this.swatches.length; i++) {\n const de00 = calcDeltaE2000(this.swatches[i - 1].lab, this.swatches[i].lab);\n values.push(values[i - 1] + de00);\n }\n\n return values;\n }\n\n get unwrapHues() {\n const hues = this.swatches.map((swatch) => swatch.hue).slice(1, -1);\n if (hues.length === 0) return [];\n\n const result = [hues[0]];\n for (let i = 1; i < hues.length; i++) {\n let diff = hues[i] - hues[i - 1];\n if (diff > 180) diff -= 360;\n else if (diff < -180) diff += 360;\n result.push(result[i - 1] + diff);\n }\n return result;\n }\n\n get lightnessLinearity() {\n const values = this.swatches.map((swatch) => swatch.lightness);\n const n = values.length;\n if (n < 2) return 1;\n\n let sumX = 0, sumY = 0, sumXY = 0, sumXX = 0;\n for (let i = 0; i < n; i++) {\n sumX += i;\n sumY += values[i];\n sumXY += i * values[i];\n sumXX += i * i;\n }\n\n const denominator = n * sumXX - sumX * sumX;\n if (Math.abs(denominator) < 1e-10) return 1;\n\n const slope = (n * sumXY - sumX * sumY) / denominator;\n const intercept = (sumY - slope * sumX) / n;\n const fitRange = Math.abs(slope * (n - 1));\n if (fitRange < 1e-3) return 1;\n\n let sumSqError = 0;\n let sumSqMaxError = 0;\n for (let i = 0; i < n; i++) {\n const target = slope * i + intercept;\n const error = values[i] - target;\n sumSqError += error * error;\n\n const maxDiff = Math.max(\n target - Math.min(intercept, slope * (n - 1) + intercept),\n Math.max(intercept, slope * (n - 1) + intercept) - target\n );\n sumSqMaxError += maxDiff * maxDiff;\n }\n\n return Math.max(0, Math.min(1, 1 - (Math.sqrt(sumSqError / n) / Math.sqrt(sumSqMaxError / n))));\n }\n\n get chromaSmoothness() {\n const values = this.swatches.map((swatch) => swatch.chroma);\n const n = values.length;\n if (n < 3) return 1;\n\n const cRef = 133.8;\n const cMaxInput = Math.max(...values);\n if (cMaxInput <= 1e-2) return 1;\n\n const normalized = values.map((value) => (value / cMaxInput) * cRef);\n const cMin = Math.min(...normalized);\n const cMax = Math.max(...normalized);\n const peakIndex = normalized.findIndex((value) => value === cMax);\n const spline = createMonotone([[0, normalized[0]], [peakIndex, cMax], [n - 1, normalized[n - 1]]]);\n\n let sumSqErr = 0;\n let sumSqMaxErr = 0;\n for (let i = 0; i < n; i++) {\n const target = spline(i);\n const err = normalized[i] - target;\n sumSqErr += err * err;\n sumSqMaxErr += Math.pow(Math.max(target - cMin, cMax - target), 2);\n }\n\n return Math.max(0, Math.min(1, 1 - (Math.sqrt(sumSqErr / n) / Math.sqrt(sumSqMaxErr / n))));\n }\n\n get spacingUniformity() {\n const values = this.deltaECurve;\n const n = values.length;\n if (n < 2) return 1;\n\n const deltas: number[] = [];\n for (let i = 1; i < n; i++) {\n const d = values[i] - values[i - 1];\n if (d < 0) return 0;\n deltas.push(d);\n }\n\n const mean = deltas.reduce((a, b) => a + b, 0) / deltas.length;\n if (mean <= 1e-6) return 0;\n\n let sumSq = 0;\n for (const d of deltas) sumSq += Math.pow(d - mean, 2);\n\n const cv = Math.sqrt(sumSq / deltas.length) / mean;\n return Math.max(0, Math.min(1, 1 / (1 + cv)));\n }\n\n get hueStability() {\n const values = this.unwrapHues;\n const n = values.length;\n if (n < 2) return 1;\n\n const ref = values[this.baseIndex - 1] ?? this.swatches[this.baseIndex]?.hue ?? 0;\n\n let sumSqError = 0;\n let sumSqMaxError = 0;\n for (let i = 0; i < n; i++) {\n let d = Math.abs(values[i] - ref) % 360;\n if (d > 180) d = 360 - d;\n sumSqError += d * d;\n const maxD = (i / (n - 1)) * 180;\n sumSqMaxError += maxD * maxD;\n }\n\n return Math.max(0, Math.min(1, 1 - (Math.sqrt(sumSqError / n) / (Math.sqrt(sumSqMaxError / n) || 1))));\n }\n\n get contrastEfficiency() {\n const span = this.wcag[45].span;\n const steps = this.steps;\n if (steps <= 1) return 1;\n\n const lambda = 0.501;\n const density = span / (steps - 1);\n\n if (density <= lambda) return 1;\n if (density >= 1) return 0;\n\n return 1 - (density - lambda) / (1 - lambda);\n }\n\n get metrics() {\n return {\n lightnessLinearity: this.lightnessLinearity,\n chromaSmoothness: this.chromaSmoothness,\n spacingUniformity: this.spacingUniformity,\n hueStability: this.hueStability,\n contrastEfficiency: this.contrastEfficiency,\n };\n }\n\n get score() {\n return calcScore(Object.values(this.metrics));\n }\n}\n","import { Ramp, type ApcaContrasts, type WcagContrasts } from \"./Ramp\";\nimport { calcScore, rootMeanSquare } from \"./utils\";\n\nexport type PaletteColors = Record<string, string[]>;\n\nexport class Palette {\n ramps: Ramp[];\n name: string;\n\n constructor(colors: PaletteColors = {}, name = \"Collection 1\") {\n this.ramps = Object.entries(colors).map(([rampName, rampColors]) => new Ramp(rampColors, rampName));\n this.name = name;\n }\n\n get colors(): PaletteColors {\n return Object.fromEntries(this.ramps.map((ramp) => [ramp.name, ramp.colors]));\n }\n\n get steps() {\n return this.ramps[0]?.steps || 0;\n }\n\n get wcag(): WcagContrasts {\n const contrasts = {} as WcagContrasts;\n const steps = this.steps;\n\n for (const level of [30, 45, 70] as const) {\n const rampContrasts = this.ramps.map((ramp) => ramp.wcag[level]);\n const span = Math.max(0, ...rampContrasts.map((contrast) => contrast?.span || 0));\n const sum = rampContrasts.reduce((acc, contrast) => acc + (contrast?.value || 0), 0);\n\n contrasts[level] = {\n target: level / 10,\n span,\n value: sum / (this.ramps.length || 1),\n efficiency: steps > 1 ? span / (steps - 1) : 0,\n };\n }\n\n return contrasts;\n }\n\n get apca(): ApcaContrasts {\n const contrasts = {} as ApcaContrasts;\n const steps = this.steps;\n\n for (const level of [45, 60, 75] as const) {\n const rampContrasts = this.ramps.map((ramp) => ramp.apca[level]);\n const span = Math.max(0, ...rampContrasts.map((contrast) => contrast?.span || 0));\n const sum = rampContrasts.reduce((acc, contrast) => acc + (contrast?.value || 0), 0);\n\n contrasts[level] = {\n target: level,\n span,\n value: sum / (this.ramps.length || 1),\n efficiency: steps > 1 ? span / (steps - 1) : 0,\n };\n }\n\n return contrasts;\n }\n\n get contrastEfficiency() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.contrastEfficiency));\n }\n\n get lightnessLinearity() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.lightnessLinearity));\n }\n\n get chromaSmoothness() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.chromaSmoothness));\n }\n\n get hueStability() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.hueStability));\n }\n\n get spacingUniformity() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.spacingUniformity));\n }\n\n get score() {\n return calcScore([\n this.contrastEfficiency,\n this.lightnessLinearity,\n this.chromaSmoothness,\n this.hueStability,\n this.spacingUniformity,\n ]);\n }\n}\n","import { createMonotone, hexToRgb, oklabToRgb, rgbToHex, rgbToOklab } from \"./utils.js\";\n\n/**\n * Rational-function warp/unwarp pair used to bend the ramp's interpolation\n * parameter so that, once sliced into N discrete steps, the resulting WCAG\n * contrast pairs land as close as possible to the theoretically ideal\n * contrast span K_ideal = ceil(0.501 * (N - 1)) (see the Contrast Efficiency\n * metric in Ramp.ts / the chromametry paper). P and Q were fit by grid search\n * + local refinement against 600 synthetic base colors sampled from the\n * hardest hue regions for perceptual uniformity (green, blue-green/cyan),\n * jointly optimizing the composite quality SCORE and how often the generated\n * ramp's actual span matches K_ideal exactly. At P=0.605, Q=0.685 the search\n * converged to ~90.6 average SCORE, ~95.9% of ramps with span <= K_ideal, and\n * ~88.5% exact span match.\n */\nconst P = 0.605;\nconst Q = 0.685;\n\nfunction warp(t: number): number {\n const tn = Math.pow(t, P);\n return tn / (1 + Q * (1 - tn));\n}\n\nfunction unwarp(y: number): number {\n const xn = (y * (1 + Q)) / (1 + y * Q);\n return Math.pow(xn, 1 / P);\n}\n\nfunction euclidean3(v1: number[], v2: number[]): number {\n return Math.sqrt(\n Math.pow(v1[0] - v2[0], 2) +\n Math.pow(v1[1] - v2[1], 2) +\n Math.pow(v1[2] - v2[2], 2),\n );\n}\n\n// Builds a continuous color-at-parameter function over Oklab-space anchors\n// (black, ...baseColors, white), sorted by lightness. The anchors' positions\n// along the polyline are placed in \"warped\" parameter space via `unwarp`\n// (cumulative Oklab arc length -> normalized distance -> unwarp), so that a\n// linearly-sampled output parameter `t`, once passed back through `warp`,\n// re-lands on the correct anchor position — same mechanism as Ramp.ts's\n// contrastEfficiency metric, run in reverse to CONSTRUCT a ramp instead of\n// SCORING one. Lightness is linearly interpolated per Oklab segment; a and b\n// (chroma channels) use a monotone cubic spline across ALL anchors for a\n// smooth, single-peak chroma trajectory (matches the Chroma Smoothness metric's\n// ideal trajectory assumption).\nfunction sequentialInterpolator(rgbs: number[][]) {\n const fullRgbs = [[0, 0, 0], ...rgbs, [1, 1, 1]];\n const anchors = fullRgbs.map((rgb) => rgbToOklab(rgb)).sort((a, b) => a[0] - b[0]);\n\n const L = anchors.map((v) => v[0]);\n const A = anchors.map((v) => v[1]);\n const B = anchors.map((v) => v[2]);\n\n const cumulativeDistances: number[] = [0];\n let totalDist = 0;\n for (let i = 1; i < anchors.length; i++) {\n totalDist += euclidean3(anchors[i], anchors[i - 1]);\n cumulativeDistances.push(totalDist);\n }\n\n const allParams = cumulativeDistances.map((d) => unwarp(totalDist > 0 ? d / totalDist : 0));\n\n const tMin = rgbs.length === 1 ? 0 : allParams[1];\n const tMax = rgbs.length === 1 ? 1 : allParams[allParams.length - 2];\n\n const aInterpolator = createMonotone(allParams.map((p, i) => [p, A[i]]));\n const bInterpolator = createMonotone(allParams.map((p, i) => [p, B[i]]));\n\n const colorAtParam = (t: number): number[] => {\n const tWarped = warp(t);\n const tMapped = tMin + tWarped * (tMax - tMin);\n\n let i = 0;\n for (let j = 0; j < allParams.length - 1; j++) {\n if (tMapped <= allParams[j + 1]) {\n i = j;\n break;\n }\n }\n\n const dStart = allParams[i];\n const dEnd = allParams[i + 1];\n const ratio = (tMapped - dStart) / (dEnd - dStart || 1);\n const l = L[i] + ratio * (L[i + 1] - L[i]);\n const a = aInterpolator(tMapped);\n const b = bInterpolator(tMapped);\n\n return oklabToRgb([l, a, b]);\n };\n\n return {\n colorAtParam,\n parameters: allParams.slice(1, -1).map((v) => (v - tMin) / (tMax - tMin)),\n };\n}\n\n/**\n * Generate a WCAG-optimized sequential monochromatic ramp from one or more\n * anchor colors, black and white implicitly bracketing the ramp. When more\n * than one anchor color is given, each becomes a fixed waypoint the ramp\n * passes through (e.g. a specific brand color pinned at a specific step),\n * still connected by the same warped Oklab interpolation.\n *\n * Output is ordered light-to-dark (index 0 lightest, last index darkest) to\n * match `@domphy/theme`'s `ThemeInput.colors[name]` convention (`light.ts`'s\n * arrays start `#ffffff`, end `#000000`) — the result can be assigned there\n * directly.\n *\n * @param hexs one hex color, or several ordered by intended position\n * @param stepsCount number of output steps (18 matches the tone scale in\n * `@domphy/theme`'s `ElementTones` — `shift-0`..`shift-17`)\n * @returns `stepsCount` hex colors, lightest first\n */\nexport function generateRamp(hexs: string | string[], stepsCount: number): string[] {\n const anchors = Array.isArray(hexs) ? hexs : [hexs];\n if (anchors.length === 0) throw new Error(\"generateRamp requires at least one anchor color\");\n if (stepsCount <= 0) return [];\n if (stepsCount === 1) return [anchors[0]];\n\n const { colorAtParam, parameters } = sequentialInterpolator(anchors.map(hexToRgb));\n const colors: string[] = [];\n\n const fullParams = [0, ...parameters, 1];\n const anchorIdx = fullParams.map((v) => Math.round(v * (stepsCount - 1)));\n\n let segment = 0;\n for (let k = 0; k < stepsCount; k++) {\n while (segment < anchorIdx.length - 2 && k > anchorIdx[segment + 1]) segment++;\n\n const startIdx = anchorIdx[segment];\n const endIdx = anchorIdx[segment + 1];\n const startParam = fullParams[segment];\n const endParam = fullParams[segment + 1];\n\n let t: number;\n if (endIdx <= startIdx) {\n t = startParam;\n } else {\n const ratio = (k - startIdx) / (endIdx - startIdx);\n t = startParam + ratio * (endParam - startParam);\n }\n\n colors.push(rgbToHex(colorAtParam(t)));\n }\n\n // sequentialInterpolator walks dark (t=0) -> light (t=1); reverse to match\n // @domphy/theme's light-first convention.\n return colors.reverse();\n}\n","export * from \"./classes.js\";\nexport * from \"./patches.js\";\nexport * from \"./types.js\";\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles an abbreviation/acronym with a dotted underline and a \"help\" cursor,\n * shifting to the accent color on hover. Apply to an `<abbr>` element.\n *\n * @hostTag abbr\n * @param props.color - Base text/decoration color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @param props.accentColor - Hover color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { abbr: \"HTML\", title: \"HyperText Markup Language\", $: [abbreviation({ accentColor: \"primary\" })] }\n */\nfunction abbreviation(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"abbr\") {\n console.warn(`\"abbreviation\" primitive patch must use abbr tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n textDecorationLine: \"underline\",\n textDecorationStyle: \"dotted\",\n textDecorationColor: (listener) =>\n themeColor(listener, \"shift-7\", color.get(listener)),\n textUnderlineOffset: themeSpacing(0.72),\n cursor: \"help\",\n \"&:hover\": {\n color: (listener) =>\n themeColor(listener, \"shift-11\", accentColor.get(listener)),\n textDecorationColor: (listener) =>\n themeColor(listener, \"shift-9\", accentColor.get(listener)),\n },\n },\n };\n}\n\nexport { abbreviation };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Container patch that groups `<details>` elements into a bordered accordion.\n * In `type: \"single\"` mode (default), opening one item closes all siblings.\n *\n * @param props.type - `\"single\"` (default) or `\"multiple\"`. Single mode auto-closes siblings.\n * @param props.color - Theme color tone for borders and backgrounds. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color for focus outlines on summary. Defaults to `\"primary\"`.\n * @example\n * { div: [\n * { details: [{ summary: \"Section A\" }, { p: \"Content A\" }], $: [details()] },\n * { details: [{ summary: \"Section B\" }, { p: \"Content B\" }], $: [details()] },\n * ], $: [accordion()] }\n */\nfunction accordion(\n props: {\n type?: \"single\" | \"multiple\";\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { type = \"single\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onMount: (node) => {\n if (type !== \"single\") return;\n\n const el = node.domElement;\n if (!el) return;\n const handler = (event: Event) => {\n const summary = (event.target as Element).closest(\"summary\");\n if (!summary) return;\n const item = summary.closest(\"details\") as HTMLDetailsElement | null;\n if (!item || item.parentElement !== el) return;\n if (!item.open) {\n Array.from(el.querySelectorAll(\":scope > details\")).forEach(\n (detail) => {\n if (detail !== item) (detail as HTMLDetailsElement).open = false;\n },\n );\n }\n };\n el.addEventListener(\"click\", handler);\n node.addHook(\"Remove\", () => el.removeEventListener(\"click\", handler));\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n outlineOffset: \"-1px\",\n overflow: \"hidden\",\n \"& > details\": {\n borderBottom: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n },\n \"& > details:last-child\": {\n borderBottom: \"none\",\n },\n \"& > details > summary:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n },\n };\n}\n\nexport { accordion };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A semantic alert surface block with a colored inset bar, padding, and\n * `role=\"alert\"`. Typically applied to a `<div>` (any block container).\n *\n * @param props.color - Surface/accent color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { div: \"Saved successfully\", $: [alert({ color: \"success\" })] }\n */\nfunction alert(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n\n return {\n role: \"alert\",\n // Alert is a semantic surface block, so it should shift the local surface context.\n dataTone: \"shift-2\",\n style: {\n display: \"flex\",\n alignItems: \"flex-start\",\n gap: themeSpacing(3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n boxShadow: (listener) =>\n `inset ${themeSpacing(1)} 0 0 0 ${themeColor(listener, \"shift-8\", color.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n },\n };\n}\n\nexport { alert };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A circular avatar container that centers initials/text and cover-fits any\n * child `<img>`. Typically applied to an inline-flex container such as a `<span>`.\n *\n * @param props.color - Background/foreground color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { span: \"JD\", $: [avatar({ color: \"primary\" })] }\n */\nfunction avatar(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n style: {\n position: \"relative\",\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n overflow: \"hidden\",\n borderRadius: \"50%\",\n flexShrink: 0,\n width: themeSpacing(9),\n height: themeSpacing(9),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontWeight: \"600\",\n userSelect: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n \"& img\": {\n position: \"absolute\",\n inset: 0,\n width: \"100%\",\n height: \"100%\",\n objectFit: \"cover\",\n },\n },\n };\n}\n\nexport { avatar };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Renders a small count/label bubble pinned to the top-right corner of its host\n * (via a `::after` pseudo-element). Typically applied to an inline container such\n * as a `<span>` wrapping an icon or element.\n *\n * @param props.color - Badge color tone. Optional `ValueOrState<ThemeColor>`, default \"danger\".\n * @param props.label - Text/number shown in the badge. Optional `ValueOrState<string | number>`, default 999.\n * @example { span: \"🔔\", $: [badge({ label: 3, color: \"danger\" })] }\n */\nfunction badge(\n props: {\n color?: ValueOrState<ThemeColor>;\n label?: ValueOrState<string | number>;\n } = {},\n): PartialElement {\n const { label = 999 } = props;\n const state = toState(label);\n const color = toState(props.color ?? \"danger\", \"color\");\n return {\n style: {\n position: \"relative\",\n \"&::after\": {\n content: (l) => `\"${state.get(l)}\"`,\n position: \"absolute\",\n top: 0,\n right: 0,\n transform: \"translate(50%,-50%)\",\n paddingInline: themeSpacing(1),\n minWidth: themeSpacing(6),\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: (l) => themeSize(l, \"decrease-1\"),\n borderRadius: themeSpacing(999),\n backgroundColor: (l) => themeColor(l, \"shift-9\", color.get(l)),\n color: (l) => themeColor(l, \"shift-0\", color.get(l)),\n },\n },\n };\n}\n\nexport { badge };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a quotation block with a colored inset side bar, padded surface, and\n * shifted tone. Apply to a `<blockquote>` element.\n *\n * @hostTag blockquote\n * @param props.color - Surface/bar color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { blockquote: \"Design is how it works.\", $: [blockquote({ color: \"primary\" })] }\n */\nfunction blockquote(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"blockquote\") {\n console.warn(`\"blockquote\" primitive patch must use blockquote tag`);\n }\n },\n dataTone: \"shift-2\",\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n boxShadow: (listener) =>\n `inset ${themeSpacing(1)} 0 0 0 ${themeColor(listener, \"shift-4\", color.get(listener))}`,\n border: \"none\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n margin: 0,\n },\n };\n}\n\nexport { blockquote };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A horizontal breadcrumb navigation that lays out its children with a\n * separator between items and highlights the `[aria-current=page]` item.\n * Apply to a `<nav>` element.\n *\n * @hostTag nav\n * @param props.color - Color tone for links/separators. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @param props.separator - String inserted between items via `::after`. Optional `string`, default \"/\".\n * @example { nav: null, $: [breadcrumb({ separator: \"›\" })] }\n */\nfunction breadcrumb(\n props: { color?: ValueOrState<ThemeColor>; separator?: string } = {},\n): PartialElement {\n const { separator = \"/\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"nav\")\n console.warn('\"breadcrumb\" patch must use nav tag');\n },\n ariaLabel: \"breadcrumb\",\n style: {\n display: \"flex\",\n alignItems: \"center\",\n flexWrap: \"wrap\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n gap: themeSpacing(1),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n \"& > *\": {\n display: \"inline-flex\",\n alignItems: \"center\",\n color: (listener) => themeColor(listener, \"muted\", color.get(listener)),\n },\n \"& > *:not(:last-child)::after\": {\n content: `\"${separator}\"`,\n color: (listener) =>\n themeColor(listener, \"shift-4\", color.get(listener)),\n paddingInlineStart: themeSpacing(1),\n },\n \"& > [aria-current=page]\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { breadcrumb };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * An ellipsis trigger button for collapsed breadcrumb items, with hover and\n * focus-visible states. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.color - Color tone for the trigger. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { button: \"…\", $: [breadcrumbEllipsis({ color: \"neutral\" })] }\n */\nfunction breadcrumbEllipsis(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn('\"breadcrumbEllipsis\" patch must use button tag');\n }\n },\n ariaLabel: \"More breadcrumb items\",\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n paddingInline: themeSpacing(1),\n border: \"none\",\n background: \"none\",\n cursor: \"pointer\",\n color: (listener) => themeColor(listener, \"muted\", color.get(listener)),\n borderRadius: themeSpacing(1),\n \"&:hover\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", color.get(listener))}`,\n outlineOffset: themeSpacing(0.5),\n },\n },\n };\n}\n\nexport { breadcrumbEllipsis };\n","/**\n * The `fontSize` step for `button()`/`buttonGhost()`'s `size` prop. Padding stays\n * per-component (button and buttonGhost start from different base paddings) so\n * only the part that's genuinely identical — the font-size step — lives here.\n */\nconst BUTTON_SIZE_FONT = {\n small: \"decrease-1\",\n medium: \"inherit\",\n large: \"increase-1\",\n} as const;\n\ntype ButtonSize = keyof typeof BUTTON_SIZE_FONT;\n\nexport { BUTTON_SIZE_FONT };\nexport type { ButtonSize };\n","import type { Listener } from \"@domphy/core\";\nimport { type ThemeColor, themeColor } from \"@domphy/theme\";\n\n/**\n * Shared `:focus-visible` ring: a 2px halo in the given accent tone, drawn via\n * box-shadow so it composes with a control's own outline-based resting border\n * instead of replacing it. Used across interactive patches (button, inputs,\n * select, textarea, segmented, tabs, toggleGroup, rating, pagination) so focus\n * reads the same way everywhere instead of each patch picking its own style.\n */\nfunction focusRing(listener: Listener, color: ThemeColor = \"primary\"): string {\n return `0 0 0 2px ${themeColor(listener, \"shift-6\", color)}`;\n}\n\nexport { focusRing };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { BUTTON_SIZE_FONT, type ButtonSize } from \"../utils/buttonSize.js\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nconst PADDING_STEPS: Record<ButtonSize, number> = {\n small: 0.5,\n medium: 1,\n large: 1.5,\n};\n\n/**\n * A transparent button with no border or background — suitable for icon\n * actions, inline controls, and delete/close triggers. Apply to a `<button>`\n * element.\n *\n * @hostTag button\n * @param props.color - Text color tone. Optional `ValueOrState<ThemeColor>`, defaults to `\"neutral\"`.\n * @param props.size - Button size preset. Optional `\"small\" | \"medium\" | \"large\"`, defaults to `\"medium\"`.\n * @example { button: \"×\", $: [buttonGhost()] }\n * @example { button: { span: null, $: [icon({ name: \"trash\" })] }, $: [buttonGhost({ color: \"error\" })] }\n */\nfunction buttonGhost(\n props: { color?: ValueOrState<ThemeColor>; size?: ButtonSize } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const padding = PADDING_STEPS[props.size ?? \"medium\"];\n const fontSize = BUTTON_SIZE_FONT[props.size ?? \"medium\"];\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn(`\"buttonGhost\" primitive patch must use button tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontSize: (listener) => themeSize(listener, fontSize),\n paddingBlock: (listener) =>\n themeSpacing(themeDensity(listener) * padding),\n paddingInline: (listener) =>\n themeSpacing(themeDensity(listener) * padding),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n display: \"inline-flex\",\n justifyContent: \"center\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 1),\n userSelect: \"none\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n border: \"none\",\n background: \"none\",\n outline: \"none\",\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n color: (listener) => themeColor(listener, \"shift-6\", color.get(listener)),\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"border-strong\", \"neutral\"),\n },\n \"&[aria-busy=true]\": {\n opacity: 0.7,\n cursor: \"wait\",\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { buttonGhost };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { BUTTON_SIZE_FONT, type ButtonSize } from \"../utils/buttonSize.js\";\nimport { focusRing } from \"../utils/focusRing.js\";\nimport { buttonGhost } from \"./buttonGhost.js\";\n\ntype ButtonVariant = \"solid\" | \"outline\" | \"ghost\";\n\nconst PADDING_STEPS: Record<ButtonSize, { block: number; inline: number }> = {\n small: { block: 0.5, inline: 2 },\n medium: { block: 1, inline: 3 },\n large: { block: 1.5, inline: 4 },\n};\n\n/**\n * A themed button control with density-aware padding/radius and hover, focus-visible,\n * `[disabled]`, and `[aria-busy=true]` states. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.color - Button color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @param props.variant - Visual style: `\"outline\"` (tinted background + outline, default,\n * backward compatible), `\"solid\"` (filled background, readable contrast text), or `\"ghost\"`\n * (no background/border — delegates to `buttonGhost()` so the two stay visually identical).\n * @param props.size - Button size preset. Optional `\"small\" | \"medium\" | \"large\"`, defaults to `\"medium\"`.\n * @example { button: \"Save\", $: [button({ color: \"primary\" })] }\n * @example { button: \"Delete\", $: [button({ color: \"error\", variant: \"solid\" })] }\n */\nfunction button(\n props: {\n color?: ValueOrState<ThemeColor>;\n variant?: ButtonVariant;\n size?: ButtonSize;\n } = {},\n): PartialElement {\n const variant = props.variant ?? \"outline\";\n if (variant === \"ghost\") {\n return buttonGhost({ color: props.color, size: props.size });\n }\n\n const color = toState(props.color ?? \"primary\", \"color\");\n const isSolid = variant === \"solid\";\n const padding = PADDING_STEPS[props.size ?? \"medium\"];\n const fontSize = BUTTON_SIZE_FONT[props.size ?? \"medium\"];\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn(`\"button\" primitive patch must use button tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontSize: (listener) => themeSize(listener, fontSize),\n // Single-line bounded control: block/radius = 1D, inline = 3D.\n paddingBlock: (listener) =>\n themeSpacing(themeDensity(listener) * padding.block),\n paddingInline: (listener) =>\n themeSpacing(themeDensity(listener) * padding.inline),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n width: \"fit-content\",\n display: \"flex\",\n justifyContent: \"center\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 1),\n userSelect: \"none\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n border: \"none\",\n outlineOffset: \"-1px\",\n outlineWidth: \"1px\",\n outline: isSolid\n ? \"none\"\n : (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-0\", color.get(listener))\n : themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-9\", color.get(listener))\n : themeColor(listener, \"inherit\", color.get(listener)),\n transition:\n \"background-color 140ms ease, color 140ms ease, border-color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n color: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-0\", color.get(listener))\n : themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-10\", color.get(listener))\n : themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n \"&[aria-busy=true]\": {\n opacity: 0.7,\n cursor: \"wait\",\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { button };\nexport type { ButtonVariant };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A pill-shaped toggle switch with `role=\"switch\"`; clicking flips the bound\n * `checked` state and slides the thumb. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.checked - Toggle state. Optional `ValueOrState<boolean>`, default false.\n * @param props.accentColor - Color tone when checked (on). Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @param props.color - Color tone when unchecked (off track). Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { button: { span: null }, $: [buttonSwitch({ checked: true })] }\n */\nfunction buttonSwitch(\n props: {\n checked?: ValueOrState<boolean>;\n accentColor?: ValueOrState<ThemeColor>;\n color?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { checked = false } = props;\n\n const check = toState(checked);\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onSchedule: (node) => {\n if (node.tagName !== \"button\") {\n console.warn(`\"buttonSwitch\" primitive patch must use button tag`);\n }\n },\n role: \"switch\",\n ariaChecked: (listener) => check.get(listener),\n dataTone: \"shift-2\",\n onClick: () => check.set(!check.get()),\n style: {\n position: \"relative\",\n display: \"inline-flex\",\n alignItems: \"center\",\n fontSize: (listener) => themeSize(listener),\n border: \"none\",\n outlineWidth: \"1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color.get(listener))}`,\n minWidth: themeSpacing(12),\n minHeight: themeSpacing(6),\n borderRadius: themeSpacing(999),\n paddingLeft: themeSpacing(7),\n paddingRight: themeSpacing(2),\n transition: \"padding-left 0.3s, padding-right 0.3s\",\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n \"& > :first-child\": {\n content: '\"\"',\n position: \"absolute\",\n display: \"inline-flex\",\n alignItems: \"center\",\n left: themeSpacing(0.5),\n top: \"50%\",\n transform: \"translateY(-50%)\",\n transition: \"left 0.3s\",\n width: themeSpacing(5),\n height: themeSpacing(5),\n borderRadius: themeSpacing(999),\n color: (listener) => themeColor(listener, \"text\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"decrease-2\", color.get(listener)),\n },\n \"&[aria-checked=true]\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"increase-3\", accentColor.get(listener)),\n outline: \"none\",\n color: (listener) => themeColor(listener, \"decrease-2\"),\n paddingLeft: themeSpacing(2),\n paddingRight: themeSpacing(7),\n },\n \"&[aria-checked=true] > :first-child\": {\n left: `calc(100% - ${themeSpacing(5.5)})`,\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n };\n}\n\nexport { buttonSwitch };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A grid-based card surface that auto-places known child elements into named\n * regions: `<img>` (image), headings (title), `<p>` (description), `<aside>`\n * (aside), `<div>` (content), and `<footer>` (footer). Typically applied to a\n * `<div>` (any block container).\n *\n * @param props.color - Surface/border color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { div: { h3: \"Title\", p: \"Body\" }, $: [card({ color: \"neutral\" })] }\n */\nfunction card(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n return {\n style: {\n display: \"grid\",\n gridTemplateColumns: \"1fr auto\",\n gridTemplateAreas:\n '\"image image\" \"title aside\" \"desc aside\" \"content content\" \"footer footer\"',\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n outlineOffset: \"-1px\",\n overflow: \"hidden\",\n \"& > img\": {\n gridArea: \"image\",\n width: \"100%\",\n height: \"auto\",\n display: \"block\",\n },\n \"& > :is(h1,h2,h3,h4,h5,h6)\": {\n gridArea: \"title\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n fontWeight: \"600\",\n margin: 0,\n },\n \"& > p\": {\n gridArea: \"desc\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n margin: 0,\n },\n \"& > aside\": {\n gridArea: \"aside\",\n alignSelf: \"center\",\n padding: (listener) => themeSpacing(themeDensity(listener) * 2),\n height: \"auto\",\n },\n \"& > div\": {\n gridArea: \"content\",\n padding: (listener) => themeSpacing(themeDensity(listener) * 4),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n },\n \"& > footer\": {\n gridArea: \"footer\",\n display: \"flex\",\n gap: themeSpacing(2),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n borderTop: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color.get(listener))}`,\n },\n },\n };\n}\n\nexport { card };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles an inline code snippet with a subtle surface background, rounded corners,\n * and shifted tone. Apply to a `<code>` element.\n *\n * @hostTag code\n * @param props.color - Surface/text color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { code: \"npm install\", $: [code({ color: \"neutral\" })] }\n */\nfunction code(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInsert: (node) => {\n if (node.tagName !== \"code\") {\n console.warn(`\"code\" primitive patch must use code tag`);\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n whiteSpace: \"nowrap\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n height: themeSpacing(6),\n paddingInline: themeSpacing(1.5),\n borderRadius: themeSpacing(1),\n },\n };\n}\n\nexport { code };\n","/** Named elevation levels for floating/raised surfaces. */\ntype ElevationLevel = \"low\" | \"medium\" | \"high\";\n\n// Layered soft shadows (a tight contact shadow + a broad ambient one), black at\n// low alpha so the same value reads correctly on both light and dark surfaces\n// without a theme/context lookup.\nconst SHADOWS: Record<ElevationLevel, string> = {\n low: \"0 1px 2px rgba(0,0,0,0.08), 0 4px 10px rgba(0,0,0,0.10)\",\n medium: \"0 2px 4px rgba(0,0,0,0.10), 0 10px 24px rgba(0,0,0,0.14)\",\n high: \"0 6px 12px rgba(0,0,0,0.14), 0 24px 48px rgba(0,0,0,0.20)\",\n};\n\n/**\n * Shared box-shadow value for a named elevation level. Used by floating/raised\n * surface patches (popover, menu, dialog, drawer, toast, tooltip, combobox/\n * selectBox dropdown, datePicker popup, fab) so elevation reads consistently\n * across the library instead of each patch picking its own shadow.\n */\nfunction elevation(level: ElevationLevel): string {\n return SHADOWS[level];\n}\n\nexport { elevation };\nexport type { ElevationLevel };\n","type Prettify<T> = {\n [K in keyof T]: T[K];\n} & {};\n\nexport type Alignment = 'start' | 'end';\nexport type Side = 'top' | 'right' | 'bottom' | 'left';\nexport type AlignedPlacement = `${Side}-${Alignment}`;\nexport type Placement = Prettify<Side | AlignedPlacement>;\nexport type Strategy = 'absolute' | 'fixed';\nexport type Axis = 'x' | 'y';\nexport type Coords = {[key in Axis]: number};\nexport type Length = 'width' | 'height';\nexport type Dimensions = {[key in Length]: number};\nexport type SideObject = {[key in Side]: number};\nexport type Rect = Prettify<Coords & Dimensions>;\nexport type Padding = number | Prettify<Partial<SideObject>>;\nexport type ClientRectObject = Prettify<Rect & SideObject>;\n\nexport interface ElementRects {\n reference: Rect;\n floating: Rect;\n}\n\n/**\n * Custom positioning reference element.\n * @see https://floating-ui.com/docs/virtual-elements\n */\nexport interface VirtualElement {\n getBoundingClientRect(): ClientRectObject;\n getClientRects?(): Array<ClientRectObject>;\n contextElement?: any;\n}\n\nexport const sides: Side[] = ['top', 'right', 'bottom', 'left'];\nexport const alignments: Alignment[] = ['start', 'end'];\nexport const placements: Placement[] = sides.reduce(\n (acc: Placement[], side) =>\n acc.concat(side, `${side}-${alignments[0]}`, `${side}-${alignments[1]}`),\n [],\n);\n\nexport const min = Math.min;\nexport const max = Math.max;\nexport const round = Math.round;\nexport const floor = Math.floor;\nexport const createCoords = (v: number) => ({x: v, y: v});\n\nconst oppositeSideMap = {\n left: 'right',\n right: 'left',\n bottom: 'top',\n top: 'bottom',\n};\n\nexport function clamp(start: number, value: number, end: number): number {\n return max(start, min(value, end));\n}\n\nexport function evaluate<T, P>(value: T | ((param: P) => T), param: P): T {\n return typeof value === 'function'\n ? (value as (param: P) => T)(param)\n : value;\n}\n\nexport function getSide(placement: Placement): Side {\n return placement.split('-')[0] as Side;\n}\n\nexport function getAlignment(placement: Placement): Alignment | undefined {\n return placement.split('-')[1] as Alignment | undefined;\n}\n\nexport function getOppositeAxis(axis: Axis): Axis {\n return axis === 'x' ? 'y' : 'x';\n}\n\nexport function getAxisLength(axis: Axis): Length {\n return axis === 'y' ? 'height' : 'width';\n}\n\nexport function getSideAxis(placement: Placement): Axis {\n const firstChar = placement[0];\n return firstChar === 't' || firstChar === 'b' ? 'y' : 'x';\n}\n\nexport function getAlignmentAxis(placement: Placement): Axis {\n return getOppositeAxis(getSideAxis(placement));\n}\n\nexport function getAlignmentSides(\n placement: Placement,\n rects: ElementRects,\n rtl = false,\n): [Side, Side] {\n const alignment = getAlignment(placement);\n const alignmentAxis = getAlignmentAxis(placement);\n const length = getAxisLength(alignmentAxis);\n\n let mainAlignmentSide: Side =\n alignmentAxis === 'x'\n ? alignment === (rtl ? 'end' : 'start')\n ? 'right'\n : 'left'\n : alignment === 'start'\n ? 'bottom'\n : 'top';\n\n if (rects.reference[length] > rects.floating[length]) {\n mainAlignmentSide = getOppositePlacement(mainAlignmentSide);\n }\n\n return [mainAlignmentSide, getOppositePlacement(mainAlignmentSide)];\n}\n\nexport function getExpandedPlacements(placement: Placement): Array<Placement> {\n const oppositePlacement = getOppositePlacement(placement);\n\n return [\n getOppositeAlignmentPlacement(placement),\n oppositePlacement,\n getOppositeAlignmentPlacement(oppositePlacement),\n ];\n}\n\nexport function getOppositeAlignmentPlacement<T extends string>(\n placement: T,\n): T {\n return placement.includes('start')\n ? (placement.replace('start', 'end') as T)\n : (placement.replace('end', 'start') as T);\n}\n\nconst lrPlacement: Placement[] = ['left', 'right'];\nconst rlPlacement: Placement[] = ['right', 'left'];\nconst tbPlacement: Placement[] = ['top', 'bottom'];\nconst btPlacement: Placement[] = ['bottom', 'top'];\n\nfunction getSideList(side: Side, isStart: boolean, rtl?: boolean): Placement[] {\n switch (side) {\n case 'top':\n case 'bottom':\n if (rtl) return isStart ? rlPlacement : lrPlacement;\n return isStart ? lrPlacement : rlPlacement;\n case 'left':\n case 'right':\n return isStart ? tbPlacement : btPlacement;\n default:\n return [];\n }\n}\n\nexport function getOppositeAxisPlacements(\n placement: Placement,\n flipAlignment: boolean,\n direction: 'none' | Alignment,\n rtl?: boolean,\n): Placement[] {\n const alignment = getAlignment(placement);\n let list = getSideList(getSide(placement), direction === 'start', rtl);\n\n if (alignment) {\n list = list.map((side) => `${side}-${alignment}` as Placement);\n\n if (flipAlignment) {\n list = list.concat(list.map(getOppositeAlignmentPlacement));\n }\n }\n\n return list;\n}\n\nexport function getOppositePlacement<T extends string>(placement: T): T {\n const side = getSide(placement as Placement);\n return (oppositeSideMap[side] + placement.slice(side.length)) as T;\n}\n\nexport function expandPaddingObject(padding: Partial<SideObject>): SideObject {\n return {top: 0, right: 0, bottom: 0, left: 0, ...padding};\n}\n\nexport function getPaddingObject(padding: Padding): SideObject {\n return typeof padding !== 'number'\n ? expandPaddingObject(padding)\n : {top: padding, right: padding, bottom: padding, left: padding};\n}\n\nexport function rectToClientRect(rect: Rect): ClientRectObject {\n const {x, y, width, height} = rect;\n return {\n width,\n height,\n top: y,\n left: x,\n right: x + width,\n bottom: y + height,\n x,\n y,\n };\n}\n","import type {Coords, ElementRects, Placement} from '@floating-ui/utils';\nimport {\n getAlignment,\n getAlignmentAxis,\n getAxisLength,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nexport function computeCoordsFromPlacement(\n {reference, floating}: ElementRects,\n placement: Placement,\n rtl?: boolean,\n): Coords {\n const sideAxis = getSideAxis(placement);\n const alignmentAxis = getAlignmentAxis(placement);\n const alignLength = getAxisLength(alignmentAxis);\n const side = getSide(placement);\n const isVertical = sideAxis === 'y';\n\n const commonX = reference.x + reference.width / 2 - floating.width / 2;\n const commonY = reference.y + reference.height / 2 - floating.height / 2;\n const commonAlign = reference[alignLength] / 2 - floating[alignLength] / 2;\n\n let coords: Coords;\n switch (side) {\n case 'top':\n coords = {x: commonX, y: reference.y - floating.height};\n break;\n case 'bottom':\n coords = {x: commonX, y: reference.y + reference.height};\n break;\n case 'right':\n coords = {x: reference.x + reference.width, y: commonY};\n break;\n case 'left':\n coords = {x: reference.x - floating.width, y: commonY};\n break;\n default:\n coords = {x: reference.x, y: reference.y};\n }\n\n switch (getAlignment(placement)) {\n case 'start':\n coords[alignmentAxis] -= commonAlign * (rtl && isVertical ? -1 : 1);\n break;\n case 'end':\n coords[alignmentAxis] += commonAlign * (rtl && isVertical ? -1 : 1);\n break;\n default:\n }\n\n return coords;\n}\n","import type {Padding, SideObject} from '@floating-ui/utils';\nimport {evaluate, getPaddingObject, rectToClientRect} from '@floating-ui/utils';\n\nimport type {\n Boundary,\n Derivable,\n ElementContext,\n MiddlewareState,\n RootBoundary,\n} from './types';\n\nexport interface DetectOverflowOptions {\n /**\n * The clipping element(s) or area in which overflow will be checked.\n * @default 'clippingAncestors'\n */\n boundary?: Boundary;\n /**\n * The root clipping area in which overflow will be checked.\n * @default 'viewport'\n */\n rootBoundary?: RootBoundary;\n /**\n * The element in which overflow is being checked relative to a boundary.\n * @default 'floating'\n */\n elementContext?: ElementContext;\n /**\n * Whether to check for overflow using the alternate element's boundary\n * (`clippingAncestors` boundary only).\n * @default false\n */\n altBoundary?: boolean;\n /**\n * Virtual padding for the resolved overflow detection offsets.\n * @default 0\n */\n padding?: Padding;\n}\n\n/**\n * Resolves with an object of overflow side offsets that determine how much the\n * element is overflowing a given clipping boundary on each side.\n * - positive = overflowing the boundary by that number of pixels\n * - negative = how many pixels left before it will overflow\n * - 0 = lies flush with the boundary\n * @see https://floating-ui.com/docs/detectOverflow\n */\nexport async function detectOverflow(\n state: MiddlewareState,\n options: DetectOverflowOptions | Derivable<DetectOverflowOptions> = {},\n): Promise<SideObject> {\n const {x, y, platform, rects, elements, strategy} = state;\n\n const {\n boundary = 'clippingAncestors',\n rootBoundary = 'viewport',\n elementContext = 'floating',\n altBoundary = false,\n padding = 0,\n } = evaluate(options, state);\n\n const paddingObject = getPaddingObject(padding);\n const altContext = elementContext === 'floating' ? 'reference' : 'floating';\n const element = elements[altBoundary ? altContext : elementContext];\n\n const clippingClientRect = rectToClientRect(\n await platform.getClippingRect({\n element:\n (await platform.isElement?.(element)) ?? true\n ? element\n : element.contextElement ||\n (await platform.getDocumentElement?.(elements.floating)),\n boundary,\n rootBoundary,\n strategy,\n }),\n );\n\n const rect =\n elementContext === 'floating'\n ? {x, y, width: rects.floating.width, height: rects.floating.height}\n : rects.reference;\n\n const offsetParent = await platform.getOffsetParent?.(elements.floating);\n const offsetScale = (await platform.isElement?.(offsetParent))\n ? (await platform.getScale?.(offsetParent)) || {x: 1, y: 1}\n : {x: 1, y: 1};\n\n const elementClientRect = rectToClientRect(\n platform.convertOffsetParentRelativeRectToViewportRelativeRect\n ? await platform.convertOffsetParentRelativeRectToViewportRelativeRect({\n elements,\n rect,\n offsetParent,\n strategy,\n })\n : rect,\n );\n\n return {\n top:\n (clippingClientRect.top - elementClientRect.top + paddingObject.top) /\n offsetScale.y,\n bottom:\n (elementClientRect.bottom -\n clippingClientRect.bottom +\n paddingObject.bottom) /\n offsetScale.y,\n left:\n (clippingClientRect.left - elementClientRect.left + paddingObject.left) /\n offsetScale.x,\n right:\n (elementClientRect.right -\n clippingClientRect.right +\n paddingObject.right) /\n offsetScale.x,\n };\n}\n","import {computeCoordsFromPlacement} from './computeCoordsFromPlacement';\nimport {detectOverflow} from './detectOverflow';\nimport type {\n ComputePosition,\n Middleware,\n MiddlewareData,\n Platform,\n} from './types';\n\n// Maximum number of resets that can occur before bailing to avoid infinite reset loops.\nconst MAX_RESET_COUNT = 50;\n\n/**\n * Computes the `x` and `y` coordinates that will place the floating element\n * next to a given reference element.\n *\n * This export does not have any `platform` interface logic. You will need to\n * write one for the platform you are using Floating UI with.\n */\nexport const computePosition: ComputePosition = async (\n reference,\n floating,\n config,\n) => {\n const {\n placement = 'bottom',\n strategy = 'absolute',\n middleware = [],\n platform,\n } = config;\n\n const platformWithDetectOverflow = (\n platform.detectOverflow ? platform : {...platform, detectOverflow}\n ) as Platform & {detectOverflow: typeof detectOverflow};\n const rtl = await platform.isRTL?.(floating);\n\n let rects = await platform.getElementRects({reference, floating, strategy});\n let {x, y} = computeCoordsFromPlacement(rects, placement, rtl);\n let statefulPlacement = placement;\n let resetCount = 0;\n\n const middlewareData: MiddlewareData = {};\n\n for (let i = 0; i < middleware.length; i++) {\n const currentMiddleware = middleware[i] as Middleware | undefined;\n\n if (!currentMiddleware) {\n continue;\n }\n\n const {name, fn} = currentMiddleware;\n\n const {\n x: nextX,\n y: nextY,\n data,\n reset,\n } = await fn({\n x,\n y,\n initialPlacement: placement,\n placement: statefulPlacement,\n strategy,\n middlewareData,\n rects,\n platform: platformWithDetectOverflow,\n elements: {reference, floating},\n });\n\n x = nextX ?? x;\n y = nextY ?? y;\n\n middlewareData[name] = {\n ...middlewareData[name],\n ...data,\n };\n\n if (reset && resetCount < MAX_RESET_COUNT) {\n resetCount++;\n\n if (typeof reset === 'object') {\n if (reset.placement) {\n statefulPlacement = reset.placement;\n }\n\n if (reset.rects) {\n rects =\n reset.rects === true\n ? await platform.getElementRects({reference, floating, strategy})\n : reset.rects;\n }\n\n ({x, y} = computeCoordsFromPlacement(rects, statefulPlacement, rtl));\n }\n\n i = -1;\n }\n }\n\n return {\n x,\n y,\n placement: statefulPlacement,\n strategy,\n middlewareData,\n };\n};\n","import type {Padding} from '@floating-ui/utils';\nimport {\n clamp,\n evaluate,\n getAlignment,\n getAlignmentAxis,\n getAxisLength,\n getPaddingObject,\n min as mathMin,\n} from '@floating-ui/utils';\n\nimport type {Derivable, Middleware} from '../types';\n\nexport interface ArrowOptions {\n /**\n * The arrow element to be positioned.\n * @default undefined\n */\n element: any;\n /**\n * The padding between the arrow element and the floating element edges.\n * Useful when the floating element has rounded corners.\n * @default 0\n */\n padding?: Padding;\n}\n\n/**\n * Provides data to position an inner element of the floating element so that it\n * appears centered to the reference element.\n * @see https://floating-ui.com/docs/arrow\n */\nexport const arrow = (\n options: ArrowOptions | Derivable<ArrowOptions>,\n): Middleware => ({\n name: 'arrow',\n options,\n async fn(state) {\n const {x, y, placement, rects, platform, elements, middlewareData} = state;\n // Since `element` is required, we don't Partial<> the type.\n const {element, padding = 0} = evaluate(options, state) || {};\n\n if (element == null) {\n return {};\n }\n\n const paddingObject = getPaddingObject(padding);\n const coords = {x, y};\n const axis = getAlignmentAxis(placement);\n const length = getAxisLength(axis);\n const arrowDimensions = await platform.getDimensions(element);\n const isYAxis = axis === 'y';\n const minProp = isYAxis ? 'top' : 'left';\n const maxProp = isYAxis ? 'bottom' : 'right';\n const clientProp = isYAxis ? 'clientHeight' : 'clientWidth';\n\n const endDiff =\n rects.reference[length] +\n rects.reference[axis] -\n coords[axis] -\n rects.floating[length];\n const startDiff = coords[axis] - rects.reference[axis];\n\n const arrowOffsetParent = await platform.getOffsetParent?.(element);\n let clientSize = arrowOffsetParent ? arrowOffsetParent[clientProp] : 0;\n\n // DOM platform can return `window` as the `offsetParent`.\n if (!clientSize || !(await platform.isElement?.(arrowOffsetParent))) {\n clientSize = elements.floating[clientProp] || rects.floating[length];\n }\n\n const centerToReference = endDiff / 2 - startDiff / 2;\n\n // If the padding is large enough that it causes the arrow to no longer be\n // centered, modify the padding so that it is centered.\n const largestPossiblePadding =\n clientSize / 2 - arrowDimensions[length] / 2 - 1;\n const minPadding = mathMin(paddingObject[minProp], largestPossiblePadding);\n const maxPadding = mathMin(paddingObject[maxProp], largestPossiblePadding);\n\n // Make sure the arrow doesn't overflow the floating element if the center\n // point is outside the floating element's bounds.\n const min = minPadding;\n const max = clientSize - arrowDimensions[length] - maxPadding;\n const center =\n clientSize / 2 - arrowDimensions[length] / 2 + centerToReference;\n const offset = clamp(min, center, max);\n\n // If the reference is small enough that the arrow's padding causes it to\n // to point to nothing for an aligned placement, adjust the offset of the\n // floating element itself. To ensure `shift()` continues to take action,\n // a single reset is performed when this is true.\n const shouldAddOffset =\n !middlewareData.arrow &&\n getAlignment(placement) != null &&\n center !== offset &&\n rects.reference[length] / 2 -\n (center < min ? minPadding : maxPadding) -\n arrowDimensions[length] / 2 <\n 0;\n const alignmentOffset = shouldAddOffset\n ? center < min\n ? center - min\n : center - max\n : 0;\n\n return {\n [axis]: coords[axis] + alignmentOffset,\n data: {\n [axis]: offset,\n centerOffset: center - offset - alignmentOffset,\n ...(shouldAddOffset && {alignmentOffset}),\n },\n reset: shouldAddOffset,\n };\n },\n});\n","import type {Alignment, Placement} from '@floating-ui/utils';\nimport {\n evaluate,\n getAlignment,\n getAlignmentSides,\n getOppositeAlignmentPlacement,\n getSide,\n placements as ALL_PLACEMENTS,\n} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware} from '../types';\n\nexport function getPlacementList(\n alignment: Alignment | null,\n autoAlignment: boolean,\n allowedPlacements: Array<Placement>,\n) {\n const allowedPlacementsSortedByAlignment = alignment\n ? [\n ...allowedPlacements.filter(\n (placement) => getAlignment(placement) === alignment,\n ),\n ...allowedPlacements.filter(\n (placement) => getAlignment(placement) !== alignment,\n ),\n ]\n : allowedPlacements.filter((placement) => getSide(placement) === placement);\n\n return allowedPlacementsSortedByAlignment.filter((placement) => {\n if (alignment) {\n return (\n getAlignment(placement) === alignment ||\n (autoAlignment\n ? getOppositeAlignmentPlacement(placement) !== placement\n : false)\n );\n }\n\n return true;\n });\n}\n\nexport interface AutoPlacementOptions extends DetectOverflowOptions {\n /**\n * The axis that runs along the alignment of the floating element. Determines\n * whether to check for most space along this axis.\n * @default false\n */\n crossAxis?: boolean;\n /**\n * Choose placements with a particular alignment.\n * @default undefined\n */\n alignment?: Alignment | null;\n /**\n * Whether to choose placements with the opposite alignment if the preferred\n * alignment does not fit.\n * @default true\n */\n autoAlignment?: boolean;\n /**\n * Which placements are allowed to be chosen. Placements must be within the\n * `alignment` option if explicitly set.\n * @default allPlacements (variable)\n */\n allowedPlacements?: Array<Placement>;\n}\n\n/**\n * Optimizes the visibility of the floating element by choosing the placement\n * that has the most space available automatically, without needing to specify a\n * preferred placement. Alternative to `flip`.\n * @see https://floating-ui.com/docs/autoPlacement\n */\nexport const autoPlacement = (\n options: AutoPlacementOptions | Derivable<AutoPlacementOptions> = {},\n): Middleware => ({\n name: 'autoPlacement',\n options,\n async fn(state) {\n const {rects, middlewareData, placement, platform, elements} = state;\n\n const {\n crossAxis = false,\n alignment,\n allowedPlacements = ALL_PLACEMENTS,\n autoAlignment = true,\n ...detectOverflowOptions\n } = evaluate(options, state);\n\n const placements =\n alignment !== undefined || allowedPlacements === ALL_PLACEMENTS\n ? getPlacementList(alignment || null, autoAlignment, allowedPlacements)\n : allowedPlacements;\n\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n\n const currentIndex = middlewareData.autoPlacement?.index || 0;\n const currentPlacement = placements[currentIndex];\n\n if (currentPlacement == null) {\n return {};\n }\n\n const alignmentSides = getAlignmentSides(\n currentPlacement,\n rects,\n await platform.isRTL?.(elements.floating),\n );\n\n // Make `computeCoords` start from the right place.\n if (placement !== currentPlacement) {\n return {\n reset: {\n placement: placements[0],\n },\n };\n }\n\n const currentOverflows = [\n overflow[getSide(currentPlacement)],\n overflow[alignmentSides[0]],\n overflow[alignmentSides[1]],\n ];\n\n const allOverflows = [\n ...(middlewareData.autoPlacement?.overflows || []),\n {placement: currentPlacement, overflows: currentOverflows},\n ];\n\n const nextPlacement = placements[currentIndex + 1];\n\n // There are more placements to check.\n if (nextPlacement) {\n return {\n data: {\n index: currentIndex + 1,\n overflows: allOverflows,\n },\n reset: {\n placement: nextPlacement,\n },\n };\n }\n\n const placementsSortedByMostSpace = allOverflows\n .map((d) => {\n const alignment = getAlignment(d.placement);\n return [\n d.placement,\n alignment && crossAxis\n ? // Check along the mainAxis and main crossAxis side.\n d.overflows.slice(0, 2).reduce((acc, v) => acc + v, 0)\n : // Check only the mainAxis.\n d.overflows[0],\n d.overflows,\n ] as const;\n })\n .sort((a, b) => a[1] - b[1]);\n\n const placementsThatFitOnEachSide = placementsSortedByMostSpace.filter(\n (d) =>\n d[2]\n .slice(\n 0,\n // Aligned placements should not check their opposite crossAxis\n // side.\n getAlignment(d[0]) ? 2 : 3,\n )\n .every((v) => v <= 0),\n );\n\n const resetPlacement =\n placementsThatFitOnEachSide[0]?.[0] || placementsSortedByMostSpace[0][0];\n\n if (resetPlacement !== placement) {\n return {\n data: {\n index: currentIndex + 1,\n overflows: allOverflows,\n },\n reset: {\n placement: resetPlacement,\n },\n };\n }\n\n return {};\n },\n});\n","import type {Placement} from '@floating-ui/utils';\nimport {\n evaluate,\n getAlignmentSides,\n getExpandedPlacements,\n getOppositeAxisPlacements,\n getOppositePlacement,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware} from '../types';\n\nexport interface FlipOptions extends DetectOverflowOptions {\n /**\n * The axis that runs along the side of the floating element. Determines\n * whether overflow along this axis is checked to perform a flip.\n * @default true\n */\n mainAxis?: boolean;\n /**\n * The axis that runs along the alignment of the floating element. Determines\n * whether overflow along this axis is checked to perform a flip.\n * - `true`: Whether to check cross axis overflow for both side and alignment flipping.\n * - `false`: Whether to disable all cross axis overflow checking.\n * - `'alignment'`: Whether to check cross axis overflow for alignment flipping only.\n * @default true\n */\n crossAxis?: boolean | 'alignment';\n /**\n * Placements to try sequentially if the preferred `placement` does not fit.\n * @default [oppositePlacement] (computed)\n */\n fallbackPlacements?: Array<Placement>;\n /**\n * What strategy to use when no placements fit.\n * @default 'bestFit'\n */\n fallbackStrategy?: 'bestFit' | 'initialPlacement';\n /**\n * Whether to allow fallback to the perpendicular axis of the preferred\n * placement, and if so, which side direction along the axis to prefer.\n * @default 'none' (disallow fallback)\n */\n fallbackAxisSideDirection?: 'none' | 'start' | 'end';\n /**\n * Whether to flip to placements with the opposite alignment if they fit\n * better.\n * @default true\n */\n flipAlignment?: boolean;\n}\n\n/**\n * Optimizes the visibility of the floating element by flipping the `placement`\n * in order to keep it in view when the preferred placement(s) will overflow the\n * clipping boundary. Alternative to `autoPlacement`.\n * @see https://floating-ui.com/docs/flip\n */\nexport const flip = (\n options: FlipOptions | Derivable<FlipOptions> = {},\n): Middleware => ({\n name: 'flip',\n options,\n async fn(state) {\n const {\n placement,\n middlewareData,\n rects,\n initialPlacement,\n platform,\n elements,\n } = state;\n\n const {\n mainAxis: checkMainAxis = true,\n crossAxis: checkCrossAxis = true,\n fallbackPlacements: specifiedFallbackPlacements,\n fallbackStrategy = 'bestFit',\n fallbackAxisSideDirection = 'none',\n flipAlignment = true,\n ...detectOverflowOptions\n } = evaluate(options, state);\n\n // If a reset by the arrow was caused due to an alignment offset being\n // added, we should skip any logic now since `flip()` has already done its\n // work.\n // https://github.com/floating-ui/floating-ui/issues/2549#issuecomment-1719601643\n if (middlewareData.arrow?.alignmentOffset) {\n return {};\n }\n\n const side = getSide(placement);\n const initialSideAxis = getSideAxis(initialPlacement);\n const isBasePlacement = getSide(initialPlacement) === initialPlacement;\n const rtl = await platform.isRTL?.(elements.floating);\n\n const fallbackPlacements =\n specifiedFallbackPlacements ||\n (isBasePlacement || !flipAlignment\n ? [getOppositePlacement(initialPlacement)]\n : getExpandedPlacements(initialPlacement));\n\n const hasFallbackAxisSideDirection = fallbackAxisSideDirection !== 'none';\n\n if (!specifiedFallbackPlacements && hasFallbackAxisSideDirection) {\n fallbackPlacements.push(\n ...getOppositeAxisPlacements(\n initialPlacement,\n flipAlignment,\n fallbackAxisSideDirection,\n rtl,\n ),\n );\n }\n\n const placements = [initialPlacement, ...fallbackPlacements];\n\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n\n const overflows = [];\n let overflowsData = middlewareData.flip?.overflows || [];\n\n if (checkMainAxis) {\n overflows.push(overflow[side]);\n }\n\n if (checkCrossAxis) {\n const sides = getAlignmentSides(placement, rects, rtl);\n overflows.push(overflow[sides[0]], overflow[sides[1]]);\n }\n\n overflowsData = [...overflowsData, {placement, overflows}];\n\n // One or more sides is overflowing.\n if (!overflows.every((side) => side <= 0)) {\n const nextIndex = (middlewareData.flip?.index || 0) + 1;\n const nextPlacement = placements[nextIndex];\n\n if (nextPlacement) {\n const ignoreCrossAxisOverflow =\n checkCrossAxis === 'alignment'\n ? initialSideAxis !== getSideAxis(nextPlacement)\n : false;\n\n if (\n !ignoreCrossAxisOverflow ||\n // We leave the current main axis only if every placement on that axis\n // overflows the main axis.\n overflowsData.every((d) =>\n getSideAxis(d.placement) === initialSideAxis\n ? d.overflows[0] > 0\n : true,\n )\n ) {\n // Try next placement and re-run the lifecycle.\n return {\n data: {\n index: nextIndex,\n overflows: overflowsData,\n },\n reset: {\n placement: nextPlacement,\n },\n };\n }\n }\n\n // First, find the candidates that fit on the mainAxis side of overflow,\n // then find the placement that fits the best on the main crossAxis side.\n let resetPlacement = overflowsData\n .filter((d) => d.overflows[0] <= 0)\n .sort((a, b) => a.overflows[1] - b.overflows[1])[0]?.placement;\n\n // Otherwise fallback.\n if (!resetPlacement) {\n switch (fallbackStrategy) {\n case 'bestFit': {\n const placement = overflowsData\n .filter((d) => {\n if (hasFallbackAxisSideDirection) {\n const currentSideAxis = getSideAxis(d.placement);\n return (\n currentSideAxis === initialSideAxis ||\n // Create a bias to the `y` side axis due to horizontal\n // reading directions favoring greater width.\n currentSideAxis === 'y'\n );\n }\n return true;\n })\n .map(\n (d) =>\n [\n d.placement,\n d.overflows\n .filter((overflow) => overflow > 0)\n .reduce((acc, overflow) => acc + overflow, 0),\n ] as const,\n )\n .sort((a, b) => a[1] - b[1])[0]?.[0];\n if (placement) {\n resetPlacement = placement;\n }\n break;\n }\n case 'initialPlacement':\n resetPlacement = initialPlacement;\n break;\n default:\n }\n }\n\n if (placement !== resetPlacement) {\n return {\n reset: {\n placement: resetPlacement,\n },\n };\n }\n }\n\n return {};\n },\n});\n","import type {Rect, SideObject} from '@floating-ui/utils';\nimport {evaluate, sides} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware} from '../types';\n\nfunction getSideOffsets(overflow: SideObject, rect: Rect) {\n return {\n top: overflow.top - rect.height,\n right: overflow.right - rect.width,\n bottom: overflow.bottom - rect.height,\n left: overflow.left - rect.width,\n };\n}\n\nfunction isAnySideFullyClipped(overflow: SideObject) {\n return sides.some((side) => overflow[side] >= 0);\n}\n\nexport interface HideOptions extends DetectOverflowOptions {\n /**\n * The strategy used to determine when to hide the floating element.\n */\n strategy?: 'referenceHidden' | 'escaped';\n}\n\n/**\n * Provides data to hide the floating element in applicable situations, such as\n * when it is not in the same clipping context as the reference element.\n * @see https://floating-ui.com/docs/hide\n */\nexport const hide = (\n options: HideOptions | Derivable<HideOptions> = {},\n): Middleware => ({\n name: 'hide',\n options,\n async fn(state) {\n const {rects, platform} = state;\n\n const {strategy = 'referenceHidden', ...detectOverflowOptions} = evaluate(\n options,\n state,\n );\n\n switch (strategy) {\n case 'referenceHidden': {\n const overflow = await platform.detectOverflow(state, {\n ...detectOverflowOptions,\n elementContext: 'reference',\n });\n const offsets = getSideOffsets(overflow, rects.reference);\n return {\n data: {\n referenceHiddenOffsets: offsets,\n referenceHidden: isAnySideFullyClipped(offsets),\n },\n };\n }\n case 'escaped': {\n const overflow = await platform.detectOverflow(state, {\n ...detectOverflowOptions,\n altBoundary: true,\n });\n const offsets = getSideOffsets(overflow, rects.floating);\n return {\n data: {\n escapedOffsets: offsets,\n escaped: isAnySideFullyClipped(offsets),\n },\n };\n }\n default: {\n return {};\n }\n }\n },\n});\n","import type {ClientRectObject, Padding} from '@floating-ui/utils';\nimport {\n evaluate,\n getPaddingObject,\n getSide,\n getSideAxis,\n max,\n min,\n rectToClientRect,\n} from '@floating-ui/utils';\n\nimport type {Derivable, Middleware} from '../types';\n\nfunction getBoundingRect(rects: Array<ClientRectObject>) {\n const minX = min(...rects.map((rect) => rect.left));\n const minY = min(...rects.map((rect) => rect.top));\n const maxX = max(...rects.map((rect) => rect.right));\n const maxY = max(...rects.map((rect) => rect.bottom));\n return {\n x: minX,\n y: minY,\n width: maxX - minX,\n height: maxY - minY,\n };\n}\n\nexport function getRectsByLine(rects: Array<ClientRectObject>) {\n const sortedRects = rects.slice().sort((a, b) => a.y - b.y);\n const groups = [];\n let prevRect: ClientRectObject | null = null;\n for (let i = 0; i < sortedRects.length; i++) {\n const rect = sortedRects[i];\n if (!prevRect || rect.y - prevRect.y > prevRect.height / 2) {\n groups.push([rect]);\n } else {\n groups[groups.length - 1].push(rect);\n }\n prevRect = rect;\n }\n return groups.map((rect) => rectToClientRect(getBoundingRect(rect)));\n}\n\nexport interface InlineOptions {\n /**\n * Viewport-relative `x` coordinate to choose a `ClientRect`.\n * @default undefined\n */\n x?: number;\n /**\n * Viewport-relative `y` coordinate to choose a `ClientRect`.\n * @default undefined\n */\n y?: number;\n /**\n * Represents the padding around a disjoined rect when choosing it.\n * @default 2\n */\n padding?: Padding;\n}\n\n/**\n * Provides improved positioning for inline reference elements that can span\n * over multiple lines, such as hyperlinks or range selections.\n * @see https://floating-ui.com/docs/inline\n */\nexport const inline = (\n options: InlineOptions | Derivable<InlineOptions> = {},\n): Middleware => ({\n name: 'inline',\n options,\n async fn(state) {\n const {placement, elements, rects, platform, strategy} = state;\n // A MouseEvent's client{X,Y} coords can be up to 2 pixels off a\n // ClientRect's bounds, despite the event listener being triggered. A\n // padding of 2 seems to handle this issue.\n const {padding = 2, x, y} = evaluate(options, state);\n\n const nativeClientRects = Array.from(\n (await platform.getClientRects?.(elements.reference)) || [],\n );\n\n const clientRects = getRectsByLine(nativeClientRects);\n const fallback = rectToClientRect(getBoundingRect(nativeClientRects));\n const paddingObject = getPaddingObject(padding);\n\n function getBoundingClientRect() {\n // There are two rects and they are disjoined.\n if (\n clientRects.length === 2 &&\n clientRects[0].left > clientRects[1].right &&\n x != null &&\n y != null\n ) {\n // Find the first rect in which the point is fully inside.\n return (\n clientRects.find(\n (rect) =>\n x > rect.left - paddingObject.left &&\n x < rect.right + paddingObject.right &&\n y > rect.top - paddingObject.top &&\n y < rect.bottom + paddingObject.bottom,\n ) || fallback\n );\n }\n\n // There are 2 or more connected rects.\n if (clientRects.length >= 2) {\n if (getSideAxis(placement) === 'y') {\n const firstRect = clientRects[0];\n const lastRect = clientRects[clientRects.length - 1];\n const isTop = getSide(placement) === 'top';\n\n const top = firstRect.top;\n const bottom = lastRect.bottom;\n const left = isTop ? firstRect.left : lastRect.left;\n const right = isTop ? firstRect.right : lastRect.right;\n const width = right - left;\n const height = bottom - top;\n\n return {\n top,\n bottom,\n left,\n right,\n width,\n height,\n x: left,\n y: top,\n };\n }\n\n const isLeftSide = getSide(placement) === 'left';\n const maxRight = max(...clientRects.map((rect) => rect.right));\n const minLeft = min(...clientRects.map((rect) => rect.left));\n const measureRects = clientRects.filter((rect) =>\n isLeftSide ? rect.left === minLeft : rect.right === maxRight,\n );\n\n const top = measureRects[0].top;\n const bottom = measureRects[measureRects.length - 1].bottom;\n const left = minLeft;\n const right = maxRight;\n const width = right - left;\n const height = bottom - top;\n\n return {\n top,\n bottom,\n left,\n right,\n width,\n height,\n x: left,\n y: top,\n };\n }\n\n return fallback;\n }\n\n const resetRects = await platform.getElementRects({\n reference: {getBoundingClientRect},\n floating: elements.floating,\n strategy,\n });\n\n if (\n rects.reference.x !== resetRects.reference.x ||\n rects.reference.y !== resetRects.reference.y ||\n rects.reference.width !== resetRects.reference.width ||\n rects.reference.height !== resetRects.reference.height\n ) {\n return {\n reset: {\n rects: resetRects,\n },\n };\n }\n\n return {};\n },\n});\n","export const originSides = new Set(['left', 'top']);\n","import {\n type Coords,\n evaluate,\n getAlignment,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nimport {originSides} from '../constants';\nimport type {Derivable, Middleware, MiddlewareState} from '../types';\n\ntype OffsetValue =\n | number\n | {\n /**\n * The axis that runs along the side of the floating element. Represents\n * the distance (gutter or margin) between the reference and floating\n * element.\n * @default 0\n */\n mainAxis?: number;\n /**\n * The axis that runs along the alignment of the floating element.\n * Represents the skidding between the reference and floating element.\n * @default 0\n */\n crossAxis?: number;\n /**\n * The same axis as `crossAxis` but applies only to aligned placements\n * and inverts the `end` alignment. When set to a number, it overrides the\n * `crossAxis` value.\n *\n * A positive number will move the floating element in the direction of\n * the opposite edge to the one that is aligned, while a negative number\n * the reverse.\n * @default null\n */\n alignmentAxis?: number | null;\n };\n\n// For type backwards-compatibility, the `OffsetOptions` type was also\n// Derivable.\nexport type OffsetOptions = OffsetValue | Derivable<OffsetValue>;\n\nexport async function convertValueToCoords(\n state: MiddlewareState,\n options: OffsetOptions,\n): Promise<Coords> {\n const {placement, platform, elements} = state;\n const rtl = await platform.isRTL?.(elements.floating);\n\n const side = getSide(placement);\n const alignment = getAlignment(placement);\n const isVertical = getSideAxis(placement) === 'y';\n const mainAxisMulti = originSides.has(side) ? -1 : 1;\n const crossAxisMulti = rtl && isVertical ? -1 : 1;\n const rawValue = evaluate(options, state);\n\n // eslint-disable-next-line prefer-const\n let {mainAxis, crossAxis, alignmentAxis} =\n typeof rawValue === 'number'\n ? {mainAxis: rawValue, crossAxis: 0, alignmentAxis: null}\n : {\n mainAxis: rawValue.mainAxis || 0,\n crossAxis: rawValue.crossAxis || 0,\n alignmentAxis: rawValue.alignmentAxis,\n };\n\n if (alignment && typeof alignmentAxis === 'number') {\n crossAxis = alignment === 'end' ? alignmentAxis * -1 : alignmentAxis;\n }\n\n return isVertical\n ? {x: crossAxis * crossAxisMulti, y: mainAxis * mainAxisMulti}\n : {x: mainAxis * mainAxisMulti, y: crossAxis * crossAxisMulti};\n}\n\n/**\n * Modifies the placement by translating the floating element along the\n * specified axes.\n * A number (shorthand for `mainAxis` or distance), or an axes configuration\n * object may be passed.\n * @see https://floating-ui.com/docs/offset\n */\nexport const offset = (options: OffsetOptions = 0): Middleware => ({\n name: 'offset',\n options,\n async fn(state) {\n const {x, y, placement, middlewareData} = state;\n const diffCoords = await convertValueToCoords(state, options);\n\n // If the placement is the same and the arrow caused an alignment offset\n // then we don't need to change the positioning coordinates.\n if (\n placement === middlewareData.offset?.placement &&\n middlewareData.arrow?.alignmentOffset\n ) {\n return {};\n }\n\n return {\n x: x + diffCoords.x,\n y: y + diffCoords.y,\n data: {\n ...diffCoords,\n placement,\n },\n };\n },\n});\n","import {\n type Coords,\n clamp,\n evaluate,\n getOppositeAxis,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nimport {originSides} from '../constants';\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware, MiddlewareState} from '../types';\n\nexport interface ShiftOptions extends DetectOverflowOptions {\n /**\n * The axis that runs along the alignment of the floating element. Determines\n * whether overflow along this axis is checked to perform shifting.\n * @default true\n */\n mainAxis?: boolean;\n /**\n * The axis that runs along the side of the floating element. Determines\n * whether overflow along this axis is checked to perform shifting.\n * @default false\n */\n crossAxis?: boolean;\n /**\n * Accepts a function that limits the shifting done in order to prevent\n * detachment.\n */\n limiter?: {\n fn: (state: MiddlewareState) => Coords;\n options?: any;\n };\n}\n\n/**\n * Optimizes the visibility of the floating element by shifting it in order to\n * keep it in view when it will overflow the clipping boundary.\n * @see https://floating-ui.com/docs/shift\n */\nexport const shift = (\n options: ShiftOptions | Derivable<ShiftOptions> = {},\n): Middleware => ({\n name: 'shift',\n options,\n async fn(state) {\n const {x, y, placement, platform} = state;\n\n const {\n mainAxis: checkMainAxis = true,\n crossAxis: checkCrossAxis = false,\n limiter = {fn: ({x, y}: Coords) => ({x, y})},\n ...detectOverflowOptions\n } = evaluate(options, state);\n\n const coords = {x, y};\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n const crossAxis = getSideAxis(getSide(placement));\n const mainAxis = getOppositeAxis(crossAxis);\n\n let mainAxisCoord = coords[mainAxis];\n let crossAxisCoord = coords[crossAxis];\n\n if (checkMainAxis) {\n const minSide = mainAxis === 'y' ? 'top' : 'left';\n const maxSide = mainAxis === 'y' ? 'bottom' : 'right';\n const min = mainAxisCoord + overflow[minSide];\n const max = mainAxisCoord - overflow[maxSide];\n\n mainAxisCoord = clamp(min, mainAxisCoord, max);\n }\n\n if (checkCrossAxis) {\n const minSide = crossAxis === 'y' ? 'top' : 'left';\n const maxSide = crossAxis === 'y' ? 'bottom' : 'right';\n const min = crossAxisCoord + overflow[minSide];\n const max = crossAxisCoord - overflow[maxSide];\n\n crossAxisCoord = clamp(min, crossAxisCoord, max);\n }\n\n const limitedCoords = limiter.fn({\n ...state,\n [mainAxis]: mainAxisCoord,\n [crossAxis]: crossAxisCoord,\n });\n\n return {\n ...limitedCoords,\n data: {\n x: limitedCoords.x - x,\n y: limitedCoords.y - y,\n enabled: {\n [mainAxis]: checkMainAxis,\n [crossAxis]: checkCrossAxis,\n },\n },\n };\n },\n});\n\ntype LimitShiftOffset =\n | number\n | {\n /**\n * Offset the limiting of the axis that runs along the alignment of the\n * floating element.\n */\n mainAxis?: number;\n /**\n * Offset the limiting of the axis that runs along the side of the\n * floating element.\n */\n crossAxis?: number;\n };\n\nexport interface LimitShiftOptions {\n /**\n * Offset when limiting starts. `0` will limit when the opposite edges of the\n * reference and floating elements are aligned.\n * - positive = start limiting earlier\n * - negative = start limiting later\n */\n offset?: LimitShiftOffset | Derivable<LimitShiftOffset>;\n /**\n * Whether to limit the axis that runs along the alignment of the floating\n * element.\n */\n mainAxis?: boolean;\n /**\n * Whether to limit the axis that runs along the side of the floating element.\n */\n crossAxis?: boolean;\n}\n\n/**\n * Built-in `limiter` that will stop `shift()` at a certain point.\n */\nexport const limitShift = (\n options: LimitShiftOptions | Derivable<LimitShiftOptions> = {},\n): {\n options: any;\n fn: (state: MiddlewareState) => Coords;\n} => ({\n options,\n fn(state) {\n const {x, y, placement, rects, middlewareData} = state;\n\n const {\n offset = 0,\n mainAxis: checkMainAxis = true,\n crossAxis: checkCrossAxis = true,\n } = evaluate(options, state);\n\n const coords = {x, y};\n const crossAxis = getSideAxis(placement);\n const mainAxis = getOppositeAxis(crossAxis);\n\n let mainAxisCoord = coords[mainAxis];\n let crossAxisCoord = coords[crossAxis];\n\n const rawOffset = evaluate(offset, state);\n const computedOffset =\n typeof rawOffset === 'number'\n ? {mainAxis: rawOffset, crossAxis: 0}\n : {mainAxis: 0, crossAxis: 0, ...rawOffset};\n\n if (checkMainAxis) {\n const len = mainAxis === 'y' ? 'height' : 'width';\n const limitMin =\n rects.reference[mainAxis] -\n rects.floating[len] +\n computedOffset.mainAxis;\n const limitMax =\n rects.reference[mainAxis] +\n rects.reference[len] -\n computedOffset.mainAxis;\n\n if (mainAxisCoord < limitMin) {\n mainAxisCoord = limitMin;\n } else if (mainAxisCoord > limitMax) {\n mainAxisCoord = limitMax;\n }\n }\n\n if (checkCrossAxis) {\n const len = mainAxis === 'y' ? 'width' : 'height';\n const isOriginSide = originSides.has(getSide(placement));\n const limitMin =\n rects.reference[crossAxis] -\n rects.floating[len] +\n (isOriginSide ? middlewareData.offset?.[crossAxis] || 0 : 0) +\n (isOriginSide ? 0 : computedOffset.crossAxis);\n const limitMax =\n rects.reference[crossAxis] +\n rects.reference[len] +\n (isOriginSide ? 0 : middlewareData.offset?.[crossAxis] || 0) -\n (isOriginSide ? computedOffset.crossAxis : 0);\n\n if (crossAxisCoord < limitMin) {\n crossAxisCoord = limitMin;\n } else if (crossAxisCoord > limitMax) {\n crossAxisCoord = limitMax;\n }\n }\n\n return {\n [mainAxis]: mainAxisCoord,\n [crossAxis]: crossAxisCoord,\n } as Coords;\n },\n});\n","import {\n evaluate,\n getAlignment,\n getSide,\n getSideAxis,\n max,\n min,\n} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware, MiddlewareState} from '../types';\n\nexport interface SizeOptions extends DetectOverflowOptions {\n /**\n * Function that is called to perform style mutations to the floating element\n * to change its size.\n * @default undefined\n */\n apply?(\n args: MiddlewareState & {\n availableWidth: number;\n availableHeight: number;\n },\n ): void | Promise<void>;\n}\n\n/**\n * Provides data that allows you to change the size of the floating element —\n * for instance, prevent it from overflowing the clipping boundary or match the\n * width of the reference element.\n * @see https://floating-ui.com/docs/size\n */\nexport const size = (\n options: SizeOptions | Derivable<SizeOptions> = {},\n): Middleware => ({\n name: 'size',\n options,\n async fn(state) {\n const {placement, rects, platform, elements} = state;\n\n const {apply = () => {}, ...detectOverflowOptions} = evaluate(\n options,\n state,\n );\n\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n const side = getSide(placement);\n const alignment = getAlignment(placement);\n const isYAxis = getSideAxis(placement) === 'y';\n const {width, height} = rects.floating;\n\n let heightSide: 'top' | 'bottom';\n let widthSide: 'left' | 'right';\n\n if (side === 'top' || side === 'bottom') {\n heightSide = side;\n widthSide =\n alignment ===\n ((await platform.isRTL?.(elements.floating)) ? 'start' : 'end')\n ? 'left'\n : 'right';\n } else {\n widthSide = side;\n heightSide = alignment === 'end' ? 'top' : 'bottom';\n }\n\n const maximumClippingHeight = height - overflow.top - overflow.bottom;\n const maximumClippingWidth = width - overflow.left - overflow.right;\n\n const overflowAvailableHeight = min(\n height - overflow[heightSide],\n maximumClippingHeight,\n );\n const overflowAvailableWidth = min(\n width - overflow[widthSide],\n maximumClippingWidth,\n );\n\n const noShift = !state.middlewareData.shift;\n\n let availableHeight = overflowAvailableHeight;\n let availableWidth = overflowAvailableWidth;\n\n if (state.middlewareData.shift?.enabled.x) {\n availableWidth = maximumClippingWidth;\n }\n if (state.middlewareData.shift?.enabled.y) {\n availableHeight = maximumClippingHeight;\n }\n\n if (noShift && !alignment) {\n const xMin = max(overflow.left, 0);\n const xMax = max(overflow.right, 0);\n const yMin = max(overflow.top, 0);\n const yMax = max(overflow.bottom, 0);\n\n if (isYAxis) {\n availableWidth =\n width -\n 2 *\n (xMin !== 0 || xMax !== 0\n ? xMin + xMax\n : max(overflow.left, overflow.right));\n } else {\n availableHeight =\n height -\n 2 *\n (yMin !== 0 || yMax !== 0\n ? yMin + yMax\n : max(overflow.top, overflow.bottom));\n }\n }\n\n await apply({...state, availableWidth, availableHeight});\n\n const nextDimensions = await platform.getDimensions(elements.floating);\n\n if (width !== nextDimensions.width || height !== nextDimensions.height) {\n return {\n reset: {\n rects: true,\n },\n };\n }\n\n return {};\n },\n});\n","type OverflowAncestors = Array<Element | Window | VisualViewport>;\n\nfunction hasWindow() {\n return typeof window !== 'undefined';\n}\n\nexport function getNodeName(node: Node | Window): string {\n if (isNode(node)) {\n return (node.nodeName || '').toLowerCase();\n }\n // Mocked nodes in testing environments may not be instances of Node. By\n // returning `#document` an infinite loop won't occur.\n // https://github.com/floating-ui/floating-ui/issues/2317\n return '#document';\n}\n\nexport function getWindow(node: any): typeof window {\n return node?.ownerDocument?.defaultView || window;\n}\n\nexport function getDocumentElement(node: Node | Window): HTMLElement {\n return (\n (isNode(node) ? node.ownerDocument : node.document) || window.document\n )?.documentElement;\n}\n\nexport function isNode(value: unknown): value is Node {\n if (!hasWindow()) {\n return false;\n }\n\n return value instanceof Node || value instanceof getWindow(value).Node;\n}\n\nexport function isElement(value: unknown): value is Element {\n if (!hasWindow()) {\n return false;\n }\n\n return value instanceof Element || value instanceof getWindow(value).Element;\n}\n\nexport function isHTMLElement(value: unknown): value is HTMLElement {\n if (!hasWindow()) {\n return false;\n }\n\n return (\n value instanceof HTMLElement ||\n value instanceof getWindow(value).HTMLElement\n );\n}\n\nexport function isShadowRoot(value: unknown): value is ShadowRoot {\n if (!hasWindow() || typeof ShadowRoot === 'undefined') {\n return false;\n }\n\n return (\n value instanceof ShadowRoot || value instanceof getWindow(value).ShadowRoot\n );\n}\n\nexport function isOverflowElement(element: Element): boolean {\n const {overflow, overflowX, overflowY, display} = getComputedStyle(element);\n return (\n /auto|scroll|overlay|hidden|clip/.test(overflow + overflowY + overflowX) &&\n display !== 'inline' &&\n display !== 'contents'\n );\n}\n\nexport function isTableElement(element: Element): boolean {\n return /^(table|td|th)$/.test(getNodeName(element));\n}\n\nexport function isTopLayer(element: Element): boolean {\n try {\n if (element.matches(':popover-open')) {\n return true;\n }\n } catch (_e) {\n // no-op\n }\n\n try {\n return element.matches(':modal');\n } catch (_e) {\n return false;\n }\n}\n\nconst willChangeRe = /transform|translate|scale|rotate|perspective|filter/;\nconst containRe = /paint|layout|strict|content/;\nconst isNotNone = (value: string) => !!value && value !== 'none';\nlet isWebKitValue: boolean | undefined;\n\nexport function isContainingBlock(\n elementOrCss: Element | CSSStyleDeclaration,\n): boolean {\n const css = isElement(elementOrCss)\n ? getComputedStyle(elementOrCss)\n : elementOrCss;\n\n // https://developer.mozilla.org/en-US/docs/Web/CSS/Containing_block#identifying_the_containing_block\n // https://drafts.csswg.org/css-transforms-2/#individual-transforms\n return (\n isNotNone(css.transform) ||\n isNotNone(css.translate) ||\n isNotNone(css.scale) ||\n isNotNone(css.rotate) ||\n isNotNone(css.perspective) ||\n (!isWebKit() && (isNotNone(css.backdropFilter) || isNotNone(css.filter))) ||\n willChangeRe.test(css.willChange || '') ||\n containRe.test(css.contain || '')\n );\n}\n\nexport function getContainingBlock(element: Element): HTMLElement | null {\n let currentNode: Node | null = getParentNode(element);\n\n while (isHTMLElement(currentNode) && !isLastTraversableNode(currentNode)) {\n if (isContainingBlock(currentNode)) {\n return currentNode;\n } else if (isTopLayer(currentNode)) {\n return null;\n }\n\n currentNode = getParentNode(currentNode);\n }\n\n return null;\n}\n\nexport function isWebKit(): boolean {\n if (isWebKitValue == null) {\n isWebKitValue =\n typeof CSS !== 'undefined' &&\n CSS.supports &&\n CSS.supports('-webkit-backdrop-filter', 'none');\n }\n\n return isWebKitValue;\n}\n\nexport function isLastTraversableNode(node: Node): boolean {\n return /^(html|body|#document)$/.test(getNodeName(node));\n}\n\nexport function getComputedStyle(element: Element): CSSStyleDeclaration {\n return getWindow(element).getComputedStyle(element);\n}\n\nexport function getNodeScroll(element: Element | Window): {\n scrollLeft: number;\n scrollTop: number;\n} {\n if (isElement(element)) {\n return {\n scrollLeft: element.scrollLeft,\n scrollTop: element.scrollTop,\n };\n }\n\n return {\n scrollLeft: element.scrollX,\n scrollTop: element.scrollY,\n };\n}\n\nexport function getParentNode(node: Node): Node {\n if (getNodeName(node) === 'html') {\n return node;\n }\n\n const result =\n // Step into the shadow DOM of the parent of a slotted node.\n (node as any).assignedSlot ||\n // DOM Element detected.\n node.parentNode ||\n // ShadowRoot detected.\n (isShadowRoot(node) && node.host) ||\n // Fallback.\n getDocumentElement(node);\n\n return isShadowRoot(result) ? result.host : result;\n}\n\nexport function getNearestOverflowAncestor(node: Node): HTMLElement {\n const parentNode = getParentNode(node);\n\n if (isLastTraversableNode(parentNode)) {\n return node.ownerDocument\n ? node.ownerDocument.body\n : (node as Document).body;\n }\n\n if (isHTMLElement(parentNode) && isOverflowElement(parentNode)) {\n return parentNode;\n }\n\n return getNearestOverflowAncestor(parentNode);\n}\n\nexport function getOverflowAncestors(\n node: Node,\n list: OverflowAncestors = [],\n traverseIframes = true,\n): OverflowAncestors {\n const scrollableAncestor = getNearestOverflowAncestor(node);\n const isBody = scrollableAncestor === node.ownerDocument?.body;\n const win = getWindow(scrollableAncestor);\n\n if (isBody) {\n const frameElement = getFrameElement(win);\n return list.concat(\n win,\n win.visualViewport || [],\n isOverflowElement(scrollableAncestor) ? scrollableAncestor : [],\n frameElement && traverseIframes ? getOverflowAncestors(frameElement) : [],\n );\n } else {\n return list.concat(\n scrollableAncestor,\n getOverflowAncestors(scrollableAncestor, [], traverseIframes),\n );\n }\n}\n\nexport function getFrameElement(win: Window): Element | null {\n return win.parent && Object.getPrototypeOf(win.parent)\n ? win.frameElement\n : null;\n}\n","import type {Dimensions} from '@floating-ui/core';\nimport {round} from '@floating-ui/utils';\nimport {getComputedStyle, isHTMLElement} from '@floating-ui/utils/dom';\n\nexport function getCssDimensions(element: Element): Dimensions & {$: boolean} {\n const css = getComputedStyle(element);\n // In testing environments, the `width` and `height` properties are empty\n // strings for SVG elements, returning NaN. Fallback to `0` in this case.\n let width = parseFloat(css.width) || 0;\n let height = parseFloat(css.height) || 0;\n const hasOffset = isHTMLElement(element);\n const offsetWidth = hasOffset ? element.offsetWidth : width;\n const offsetHeight = hasOffset ? element.offsetHeight : height;\n const shouldFallback =\n round(width) !== offsetWidth || round(height) !== offsetHeight;\n\n if (shouldFallback) {\n width = offsetWidth;\n height = offsetHeight;\n }\n\n return {\n width,\n height,\n $: shouldFallback,\n };\n}\n","import {isElement} from '../platform/isElement';\nimport type {VirtualElement} from '../types';\n\nexport function unwrapElement(element: Element | VirtualElement) {\n return !isElement(element) ? element.contextElement : element;\n}\n","import type {Coords} from '@floating-ui/core';\nimport {createCoords, round} from '@floating-ui/utils';\nimport {isHTMLElement} from '@floating-ui/utils/dom';\n\nimport type {VirtualElement} from '../types';\nimport {getCssDimensions} from '../utils/getCssDimensions';\nimport {unwrapElement} from '../utils/unwrapElement';\n\nexport function getScale(element: Element | VirtualElement): Coords {\n const domElement = unwrapElement(element);\n\n if (!isHTMLElement(domElement)) {\n return createCoords(1);\n }\n\n const rect = domElement.getBoundingClientRect();\n const {width, height, $} = getCssDimensions(domElement);\n let x = ($ ? round(rect.width) : rect.width) / width;\n let y = ($ ? round(rect.height) : rect.height) / height;\n\n // 0, NaN, or Infinity should always fallback to 1.\n\n if (!x || !Number.isFinite(x)) {\n x = 1;\n }\n\n if (!y || !Number.isFinite(y)) {\n y = 1;\n }\n\n return {\n x,\n y,\n };\n}\n","import type {Coords} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {getWindow, isWebKit} from '@floating-ui/utils/dom';\n\nconst noOffsets = createCoords(0);\n\nexport function getVisualOffsets(element: Element | undefined): Coords {\n const win = getWindow(element);\n\n if (!isWebKit() || !win.visualViewport) {\n return noOffsets;\n }\n\n return {\n x: win.visualViewport.offsetLeft,\n y: win.visualViewport.offsetTop,\n };\n}\n\nexport function shouldAddVisualOffsets(\n element: Element | undefined,\n isFixed = false,\n floatingOffsetParent?: Element | Window | undefined,\n): boolean {\n if (\n !floatingOffsetParent ||\n (isFixed && floatingOffsetParent !== getWindow(element))\n ) {\n return false;\n }\n\n return isFixed;\n}\n","import type {ClientRectObject} from '@floating-ui/core';\nimport {rectToClientRect} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {getComputedStyle, getWindow} from '@floating-ui/utils/dom';\n\nimport {getScale} from '../platform/getScale';\nimport {isElement} from '../platform/isElement';\nimport {getVisualOffsets, shouldAddVisualOffsets} from './getVisualOffsets';\nimport {unwrapElement} from './unwrapElement';\nimport type {VirtualElement} from '../types';\nimport {getFrameElement} from '@floating-ui/utils/dom';\n\nexport function getBoundingClientRect(\n element: Element | VirtualElement,\n includeScale = false,\n isFixedStrategy = false,\n offsetParent?: Element | Window,\n): ClientRectObject {\n const clientRect = element.getBoundingClientRect();\n const domElement = unwrapElement(element);\n\n let scale = createCoords(1);\n if (includeScale) {\n if (offsetParent) {\n if (isElement(offsetParent)) {\n scale = getScale(offsetParent);\n }\n } else {\n scale = getScale(element);\n }\n }\n\n const visualOffsets = shouldAddVisualOffsets(\n domElement,\n isFixedStrategy,\n offsetParent,\n )\n ? getVisualOffsets(domElement)\n : createCoords(0);\n\n let x = (clientRect.left + visualOffsets.x) / scale.x;\n let y = (clientRect.top + visualOffsets.y) / scale.y;\n let width = clientRect.width / scale.x;\n let height = clientRect.height / scale.y;\n\n if (domElement) {\n const win = getWindow(domElement);\n const offsetWin =\n offsetParent && isElement(offsetParent)\n ? getWindow(offsetParent)\n : offsetParent;\n\n let currentWin = win;\n let currentIFrame = getFrameElement(currentWin);\n while (currentIFrame && offsetParent && offsetWin !== currentWin) {\n const iframeScale = getScale(currentIFrame);\n const iframeRect = currentIFrame.getBoundingClientRect();\n const css = getComputedStyle(currentIFrame);\n const left =\n iframeRect.left +\n (currentIFrame.clientLeft + parseFloat(css.paddingLeft)) *\n iframeScale.x;\n const top =\n iframeRect.top +\n (currentIFrame.clientTop + parseFloat(css.paddingTop)) * iframeScale.y;\n\n x *= iframeScale.x;\n y *= iframeScale.y;\n width *= iframeScale.x;\n height *= iframeScale.y;\n\n x += left;\n y += top;\n\n currentWin = getWindow(currentIFrame);\n currentIFrame = getFrameElement(currentWin);\n }\n }\n\n return rectToClientRect({width, height, x, y});\n}\n","import {getNodeScroll} from '@floating-ui/utils/dom';\n\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getBoundingClientRect} from './getBoundingClientRect';\n\n// If <html> has a CSS width greater than the viewport, then this will be\n// incorrect for RTL.\nexport function getWindowScrollBarX(element: Element, rect?: DOMRect): number {\n const leftScroll = getNodeScroll(element).scrollLeft;\n\n if (!rect) {\n return getBoundingClientRect(getDocumentElement(element)).left + leftScroll;\n }\n\n return rect.left + leftScroll;\n}\n","import type {NodeScroll} from '../types';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\n\nexport function getHTMLOffset(\n documentElement: HTMLElement,\n scroll: NodeScroll,\n) {\n const htmlRect = documentElement.getBoundingClientRect();\n const x =\n htmlRect.left +\n scroll.scrollLeft -\n getWindowScrollBarX(documentElement, htmlRect);\n const y = htmlRect.top + scroll.scrollTop;\n\n return {\n x,\n y,\n };\n}\n","import type {Elements, Rect, Strategy} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {\n getDocumentElement,\n getNodeName,\n getNodeScroll,\n isHTMLElement,\n isOverflowElement,\n isTopLayer,\n} from '@floating-ui/utils/dom';\n\nimport {getBoundingClientRect} from '../utils/getBoundingClientRect';\nimport {getScale} from './getScale';\nimport {getHTMLOffset} from '../utils/getHTMLOffset';\n\nexport function convertOffsetParentRelativeRectToViewportRelativeRect({\n elements,\n rect,\n offsetParent,\n strategy,\n}: {\n elements?: Elements;\n rect: Rect;\n offsetParent: Element | Window;\n strategy: Strategy;\n}): Rect {\n const isFixed = strategy === 'fixed';\n const documentElement = getDocumentElement(offsetParent);\n const topLayer = elements ? isTopLayer(elements.floating) : false;\n\n if (offsetParent === documentElement || (topLayer && isFixed)) {\n return rect;\n }\n\n let scroll = {scrollLeft: 0, scrollTop: 0};\n let scale = createCoords(1);\n const offsets = createCoords(0);\n const isOffsetParentAnElement = isHTMLElement(offsetParent);\n\n if (isOffsetParentAnElement || (!isOffsetParentAnElement && !isFixed)) {\n if (\n getNodeName(offsetParent) !== 'body' ||\n isOverflowElement(documentElement)\n ) {\n scroll = getNodeScroll(offsetParent);\n }\n\n if (isOffsetParentAnElement) {\n const offsetRect = getBoundingClientRect(offsetParent);\n scale = getScale(offsetParent);\n offsets.x = offsetRect.x + offsetParent.clientLeft;\n offsets.y = offsetRect.y + offsetParent.clientTop;\n }\n }\n\n const htmlOffset =\n documentElement && !isOffsetParentAnElement && !isFixed\n ? getHTMLOffset(documentElement, scroll)\n : createCoords(0);\n\n return {\n width: rect.width * scale.x,\n height: rect.height * scale.y,\n x:\n rect.x * scale.x - scroll.scrollLeft * scale.x + offsets.x + htmlOffset.x,\n y: rect.y * scale.y - scroll.scrollTop * scale.y + offsets.y + htmlOffset.y,\n };\n}\n","export function getClientRects(element: Element) {\n return Array.from(element.getClientRects());\n}\n","import type {Rect} from '@floating-ui/core';\nimport {max} from '@floating-ui/utils';\nimport {getComputedStyle, getNodeScroll} from '@floating-ui/utils/dom';\n\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\n\n// Gets the entire size of the scrollable document area, even extending outside\n// of the `<html>` and `<body>` rect bounds if horizontally scrollable.\nexport function getDocumentRect(element: HTMLElement): Rect {\n const html = getDocumentElement(element);\n const scroll = getNodeScroll(element);\n const body = element.ownerDocument.body;\n\n const width = max(\n html.scrollWidth,\n html.clientWidth,\n body.scrollWidth,\n body.clientWidth,\n );\n const height = max(\n html.scrollHeight,\n html.clientHeight,\n body.scrollHeight,\n body.clientHeight,\n );\n\n let x = -scroll.scrollLeft + getWindowScrollBarX(element);\n const y = -scroll.scrollTop;\n\n if (getComputedStyle(body).direction === 'rtl') {\n x += max(html.clientWidth, body.clientWidth) - width;\n }\n\n return {\n width,\n height,\n x,\n y,\n };\n}\n","import type {Rect, Strategy} from '@floating-ui/core';\nimport {getWindow, isWebKit} from '@floating-ui/utils/dom';\n\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\n\n// Safety check: ensure the scrollbar space is reasonable in case this\n// calculation is affected by unusual styles.\n// Most scrollbars leave 15-18px of space.\nconst SCROLLBAR_MAX = 25;\n\nexport function getViewportRect(element: Element, strategy: Strategy): Rect {\n const win = getWindow(element);\n const html = getDocumentElement(element);\n const visualViewport = win.visualViewport;\n\n let width = html.clientWidth;\n let height = html.clientHeight;\n let x = 0;\n let y = 0;\n\n if (visualViewport) {\n width = visualViewport.width;\n height = visualViewport.height;\n\n const visualViewportBased = isWebKit();\n\n if (!visualViewportBased || (visualViewportBased && strategy === 'fixed')) {\n x = visualViewport.offsetLeft;\n y = visualViewport.offsetTop;\n }\n }\n\n const windowScrollbarX = getWindowScrollBarX(html);\n // <html> `overflow: hidden` + `scrollbar-gutter: stable` reduces the\n // visual width of the <html> but this is not considered in the size\n // of `html.clientWidth`.\n if (windowScrollbarX <= 0) {\n const doc = html.ownerDocument;\n const body = doc.body;\n const bodyStyles = getComputedStyle(body);\n const bodyMarginInline =\n doc.compatMode === 'CSS1Compat'\n ? parseFloat(bodyStyles.marginLeft) +\n parseFloat(bodyStyles.marginRight) || 0\n : 0;\n const clippingStableScrollbarWidth = Math.abs(\n html.clientWidth - body.clientWidth - bodyMarginInline,\n );\n\n if (clippingStableScrollbarWidth <= SCROLLBAR_MAX) {\n width -= clippingStableScrollbarWidth;\n }\n } else if (windowScrollbarX <= SCROLLBAR_MAX) {\n // If the <body> scrollbar is on the left, the width needs to be extended\n // by the scrollbar amount so there isn't extra space on the right.\n width += windowScrollbarX;\n }\n\n return {\n width,\n height,\n x,\n y,\n };\n}\n","import type {\n Boundary,\n ClientRectObject,\n Rect,\n RootBoundary,\n Strategy,\n} from '@floating-ui/core';\nimport {rectToClientRect} from '@floating-ui/core';\nimport {createCoords, max, min} from '@floating-ui/utils';\nimport {\n getComputedStyle,\n getDocumentElement,\n getNodeName,\n getOverflowAncestors,\n getParentNode,\n isContainingBlock,\n isHTMLElement,\n isLastTraversableNode,\n isOverflowElement,\n isTopLayer,\n} from '@floating-ui/utils/dom';\n\nimport type {Platform, ReferenceElement} from '../types';\nimport {getBoundingClientRect} from '../utils/getBoundingClientRect';\nimport {getDocumentRect} from '../utils/getDocumentRect';\nimport {getViewportRect} from '../utils/getViewportRect';\nimport {getVisualOffsets} from '../utils/getVisualOffsets';\nimport {getScale} from './getScale';\nimport {isElement} from './isElement';\n\ntype PlatformWithCache = Platform & {\n _c: Map<ReferenceElement, Element[]>;\n};\n\n// Returns the inner client rect, subtracting scrollbars if present.\nfunction getInnerBoundingClientRect(\n element: Element,\n strategy: Strategy,\n): Rect {\n const clientRect = getBoundingClientRect(element, true, strategy === 'fixed');\n const top = clientRect.top + element.clientTop;\n const left = clientRect.left + element.clientLeft;\n const scale = isHTMLElement(element) ? getScale(element) : createCoords(1);\n const width = element.clientWidth * scale.x;\n const height = element.clientHeight * scale.y;\n const x = left * scale.x;\n const y = top * scale.y;\n\n return {\n width,\n height,\n x,\n y,\n };\n}\n\nfunction getClientRectFromClippingAncestor(\n element: Element,\n clippingAncestor: Element | RootBoundary,\n strategy: Strategy,\n): ClientRectObject {\n let rect: Rect;\n\n if (clippingAncestor === 'viewport') {\n rect = getViewportRect(element, strategy);\n } else if (clippingAncestor === 'document') {\n rect = getDocumentRect(getDocumentElement(element));\n } else if (isElement(clippingAncestor)) {\n rect = getInnerBoundingClientRect(clippingAncestor, strategy);\n } else {\n const visualOffsets = getVisualOffsets(element);\n rect = {\n x: clippingAncestor.x - visualOffsets.x,\n y: clippingAncestor.y - visualOffsets.y,\n width: clippingAncestor.width,\n height: clippingAncestor.height,\n };\n }\n\n return rectToClientRect(rect);\n}\n\nfunction hasFixedPositionAncestor(element: Element, stopNode: Node): boolean {\n const parentNode = getParentNode(element);\n if (\n parentNode === stopNode ||\n !isElement(parentNode) ||\n isLastTraversableNode(parentNode)\n ) {\n return false;\n }\n\n return (\n getComputedStyle(parentNode).position === 'fixed' ||\n hasFixedPositionAncestor(parentNode, stopNode)\n );\n}\n\n// A \"clipping ancestor\" is an `overflow` element with the characteristic of\n// clipping (or hiding) child elements. This returns all clipping ancestors\n// of the given element up the tree.\nfunction getClippingElementAncestors(\n element: Element,\n cache: PlatformWithCache['_c'],\n): Array<Element> {\n const cachedResult = cache.get(element);\n if (cachedResult) {\n return cachedResult;\n }\n\n let result = getOverflowAncestors(element, [], false).filter(\n (el) => isElement(el) && getNodeName(el) !== 'body',\n ) as Array<Element>;\n let currentContainingBlockComputedStyle: CSSStyleDeclaration | null = null;\n const elementIsFixed = getComputedStyle(element).position === 'fixed';\n let currentNode: Node | null = elementIsFixed\n ? getParentNode(element)\n : element;\n\n // https://developer.mozilla.org/en-US/docs/Web/CSS/Containing_block#identifying_the_containing_block\n while (isElement(currentNode) && !isLastTraversableNode(currentNode)) {\n const computedStyle = getComputedStyle(currentNode);\n const currentNodeIsContaining = isContainingBlock(currentNode);\n\n if (!currentNodeIsContaining && computedStyle.position === 'fixed') {\n currentContainingBlockComputedStyle = null;\n }\n\n const shouldDropCurrentNode = elementIsFixed\n ? !currentNodeIsContaining && !currentContainingBlockComputedStyle\n : (!currentNodeIsContaining &&\n computedStyle.position === 'static' &&\n !!currentContainingBlockComputedStyle &&\n (currentContainingBlockComputedStyle.position === 'absolute' ||\n currentContainingBlockComputedStyle.position === 'fixed')) ||\n (isOverflowElement(currentNode) &&\n !currentNodeIsContaining &&\n hasFixedPositionAncestor(element, currentNode));\n\n if (shouldDropCurrentNode) {\n // Drop non-containing blocks.\n result = result.filter((ancestor) => ancestor !== currentNode);\n } else {\n // Record last containing block for next iteration.\n currentContainingBlockComputedStyle = computedStyle;\n }\n\n currentNode = getParentNode(currentNode);\n }\n\n cache.set(element, result);\n\n return result;\n}\n\n// Gets the maximum area that the element is visible in due to any number of\n// clipping ancestors.\nexport function getClippingRect(\n this: PlatformWithCache,\n {\n element,\n boundary,\n rootBoundary,\n strategy,\n }: {\n element: Element;\n boundary: Boundary;\n rootBoundary: RootBoundary;\n strategy: Strategy;\n },\n): Rect {\n const elementClippingAncestors =\n boundary === 'clippingAncestors'\n ? isTopLayer(element)\n ? []\n : getClippingElementAncestors(element, this._c)\n : [].concat(boundary);\n const clippingAncestors = [...elementClippingAncestors, rootBoundary];\n\n const firstRect = getClientRectFromClippingAncestor(\n element,\n clippingAncestors[0],\n strategy,\n );\n let top = firstRect.top;\n let right = firstRect.right;\n let bottom = firstRect.bottom;\n let left = firstRect.left;\n\n for (let i = 1; i < clippingAncestors.length; i++) {\n const rect = getClientRectFromClippingAncestor(\n element,\n clippingAncestors[i],\n strategy,\n );\n top = max(rect.top, top);\n right = min(rect.right, right);\n bottom = min(rect.bottom, bottom);\n left = max(rect.left, left);\n }\n\n return {\n width: right - left,\n height: bottom - top,\n x: left,\n y: top,\n };\n}\n","import type {Dimensions} from '@floating-ui/core';\n\nimport {getCssDimensions} from '../utils/getCssDimensions';\n\nexport function getDimensions(element: Element): Dimensions {\n const {width, height} = getCssDimensions(element);\n return {width, height};\n}\n","import type {Rect, Strategy} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {\n getNodeName,\n getNodeScroll,\n isHTMLElement,\n isOverflowElement,\n} from '@floating-ui/utils/dom';\n\nimport type {VirtualElement} from '../types';\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getBoundingClientRect} from './getBoundingClientRect';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\nimport {getHTMLOffset} from './getHTMLOffset';\n\nexport function getRectRelativeToOffsetParent(\n element: Element | VirtualElement,\n offsetParent: Element | Window,\n strategy: Strategy,\n): Rect {\n const isOffsetParentAnElement = isHTMLElement(offsetParent);\n const documentElement = getDocumentElement(offsetParent);\n const isFixed = strategy === 'fixed';\n const rect = getBoundingClientRect(element, true, isFixed, offsetParent);\n\n let scroll = {scrollLeft: 0, scrollTop: 0};\n const offsets = createCoords(0);\n\n // If the <body> scrollbar appears on the left (e.g. RTL systems). Use\n // Firefox with layout.scrollbar.side = 3 in about:config to test this.\n function setLeftRTLScrollbarOffset() {\n offsets.x = getWindowScrollBarX(documentElement);\n }\n\n if (isOffsetParentAnElement || (!isOffsetParentAnElement && !isFixed)) {\n if (\n getNodeName(offsetParent) !== 'body' ||\n isOverflowElement(documentElement)\n ) {\n scroll = getNodeScroll(offsetParent);\n }\n\n if (isOffsetParentAnElement) {\n const offsetRect = getBoundingClientRect(\n offsetParent,\n true,\n isFixed,\n offsetParent,\n );\n offsets.x = offsetRect.x + offsetParent.clientLeft;\n offsets.y = offsetRect.y + offsetParent.clientTop;\n } else if (documentElement) {\n setLeftRTLScrollbarOffset();\n }\n }\n\n if (isFixed && !isOffsetParentAnElement && documentElement) {\n setLeftRTLScrollbarOffset();\n }\n\n const htmlOffset =\n documentElement && !isOffsetParentAnElement && !isFixed\n ? getHTMLOffset(documentElement, scroll)\n : createCoords(0);\n\n const x = rect.left + scroll.scrollLeft - offsets.x - htmlOffset.x;\n const y = rect.top + scroll.scrollTop - offsets.y - htmlOffset.y;\n\n return {\n x,\n y,\n width: rect.width,\n height: rect.height,\n };\n}\n","import {getComputedStyle} from '@floating-ui/utils/dom';\n\nexport function isStaticPositioned(element: Element): boolean {\n return getComputedStyle(element).position === 'static';\n}\n","import {\n getComputedStyle,\n getContainingBlock,\n getDocumentElement,\n getParentNode,\n getWindow,\n isContainingBlock,\n isElement,\n isHTMLElement,\n isLastTraversableNode,\n isTableElement,\n isTopLayer,\n} from '@floating-ui/utils/dom';\nimport {isStaticPositioned} from '../utils/isStaticPositioned';\n\ntype Polyfill = (element: HTMLElement) => Element | null;\n\nfunction getTrueOffsetParent(\n element: Element,\n polyfill: Polyfill | undefined,\n): Element | null {\n if (\n !isHTMLElement(element) ||\n getComputedStyle(element).position === 'fixed'\n ) {\n return null;\n }\n\n if (polyfill) {\n return polyfill(element);\n }\n\n let rawOffsetParent = element.offsetParent;\n\n // Firefox returns the <html> element as the offsetParent if it's non-static,\n // while Chrome and Safari return the <body> element. The <body> element must\n // be used to perform the correct calculations even if the <html> element is\n // non-static.\n if (getDocumentElement(element) === rawOffsetParent) {\n rawOffsetParent = rawOffsetParent.ownerDocument.body;\n }\n\n return rawOffsetParent;\n}\n\n// Gets the closest ancestor positioned element. Handles some edge cases,\n// such as table ancestors and cross browser bugs.\nexport function getOffsetParent(\n element: Element,\n polyfill?: Polyfill,\n): Element | Window {\n const win = getWindow(element);\n\n if (isTopLayer(element)) {\n return win;\n }\n\n if (!isHTMLElement(element)) {\n let svgOffsetParent = getParentNode(element);\n while (svgOffsetParent && !isLastTraversableNode(svgOffsetParent)) {\n if (isElement(svgOffsetParent) && !isStaticPositioned(svgOffsetParent)) {\n return svgOffsetParent;\n }\n svgOffsetParent = getParentNode(svgOffsetParent);\n }\n return win;\n }\n\n let offsetParent = getTrueOffsetParent(element, polyfill);\n\n while (\n offsetParent &&\n isTableElement(offsetParent) &&\n isStaticPositioned(offsetParent)\n ) {\n offsetParent = getTrueOffsetParent(offsetParent, polyfill);\n }\n\n if (\n offsetParent &&\n isLastTraversableNode(offsetParent) &&\n isStaticPositioned(offsetParent) &&\n !isContainingBlock(offsetParent)\n ) {\n return win;\n }\n\n return offsetParent || getContainingBlock(element) || win;\n}\n","import type {Platform} from '../types';\nimport {getRectRelativeToOffsetParent} from '../utils/getRectRelativeToOffsetParent';\nimport {getOffsetParent} from './getOffsetParent';\n\nexport const getElementRects: Platform['getElementRects'] = async function (\n this: Platform,\n data,\n) {\n const getOffsetParentFn = this.getOffsetParent || getOffsetParent;\n const getDimensionsFn = this.getDimensions;\n const floatingDimensions = await getDimensionsFn(data.floating);\n\n return {\n reference: getRectRelativeToOffsetParent(\n data.reference,\n await getOffsetParentFn(data.floating),\n data.strategy,\n ),\n floating: {\n x: 0,\n y: 0,\n width: floatingDimensions.width,\n height: floatingDimensions.height,\n },\n };\n};\n","import {getComputedStyle} from '@floating-ui/utils/dom';\n\nexport function isRTL(element: Element) {\n return getComputedStyle(element).direction === 'rtl';\n}\n","import {convertOffsetParentRelativeRectToViewportRelativeRect} from './platform/convertOffsetParentRelativeRectToViewportRelativeRect';\nimport {getClientRects} from './platform/getClientRects';\nimport {getClippingRect} from './platform/getClippingRect';\nimport {getDimensions} from './platform/getDimensions';\nimport {getDocumentElement} from './platform/getDocumentElement';\nimport {getElementRects} from './platform/getElementRects';\nimport {getOffsetParent} from './platform/getOffsetParent';\nimport {getScale} from './platform/getScale';\nimport {isElement} from './platform/isElement';\nimport {isRTL} from './platform/isRTL';\nimport type {Platform} from './types';\n\nexport const platform: Platform = {\n convertOffsetParentRelativeRectToViewportRelativeRect,\n getDocumentElement,\n getClippingRect,\n getOffsetParent,\n getElementRects,\n getClientRects,\n getDimensions,\n getScale,\n isElement,\n isRTL,\n};\n","import type {ClientRectObject} from '@floating-ui/core';\n\nexport function rectsAreEqual(a: ClientRectObject, b: ClientRectObject) {\n return (\n a.x === b.x && a.y === b.y && a.width === b.width && a.height === b.height\n );\n}\n","import {floor, max, min} from '@floating-ui/utils';\nimport {getDocumentElement, getOverflowAncestors} from '@floating-ui/utils/dom';\n\nimport type {FloatingElement, ReferenceElement} from './types';\nimport {getBoundingClientRect} from './utils/getBoundingClientRect';\nimport {unwrapElement} from './utils/unwrapElement';\nimport {rectsAreEqual} from './utils/rectsAreEqual';\n\nexport interface AutoUpdateOptions {\n /**\n * Whether to update the position when an overflow ancestor is scrolled.\n * @default true\n */\n ancestorScroll?: boolean;\n /**\n * Whether to update the position when an overflow ancestor is resized. This\n * uses the native `resize` event.\n * @default true\n */\n ancestorResize?: boolean;\n /**\n * Whether to update the position when either the reference or floating\n * elements resized. This uses a `ResizeObserver`.\n * @default true\n */\n elementResize?: boolean;\n /**\n * Whether to update the position when the reference relocated on the screen\n * due to layout shift.\n * @default true\n */\n layoutShift?: boolean;\n /**\n * Whether to update on every animation frame if necessary. Only use if you\n * need to update the position in response to an animation using transforms.\n * @default false\n */\n animationFrame?: boolean;\n}\n\n// https://samthor.au/2021/observing-dom/\nfunction observeMove(element: Element, onMove: () => void) {\n let io: IntersectionObserver | null = null;\n let timeoutId: NodeJS.Timeout;\n\n const root = getDocumentElement(element);\n\n function cleanup() {\n clearTimeout(timeoutId);\n io?.disconnect();\n io = null;\n }\n\n function refresh(skip = false, threshold = 1) {\n cleanup();\n\n const elementRectForRootMargin = element.getBoundingClientRect();\n const {left, top, width, height} = elementRectForRootMargin;\n\n if (!skip) {\n onMove();\n }\n\n if (!width || !height) {\n return;\n }\n\n const insetTop = floor(top);\n const insetRight = floor(root.clientWidth - (left + width));\n const insetBottom = floor(root.clientHeight - (top + height));\n const insetLeft = floor(left);\n const rootMargin = `${-insetTop}px ${-insetRight}px ${-insetBottom}px ${-insetLeft}px`;\n\n const options = {\n rootMargin,\n threshold: max(0, min(1, threshold)) || 1,\n };\n\n let isFirstUpdate = true;\n\n function handleObserve(entries: IntersectionObserverEntry[]) {\n const ratio = entries[0].intersectionRatio;\n\n if (ratio !== threshold) {\n if (!isFirstUpdate) {\n return refresh();\n }\n\n if (!ratio) {\n // If the reference is clipped, the ratio is 0. Throttle the refresh\n // to prevent an infinite loop of updates.\n timeoutId = setTimeout(() => {\n refresh(false, 1e-7);\n }, 1000);\n } else {\n refresh(false, ratio);\n }\n }\n\n if (\n ratio === 1 &&\n !rectsAreEqual(\n elementRectForRootMargin,\n element.getBoundingClientRect(),\n )\n ) {\n // It's possible that even though the ratio is reported as 1, the\n // element is not actually fully within the IntersectionObserver's root\n // area anymore. This can happen under performance constraints. This may\n // be a bug in the browser's IntersectionObserver implementation. To\n // work around this, we compare the element's bounding rect now with\n // what it was at the time we created the IntersectionObserver. If they\n // are not equal then the element moved, so we refresh.\n refresh();\n }\n\n isFirstUpdate = false;\n }\n\n // Older browsers don't support a `document` as the root and will throw an\n // error.\n try {\n io = new IntersectionObserver(handleObserve, {\n ...options,\n // Handle <iframe>s\n root: root.ownerDocument,\n });\n } catch (_e) {\n io = new IntersectionObserver(handleObserve, options);\n }\n\n io.observe(element);\n }\n\n refresh(true);\n\n return cleanup;\n}\n\n/**\n * Automatically updates the position of the floating element when necessary.\n * Should only be called when the floating element is mounted on the DOM or\n * visible on the screen.\n * @returns cleanup function that should be invoked when the floating element is\n * removed from the DOM or hidden from the screen.\n * @see https://floating-ui.com/docs/autoUpdate\n */\nexport function autoUpdate(\n reference: ReferenceElement,\n floating: FloatingElement | null,\n update: () => void,\n options: AutoUpdateOptions = {},\n) {\n const {\n ancestorScroll = true,\n ancestorResize = true,\n elementResize = typeof ResizeObserver === 'function',\n layoutShift = typeof IntersectionObserver === 'function',\n animationFrame = false,\n } = options;\n\n const referenceEl = unwrapElement(reference);\n\n const ancestors =\n ancestorScroll || ancestorResize\n ? [\n ...(referenceEl ? getOverflowAncestors(referenceEl) : []),\n ...(floating ? getOverflowAncestors(floating) : []),\n ]\n : [];\n\n ancestors.forEach((ancestor) => {\n ancestorScroll &&\n ancestor.addEventListener('scroll', update, {passive: true});\n ancestorResize && ancestor.addEventListener('resize', update);\n });\n\n const cleanupIo =\n referenceEl && layoutShift ? observeMove(referenceEl, update) : null;\n\n let reobserveFrame = -1;\n let resizeObserver: ResizeObserver | null = null;\n\n if (elementResize) {\n resizeObserver = new ResizeObserver(([firstEntry]) => {\n if (\n firstEntry &&\n firstEntry.target === referenceEl &&\n resizeObserver &&\n floating\n ) {\n // Prevent update loops when using the `size` middleware.\n // https://github.com/floating-ui/floating-ui/issues/1740\n resizeObserver.unobserve(floating);\n cancelAnimationFrame(reobserveFrame);\n reobserveFrame = requestAnimationFrame(() => {\n resizeObserver?.observe(floating);\n });\n }\n update();\n });\n\n if (referenceEl && !animationFrame) {\n resizeObserver.observe(referenceEl);\n }\n\n if (floating) {\n resizeObserver.observe(floating);\n }\n }\n\n let frameId: number;\n let prevRefRect = animationFrame ? getBoundingClientRect(reference) : null;\n\n if (animationFrame) {\n frameLoop();\n }\n\n function frameLoop() {\n const nextRefRect = getBoundingClientRect(reference);\n\n if (prevRefRect && !rectsAreEqual(prevRefRect, nextRefRect)) {\n update();\n }\n\n prevRefRect = nextRefRect;\n frameId = requestAnimationFrame(frameLoop);\n }\n\n update();\n\n return () => {\n ancestors.forEach((ancestor) => {\n ancestorScroll && ancestor.removeEventListener('scroll', update);\n ancestorResize && ancestor.removeEventListener('resize', update);\n });\n\n cleanupIo?.();\n resizeObserver?.disconnect();\n resizeObserver = null;\n\n if (animationFrame) {\n cancelAnimationFrame(frameId);\n }\n };\n}\n","// createFloating — Popper.js-equivalent imperative manager for @domphy/floating.\r\n//\r\n// Wraps `computePosition` + `autoUpdate` into a stateful handle so callers do\r\n// not have to manage the cleanup function themselves or re-implement the\r\n// \"call computePosition on every autoUpdate tick\" loop.\r\n//\r\n// Intentionally framework-agnostic: no @domphy/core dependency. Wire it to\r\n// any lifecycle system — Domphy `_onMount`/`_onBeforeRemove`, vanilla JS, or\r\n// plain event listeners.\r\n\r\nimport {computePosition as computePositionCore} from '@floating-ui/core';\r\nimport type {MiddlewareData, Placement, Strategy} from '@floating-ui/core';\r\n\r\nimport {autoUpdate} from './autoUpdate.js';\r\nimport {platform} from './platform.js';\r\nimport type {\r\n AutoUpdateOptions,\r\n ComputePositionConfig,\r\n FloatingElement,\r\n ReferenceElement,\r\n} from './types.js';\r\n\r\n/**\r\n * The position result from the most recent `computePosition` call. Mirrors\r\n * the shape returned by `computePosition` for easy destructuring.\r\n */\r\nexport interface FloatingPosition {\r\n /** Left offset in pixels — apply as `style.left`. */\r\n x: number;\r\n /** Top offset in pixels — apply as `style.top`. */\r\n y: number;\r\n /**\r\n * The resolved placement after all middleware ran. May differ from the\r\n * preferred placement when `flip` or `autoPlacement` changed it.\r\n */\r\n placement: Placement;\r\n /**\r\n * CSS position strategy. Matches the `strategy` option passed to\r\n * `computePosition` and must match `style.position` on the floating element.\r\n */\r\n strategy: Strategy;\r\n /** Per-middleware output (arrow offsets, hide flags, size data, …). */\r\n middlewareData: MiddlewareData;\r\n}\r\n\r\n/**\r\n * Stateful floating-element manager returned by `createFloating`.\r\n *\r\n * Popper.js equivalences:\r\n * - `connect(reference, floating)` → `createPopper(reference, popper, options)`\r\n * - `disconnect()` → `popper.destroy()`\r\n * - `onUpdate(callback)` → subscribe to position state changes\r\n * - `position` → equivalent of `popper.state`\r\n */\r\nexport interface FloatingHandle {\r\n /**\r\n * Wire the reference and floating DOM elements together and start\r\n * `autoUpdate`. Call this once both elements are in the DOM (e.g. from a\r\n * Domphy `_onMount` lifecycle hook). Calling `connect` while already\r\n * connected first tears down the previous auto-update.\r\n */\r\n connect(\r\n reference: ReferenceElement,\r\n floating: FloatingElement,\r\n updateOptions?: AutoUpdateOptions,\r\n ): void;\r\n /**\r\n * Stop `autoUpdate` and release element references. Call from\r\n * `_onBeforeRemove` — or when the floating element is hidden if it stays\r\n * mounted and you want to pause updates.\r\n */\r\n disconnect(): void;\r\n /**\r\n * The last computed position, or `null` before the first `computePosition`\r\n * call completes.\r\n */\r\n readonly position: FloatingPosition | null;\r\n /**\r\n * Subscribe to position updates. The callback is called synchronously\r\n * after each `computePosition` resolves with the new position. Returns an\r\n * unsubscribe function — call it to remove the listener.\r\n *\r\n * Typical Domphy usage: call `onUpdate` once and write the `x`/`y` values\r\n * to the floating element's style inside the callback.\r\n */\r\n onUpdate(callback: (position: FloatingPosition) => void): () => void;\r\n}\r\n\r\n/**\r\n * Create a stateful floating-element manager. Equivalent to `createPopper()`\r\n * from Popper.js, but built on the Floating UI primitives vendored by\r\n * `@domphy/floating`.\r\n *\r\n * ```ts\r\n * import { createFloating, offset, flip, shift } from \"@domphy/floating\"\r\n *\r\n * const handle = createFloating({\r\n * placement: \"bottom\",\r\n * middleware: [offset(8), flip(), shift()],\r\n * strategy: \"fixed\",\r\n * })\r\n *\r\n * // In _onMount (once both elements are available):\r\n * handle.connect(referenceEl, floatingEl)\r\n * handle.onUpdate(({ x, y }) => {\r\n * Object.assign(floatingEl.style, { left: `${x}px`, top: `${y}px` })\r\n * })\r\n *\r\n * // In _onBeforeRemove:\r\n * handle.disconnect()\r\n * ```\r\n */\r\nexport function createFloating(\r\n config: Partial<ComputePositionConfig> = {},\r\n): FloatingHandle {\r\n let cleanupAutoUpdate: (() => void) | null = null;\r\n let currentReference: ReferenceElement | null = null;\r\n let currentFloating: FloatingElement | null = null;\r\n let position: FloatingPosition | null = null;\r\n const listeners = new Set<(position: FloatingPosition) => void>();\r\n\r\n function runUpdate(): void {\r\n if (!currentReference || !currentFloating) return;\r\n const reference = currentReference;\r\n const floating = currentFloating;\r\n\r\n // Mirror the cache strategy from computePosition in dom/index.ts: one Map\r\n // per update call so middleware can de-dupe expensive ancestor lookups\r\n // within the same computation without leaking between calls.\r\n const cache = new Map<ReferenceElement, Array<Element>>();\r\n const mergedOptions = {platform, ...config};\r\n const platformWithCache = {...mergedOptions.platform, _c: cache};\r\n\r\n computePositionCore(reference, floating, {\r\n ...mergedOptions,\r\n platform: platformWithCache,\r\n })\r\n .then((result) => {\r\n // Guard against a late-resolving promise after disconnect() — or a\r\n // connect() to a different pair — happened while this call was in\r\n // flight. Identity (not just nullity) check avoids a stale\r\n // computation for an old reference/floating pair overwriting a\r\n // newer one.\r\n if (currentReference !== reference || currentFloating !== floating) {\r\n return;\r\n }\r\n position = result as FloatingPosition;\r\n for (const listener of listeners) {\r\n try {\r\n listener(position);\r\n } catch (error) {\r\n console.error(error);\r\n }\r\n }\r\n })\r\n .catch((error) => {\r\n console.error(error);\r\n });\r\n }\r\n\r\n return {\r\n connect(reference, floating, updateOptions) {\r\n // Tear down any prior auto-update before wiring new elements.\r\n cleanupAutoUpdate?.();\r\n currentReference = reference;\r\n currentFloating = floating;\r\n runUpdate();\r\n cleanupAutoUpdate = autoUpdate(\r\n reference,\r\n floating,\r\n runUpdate,\r\n updateOptions,\r\n );\r\n },\r\n\r\n disconnect() {\r\n cleanupAutoUpdate?.();\r\n cleanupAutoUpdate = null;\r\n currentReference = null;\r\n currentFloating = null;\r\n },\r\n\r\n get position() {\r\n return position;\r\n },\r\n\r\n onUpdate(callback) {\r\n listeners.add(callback);\r\n return () => {\r\n listeners.delete(callback);\r\n };\r\n },\r\n };\r\n}\r\n","import type {\n Coords,\n InlineOptions,\n LimitShiftOptions,\n SideObject,\n} from '@floating-ui/core';\nimport {\n arrow as arrowCore,\n autoPlacement as autoPlacementCore,\n detectOverflow as detectOverflowCore,\n flip as flipCore,\n hide as hideCore,\n inline as inlineCore,\n limitShift as limitShiftCore,\n offset as offsetCore,\n shift as shiftCore,\n size as sizeCore,\n} from '@floating-ui/core';\n\nimport type {\n ArrowOptions,\n AutoPlacementOptions,\n Derivable,\n DetectOverflowOptions,\n FlipOptions,\n HideOptions,\n Middleware,\n MiddlewareState,\n OffsetOptions,\n ShiftOptions,\n SizeOptions,\n} from './types';\n\n/**\n * Resolves with an object of overflow side offsets that determine how much the\n * element is overflowing a given clipping boundary on each side.\n * - positive = overflowing the boundary by that number of pixels\n * - negative = how many pixels left before it will overflow\n * - 0 = lies flush with the boundary\n * @see https://floating-ui.com/docs/detectOverflow\n */\nexport const detectOverflow: (\n state: MiddlewareState,\n options?: DetectOverflowOptions | Derivable<DetectOverflowOptions>,\n) => Promise<SideObject> = detectOverflowCore;\n\n/**\n * Modifies the placement by translating the floating element along the\n * specified axes.\n * A number (shorthand for `mainAxis` or distance), or an axes configuration\n * object may be passed.\n * @see https://floating-ui.com/docs/offset\n */\nexport const offset: (options?: OffsetOptions) => Middleware = offsetCore;\n\n/**\n * Optimizes the visibility of the floating element by choosing the placement\n * that has the most space available automatically, without needing to specify a\n * preferred placement. Alternative to `flip`.\n * @see https://floating-ui.com/docs/autoPlacement\n */\nexport const autoPlacement: (\n options?: AutoPlacementOptions | Derivable<AutoPlacementOptions>,\n) => Middleware = autoPlacementCore;\n\n/**\n * Optimizes the visibility of the floating element by shifting it in order to\n * keep it in view when it will overflow the clipping boundary.\n * @see https://floating-ui.com/docs/shift\n */\nexport const shift: (\n options?: ShiftOptions | Derivable<ShiftOptions>,\n) => Middleware = shiftCore;\n\n/**\n * Optimizes the visibility of the floating element by flipping the `placement`\n * in order to keep it in view when the preferred placement(s) will overflow the\n * clipping boundary. Alternative to `autoPlacement`.\n * @see https://floating-ui.com/docs/flip\n */\nexport const flip: (\n options?: FlipOptions | Derivable<FlipOptions>,\n) => Middleware = flipCore;\n\n/**\n * Provides data that allows you to change the size of the floating element —\n * for instance, prevent it from overflowing the clipping boundary or match the\n * width of the reference element.\n * @see https://floating-ui.com/docs/size\n */\nexport const size: (\n options?: SizeOptions | Derivable<SizeOptions>,\n) => Middleware = sizeCore;\n\n/**\n * Provides data to hide the floating element in applicable situations, such as\n * when it is not in the same clipping context as the reference element.\n * @see https://floating-ui.com/docs/hide\n */\nexport const hide: (\n options?: HideOptions | Derivable<HideOptions>,\n) => Middleware = hideCore;\n\n/**\n * Provides data to position an inner element of the floating element so that it\n * appears centered to the reference element.\n * @see https://floating-ui.com/docs/arrow\n */\nexport const arrow: (\n options: ArrowOptions | Derivable<ArrowOptions>,\n) => Middleware = arrowCore;\n\n/**\n * Provides improved positioning for inline reference elements that can span\n * over multiple lines, such as hyperlinks or range selections.\n * @see https://floating-ui.com/docs/inline\n */\nexport const inline: (\n options?: InlineOptions | Derivable<InlineOptions>,\n) => Middleware = inlineCore;\n\n/**\n * Built-in `limiter` that will stop `shift()` at a certain point.\n */\nexport const limitShift: (\n options?: LimitShiftOptions | Derivable<LimitShiftOptions>,\n) => {\n options: any;\n fn: (state: MiddlewareState) => Coords;\n} = limitShiftCore;\n","import {computePosition as computePositionCore} from '@floating-ui/core';\n\nimport {platform} from './platform';\nimport type {\n ComputePositionConfig,\n FloatingElement,\n ReferenceElement,\n} from './types';\n\n/**\n * Computes the `x` and `y` coordinates that will place the floating element\n * next to a given reference element.\n */\nexport const computePosition = (\n reference: ReferenceElement,\n floating: FloatingElement,\n options?: Partial<ComputePositionConfig>,\n) => {\n // This caches the expensive `getClippingElementAncestors` function so that\n // multiple lifecycle resets re-use the same result. It only lives for a\n // single call. If other functions become expensive, we can add them as well.\n const cache = new Map<ReferenceElement, Array<Element>>();\n const mergedOptions = {platform, ...options};\n const platformWithCache = {...mergedOptions.platform, _c: cache};\n return computePositionCore(reference, floating, {\n ...mergedOptions,\n platform: platformWithCache,\n });\n};\n\nexport {autoUpdate} from './autoUpdate';\nexport {createFloating} from './createFloating';\nexport type {FloatingHandle, FloatingPosition} from './createFloating';\nexport {\n arrow,\n autoPlacement,\n detectOverflow,\n flip,\n hide,\n inline,\n limitShift,\n offset,\n shift,\n size,\n} from './middleware';\nexport {platform} from './platform';\nexport type {\n ArrowOptions,\n AutoPlacementOptions,\n AutoUpdateOptions,\n Boundary,\n ComputePositionConfig,\n Derivable,\n DetectOverflowOptions,\n Elements,\n FlipOptions,\n FloatingElement,\n HideOptions,\n Middleware,\n MiddlewareArguments,\n MiddlewareState,\n NodeScroll,\n OffsetOptions,\n Platform,\n ReferenceElement,\n ShiftOptions,\n SizeOptions,\n VirtualElement,\n} from './types';\nexport type {\n AlignedPlacement,\n Alignment,\n Axis,\n ClientRectObject,\n ComputePositionReturn,\n Coords,\n Dimensions,\n ElementContext,\n ElementRects,\n InlineOptions,\n Length,\n LimitShiftOptions,\n MiddlewareData,\n MiddlewareReturn,\n Padding,\n Placement,\n Rect,\n RootBoundary,\n Side,\n SideObject,\n Strategy,\n} from '@floating-ui/core';\n// This export exists only for backwards compatibility. It will be removed in\n// the next major version.\nexport {getOverflowAncestors} from '@floating-ui/utils/dom';\n","import {\n behavior,\n type BehaviorInstance,\n type DomphyElement,\n type ElementNode,\n merge,\n type PartialElement,\n type State,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n autoUpdate,\n computePosition,\n flip,\n offset,\n type Placement,\n shift,\n} from \"@domphy/floating\";\n\ntype FloatingProps = {\n openState: State<boolean>;\n placement: State<Placement>;\n content: DomphyElement;\n // popover's openOn === \"hover\" case: hovering the floating PANEL itself\n // (not just the anchor) must keep it open, so the pointer can travel from\n // trigger to panel without the debounced hide() firing first.\n keepOpenOnContentHover: boolean;\n};\n\ntype FloatingInstance = BehaviorInstance<FloatingProps> & {\n show: () => void;\n hide: () => void;\n};\n\n// The per-anchor persistent state a floating component needs (position\n// cleanup, the inserted panel node, debounce timer) used to live in\n// createFloating()'s own closure — but that closure is recreated fresh every\n// time a reactive ancestor re-renders the anchor (popover()/tooltip() called\n// again on the SAME reused DOM element). Only the FIRST-ever generation's\n// _onMount ever fires (ElementNode hooks run once per node), so imperative,\n// document-level listeners (outside-click, Escape-inside-panel) that closed\n// over that generation's `openState`/`reference`/`floating` kept acting on an\n// orphaned copy forever, while live-rebound trigger events (onClick etc.)\n// moved on to whatever generation was actually current — the trigger opened\n// the panel, but nothing could ever close it again from outside.\n//\n// Fixed by moving all of this into ONE `behavior()` instance per (anchor,\n// kind): `attach` runs once, and every later generation's `show`/`hide`\n// calls and `_behaviors` re-declaration route into that SAME instance via\n// `getBehavior`/`update()` — so there is exactly one canonical `openState`/\n// `reference`/`floating` for the anchor's whole lifetime, not one per\n// generation.\nfunction attachFloating(\n node: ElementNode,\n initialProps: FloatingProps,\n): FloatingInstance {\n let { openState, placement, content, keepOpenOnContentHover } =\n initialProps;\n\n let timer: ReturnType<typeof setTimeout> | null = null;\n let cleanup: (() => void) | null = null;\n let floating: HTMLElement | null = null;\n let floatingNode: ElementNode | null = null;\n let mounted = false;\n\n const reference = node.domElement as HTMLElement;\n const rootNode = node.getRoot();\n\n const floatingPartial: PartialElement = {\n style: {\n position: \"fixed\",\n pointerEvents: \"auto\",\n visibility: (listener) =>\n openState.get(listener) ? \"visible\" : \"hidden\",\n },\n // Escape must dismiss the panel from INSIDE it too: the content is\n // portaled as a DOM sibling of the anchor, so a keydown on a focused\n // element within the panel (menu item, calendar cell, footer button)\n // never bubbles to the anchor's own Escape handler.\n onKeyDown: (event) => {\n if ((event as KeyboardEvent).key === \"Escape\") hide();\n },\n onMouseEnter: () => keepOpenOnContentHover && show(),\n onMouseLeave: () => keepOpenOnContentHover && hide(),\n _onMount: (mountedNode) => {\n floating = mountedNode.domElement as HTMLElement;\n // Propagate data-theme from the trigger's ancestor so floating content\n // inherits CSS variable scope. Stamped on the PANEL, not the shared\n // overlay: the one overlay serves every floating component under the\n // root, so an overlay-level stamp would let whichever anchor opened\n // FIRST permanently impose its theme on later panels anchored under a\n // different [data-theme] scope. Skipped when the content declares its\n // own data-theme.\n if (reference && floating && !floating.hasAttribute(\"data-theme\")) {\n const dataTheme = reference\n .closest(\"[data-theme]\")\n ?.getAttribute(\"data-theme\");\n if (dataTheme) floating.setAttribute(\"data-theme\", dataTheme);\n }\n },\n _portal: (rNode) => {\n let overlay = rNode.domElement!.querySelector(`#domphy-floating`);\n if (!overlay) {\n const overlayEle: DomphyElement<\"div\"> = {\n div: [],\n id: `domphy-floating`,\n style: {\n position: \"fixed\",\n inset: 0,\n zIndex: 20,\n pointerEvents: \"none\",\n },\n };\n const overlayNode = rNode.children!.insert(overlayEle) as ElementNode;\n overlay = overlayNode.domElement!;\n }\n return overlay;\n },\n };\n\n // Later generations declare their OWN fresh `content` object (a new object\n // literal at the popover()/tooltip() call site) — wire it every time, not\n // just at attach, so the panel wiring (theming, portal, dismiss handlers)\n // is present regardless of which generation's content ends up mounted.\n const wireContent = (target: DomphyElement) => merge(target, floatingPartial);\n wireContent(content);\n\n const ensureMounted = () => {\n if (mounted) return;\n mounted = true;\n floatingNode = rootNode.children!.insert(content) as ElementNode;\n };\n\n const instantShow = () => {\n ensureMounted();\n if (reference && floating) {\n cleanup?.();\n cleanup = autoUpdate(reference, floating, () => {\n computePosition(reference as HTMLElement, floating as HTMLElement, {\n placement: placement.get() as Placement,\n middleware: [offset(12), flip(), shift()],\n strategy: \"fixed\",\n }).then(({ x, y, placement: resolved }) => {\n // Teardown can run while computePosition's async work is in\n // flight (it nulls `floating` and removes the panel) — skip the\n // late positioning instead of dereferencing null.\n if (!floating) return;\n Object.assign(floating.style, {\n left: `${x}px`,\n top: `${y}px`,\n });\n placement.set(resolved);\n });\n });\n openState.set(true);\n }\n };\n // Fully unmounts (not just CSS-hides) the panel — mirrors show()'s own\n // insert-on-demand: a closed floating component holds no DOM/listeners.\n // ensureMounted() re-inserts a fresh panel node next time show() runs.\n const instantHide = () => {\n cleanup?.();\n cleanup = null;\n if (floatingNode) {\n floatingNode.remove();\n floatingNode = null;\n }\n floating = null;\n mounted = false;\n openState.set(false);\n };\n const show = () => {\n timer && clearTimeout(timer);\n timer = setTimeout(instantShow, 100);\n };\n const hide = () => {\n timer && clearTimeout(timer);\n timer = setTimeout(instantHide, 100);\n };\n\n const handleOutside = (event: MouseEvent) => {\n if (!openState.get() || !reference || !floating) return;\n const target = event.target as Node;\n if (!reference.contains(target) && !floating.contains(target)) hide();\n };\n rootNode.domElement?.addEventListener(\"click\", handleOutside);\n\n return {\n show,\n hide,\n update(props) {\n openState = props.openState;\n placement = props.placement;\n content = props.content;\n keepOpenOnContentHover = props.keepOpenOnContentHover;\n wireContent(content);\n // Reflect the new generation's declared content into the already-\n // mounted panel in place (same DOM node, no flicker/teardown) — the\n // ordinary reused-node \"patch, don't recreate\" contract, applied to\n // the imperatively-inserted panel too.\n if (floatingNode) floatingNode.patch(content);\n },\n destroy() {\n if (timer) clearTimeout(timer);\n cleanup?.();\n floatingNode?.remove();\n rootNode.domElement?.removeEventListener(\"click\", handleOutside);\n },\n };\n}\n\nfunction createFloating(props: {\n kind: string;\n open?: ValueOrState<boolean>;\n placement: State<Placement>;\n content: DomphyElement;\n keepOpenOnContentHover?: boolean;\n}) {\n const { kind, open = false, placement } = props;\n const openState = toState(open);\n const behaviorKey = `floating:${kind}`;\n\n // Trigger event handlers ARE live-rebound on every patch and already\n // receive the current ElementNode as their 2nd argument (unlike lifecycle\n // hooks) — so show(node)/hide(node) just forward to whatever instance is\n // attached there, regardless of which generation's closure is calling.\n const show = (node?: ElementNode) =>\n node?.getBehavior<FloatingInstance>(behaviorKey)?.show();\n const hide = (node?: ElementNode) =>\n node?.getBehavior<FloatingInstance>(behaviorKey)?.hide();\n\n // Plain spread, NOT merge(): merge() defensively deep-clones its `target`\n // argument, which would snapshot `props.content` right now — but the\n // caller (popover()/tooltip()) hasn't finished mutating it yet (it pushes\n // its OWN partial onto `content.$` right after this call returns). A\n // premature clone silently drops that later mutation, so the panel loses\n // its role/style/dismiss wiring. Spread keeps the `_behaviors` record's\n // `props.content` a live reference to the SAME object the caller mutates.\n const anchorPartial: PartialElement = {\n onKeyDown: (e: Event, node: ElementNode) =>\n (e as KeyboardEvent).key === \"Escape\" && hide(node),\n ...behavior<FloatingProps>(behaviorKey, attachFloating, {\n openState,\n placement,\n content: props.content,\n keepOpenOnContentHover: !!props.keepOpenOnContentHover,\n }),\n };\n\n return { show, hide, anchorPartial };\n}\n\nexport { createFloating };\n","import type { DomphyElement, PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\nconst xSvg = `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"currentColor\"><path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/><path d=\"M6.707 5.293l5.293 5.292l5.293 -5.292a1 1 0 0 1 1.414 1.414l-5.292 5.293l5.292 5.293a1 1 0 0 1 -1.414 1.414l-5.293 -5.292l-5.293 5.292a1 1 0 1 1 -1.414 -1.414l5.292 -5.293l-5.292 -5.293a1 1 0 0 1 1.414 -1.414\" /></svg>`;\n\n/**\n * Styles an inline chip/tag (rounded, bordered, optional remove button).\n * No host tag check; typically applied to a `<span>`. When `removable` is true,\n * a close button is inserted that removes the host node on click.\n *\n * @hostTag span\n * @param props.color - Theme color for the chip background/border/text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @param props.removable - When true, renders a remove (x) button that removes the tag on click. Optional. Defaults to `false`.\n * @example { span: \"Label\", $: [tag({ removable: true })] }\n */\nfunction tag(\n props: { color?: ValueOrState<ThemeColor>; removable?: boolean } = {},\n): PartialElement {\n const { removable = false } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInit: (node) => {\n const removeBtn: DomphyElement<\"span\"> = {\n span: xSvg,\n onClick: (e) => {\n (e as Event).stopPropagation();\n node.remove();\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n cursor: \"pointer\",\n borderRadius: themeSpacing(1),\n width: themeSpacing(4),\n height: themeSpacing(4),\n flexShrink: 0,\n \"&:hover\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", color.get(listener)),\n },\n },\n };\n\n removable && node.children.insert(removeBtn);\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n whiteSpace: \"nowrap\",\n userSelect: \"none\",\n height: themeSpacing(6),\n paddingBlock: 0,\n borderRadius: themeSpacing(1),\n paddingInlineStart: themeSpacing(2),\n paddingInlineEnd: removable ? themeSpacing(1) : themeSpacing(2),\n gap: themeSpacing(2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n },\n };\n}\n\nexport { tag };\n","import {\n type DomphyElement,\n merge,\n type PartialElement,\n type StyleObject,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\nimport { tag } from \"./tag.js\";\n\n/**\n * A combobox/multi-select control: renders selected options as removable tags\n * plus an input, and shows a floating popover (`content`) anchored to the host.\n * Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props.multiple - Allow selecting multiple values (popover stays open on click). Optional `boolean`, default false.\n * @param props.value - Selected value(s). Optional `ValueOrState<Array<number | string | null | undefined> | number | string | null | undefined>`, no default.\n * @param props.options - Available `{ label, value }` options used to render selected tags. Optional `Array<{ label: string; value: string }>`, default `[]`.\n * @param props.placement - Floating popover placement. Optional `ValueOrState<Placement>`, default \"bottom\".\n * @param props.content - The floating popover content element. Required `DomphyElement`.\n * @param props.color - Color tone for the control. Optional `ThemeColor`, default \"neutral\".\n * @param props.open - Whether the popover is open. Optional `ValueOrState<boolean>`, default false.\n * @param props.input - Custom input element; when omitted a default `<input>` is created. Optional `DomphyElement`.\n * @example { div: null, $: [combobox({ options: [{ label: \"A\", value: \"a\" }], content: { div: null } })] }\n */\nfunction combobox(props: {\n multiple?: boolean;\n value?: ValueOrState<\n | Array<number | string | null | undefined>\n | number\n | string\n | null\n | undefined\n >;\n options?: Array<{ label: string; value: string }>;\n placement?: ValueOrState<Placement>;\n content: DomphyElement;\n color?: ThemeColor;\n open?: ValueOrState<boolean>;\n input?: DomphyElement;\n}): PartialElement {\n const {\n options = [],\n placement = \"bottom\",\n color = \"neutral\",\n open = false,\n multiple = false,\n } = props;\n\n const state = toState(props.value);\n const openState = toState(open);\n const { show, hide, anchorPartial } = createFloating({\n kind: \"combobox\",\n open: openState,\n placement: toState(placement),\n content: props.content,\n });\n\n const popoverPartial: PartialElement = {\n onClick: (_e, node) => !multiple && hide(node),\n dataTone: \"shift-14\",\n style: {\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\")}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n };\n\n merge(props.content, popoverPartial);\n\n const inputStyle: StyleObject = {\n border: \"none\",\n outline: \"none\",\n padding: 0,\n margin: 0,\n flex: 1,\n height: themeSpacing(6),\n marginInlineStart: themeSpacing(2),\n fontSize: (listener: any) => themeSize(listener, \"inherit\"),\n color: (listener: any) => themeColor(listener, \"text\", color),\n backgroundColor: (listener: any) => themeColor(listener, \"inherit\", color),\n };\n\n let inputElement: DomphyElement;\n if (props.input) {\n const inputPartial: PartialElement = {\n onFocus: (_e, node) => show(node),\n style: inputStyle,\n _key: \"combobox-input\",\n };\n merge(props.input, inputPartial);\n inputElement = props.input;\n } else {\n inputElement = {\n input: null,\n onFocus: (_e, node) => show(node),\n value: (listener: any) => {\n state.get(listener);\n return \"\";\n },\n style: inputStyle,\n _key: \"combobox-input\",\n };\n }\n\n const wrap: DomphyElement<\"div\"> = {\n div: (listener) => {\n const val = state.get(listener);\n const vals = Array.isArray(val) ? val : [val];\n const opts = options.filter((opt) => vals.includes(opt.value));\n const items: DomphyElement[] = opts.map((opt) => {\n return {\n span: opt.label,\n $: [tag({ color, removable: true })],\n _key: opt.value,\n _onRemove: (_node) => {\n const cur = state.get();\n const curVals = Array.isArray(cur) ? cur : [cur];\n const filter = curVals.filter((v) => v !== opt.value);\n multiple ? state.set(filter as any) : state.set(filter[0] as any);\n },\n };\n });\n items.push(inputElement);\n return items;\n },\n style: {\n display: \"flex\",\n flexWrap: \"wrap\",\n gap: themeSpacing(1),\n },\n };\n\n const partial: PartialElement = {\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"combobox\" primitive patch must use div tag`);\n }\n },\n _onInit: (node) => node.children.insert(wrap),\n style: {\n minWidth: themeSpacing(32),\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n },\n };\n\n merge(anchorPartial, partial);\n return anchorPartial;\n}\n\nexport { combobox };\n","import { merge, type PartialElement, toState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Command-palette container patch. Sets up a vertical flex column and provides a\n * shared `command` context (a query State) consumed by `commandSearch` and\n * `commandItem` descendants to filter the list. Typically applied to a `<div>`.\n *\n * @example { div: [...], $: [command()] }\n */\nfunction command(): PartialElement {\n return {\n _onSchedule: (_node, element) => {\n merge(element, {\n _context: {\n command: {\n query: toState(\"\"),\n },\n },\n });\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n overflow: \"hidden\",\n },\n };\n}\n\n/**\n * Search input for a command palette. Wires the input's value into the parent\n * `command` context's query State so descendant `commandItem`s filter live.\n * Apply to an `<input>` element used inside a `command()`.\n *\n * @hostTag input\n * @param props.color - Base theme color tone. Defaults to \"neutral\".\n * @param props.accentColor - Accent color used for the focus border. Defaults to \"primary\".\n * @example { input: \"\", $: [commandSearch({ accentColor: \"primary\" })] }\n */\nfunction commandSearch(\n props: { color?: ThemeColor; accentColor?: ThemeColor } = {},\n): PartialElement {\n const { color = \"neutral\", accentColor = \"primary\" } = props;\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"commandSearch\" patch must use input tag`);\n }\n },\n _onMount: (node) => {\n const ctx = node.getContext(\"command\");\n if (!ctx) {\n console.warn(`\"commandSearch\" patch must be used inside a \"command\"`);\n return;\n }\n const input = node.domElement as HTMLInputElement;\n const onInput = () => ctx.query.set(input.value);\n input.addEventListener(\"input\", onInput);\n node.addHook(\"Remove\", () => input.removeEventListener(\"input\", onInput));\n },\n style: {\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n border: \"none\",\n borderBottom: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color)}`,\n outline: \"none\",\n color: (listener) => themeColor(listener, \"shift-10\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n \"&::placeholder\": {\n color: (listener) => themeColor(listener, \"shift-7\"),\n },\n \"&:focus-visible\": {\n borderBottomColor: (listener) =>\n themeColor(listener, \"shift-6\", accentColor),\n },\n },\n };\n}\n\n/**\n * Selectable item (`role=\"option\"`) in a command palette. On mount, immediately\n * hides itself if the current query doesn't match its text content, and subscribes\n * to future query changes — so items added dynamically after a search is typed are\n * correctly filtered. Typically applied to a `<button>` (or any clickable element)\n * used inside a `command()`.\n *\n * @param props.color - Base theme color tone. Defaults to \"neutral\".\n * @param props.accentColor - Accent color used for the focus outline. Defaults to \"primary\".\n * @example { button: \"Open file\", $: [commandItem({ color: \"neutral\" })] }\n */\nfunction commandItem(\n props: { color?: ThemeColor; accentColor?: ThemeColor } = {},\n): PartialElement {\n const { color = \"neutral\", accentColor = \"primary\" } = props;\n return {\n role: \"option\",\n _onMount: (node) => {\n const ctx = node.getContext(\"command\");\n if (!ctx) {\n console.warn(`\"commandItem\" patch must be used inside a \"command\"`);\n return;\n }\n const el = node.domElement as HTMLElement;\n const text = el.textContent?.toLowerCase() ?? \"\";\n const applyFilter = (q: string) => {\n el.hidden = q.length > 0 && !text.includes(q.toLowerCase());\n };\n applyFilter(ctx.query.get());\n const release = ctx.query.addListener(applyFilter);\n node.addHook(\"Remove\", release);\n },\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n width: \"100%\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n border: \"none\",\n outline: \"none\",\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener) => themeColor(listener, \"hover\", color),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor)}`,\n outlineOffset: `-${themeSpacing(0.5)}`,\n },\n },\n };\n}\n\nexport { command, commandSearch, commandItem };\n","import {\n type DomphyElement,\n type ElementNode,\n type Listener,\n merge,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\n\n/** A single date selection, or a `[start, end]` tuple in range mode. */\nexport type DatePickerValue = Date | null | [Date | null, Date | null];\n\nexport interface DatePickerProps {\n /** Controlled value: a `Date` in single mode, a `[start, end]` tuple in range mode. */\n value?: ValueOrState<DatePickerValue>;\n /** Selection mode. */\n mode?: \"single\" | \"range\";\n /** Also pick hour + minute. The chosen time applies to the selected date(s). */\n time?: boolean;\n /** Earliest selectable day (inclusive). */\n min?: Date;\n /** Latest selectable day (inclusive). */\n max?: Date;\n /** Disable arbitrary days. */\n disabledDate?: (date: Date) => boolean;\n /** BCP-47 locale for month/weekday names, first-day-of-week, and formatting. */\n locale?: string;\n /** Override the first day of the week (0 = Sunday … 6 = Saturday). */\n weekStartsOn?: number;\n /** Override the input display string. */\n format?: (value: DatePickerValue) => string;\n /** Called whenever the selection changes. */\n onChange?: (value: DatePickerValue) => void;\n /** Accent color for the selected/active days. */\n accentColor?: ValueOrState<ThemeColor>;\n /** Popover placement relative to the input. */\n placement?: ValueOrState<Placement>;\n}\n\n// --- date helpers (no third-party library) -----------------------------------\n\nconst atMidnight = (date: Date): Date =>\n new Date(date.getFullYear(), date.getMonth(), date.getDate());\nconst addDays = (date: Date, count: number): Date =>\n new Date(date.getFullYear(), date.getMonth(), date.getDate() + count);\nconst addMonths = (date: Date, count: number): Date =>\n new Date(date.getFullYear(), date.getMonth() + count, date.getDate());\nconst sameDay = (a: Date | null, b: Date | null): boolean =>\n !!a &&\n !!b &&\n a.getFullYear() === b.getFullYear() &&\n a.getMonth() === b.getMonth() &&\n a.getDate() === b.getDate();\nconst isoOf = (date: Date): string =>\n `${date.getFullYear()}-${String(date.getMonth() + 1).padStart(2, \"0\")}-${String(\n date.getDate(),\n ).padStart(2, \"0\")}`;\nconst startOfWeek = (date: Date, weekStart: number): Date =>\n addDays(date, -((date.getDay() - weekStart + 7) % 7));\n\n/** Resolves the locale's first day of week, falling back to Sunday. */\nfunction localeWeekStart(locale: string): number {\n try {\n const localeObject = new Intl.Locale(locale) as Intl.Locale & {\n weekInfo?: { firstDay: number };\n getWeekInfo?: () => { firstDay: number };\n };\n const info = localeObject.getWeekInfo?.() ?? localeObject.weekInfo;\n if (info?.firstDay) return info.firstDay % 7; // Intl uses 1=Mon … 7=Sun\n } catch {\n // unsupported locale or engine — fall through to Sunday\n }\n return 0;\n}\n\n/**\n * A native, themeable date picker patch for an `<input>`. Opens a calendar\n * popover (rendered with Domphy elements, positioned via `@domphy/floating`)\n * supporting single/range selection, optional time, min/max + disabled days,\n * localized names, and keyboard navigation. The input is read-only and shows the\n * formatted selection; compose with `inputText()` for the input's look.\n *\n * @hostTag input\n * @param props.value - Controlled value (`ValueOrState<DatePickerValue>`): a `Date`/`null` in single mode, a `[start, end]` tuple in range mode.\n * @param props.mode - Selection mode, \"single\" | \"range\". Defaults to \"single\".\n * @param props.time - When true, also pick hour + minute (applied to the selected date(s)). Defaults to false.\n * @param props.min - Earliest selectable day (inclusive), a `Date`.\n * @param props.max - Latest selectable day (inclusive), a `Date`.\n * @param props.disabledDate - Predicate `(date: Date) => boolean` to disable arbitrary days.\n * @param props.locale - BCP-47 locale for names/first-day-of-week/formatting. Defaults to `navigator.language` (or \"en-US\" in non-browser).\n * @param props.weekStartsOn - Override first day of week (0 = Sunday … 6 = Saturday). Defaults to the locale's first day.\n * @param props.format - Override the input display string, `(value: DatePickerValue) => string`.\n * @param props.onChange - Called with the new value whenever the selection changes, `(value: DatePickerValue) => void`.\n * @param props.accentColor - Accent color (`ValueOrState<ThemeColor>`) for selected/active days. Defaults to \"primary\".\n * @param props.placement - Popover placement (`ValueOrState<Placement>`) relative to the input. Defaults to \"bottom-start\".\n * @example { input: \"\", $: [inputText(), datePicker({ mode: \"range\" })] }\n */\nfunction datePicker(props: DatePickerProps = {}): PartialElement {\n const {\n mode = \"single\",\n time = false,\n min,\n max,\n disabledDate,\n locale = typeof navigator !== \"undefined\" ? navigator.language : \"en-US\",\n format,\n onChange,\n } = props;\n\n const weekStart = props.weekStartsOn ?? localeWeekStart(locale);\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n const placeState = toState(props.placement ?? \"bottom-start\");\n\n const selection = toState<DatePickerValue>(\n props.value ?? (mode === \"range\" ? [null, null] : null),\n );\n const releaseOnChange = onChange\n ? selection.addListener((value) => onChange(value))\n : null;\n\n const primaryDate = ((): Date => {\n const current = selection.get();\n const base =\n mode === \"range\" ? (current as [Date | null, Date | null])?.[0] : current;\n return base instanceof Date ? base : new Date();\n })();\n\n const viewYear = toState(primaryDate.getFullYear(), \"viewYear\");\n const viewMonth = toState(primaryDate.getMonth(), \"viewMonth\");\n const focused = toState<Date>(atMidnight(primaryDate), \"focused\");\n const hovered = toState<Date | null>(null, \"hovered\");\n const hour = toState(primaryDate.getHours(), \"hour\");\n const minute = toState(primaryDate.getMinutes(), \"minute\");\n\n let contentElement: HTMLElement | null = null;\n\n // --- formatting -----------------------------------------------------------\n const dateFormatter = new Intl.DateTimeFormat(locale, {\n dateStyle: \"medium\",\n ...(time ? { timeStyle: \"short\" as const } : {}),\n });\n const monthFormatter = new Intl.DateTimeFormat(locale, {\n month: \"long\",\n year: \"numeric\",\n });\n const weekdayFormatter = new Intl.DateTimeFormat(locale, {\n weekday: \"short\",\n });\n const fullDateFormatter = new Intl.DateTimeFormat(locale, {\n dateStyle: \"full\",\n });\n\n const formatOne = (date: Date | null): string =>\n date ? dateFormatter.format(date) : \"\";\n const formatDisplay = (value: DatePickerValue): string => {\n if (format) return format(value);\n if (mode === \"range\") {\n const [start, end] = (value as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n return start ? `${formatOne(start)} – ${formatOne(end)}` : \"\";\n }\n return formatOne(value as Date | null);\n };\n\n // 2023-01-01 is a Sunday, so index 0 maps to Sunday before the week-start shift.\n const weekdayNames = Array.from({ length: 7 }, (_unused, index) =>\n weekdayFormatter.format(new Date(2023, 0, 1 + ((index + weekStart) % 7))),\n );\n\n // --- selection logic ------------------------------------------------------\n const isDisabled = (date: Date): boolean =>\n (!!min && atMidnight(date) < atMidnight(min)) ||\n (!!max && atMidnight(date) > atMidnight(max)) ||\n (!!disabledDate && disabledDate(date));\n\n const withTime = (date: Date): Date => {\n if (!time) return atMidnight(date);\n const result = atMidnight(date);\n result.setHours(hour.get(), minute.get(), 0, 0);\n return result;\n };\n\n const selectDate = (date: Date): void => {\n if (isDisabled(date)) return;\n if (mode === \"single\") {\n selection.set(withTime(date));\n if (!time) instantHideRef();\n return;\n }\n const [start, end] = (selection.get() as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n if (!start || (start && end)) {\n selection.set([withTime(date), null]);\n } else if (atMidnight(date) < atMidnight(start)) {\n selection.set([withTime(date), withTime(start)]);\n if (!time) instantHideRef();\n } else {\n selection.set([start, withTime(date)]);\n if (!time) instantHideRef();\n }\n };\n\n const reapplyTime = (): void => {\n if (!time) return;\n if (mode === \"single\") {\n const current = selection.get() as Date | null;\n if (current) selection.set(withTime(current));\n } else {\n const [start, end] = (selection.get() as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n selection.set([\n start ? withTime(start) : start,\n end ? withTime(end) : end,\n ]);\n }\n };\n\n const inSelectedRange = (date: Date, listener?: Listener): boolean => {\n if (mode !== \"range\") return false;\n const [start, end] = (selection.get(listener) as [\n Date | null,\n Date | null,\n ]) ?? [null, null];\n const tail = end ?? hovered.get(listener);\n if (!start || !tail) return false;\n const low = atMidnight(start) <= atMidnight(tail) ? start : tail;\n const high = atMidnight(start) <= atMidnight(tail) ? tail : start;\n const day = atMidnight(date);\n return day >= atMidnight(low) && day <= atMidnight(high);\n };\n\n const isSelectedEnd = (date: Date, listener?: Listener): boolean => {\n const current = selection.get(listener);\n if (mode === \"range\") {\n const [start, end] = (current as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n return sameDay(date, start) || sameDay(date, end);\n }\n return sameDay(date, current as Date | null);\n };\n\n // --- view navigation ------------------------------------------------------\n const goToDate = (date: Date): void => {\n viewYear.set(date.getFullYear());\n viewMonth.set(date.getMonth());\n };\n const shiftMonth = (delta: number): void => {\n const next = addMonths(new Date(viewYear.get(), viewMonth.get(), 1), delta);\n goToDate(next);\n };\n const shiftYear = (delta: number): void =>\n viewYear.set(viewYear.get() + delta);\n\n const focusActiveCell = (): void => {\n setTimeout(() => {\n contentElement\n ?.querySelector<HTMLElement>(`[data-date=\"${isoOf(focused.get())}\"]`)\n ?.focus();\n }, 0);\n };\n\n // --- floating popover ------------------------------------------------------\n const calendar = buildCalendar();\n const { show, hide, anchorPartial } = createFloating({\n kind: \"datePicker\",\n open: false,\n placement: placeState,\n content: calendar,\n });\n // selectDate calls this before `createFloating` returns `hide`, so route through a ref.\n function instantHideRef(): void {\n hide();\n }\n\n // Move focus into the grid when the popover opens.\n anchorPartial.onClick = () => {};\n const triggerPartial: PartialElement = {\n type: \"text\",\n readonly: true,\n value: (listener) => formatDisplay(selection.get(listener)),\n ariaHaspopup: \"dialog\",\n ariaLabel: \"Choose date\",\n style: { cursor: \"pointer\" },\n onClick: (_e, node) => {\n openAndFocus(node);\n },\n onFocus: (_e, node) => {\n openAndFocus(node);\n },\n onKeyDown: (event, node) => {\n const key = (event as KeyboardEvent).key;\n if (key === \"ArrowDown\" || key === \"Enter\") {\n event.preventDefault();\n openAndFocus(node);\n }\n },\n _onMount: (node) =>\n releaseOnChange &&\n node.addHook(\"Remove\", () => {\n releaseOnChange();\n }),\n };\n function openAndFocus(node?: ElementNode): void {\n const current = isSelectedPrimary() ?? new Date();\n focused.set(atMidnight(current));\n goToDate(current);\n show(node);\n focusActiveCell();\n }\n function isSelectedPrimary(): Date | null {\n const current = selection.get();\n if (mode === \"range\")\n return (current as [Date | null, Date | null])?.[0] ?? null;\n return (current as Date | null) ?? null;\n }\n merge(anchorPartial, triggerPartial);\n return anchorPartial;\n\n // --- calendar builder -----------------------------------------------------\n function buildCalendar(): DomphyElement<\"div\"> {\n const navButton = (label: string, ariaLabel: string, onClick: () => void) =>\n ({\n button: label,\n type: \"button\",\n ariaLabel,\n onClick,\n style: navButtonStyle(),\n }) as DomphyElement;\n\n const header: DomphyElement<\"div\"> = {\n div: [\n navButton(\"«\", \"Previous year\", () => shiftYear(-1)),\n navButton(\"‹\", \"Previous month\", () => shiftMonth(-1)),\n {\n div: (listener) =>\n monthFormatter.format(\n new Date(viewYear.get(listener), viewMonth.get(listener), 1),\n ),\n ariaLive: \"polite\",\n style: {\n flex: \"1\",\n textAlign: \"center\",\n fontWeight: \"600\",\n fontSize: (listener) => themeSize(listener),\n },\n },\n navButton(\"›\", \"Next month\", () => shiftMonth(1)),\n navButton(\"»\", \"Next year\", () => shiftYear(1)),\n ],\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(1),\n marginBottom: themeSpacing(2),\n },\n };\n\n const weekdayHeader: DomphyElement<\"div\"> = {\n div: weekdayNames.map((name, index) => ({\n div: name,\n style: {\n textAlign: \"center\",\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n fontWeight: \"600\",\n color: (listener) => themeColor(listener, \"shift-7\"),\n paddingBlock: themeSpacing(1),\n },\n _key: index,\n })),\n role: \"row\",\n style: gridRowStyle(),\n };\n\n const grid: DomphyElement<\"div\"> = {\n div: (listener) => buildWeeks(listener),\n role: \"grid\",\n ariaLabel: \"Calendar\",\n onKeyDown: onGridKey,\n onMouseLeave: () => mode === \"range\" && hovered.set(null),\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: themeSpacing(0.5),\n },\n };\n\n const children: DomphyElement[] = [header, weekdayHeader, grid];\n if (time) children.push(buildTimeRow());\n children.push(buildFooter());\n\n return {\n div: children,\n role: \"dialog\",\n ariaModal: \"false\",\n _onMount: (node) => {\n contentElement = node.domElement as HTMLElement;\n },\n style: {\n minWidth: themeSpacing(70),\n padding: themeSpacing(3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n backgroundColor: (listener) => themeColor(listener, \"base\"),\n color: (listener) => themeColor(listener, \"shift-10\"),\n border: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\")}`,\n boxShadow: elevation(\"medium\"),\n },\n };\n }\n\n function buildWeeks(listener: Listener): DomphyElement[] {\n const first = new Date(viewYear.get(listener), viewMonth.get(listener), 1);\n const month = viewMonth.get(listener);\n const start = startOfWeek(first, weekStart);\n const weeks: DomphyElement[] = [];\n for (let week = 0; week < 6; week++) {\n const cells: DomphyElement[] = [];\n for (let day = 0; day < 7; day++) {\n const date = addDays(start, week * 7 + day);\n cells.push(buildDayCell(date, month, listener));\n }\n weeks.push({\n div: cells,\n role: \"row\",\n style: gridRowStyle(),\n _key: week,\n });\n }\n return weeks;\n }\n\n function buildDayCell(\n date: Date,\n month: number,\n listener: Listener,\n ): DomphyElement {\n const disabled = isDisabled(date);\n const selected = isSelectedEnd(date, listener);\n const within = inSelectedRange(date, listener);\n const outside = date.getMonth() !== month;\n const isFocused = sameDay(date, focused.get(listener));\n const isToday = sameDay(date, new Date());\n\n return {\n button: String(date.getDate()),\n type: \"button\",\n role: \"gridcell\",\n tabIndex: isFocused ? 0 : -1,\n ariaSelected: selected,\n ariaDisabled: disabled,\n disabled,\n ariaLabel: fullDateFormatter.format(date),\n dataDate: isoOf(date),\n onClick: () => selectDate(date),\n onMouseEnter: () => mode === \"range\" && hovered.set(date),\n style: {\n appearance: \"none\",\n border: \"none\",\n cursor: disabled ? \"not-allowed\" : \"pointer\",\n aspectRatio: \"1\",\n borderRadius: themeSpacing(1),\n fontSize: (l: Listener) => themeSize(l),\n fontFamily: \"inherit\",\n opacity: disabled ? 0.35 : outside ? 0.5 : 1,\n backgroundColor: (l: Listener) =>\n selected\n ? themeColor(l, \"shift-7\", accentColor.get(l))\n : within\n ? themeColor(l, \"hover\", accentColor.get(l))\n : \"transparent\",\n color: (l: Listener) =>\n selected\n ? themeColor(l, \"shift-0\", accentColor.get(l))\n : themeColor(l, \"text\"),\n outline: isToday\n ? (l: Listener) =>\n `1px solid ${themeColor(l, \"shift-6\", accentColor.get(l))}`\n : \"none\",\n outlineOffset: \"-2px\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (l: Listener) =>\n selected\n ? themeColor(l, \"shift-7\", accentColor.get(l))\n : themeColor(l, \"shift-3\", accentColor.get(l)),\n },\n \"&:focus-visible\": {\n outline: (l: Listener) =>\n `2px solid ${themeColor(l, \"shift-6\", accentColor.get(l))}`,\n },\n },\n _key: isoOf(date),\n } as DomphyElement;\n }\n\n function buildTimeRow(): DomphyElement<\"div\"> {\n const numberSelect = (\n count: number,\n state: ReturnType<typeof toState<number>>,\n ariaLabel: string,\n ): DomphyElement => ({\n select: Array.from({ length: count }, (_unused, value) => ({\n option: String(value).padStart(2, \"0\"),\n value: String(value),\n selected: (listener) => state.get(listener) === value,\n _key: value,\n })) as DomphyElement[],\n ariaLabel,\n onChange: (event) => {\n state.set(Number((event.target as HTMLSelectElement).value));\n reapplyTime();\n },\n style: timeSelectStyle(),\n });\n\n return {\n div: [\n numberSelect(24, hour, \"Hour\"),\n { span: \":\", style: { fontWeight: \"600\" } },\n numberSelect(60, minute, \"Minute\"),\n ],\n style: {\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n gap: themeSpacing(1),\n marginTop: themeSpacing(3),\n },\n };\n }\n\n function buildFooter(): DomphyElement<\"div\"> {\n const action = (label: string, onClick: () => void): DomphyElement => ({\n button: label,\n type: \"button\",\n onClick,\n style: {\n appearance: \"none\",\n border: \"none\",\n background: \"transparent\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n fontSize: (l: Listener) => themeSize(l, \"decrease-1\"),\n color: (l: Listener) => themeColor(l, \"muted\", accentColor.get(l)),\n padding: themeSpacing(1),\n },\n });\n return {\n div: [\n action(\"Today\", () => {\n const today = new Date();\n focused.set(atMidnight(today));\n goToDate(today);\n focusActiveCell();\n }),\n action(\"Clear\", () => {\n selection.set(mode === \"range\" ? [null, null] : null);\n hovered.set(null);\n }),\n ],\n style: {\n display: \"flex\",\n justifyContent: \"space-between\",\n marginTop: themeSpacing(2),\n paddingTop: themeSpacing(2),\n borderTop: (l: Listener) => `1px solid ${themeColor(l, \"border\")}`,\n },\n };\n }\n\n function onGridKey(event: Event): void {\n const keyboard = event as KeyboardEvent;\n const current = focused.get();\n let next: Date | null = null;\n switch (keyboard.key) {\n case \"ArrowLeft\":\n next = addDays(current, -1);\n break;\n case \"ArrowRight\":\n next = addDays(current, 1);\n break;\n case \"ArrowUp\":\n next = addDays(current, -7);\n break;\n case \"ArrowDown\":\n next = addDays(current, 7);\n break;\n case \"Home\":\n next = startOfWeek(current, weekStart);\n break;\n case \"End\":\n next = addDays(startOfWeek(current, weekStart), 6);\n break;\n case \"PageUp\":\n next = addMonths(current, keyboard.shiftKey ? -12 : -1);\n break;\n case \"PageDown\":\n next = addMonths(current, keyboard.shiftKey ? 12 : 1);\n break;\n case \"Enter\":\n case \" \":\n keyboard.preventDefault();\n selectDate(current);\n return;\n default:\n return;\n }\n keyboard.preventDefault();\n focused.set(next);\n goToDate(next);\n focusActiveCell();\n }\n}\n\n// --- shared style fragments --------------------------------------------------\n\nfunction gridRowStyle() {\n return {\n display: \"grid\",\n gridTemplateColumns: \"repeat(7, 1fr)\",\n gap: themeSpacing(0.5),\n };\n}\n\nfunction navButtonStyle() {\n return {\n appearance: \"none\" as const,\n border: \"none\",\n background: \"transparent\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n fontSize: (l: Listener) => themeSize(l),\n color: (l: Listener) => themeColor(l, \"muted\"),\n width: themeSpacing(7),\n height: themeSpacing(7),\n borderRadius: themeSpacing(1),\n \"&:hover\": {\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\"),\n },\n };\n}\n\nfunction timeSelectStyle() {\n return {\n fontFamily: \"inherit\",\n fontSize: (l: Listener) => themeSize(l),\n padding: themeSpacing(1),\n borderRadius: themeSpacing(1),\n border: (l: Listener) => `1px solid ${themeColor(l, \"border-strong\")}`,\n backgroundColor: (l: Listener) => themeColor(l, \"base\"),\n color: (l: Listener) => themeColor(l, \"text\"),\n };\n}\n\nexport { datePicker };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a description list as a two-column grid (terms in the first column,\n * descriptions in the second), theming the nested `<dt>`/`<dd>` elements.\n * Apply to a `<dl>` element.\n *\n * @hostTag dl\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the term/description text. Defaults to \"neutral\".\n * @example { dl: [{ dt: \"Name\" }, { dd: \"Domphy\" }], $: [descriptionList()] }\n */\nfunction descriptionList(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"dl\") {\n console.warn(`\"descriptionList\" primitive patch must use dl tag`);\n }\n },\n style: {\n display: \"grid\",\n gridTemplateColumns: `minmax(${themeSpacing(24)}, max-content) 1fr`,\n columnGap: themeSpacing(4),\n margin: 0,\n \"& dt\": {\n margin: 0,\n fontWeight: 600,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n },\n \"& dd\": {\n margin: 0,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n },\n };\n}\n\nexport { descriptionList };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a native disclosure widget: a themed `<summary>` header with an\n * animated rotating chevron and an expand/collapse transition on the body\n * content. Apply to a `<details>` element.\n *\n * @hostTag details\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the body/summary. Defaults to \"neutral\".\n * @param props.accentColor - Accent color (`ValueOrState<ThemeColor>`) for the summary's focus outline. Defaults to \"primary\".\n * @param props.duration - Open/close transition duration in milliseconds. Defaults to 240.\n * @example { details: [{ summary: \"More\" }, { div: \"Body\" }], $: [details()] }\n */\nfunction details(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n duration?: number;\n } = {},\n): PartialElement {\n const { duration = 240 } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"details\") {\n console.warn(`\"details\" primitive patch must use details tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n\n overflow: \"hidden\",\n \"& > summary\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n listStyle: \"none\",\n display: \"flex\",\n justifyContent: \"space-between\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n cursor: \"pointer\",\n userSelect: \"none\",\n fontWeight: 500,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n height: themeSpacing(10),\n },\n \"& > summary::-webkit-details-marker\": {\n display: \"none\",\n },\n \"& > summary::marker\": {\n content: `\"\"`,\n },\n \"& > summary::after\": {\n content: `\"\"`,\n width: themeSpacing(2),\n height: themeSpacing(2),\n flexShrink: 0,\n marginTop: `-${themeSpacing(0.5)}`,\n borderInlineEnd: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-9\", color.get(listener))}`,\n borderBottom: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-9\", color.get(listener))}`,\n transform: \"rotate(45deg)\",\n transition: `transform ${duration}ms ease`,\n },\n \"&[open] > summary::after\": {\n transform: \"rotate(-135deg)\",\n },\n \"& > summary:hover\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n },\n \"& > summary:focus-visible\": {\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n outlineOffset: `-${themeSpacing(0.5)}`,\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"& > :not(summary)\": {\n maxHeight: 0,\n opacity: 0,\n overflow: \"hidden\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingTop: 0,\n paddingBottom: 0,\n transition: `max-height ${duration}ms ease, opacity ${duration}ms ease, padding ${duration}ms ease`,\n },\n \"&[open] > :not(summary)\": {\n maxHeight: themeSpacing(250),\n opacity: 1,\n paddingTop: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingBottom: (listener) => themeSpacing(themeDensity(listener) * 3),\n },\n },\n };\n}\n\nexport { details };\n","// Shared page-scroll lock for modal-like patches (dialog, drawer). A\n// module-level counter (not a plain boolean) is required because two\n// overlays can be open at once (e.g. a dialog opened from within a drawer);\n// without a counter, closing the inner one would clear `overflow` while the\n// outer one is still open.\nlet lockCount = 0;\n\nfunction lockScroll(): void {\n lockCount++;\n if (lockCount === 1) document.body.style.overflow = \"hidden\";\n}\n\nfunction unlockScroll(): void {\n lockCount = Math.max(0, lockCount - 1);\n if (lockCount === 0) document.body.style.overflow = \"\";\n}\n\n// Test-only: reset the module-level counter so a test that unmounts its tree\n// via `document.body.innerHTML = \"\"` (skipping the Remove hook / unlockScroll\n// call) doesn't leak a locked count into the next test.\nfunction _resetScrollLock(): void {\n lockCount = 0;\n}\n\nexport { lockScroll, unlockScroll, _resetScrollLock };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { lockScroll, unlockScroll } from \"../utils/scrollLock.js\";\n\nconst FOCUSABLE =\n 'button:not([disabled]), [href], input:not([disabled]), select:not([disabled]), textarea:not([disabled]), details, [tabindex]:not([tabindex=\"-1\"])';\n\n/**\n * Modal dialog patch driven by an `open` State. Calls `showModal()`/`close()`,\n * fades via opacity, locks page scroll while open, traps Tab focus within the\n * dialog, restores focus to the previously focused element on close, sets\n * `aria-modal`, and closes on outside (backdrop) click. Apply to a `<dialog>`.\n *\n * @hostTag dialog\n * @param props.color - Theme color tone for the dialog surface. Defaults to \"neutral\".\n * @param props.open - Open state (`ValueOrState<boolean>`); set it to true/false to show/hide. Defaults to false.\n * @example { dialog: [...], $: [dialog({ open })] }\n */\nfunction dialog(\n props: { color?: ThemeColor; open?: ValueOrState<boolean> } = {},\n): PartialElement {\n const { color = \"neutral\", open = false } = props;\n const state = toState(open);\n let previousFocus: HTMLElement | null = null;\n let closing = false;\n let scrollLocked = false;\n\n const finalizeClose = (dlg: HTMLDialogElement) => {\n closing = false;\n dlg.close();\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n previousFocus?.focus();\n previousFocus = null;\n };\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"dialog\") {\n console.warn(`\"dialog\" primitive patch must use dialog tag`);\n }\n },\n onClick: (e: MouseEvent, node) => {\n if (e.target !== node.domElement) return;\n const r = node.domElement!.getBoundingClientRect();\n const inside =\n e.clientX >= r.left &&\n e.clientX <= r.right &&\n e.clientY >= r.top &&\n e.clientY <= r.bottom;\n if (!inside) state.set(false);\n },\n onTransitionEnd: (e, node) => {\n if (!closing) return;\n // Guard against bubbled transitionend from nested content (e.g. an\n // accordion/details transition inside the dialog) prematurely\n // triggering close-finalization.\n if (e.target !== node.domElement) return;\n if (e.propertyName !== \"opacity\") return;\n finalizeClose(node.domElement as HTMLDialogElement);\n },\n _onMount: (node) => {\n const dlg = node.domElement as HTMLDialogElement;\n dlg.setAttribute(\"aria-modal\", \"true\");\n let closeTimer: ReturnType<typeof setTimeout> | null = null;\n\n const trapFocus = (e: KeyboardEvent) => {\n if (e.key !== \"Tab\") return;\n const focusables = Array.from(\n dlg.querySelectorAll<HTMLElement>(FOCUSABLE),\n ).filter(\n (el) =>\n !el.closest(\"[aria-hidden='true']\") && el.offsetParent !== null,\n );\n if (!focusables.length) {\n e.preventDefault();\n return;\n }\n const first = focusables[0];\n const last = focusables[focusables.length - 1];\n if (e.shiftKey) {\n if (\n document.activeElement === first ||\n document.activeElement === dlg\n ) {\n e.preventDefault();\n last.focus();\n }\n } else {\n if (document.activeElement === last) {\n e.preventDefault();\n first.focus();\n }\n }\n };\n\n const onCancel = (e: Event) => {\n e.preventDefault();\n state.set(false);\n };\n dlg.addEventListener(\"cancel\", onCancel);\n\n const update = (val: boolean) => {\n if (val) {\n previousFocus = document.activeElement as HTMLElement;\n dlg.showModal();\n if (!scrollLocked) {\n lockScroll();\n scrollLocked = true;\n }\n dlg.addEventListener(\"keydown\", trapFocus);\n requestAnimationFrame(() => {\n dlg.style.opacity = \"1\";\n const focusable = dlg.querySelector<HTMLElement>(FOCUSABLE);\n focusable?.focus();\n });\n } else {\n closing = true;\n dlg.style.opacity = \"0\";\n dlg.removeEventListener(\"keydown\", trapFocus);\n // Fallback: if transitionend never fires (reduced-motion, display:none),\n // unblock close after the transition duration + buffer.\n closeTimer = setTimeout(() => {\n closeTimer = null;\n if (!closing) return;\n finalizeClose(dlg);\n }, 350);\n }\n };\n update(state.get());\n const release = state.addListener(update);\n node.addHook(\"Remove\", () => {\n if (closeTimer) {\n clearTimeout(closeTimer);\n closeTimer = null;\n }\n release();\n dlg.removeEventListener(\"cancel\", onCancel);\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n dlg.removeEventListener(\"keydown\", trapFocus);\n previousFocus?.focus();\n previousFocus = null;\n });\n },\n style: {\n opacity: \"0\",\n transition: \"opacity 200ms ease\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"shift-10\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n border: \"none\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n padding: (listener) => themeSpacing(themeDensity(listener) * 3),\n boxShadow: elevation(\"high\"),\n \"&::backdrop\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n opacity: 0.75,\n },\n },\n };\n}\n\nexport { dialog };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A horizontal separator (`role=\"separator\"`) with a line on each side of its\n * content, suitable for labelled dividers (\"or\"). Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the label text and rules. Defaults to \"neutral\".\n * @example { div: \"or\", $: [divider()] }\n */\nfunction divider(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n role: \"separator\",\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"divider\" patch should be used with <div>`);\n }\n },\n style: {\n display: \"flex\",\n justifyContent: \"center\",\n alignItems: \"baseline\",\n gap: themeSpacing(2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n minHeight: \"1lh\",\n \"&::before\": {\n content: `\"\"`,\n flex: 1,\n borderColor: (listener) =>\n themeColor(listener, \"border-strong\", color.get(listener)),\n borderWidth: \"1px\",\n borderBottomStyle: \"solid\",\n },\n \"&::after\": {\n content: `\"\"`,\n flex: 1,\n borderColor: (listener) =>\n themeColor(listener, \"border-strong\", color.get(listener)),\n borderWidth: \"1px\",\n borderBottomStyle: \"solid\",\n },\n },\n };\n}\n\nexport { divider };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { lockScroll, unlockScroll } from \"../utils/scrollLock.js\";\n\ntype PhysicalPlacement = \"left\" | \"right\" | \"top\" | \"bottom\";\ntype Placement = PhysicalPlacement | \"start\" | \"end\";\n\nconst translateOut: Record<PhysicalPlacement, string> = {\n left: \"translateX(-100%)\",\n right: \"translateX(100%)\",\n top: \"translateY(-100%)\",\n bottom: \"translateY(100%)\",\n};\n\nconst marginMap: Record<PhysicalPlacement, string> = {\n left: \"0 auto 0 0\",\n right: \"0 0 0 auto\",\n top: \"0 0 auto 0\",\n bottom: \"auto 0 0 0\",\n};\n\nconst isVertical = (p: PhysicalPlacement) => p === \"left\" || p === \"right\";\n\nfunction resolvePhysical(\n placement: Placement,\n isRTL: boolean,\n): PhysicalPlacement {\n if (placement === \"start\") return isRTL ? \"right\" : \"left\";\n if (placement === \"end\") return isRTL ? \"left\" : \"right\";\n return placement;\n}\n\n/**\n * Edge-anchored modal drawer driven by an `open` State. Slides in/out from a\n * chosen edge via a 250 ms transform transition, calls `showModal()`/`close()`,\n * locks page scroll while open, and closes on backdrop click. A 350 ms fallback\n * ensures `close()` is always called even when `transitionend` doesn't fire\n * (reduced-motion, `display:none`, detached element). Apply to a `<dialog>`.\n *\n * Because the patch uses the native `<dialog>` `showModal()` API, the browser\n * traps focus inside the drawer while it is open and restores focus to the\n * previously focused element when `close()` is called. Sets `aria-modal=\"true\"`.\n * Escape key closes the drawer via the animated state path (not immediate close).\n *\n * `\"start\"` and `\"end\"` placements resolve to left/right based on the\n * document's `dir` attribute at mount time, enabling RTL-aware drawers:\n * `\"start\"` → left (LTR) / right (RTL); `\"end\"` → right (LTR) / left (RTL).\n *\n * @hostTag dialog\n * @param props.color - Theme color tone for the drawer surface. Defaults to \"neutral\".\n * @param props.open - Open state (`ValueOrState<boolean>`); set true/false to show/hide. Defaults to false.\n * @param props.placement - Edge to anchor to. \"left\" | \"right\" | \"top\" | \"bottom\" | \"start\" | \"end\". Defaults to \"end\".\n * @param props.size - CSS length for the drawer's width (left/right/start/end) or height (top/bottom). Defaults to themeSpacing(80) for left/right, themeSpacing(64) for top/bottom.\n * @example { dialog: [...], $: [drawer({ open, placement: \"start\" })] }\n */\nfunction drawer(\n props: {\n color?: ThemeColor;\n open?: ValueOrState<boolean>;\n placement?: Placement;\n size?: string;\n } = {},\n): PartialElement {\n const { color = \"neutral\", open = false, placement = \"end\", size } = props;\n const state = toState(open);\n const isLogical = placement === \"start\" || placement === \"end\";\n\n // For static rendering / SSR assume LTR as fallback; corrected at mount time.\n const physicalFallback = resolvePhysical(placement, false);\n const defaultSize = isVertical(physicalFallback)\n ? themeSpacing(80)\n : themeSpacing(64);\n const drawerSize = size ?? defaultSize;\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"dialog\") {\n console.warn(`\"drawer\" patch must use dialog tag`);\n }\n },\n onClick: (e: MouseEvent, node) => {\n if (e.target !== node.domElement) return;\n state.set(false);\n },\n _onMount: (node) => {\n const dlg = node.domElement as HTMLDialogElement;\n dlg.setAttribute(\"aria-modal\", \"true\");\n\n const onCancel = (e: Event) => {\n e.preventDefault();\n state.set(false);\n };\n dlg.addEventListener(\"cancel\", onCancel);\n\n // Resolve logical placements at mount time using document direction.\n const isRTL =\n isLogical &&\n (dlg.ownerDocument.documentElement.dir === \"rtl\" ||\n dlg.ownerDocument.dir === \"rtl\");\n const physical = resolvePhysical(placement, isRTL);\n\n // Correct initial styles for logical placements whose physical direction\n // may differ from the LTR fallback used in the static style block.\n if (isLogical) {\n dlg.style.transform = translateOut[physical];\n dlg.style.margin = marginMap[physical];\n dlg.style.width = isVertical(physical) ? drawerSize : \"100dvw\";\n dlg.style.height = isVertical(physical) ? \"100dvh\" : drawerSize;\n }\n\n let closing = false;\n let scrollLocked = false;\n let closeTimer: ReturnType<typeof setTimeout> | null = null;\n const finishClose = () => {\n closeTimer = null;\n if (!closing) return;\n closing = false;\n dlg.close();\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n };\n\n const onTransitionEnd = (e: Event) => {\n if (e.target !== dlg) return;\n if ((e as TransitionEvent).propertyName !== \"transform\") return;\n finishClose();\n };\n dlg.addEventListener(\"transitionend\", onTransitionEnd);\n\n const update = (val: boolean) => {\n if (val) {\n closing = false;\n dlg.showModal();\n if (!scrollLocked) {\n lockScroll();\n scrollLocked = true;\n }\n requestAnimationFrame(() => {\n dlg.style.transform = \"translate(0, 0)\";\n });\n } else {\n closing = true;\n dlg.style.transform = translateOut[physical];\n closeTimer = setTimeout(finishClose, 350);\n }\n };\n update(state.get());\n const release = state.addListener(update);\n node.addHook(\"Remove\", () => {\n if (closeTimer) {\n clearTimeout(closeTimer);\n closeTimer = null;\n }\n release();\n dlg.removeEventListener(\"cancel\", onCancel);\n dlg.removeEventListener(\"transitionend\", onTransitionEnd);\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n });\n },\n style: {\n transform: translateOut[physicalFallback],\n transition: \"transform 0.25s ease\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"shift-10\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n border: \"none\",\n padding: (listener) => themeSpacing(themeDensity(listener) * 3),\n margin: marginMap[physicalFallback],\n width: isVertical(physicalFallback) ? drawerSize : \"100dvw\",\n height: isVertical(physicalFallback) ? \"100dvh\" : drawerSize,\n maxWidth: \"100dvw\",\n maxHeight: \"100dvh\",\n boxShadow: elevation(\"high\"),\n \"&::backdrop\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n opacity: 0.75,\n },\n },\n };\n}\n\nexport { drawer };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Italic emphasized inline text. Apply to an `<em>` element.\n *\n * @hostTag em\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the text. Defaults to \"neutral\".\n * @example { em: \"important\", $: [emphasis()] }\n */\nfunction emphasis(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"em\") {\n console.warn(`\"emphasis\" primitive patch must use em tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontStyle: \"italic\",\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n },\n };\n}\n\nexport { emphasis };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a container as an empty-state placeholder: centered flex column with\n * muted coloring and comfortable padding. Provide the icon, title, and\n * description as child elements.\n *\n * @param props.color - Theme color tone for the muted text/icon. Defaults to `\"neutral\"`.\n * @example\n * { div: [\n * { span: \"📭\" },\n * { p: \"No items yet\", $: [paragraph()] },\n * { span: \"Add your first item to get started\", $: [small()] },\n * ], $: [empty()] }\n */\nfunction empty(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n alignItems: \"center\",\n justifyContent: \"center\",\n gap: themeSpacing(3),\n paddingBlock: themeSpacing(12),\n paddingInline: themeSpacing(6),\n textAlign: \"center\",\n color: (listener) => themeColor(listener, \"shift-6\", color.get(listener)),\n // First child (icon area): more muted color to visually recede behind the text\n \"& > :first-child\": {\n color: (listener) =>\n themeColor(listener, \"shift-5\", color.get(listener)),\n },\n },\n };\n}\n\nexport { empty };\n","import type { DomphyElement, PartialElement } from \"@domphy/core\";\n\n/**\n * Catches errors thrown inside reactive child expressions and renders a\n * fallback element instead of crashing the whole tree. Apply to any container.\n *\n * Only errors in *reactive* children (functions returning element arrays) are\n * caught. Errors during static construction propagate normally — those are\n * programming errors, not runtime data errors.\n *\n * @hostTag any\n * @param props.fallback - Fallback element or factory `(error, reset) => element`. Defaults to a plain error message div.\n * @param props.onError - Optional callback for logging/telemetry.\n * @example { div: (l) => renderUserContent(l), $: [errorBoundary({ fallback: { p: \"Something went wrong.\" } })] }\n */\nfunction errorBoundary(\n props: {\n fallback?:\n | DomphyElement\n | ((error: unknown, reset: () => void) => DomphyElement);\n onError?: (error: unknown) => void;\n } = {},\n): PartialElement {\n return {\n _onError: (node, error, reset) => {\n props.onError?.(error);\n const fallbackEl =\n typeof props.fallback === \"function\"\n ? props.fallback(error, reset)\n : (props.fallback ??\n ({ div: \"An error occurred.\" } as DomphyElement));\n node.children.update([fallbackEl]);\n },\n };\n}\n\nexport { errorBoundary };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nconst SIZE_MAP = { small: 8, medium: 10, large: 14 } as const;\n\n/**\n * Floating Action Button — a circular elevated button typically used for the\n * primary action on a screen. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.color - Button color tone. Optional `ValueOrState<ThemeColor>`, defaults to `\"primary\"`.\n * @param props.size - Button size preset. Optional `\"small\" | \"medium\" | \"large\"`, defaults to `\"medium\"`.\n * @example { button: \"+\", $: [fab()] }\n * @example { button: \"+\", $: [fab({ size: \"small\", color: \"neutral\" })] }\n */\nfunction fab(\n props: {\n color?: ValueOrState<ThemeColor>;\n size?: \"small\" | \"medium\" | \"large\";\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n const dim = themeSpacing(SIZE_MAP[props.size ?? \"medium\"]);\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn('\"fab\" patch must use button tag');\n }\n },\n style: {\n appearance: \"none\",\n border: \"none\",\n cursor: \"pointer\",\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n flexShrink: 0,\n width: dim,\n height: dim,\n borderRadius: \"50%\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-9\", color.get(listener)),\n color: (listener) => themeColor(listener, \"shift-0\", color.get(listener)),\n boxShadow: elevation(\"low\"),\n transition: \"background-color 200ms ease, box-shadow 200ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n boxShadow: elevation(\"medium\"),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) =>\n `${elevation(\"medium\")}, ${focusRing(listener, color.get(listener))}`,\n },\n \"&[disabled]\": { opacity: 0.5, cursor: \"not-allowed\" },\n },\n };\n}\n\nexport { fab };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Lays out a figure as a column with block-level media (img/svg/video/canvas)\n * and a themed `<figcaption>`. Apply to a `<figure>` element.\n *\n * @hostTag figure\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the figure/caption text. Defaults to \"neutral\".\n * @example { figure: [{ img: \"\", src }, { figcaption: \"A caption\" }], $: [figure()] }\n */\nfunction figure(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"figure\") {\n console.warn(`\"figure\" primitive patch must use figure tag`);\n }\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: themeSpacing(2),\n marginInline: 0,\n marginTop: themeSpacing(3),\n marginBottom: themeSpacing(3),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n \"& img, & svg, & video, & canvas\": {\n display: \"block\",\n maxWidth: \"100%\",\n borderRadius: themeSpacing(2),\n },\n \"& figcaption\": {\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n color: (listener) => themeColor(listener, \"muted\", color.get(listener)),\n lineHeight: 1.45,\n },\n },\n };\n}\n\nexport { figure };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Layout patch for a group of form fields. Arranges a `<legend>`, `<label>`s,\n * controls, and helper `<p>`s in a grid — labels beside controls (horizontal)\n * or stacked above them (vertical). Apply to a `<fieldset>` element.\n *\n * @hostTag fieldset\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for legend/text/surface. Defaults to \"neutral\".\n * @param props.layout - Field arrangement, \"horizontal\" (label beside control) | \"vertical\" (label above). Defaults to \"horizontal\".\n * @example { fieldset: [{ legend: \"Profile\" }, { label: \"Name\" }, { input: \"\" }], $: [formGroup({ layout: \"vertical\" })] }\n */\nfunction formGroup(\n props: {\n color?: ValueOrState<ThemeColor>;\n layout?: \"horizontal\" | \"vertical\";\n } = {},\n): PartialElement {\n const { layout = \"horizontal\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n const isVertical = layout === \"vertical\";\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"fieldset\") {\n console.warn(`\"formGroup\" patch must use fieldset tag`);\n }\n },\n style: {\n margin: 0,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 3),\n border: \"none\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n display: \"grid\",\n gridTemplateColumns: isVertical\n ? `minmax(0, 1fr)`\n : `max-content minmax(0, 1fr)`,\n columnGap: themeSpacing(4),\n rowGap: themeSpacing(3),\n alignItems: \"start\",\n \"& > legend\": {\n gridColumn: \"1 / -1\",\n margin: 0,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontWeight: 600,\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n },\n \"& > label\": {\n gridColumn: \"1\",\n alignSelf: \"start\",\n margin: 0,\n paddingBlock: (listener) =>\n isVertical ? 0 : themeSpacing(themeDensity(listener) * 1),\n },\n \"& > label:has(+ :not(legend, label, p) + p)\": {\n gridRow: isVertical ? \"auto\" : \"span 2\",\n },\n \"& > :not(legend, label, p)\": {\n gridColumn: isVertical ? \"1\" : \"2\",\n minWidth: 0,\n width: \"100%\",\n boxSizing: \"border-box\",\n },\n \"& > p\": {\n gridColumn: isVertical ? \"1\" : \"2\",\n minWidth: 0,\n margin: 0,\n marginBlockStart: `calc(${themeSpacing(2)} * -1)`,\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n },\n };\n}\n\nexport { formGroup };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\nconst HeadingShift: Record<string, string> = {\n h6: \"decrease-1\",\n h5: \"inherit\",\n h4: \"increase-1\",\n h3: \"increase-2\",\n h2: \"increase-3\",\n h1: \"increase-4\",\n};\n\n/**\n * Styles a heading, scaling its font size by level (h1 largest … h6 smallest)\n * relative to the theme base size. Apply to a heading element `<h1>`–`<h6>`.\n *\n * @hostTag h1\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the heading text. Defaults to \"neutral\".\n * @example { h2: \"Section title\", $: [heading()] }\n */\nfunction heading(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (![\"h1\", \"h2\", \"h3\", \"h4\", \"h5\", \"h6\"].includes(node.tagName)) {\n console.warn(\n `\"heading\" primitive patch must use heading tags [h1...h6]`,\n );\n }\n },\n style: {\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n marginTop: 0,\n marginBottom: themeSpacing(2),\n fontSize: (listener) => {\n const offset = HeadingShift[listener.elementNode.tagName] || \"inherit\";\n return themeSize(listener, offset);\n },\n },\n };\n}\n\nexport { heading };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * A thematic break rendered as a thin 1px themed line with vertical margin.\n * Apply to an `<hr>` element.\n *\n * @hostTag hr\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the rule. Defaults to \"neutral\".\n * @example { hr: \"\", $: [horizontalRule()] }\n */\nfunction horizontalRule(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"hr\") {\n console.warn(`\"horizontalRule\" primitive patch must use hr tag`);\n }\n },\n style: {\n border: 0,\n height: \"1px\",\n marginInline: 0,\n marginTop: themeSpacing(3),\n marginBottom: themeSpacing(3),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", color.get(listener)),\n },\n };\n}\n\nexport { horizontalRule };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles an inline icon container: square box that centers its content and\n * applies the themed icon color. Apply to a `<span>` element.\n *\n * @hostTag span\n * @param props.color - Optional theme color tone for the icon (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @example { span: null, $: [icon()] }\n */\nfunction icon(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"span\") {\n console.warn(`\"icon\" primitive patch should use span tag`);\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n alignSelf: \"center\",\n justifySelf: \"center\",\n verticalAlign: \"middle\",\n width: themeSpacing(4),\n height: themeSpacing(4),\n flexShrink: \"0\",\n fontSize: (listener) => themeSize(listener),\n backgroundColor: \"transparent\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { icon };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a responsive image: full-width, cover-fit, rounded corners with a\n * themed placeholder background. Apply to an `<img>` element.\n *\n * @hostTag img\n * @param props.color - Optional theme color tone for the placeholder background (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @example { img: null, src: \"photo.jpg\", alt: \"Photo\", $: [image()] }\n */\nfunction image(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInsert: (node) => {\n if (node.tagName !== \"img\") {\n console.warn(`\"image\" primitive patch must use img tag`);\n }\n },\n style: {\n display: \"block\",\n width: \"100%\",\n maxWidth: \"100%\",\n height: \"auto\",\n objectFit: \"cover\",\n borderRadius: themeSpacing(2),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n },\n };\n}\n\nexport { image };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a custom checkbox with themed box, check mark, indeterminate state,\n * hover, focus and disabled styling. Apply to an `<input>` element of\n * type `checkbox` (the patch sets `type: \"checkbox\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for the box/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the checked/indeterminate fill and focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"checkbox\", $: [inputCheckbox()] }\n */\nfunction inputCheckbox(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"checkbox\",\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputCheckbox\" primitive patch must use input tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n display: \"inline-flex\",\n position: \"relative\",\n width: themeSpacing(6),\n height: themeSpacing(6),\n justifyContent: \"center\",\n alignItems: \"center\",\n transition: \"background-color 300ms, outline-color 300ms\",\n margin: 0,\n padding: 0,\n \"&::before\": {\n content: `\"\"`,\n display: \"block\",\n borderRadius: themeSpacing(1),\n lineHeight: 1,\n cursor: \"pointer\",\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n width: themeSpacing(4),\n height: themeSpacing(4),\n },\n \"&:hover::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:checked::before\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-8\", accentColor.get(listener)),\n },\n \"&:checked:hover:not([disabled])::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-7\", accentColor.get(listener)),\n },\n \"&:checked::after\": {\n content: `\"\"`,\n display: \"block\",\n position: \"absolute\",\n top: \"25%\",\n insetInlineStart: \"37%\",\n width: \"20%\",\n height: \"30%\",\n border: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"inherit\", accentColor.get(listener))}`,\n borderTop: 0,\n borderInlineStart: 0,\n transform: \"rotate(45deg)\",\n },\n \"&:indeterminate::before\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", accentColor.get(listener)),\n },\n \"&:indeterminate::after\": {\n content: `\"\"`,\n position: \"absolute\",\n inset: \"30%\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-8\", accentColor.get(listener)),\n },\n \"&:indeterminate:hover:not([disabled])::after\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-7\", accentColor.get(listener)),\n },\n \"&:focus-visible\": {\n borderRadius: themeSpacing(1.5),\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&[disabled]\": {\n cursor: \"not-allowed\",\n },\n \"&[disabled]::before, &[disabled]::after\": {\n outline: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", \"neutral\"),\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { inputCheckbox };\n","import type { PartialElement, ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a native color picker swatch with themed padding, rounded swatch and\n * disabled styling. Apply to an `<input>` element of type `color` (the patch\n * sets `type: \"color\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone used for the disabled state (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"color\", $: [inputColor()] }\n */\nfunction inputColor(\n _props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n return {\n type: \"color\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputColor\" primitive patch must use input tag`);\n }\n (element as any).type = \"color\";\n },\n style: {\n appearance: \"none\",\n border: \"none\",\n cursor: \"pointer\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 1),\n blockSize: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n inlineSize: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n backgroundColor: \"transparent\",\n \"&::-webkit-color-swatch-wrapper\": {\n margin: 0,\n padding: 0,\n },\n \"&::-webkit-color-swatch\": {\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n },\n },\n };\n}\n\nexport { inputColor };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\ntype InputDateTimeMode = \"date\" | \"time\" | \"week\" | \"month\" | \"datetime-local\";\n\n/**\n * Styles a native date/time input with themed border, padding, hover, focus,\n * invalid and disabled states. The `mode` selects the input `type`. Apply to\n * an `<input>` element (the patch sets `type` to the chosen `mode`).\n *\n * @hostTag input\n * @param props.mode - Input mode selecting the host `type`: `\"date\" | \"time\" | \"week\" | \"month\" | \"datetime-local\"`. Defaults to `\"datetime-local\"`.\n * @param props.color - Optional theme color tone for text/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"datetime-local\", $: [inputDateTime()] }\n */\nfunction inputDateTime(\n props: {\n mode?: InputDateTimeMode;\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { mode = \"datetime-local\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: mode,\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputDateTime\" primitive patch must use input tag`);\n }\n (element as any).type = mode;\n },\n style: {\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::-webkit-calendar-picker-indicator\": {\n cursor: \"pointer\",\n opacity: 0.85,\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n },\n \"&:invalid\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"error\")}`,\n },\n },\n };\n}\n\nexport { inputDateTime };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a native file input with a themed upload button, border, hover, focus\n * and disabled states. Apply to an `<input>` element of type `file` (the patch\n * sets `type: \"file\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for text/border and the upload button (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"file\", $: [inputFile()] }\n */\nfunction inputFile(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"file\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputFile\" primitive patch must use input tag`);\n }\n (element as any).type = \"file\";\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 1),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::-webkit-file-upload-button\": {\n marginTop: (listener) => themeSpacing(themeDensity(listener)),\n fontFamily: \"inherit\",\n fontSize: \"inherit\",\n border: \"none\",\n borderRadius: themeSpacing(1),\n height: themeSpacing(6),\n paddingInline: themeSpacing(2),\n cursor: \"pointer\",\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"surface\", color.get(listener)),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.8,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"surface\", \"neutral\"),\n },\n \"&[disabled]::-webkit-file-upload-button\": {\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", \"neutral\"),\n },\n },\n };\n}\n\nexport { inputFile };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a native number input with themed border, padding, visible spin\n * buttons, hover, focus and disabled states. Apply to an `<input>` element of\n * type `number` (the patch sets `type: \"number\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for text/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"number\", $: [inputNumber()] }\n */\nfunction inputNumber(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"number\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputNumber\" primitive patch must use input tag`);\n }\n (element as any).type = \"number\";\n },\n style: {\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n minWidth: themeSpacing(10),\n paddingInlineStart: (listener) =>\n themeSpacing(themeDensity(listener) * 3),\n paddingInlineEnd: (listener) =>\n themeSpacing(themeDensity(listener) * 1.5),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::-webkit-inner-spin-button, &::-webkit-outer-spin-button\": {\n opacity: 1,\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { inputNumber };\n","import type { DomphyElement, PartialElement, StyleObject } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n// Tabler Icons (MIT) — eye and eye-off outlines.\nconst EYE_SVG =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"none\" ` +\n `stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" ` +\n `width=\"1em\" height=\"1em\">` +\n `<path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/>` +\n `<path d=\"M10 12a2 2 0 1 0 4 0a2 2 0 0 0 -4 0\"/>` +\n `<path d=\"M21 12c-2.4 4 -5.4 6 -9 6c-3.6 0 -6.6 -2 -9 -6c2.4 -4 5.4 -6 9 -6c3.6 0 6.6 2 9 6\"/>` +\n `</svg>`;\n\nconst EYE_OFF_SVG =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"none\" ` +\n `stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" ` +\n `width=\"1em\" height=\"1em\">` +\n `<path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/>` +\n `<path d=\"M10.585 10.587a2 2 0 0 0 2.829 2.828\"/>` +\n `<path d=\"M16.681 16.673a8.717 8.717 0 0 1 -4.681 1.327c-3.6 0 -6.6 -2 -9 -6` +\n `c1.272 -2.12 2.712 -3.678 4.32 -4.674m2.86 -1.146a9.055 9.055 0 0 1 1.82 -.18` +\n `c3.6 0 6.6 2 9 6c-.666 1.11 -1.379 2.067 -2.138 2.87\"/>` +\n `<path d=\"M3 3l18 18\"/>` +\n `</svg>`;\n\n/**\n * Password input wrapper: a styled `<div>` that inserts an `<input type=\"password\">`\n * and a show/hide toggle button. The outer div carries the focus-ring outline via\n * `:focus-within`. Apply to an empty `<div>`.\n *\n * @hostTag div\n * @param props.color - Base color tone for border/background/text. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent outline color on focus-within. Defaults to `\"primary\"`.\n * @example { div: null, $: [inputPassword()] }\n */\nfunction inputPassword(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const colorState = toState(props.color ?? \"neutral\", \"color\");\n const accentState = toState(props.accentColor ?? \"primary\", \"accentColor\");\n const visibleState = toState(false);\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn('\"inputPassword\" patch must use div tag');\n }\n },\n // Build the input/toggle as real child elements (not imperative DOM\n // mutation in _onMount) so generateHTML()/SSR emits the actual markup.\n _onInit: (node) => {\n const field: DomphyElement<\"input\"> = {\n input: null,\n type: (l) => (visibleState.get(l) ? \"text\" : \"password\"),\n style: {\n flex: 1,\n minWidth: 0,\n border: \"none\",\n outline: \"none\",\n backgroundColor: \"transparent\",\n padding: 0,\n margin: 0,\n font: \"inherit\",\n color: \"inherit\",\n },\n };\n\n const toggle: DomphyElement<\"button\"> = {\n button: (l) => (visibleState.get(l) ? EYE_OFF_SVG : EYE_SVG),\n type: \"button\",\n ariaLabel: (l) =>\n visibleState.get(l) ? \"Hide password\" : \"Show password\",\n onClick: () => visibleState.set(!visibleState.get()),\n style: {\n background: \"none\",\n border: \"none\",\n padding: 0,\n margin: 0,\n cursor: \"pointer\",\n color: \"inherit\",\n display: \"flex\",\n alignItems: \"center\",\n flexShrink: 0,\n opacity: 0.6,\n },\n };\n\n node.children.insert(field);\n node.children.insert(toggle);\n },\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: (l) => themeSpacing(themeDensity(l) * 1),\n paddingBlock: (l) => themeSpacing(themeDensity(l) * 1),\n paddingInline: (l) => themeSpacing(themeDensity(l) * 3),\n borderRadius: (l) => themeSpacing(themeDensity(l) * 1.5),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (l) =>\n `1px solid ${themeColor(l, \"border-strong\", colorState.get(l))}`,\n color: (l) => themeColor(l, \"text\", colorState.get(l)),\n backgroundColor: (l) => themeColor(l, \"inherit\", colorState.get(l)),\n fontSize: (l) => themeSize(l, \"inherit\"),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not(:has([disabled])):not(:focus-within)\": {\n outline: (l) =>\n `1px solid ${themeColor(l, \"shift-5\", accentState.get(l))}`,\n },\n \"&:focus-within\": {\n boxShadow: (l) => focusRing(l, accentState.get(l)),\n },\n } as StyleObject,\n };\n}\n\nexport { inputPassword };\n","import type { PartialElement } from \"@domphy/core\";\nimport { themeSpacing } from \"@domphy/theme\";\n\n/**\n * Lays out a one-time-password container as a horizontal row of inputs and\n * wires keyboard navigation: auto-advance on input, backspace/arrow movement,\n * and paste distribution across the child inputs. Apply to a container element\n * (e.g. `<div>`) whose direct children are the OTP `<input>` boxes. Takes no\n * props.\n *\n * @example { div: null, $: [inputOTP()], children: [{ input: null }, { input: null }] }\n */\nfunction inputOTP(): PartialElement {\n return {\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n \"& > *\": {\n minWidth: `${themeSpacing(9)}!important`,\n },\n },\n _onMount: (node) => {\n const container = node.domElement as HTMLElement;\n const getInputs = () =>\n Array.from(container.querySelectorAll(\"input\")) as HTMLInputElement[];\n\n const onInput = (e: Event) => {\n const inputs = getInputs();\n const target = e.target as HTMLInputElement;\n const idx = inputs.indexOf(target);\n if (target.value && idx < inputs.length - 1) {\n inputs[idx + 1].focus();\n }\n };\n\n const onKeydown = (e: KeyboardEvent) => {\n const inputs = getInputs();\n const target = e.target as HTMLInputElement;\n const idx = inputs.indexOf(target);\n if (e.key === \"Backspace\" && !target.value && idx > 0) {\n inputs[idx - 1].focus();\n }\n if (e.key === \"ArrowLeft\" && idx > 0) inputs[idx - 1].focus();\n if (e.key === \"ArrowRight\" && idx < inputs.length - 1)\n inputs[idx + 1].focus();\n };\n\n const onPaste = (e: ClipboardEvent) => {\n e.preventDefault();\n const text = e.clipboardData?.getData(\"text\") ?? \"\";\n const inputs = getInputs();\n const found = inputs.indexOf(e.target as HTMLInputElement);\n const startIdx = found === -1 ? 0 : found;\n [...text].forEach((char, i) => {\n if (inputs[startIdx + i]) inputs[startIdx + i].value = char;\n });\n const lastFilled = Math.min(\n startIdx + text.length - 1,\n inputs.length - 1,\n );\n inputs[lastFilled]?.focus();\n };\n\n container.addEventListener(\"input\", onInput);\n container.addEventListener(\"keydown\", onKeydown as EventListener);\n container.addEventListener(\"paste\", onPaste as EventListener);\n\n node.addHook(\"Remove\", () => {\n container.removeEventListener(\"input\", onInput);\n container.removeEventListener(\"keydown\", onKeydown as EventListener);\n container.removeEventListener(\"paste\", onPaste as EventListener);\n });\n },\n };\n}\n\nexport { inputOTP };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a custom radio button with a themed circular box, checked dot, hover,\n * focus and disabled states. Apply to an `<input>` element of type `radio`\n * (the patch sets `type: \"radio\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for the box/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the checked dot and focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"radio\", $: [inputRadio()] }\n */\nfunction inputRadio(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"radio\",\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(\n `\"inputRadio\" primitive patch must use input tag and radio type`,\n );\n return;\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n appearance: \"none\",\n display: \"inline-flex\",\n position: \"relative\",\n width: themeSpacing(6),\n height: themeSpacing(6),\n justifyContent: \"center\",\n alignItems: \"center\",\n transition: \"background-color 300ms, outline-color 300ms\",\n margin: 0,\n padding: 0,\n \"&::before\": {\n content: `\"\"`,\n display: \"block\",\n borderRadius: \"50%\",\n lineHeight: 1,\n cursor: \"pointer\",\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n width: themeSpacing(4),\n height: themeSpacing(4),\n },\n \"&:hover::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:checked::before\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&:checked::after\": {\n content: `\"\"`,\n position: \"absolute\",\n inset: \"30%\",\n borderRadius: \"50%\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-8\", accentColor.get(listener)),\n },\n \"&:checked:hover:not([disabled])::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-7\", accentColor.get(listener)),\n },\n \"&:focus-visible\": {\n borderRadius: \"50%\",\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&[disabled]\": {\n cursor: \"not-allowed\",\n },\n \"&[disabled]::before, &[disabled]::after\": {\n outline: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", \"neutral\"),\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { inputRadio };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a range slider with a themed track and thumb, hover, focus and\n * disabled states. Apply to an `<input>` element of type `range` (the patch\n * sets `type: \"range\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for the slider track (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the thumb and focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"range\", $: [inputRange()] }\n */\nfunction inputRange(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"range\",\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputRange\" primitive patch must use input tag`);\n }\n },\n style: {\n appearance: \"none\",\n width: \"100%\",\n margin: 0,\n padding: 0,\n height: themeSpacing(4),\n background: \"transparent\",\n cursor: \"pointer\",\n \"&::-webkit-slider-runnable-track\": {\n height: themeSpacing(1.5),\n borderRadius: themeSpacing(999),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n },\n \"&::-webkit-slider-thumb\": {\n appearance: \"none\",\n width: themeSpacing(4),\n height: themeSpacing(4),\n borderRadius: themeSpacing(999),\n border: \"none\",\n marginTop: `calc((${themeSpacing(1.5)} - ${themeSpacing(4)}) / 2)`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-9\", accentColor.get(listener)),\n },\n \"&:hover:not([disabled])::-webkit-slider-thumb\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-10\", accentColor.get(listener)),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n outlineOffset: themeSpacing(1),\n borderRadius: themeSpacing(2),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n };\n}\n\nexport { inputRange };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a search input with themed border, padding, placeholder color, native\n * search decorations, hover, focus and disabled states. Apply to an `<input>`\n * element of type `search` (the patch sets `type: \"search\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for text/border/placeholder (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"search\", $: [inputSearch()] }\n */\nfunction inputSearch(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"search\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputSearch\" primitive patch must use input tag`);\n }\n (element as any).type = \"search\";\n },\n style: {\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n minWidth: themeSpacing(32),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::placeholder\": {\n color: (listener) =>\n themeColor(listener, \"shift-7\", color.get(listener)),\n },\n \"&::-webkit-search-decoration\": {\n display: \"none\",\n },\n \"&::-webkit-search-cancel-button\": {\n cursor: \"pointer\",\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n },\n },\n };\n}\n\nexport { inputSearch };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a checkbox as a toggle switch: themed track and sliding knob that\n * animates and recolors on checked, plus a disabled state. Apply to an\n * `<input>` element of type `checkbox` (the patch sets `type: \"checkbox\"`).\n *\n * @hostTag input\n * @param props.accentColor - Optional theme color tone for the checked track (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"checkbox\", $: [inputSwitch()] }\n */\nfunction inputSwitch(\n props: { accentColor?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n role: \"switch\",\n dataTone: \"shift-2\",\n type: \"checkbox\",\n _onSchedule: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputSwitch\" primitive patch must use input tag`);\n return;\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n appearance: \"none\",\n position: \"relative\",\n display: \"inline-flex\",\n width: themeSpacing(9),\n height: themeSpacing(6),\n cursor: \"pointer\",\n margin: `0`,\n paddingBlock: themeSpacing(1),\n \"&:checked\": {\n \"&::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"increase-3\", accentColor.get(listener)),\n },\n \"&::after\": {\n left: `calc(100% - ${themeSpacing(3.5)})`,\n },\n },\n \"&::after\": {\n content: `\"\"`,\n aspectRatio: `1/1`,\n position: \"absolute\",\n width: themeSpacing(3),\n height: themeSpacing(3),\n borderRadius: themeSpacing(999),\n left: themeSpacing(0.5),\n top: \"50%\",\n transform: \"translateY(-50%)\",\n transition: \"left 0.3s\",\n backgroundColor: (listener) => themeColor(listener, \"decrease-3\"),\n },\n \"&::before\": {\n content: '\"\"',\n width: \"100%\",\n borderRadius: themeSpacing(999),\n display: \"inline-block\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: 1,\n backgroundColor: (listener) => themeColor(listener),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n };\n}\n\nexport { inputSwitch };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Themed single-line text input primitive. Sets `type=\"text\"` and styles the\n * field with themed border, focus ring, placeholder, disabled and validation\n * (`data-status`) states. Apply to an `<input>` element.\n *\n * @hostTag input\n * @param props - Optional configuration.\n * @param props.color - Base color tone for text/border/background. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color tone for the hover/focus outline. Defaults to `\"primary\"`.\n * @example { input: \"\", type: \"text\", placeholder: \"Name\", $: [inputText()] }\n */\nfunction inputText(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"text\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(\n `\"inputText\" primitive patch must use input tag and text type`,\n );\n }\n (element as any).type = \"text\";\n },\n style: {\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n minWidth: themeSpacing(10),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::placeholder\": {\n color: (listener) => themeColor(listener, \"shift-7\"),\n },\n \"&:not(:placeholder-shown)\": {\n color: (listener) => themeColor(listener, \"shift-10\"),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n \"&:invalid:not(:placeholder-shown)\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"error\")}`,\n },\n \"&[data-status=error]\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"error\")}`,\n },\n \"&[data-status=warning]\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"warning\")}`,\n },\n },\n };\n}\n\nexport { inputText };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Renders keyboard-key styling (themed background, border and padding) for a\n * keystroke hint. Apply to a `<kbd>` element.\n *\n * @hostTag kbd\n * @param props - Optional configuration.\n * @param props.color - Color tone for text/background/border. Defaults to `\"neutral\"`.\n * @example { kbd: \"Ctrl\", $: [keyboard()] }\n */\nfunction keyboard(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"kbd\") {\n console.warn(`\"keyboard\" primitive patch must use kbd tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n paddingBlock: themeSpacing(0.5),\n paddingInline: themeSpacing(1.5),\n borderRadius: themeSpacing(1),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n },\n };\n}\n\nexport { keyboard };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed form-label primitive: inline-flex layout with gap, themed text color,\n * focus-within highlighting and a disabled (`aria-disabled`) state. Apply to a\n * `<label>` element.\n *\n * @hostTag label\n * @param props - Optional configuration.\n * @param props.color - Base color tone for the label text. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color tone applied on focus-within. Defaults to `\"primary\"`.\n * @example { label: \"Email\", htmlFor: \"email\", $: [label()] }\n */\nfunction label(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"label\") {\n console.warn(`\"label\" primitive patch must use label tag`);\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n cursor: \"pointer\",\n \"&:focus-within\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", accentColor.get(listener)),\n },\n \"&[aria-disabled=true]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { label };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed hyperlink primitive: styles text color, hover underline, visited,\n * focus ring and a disabled state. Apply to an `<a>` element.\n *\n * @hostTag a\n * @param props - Optional configuration.\n * @param props.color - Base color tone for the link text. Defaults to `\"primary\"`.\n * @param props.accentColor - Accent color tone for visited/focus states. Defaults to `\"secondary\"`.\n * @example { a: \"Home\", href: \"/\", $: [link()] }\n */\nfunction link(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n const accentColor = toState(props.accentColor ?? \"secondary\", \"accentColor\");\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"a\") {\n console.warn(`\"link\" primitive patch must use a tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n textDecoration: \"none\",\n \"&:visited\": {\n color: (listener) =>\n themeColor(listener, \"text\", accentColor.get(listener)),\n },\n \"&:hover:not([disabled])\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n textDecoration: \"underline\",\n },\n \"&:focus-visible\": {\n borderRadius: themeSpacing(1),\n outlineOffset: themeSpacing(1),\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { link };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * An `<a>` element styled to look like a button — same visual appearance as\n * `button()` but preserves link semantics (href, middle-click, right-click).\n * Apply to an `<a>` element.\n *\n * @hostTag a\n * @param props.color - Button color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { a: \"Open app\", href: \"/app\", $: [linkButton({ color: \"primary\" })] }\n */\nfunction linkButton(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"a\") {\n console.warn(`\"linkButton\" primitive patch must use a tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n textDecoration: \"none\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n width: \"fit-content\",\n display: \"inline-flex\",\n justifyContent: \"center\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 1),\n userSelect: \"none\",\n cursor: \"pointer\",\n outlineOffset: \"-1px\",\n outlineWidth: \"1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n \"&:hover\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color.get(listener)),\n },\n \"&[aria-disabled=true]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n pointerEvents: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { linkButton };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a navigation/display list container. Sets `list-style: none` and\n * zero padding; pairs with `listItem` and `listItemButton`. Apply to `<ul>`.\n *\n * @hostTag ul\n * @param props.color - Surface color tone. Optional `ThemeColor`, defaults to `\"neutral\"`.\n * @example { ul: [...], $: [list()] }\n */\nfunction list(_props: { color?: ThemeColor } = {}): PartialElement {\n return {\n style: {\n listStyle: \"none\",\n margin: 0,\n padding: 0,\n display: \"flex\",\n flexDirection: \"column\",\n },\n };\n}\n\n/**\n * A non-interactive list row. Typically wraps an icon + text. Apply to `<li>`.\n *\n * @hostTag li\n * @param props.dense - Reduce vertical padding. Optional `boolean`, defaults to `false`.\n * @example { li: \"Item\", $: [listItem()] }\n */\nfunction listItem(props: { dense?: boolean } = {}): PartialElement {\n const { dense = false } = props;\n return {\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBlock: (listener) =>\n themeSpacing(dense ? 1 : themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n },\n };\n}\n\n/**\n * An interactive (clickable) list row with hover/focus-visible states. Apply\n * to `<button>` or `<a>` inside an `<li>`.\n *\n * @param props.color - Color tone. Optional `ValueOrState<ThemeColor>`, defaults to `\"neutral\"`.\n * @param props.accentColor - Focus/active accent. Optional `ThemeColor`, defaults to `\"primary\"`.\n * @param props.dense - Reduce vertical padding. Optional `boolean`, defaults to `false`.\n * @example { button: \"Action\", $: [listItemButton()] }\n */\nfunction listItemButton(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ThemeColor;\n dense?: boolean;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = props.accentColor ?? \"primary\";\n const { dense = false } = props;\n\n return {\n style: {\n cursor: \"pointer\",\n appearance: \"none\",\n border: \"none\",\n background: \"transparent\",\n textDecoration: \"none\",\n textAlign: \"left\",\n display: \"flex\",\n alignItems: \"center\",\n width: \"100%\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBlock: (listener) =>\n themeSpacing(dense ? 1 : themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n transition: \"background-color 150ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&[aria-current=page], &[aria-selected=true]\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", accentColor),\n color: (listener) => themeColor(listener, \"shift-12\", accentColor),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `2px solid ${themeColor(listener, \"shift-6\", accentColor)}`,\n outlineOffset: \"-2px\",\n },\n \"&[disabled]\": { opacity: 0.5, cursor: \"not-allowed\" },\n },\n };\n}\n\nexport { list, listItem, listItemButton };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed highlight primitive: gives marked/highlighted inline text a tinted\n * background, rounded corners and padding. Apply to a `<mark>` element.\n *\n * @hostTag mark\n * @param props - Optional configuration.\n * @param props.accentColor - Accent color tone for the highlight fill and text. Defaults to `\"highlight\"`.\n * @example { mark: \"important\", $: [mark()] }\n */\nfunction mark(\n props: { accentColor?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const accentColor = toState(props.accentColor ?? \"highlight\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"mark\") {\n console.warn(`\"mark\" primitive patch must use mark tag`);\n }\n },\n dataTone: \"shift-2\",\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) =>\n themeColor(listener, \"text\", accentColor.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", accentColor.get(listener)),\n height: themeSpacing(6),\n borderRadius: themeSpacing(1),\n paddingInline: themeSpacing(1.5),\n },\n };\n}\n\nexport { mark };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\n\n/** One item inside a menu. */\ntype MenuItem = {\n /** Button label — plain string (auto-wrapped) or any DomphyElement (e.g. icon + text). */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index. */\n key?: string | number;\n /** Called when the item is clicked. */\n onClick?: () => void;\n};\n\n/**\n * All-in-one vertical menu. Generates `<button>` `[role=menuitem]` elements\n * from the `items` array with keyboard navigation (Arrow/Home/End/Enter/Space).\n * Apply to any wrapper element (`div`, `ul`, …).\n *\n * @param props.items - Item definitions `{ label, key?, onClick? }`. Pass `[]`\n * to keep the wrapper's own children (escape hatch for fully custom rows —\n * only the menu container styling and `role=\"menu\"` semantics apply then).\n * @param props.activeKey - Currently selected key (value or State). Defaults to `null`.\n * @param props.selectable - Whether items track and update the active selection. Defaults to `true`.\n * @param props.color - Background color tone for the menu. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color for the active/focus item. Defaults to `\"primary\"`.\n * @example\n * { div: null, $: [menu({ items: [\n * { label: \"Profile\", key: \"profile\", onClick: () => navigate(\"/profile\") },\n * { label: \"Settings\", key: \"settings\", onClick: () => navigate(\"/settings\") },\n * ] })] }\n */\nfunction menu(\n props: {\n items: MenuItem[];\n activeKey?: ValueOrState<number | string | null>;\n selectable?: boolean;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const {\n items = [],\n selectable = true,\n color = \"neutral\",\n accentColor = \"primary\",\n } = props;\n const activeKey = toState(props.activeKey ?? null);\n\n return {\n role: \"menu\",\n dataTone: \"shift-17\",\n _onSchedule: (node, element) => {\n // Empty items = the caller renders its own rows; leave children alone.\n if (items.length === 0) return;\n const id = node.nodeId;\n\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? index;\n\n return {\n button:\n typeof item.label === \"string\"\n ? [{ span: item.label } as DomphyElement<\"span\">]\n : [item.label],\n _key: key,\n type: \"button\",\n id: `menuitem${id}${key}`,\n role: \"menuitem\",\n ...(selectable\n ? {\n ariaCurrent: (l: Listener) =>\n activeKey.get(l) === key || undefined,\n }\n : {}),\n onClick: () => {\n if (selectable) activeKey.set(key);\n item.onClick?.();\n },\n onKeyDown: (e: Event) => {\n const k = (e as KeyboardEvent).key;\n if (k === \"Enter\" || k === \" \") {\n e.preventDefault();\n (e.target as HTMLElement).click();\n return;\n }\n if (![\"ArrowDown\", \"ArrowUp\", \"Home\", \"End\"].includes(k)) return;\n e.preventDefault();\n const keys = items.map((it, i) => it.key ?? i);\n const idx = keys.indexOf(key);\n let next = idx;\n if (k === \"ArrowDown\") next = (idx + 1) % keys.length;\n else if (k === \"ArrowUp\")\n next = (idx - 1 + keys.length) % keys.length;\n else if (k === \"Home\") next = 0;\n else if (k === \"End\") next = keys.length - 1;\n (\n document.getElementById(\n `menuitem${id}${keys[next]}`,\n ) as HTMLElement\n )?.focus();\n },\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n width: \"100%\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: (l: Listener) => themeSpacing(6 + themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 3),\n border: \"none\",\n outline: \"none\",\n color: (l: Listener) => themeColor(l, \"text\", color),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n transition: \"background-color 140ms ease\",\n \"&:hover:not([disabled]):not([aria-current=true])\": {\n backgroundColor: (l: Listener) => themeColor(l, \"hover\", color),\n },\n \"&[aria-current=true]\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-3\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-10\"),\n },\n \"&:focus-visible\": {\n outline: (l: Listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(l, \"shift-6\", accentColor)}`,\n outlineOffset: `-${themeSpacing(0.5)}`,\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n (element as any)[node.tagName] = buttons;\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n paddingBlock: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n borderRadius: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n outline: (l: Listener) =>\n `1px solid ${themeColor(l, \"border-strong\", color)}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n };\n}\n\nexport { menu };\nexport type { MenuItem };\n","import type { PartialElement, State } from \"@domphy/core\";\n\n/**\n * One keyframe. Shorthands `x`/`y` (px), `scale`, `rotate` (deg) compose into a\n * single `transform`; any other key is a raw CSS property (e.g. `opacity`,\n * `backgroundColor`).\n */\nexport type MotionKeyframe = {\n x?: number | string;\n y?: number | string;\n scale?: number | string;\n rotate?: number | string;\n} & Record<string, string | number>;\n\nexport interface MotionProps {\n /** Starting keyframe applied before the enter animation. */\n initial?: MotionKeyframe;\n /** Target keyframe. Pass a `State` to re-animate whenever it changes. */\n animate?: MotionKeyframe | State<MotionKeyframe>;\n /** Keyframe animated to before the element is removed. */\n exit?: MotionKeyframe;\n transition?: {\n /** ms, default 300. */\n duration?: number;\n /** ms, default 0. */\n delay?: number;\n /** CSS easing, default \"ease\". */\n easing?: string;\n iterations?: number;\n };\n}\n\nconst isState = (value: unknown): value is State<MotionKeyframe> =>\n !!value &&\n typeof (value as State<MotionKeyframe>).get === \"function\" &&\n (value as { _isState?: boolean })._isState === true;\n\nconst toStyles = (frame: MotionKeyframe): Keyframe => {\n const out: Record<string, string | number> = {};\n const transforms: string[] = [];\n for (const key in frame) {\n const value = frame[key];\n if (key === \"x\") {\n transforms.push(\n `translateX(${typeof value === \"number\" ? `${value}px` : value})`,\n );\n } else if (key === \"y\") {\n transforms.push(\n `translateY(${typeof value === \"number\" ? `${value}px` : value})`,\n );\n } else if (key === \"scale\") {\n transforms.push(`scale(${value})`);\n } else if (key === \"rotate\") {\n transforms.push(\n `rotate(${typeof value === \"number\" ? `${value}deg` : value})`,\n );\n } else {\n out[key] = value;\n }\n }\n if (transforms.length) out.transform = transforms.join(\" \");\n return out as Keyframe;\n};\n\n/**\n * Animation primitive driven by the Web Animations API. Runs an enter\n * animation on mount (`initial` -> `animate`), re-animates whenever `animate`\n * is a `State` that changes, and plays the `exit` keyframe before removal.\n * Has no host-tag restriction; apply to any element you want to animate.\n *\n * @param props - Optional configuration (see {@link MotionProps}).\n * @param props.initial - Starting keyframe applied before the enter animation.\n * @param props.animate - Target keyframe, or a `State` to re-animate on change.\n * @param props.exit - Keyframe animated to before the element is removed.\n * @param props.transition - Timing options.\n * @param props.transition.duration - Duration in ms. Defaults to `300`.\n * @param props.transition.delay - Delay in ms. Defaults to `0`.\n * @param props.transition.easing - CSS easing. Defaults to `\"ease\"`.\n * @param props.transition.iterations - Number of iterations. Defaults to `1`.\n * @example { div: \"Hello\", $: [motion({ initial: { opacity: 0 }, animate: { opacity: 1 } })] }\n */\nfunction motion(props: MotionProps = {}): PartialElement {\n const { initial, animate, exit, transition = {} } = props;\n const options: KeyframeAnimationOptions = {\n duration: transition.duration ?? 300,\n delay: transition.delay ?? 0,\n easing: transition.easing ?? \"ease\",\n iterations: transition.iterations ?? 1,\n fill: \"both\",\n };\n\n return {\n _onMount: (node) => {\n const el = node.domElement as HTMLElement | null;\n if (!el || typeof el.animate !== \"function\") return;\n const target = isState(animate) ? animate.get() : animate;\n if (target) {\n el.animate(\n initial ? [toStyles(initial), toStyles(target)] : [toStyles(target)],\n options,\n );\n } else if (initial) {\n Object.assign(el.style, toStyles(initial));\n }\n if (isState(animate)) {\n const release = animate.addListener((next: MotionKeyframe) => {\n el.animate([toStyles(next)], options);\n });\n node.setMetadata(\"motionRelease\", release);\n }\n },\n _onBeforeRemove: (node, done) => {\n const el = node.domElement as HTMLElement | null;\n if (!el || !exit || typeof el.animate !== \"function\") return done();\n el.animate([toStyles(exit)], options).finished.then(done, done);\n },\n _onRemove: (node) => {\n const release = node.getMetadata(\"motionRelease\") as\n | (() => void)\n | undefined;\n release?.();\n },\n };\n}\n\nexport { motion };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed ordered-list primitive: decimal markers positioned outside, reset\n * margins and themed text color. Apply to an `<ol>` element.\n *\n * @hostTag ol\n * @param props - Optional configuration.\n * @param props.color - Color tone for the list text. Defaults to `\"neutral\"`.\n * @example { ol: \"\", $: [orderedList()], children: [{ li: \"First\" }] }\n */\nfunction orderedList(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"ol\") {\n console.warn(`\"orderedList\" primitive patch must use ol tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n marginTop: 0,\n marginBottom: 0,\n paddingLeft: themeSpacing(3),\n listStyleType: \"decimal\",\n listStylePosition: \"outside\",\n },\n };\n}\n\nexport { orderedList };\n","import {\n type DomphyElement,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nfunction getPages(current: number, total: number): (number | \"...\")[] {\n if (total <= 7) return Array.from({ length: total }, (_, i) => i + 1);\n const pages: (number | \"...\")[] = [1];\n if (current > 3) pages.push(\"...\");\n const start = Math.max(2, current - 1);\n const end = Math.min(total - 1, current + 1);\n for (let i = start; i <= end; i++) pages.push(i);\n if (current < total - 2) pages.push(\"...\");\n pages.push(total);\n return pages;\n}\n\n/**\n * Themed pagination control. Renders previous/next buttons plus truncated page\n * numbers (with ellipses), tracks the current page in a `State`, and updates it\n * on click. Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props - Configuration.\n * @param props.total - Required. Total number of pages.\n * @param props.value - Current page, accepts a value or `State`. Defaults to `1`.\n * @param props.color - Base color tone for the page buttons. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color tone for the active page. Defaults to `\"primary\"`.\n * @example { div: \"\", $: [pagination({ total: 10, value: 1 })] }\n */\nfunction pagination(props: {\n value?: ValueOrState<number>;\n total: number;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n}): PartialElement {\n const { total, color = \"neutral\", accentColor = \"primary\" } = props;\n const state = toState(props.value ?? 1);\n\n const btnBase = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n minWidth: (listener: any) => themeSpacing(6 + themeDensity(listener) * 2),\n height: (listener: any) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener: any) => themeSpacing(themeDensity(listener) * 2),\n borderRadius: (listener: any) => themeSpacing(themeDensity(listener) * 1.5),\n border: \"none\",\n cursor: \"pointer\",\n fontSize: (listener: any) => themeSize(listener, \"inherit\"),\n backgroundColor: \"transparent\",\n color: (listener: any) => themeColor(listener, \"text\", color),\n transition: \"background-color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener: any) => themeColor(listener, \"hover\", color),\n },\n \"&:focus-visible\": {\n boxShadow: (listener: any) => focusRing(listener, accentColor),\n },\n \"&[disabled]\": {\n opacity: 0.4,\n cursor: \"not-allowed\",\n },\n };\n\n const activeStyle = {\n ...btnBase,\n backgroundColor: (listener: any) =>\n themeColor(listener, \"shift-6\", accentColor),\n color: (listener: any) => themeColor(listener, \"shift-11\", accentColor),\n fontWeight: \"600\",\n cursor: \"default\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener: any) =>\n themeColor(listener, \"shift-6\", accentColor),\n },\n };\n\n return {\n role: \"navigation\",\n ariaLabel: \"Pagination\",\n _onInsert: (node) => {\n if (node.tagName !== \"div\")\n console.warn('\"pagination\" patch must use div tag');\n },\n _onInit: (node) => {\n const content: DomphyElement<\"div\"> = {\n div: (listener) => {\n const page = state.get(listener);\n const items: DomphyElement[] = [];\n\n // Prev button\n items.push({\n button: \"‹\",\n _key: \"prev\",\n type: \"button\",\n ariaLabel: \"Previous page\",\n disabled: page <= 1,\n onClick: () => page > 1 && state.set(page - 1),\n style: btnBase,\n });\n\n // Page buttons. Keyed by page number (or a running ellipsis index —\n // there can be up to two \"...\" spans) so the list survives length\n // changes across pages without the unkeyed-reuse footgun.\n let ellipsisIndex = 0;\n for (const p of getPages(page, total)) {\n if (p === \"...\") {\n items.push({\n span: \"…\",\n _key: `ellipsis-${ellipsisIndex++}`,\n ariaHidden: \"true\",\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n paddingInline: (listener: any) =>\n themeSpacing(themeDensity(listener) * 2),\n color: (listener: any) =>\n themeColor(listener, \"shift-7\", color),\n },\n });\n } else {\n const isActive = p === page;\n items.push({\n button: String(p),\n _key: `page-${p}`,\n type: \"button\",\n ariaLabel: `Page ${p}`,\n ariaCurrent: isActive ? \"page\" : undefined,\n disabled: isActive,\n onClick: () => state.set(p),\n style: isActive ? activeStyle : btnBase,\n });\n }\n }\n\n // Next button\n items.push({\n button: \"›\",\n _key: \"next\",\n type: \"button\",\n ariaLabel: \"Next page\",\n disabled: page >= total,\n onClick: () => page < total && state.set(page + 1),\n style: btnBase,\n });\n\n return items;\n },\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(1),\n },\n };\n node.children.insert(content);\n },\n style: {\n display: \"inline-flex\",\n },\n };\n}\n\nexport { pagination };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A padded section for side-panel/inspector UIs — density-aware padding on\n * all sides, with an optional bottom divider for sections stacked one after\n * another. A thin wrapper: it does not impose flex layout on its children —\n * pair it with `stack()` or `row()` for that. No host-tag check; apply to\n * any block element.\n *\n * @param props.padding - Spacing multiplier for padding on all sides (default 4 = 1em at density 1).\n * @param props.divider - Adds a bottom border, for sections stacked one after another. Defaults to `false`.\n * @param props.color - Theme color tone for the divider border. Defaults to `\"neutral\"`.\n * @example { div: [{ h3: \"Parameters\" }, { p: \"...\" }], $: [panelSection()] }\n * @example\n * { div: [\n * { div: \"Section A\", $: [panelSection({ divider: true })] },\n * { div: \"Section B\", $: [panelSection()] },\n * ], $: [stack({ gap: 0 })] }\n */\nfunction panelSection(\n props: {\n padding?: number;\n divider?: boolean;\n color?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { padding = 4, divider = false } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n return {\n style: {\n padding: (listener) => themeSpacing(themeDensity(listener) * padding),\n ...(divider\n ? {\n borderBottom: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color.get(listener))}`,\n }\n : {}),\n },\n };\n}\n\nexport { panelSection };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Themed paragraph primitive: comfortable line-height, reset margins and themed\n * text color. Apply to a `<p>` element.\n *\n * @hostTag p\n * @param props - Optional configuration.\n * @param props.color - Color tone for the paragraph text. Defaults to `\"neutral\"`.\n * @example { p: \"Hello world\", $: [paragraph()] }\n */\nfunction paragraph(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"p\") {\n console.warn(`\"paragraph\" primitive patch must use p tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n lineHeight: 1.5,\n marginTop: 0,\n marginBottom: 0,\n },\n };\n}\n\nexport { paragraph };\n","import {\n type DomphyElement,\n type Listener,\n merge,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport { themeColor, themeDensity, themeSpacing } from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\n\n/**\n * Floating popover primitive. Attaches to its host as the anchor/trigger and\n * shows a floating `content` element (with `role=\"dialog\"`) on click or hover,\n * positioned via `@domphy/floating`. Returns the anchor partial, which merges\n * trigger wiring (haspopup/expanded, focus/blur dismissal). Apply to the\n * trigger element you want the popover anchored to.\n *\n * @param props - Configuration.\n * @param props.openOn - Interaction that opens the popover: `\"click\"` or `\"hover\"`. Defaults to `\"click\"`.\n * @param props.open - Open state, accepts a value or `State`. Defaults to `false`.\n * @param props.placement - Floating placement (e.g. `\"bottom\"`, `\"top-start\"`), value or `State`. Defaults to `\"bottom\"`.\n * @param props.content - The floating content element to display.\n * @example { button: \"Open\", $: [popover({ openOn: \"click\", content: { div: \"Hi\" } })] }\n */\nfunction popover(props: {\n openOn?: \"click\" | \"hover\";\n open?: ValueOrState<boolean>;\n placement?: ValueOrState<Placement>;\n content: DomphyElement;\n}): PartialElement {\n const { open = false, placement = \"bottom\", openOn = \"click\" } = props;\n\n let popoverId: string | null = null;\n const openState = toState(open);\n const placeState = toState(placement);\n\n const { show, hide, anchorPartial } = createFloating({\n kind: \"popover\",\n open: openState,\n placement: placeState,\n content: props.content,\n // Hovering the panel itself (not just the trigger) must keep it open —\n // handled generically inside floating.ts's behavior instance.\n keepOpenOnContentHover: openOn === \"hover\",\n });\n\n const popoverPartial: PartialElement = {\n role: \"dialog\",\n dataTone: \"shift-14\",\n style: {\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\"),\n borderRadius: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n outline: (l: Listener) => `1px solid ${themeColor(l, \"border-strong\")}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n _onInsert: (node) => {\n const id = node.attributes.get(\"id\");\n popoverId = id || node.nodeId;\n !id && node.attributes.set(\"id\", popoverId);\n },\n };\n\n props.content.$ ||= [];\n props.content.$.push(popoverPartial);\n\n const triggerPartial: PartialElement = {\n ariaHaspopup: \"dialog\",\n ariaExpanded: (listener) => openState.get(listener),\n onMouseEnter: (_e, node) => openOn === \"hover\" && show(node),\n onMouseLeave: (_e, node) => openOn === \"hover\" && hide(node),\n onClick: (_e, node) => {\n if (openOn === \"click\") {\n if (openState.get()) {\n hide(node);\n } else {\n show(node);\n }\n }\n },\n onKeyDown: (e, node) => {\n if ((e as KeyboardEvent).key === \"Escape\" && openState.get()) hide(node);\n },\n onFocus: (_e, node) => openOn === \"hover\" && show(node),\n onBlur: (e, node) => {\n const related = (e as FocusEvent).relatedTarget as Node | null;\n const root = node.getRoot().domElement as Element;\n const floatingEl = popoverId\n ? root.querySelector(`#${CSS.escape(popoverId)}`)\n : null;\n if (related && floatingEl?.contains(related)) return;\n hide(node);\n },\n _onMount: (node) =>\n popoverId && node.attributes.set(\"ariaControls\", popoverId),\n };\n merge(anchorPartial, triggerPartial);\n\n return anchorPartial;\n}\n\nexport { popover };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Renders a small rotated arrow (via a `::after` pseudo-element) that points from a\n * popover/tooltip toward its anchor, positioned and oriented based on the floating placement.\n * The arrow direction is computed by flipping the given placement. No host-tag check is\n * performed; apply it to the popover container element.\n *\n * @param props.placement - Floating placement the popover sits at; the arrow is drawn on the\n * opposite (flipped) side. Accepts a value or reactive state. Defaults to `\"bottom-end\"`.\n * One of: `top` | `bottom` | `left` | `right` | `top-start` | `top-end` | `bottom-start` |\n * `bottom-end` | `left-start` | `left-end` | `right-start` | `right-end`.\n * @param props.sideOffset - CSS length used to offset the arrow toward the start/end edge.\n * Defaults to `themeSpacing(6)`.\n * @param props.color - Theme color tone for the arrow fill and border. Defaults to `\"neutral\"`.\n * @param props.bordered - Whether the arrow draws a 1px border (set to `0px` when false).\n * Defaults to `true`.\n * @example { div: [...], $: [popoverArrow({ placement: \"top\" })] }\n */\nfunction popoverArrow(\n props: {\n placement?: ValueOrState<Placement>;\n sideOffset?: string;\n color?: ThemeColor;\n bordered?: boolean;\n } = {},\n): PartialElement {\n const {\n placement = \"bottom-end\",\n color = \"neutral\",\n sideOffset = themeSpacing(6),\n bordered = true,\n } = props;\n\n const place = toState(placement);\n\n const flipMap: Record<Placement, Placement> = {\n top: \"bottom\",\n bottom: \"top\",\n left: \"right\",\n right: \"left\",\n \"top-start\": \"bottom-end\",\n \"top-end\": \"bottom-start\",\n \"bottom-start\": \"top-end\",\n \"bottom-end\": \"top-start\",\n \"left-start\": \"right-end\",\n \"left-end\": \"right-start\",\n \"right-start\": \"left-end\",\n \"right-end\": \"left-start\",\n };\n\n const getFlipped = (listener: any) =>\n flipMap[place.get(listener)] ?? flipMap[\"bottom-end\"];\n const start = (pos: string) =>\n pos.includes(\"start\") ? sideOffset : pos.includes(\"end\") ? \"auto\" : \"50%\";\n const end = (pos: string) =>\n pos.includes(\"end\") ? sideOffset : pos.includes(\"start\") ? \"auto\" : \"50%\";\n\n return {\n style: {\n fontSize: (listener) => themeSize(listener),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color),\n position: \"relative\",\n \"&::after\": {\n content: `\"\"`,\n position: \"absolute\",\n width: themeSpacing(1.5),\n height: themeSpacing(1.5),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n borderWidth: bordered ? \"1px\" : 0,\n borderColor: (listener) => themeColor(listener, \"inherit\", color),\n borderTopStyle: (listener) => {\n const pos = getFlipped(listener);\n\n return pos.includes(\"top\") || pos.includes(\"right\")\n ? `solid`\n : \"none\";\n },\n borderBottomStyle: (listener) => {\n const pos = getFlipped(listener);\n\n return pos.includes(\"bottom\") || pos.includes(\"left\")\n ? `solid`\n : \"none\";\n },\n borderLeftStyle: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"top\") || pos.includes(\"left\") ? `solid` : \"none\";\n },\n borderRightStyle: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"bottom\") || pos.includes(\"right\")\n ? `solid`\n : \"none\";\n },\n top: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"top\")\n ? 0\n : pos.includes(\"bottom\")\n ? \"auto\"\n : start(pos);\n },\n right: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"right\")\n ? 0\n : pos.includes(\"left\")\n ? \"auto\"\n : end(pos);\n },\n bottom: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"bottom\")\n ? 0\n : pos.includes(\"top\")\n ? \"auto\"\n : end(pos);\n },\n left: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"left\")\n ? 0\n : pos.includes(\"right\")\n ? \"auto\"\n : start(pos);\n },\n transform: (listener) => {\n const pos = getFlipped(listener);\n const x =\n pos.includes(\"right\") ||\n (pos.includes(\"end\") && !pos.includes(\"left\"))\n ? \"50%\"\n : \"-50%\";\n const y =\n pos.includes(\"bottom\") ||\n (pos.includes(\"end\") && !pos.includes(\"top\"))\n ? \"50%\"\n : \"-50%\";\n return `translate(${x},${y}) rotate(45deg)`;\n },\n },\n },\n };\n}\n\nexport { popoverArrow };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a preformatted text block: inherited font size, themed foreground/background,\n * no border, density-scaled padding and rounded corners.\n *\n * @hostTag pre\n * @param props.color - Theme color tone for text and background. Accepts a value or reactive\n * state. Defaults to `\"neutral\"`.\n * @example { pre: \"const x = 1\", $: [preformated()] }\n */\nfunction preformated(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInsert: (node) => {\n if (node.tagName !== \"pre\") {\n console.warn(`\"preformated\" primitive patch must use pre tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n },\n };\n}\n\nexport { preformated };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a native progress bar: full-width, pill-shaped track with a themed fill,\n * including the WebKit progress-bar/value pseudo-elements and a width transition.\n *\n * @hostTag progress\n * @param props.color - Theme color tone for the track/background. Accepts a value or reactive\n * state. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color tone for the filled value. Accepts a value or reactive\n * state. Defaults to `\"primary\"`.\n * @example { progress: null, value: 40, max: 100, $: [progress()] }\n */\nfunction progress(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"progress\") {\n console.warn(`\"progress\" primitive patch must use progress tag`);\n }\n },\n style: {\n appearance: \"none\",\n width: \"100%\",\n height: themeSpacing(2),\n border: 0,\n borderRadius: themeSpacing(999),\n overflow: \"hidden\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n \"&::-webkit-progress-bar\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n borderRadius: themeSpacing(999),\n },\n \"&::-webkit-progress-value\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-9\", accentColor.get(listener)),\n borderRadius: themeSpacing(999),\n transition: \"width 220ms ease\",\n },\n },\n };\n}\n\nexport { progress };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nconst STAR_FILLED =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"currentColor\" width=\"1em\" height=\"1em\">` +\n `<path d=\"M12 17.27L18.18 21l-1.64-7.03L22 9.24l-7.19-.61L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21z\"/>` +\n `</svg>`;\nconst STAR_EMPTY =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"currentColor\" width=\"1em\" height=\"1em\">` +\n `<path d=\"M22 9.24l-7.19-.62L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21 12 17.27 18.18 21l-1.63-7.03L22 9.24zM12 15.4l-3.76 2.27 1-4.28-3.32-2.88 4.38-.38L12 6.1l1.71 4.04 4.38.38-3.32 2.88 1 4.28L12 15.4z\"/>` +\n `</svg>`;\n\n/**\n * Interactive star rating applied to a container `<div>`. Manages its own star\n * children: click to set, Arrow keys to adjust, hover to preview. In `readOnly`\n * mode stars are non-interactive. Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props.value - Current rating (0 – max). `ValueOrState<number>`, defaults to `0`.\n * @param props.max - Total number of stars. Optional `number`, defaults to `5`.\n * @param props.onChange - Called with the new value when the user picks a star.\n * @param props.readOnly - Disable interaction. Optional `boolean`, defaults to `false`.\n * @param props.color - Star color tone. Optional `ThemeColor`, defaults to `\"warning\"`.\n * @example { div: null, $: [rating({ value: ratingState, onChange: (v) => ratingState.set(v) })] }\n */\nfunction rating(\n props: {\n value?: ValueOrState<number>;\n max?: number;\n onChange?: (value: number) => void;\n readOnly?: boolean;\n color?: ThemeColor;\n } = {},\n): PartialElement {\n const { max = 5, readOnly = false, onChange } = props;\n const color = props.color ?? \"warning\";\n const valueState = toState(props.value ?? 0);\n // Hover preview only — never reported via onChange, only affects display.\n const hoveredState = toState(0);\n\n const activeCount = (listener: Listener) => {\n const hovered = hoveredState.get(listener);\n return hovered > 0 ? hovered : valueState.get(listener);\n };\n\n return {\n role: \"group\",\n ariaLabel: \"Rating\",\n style: {\n display: \"inline-flex\",\n gap: themeSpacing(0.5),\n fontSize: \"1.5rem\",\n cursor: readOnly ? \"default\" : \"pointer\",\n color: (listener) => themeColor(listener, \"muted\", color),\n },\n // Build stars as real child elements (not imperative DOM mutation in\n // _onMount) so generateHTML()/SSR emits the actual star markup.\n _onInit: (node) => {\n for (let i = 1; i <= max; i++) {\n const index = i;\n const interactive = readOnly\n ? {}\n : {\n onClick: () => {\n const next = index === valueState.get() ? 0 : index;\n valueState.set(next);\n onChange?.(next);\n hoveredState.set(0);\n },\n onMouseEnter: () => hoveredState.set(index),\n onMouseLeave: () => hoveredState.set(0),\n onKeyDown: (e: KeyboardEvent) => {\n const current = valueState.get();\n let next = current;\n if (e.key === \"ArrowRight\" || e.key === \"ArrowUp\") {\n next = Math.min(max, current + 1);\n e.preventDefault();\n } else if (e.key === \"ArrowLeft\" || e.key === \"ArrowDown\") {\n next = Math.max(0, current - 1);\n e.preventDefault();\n } else {\n return;\n }\n valueState.set(next);\n onChange?.(next);\n const target = next > 0 ? next - 1 : 0;\n (node.domElement?.children[target] as HTMLElement)?.focus();\n },\n };\n\n const star: DomphyElement<\"button\"> = {\n button: (listener) =>\n index <= activeCount(listener) ? STAR_FILLED : STAR_EMPTY,\n _key: index,\n type: \"button\",\n ariaLabel: `${index} star${index > 1 ? \"s\" : \"\"}`,\n ...interactive,\n style: {\n background: \"none\",\n border: \"none\",\n outline: \"none\",\n borderRadius: themeSpacing(1),\n padding: 0,\n cursor: \"inherit\",\n color: \"inherit\",\n fontSize: \"inherit\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"box-shadow 140ms ease\",\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color),\n },\n },\n };\n node.children.insert(star);\n }\n },\n };\n}\n\nexport { rating };\n","import type { PartialElement, StyleObject } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Circular ring progress indicator rendered via CSS `conic-gradient` and a\n * circular `mask`. Progress starts at 12 o'clock and advances clockwise.\n * Exposes `role=\"progressbar\"` with `aria-valuenow/min/max`. Apply to a `<div>`.\n *\n * @hostTag div\n * @param props.value - Progress percentage 0–100. Accepts a value or reactive state. Defaults to `0`.\n * @param props.color - Theme color for the filled arc. Accepts a value or reactive state. Defaults to `\"primary\"`.\n * @param props.trackColor - Theme color for the background track. Accepts a value or reactive state. Defaults to `\"neutral\"`.\n * @param props.size - Diameter in `themeSpacing` units. Defaults to `16` (= `4em`).\n * @param props.thickness - Ring stroke as a fraction of the radius (0–0.5). Defaults to `0.25`.\n * @example { div: null, $: [ringProgress({ value: 65 })] }\n * @example { div: null, $: [ringProgress({ value: loadingState, color: \"success\", size: 20 })] }\n */\nfunction ringProgress(\n props: {\n value?: ValueOrState<number>;\n color?: ValueOrState<ThemeColor>;\n trackColor?: ValueOrState<ThemeColor>;\n size?: number;\n thickness?: number;\n } = {},\n): PartialElement {\n const { size = 16, thickness = 0.25 } = props;\n const value = toState(props.value ?? 0, \"value\");\n const color = toState(props.color ?? \"primary\", \"color\");\n const trackColor = toState(props.trackColor ?? \"neutral\", \"trackColor\");\n\n // Mask cuts the center to create a donut shape.\n // Uses `closest-side` so the gradient circle matches the visible element circle\n // exactly, making `holePercent` directly represent the fraction of outer radius.\n const holePercent = Math.round((1 - thickness) * 100);\n const mask = `radial-gradient(circle closest-side, transparent ${holePercent}%, black ${holePercent}%)`;\n\n return {\n role: \"progressbar\",\n ariaValuenow: (l) => String(Math.round(value.get(l))),\n ariaValuemin: \"0\",\n ariaValuemax: \"100\",\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn('\"ringProgress\" patch must use div tag');\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: themeSpacing(size),\n height: themeSpacing(size),\n borderRadius: \"50%\",\n // Fill arc from 12 o'clock clockwise; `from -90deg` rotates the start point.\n background: (l) =>\n `conic-gradient(from -90deg, ${themeColor(l, \"shift-9\", color.get(l))} ${value.get(l)}%, ${themeColor(l, \"shift-3\", trackColor.get(l))} 0%)`,\n WebkitMask: mask,\n mask,\n } as StyleObject,\n };\n}\n\nexport { ringProgress };\n","import type { PartialElement } from \"@domphy/core\";\nimport { themeDensity, themeSpacing } from \"@domphy/theme\";\nimport type { FlexAlign } from \"./stack.js\";\n\ntype FlexJustify =\n | \"flex-start\"\n | \"center\"\n | \"flex-end\"\n | \"space-between\"\n | \"space-around\"\n | \"space-evenly\";\n\n/**\n * A horizontal flex row with spacing between children, vertically centered by\n * default. The general-purpose primitive for icon+label rows, field rows,\n * and button groups — instead of hand-rolling `display: flex; alignItems:\n * center; gap: ...`. `toolbar()` is a semantic alias of this same shape for\n * headers/nav bars. Styles the host only; apply to any block element.\n *\n * @param props.gap - Spacing multiplier for gap between items (default 4 = 1em at density 1).\n * @param props.align - Cross-axis alignment (`alignItems`). Defaults to `\"center\"`.\n * @param props.justify - Main-axis distribution (`justifyContent`). Unset by default (flex-start).\n * @param props.wrap - Allow items to wrap onto multiple lines. Defaults to `false`.\n * @example { div: [{ span: \"Icon\" }, { span: \"Label\" }], $: [row()] }\n * @example { div: [...], $: [row({ justify: \"space-between\", wrap: true })] }\n */\nfunction row(\n props: {\n gap?: number;\n align?: FlexAlign;\n justify?: FlexJustify;\n wrap?: boolean;\n } = {},\n): PartialElement {\n const { gap = 4, align = \"center\", justify, wrap = false } = props;\n return {\n style: {\n display: \"flex\",\n alignItems: align,\n gap: (listener) => themeSpacing(themeDensity(listener) * gap),\n ...(justify ? { justifyContent: justify } : {}),\n ...(wrap ? { flexWrap: \"wrap\" } : {}),\n },\n };\n}\n\nexport { row };\nexport type { FlexJustify };\n","import type { PartialElement, StyleObject } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Applies thin, themed overlay scrollbars to any scrollable container.\n * Covers WebKit (Chrome/Safari/Edge) via `::-webkit-scrollbar` pseudo-elements\n * and Firefox via `scrollbar-width`/`scrollbar-color`. Sets `overflow: auto`.\n * No host-tag check; apply to any block element.\n *\n * @param props.color - Theme color for the scrollbar thumb. Accepts a value or\n * reactive state. Defaults to `\"neutral\"`.\n * @example { div: [...], style: { maxHeight: \"300px\" }, $: [scrollArea()] }\n */\nfunction scrollArea(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n style: {\n overflow: \"auto\",\n \"&::-webkit-scrollbar\": {\n width: themeSpacing(2),\n height: themeSpacing(2),\n },\n \"&::-webkit-scrollbar-track\": {\n background: \"transparent\",\n },\n \"&::-webkit-scrollbar-thumb\": {\n backgroundColor: (l) => themeColor(l, \"shift-5\", color.get(l)),\n borderRadius: themeSpacing(999),\n // Transparent border creates visual padding around the thumb.\n border: `${themeSpacing(0.5)} solid transparent`,\n backgroundClip: \"content-box\",\n },\n \"&::-webkit-scrollbar-thumb:hover\": {\n backgroundColor: (l) => themeColor(l, \"shift-7\", color.get(l)),\n },\n // Firefox thin scrollbar with matching thumb/track colors.\n scrollbarWidth: \"thin\",\n scrollbarColor: (l) =>\n `${themeColor(l, \"shift-5\", color.get(l))} transparent`,\n } as StyleObject,\n };\n}\n\nexport { scrollArea };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/** One item inside a segmented control. */\ntype SegmentedItem = {\n /** Button label — plain string (auto-wrapped) or any DomphyElement. */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index. */\n key?: string;\n};\n\n/**\n * All-in-one single-select segmented control. Generates `<button>` option\n * elements from the `items` array. Apply to any wrapper element.\n *\n * @param props.items - Item definitions `{ label, key? }`.\n * @param props.value - Initially selected key (value or State). Defaults to the first item's key.\n * @param props.color - Theme color for the control background. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for the selected item. Defaults to `\"primary\"`.\n * @example\n * { div: null, $: [segmented({ items: [\n * { label: \"Day\", key: \"day\" },\n * { label: \"Month\", key: \"month\" },\n * { label: \"Year\", key: \"year\" },\n * ] })] }\n */\nfunction segmented(\n props: {\n items: SegmentedItem[];\n value?: ValueOrState<string>;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const { items = [], color = \"neutral\", accentColor = \"primary\" } = props;\n const value = toState(props.value ?? items[0]?.key ?? \"\");\n\n return {\n role: \"radiogroup\",\n // Expose value in context so segmentedItem() escape-hatch still works.\n _context: { segmented: { value } },\n _onSchedule: (node, element) => {\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? String(index);\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n button: [labelEl],\n _key: key,\n type: \"button\",\n role: \"radio\",\n ariaChecked: (l: Listener) => value.get(l) === key,\n onClick: () => value.set(key),\n style: {\n cursor: \"pointer\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: themeSpacing(6),\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(3),\n border: \"none\",\n borderRadius: themeSpacing(10),\n color: (l: Listener) => themeColor(l, \"text\", color),\n backgroundColor: \"transparent\",\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled]):not([aria-checked=true])\": {\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n },\n \"&[aria-checked=true]\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-0\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-10\", accentColor),\n },\n \"&:focus-visible\": {\n boxShadow: (l: Listener) => focusRing(l, accentColor),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n (element as any)[node.tagName] = buttons;\n },\n style: {\n display: \"inline-flex\",\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(1),\n gap: themeSpacing(0.5),\n borderRadius: themeSpacing(10),\n backgroundColor: (l: Listener) => themeColor(l, \"shift-2\", color),\n },\n };\n}\n\nexport { segmented };\nexport type { SegmentedItem };\n","import type { Listener, PartialElement } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeColorToken,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a native `<select>` control: removes the default appearance, applies themed\n * colors, outline, density-scaled padding/radius, a custom chevron background icon, and\n * hover/focus/disabled/optgroup/option states.\n *\n * @hostTag select\n * @param props.color - Theme color tone for text, background and outline. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color tone for hover/focus outlines. Defaults to `\"primary\"`.\n * @example { select: [{ option: \"A\" }], $: [select()] }\n */\nfunction select(\n props: { color?: ThemeColor; accentColor?: ThemeColor } = {},\n): PartialElement {\n const { color = \"neutral\", accentColor = \"primary\" } = props;\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"select\") {\n console.warn(`\"select\" primitive patch must use select tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color)}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingLeft: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingRight: (listener) => themeSpacing(themeDensity(listener) * 5),\n backgroundImage: (l: Listener) => {\n const svg = `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 10 6\"><path d=\"M1 1l4 4 4-4\" stroke=\"${themeColorToken(l, \"shift-7\")}\" stroke-width=\"1.5\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\"/></svg>`;\n return `url(\"data:image/svg+xml,${encodeURIComponent(svg)}\")`;\n },\n backgroundRepeat: \"no-repeat\",\n backgroundPosition: `right ${themeSpacing(2)} center`,\n backgroundSize: `${themeSpacing(2.5)} ${themeSpacing(1.5)}`,\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&:not([multiple])\": {\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor)}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor),\n },\n \"& optgroup\": {\n color: (listener) => themeColor(listener, \"shift-11\", color),\n },\n \"& option[disabled]\": {\n color: (listener) => themeColor(listener, \"shift-7\", \"neutral\"),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n },\n },\n };\n}\n\nexport { select };\n","import {\n type DomphyElement,\n merge,\n type PartialElement,\n type StyleObject,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\nimport { tag } from \"./tag.js\";\n\n/**\n * A clickable select trigger box that renders the currently selected option(s) as removable\n * tags and toggles a floating popover (the dropdown content) anchored to itself. Selected\n * labels are derived from `options` matching the bound `value`; removing a tag updates the value.\n *\n * @hostTag div\n * @param props.multiple - Whether multiple selection is allowed (renders removable tags and\n * keeps the popover open on click). Defaults to `false`.\n * @param props.value - Bound selection value(s). Accepts a value or reactive state of an array of\n * `number | string | null | undefined`, or a single `number | string | null | undefined`.\n * @param props.options - List of `{ label, value }` options used to resolve selected labels.\n * Defaults to `[]`.\n * @param props.placement - Floating placement of the dropdown popover. Accepts a value or\n * reactive state. Defaults to `\"bottom\"`.\n * @param props.content - Required. The popover/dropdown content element shown when open.\n * @param props.color - Theme color tone for the box text/background. Defaults to `\"neutral\"`.\n * @param props.open - Whether the popover is open. Accepts a value or reactive state. Defaults to `false`.\n * @example { div: null, $: [selectBox({ content: { div: [...] }, options: [{ label: \"A\", value: \"a\" }] })] }\n */\nfunction selectBox(props: {\n multiple?: boolean;\n value?: ValueOrState<\n | Array<number | string | null | undefined>\n | number\n | string\n | null\n | undefined\n >;\n options?: Array<{ label: string; value: string }>;\n placement?: ValueOrState<Placement>;\n content: DomphyElement;\n color?: ThemeColor;\n open?: ValueOrState<boolean>;\n}): PartialElement {\n const {\n options = [],\n placement = \"bottom\",\n color = \"neutral\",\n open = false,\n multiple = false,\n } = props;\n\n const state = toState(props.value);\n const openState = toState(open);\n const { show, hide, anchorPartial } = createFloating({\n kind: \"selectBox\",\n open: openState,\n placement: toState(placement),\n content: props.content,\n });\n\n const popoverPartial: PartialElement = {\n onClick: (_e, node) => !multiple && hide(node),\n dataTone: \"shift-14\",\n style: {\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\")}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n };\n\n merge(props.content, popoverPartial);\n\n const wrap: DomphyElement<\"div\"> = {\n div: (listener) => {\n const val = state.get(listener);\n const vals = Array.isArray(val) ? val : [val];\n const opts = options.filter((opt) => vals.includes(opt.value));\n return opts.map((opt) => ({\n span: opt.label,\n $: [tag({ color, removable: multiple })],\n _key: opt.value,\n _onRemove: (_node) => {\n const cur = state.get();\n const curVals = Array.isArray(cur) ? cur : [cur];\n const filter = curVals.filter((v) => v !== opt.value);\n multiple ? state.set(filter as any) : state.set(filter[0] as any);\n },\n })) as DomphyElement<\"span\">[];\n },\n style: {\n display: \"flex\",\n flexWrap: \"wrap\",\n gap: themeSpacing(1),\n flex: 1,\n } as StyleObject,\n };\n\n const partial: PartialElement = {\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"selectBox\" patch must use div tag`);\n }\n },\n _onInit: (node) => node.children.insert(wrap),\n onClick: (_e, node) => (openState.get() ? hide(node) : show(node)),\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n minHeight: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n minWidth: themeSpacing(32),\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 2),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n },\n };\n\n merge(anchorPartial, partial);\n return anchorPartial;\n}\n\nexport { selectBox };\n","import type { PartialElement } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A single selectable option row (`role=\"option\"`) for use inside a `selectList`. Reads the\n * `select` context to reflect/toggle selection: it sets `aria-selected` from the bound value and\n * toggles the value (single or multiple) on click. Styles hover/selected/focus states.\n *\n * @hostTag div\n * @param props.accentColor - Theme color tone for the selected/focus state. Defaults to `\"primary\"`.\n * @param props.color - Theme color tone for text/background. Defaults to `\"neutral\"`.\n * @param props.value - The option value compared against and written to the select state.\n * Defaults to `null`.\n * @example { div: \"Option A\", $: [selectItem({ value: \"a\" })] }\n */\nfunction selectItem(\n props: {\n accentColor?: ThemeColor;\n color?: ThemeColor;\n value?: number | string;\n } = {},\n): PartialElement {\n const { accentColor = \"primary\", color = \"neutral\", value = null } = props;\n\n const partial: PartialElement = {\n role: \"option\",\n _onInit: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"selectItem\" patch must use div tag`);\n }\n const select = node.getContext(\"select\");\n if (select) {\n const state = select.value;\n node.attributes.set(\"ariaSelected\", (listener) => {\n const val = state.get(listener);\n return select.multiple ? val.includes(value) : val === value;\n });\n node.addEvent(\"click\", () => {\n const val = state.get();\n if (select.multiple) {\n val.includes(value)\n ? state.set(val.filter((v: number | string) => v !== value))\n : state.set(val.concat([value]));\n } else {\n val !== value && state.set(value);\n }\n });\n }\n },\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n border: \"none\",\n outline: \"none\",\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n \"&:hover:not([disabled]):not([aria-selected=true])\": {\n backgroundColor: (listener) => themeColor(listener, \"hover\", color),\n },\n \"&[aria-selected=true]\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-6\", accentColor),\n color: (listener) => themeColor(listener, \"shift-11\"),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor)}`,\n outlineOffset: `-${themeSpacing(0.5)}`,\n },\n },\n };\n return partial;\n}\n\nexport { selectItem };\n","import {\n type DomphyElement,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Container for a list of `selectItem`s that owns the selection state. It exposes a `select`\n * context (`{ value, multiple }`) consumed by child items, and injects hidden `<input>`(s)\n * carrying the selected value(s) under `name` for form submission.\n *\n * @hostTag div\n * @param props.multiple - Whether multiple selection is allowed; also sets the default empty\n * value (`[]` vs `null`). Defaults to `false`.\n * @param props.value - Bound selection value(s). Accepts a value or reactive state of an array of\n * `number | string | null`, or a single `number | string | null`. Defaults to `[]` when\n * `multiple`, otherwise `null`.\n * @param props.color - Theme color tone for the background. Defaults to `\"neutral\"`.\n * @param props.name - Name attribute for the hidden inputs (form field name).\n * @example { div: [{ div: \"A\", $: [selectItem({ value: \"a\" })] }], $: [selectList({ name: \"pick\" })] }\n */\nfunction selectList(\n props: {\n multiple?: boolean;\n value?: ValueOrState<\n Array<number | string | null> | number | string | null\n >;\n color?: ThemeColor;\n name?: string;\n } = {},\n): PartialElement {\n const { color = \"neutral\", multiple = false } = props;\n const state = toState(props.value ?? (multiple ? [] : null));\n\n const inputs: DomphyElement<\"div\"> = {\n div: (listener) => {\n const val = state.get(listener);\n const vals = Array.isArray(val) ? val : [val];\n return vals.map((v) => ({\n input: null,\n name: props.name,\n // Preserve a legitimate numeric 0 (and other falsy-but-valid values);\n // `v || \"\"` would drop them.\n value: v == null ? \"\" : String(v),\n }));\n },\n hidden: true,\n };\n\n const partial: PartialElement = {\n dataTone: \"shift-17\",\n _context: {\n select: {\n value: state,\n multiple,\n },\n },\n _onInit: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"selectList\" patch must use a div tag`);\n }\n node.children.insert(inputs);\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n },\n };\n return partial;\n}\n\nexport { selectList };\n","import {\n hashString,\n type PartialElement,\n type StyleObject,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A loading placeholder block with a pulsing opacity animation. Marked `aria-hidden`, themed\n * background/foreground, fixed height, slight rounding. No host-tag check; typically applied\n * to a block-level element such as a `div` or `span`.\n *\n * @param props.color - Theme color tone for the placeholder. Accepts a value or reactive state.\n * Defaults to `\"neutral\"`.\n * @example { div: null, $: [skeleton()] }\n */\nfunction skeleton(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n const keyframes = {\n \"0%,100%\": { opacity: 1 },\n \"50%\": { opacity: 0.4 },\n };\n const animationName = hashString(JSON.stringify(keyframes));\n return {\n ariaHidden: \"true\",\n dataTone: \"shift-2\",\n style: {\n fontSize: (listener) => themeSize(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n height: themeSpacing(6),\n display: \"block\",\n borderRadius: themeSpacing(1),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n animation: `${animationName} 1.5s ease-in-out infinite`,\n [`@keyframes ${animationName}`]: keyframes,\n } as StyleObject,\n };\n}\n\nexport { skeleton };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Styles small/secondary text: one step smaller font size (`data-size=\"decrease-1\"`) with a\n * themed foreground color.\n *\n * @hostTag small\n * @param props.color - Theme color tone for the text. Accepts a value or reactive state.\n * Defaults to `\"neutral\"`.\n * @example { small: \"fine print\", $: [small()] }\n */\nfunction small(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"small\") {\n console.warn('\"small\" patch must use small tag');\n }\n },\n dataSize: \"decrease-1\",\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { small };\n","import type { PartialElement, StyleObject } from \"@domphy/core\";\nimport { hashString, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\nconst keyframes = { to: { transform: \"rotate(360deg)\" } };\nconst animationName = hashString(JSON.stringify(keyframes));\n\n/**\n * A circular loading spinner: a themed ring with a contrasting top border that rotates\n * continuously. Marked `role=\"status\"` with `aria-label=\"loading\"`.\n *\n * @hostTag span\n * @param props.color - Theme color tone for the ring/highlight. Accepts a value or reactive\n * state. Defaults to `\"neutral\"`.\n * @example { span: null, $: [spinner()] }\n */\nfunction spinner(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n role: \"status\",\n ariaLabel: \"loading\",\n _onInsert: (node) => {\n if (node.tagName !== \"span\") {\n console.warn(`\"spinner\" patch must use span tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n display: \"inline-block\",\n margin: 0,\n flexShrink: 0,\n width: themeSpacing(6),\n height: themeSpacing(6),\n borderRadius: \"50%\",\n border: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderTopColor: (listener) =>\n themeColor(listener, \"shift-9\", color.get(listener)),\n boxSizing: \"border-box\",\n padding: 0,\n animation: `${animationName} 0.7s linear infinite`,\n [`@keyframes ${animationName}`]: keyframes,\n } as StyleObject,\n };\n}\n\nexport { spinner };\n","import { merge, type PartialElement, toState } from \"@domphy/core\";\nimport { themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Root of a resizable split layout. Lays out children as a flex row (horizontal) or column\n * (vertical) and provides a `splitter` context (`{ direction, size, min, max }`) consumed by\n * `splitterPanel` and `splitterHandle`. `size` is a reactive state holding the first panel's\n * percentage. No host-tag check; typically applied to a `div`.\n *\n * @param props.direction - Split orientation, `\"horizontal\"` | `\"vertical\"`. Defaults to `\"horizontal\"`.\n * @param props.defaultSize - Initial size (percentage) of the resizable panel. Defaults to `50`.\n * @param props.min - Minimum panel size (percentage). Defaults to `10`.\n * @param props.max - Maximum panel size (percentage). Defaults to `90`.\n * @example { div: [...], $: [splitter({ direction: \"vertical\" })] }\n */\nfunction splitter(\n props: {\n direction?: \"horizontal\" | \"vertical\";\n defaultSize?: number;\n min?: number;\n max?: number;\n } = {},\n): PartialElement {\n const {\n direction = \"horizontal\",\n defaultSize = 50,\n min = 10,\n max = 90,\n } = props;\n return {\n _onSchedule: (_node, element) => {\n merge(element, {\n _context: {\n splitter: {\n direction,\n size: toState(defaultSize),\n min,\n max,\n // Mutable bookkeeping (not reactive state) so splitterPanel can\n // tell the first panel from later ones — see its own comment.\n panelCount: 0,\n },\n },\n });\n },\n style: {\n display: \"flex\",\n flexDirection: direction === \"horizontal\" ? \"row\" : \"column\",\n overflow: \"hidden\",\n },\n };\n}\n\n/**\n * The resizable panel inside a `splitter`. Reads the `splitter` context and binds its\n * width (horizontal) or height (vertical) to the context `size` state, updating reactively as\n * the handle is dragged. Intended for exactly two panels either side of one `splitterHandle`:\n * the first `splitterPanel` mounted takes `size`%, and the second takes the complementary\n * `100 - size`% — so the pair always sums to the full width/height instead of both tracking\n * the same number (which would make them grow and shrink together instead of trading space).\n * Warns if used outside a `splitter`. Takes no props.\n *\n * @example { div: [...], $: [splitterPanel()] }\n */\nfunction splitterPanel(): PartialElement {\n return {\n _onMount: (node) => {\n const ctx = node.getContext(\"splitter\");\n if (!ctx) {\n console.warn(`\"splitterPanel\" patch must be used inside a \"splitter\"`);\n return;\n }\n const el = node.domElement as HTMLElement;\n const prop = ctx.direction === \"horizontal\" ? \"width\" : \"height\";\n const isFirst = ctx.panelCount++ === 0;\n\n const apply = (size: number) => {\n el.style[prop] = `${isFirst ? size : 100 - size}%`;\n };\n apply(ctx.size.get());\n el.style.flexShrink = \"0\";\n el.style.overflow = \"auto\";\n\n const release = ctx.size.addListener(apply);\n node.addHook(\"Remove\", release);\n },\n };\n}\n\n/**\n * The draggable divider inside a `splitter`. Reads the `splitter` context, shows the\n * appropriate resize cursor, and updates the context `size` state (clamped to `min`/`max`)\n * via mouse drag or keyboard: Arrow keys move by 1%, Home/End jump to min/max, hold Shift\n * for 10× step. Sets `role=\"separator\"`, `tabindex=\"0\"`, and `aria-value*` attributes.\n * Warns if used outside a `splitter`. Takes no props.\n *\n * @example { div: null, $: [splitterHandle()] }\n */\nfunction splitterHandle(): PartialElement {\n return {\n role: \"separator\",\n tabindex: 0,\n _onMount: (node) => {\n const ctx = node.getContext(\"splitter\");\n if (!ctx) {\n console.warn(`\"splitterHandle\" patch must be used inside a \"splitter\"`);\n return;\n }\n const handle = node.domElement as HTMLElement;\n const isHorizontal = ctx.direction === \"horizontal\";\n\n handle.style.cursor = isHorizontal ? \"col-resize\" : \"row-resize\";\n handle.setAttribute(\n \"aria-orientation\",\n isHorizontal ? \"vertical\" : \"horizontal\",\n );\n handle.setAttribute(\"aria-valuemin\", String(ctx.min));\n handle.setAttribute(\"aria-valuemax\", String(ctx.max));\n handle.setAttribute(\"aria-valuenow\", String(Math.round(ctx.size.get())));\n\n const releaseAriaValue = ctx.size.addListener((size: number) => {\n handle.setAttribute(\"aria-valuenow\", String(Math.round(size)));\n });\n\n const onKeydown = (e: KeyboardEvent) => {\n const step = e.shiftKey ? 10 : 1;\n let next: number | null = null;\n if (isHorizontal) {\n if (e.key === \"ArrowRight\")\n next = Math.min(ctx.size.get() + step, ctx.max);\n else if (e.key === \"ArrowLeft\")\n next = Math.max(ctx.size.get() - step, ctx.min);\n } else {\n if (e.key === \"ArrowDown\")\n next = Math.min(ctx.size.get() + step, ctx.max);\n else if (e.key === \"ArrowUp\")\n next = Math.max(ctx.size.get() - step, ctx.min);\n }\n if (e.key === \"Home\") next = ctx.min;\n else if (e.key === \"End\") next = ctx.max;\n if (next !== null) {\n e.preventDefault();\n ctx.size.set(next);\n }\n };\n\n let cancelDrag: (() => void) | null = null;\n\n const onMousedown = (e: MouseEvent) => {\n e.preventDefault();\n const container = handle.parentElement!;\n\n const onMousemove = (e: MouseEvent) => {\n const rect = container.getBoundingClientRect();\n const raw = isHorizontal\n ? ((e.clientX - rect.left) / rect.width) * 100\n : ((e.clientY - rect.top) / rect.height) * 100;\n ctx.size.set(Math.min(Math.max(raw, ctx.min), ctx.max));\n };\n\n const onMouseup = () => {\n document.removeEventListener(\"mousemove\", onMousemove);\n document.removeEventListener(\"mouseup\", onMouseup);\n cancelDrag = null;\n };\n\n cancelDrag = () => {\n document.removeEventListener(\"mousemove\", onMousemove);\n document.removeEventListener(\"mouseup\", onMouseup);\n cancelDrag = null;\n };\n\n document.addEventListener(\"mousemove\", onMousemove);\n document.addEventListener(\"mouseup\", onMouseup);\n };\n\n handle.addEventListener(\"keydown\", onKeydown);\n handle.addEventListener(\"mousedown\", onMousedown);\n node.addHook(\"Remove\", () => {\n cancelDrag?.();\n releaseAriaValue();\n handle.removeEventListener(\"keydown\", onKeydown);\n handle.removeEventListener(\"mousedown\", onMousedown);\n });\n },\n style: {\n flexShrink: 0,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n backgroundColor: (listener) => themeColor(listener, \"shift-2\"),\n \"&:hover\": {\n backgroundColor: (listener) => themeColor(listener, \"shift-3\"),\n },\n \"&:focus-visible\": {\n outline: (listener) => `2px solid ${themeColor(listener, \"shift-6\")}`,\n outlineOffset: \"2px\",\n },\n \"&::after\": {\n content: '\"\"',\n // A small grip dot so the handle is visibly draggable. Without an\n // explicit size the pseudo-element collapses to 0x0 and is invisible.\n width: themeSpacing(1),\n height: themeSpacing(1),\n borderRadius: themeSpacing(999),\n backgroundColor: (listener) => themeColor(listener, \"shift-4\"),\n },\n },\n };\n}\n\nexport { splitter, splitterPanel, splitterHandle };\n","import type { PartialElement } from \"@domphy/core\";\nimport { themeDensity, themeSpacing } from \"@domphy/theme\";\n\ntype FlexAlign = \"flex-start\" | \"center\" | \"flex-end\" | \"stretch\" | \"baseline\";\n\n/**\n * A vertical flex column with spacing between children. The general-purpose\n * primitive for stacking blocks — form sections, panel content, card bodies —\n * instead of hand-rolling `display: flex; flexDirection: column; gap: ...`.\n * Styles the host only; apply to any block element.\n *\n * @param props.gap - Spacing multiplier for gap between children (default 3 = 0.75em at density 1).\n * @param props.align - Cross-axis alignment (`alignItems`). Unset by default (flex default, stretch).\n * @example { div: [{ h3: \"Title\" }, { p: \"Body\" }], $: [stack()] }\n * @example { div: [...], $: [stack({ gap: 2, align: \"center\" })] }\n */\nfunction stack(props: { gap?: number; align?: FlexAlign } = {}): PartialElement {\n const { gap = 3, align } = props;\n return {\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: (listener) => themeSpacing(themeDensity(listener) * gap),\n ...(align ? { alignItems: align } : {}),\n },\n };\n}\n\nexport { stack };\nexport type { FlexAlign };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/** One step entry. */\ntype StepItem = {\n /** Step label — plain string (auto-wrapped) or any DomphyElement. */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index. */\n key?: string | number;\n};\n\n/**\n * All-in-one step-progress indicator. Generates `<li>` step elements from the\n * `items` array. Apply to an `<ol>` or `<ul>` element.\n *\n * @param props.items - Step definitions `{ label, key? }`.\n * @param props.current - Zero-based index of the active step (value or State). Defaults to `0`.\n * @param props.direction - `\"horizontal\"` (default) or `\"vertical\"` layout.\n * @param props.color - Theme color for pending/track elements. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for active/completed elements. Defaults to `\"primary\"`.\n * @example\n * { ol: null, $: [steps({ current: 1, items: [\n * { label: \"Cart\" },\n * { label: \"Shipping\" },\n * { label: \"Payment\" },\n * ] })] }\n */\nfunction steps(\n props: {\n items: StepItem[];\n current?: ValueOrState<number>;\n direction?: \"horizontal\" | \"vertical\";\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const {\n items = [],\n direction = \"horizontal\",\n color = \"neutral\",\n accentColor = \"primary\",\n } = props;\n const current = toState(props.current ?? 0);\n\n return {\n // Expose state in context so stepItem() escape-hatch still works.\n _context: { steps: { current, direction, color, accentColor } },\n _onSchedule: (node, element) => {\n const stepEls: DomphyElement<\"li\">[] = items.map((item, index) => {\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n li: [labelEl],\n _key: item.key ?? index,\n dataStep: String(index + 1),\n dataStatus: (l: Listener) => {\n const cur = current.get(l);\n if (index < cur) return \"done\";\n if (index === cur) return \"active\";\n return \"pending\";\n },\n ariaCurrent: (l: Listener) =>\n current.get(l) === index ? \"step\" : undefined,\n style: {\n position: \"relative\",\n display: \"flex\",\n flexDirection: \"column\",\n alignItems: \"center\",\n gap: themeSpacing(1),\n flex: \"1\",\n fontSize: (l: Listener) => themeSize(l, \"decrease-1\"),\n textAlign: \"center\",\n \"&::before\": {\n content: \"attr(data-step)\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: themeSpacing(6),\n height: themeSpacing(6),\n borderRadius: themeSpacing(999),\n fontSize: (l: Listener) => themeSize(l, \"decrease-1\"),\n fontWeight: \"600\",\n flexShrink: \"0\",\n border: (l: Listener) =>\n `2px solid ${themeColor(l, \"border-strong\", color)}`,\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\"),\n color: (l: Listener) => themeColor(l, \"muted\"),\n transition:\n \"background-color 200ms ease, color 200ms ease, border-color 200ms ease\",\n zIndex: \"1\",\n },\n \"&:not(:first-child)::after\": {\n content: '\"\"',\n position: \"absolute\",\n top: themeSpacing(3),\n right: `calc(50% + ${themeSpacing(3)})`,\n left: `calc(-50% + ${themeSpacing(3)})`,\n height: \"2px\",\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n zIndex: \"0\",\n },\n \"&[data-status=active]::before\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-6\", accentColor),\n borderColor: (l: Listener) =>\n themeColor(l, \"shift-6\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-15\", accentColor),\n },\n \"&[data-status=done]::before\": {\n content: '\"✓\"',\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n borderColor: (l: Listener) => themeColor(l, \"border\", color),\n color: (l: Listener) => themeColor(l, \"text\", color),\n },\n \"&[data-status=done]:not(:first-child)::after\": {\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n },\n \"&[data-status=active]:not(:first-child)::after\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-6\", accentColor),\n },\n \"&[data-status=pending]\": {\n color: (l: Listener) => themeColor(l, \"shift-7\"),\n },\n \"&[data-status=active]\": {\n color: (l: Listener) => themeColor(l, \"shift-10\"),\n fontWeight: \"600\",\n },\n \"&[data-status=done]\": {\n color: (l: Listener) => themeColor(l, \"muted\"),\n },\n },\n } as DomphyElement<\"li\">;\n });\n\n (element as any)[node.tagName] = stepEls;\n },\n style: {\n display: \"flex\",\n flexDirection: direction === \"vertical\" ? \"column\" : \"row\",\n alignItems: direction === \"vertical\" ? \"flex-start\" : \"center\",\n gap: themeSpacing(2),\n listStyle: \"none\",\n margin: \"0\",\n padding: \"0\",\n },\n };\n}\n\nexport { steps };\nexport type { StepItem };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Styles strongly emphasized (bold) text: inherited font size, `font-weight: 700`, and a\n * themed foreground color.\n *\n * @hostTag strong\n * @param props.color - Theme color tone for the text. Accepts a value or reactive state.\n * Defaults to `\"neutral\"`.\n * @example { strong: \"important\", $: [strong()] }\n */\nfunction strong(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"strong\") {\n console.warn(`\"strong\" primitive patch must use strong tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontWeight: 700,\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n backgroundColor: (listener) => themeColor(listener),\n },\n };\n}\n\nexport { strong };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Renders subscript text (shrunk, baseline-lowered) for the host `<sub>` element.\n *\n * @hostTag sub\n * @param props.color - Theme color for the text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { sub: \"2\", $: [subscript()] }\n */\nfunction subscript(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"sub\") {\n console.warn(`\"subscript\" primitive patch must use sub tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n verticalAlign: \"sub\",\n lineHeight: 0,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { subscript };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Renders superscript text (shrunk, baseline-raised) for the host `<sup>` element.\n *\n * @hostTag sup\n * @param props.color - Theme color for the text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { sup: \"2\", $: [superscript()] }\n */\nfunction superscript(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"sup\") {\n console.warn(`\"superscript\" primitive patch must use sup tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n verticalAlign: \"super\",\n lineHeight: 0,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { superscript };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a data table (header/body/footer cells, caption, row hover, borders)\n * on the host `<table>` element.\n *\n * @hostTag table\n * @param props.color - Theme color applied across cells and text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { table: null, $: [table()] }\n */\nfunction table(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"table\") {\n console.warn(`\"table\" primitive patch must use table tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n width: \"100%\",\n borderCollapse: \"collapse\",\n \"& caption\": {\n captionSide: \"bottom\",\n },\n \"& th, & thead td\": {\n textAlign: \"left\",\n fontWeight: 500,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n },\n \"& td\": {\n textAlign: \"left\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n boxShadow: (listener) =>\n `inset 0 1px 0 ${themeColor(listener, \"shift-3\", color.get(listener))}`,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n },\n \"& tfoot th, & tfoot td\": {\n textAlign: \"left\",\n fontWeight: 500,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n color: (l) => themeColor(l, \"shift-10\", color.get(l)),\n backgroundColor: (l) => themeColor(l, \"inherit\"),\n boxShadow: (l) =>\n `inset 0 -1px 0 ${themeColor(l, \"shift-4\", color.get(l))}`,\n },\n \"& tr\": {\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n },\n\n // No !important needed: \".scope tbody tr:hover\" (two classes + two\n // elements) already out-specifies any row's own auto-scope class rule.\n \"& tbody tr:hover\": {\n backgroundColor: (listener) => themeColor(listener, \"hover\"),\n },\n },\n };\n}\n\nexport { table };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/** One tab entry: a trigger label and its panel content. */\ntype TabItem = {\n /** Tab button label — a plain string (auto-wrapped in span) or any DomphyElement. */\n label: string | DomphyElement;\n /** Panel content rendered when this tab is active. */\n content: DomphyElement;\n /** Stable identity key. Defaults to the item's zero-based index. */\n key?: string | number;\n};\n\n/**\n * All-in-one tabs patch. Generates a `[role=tablist]` button row and\n * `[role=tabpanel]` panels from the `items` array. Apply to any wrapper\n * element (`div`, `section`, …). No companion `tab()` / `tabPanel()` needed.\n *\n * To control the active tab programmatically, pass an external `State` as\n * `activeKey` and call `.set()` on it from outside.\n *\n * @param props.items - Tab definitions `{ label, content, key? }`.\n * @param props.activeKey - Initially active key (value or State). Defaults to the first item's key.\n * @param props.accentColor - Theme color for the active underline indicator. Defaults to `\"primary\"`.\n * @param props.color - Theme color for the resting underline. Defaults to `\"neutral\"`.\n * @example\n * { div: null, $: [tabs({ items: [\n * { label: \"Overview\", content: { p: \"Overview content\" } },\n * { label: \"API\", content: { p: \"API content\" } },\n * ] })] }\n */\nfunction tabs(\n props: {\n items: TabItem[];\n activeKey?: ValueOrState<string | number>;\n accentColor?: ThemeColor;\n color?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const { items = [], accentColor = \"primary\", color = \"neutral\" } = props;\n const activeKey = toState(props.activeKey ?? items[0]?.key ?? 0);\n\n return {\n _onSchedule: (node, element) => {\n const id = node.nodeId;\n\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? index;\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n button: [labelEl],\n _key: key,\n type: \"button\",\n role: \"tab\",\n id: `tab${id}${key}`,\n ariaControls: `panel${id}${key}`,\n ariaSelected: (l: Listener) => activeKey.get(l) === key,\n onClick: () => activeKey.set(key),\n onKeyDown: (e: Event) => {\n const k = (e as KeyboardEvent).key;\n if (![\"ArrowLeft\", \"ArrowRight\", \"Home\", \"End\"].includes(k)) return;\n e.preventDefault();\n const keys = items.map((it, i) => it.key ?? i);\n const idx = keys.indexOf(key);\n let next = idx;\n if (k === \"ArrowRight\") next = (idx + 1) % keys.length;\n else if (k === \"ArrowLeft\")\n next = (idx - 1 + keys.length) % keys.length;\n else if (k === \"Home\") next = 0;\n else if (k === \"End\") next = keys.length - 1;\n activeKey.set(keys[next]);\n },\n style: {\n cursor: \"pointer\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: (l: Listener) => themeSpacing(6 + themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 4),\n border: \"none\",\n outline: \"none\",\n color: (l: Listener) => themeColor(l, \"text\"),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\"),\n boxShadow: (l: Listener) =>\n `inset 0 -${themeSpacing(0.5)} 0 0 ${themeColor(l, \"shift-1\", color)}`,\n transition: \"box-shadow 140ms ease, color 140ms ease\",\n \"&:hover:not([disabled])\": {\n boxShadow: (l: Listener) =>\n `inset 0 -${themeSpacing(0.5)} 0 0 ${themeColor(l, \"shift-2\", color)}`,\n },\n \"&[aria-selected=true]:not([disabled])\": {\n boxShadow: (l: Listener) =>\n `inset 0 -${themeSpacing(0.5)} 0 0 ${themeColor(l, \"shift-6\", accentColor)}`,\n },\n \"&:focus-visible\": {\n boxShadow: (l: Listener) => focusRing(l, accentColor),\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n const tablist: DomphyElement<\"div\"> = {\n div: buttons,\n role: \"tablist\",\n ariaOrientation: \"horizontal\",\n style: { display: \"flex\" },\n } as DomphyElement<\"div\">;\n\n const panels: DomphyElement<\"div\">[] = items.map((item, index) => {\n const key = item.key ?? index;\n return {\n div: [item.content],\n _key: key,\n role: \"tabpanel\",\n id: `panel${id}${key}`,\n ariaLabelledby: `tab${id}${key}`,\n hidden: (l: Listener) => activeKey.get(l) !== key,\n style: {\n paddingBlock: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n },\n } as DomphyElement<\"div\">;\n });\n\n // Inject generated structure into the host element's children slot.\n (element as any)[node.tagName] = [tablist, ...panels];\n },\n };\n}\n\nexport { tabs };\nexport type { TabItem };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a multi-line text input (border, focus/hover/invalid/disabled states)\n * on the host `<textarea>` element, with optional auto-resize to content.\n *\n * @hostTag textarea\n * @param props.color - Theme color for the border and text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for hover/focus outline. Optional, accepts a value or state. Defaults to `\"primary\"`.\n * @param props.autoResize - When true, grows the textarea height to fit its content on input. Optional. Defaults to `false`.\n * @example { textarea: null, $: [textarea({ autoResize: true })] }\n */\nfunction textarea(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n autoResize?: boolean;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n const { autoResize = false } = props;\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"textarea\") {\n console.warn(`\"textarea\" primitive patch must use textarea tag`);\n }\n },\n _onMount: (node) => {\n if (autoResize) {\n const el = node.domElement as HTMLTextAreaElement;\n el.style.overflow = \"hidden\";\n const resize = () => {\n el.style.height = \"auto\";\n el.style.height = `${el.scrollHeight}px`;\n };\n el.addEventListener(\"input\", resize);\n resize();\n node.addHook(\"Remove\", () => el.removeEventListener(\"input\", resize));\n }\n },\n style: {\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n resize: \"vertical\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n border: \"none\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::placeholder\": {\n color: (listener) => themeColor(listener, \"shift-7\"),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&:invalid\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-5\", \"error\")}`,\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n },\n },\n };\n}\n\nexport { textarea };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Container for a vertical timeline. Sets list reset styles. Apply to `<ol>` or `<ul>`.\n *\n * @example { ol: [...], $: [timeline()] }\n */\nfunction timeline(): PartialElement {\n return {\n style: {\n listStyle: \"none\",\n margin: 0,\n padding: 0,\n display: \"flex\",\n flexDirection: \"column\",\n },\n };\n}\n\n/**\n * A single event row in a `timeline`. Uses a 2-column grid: the left column holds\n * a dot (`::before`) and optional connector line (`::after`); the right column holds\n * the user's content. Apply to `<li>`.\n *\n * @param props.active - Full-opacity dot (accent color). `ValueOrState<boolean>`, defaults to `false`.\n * @param props.last - Suppress the vertical connector below this item. `boolean`, defaults to `false`.\n * @param props.color - Dot/connector color tone. `ThemeColor`, defaults to `\"neutral\"`.\n * @param props.accentColor - Active dot color tone. `ThemeColor`, defaults to `\"primary\"`.\n * @example { li: [{ b: \"2024\" }, { p: \"Event\" }], $: [timelineItem({ active: true })] }\n */\nfunction timelineItem(\n props: {\n active?: ValueOrState<boolean>;\n last?: boolean;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = {},\n): PartialElement {\n const { last = false } = props;\n const color = props.color ?? \"neutral\";\n const accentColor = props.accentColor ?? \"primary\";\n const activeState = toState(props.active ?? false);\n\n return {\n style: {\n display: \"grid\",\n gridTemplateColumns: \"2rem 1fr\",\n columnGap: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBottom: (listener) =>\n last ? \"0\" : themeSpacing(themeDensity(listener) * 4),\n position: \"relative\",\n\n // Dot\n \"&::before\": {\n content: '\"\"',\n display: \"block\",\n width: \"0.75rem\",\n height: \"0.75rem\",\n borderRadius: \"50%\",\n justifySelf: \"center\",\n marginTop: \"0.25em\",\n transition: \"background-color 200ms ease, opacity 200ms ease\",\n backgroundColor: (listener) =>\n themeColor(\n listener,\n \"shift-8\",\n activeState.get(listener) ? accentColor : color,\n ),\n opacity: (listener) => (activeState.get(listener) ? \"1\" : \"0.4\"),\n },\n\n // Vertical connector to the next item\n ...(last\n ? {}\n : {\n \"&::after\": {\n content: '\"\"',\n position: \"absolute\",\n left: \"calc(1rem - 1px)\",\n top: \"1.25rem\",\n bottom: (listener) =>\n `-${themeSpacing(themeDensity(listener) * 4)}`,\n width: \"2px\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color),\n },\n }),\n },\n };\n}\n\nexport { timeline, timelineItem };\n","import type { DomphyElement, ElementNode, PartialElement } from \"@domphy/core\";\nimport { toState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\n\ntype ToastPosition =\n | \"top-left\"\n | \"top-center\"\n | \"top-right\"\n | \"bottom-left\"\n | \"bottom-center\"\n | \"bottom-right\";\n\n/**\n * Renders a transient notification surface as a fixed-position overlay (portaled\n * into a corner stack), animating in on mount and out before removal. No host\n * tag check; typically applied to a `<div>`.\n *\n * @param props.position - Corner of the screen for the toast stack. Optional, one of `\"top-left\" | \"top-center\" | \"top-right\" | \"bottom-left\" | \"bottom-center\" | \"bottom-right\"`. Defaults to `\"top-center\"`.\n * @param props.color - Theme color for the toast surface. Optional. Defaults to `\"neutral\"`.\n * @example { div: \"Saved!\", $: [toast({ position: \"top-right\" })] }\n */\nfunction toast(\n props: { position?: ToastPosition; color?: ThemeColor } = {},\n): PartialElement {\n const { position = \"top-center\", color = \"neutral\" } = props;\n const state = toState(false);\n\n const isTop = position.startsWith(\"top\");\n const isCenter = position.endsWith(\"center\");\n const isRight = position.endsWith(\"right\");\n\n const overlayEle: DomphyElement<\"div\"> = {\n div: [],\n id: `domphy-toast-${position}`,\n style: {\n position: \"fixed\",\n display: \"flex\",\n flexDirection: isTop ? \"column\" : \"column-reverse\",\n alignItems: isCenter ? \"center\" : isRight ? \"end\" : \"start\",\n inset: 0,\n gap: themeSpacing(4),\n zIndex: 30,\n padding: themeSpacing(6),\n pointerEvents: \"none\",\n },\n };\n\n return {\n _portal: (rootNode) => {\n let overlay = rootNode.domElement!.querySelector(\n `#domphy-toast-${position}`,\n );\n if (!overlay) {\n const overlayNode = rootNode.children!.insert(\n overlayEle,\n ) as ElementNode;\n overlay = overlayNode.domElement!;\n }\n return overlay;\n },\n role: \"status\",\n ariaAtomic: \"true\",\n // Toast is rendered as an overlay surface, so it uses the inverted branch.\n dataTone: \"shift-17\",\n style: {\n minWidth: themeSpacing(32),\n pointerEvents: \"auto\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n boxShadow: elevation(\"medium\"),\n opacity: (listener) => Number(state.get(listener)),\n transform: (listener) =>\n state.get(listener)\n ? \"translateY(0)\"\n : isTop\n ? \"translateY(-100%)\"\n : \"translateY(100%)\",\n transition: \"opacity 300ms ease, transform 300ms ease\",\n },\n _onMount: () => requestAnimationFrame(() => state.set(true)),\n _onBeforeRemove: (node, done) => {\n let finished = false;\n let timer: ReturnType<typeof setTimeout> | null = null;\n const finish = () => {\n if (finished) return;\n finished = true;\n if (timer) {\n clearTimeout(timer);\n timer = null;\n }\n node.domElement!.removeEventListener(\"transitionend\", onEnd);\n done();\n };\n const onEnd = (e: Event) => {\n if ((e as TransitionEvent).propertyName === \"transform\") finish();\n };\n node.domElement!.addEventListener(\"transitionend\", onEnd);\n // Fallback: if transitionend never fires (reduced-motion, display:none,\n // early detach), unblock removal after the transition duration + buffer.\n timer = setTimeout(finish, 350);\n // If the node is detached before the exit animation settles, clear the\n // pending fallback timer and the transitionend listener so they cannot\n // fire on a removed node.\n node.addHook(\"Remove\", () => {\n if (timer) {\n clearTimeout(timer);\n timer = null;\n }\n node.domElement?.removeEventListener(\"transitionend\", onEnd);\n });\n state.set(false);\n },\n };\n}\n\nexport { toast };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/** One item inside a toggle group. */\ntype ToggleItem = {\n /** Button label — plain string (auto-wrapped) or any DomphyElement. */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index as a string. */\n key?: string;\n};\n\n/**\n * All-in-one toggle group — single or multi-select button group. Generates\n * `<button>` toggle elements from the `items` array. Apply to any wrapper element.\n *\n * @param props.items - Item definitions `{ label, key? }`.\n * @param props.value - Selected key(s) (value or State). Defaults to `[]` (multiple) or `\"\"` (single).\n * @param props.multiple - Allow multiple items selected at once. Defaults to `false`.\n * @param props.color - Theme color for the group background/border. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for the pressed state. Defaults to `\"primary\"`.\n * @example\n * { div: null, $: [toggleGroup({ multiple: true, items: [\n * { label: \"Bold\", key: \"bold\" },\n * { label: \"Italic\", key: \"italic\" },\n * ] })] }\n */\nfunction toggleGroup(\n props: {\n items: ToggleItem[];\n value?: ValueOrState<string | string[]>;\n multiple?: boolean;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const {\n items = [],\n multiple = false,\n color = \"neutral\",\n accentColor = \"primary\",\n } = props;\n const value = toState(props.value ?? (multiple ? [] : \"\"));\n\n return {\n role: \"group\",\n // Expose value + multiple in context so toggle() escape-hatch still works.\n _context: { toggleGroup: { value, multiple } },\n _onSchedule: (node, element) => {\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? String(index);\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n button: [labelEl],\n _key: key,\n type: \"button\",\n role: \"button\",\n ariaPressed: (l: Listener) => {\n const val = value.get(l);\n return Array.isArray(val) ? val.includes(key) : val === key;\n },\n onClick: () => {\n const val = value.get();\n if (multiple) {\n const arr = Array.isArray(val) ? [...val] : [];\n value.set(\n arr.includes(key)\n ? arr.filter((v) => v !== key)\n : [...arr, key],\n );\n } else {\n value.set(val === key ? \"\" : key);\n }\n },\n style: {\n cursor: \"pointer\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: themeSpacing(6),\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(2),\n border: \"none\",\n borderRadius: themeSpacing(1.5),\n color: (l: Listener) => themeColor(l, \"text\", color),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (l: Listener) => themeColor(l, \"hover\", color),\n },\n \"&[aria-pressed=true]\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-3\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-12\", accentColor),\n },\n \"&:focus-visible\": {\n boxShadow: (l: Listener) => focusRing(l, accentColor),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n (element as any)[node.tagName] = buttons;\n },\n style: {\n display: \"flex\",\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(1),\n gap: themeSpacing(1),\n borderRadius: themeSpacing(2),\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n outline: (l: Listener) => `1px solid ${themeColor(l, \"border\", color)}`,\n outlineOffset: \"-1px\",\n },\n };\n}\n\nexport { toggleGroup };\nexport type { ToggleItem };\n","import type { DomphyElement, PartialElement } from \"@domphy/core\";\nimport { row } from \"./row.js\";\n\n/**\n * A horizontal flex row with vertically centered items. Useful for headers,\n * toolbars, navigation bars, and action strips. A semantic alias of `row()`\n * at its default alignment — reach for `row()` directly for `justify`/`wrap`/\n * `align` beyond this shape.\n *\n * @param props.gap - Spacing multiplier for gap between items (default 4 = 1em).\n * @example { header: [...], $: [toolbar()] }\n * @example { nav: [...], $: [toolbar({ gap: 3 })] }\n */\nfunction toolbar(props: { gap?: number } = {}): PartialElement {\n return row({ gap: props.gap });\n}\n\n/**\n * A flex spacer that expands to fill available space in a toolbar, pushing\n * subsequent items to the far end.\n *\n * @example { header: [logo, toolbarSpacer(), nav, actions], $: [toolbar()] }\n */\nfunction toolbarSpacer(): DomphyElement {\n return { div: null, style: { flex: \"1 1 0\" } };\n}\n\nexport { toolbar, toolbarSpacer };\n","import {\n type DomphyElement,\n merge,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\nimport { popoverArrow } from \"./popoverArrow.js\";\n\n/**\n * Attaches a floating tooltip to the host element, shown on hover/focus and\n * hidden on leave/blur/Escape. Returns the anchor (trigger) partial; the tooltip\n * surface is positioned via the floating utility and linked with\n * `aria-describedby`. No host tag check; applied to the trigger element.\n *\n * @param props.open - Controlled open state. Optional, accepts a value or state. Defaults to `false`.\n * @param props.placement - Floating placement relative to the trigger. Optional, accepts a value or state (`Placement`). Defaults to `\"top\"`.\n * @param props.content - Tooltip text content. Optional, accepts a value or state (string only). Defaults to `\"Tooltip Content\"`.\n * @example { button: \"Hover me\", $: [tooltip({ content: \"Help text\" })] }\n */\nfunction tooltip(\n props: {\n open?: ValueOrState<boolean>;\n placement?: ValueOrState<Placement>;\n content?: ValueOrState<string>;\n } = {},\n): PartialElement {\n const {\n open = false,\n placement = \"top\",\n content = \"Tooltip Content\",\n } = props;\n\n const placeState = toState(placement);\n const contentState = toState(content);\n\n // Pre-generate ID so the trigger can reference it via aria-describedby\n // before the tooltip content element is first inserted into the DOM.\n const tooltipId = `domphy-tt-${Math.random().toString(36).slice(2, 9)}`;\n\n const contentElement: DomphyElement<\"span\"> = {\n span: (listener) => contentState.get(listener),\n id: tooltipId,\n };\n\n const { show, hide, anchorPartial } = createFloating({\n kind: \"tooltip\",\n open,\n placement: placeState,\n content: contentElement,\n });\n\n const tooltipPartial: PartialElement = {\n role: \"tooltip\",\n dataSize: \"decrease-1\",\n dataTone: \"shift-17\",\n style: {\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n color: (listener) => themeColor(listener, \"text\"),\n backgroundColor: (listener) => themeColor(listener),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n boxShadow: elevation(\"low\"),\n },\n $: [popoverArrow({ placement: placeState, bordered: false })],\n };\n contentElement.$ ||= [];\n contentElement.$.push(tooltipPartial);\n\n const triggerPartial: PartialElement = {\n ariaDescribedby: tooltipId,\n onMouseEnter: (_e, node) => show(node),\n onMouseLeave: (_e, node) => hide(node),\n onFocus: (_e, node) => show(node),\n onBlur: (_e, node) => hide(node),\n onKeyDown: (e, node) => (e as KeyboardEvent).key === \"Escape\" && hide(node),\n };\n\n merge(anchorPartial, triggerPartial);\n\n return anchorPartial;\n}\n\nexport { tooltip };\n","import { ElementNode, type PartialElement } from \"@domphy/core\";\n\ntype RectMap = Map<string, DOMRect>;\n\nfunction getItemId(node: ElementNode, index: number): string {\n if (node.key !== undefined && node.key !== null) {\n return String(node.key);\n }\n return `index-${index}`;\n}\n\n/**\n * Animates child reordering using the FLIP technique: records each child's\n * position before an update and smoothly transitions it from its old to new\n * position afterward. No host tag check; applied to the list container.\n *\n * @param props.duration - Transition duration in milliseconds. Optional. Defaults to `300`.\n * @param props.delay - Transition delay in milliseconds. Optional. Defaults to `0`.\n * @example { ul: null, $: [transitionGroup({ duration: 300 })] }\n */\nfunction transitionGroup(\n props: { duration?: number; delay?: number } = {},\n): PartialElement {\n const { duration = 300, delay = 0 } = props;\n\n let previousRects: RectMap = new Map();\n // Cancels any in-flight animation for a given DOM element before starting a new one.\n const cancelMap = new Map<HTMLElement, () => void>();\n // Pending fallback timers and queued rAF callbacks, tracked so a removal of\n // the container mid-animation can clear them instead of firing on a detached node.\n const pendingTimers = new Set<ReturnType<typeof setTimeout>>();\n const pendingFrames = new Set<number>();\n\n return {\n _onMount: (node) => {\n node.addHook(\"Remove\", () => {\n // Stop every in-flight animation: removes transitionend listeners.\n for (const cancel of Array.from(cancelMap.values())) cancel();\n cancelMap.clear();\n // Clear queued fallback timers.\n for (const timer of pendingTimers) clearTimeout(timer);\n pendingTimers.clear();\n // Cancel queued animation frames.\n for (const frame of pendingFrames) cancelAnimationFrame(frame);\n pendingFrames.clear();\n });\n },\n _onBeforeUpdate: (node) => {\n previousRects = new Map();\n node.children.items.forEach((item, index) => {\n if (!(item instanceof ElementNode)) return;\n const dom = item.domElement as HTMLElement | undefined;\n if (!dom) return;\n previousRects.set(getItemId(item, index), dom.getBoundingClientRect());\n });\n },\n _onUpdate: (node) => {\n node.children.items.forEach((item, index) => {\n if (!(item instanceof ElementNode)) return;\n const dom = item.domElement as HTMLElement | undefined;\n if (!dom) return;\n\n const key = getItemId(item, index);\n const prev = previousRects.get(key);\n if (!prev) return;\n\n const next = dom.getBoundingClientRect();\n const deltaX = prev.left - next.left;\n const deltaY = prev.top - next.top;\n if (Math.abs(deltaX) < 0.5 && Math.abs(deltaY) < 0.5) return;\n\n // Cancel any in-flight animation on this element before starting a new one.\n cancelMap.get(dom)?.();\n\n dom.style.transition = \"none\";\n dom.style.transform = `translate(${deltaX}px, ${deltaY}px)`;\n dom.getBoundingClientRect();\n\n const frame = requestAnimationFrame(() => {\n pendingFrames.delete(frame);\n dom.style.transition = `transform ${duration}ms ease ${delay}ms`;\n dom.style.transform = \"translate(0px, 0px)\";\n });\n pendingFrames.add(frame);\n\n let cancelled = false;\n let timer: ReturnType<typeof setTimeout> | null = null;\n const finish = () => {\n if (cancelled) return;\n cancelled = true;\n if (timer) {\n pendingTimers.delete(timer);\n timer = null;\n }\n cancelMap.delete(dom);\n dom.removeEventListener(\"transitionend\", onEnd);\n dom.style.transition = \"\";\n dom.style.transform = \"\";\n };\n\n const onEnd = (event: Event) => {\n if ((event as TransitionEvent).propertyName === \"transform\") finish();\n };\n\n cancelMap.set(dom, () => {\n cancelled = true;\n if (timer) {\n clearTimeout(timer);\n pendingTimers.delete(timer);\n timer = null;\n }\n cancelMap.delete(dom);\n dom.removeEventListener(\"transitionend\", onEnd);\n });\n\n dom.addEventListener(\"transitionend\", onEnd);\n timer = setTimeout(finish, duration + delay + 34);\n pendingTimers.add(timer);\n });\n previousRects.clear();\n },\n };\n}\n\nexport { transitionGroup };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a bulleted list (disc markers, reset margins, themed text) on the host\n * `<ul>` element.\n *\n * @hostTag ul\n * @param props.color - Theme color for the list text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { ul: null, $: [unorderedList()] }\n */\nfunction unorderedList(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"ul\") {\n console.warn(`\"unorderedList\" primitive patch must use ul tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n marginTop: 0,\n marginBottom: 0,\n paddingLeft: themeSpacing(3),\n listStyleType: \"disc\",\n listStylePosition: \"outside\",\n },\n };\n}\n\nexport { unorderedList };\n"],"mappings":"kzBAAA,IAAAA,GAAA,GAAAC,GAAAD,GAAA,UAAAE,GAAA,UAAAA,GAAA,OAAAC,s8BCAaC,GAAoB,CAC/B,kBACA,QACA,YACA,WACA,UACA,UACA,kBACA,WACA,UACA,UACA,QACA,WACA,iBACA,SACA,QACA,YACA,OACA,WACA,QACA,SACA,UACA,aACA,OACA,cACA,WACA,WACA,WACA,SACA,WACA,WACA,YACA,gBACA,QACA,aACA,QACA,WACA,WACA,SACA,sBACF,ECxCaC,GAA4B,CACvC,UACA,sBACA,oBACA,gBACA,eACA,cACA,YACA,YACA,eACA,cACA,cACA,OACA,OACA,sBACA,mBACA,eACA,cACA,iBACA,mBACA,gBACA,mBACA,YACA,gBACA,aACA,mBACA,mBACA,eACA,4BACA,YACF,ECjBaC,GAA6C,CAExD,QAAS,MAGT,gBAAiB,kBACjB,UAAW,YACX,SAAU,WACV,gBAAiB,kBACjB,eAAgB,iBAChB,MAAO,QACP,UAAW,YACX,OAAQ,SACR,QAAS,UACT,WAAY,aACZ,YAAa,cACb,UAAW,YACX,cAAe,gBACf,WAAY,aACZ,SAAU,WACV,qBAAsB,uBAGtB,eAAgB,iBAGhB,UAAW,YACX,aAAc,eACd,UAAW,YACX,OAAQ,SACR,SAAU,WACV,QAAS,UACT,SAAU,WACV,SAAU,WACV,mBAAoB,qBAGpB,QAAS,UACT,SAAU,WACV,YAAa,cACb,MAAO,QACP,QAAS,UACT,MAAO,QACP,WAAY,aACZ,YAAa,cACb,WAAY,aACZ,WAAY,aACZ,cAAe,gBACf,oBAAqB,sBACrB,oBAAqB,sBACrB,eAAgB,iBAChB,YAAa,cACb,SAAU,WACV,aAAc,eACd,YAAa,cACb,eAAgB,iBAChB,OAAQ,SACR,OAAQ,SACR,cAAe,gBACf,OAAQ,SACR,QAAS,UACT,OAAQ,SACR,OAAQ,SACR,QAAS,UACT,WAAY,aACZ,YAAa,cACb,QAAS,UACT,SAAU,WACV,SAAU,WACV,UAAW,YACX,mBAAoB,qBACpB,yBAA0B,2BAC1B,eAAgB,iBAChB,QAAS,UACT,QAAS,UACT,OAAQ,SACR,OAAQ,SACR,QAAS,UACT,UAAW,YACX,UAAW,YACX,aAAc,eACd,QAAS,UACT,SAAU,UACZ,EChGaC,GAAW,CACtB,IACA,OACA,UACA,UACA,QACA,QACA,IACA,OACA,aACA,KACA,SACA,SACA,UACA,OACA,OACA,MACA,WACA,OACA,WACA,KACA,MACA,UACA,MACA,SACA,MACA,KACA,KACA,KACA,WACA,aACA,SACA,SACA,OACA,KACA,KACA,KACA,KACA,KACA,KACA,SACA,SACA,IACA,SACA,MACA,QACA,MACA,MACA,QACA,SACA,KACA,OACA,MACA,OACA,OACA,QACA,MACA,WACA,SACA,KACA,WACA,SACA,SACA,IACA,QACA,UACA,MACA,WACA,IACA,KACA,KACA,OACA,IACA,OACA,UACA,SACA,OACA,QACA,SACA,OACA,SACA,MACA,UACA,MACA,QACA,QACA,KACA,WACA,WACA,QACA,KACA,QACA,OACA,QACA,KACA,QACA,IACA,KACA,MACA,QACA,MACA,MACA,MACA,OACA,OACA,SACA,OACA,QACA,KACA,UACA,gBACA,mBACA,SACA,WACA,SACA,OACA,OACA,UACA,UACA,gBACA,sBACA,cACA,mBACA,oBACA,oBACA,iBACA,eACA,UACA,UACA,UACA,UACA,UACA,iBACA,UACA,UACA,cACA,eACA,WACA,eACA,qBACA,cACA,SACA,eACA,SACA,gBACA,IACA,QACA,OACA,iBACA,SACA,OACA,WACA,QACA,OACA,UACA,UACA,WACA,WACA,iBACA,OACA,MACA,aACA,OACA,MACA,SACA,SACA,SACA,OACA,WACA,QACA,MACA,MACF,EC3KaC,GAAsC,CACjD,UAAW,CAAC,SAAU,IAAI,EAC1B,WAAY,CAAC,SAAU,IAAI,EAC3B,UAAW,CAAC,QAAQ,EACpB,WAAY,CAAC,SAAU,IAAI,EAC3B,cAAe,CAAC,SAAU,IAAI,EAC9B,SAAU,CAAC,SAAU,IAAI,EACzB,eAAgB,CAAC,SAAU,IAAI,EAC/B,WAAY,CAAC,SAAU,IAAI,EAC3B,UAAW,CAAC,SAAU,IAAI,EAC1B,MAAO,CAAC,SAAU,IAAI,EACtB,SAAU,CAAC,SAAU,IAAI,EACzB,WAAY,CAAC,SAAU,IAAI,EAC3B,UAAW,CAAC,SAAU,IAAI,EAC1B,QAAS,CAAC,QAAQ,EAClB,YAAa,CAAC,QAAQ,EACtB,UAAW,CAAC,QAAQ,EACpB,WAAY,CAAC,QAAQ,EACrB,YAAa,CAAC,QAAQ,EACtB,UAAW,CAAC,QAAQ,EACpB,WAAY,CAAC,SAAU,KAAK,EAC5B,OAAQ,CAAC,QAAQ,EACjB,eAAgB,CAAC,QAAQ,EACzB,SAAU,CAAC,QAAQ,EACnB,KAAM,CAAC,QAAQ,EACf,UAAW,CAAC,QAAQ,EACpB,eAAgB,CAAC,SAAU,IAAI,EAC/B,QAAS,CAAC,SAAU,IAAI,EACxB,YAAa,CAAC,SAAU,IAAI,EAC5B,oBAAqB,CAAC,IAAI,EAC1B,iBAAkB,CAAC,IAAI,EACvB,gBAAiB,CAAC,IAAI,EACtB,aAAc,CAAC,IAAI,EACnB,WAAY,CAAC,IAAI,EACjB,QAAS,CAAC,IAAI,EACd,kBAAmB,CAAC,QAAQ,EAC5B,gBAAiB,CAAC,QAAQ,EAC1B,mBAAoB,CAAC,QAAQ,EAC7B,iBAAkB,CAAC,QAAQ,EAC3B,cAAe,CAAC,QAAQ,EACxB,cAAe,CAAC,QAAQ,EACxB,aAAc,CAAC,QAAQ,EACvB,aAAc,CAAC,QAAQ,EACvB,WAAY,CAAC,QAAQ,EACrB,UAAW,CAAC,QAAQ,EACpB,QAAS,CAAC,KAAK,EACf,mBAAoB,CAAC,SAAU,IAAI,EACnC,YAAa,CAAC,IAAI,EAClB,OAAQ,CAAC,QAAQ,EACjB,iBAAkB,CAAC,QAAQ,EAC3B,eAAgB,CAAC,QAAQ,EACzB,mBAAoB,CAAC,QAAQ,EAC7B,kBAAmB,CAAC,QAAQ,CAC9B,ECtDaC,GAAU,CACrB,MACA,SACA,OACA,OACA,UACA,OACA,WACA,UACA,IACA,OACA,MACA,SACA,iBACA,iBACA,OACA,WACA,OACA,SACA,OACA,QACA,WACA,QACA,UACA,SACA,UACA,mBACA,gBACA,iBACA,cACA,gBACA,UACA,cACA,WACA,UACA,UACA,eACA,oBACA,sBACA,UACA,UACA,UACA,UACA,eACF,EC5CaC,GAAW,CACtB,OACA,OACA,KACA,MACA,QACA,KACA,MACA,QACA,OACA,OACA,SACA,QACA,KACF,ECVMC,GAAwB,CAAC,EAExB,SAASC,GAAUC,EAAsC,CAC9D,OAAO,OAAOF,GAASE,CAAO,CAChC,CAEO,SAASC,IAAoC,CAClD,OAAOH,EACT,CCZO,IAAMI,GAAkB,CAC7B,UACA,aACA,gBACA,iBACA,SACA,WACA,YACA,mBACA,WACA,UACA,UACA,gBACA,gBACA,oBACA,SACA,cACA,QACA,aACA,SACA,YACA,cACA,cACA,aACA,cACA,SACA,mBACA,YACA,UACA,UACA,UACA,aACA,UACA,YACA,YACA,aACA,UACA,SACA,eACA,mBACA,cACA,cACA,eACA,eACA,cACA,aACA,cACA,YACA,UACA,UACA,SACA,YACA,aACA,eACA,UACA,WACA,WACA,cACA,4BACA,WACA,YACA,WACA,eACA,YACA,WACA,YACA,eACA,WACA,iBACA,YACA,UACA,eACA,cACA,aACA,gBACA,gBACA,gBACA,cACA,kBACA,iBACA,iBACA,gBACA,eACA,sBACA,uBACA,qBACA,sBACA,mBACA,kBACA,oBACA,mBACA,iBACA,uBACA,qBACA,oBACA,YACA,YACF,EAEaC,GAAeD,GAAgB,OAC1C,CAACE,EAAKC,IAAO,CACX,IAAMC,EAAMD,EAAG,MAAM,CAAC,EAAE,YAAY,EACpC,OAAAD,EAAIE,CAAG,EAAID,EACJD,CACT,EACA,CAAC,CAGH,EChGaG,GAAN,KAAgB,CAOrB,YAAYC,EAAgC,CAF5C,KAAQ,UAA6B,IAAI,IAGvC,IAAMC,GAAW,IAAMD,EAAmB,GAG1CC,EAAQ,YAAeC,GAAwB,CAC7C,KAAK,UAAU,IAAIA,CAAO,CAC5B,EACA,KAAK,QAAUD,CACjB,CAKA,OAAc,CACZ,QAAWC,KAAW,KAAK,UAAWA,EAAQ,EAC9C,KAAK,UAAU,MAAM,CACvB,CAEA,IAAI,iBAA0B,CAC5B,OAAO,KAAK,UAAU,IACxB,CACF,EAKMC,GAA+B,CAAC,EAIlCC,GAAgB,EAIb,SAASC,IAAoC,CA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VpJA,IAAMU,GAAoB,CACxB,UAAW,SACX,OAAQ,CACN,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,UAAW,CACT,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,KAAM,CACJ,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,UAAW,CACT,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,MAAO,CACL,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,OAAQ,CACN,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,UAAW,CACT,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,CACF,EACA,UAAW,CACT,UAAW,EACX,QAAS,EACT,UAAW,EACX,MAAO,EACP,OAAQ,EACR,UAAW,EACX,QAAS,EACT,KAAM,EACN,QAAS,EACT,QA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","names":["global_exports","__export","dist_exports","src_exports","BooleanAttributes","CamelAttributes","HtmlAttributeNames","HtmlTags","PrefixCSS","SvgTags","VoidTags","_config","configure","options","getConfig","EventProperties","eventNameMap","acc","ev","key","Collector","onDependencyChange","handler","release","COLLECTOR_STACK","UNTRACK_DEPTH","activeCollector","runWithCollector","collector","fn","runUntracked","_chain","_microtask","cb","e","SELF_NOTIFY_CAP","_batchDepth","_batchedNotifiers","_scheduledNotifiers","runBatched","notifiers","notifier","Notifier","event","listener","listeners","_a","_b","_c","args","top","inflight","idx","n","names","pending","chain","hasPendingNotifiers","flushPendingNotifiers","guard","State","initialValue","name","newValue","merge","source","target","comma","space","adjacent","deepClone","value","old","val1","val2","addEvent","addHook","hashString","str","hash","i","toState","val","isState","readonly","behavior","attach","props","partial","hookName","hookProperty","current","attributes","eventName","eventProperty","node","seen","clone","v","k","proto","validate","element","asPartial","keys","isHTML","sanitizeHTMLString","html","result","escapeHTML","getTagName","camelToKebab","selectorSplitter","selectors","splitted","parens","angulars","soFar","len","char","normalizeSelectorKey","selectorText","text","collectCSSRules","rules","map","rule","ensureDomStyle","styleParent","nonce","domStyle","resolvedNonce","mergePartial","part","p","EnumeratedBooleanAttributes","ElementAttribute","parent","domElement","mutateAttrs","prev","releaseSubscription","callback","AttributeList","attr","domName","force","className","add","classes","newClass","list","declared","currentIsFn","nextIsFn","updated","cls","oldClass","__DEV__","StyleProperty","parentRule","domRule","style","prefix","_d","StyleRule","_StyleRule","StyleList","prop","root","styleStr","decl","nested","sheet","domSheet","index","css","err","obj","parentSelector","basic","conditionalRules","getSelector","selector","splitKeys","currentSelector","newSelector","r","existingKey","domRuleMap","domRuleList","wrongCount","fixOddEven","dom","ElementNode","_ElementNode","domphyElement","_parent","ElementList","tempPath","_k","children","input","error","releases","originalKey","rawElement","content","next","autoClass","reserved","hookKeys","keep","userClass","userClassFn","boundary","composed","behaviors","spec","instance","child","childNode","newNode","done","called","once","beforeRemoveHook","TextNode","textContent","tpl","el","wasHTML","fresh","domText","_warnedKeylessSites","_resetKeylessWarnings","item","ref","aNode","bNode","a","b","aNext","bNext","inputs","updateDom","silent","imperative","oldItems","keyed","oldSet","claimed","unkeyedObjectInputs","lengthChanged","isObj","tag","reused","cur","isPortal","at","extras","siteId","msg","length","finalIndex","domNode","doneCalled","onceDone","snapshot","aIndex","bIndex","itemA","itemB","fromIndex","toIndex","REACTION_QUEUE","reactionDrainScheduled","scheduleReaction","job","drainReactions","jobs","flushSync","SCOPE_STACK","activeScope","registerDisposer","dispose","scope","EffectScope","effectScope","effect","disposed","running","run","computed","EVENT","cachedValue","dirty","hasValue","recomputeAndNotify","recompute","previous","had","get","outer","batch","untrack","watch","oldValue","firstRun","nextTick","RecordState","record","__spreadValues","l","dist_exports","__export","se","g","oe","ue","m","ee","te","L","ge","Te","ae","re","p","he","ne","O","h","lrgbToSrgb","rgb","toSRGB","c","clamped","s","srgbToLrgb","toLRGB","rgbToHex","r","g","b","hexToRgb","hex","rgbToOklab","l","m","l_","m_","s_","oklabToRgb","lab","L","a","rgbToLab","rgb","r","g","b","x","y","z","Xn","Yn","Zn","f","t","fx","fy","fz","calcDeltaE2000","lab1","lab2","L1","a1","b1","L2","a2","b2","avgL","C1","C2","avgC","G","a1p","a2p","C1p","C2p","avgCp","h1p","h2p","dhp","avgHp","T","dLp","dCp","dHp","SL","SC","SH","dtheta","RT","createMonotone","points","_t","sorted","a","b","uniquePoints","i","n","x","p","y","h","secants","m","d0","d1","alpha","t","low","high","mid","dx","s","s2","s3","m0","m1","P","Q","warp","t","tn","unwarp","y","xn","euclidean3","v1","v2","sequentialInterpolator","rgbs","anchors","rgb","rgbToOklab","a","b","L","v","A","B","cumulativeDistances","totalDist","i","allParams","d","tMin","tMax","aInterpolator","createMonotone","p","bInterpolator","tWarped","tMapped","j","dStart","dEnd","ratio","l","oklabToRgb","generateRamp","hexs","stepsCount","colorAtParam","parameters","hexToRgb","colors","fullParams","anchorIdx","segment","k","startIdx","endIdx","startParam","endParam","rgbToHex","light","light_default","clone","v","escapeKey","k","themes","createDark","_themeVarsCache","_themeTokensCache","colorSteps","input","firstColor","validateTheme","partial","key","custom","colors","c","baseTones","deepMerge","target","source","_a","buildThemeCSS","name","styles","toneSteps","value","colorName","i","text","prop","getTheme","setTheme","dark","themeTokens","cached","tokens","colorTones","themeVars","theme","themeCSS","themeApply","el","themeSpacing","n","themeFluidSpacing","min","max","viewportMin","viewportMax","minEm","maxEm","slope","intercept","preferred","applySystemTheme","targetEl","options","persist","storageKey","resolve","saved","mql","handler","event","themeName","object","node","COLOR_ROLES","ElementDensities","offsetDensity","origin","density","resultDensity","offset","contextDensity","themeDensity","index","DEFAULT_FONT_SIZES","DEFAULT_DENSITIES","nearestStepIndex","ramp","baseHex","baseLab","rgbToLab","hexToRgb","best","bestDist","dist","calcDeltaE2000","generateTheme","baseColors","_b","_c","_d","_e","_f","steps","hex","generateRamp","ElementSizes","offsetSize","size","resultSize","contextSize","themeSize","TONE_STEPS","ToneAliases","ElementTones","adjustTone","tone","level","newIndex","shiftTone","midpoint","offsetTone","originTone","contextTone","biasContext","context","direction","bias","themeColor","color","resultTone","themeColorToken","colorTokens","src_exports","__export","abbreviation","accordion","alert","avatar","badge","blockquote","breadcrumb","breadcrumbEllipsis","button","buttonGhost","buttonSwitch","card","code","combobox","command","commandItem","commandSearch","datePicker","descriptionList","details","dialog","divider","drawer","emphasis","empty","errorBoundary","fab","figure","formGroup","heading","horizontalRule","icon","image","inputCheckbox","inputColor","inputDateTime","inputFile","inputNumber","inputOTP","inputPassword","inputRadio","inputRange","inputSearch","inputSwitch","inputText","keyboard","label","link","linkButton","list","listItem","listItemButton","mark","menu","motion","orderedList","pagination","panelSection","paragraph","popover","popoverArrow","preformated","progress","rating","ringProgress","row","scrollArea","segmented","select","selectBox","selectItem","selectList","skeleton","small","spinner","splitter","splitterHandle","splitterPanel","stack","steps","strong","subscript","superscript","table","tabs","tag","textarea","timeline","timelineItem","toast","toggleGroup","toolbar","toolbarSpacer","tooltip","transitionGroup","unorderedList","abbreviation","props","_a","_b","color","nt","accentColor","node","listener","he","ge","ne","accordion","props","_a","_b","type","color","nt","accentColor","node","el","handler","event","summary","item","detail","listener","ne","ae","ge","alert","props","_a","color","nt","ne","listener","ae","ge","he","avatar","props","_a","color","nt","ne","listener","he","ge","badge","props","_a","label","state","nt","color","l","ne","he","ge","blockquote","props","_a","color","nt","node","listener","he","ge","ne","ae","breadcrumb","props","_a","separator","color","nt","node","listener","he","ne","ge","breadcrumbEllipsis","props","_a","color","nt","node","listener","he","ne","ge","BUTTON_SIZE_FONT","focusRing","listener","color","ge","PADDING_STEPS","buttonGhost","props","_a","_b","_c","color","nt","padding","fontSize","BUTTON_SIZE_FONT","node","listener","he","ne","ae","ge","focusRing","PADDING_STEPS","button","props","_a","_b","_c","_d","variant","buttonGhost","color","nt","isSolid","padding","fontSize","BUTTON_SIZE_FONT","node","listener","he","ne","ae","ge","focusRing","buttonSwitch","props","_a","_b","checked","check","nt","color","accentColor","node","listener","he","ge","ne","card","props","_a","color","nt","listener","ne","ae","ge","code","props","_a","color","nt","node","listener","he","ge","ne","SHADOWS","elevation","level","sides","alignments","placements","acc","side","min","max","round","floor","createCoords","v","oppositeSideMap","clamp","start","value","end","evaluate","param","getSide","placement","getAlignment","getOppositeAxis","axis","getAxisLength","getSideAxis","firstChar","getAlignmentAxis","getAlignmentSides","rects","rtl","alignment","alignmentAxis","length","mainAlignmentSide","getOppositePlacement","getExpandedPlacements","oppositePlacement","getOppositeAlignmentPlacement","lrPlacement","rlPlacement","tbPlacement","btPlacement","getSideList","isStart","getOppositeAxisPlacements","flipAlignment","direction","list","expandPaddingObject","padding","__spreadValues","getPaddingObject","rectToClientRect","rect","x","y","width","height","computeCoordsFromPlacement","reference","floating","sideAxis","alignLength","isVertical","commonX","commonY","commonAlign","coords","detectOverflow","_0","__async","state","options","_a","_b","_c","_d","_e","_f","platform","elements","strategy","boundary","rootBoundary","elementContext","altBoundary","paddingObject","element","clippingClientRect","offsetParent","offsetScale","elementClientRect","MAX_RESET_COUNT","computePosition","config","middleware","platformWithDetectOverflow","__spreadProps","statefulPlacement","resetCount","middlewareData","i","currentMiddleware","name","fn","nextX","nextY","data","reset","flip","options","state","__async","_b","_c","_d","_e","_f","_g","placement","middlewareData","rects","initialPlacement","platform","elements","_a","evaluate","checkMainAxis","checkCrossAxis","specifiedFallbackPlacements","fallbackStrategy","fallbackAxisSideDirection","flipAlignment","detectOverflowOptions","__objRest","side","getSide","initialSideAxis","getSideAxis","isBasePlacement","rtl","fallbackPlacements","getOppositePlacement","getExpandedPlacements","hasFallbackAxisSideDirection","getOppositeAxisPlacements","placements","overflow","overflows","overflowsData","sides","getAlignmentSides","nextIndex","nextPlacement","d","resetPlacement","a","b","currentSideAxis","acc","originSides","convertValueToCoords","state","options","__async","_a","placement","platform","elements","rtl","side","getSide","alignment","getAlignment","isVertical","getSideAxis","mainAxisMulti","crossAxisMulti","rawValue","evaluate","mainAxis","crossAxis","alignmentAxis","offset","_b","x","y","middlewareData","diffCoords","__spreadProps","__spreadValues","shift","checkMainAxis","checkCrossAxis","limiter","detectOverflowOptions","__objRest","coords","overflow","getOppositeAxis","mainAxisCoord","crossAxisCoord","minSide","maxSide","min","max","clamp","limitedCoords","hasWindow","getNodeName","node","isNode","getWindow","_a","getDocumentElement","value","isElement","isHTMLElement","isShadowRoot","isOverflowElement","element","overflow","overflowX","overflowY","display","getComputedStyle","isTableElement","isTopLayer","_e","willChangeRe","containRe","isNotNone","isWebKitValue","isContainingBlock","elementOrCss","css","isWebKit","getContainingBlock","currentNode","getParentNode","isLastTraversableNode","getNodeScroll","result","getNearestOverflowAncestor","parentNode","getOverflowAncestors","list","traverseIframes","scrollableAncestor","isBody","win","frameElement","getFrameElement","getCssDimensions","width","height","hasOffset","offsetWidth","offsetHeight","shouldFallback","round","unwrapElement","getScale","domElement","createCoords","rect","$","x","y","noOffsets","getVisualOffsets","shouldAddVisualOffsets","isFixed","floatingOffsetParent","getBoundingClientRect","includeScale","isFixedStrategy","offsetParent","clientRect","scale","visualOffsets","offsetWin","currentWin","currentIFrame","iframeScale","iframeRect","left","top","rectToClientRect","getWindowScrollBarX","leftScroll","getHTMLOffset","documentElement","scroll","htmlRect","convertOffsetParentRelativeRectToViewportRelativeRect","elements","strategy","topLayer","offsets","isOffsetParentAnElement","offsetRect","htmlOffset","getClientRects","getDocumentRect","html","body","max","SCROLLBAR_MAX","getViewportRect","visualViewport","visualViewportBased","windowScrollbarX","doc","bodyStyles","bodyMarginInline","clippingStableScrollbarWidth","getInnerBoundingClientRect","getClientRectFromClippingAncestor","clippingAncestor","hasFixedPositionAncestor","stopNode","getClippingElementAncestors","cache","cachedResult","el","currentContainingBlockComputedStyle","elementIsFixed","computedStyle","currentNodeIsContaining","ancestor","getClippingRect","boundary","rootBoundary","clippingAncestors","firstRect","right","bottom","i","min","getDimensions","getRectRelativeToOffsetParent","setLeftRTLScrollbarOffset","isStaticPositioned","getTrueOffsetParent","polyfill","rawOffsetParent","getOffsetParent","svgOffsetParent","getElementRects","data","__async","getOffsetParentFn","getDimensionsFn","floatingDimensions","isRTL","platform","rectsAreEqual","a","b","observeMove","onMove","io","timeoutId","root","cleanup","refresh","skip","threshold","elementRectForRootMargin","insetTop","floor","insetRight","insetBottom","insetLeft","options","isFirstUpdate","handleObserve","entries","ratio","__spreadProps","__spreadValues","autoUpdate","reference","floating","update","ancestorScroll","ancestorResize","elementResize","layoutShift","animationFrame","referenceEl","ancestors","cleanupIo","reobserveFrame","resizeObserver","firstEntry","frameId","prevRefRect","frameLoop","nextRefRect","offset","shift","flip","computePosition","reference","floating","options","cache","mergedOptions","__spreadValues","platform","platformWithCache","__spreadProps","attachFloating","node","initialProps","_a","openState","placement","content","keepOpenOnContentHover","timer","cleanup","floating","floatingNode","mounted","reference","rootNode","floatingPartial","listener","event","hide","show","mountedNode","dataTheme","rNode","overlay","overlayEle","wireContent","target","w","ensureMounted","instantShow","Qt","nr","Je","Ze","Qe","x","y","resolved","instantHide","handleOutside","props","createFloating","kind","open","nt","behaviorKey","anchorPartial","__spreadValues","e","at","xSvg","tag","props","_a","removable","color","nt","node","removeBtn","e","ne","listener","ge","he","combobox","props","options","placement","color","open","multiple","state","nt","openState","show","hide","anchorPartial","createFloating","popoverPartial","_e","node","listener","ge","ne","ae","elevation","w","inputStyle","he","inputElement","inputPartial","wrap","val","vals","items","opt","tag","_node","cur","filter","v","partial","command","_node","element","w","nt","commandSearch","props","color","accentColor","node","ctx","input","onInput","listener","he","ne","ae","ge","commandItem","_a","_b","el","text","applyFilter","q","release","atMidnight","date","addDays","count","addMonths","sameDay","a","b","isoOf","startOfWeek","weekStart","localeWeekStart","locale","_a","_b","localeObject","info","e","datePicker","props","_c","_d","mode","time","min","max","disabledDate","format","onChange","accentColor","nt","placeState","selection","releaseOnChange","value","primaryDate","current","base","viewYear","viewMonth","focused","hovered","hour","minute","contentElement","dateFormatter","__spreadValues","monthFormatter","weekdayFormatter","fullDateFormatter","formatOne","formatDisplay","start","end","weekdayNames","_unused","index","isDisabled","withTime","result","selectDate","instantHideRef","reapplyTime","inSelectedRange","listener","tail","low","high","day","isSelectedEnd","goToDate","shiftMonth","delta","next","shiftYear","focusActiveCell","calendar","buildCalendar","show","hide","anchorPartial","createFloating","triggerPartial","_e","node","openAndFocus","event","key","isSelectedPrimary","w","navButton","label","ariaLabel","onClick","navButtonStyle","header","he","ne","weekdayHeader","name","ge","gridRowStyle","grid","buildWeeks","onGridKey","children","buildTimeRow","buildFooter","ae","elevation","first","month","weeks","week","cells","buildDayCell","disabled","selected","within","outside","isFocused","isToday","l","numberSelect","state","timeSelectStyle","action","today","keyboard","descriptionList","props","_a","color","nt","node","ne","listener","he","ge","details","props","_a","_b","duration","color","nt","accentColor","node","listener","he","ge","ne","ae","lockCount","lockScroll","unlockScroll","FOCUSABLE","dialog","props","color","open","state","nt","previousFocus","closing","scrollLocked","finalizeClose","dlg","unlockScroll","node","e","r","closeTimer","trapFocus","focusables","el","first","last","onCancel","update","val","lockScroll","focusable","release","listener","he","ge","ne","ae","elevation","divider","props","_a","color","nt","node","ne","listener","he","ge","translateOut","marginMap","isVertical","p","resolvePhysical","placement","isRTL","drawer","props","color","open","size","state","nt","isLogical","physicalFallback","defaultSize","ne","drawerSize","node","e","dlg","onCancel","physical","closing","scrollLocked","closeTimer","finishClose","unlockScroll","onTransitionEnd","update","val","lockScroll","release","listener","he","ge","ae","elevation","emphasis","props","_a","color","nt","node","listener","he","ge","empty","props","_a","color","nt","ne","listener","ge","errorBoundary","props","node","error","reset","_a","_b","fallbackEl","SIZE_MAP","fab","props","_a","_b","color","nt","dim","ne","node","listener","he","ge","elevation","focusRing","figure","props","_a","color","nt","node","ne","listener","ge","he","formGroup","props","_a","layout","color","nt","isVertical","node","listener","ne","ae","he","ge","HeadingShift","heading","props","_a","color","nt","node","listener","ge","ne","offset","he","horizontalRule","props","_a","color","nt","node","ne","listener","ge","icon","props","_a","color","nt","node","ne","listener","he","ge","image","props","_a","color","nt","node","ne","listener","ge","inputCheckbox","props","_a","_b","color","nt","accentColor","node","listener","he","ne","ge","inputColor","_props","node","element","listener","he","ne","ae","ge","inputDateTime","props","_a","_b","mode","color","nt","accentColor","node","element","listener","he","ge","ne","ae","focusRing","inputFile","props","_a","_b","color","nt","accentColor","node","element","listener","he","ge","ne","ae","focusRing","inputNumber","props","_a","_b","color","nt","accentColor","node","element","ne","listener","ae","he","ge","focusRing","EYE_SVG","EYE_OFF_SVG","inputPassword","props","_a","_b","colorState","nt","accentState","visibleState","node","field","l","toggle","ne","ae","ge","he","focusRing","inputOTP","ne","node","container","getInputs","onInput","e","inputs","target","idx","onKeydown","onPaste","_a","_b","_c","text","found","startIdx","char","i","lastFilled","inputRadio","props","_a","_b","color","nt","accentColor","node","listener","he","ne","ge","inputRange","props","_a","_b","color","nt","accentColor","node","ne","listener","ge","inputSearch","props","_a","_b","color","nt","accentColor","node","element","listener","he","ge","ne","ae","focusRing","inputSwitch","props","_a","accentColor","nt","node","listener","he","ne","ge","inputText","props","_a","_b","color","nt","accentColor","node","element","ne","listener","ae","he","ge","focusRing","keyboard","props","_a","color","nt","node","listener","he","ge","ne","label","props","_a","_b","color","nt","accentColor","node","ne","listener","he","ge","link","props","_a","_b","color","nt","accentColor","node","listener","he","ge","ne","linkButton","props","_a","color","nt","node","listener","he","ne","ae","ge","focusRing","list","_props","listItem","props","dense","listener","ne","ae","he","listItemButton","_a","_b","color","nt","accentColor","ge","mark","props","_a","accentColor","nt","node","listener","he","ge","ne","menu","props","_a","items","selectable","color","accentColor","activeKey","nt","node","element","id","buttons","item","index","key","__spreadProps","__spreadValues","l","e","k","keys","it","i","idx","next","ne","he","ae","ge","elevation","isState","value","toStyles","frame","out","transforms","key","motion","props","_a","_b","_c","_d","initial","animate","exit","transition","options","node","el","target","release","next","done","orderedList","props","_a","color","nt","node","listener","he","ge","ne","getPages","current","total","_","i","pages","start","end","pagination","props","_a","color","accentColor","state","nt","btnBase","listener","ne","ae","he","ge","focusRing","activeStyle","__spreadProps","__spreadValues","node","content","page","items","ellipsisIndex","p","isActive","panelSection","props","_a","padding","divider","color","nt","__spreadValues","listener","ne","ae","ge","paragraph","props","_a","color","nt","node","listener","he","ge","popover","props","_a","open","placement","openOn","popoverId","openState","nt","placeState","show","hide","anchorPartial","createFloating","popoverPartial","l","ge","ne","ae","elevation","node","id","w","listener","_e","e","related","root","floatingEl","popoverArrow","props","placement","color","sideOffset","ne","bordered","place","nt","flipMap","getFlipped","listener","_a","start","pos","end","he","ge","x","y","preformated","props","_a","color","nt","node","listener","he","ge","ne","ae","progress","props","_a","_b","color","nt","accentColor","node","ne","listener","ge","STAR_FILLED","STAR_EMPTY","rating","props","_a","_b","max","readOnly","onChange","color","valueState","nt","hoveredState","activeCount","listener","hovered","ne","ge","node","i","index","interactive","next","e","current","target","star","__spreadProps","__spreadValues","focusRing","ringProgress","props","_a","_b","_c","size","thickness","value","nt","color","trackColor","holePercent","mask","l","node","ne","ge","row","props","gap","align","justify","wrap","__spreadValues","listener","ne","ae","scrollArea","props","_a","color","nt","ne","l","ge","segmented","props","_a","_b","_c","items","color","accentColor","value","nt","node","element","buttons","item","index","key","l","he","ne","ge","focusRing","select","props","color","accentColor","node","listener","he","ge","ne","ae","l","svg","Te","focusRing","selectBox","props","options","placement","color","open","multiple","state","nt","openState","show","hide","anchorPartial","createFloating","popoverPartial","_e","node","listener","ge","ne","ae","elevation","w","wrap","val","vals","opt","tag","_node","cur","filter","v","partial","he","selectItem","props","accentColor","color","value","node","select","state","listener","val","v","he","ne","ae","ge","selectList","props","_a","color","multiple","state","nt","inputs","listener","val","v","node","ne","ae","he","ge","skeleton","props","_a","color","nt","keyframes","animationName","we","listener","he","ge","ne","small","props","_a","color","nt","node","listener","he","ge","keyframes","animationName","we","spinner","props","_a","color","nt","node","listener","he","ge","ne","splitter","props","direction","defaultSize","min","max","_node","element","w","nt","splitterPanel","node","ctx","el","prop","isFirst","apply","size","release","splitterHandle","handle","isHorizontal","releaseAriaValue","onKeydown","e","step","next","cancelDrag","onMousedown","container","onMousemove","rect","raw","onMouseup","listener","ge","ne","stack","props","gap","align","__spreadValues","listener","ne","ae","steps","props","_a","items","direction","color","accentColor","current","nt","node","element","stepEls","item","index","l","cur","ne","he","ge","strong","props","_a","color","nt","node","listener","he","ge","subscript","props","_a","color","nt","node","listener","he","ge","superscript","props","_a","color","nt","node","listener","he","ge","table","props","_a","color","nt","node","listener","he","ge","ne","ae","l","tabs","props","_a","_b","_c","items","accentColor","color","activeKey","nt","node","element","id","tablist","item","index","key","l","e","k","keys","it","i","idx","next","he","ne","ae","ge","focusRing","panels","textarea","props","_a","_b","color","nt","accentColor","autoResize","node","el","resize","listener","ne","ae","he","ge","focusRing","timeline","timelineItem","props","_a","_b","_c","last","color","accentColor","activeState","nt","__spreadValues","listener","ne","ae","ge","toast","props","position","color","state","nt","isTop","isCenter","isRight","overlayEle","ne","rootNode","overlay","listener","ae","he","ge","elevation","node","done","finished","timer","finish","onEnd","e","_a","toggleGroup","props","_a","items","multiple","color","accentColor","value","nt","node","element","buttons","item","index","key","l","val","arr","v","he","ne","ge","focusRing","toolbar","props","row","toolbarSpacer","tooltip","props","open","placement","content","placeState","nt","contentState","tooltipId","contentElement","listener","show","hide","anchorPartial","createFloating","tooltipPartial","ne","ae","ge","he","elevation","popoverArrow","w","_e","node","e","getItemId","node","index","transitionGroup","props","duration","delay","previousRects","cancelMap","pendingTimers","pendingFrames","cancel","timer","frame","item","g","dom","_a","key","prev","next","deltaX","deltaY","cancelled","finish","onEnd","event","unorderedList","props","_a","color","nt","node","listener","he","ge","ne"]}
|
|
1
|
+
{"version":3,"sources":["../src/global.ts","../../core/src/constants/BooleanAttributes.ts","../../core/src/constants/CamelAttributes.ts","../../core/src/constants/HtmlAttributeNames.ts","../../core/src/constants/HtmlTags.ts","../../core/src/constants/PrefixCSS.ts","../../core/src/constants/SvgTags.ts","../../core/src/constants/VoidTags.ts","../../core/src/config.ts","../../core/src/types/EventProperties.ts","../../core/src/classes/Collector.ts","../../core/src/classes/Notifier.ts","../../core/src/classes/State.ts","../../core/src/utils.ts","../../core/src/helpers.ts","../../core/src/classes/ElementAttribute.ts","../../core/src/classes/AttributeList.ts","../../core/src/dev.ts","../../core/src/classes/StyleProperty.ts","../../core/src/classes/StyleRule.ts","../../core/src/classes/StyleList.ts","../../core/src/classes/ElementNode.ts","../../core/src/classes/TextNode.ts","../../core/src/classes/ElementList.ts","../../core/src/classes/Reactive.ts","../../core/src/classes/RecordState.ts","../../theme/src/light.ts","../../theme/src/theme.ts","../../theme/src/density.ts","../../theme/src/generate.ts","../../theme/src/size.ts","../../theme/src/tone.ts","../../palette/src/utils.ts","../../palette/src/Swatch.ts","../../palette/src/Ramp.ts","../../palette/src/Palette.ts","../../palette/src/Generator.ts","../src/index.ts","../src/patches/abbreviation.ts","../src/patches/accordion.ts","../src/patches/alert.ts","../src/patches/avatar.ts","../src/patches/badge.ts","../src/patches/blockquote.ts","../src/patches/breadcrumb.ts","../src/patches/breadcrumbEllipsis.ts","../src/utils/buttonSize.ts","../src/utils/focusRing.ts","../src/patches/buttonGhost.ts","../src/patches/button.ts","../src/patches/buttonSwitch.ts","../src/patches/card.ts","../src/patches/code.ts","../src/utils/elevation.ts","../../floating/src/utils/index.ts","../../floating/src/core/computeCoordsFromPlacement.ts","../../floating/src/core/detectOverflow.ts","../../floating/src/core/computePosition.ts","../../floating/src/core/middleware/arrow.ts","../../floating/src/core/middleware/autoPlacement.ts","../../floating/src/core/middleware/flip.ts","../../floating/src/core/middleware/hide.ts","../../floating/src/core/middleware/inline.ts","../../floating/src/core/constants.ts","../../floating/src/core/middleware/offset.ts","../../floating/src/core/middleware/shift.ts","../../floating/src/core/middleware/size.ts","../../floating/src/utils/dom.ts","../../floating/src/dom/utils/getCssDimensions.ts","../../floating/src/dom/utils/unwrapElement.ts","../../floating/src/dom/platform/getScale.ts","../../floating/src/dom/utils/getVisualOffsets.ts","../../floating/src/dom/utils/getBoundingClientRect.ts","../../floating/src/dom/utils/getWindowScrollBarX.ts","../../floating/src/dom/utils/getHTMLOffset.ts","../../floating/src/dom/platform/convertOffsetParentRelativeRectToViewportRelativeRect.ts","../../floating/src/dom/platform/getClientRects.ts","../../floating/src/dom/utils/getDocumentRect.ts","../../floating/src/dom/utils/getViewportRect.ts","../../floating/src/dom/platform/getClippingRect.ts","../../floating/src/dom/platform/getDimensions.ts","../../floating/src/dom/utils/getRectRelativeToOffsetParent.ts","../../floating/src/dom/utils/isStaticPositioned.ts","../../floating/src/dom/platform/getOffsetParent.ts","../../floating/src/dom/platform/getElementRects.ts","../../floating/src/dom/platform/isRTL.ts","../../floating/src/dom/platform.ts","../../floating/src/dom/utils/rectsAreEqual.ts","../../floating/src/dom/autoUpdate.ts","../../floating/src/dom/createFloating.ts","../../floating/src/dom/middleware.ts","../../floating/src/dom/index.ts","../src/utils/floating.ts","../src/patches/tag.ts","../src/patches/combobox.ts","../src/patches/command.ts","../src/patches/datePicker.ts","../src/patches/descriptionList.ts","../src/patches/details.ts","../src/utils/scrollLock.ts","../src/patches/dialog.ts","../src/patches/divider.ts","../src/patches/drawer.ts","../src/patches/emphasis.ts","../src/patches/empty.ts","../src/patches/errorBoundary.ts","../src/patches/fab.ts","../src/patches/figure.ts","../src/patches/formGroup.ts","../src/patches/heading.ts","../src/patches/horizontalRule.ts","../src/patches/icon.ts","../src/patches/image.ts","../src/patches/inputCheckbox.ts","../src/patches/inputColor.ts","../src/patches/inputDateTime.ts","../src/patches/inputFile.ts","../src/patches/inputNumber.ts","../src/patches/inputPassword.ts","../src/patches/inputOTP.ts","../src/patches/inputRadio.ts","../src/patches/inputRange.ts","../src/patches/inputSearch.ts","../src/patches/inputSwitch.ts","../src/patches/inputText.ts","../src/patches/keyboard.ts","../src/patches/label.ts","../src/patches/link.ts","../src/patches/linkButton.ts","../src/patches/list.ts","../src/patches/mark.ts","../src/patches/menu.ts","../src/patches/motion.ts","../src/patches/orderedList.ts","../src/patches/pagination.ts","../src/patches/panelSection.ts","../src/patches/paragraph.ts","../src/patches/popover.ts","../src/patches/popoverArrow.ts","../src/patches/preformated.ts","../src/patches/progress.ts","../src/patches/rating.ts","../src/patches/ringProgress.ts","../src/patches/row.ts","../src/patches/scrollArea.ts","../src/patches/segmented.ts","../src/patches/select.ts","../src/patches/selectBox.ts","../src/patches/selectItem.ts","../src/patches/selectList.ts","../src/patches/skeleton.ts","../src/patches/small.ts","../src/patches/spinner.ts","../src/patches/splitter.ts","../src/patches/stack.ts","../src/patches/steps.ts","../src/patches/strong.ts","../src/patches/subscript.ts","../src/patches/superscript.ts","../src/patches/table.ts","../src/patches/tabs.ts","../src/patches/textarea.ts","../src/patches/timeline.ts","../src/patches/toast.ts","../src/patches/toggleGroup.ts","../src/patches/toolbar.ts","../src/patches/tooltip.ts","../src/patches/transitionGroup.ts","../src/patches/unorderedList.ts"],"sourcesContent":["export * as core from \"@domphy/core\";\nexport * as theme from \"@domphy/theme\";\nexport * as ui from \"./index.js\";\n","export const BooleanAttributes = [\n \"allowFullScreen\",\n \"async\",\n \"autoFocus\",\n \"autoPlay\",\n \"checked\",\n \"compact\",\n \"contentEditable\",\n \"controls\",\n \"declare\",\n \"default\",\n \"defer\",\n \"disabled\",\n \"formNoValidate\",\n \"hidden\",\n \"isMap\",\n \"itemScope\",\n \"loop\",\n \"multiple\",\n \"muted\",\n \"noHref\",\n \"noShade\",\n \"noValidate\",\n \"open\",\n \"playsInline\",\n \"readonly\",\n \"required\",\n \"reversed\",\n \"scoped\",\n \"selected\",\n \"sortable\",\n \"trueSpeed\",\n \"typeMustMatch\",\n \"wmode\",\n \"spellCheck\",\n \"inert\",\n \"download\",\n \"noModule\",\n \"paused\",\n \"autoPictureInPicture\",\n] as const;\n","export const CamelAttributes: string[] = [\n \"viewBox\",\n \"preserveAspectRatio\",\n \"gradientTransform\",\n \"gradientUnits\",\n \"spreadMethod\",\n \"markerStart\",\n \"markerMid\",\n \"markerEnd\",\n \"markerHeight\",\n \"markerWidth\",\n \"markerUnits\",\n \"refX\",\n \"refY\",\n \"patternContentUnits\",\n \"patternTransform\",\n \"patternUnits\",\n \"filterUnits\",\n \"primitiveUnits\",\n \"kernelUnitLength\",\n \"clipPathUnits\",\n \"maskContentUnits\",\n \"maskUnits\",\n \"baseFrequency\",\n \"numOctaves\",\n \"xChannelSelector\",\n \"yChannelSelector\",\n \"stdDeviation\",\n \"colorInterpolationFilters\",\n \"pathLength\",\n] as const;\n","// Multi-word HTML/global attribute names whose real DOM content-attribute\n// spelling is either a plain lowercase concatenation (no hyphen at all, e.g.\n// autoFocus -> autofocus, tabIndex -> tabindex) or an outright rename\n// (htmlFor -> for). The generic camelToKebab() helper only knows how to\n// insert a hyphen before every capital letter, so it cannot produce these —\n// it is only correct for the small set of HTML attributes whose real name IS\n// genuinely hyphenated (http-equiv, accept-charset) and for aria-*/data-*,\n// which follow that same hyphenated convention.\n//\n// ElementAttribute's constructor checks this map before falling back to\n// camelToKebab(), so any camelCase key NOT listed here (including custom\n// attributes such as web-component props, e.g. myWidgetProp) still gets the\n// previous kebab-case treatment unchanged.\nexport const HtmlAttributeNames: Record<string, string> = {\n // Rename, not just a case change.\n htmlFor: \"for\",\n\n // Boolean HTML attributes (BooleanAttributes.ts) with camelCase humps.\n allowFullScreen: \"allowfullscreen\",\n autoFocus: \"autofocus\",\n autoPlay: \"autoplay\",\n contentEditable: \"contenteditable\",\n formNoValidate: \"formnovalidate\",\n isMap: \"ismap\",\n itemScope: \"itemscope\",\n noHref: \"nohref\",\n noShade: \"noshade\",\n noValidate: \"novalidate\",\n playsInline: \"playsinline\",\n trueSpeed: \"truespeed\",\n typeMustMatch: \"typemustmatch\",\n spellCheck: \"spellcheck\",\n noModule: \"nomodule\",\n autoPictureInPicture: \"autopictureinpicture\",\n\n // Enumerated (yes/no, on/off) attributes.\n autoCapitalize: \"autocapitalize\",\n\n // Other global attributes.\n accessKey: \"accesskey\",\n enterKeyHint: \"enterkeyhint\",\n inputMode: \"inputmode\",\n itemId: \"itemid\",\n itemProp: \"itemprop\",\n itemRef: \"itemref\",\n itemType: \"itemtype\",\n tabIndex: \"tabindex\",\n writingSuggestions: \"writingsuggestions\",\n\n // Common non-boolean multi-word HTML attributes.\n charSet: \"charset\",\n hrefLang: \"hreflang\",\n crossOrigin: \"crossorigin\",\n aLink: \"alink\",\n bgColor: \"bgcolor\",\n vLink: \"vlink\",\n formAction: \"formaction\",\n formEncType: \"formenctype\",\n formMethod: \"formmethod\",\n formTarget: \"formtarget\",\n popoverTarget: \"popovertarget\",\n popoverTargetAction: \"popovertargetaction\",\n allowPaymentRequest: \"allowpaymentrequest\",\n allowUserMedia: \"allowusermedia\",\n frameBorder: \"frameborder\",\n longDesc: \"longdesc\",\n marginHeight: \"marginheight\",\n marginWidth: \"marginwidth\",\n referrerPolicy: \"referrerpolicy\",\n srcDoc: \"srcdoc\",\n hSpace: \"hspace\",\n fetchPriority: \"fetchpriority\",\n srcSet: \"srcset\",\n srcLang: \"srclang\",\n useMap: \"usemap\",\n vSpace: \"vspace\",\n dirName: \"dirname\",\n imageSizes: \"imagesizes\",\n imageSrcSet: \"imagesrcset\",\n classId: \"classid\",\n codeBase: \"codebase\",\n codeType: \"codetype\",\n valueType: \"valuetype\",\n shadowRootClonable: \"shadowrootclonable\",\n shadowRootDelegatesFocus: \"shadowrootdelegatesfocus\",\n shadowRootMode: \"shadowrootmode\",\n colSpan: \"colspan\",\n rowSpan: \"rowspan\",\n noWrap: \"nowrap\",\n vAlign: \"valign\",\n charOff: \"charoff\",\n maxLength: \"maxlength\",\n minLength: \"minlength\",\n autoComplete: \"autocomplete\",\n encType: \"enctype\",\n dateTime: \"datetime\",\n};\n","export const HtmlTags = [\n \"a\",\n \"abbr\",\n \"address\",\n \"article\",\n \"aside\",\n \"audio\",\n \"b\",\n \"base\",\n \"blockquote\",\n \"br\",\n \"button\",\n \"canvas\",\n \"caption\",\n \"cite\",\n \"code\",\n \"col\",\n \"colgroup\",\n \"data\",\n \"datalist\",\n \"dd\",\n \"del\",\n \"details\",\n \"dfn\",\n \"dialog\",\n \"div\",\n \"dl\",\n \"dt\",\n \"em\",\n \"fieldset\",\n \"figcaption\",\n \"figure\",\n \"footer\",\n \"form\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"header\",\n \"hgroup\",\n \"i\",\n \"iframe\",\n \"img\",\n \"input\",\n \"ins\",\n \"kbd\",\n \"label\",\n \"legend\",\n \"li\",\n \"main\",\n \"map\",\n \"mark\",\n \"meta\",\n \"meter\",\n \"nav\",\n \"noscript\",\n \"object\",\n \"ol\",\n \"optgroup\",\n \"option\",\n \"output\",\n \"p\",\n \"param\",\n \"picture\",\n \"pre\",\n \"progress\",\n \"q\",\n \"rp\",\n \"rt\",\n \"ruby\",\n \"s\",\n \"samp\",\n \"section\",\n \"select\",\n \"slot\",\n \"small\",\n \"source\",\n \"span\",\n \"strong\",\n \"sub\",\n \"summary\",\n \"sup\",\n \"table\",\n \"tbody\",\n \"td\",\n \"template\",\n \"textarea\",\n \"tfoot\",\n \"th\",\n \"thead\",\n \"time\",\n \"title\",\n \"tr\",\n \"track\",\n \"u\",\n \"ul\",\n \"var\",\n \"video\",\n \"wbr\",\n \"bdi\",\n \"bdo\",\n \"math\",\n \"menu\",\n \"search\",\n \"area\",\n \"embed\",\n \"hr\",\n \"animate\",\n \"animateMotion\",\n \"animateTransform\",\n \"circle\",\n \"clipPath\",\n \"cursor\",\n \"defs\",\n \"desc\",\n \"ellipse\",\n \"feBlend\",\n \"feColorMatrix\",\n \"feComponentTransfer\",\n \"feComposite\",\n \"feConvolveMatrix\",\n \"feDiffuseLighting\",\n \"feDisplacementMap\",\n \"feDistantLight\",\n \"feDropShadow\",\n \"feFlood\",\n \"feFuncA\",\n \"feFuncB\",\n \"feFuncG\",\n \"feFuncR\",\n \"feGaussianBlur\",\n \"feImage\",\n \"feMerge\",\n \"feMergeNode\",\n \"feMorphology\",\n \"feOffset\",\n \"fePointLight\",\n \"feSpecularLighting\",\n \"feSpotLight\",\n \"feTile\",\n \"feTurbulence\",\n \"filter\",\n \"foreignObject\",\n \"g\",\n \"image\",\n \"line\",\n \"linearGradient\",\n \"marker\",\n \"mask\",\n \"metadata\",\n \"mpath\",\n \"path\",\n \"pattern\",\n \"polygon\",\n \"polyline\",\n \"prefetch\",\n \"radialGradient\",\n \"rect\",\n \"set\",\n \"solidColor\",\n \"stop\",\n \"svg\",\n \"switch\",\n \"symbol\",\n \"tbreak\",\n \"text\",\n \"textPath\",\n \"tspan\",\n \"use\",\n \"view\",\n];\n","//browserslist query \"> 0.1%, not dead\"\nexport const PrefixCSS: Record<string, string[]> = {\n transform: [\"webkit\", \"ms\"],\n transition: [\"webkit\", \"ms\"],\n animation: [\"webkit\"],\n userSelect: [\"webkit\", \"ms\"],\n flexDirection: [\"webkit\", \"ms\"],\n flexWrap: [\"webkit\", \"ms\"],\n justifyContent: [\"webkit\", \"ms\"],\n alignItems: [\"webkit\", \"ms\"],\n alignSelf: [\"webkit\", \"ms\"],\n order: [\"webkit\", \"ms\"],\n flexGrow: [\"webkit\", \"ms\"],\n flexShrink: [\"webkit\", \"ms\"],\n flexBasis: [\"webkit\", \"ms\"],\n columns: [\"webkit\"],\n columnCount: [\"webkit\"],\n columnGap: [\"webkit\"],\n columnRule: [\"webkit\"],\n columnWidth: [\"webkit\"],\n boxSizing: [\"webkit\"],\n appearance: [\"webkit\", \"moz\"],\n filter: [\"webkit\"],\n backdropFilter: [\"webkit\"],\n clipPath: [\"webkit\"],\n mask: [\"webkit\"],\n maskImage: [\"webkit\"],\n textSizeAdjust: [\"webkit\", \"ms\"],\n hyphens: [\"webkit\", \"ms\"],\n writingMode: [\"webkit\", \"ms\"],\n gridTemplateColumns: [\"ms\"],\n gridTemplateRows: [\"ms\"],\n gridAutoColumns: [\"ms\"],\n gridAutoRows: [\"ms\"],\n gridColumn: [\"ms\"],\n gridRow: [\"ms\"],\n marginInlineStart: [\"webkit\"],\n marginInlineEnd: [\"webkit\"],\n paddingInlineStart: [\"webkit\"],\n paddingInlineEnd: [\"webkit\"],\n minInlineSize: [\"webkit\"],\n maxInlineSize: [\"webkit\"],\n minBlockSize: [\"webkit\"],\n maxBlockSize: [\"webkit\"],\n inlineSize: [\"webkit\"],\n blockSize: [\"webkit\"],\n tabSize: [\"moz\"],\n overscrollBehavior: [\"webkit\", \"ms\"],\n touchAction: [\"ms\"],\n resize: [\"webkit\"],\n printColorAdjust: [\"webkit\"],\n backgroundClip: [\"webkit\"],\n boxDecorationBreak: [\"webkit\"],\n overflowScrolling: [\"webkit\"],\n};\n","export const SvgTags = [\n \"svg\",\n \"circle\",\n \"path\",\n \"rect\",\n \"ellipse\",\n \"line\",\n \"polyline\",\n \"polygon\",\n \"g\",\n \"defs\",\n \"use\",\n \"symbol\",\n \"linearGradient\",\n \"radialGradient\",\n \"stop\",\n \"clipPath\",\n \"mask\",\n \"filter\",\n \"text\",\n \"tspan\",\n \"textPath\",\n \"image\",\n \"pattern\",\n \"marker\",\n \"animate\",\n \"animateTransform\",\n \"animateMotion\",\n \"feGaussianBlur\",\n \"feComposite\",\n \"feColorMatrix\",\n \"feMerge\",\n \"feMergeNode\",\n \"feOffset\",\n \"feFlood\",\n \"feBlend\",\n \"feTurbulence\",\n \"feDisplacementMap\",\n \"feComponentTransfer\",\n \"feFuncR\",\n \"feFuncG\",\n \"feFuncB\",\n \"feFuncA\",\n \"foreignObject\",\n];\n","export const VoidTags = [\n \"area\",\n \"base\",\n \"br\",\n \"col\",\n \"embed\",\n \"hr\",\n \"img\",\n \"input\",\n \"link\",\n \"meta\",\n \"source\",\n \"track\",\n \"wbr\",\n] as const;\n\nexport type VoidTagName = (typeof VoidTags)[number];\n","interface DomphyConfig {\n cspNonce?: string;\n}\n\nconst _config: DomphyConfig = {};\n\nexport function configure(options: Partial<DomphyConfig>): void {\n Object.assign(_config, options);\n}\n\nexport function getConfig(): Readonly<DomphyConfig> {\n return _config;\n}\n","export const EventProperties = [\n \"onAbort\",\n \"onAuxClick\",\n \"onBeforeMatch\",\n \"onBeforeToggle\",\n \"onBlur\",\n \"onCancel\",\n \"onCanPlay\",\n \"onCanPlayThrough\",\n \"onChange\",\n \"onClick\",\n \"onClose\",\n \"onContextLost\",\n \"onContextMenu\",\n \"onContextRestored\",\n \"onCopy\",\n \"onCueChange\",\n \"onCut\",\n \"onDblClick\",\n \"onDrag\",\n \"onDragEnd\",\n \"onDragEnter\",\n \"onDragLeave\",\n \"onDragOver\",\n \"onDragStart\",\n \"onDrop\",\n \"onDurationChange\",\n \"onEmptied\",\n \"onEnded\",\n \"onError\",\n \"onFocus\",\n \"onFormData\",\n \"onInput\",\n \"onInvalid\",\n \"onKeyDown\",\n \"onKeyPress\",\n \"onKeyUp\",\n \"onLoad\",\n \"onLoadedData\",\n \"onLoadedMetadata\",\n \"onLoadStart\",\n \"onMouseDown\",\n \"onMouseEnter\",\n \"onMouseLeave\",\n \"onMouseMove\",\n \"onMouseOut\",\n \"onMouseOver\",\n \"onMouseUp\",\n \"onPaste\",\n \"onPause\",\n \"onPlay\",\n \"onPlaying\",\n \"onProgress\",\n \"onRateChange\",\n \"onReset\",\n \"onResize\",\n \"onScroll\",\n \"onScrollEnd\",\n \"onSecurityPolicyViolation\",\n \"onSeeked\",\n \"onSeeking\",\n \"onSelect\",\n \"onSlotChange\",\n \"onStalled\",\n \"onSubmit\",\n \"onSuspend\",\n \"onTimeUpdate\",\n \"onToggle\",\n \"onVolumeChange\",\n \"onWaiting\",\n \"onWheel\",\n \"onTouchStart\",\n \"onTouchMove\",\n \"onTouchEnd\",\n \"onTouchCancel\",\n \"onPointerDown\",\n \"onPointerMove\",\n \"onPointerUp\",\n \"onPointerCancel\",\n \"onPointerEnter\",\n \"onPointerLeave\",\n \"onPointerOver\",\n \"onPointerOut\",\n \"onGotPointerCapture\",\n \"onLostPointerCapture\",\n \"onCompositionStart\",\n \"onCompositionUpdate\",\n \"onCompositionEnd\",\n \"onTransitionEnd\",\n \"onTransitionStart\",\n \"onAnimationStart\",\n \"onAnimationEnd\",\n \"onAnimationIteration\",\n \"onFullscreenChange\",\n \"onFullscreenError\",\n \"onFocusIn\",\n \"onFocusOut\",\n] as const;\n\nexport const eventNameMap = EventProperties.reduce(\n (acc, ev) => {\n const key = ev.slice(2).toLowerCase() as keyof HTMLElementEventMap;\n acc[key] = ev;\n return acc;\n },\n {} as Partial<\n Record<keyof HTMLElementEventMap, (typeof EventProperties)[number]>\n >,\n);\n","import type { Handler } from \"../types.js\";\n\n// A Collector is the bridge between auto-tracked reads (State.get / RecordState.get\n// called WITHOUT an explicit listener) and the existing Notifier subscription model.\n//\n// When a Collector is active and a reactive source is read, the source subscribes\n// the Collector's `handler` to its Notifier exactly as it would any other listener.\n// The Notifier hands back a `release` callback through `handler.onSubscribe`; the\n// Collector records every release it receives so the whole dependency set can be\n// torn down at once on the next re-run (effect/computed) or on dispose. This reuses\n// Notifier's subscribe/notify/flush and `_chain` cycle detection — there is no\n// parallel reactivity system.\nexport class Collector {\n // The function the Notifier actually stores as a listener. Invoked (via the\n // Notifier flush) whenever any tracked dependency changes.\n readonly handler: Handler;\n // Release callbacks for the dependencies subscribed during the current run.\n private _releases: Set<() => void> = new Set();\n\n constructor(onDependencyChange: () => void) {\n const handler = (() => onDependencyChange()) as Handler;\n // Notifier.addListener calls onSubscribe(release) right after adding the\n // listener. Record the release so we can drop this exact subscription later.\n handler.onSubscribe = (release: () => void) => {\n this._releases.add(release);\n };\n this.handler = handler;\n }\n\n // Release every dependency subscribed since the last reset. Called before a\n // re-run (so stale deps are dropped and only freshly read deps remain) and on\n // dispose (so nothing is left subscribed).\n reset(): void {\n for (const release of this._releases) release();\n this._releases.clear();\n }\n\n get dependencyCount(): number {\n return this._releases.size;\n }\n}\n\n// Stack of active collectors. A stack (not a single slot) so nested reactive\n// computations compose: a `computed` read inside an `effect` pushes its own\n// collector while running, then pops, restoring the effect as the active one.\nconst COLLECTOR_STACK: Collector[] = [];\n\n// Depth of active `untrack` regions. While > 0, reads do NOT register into the\n// active collector even though one is on the stack.\nlet UNTRACK_DEPTH = 0;\n\n// The collector that auto-tracked reads should subscribe to right now, or null\n// when tracking is suppressed (inside untrack) or no computation is running.\nexport function activeCollector(): Collector | null {\n if (UNTRACK_DEPTH > 0) return null;\n return COLLECTOR_STACK.length\n ? COLLECTOR_STACK[COLLECTOR_STACK.length - 1]\n : null;\n}\n\n// Run `fn` with `collector` active, guaranteeing the stack is restored even if\n// `fn` throws.\nexport function runWithCollector<T>(collector: Collector, fn: () => T): T {\n COLLECTOR_STACK.push(collector);\n try {\n return fn();\n } finally {\n COLLECTOR_STACK.pop();\n }\n}\n\n// Run `fn` with tracking suppressed; reads inside register nowhere.\nexport function runUntracked<T>(fn: () => T): T {\n UNTRACK_DEPTH++;\n try {\n return fn();\n } finally {\n UNTRACK_DEPTH--;\n }\n}\n","import type { Handler } from \"../types.js\";\n\ntype ChainEntry = [notifier: Notifier, event: string];\n\n// Shared across all instances to track the flush chain for circular detection.\nlet _chain: ChainEntry[] = [];\n\n// Microtask scheduler. Older embedded Chromium runtimes (SketchUp 2020 /\n// 2021.0 ship CEF 64) predate `queueMicrotask` (added in Chrome 71). A\n// resolved Promise's `.then` runs as a microtask in the same checkpoint, so\n// it is the standard fallback. The `.catch` mimics `queueMicrotask`'s\n// behaviour of surfacing thrown errors to the global error handler rather\n// than silently becoming an unhandled-rejection.\nexport const _microtask: (cb: () => void) => void =\n typeof queueMicrotask === \"function\"\n ? queueMicrotask\n : (cb) => {\n Promise.resolve()\n .then(cb)\n .catch((e) => {\n setTimeout(() => {\n throw e;\n }, 0);\n });\n };\n\n// Cap on self-re-notifications within one settle burst. A converging update\n// (clamp/normalize) reaches a fixpoint in a pass or two; anything beyond this is\n// a genuinely diverging self-feedback loop and is stopped like a cycle.\nconst SELF_NOTIFY_CAP = 100;\n\n// Batching: while `_batchDepth > 0`, every `notify` records its pending entry as\n// usual but does NOT schedule a flush. Notifiers that received writes during the\n// batch are collected in `_batchedNotifiers`; when the outermost batch ends they\n// are scheduled together, so the whole batch coalesces into a SINGLE microtask\n// flush instead of one per write. This composes with the existing per-event\n// `_pending` coalescing (repeated writes to the same event still collapse to one\n// entry) without ever double-flushing.\nlet _batchDepth = 0;\nlet _batchedNotifiers: Set<Notifier> = new Set();\n\n// Every Notifier with a flush scheduled but not yet run. flushSync() drains this\n// to apply pending state-change notifications synchronously (see\n// flushPendingNotifiers); normal operation still flushes via the microtask.\nconst _scheduledNotifiers: Set<Notifier> = new Set();\n\n// Run `fn`, deferring all flushes triggered inside it into one flush afterwards.\n// Nested batches collapse into the outermost one. Reentrant-safe: the stack is\n// restored and the batched set is flushed even if `fn` throws.\nexport function runBatched<T>(fn: () => T): T {\n _batchDepth++;\n try {\n return fn();\n } finally {\n _batchDepth--;\n if (_batchDepth === 0) {\n const notifiers = _batchedNotifiers;\n _batchedNotifiers = new Set();\n for (const notifier of notifiers) notifier._scheduleFlush();\n }\n }\n}\n\nexport class Notifier {\n // `Object.create(null)` avoids inheriting Object.prototype (`constructor`,\n // `toString`, `hasOwnProperty`, `__proto__`, ...): a plain `{}` would resolve\n // `this._listeners[event]` to an inherited value for those event names,\n // which is truthy but not a Set, crashing `.has`/`.add` on first subscribe.\n private _listeners: Record<string, Set<Handler>> | null = Object.create(\n null,\n );\n private _pending: Map<string, { args: unknown[]; chain: ChainEntry[] }> =\n new Map();\n private _scheduled = false;\n // Args currently being delivered per event (used to detect a self-update fixpoint).\n private _flushing: Map<string, unknown[]> = new Map();\n // Self-re-notification depth in the current settle burst (runaway guard).\n private _selfDepth = 0;\n\n _dispose(): void {\n if (this._listeners) {\n for (const event in this._listeners) {\n this._listeners[event].clear();\n }\n }\n this._listeners = null;\n }\n\n addListener(event: string, listener: Handler): () => void {\n if (!this._listeners) return () => {};\n\n if (typeof event !== \"string\" || typeof listener !== \"function\") {\n throw new Error(\n \"Event name must be a string, listener must be a function\",\n );\n }\n\n if (!this._listeners[event]) {\n this._listeners[event] = new Set();\n }\n\n const release = () => this.removeListener(event, listener);\n\n if (this._listeners[event].has(listener)) return release;\n\n this._listeners[event].add(listener);\n if (typeof listener.onSubscribe === \"function\") {\n listener.onSubscribe(release);\n }\n\n return release;\n }\n\n removeListener(event: string, listener: Handler): void {\n if (!this._listeners) return;\n\n const listeners = this._listeners[event];\n if (listeners && listeners.has(listener)) {\n listeners.delete(listener);\n if (listeners.size === 0) {\n delete this._listeners[event];\n }\n }\n }\n\n // Number of listeners subscribed to an event. Used by `computed` to stay lazy:\n // an unobserved computed only marks itself dirty on a dependency change and\n // defers recomputation until the next read.\n listenerCount(event: string): number {\n return this._listeners?.[event]?.size ?? 0;\n }\n\n notify(event: string, ...args: unknown[]): void {\n if (!this._listeners) return;\n if (!this._listeners[event]) return;\n\n // A listener that re-sets its OWN state mid-flush shows up as [this,event] at\n // the TOP of the chain. That is a converging self-update (clamp/normalize),\n // not a cross-state cycle — let it re-propagate with a fresh chain. A deeper\n // match (intervening notifiers) is a real cycle and is still rejected.\n const top = _chain.length ? _chain[_chain.length - 1] : null;\n const selfReentry = !!top && top[0] === this && top[1] === event;\n\n if (selfReentry) {\n const inflight = this._flushing.get(event);\n // Same value as the one being delivered → fixpoint reached, stop quietly.\n if (inflight && inflight[0] === args[0]) return;\n if (this._selfDepth >= SELF_NOTIFY_CAP) {\n console.error(\n `[Domphy] Runaway self-update on \"${event}\" — stopped after ${SELF_NOTIFY_CAP} iterations`,\n );\n return;\n }\n this._selfDepth++;\n this._pending.set(event, { args, chain: [] });\n } else {\n if (this._isCircular(event)) return;\n this._pending.set(event, { args, chain: [..._chain] });\n }\n\n // While batching, defer scheduling: just remember this notifier has pending\n // work so the outermost batch can flush it once. Outside a batch, schedule\n // the microtask flush immediately as before.\n if (_batchDepth > 0) {\n _batchedNotifiers.add(this);\n } else {\n this._scheduleFlush();\n }\n }\n\n // Schedule the microtask flush if one is not already pending. Idempotent, so a\n // batch flushing many notifiers (and concurrent direct notifies) never queues\n // two flushes for the same instance.\n _scheduleFlush(): void {\n if (this._scheduled) return;\n this._scheduled = true;\n _scheduledNotifiers.add(this);\n _microtask(() => this._flushAll());\n }\n\n private _isCircular(event: string): boolean {\n const idx = _chain.findIndex(([n, e]) => n === this && e === event);\n if (idx === -1) return false;\n\n const names = [..._chain.slice(idx).map(([, e]) => e), event];\n console.error(\n `[Domphy] Circular dependency detected:\\n ${names.join(\" → \")}`,\n );\n return true;\n }\n\n _flushAll(): void {\n this._scheduled = false;\n _scheduledNotifiers.delete(this);\n const pending = this._pending;\n this._pending = new Map();\n\n for (const [event, { args, chain }] of pending) {\n _chain = chain;\n this._flush(event, args);\n }\n _chain = [];\n // Burst settled (no self-update re-queued anything) → reset the runaway guard.\n if (this._pending.size === 0) this._selfDepth = 0;\n }\n\n private _flush(event: string, args: unknown[]): void {\n if (!this._listeners) return;\n const listeners = this._listeners[event];\n if (!listeners) return;\n\n _chain.push([this, event]);\n this._flushing.set(event, args);\n\n for (const listener of [...listeners]) {\n if (!listeners.has(listener)) continue;\n try {\n listener(...args);\n } catch (e) {\n console.error(e);\n }\n }\n\n this._flushing.delete(event);\n _chain.pop();\n }\n}\n\n// True when any Notifier has a flush scheduled but not yet run. flushSync() uses\n// this to decide whether more synchronous draining is needed.\nexport function hasPendingNotifiers(): boolean {\n return _scheduledNotifiers.size > 0;\n}\n\n// Synchronously run every scheduled Notifier flush, including notifiers\n// scheduled while draining (a listener that writes another state re-schedules\n// its own Notifier). Driven by flushSync() alongside the reaction queue.\nexport function flushPendingNotifiers(): void {\n let guard = 0;\n while (_scheduledNotifiers.size > 0) {\n if (guard++ > 10000) {\n console.error(\"[Domphy] flushSync: notifier queue did not settle\");\n break;\n }\n const notifiers = [..._scheduledNotifiers];\n _scheduledNotifiers.clear();\n for (const notifier of notifiers) notifier._flushAll();\n }\n}\n","import type { Handler } from \"../types.js\";\nimport { activeCollector } from \"./Collector.js\";\nimport { Notifier } from \"./Notifier.js\";\n\nexport type ValueListener<T> = ((_value: T) => void) & Handler;\nexport type ReadableState<T> = {\n readonly _isState: true;\n get(listener?: ValueListener<T>): T;\n};\nexport type ValueOrState<T> = T | State<T> | ReadableState<T>;\n\nexport class State<T> {\n readonly _isState = true;\n private _value: T;\n readonly initialValue: T;\n private _notifier: Notifier | null = new Notifier();\n\n constructor(\n initialValue: T,\n readonly name: string = typeof initialValue,\n ) {\n this.initialValue = initialValue;\n this._value = initialValue;\n }\n\n get(listener?: ValueListener<T>): T {\n if (listener) {\n this.addListener(listener);\n } else {\n // Auto-tracking: with no explicit listener, subscribe the active collector\n // (a running computed/effect) so it re-runs when this state changes. When\n // no collector is active the read is a plain, untracked value read — the\n // original behavior is preserved exactly.\n const collector = activeCollector();\n if (collector) this.addListener(collector.handler as ValueListener<T>);\n }\n return this._value;\n }\n\n set(newValue: T): void {\n if (!this._notifier) return;\n this._value = newValue;\n this._notifier.notify(this.name, newValue);\n }\n\n reset(): void {\n this.set(this.initialValue);\n }\n\n addListener(listener: ValueListener<T>): () => void {\n if (!this._notifier) return () => {};\n return this._notifier.addListener(this.name, listener);\n }\n\n removeListener(listener: ValueListener<T>): void {\n if (!this._notifier) return;\n this._notifier.removeListener(this.name, listener);\n }\n\n _dispose(): void {\n if (this._notifier) {\n this._notifier._dispose();\n this._notifier = null;\n }\n }\n}\n","import { type ReadableState, State, type ValueListener } from \"./classes/State.js\";\nimport { addEvent, addHook, deepClone } from \"./helpers.js\";\nimport type {\n BehaviorAttach,\n DomphyElement,\n EventName,\n Handler,\n HookMap,\n PartialElement,\n} from \"./types.js\";\n\nexport function merge(\n source: Record<string, any> = {},\n target: Record<string, any> = {},\n): Record<string, any> {\n const comma = [\n \"animation\",\n \"transition\",\n \"boxShadow\",\n \"textShadow\",\n \"background\",\n \"fontFamily\",\n ];\n const space = [\"class\", \"rel\", \"transform\", \"acceptCharset\", \"sandbox\"];\n const adjacent = [\"content\"];\n if (\n Object.prototype.toString.call(target) === \"[object Object]\" &&\n Object.getPrototypeOf(target) === Object.prototype\n ) {\n // plainjs not class instance\n target = deepClone(target);\n }\n\n for (const key in target) {\n const value = target[key];\n if (value === undefined || value === null || value === \"\") continue;\n\n if (typeof value === \"object\" && !Array.isArray(value)) {\n if (typeof source[key] === \"object\") {\n source[key] = merge(source[key], value);\n } else {\n source[key] = value;\n }\n } else {\n if (comma.includes(key)) {\n if (typeof source[key] === \"function\" || typeof value === \"function\") {\n const old = source[key];\n source[key] = (listener: Handler) => {\n const val1 = typeof old === \"function\" ? old(listener) : old;\n const val2 = typeof value === \"function\" ? value(listener) : value;\n return [val1, val2].filter((e) => e).join(\", \");\n };\n } else {\n source[key] = [source[key], value].filter((e) => e).join(\", \");\n }\n } else if (adjacent.includes(key)) {\n if (typeof source[key] === \"function\" || typeof value === \"function\") {\n const old = source[key];\n source[key] = (listener: Handler) => {\n const val1 = typeof old === \"function\" ? old(listener) : old;\n const val2 = typeof value === \"function\" ? value(listener) : value;\n return [val1, val2].filter((e) => e).join(\"\");\n };\n } else {\n source[key] = [source[key], value].filter((e) => e).join(\"\");\n }\n } else if (space.includes(key)) {\n if (typeof source[key] === \"function\" || typeof value === \"function\") {\n const old = source[key];\n source[key] = (listener: Handler) => {\n const val1 = typeof old === \"function\" ? old(listener) : old;\n const val2 = typeof value === \"function\" ? value(listener) : value;\n return [val1, val2].filter((e) => e).join(\" \");\n };\n } else {\n source[key] = [source[key], value].filter((e) => e).join(\" \");\n }\n } else if (key.startsWith(\"on\")) {\n const name = key.replace(\"on\", \"\").toLowerCase() as EventName;\n addEvent(source as DomphyElement, name, value);\n } else if (key.startsWith(\"_on\")) {\n const name = key.replace(\"_on\", \"\") as keyof HookMap;\n addHook(source as DomphyElement, name, value);\n } else {\n source[key] = value;\n }\n }\n }\n return source;\n}\n\nexport function hashString(str: string = \"\"): string {\n let hash = 0x811c9dc5; // FNV-1a 32-bit offset basis\n for (let i = 0; i < str.length; i++) {\n hash ^= str.charCodeAt(i);\n hash = (hash * 0x01000193) >>> 0; // FNV prime, keep 32-bit unsigned\n }\n return String.fromCharCode(97 + (hash % 26)) + hash.toString(16);\n}\n\n// Normalizes `val` into a State-like object exposing `.get()`.\n//\n// WARNING: if `val` is already a State or any ReadableState (including the\n// output of `readonly()`/`computed()`), it is returned UNCHANGED — even\n// though the return type says `State<T>`. A ReadableState that isn't\n// actually a `State` instance has no `.set()` method at runtime; calling\n// `.set()` on the value returned by `toState()` is only safe when you know\n// `val` was not already a read-only source. This is by design — a\n// read-only source must stay read-only — so `toState` never fabricates a\n// `.set()`. Callers that need to write must either accept a plain value (so\n// `toState` allocates a fresh, writable `State`) or check `isState`/inspect\n// the source before calling `.set()`.\nexport function toState<T>(\n val: T | State<T> | ReadableState<T>,\n name?: string,\n): State<T> {\n return val instanceof State || (val as any)?._isState\n ? (val as State<T>)\n : new State<T>(val as T, name);\n}\n\n// Returns true when `value` is a State or any ReadableState (including\n// Computed<T>). Use this as a type guard when writing utilities that accept\n// either a raw value or a reactive source.\n//\n// function bindOrUse<T>(src: T | ReadableState<T>) {\n// if (isState(src)) return src.get()\n// return src\n// }\nexport function isState<T = unknown>(value: unknown): value is ReadableState<T> {\n return (\n typeof value === \"object\" &&\n value !== null &&\n (value as any)._isState === true\n );\n}\n\n// Wraps a State or ReadableState in a read-only view. The returned object exposes\n// only `.get()` — callers cannot call `.set()`. Useful for exposing internal\n// state from a module or factory without granting write access.\n//\n// const _count = toState(0)\n// export const count = readonly(_count) // consumers can read, not write\n// export const increment = () => _count.set(_count.get() + 1)\nexport function readonly<T>(source: ReadableState<T>): ReadableState<T> {\n return {\n _isState: true as const,\n get(listener?: ValueListener<T>): T {\n return source.get(listener);\n },\n };\n}\n\n// Declares a per-node behavior (Svelte-action-like) inside a patch factory.\n// `attach` runs once for the real DOM node the returned partial lands on, no\n// matter how many times the factory itself is re-invoked by a reactive\n// parent; every later call routes its `props` into the SAME instance via\n// `update()` instead of creating a new, disconnected one. Compose with other\n// patch fields normally (spread, `merge()`, or via `$`):\n//\n// function draggable(props: { onMove(dx: number, dy: number): void }) {\n// return behavior(\"draggable\", (node, props) => {\n// const onPointerMove = (e: PointerEvent) => props.onMove(e.movementX, e.movementY)\n// node.domElement!.addEventListener(\"pointermove\", onPointerMove)\n// return {\n// update: (next) => { props = next },\n// destroy: () => node.domElement!.removeEventListener(\"pointermove\", onPointerMove),\n// }\n// }, props)\n// }\n//\n// `key` must be unique per concern on one element (not per patch instance) —\n// two DIFFERENT patches sharing an element (e.g. a tooltip AND a popover on\n// the same button) should use distinct keys so their instances stay\n// independent; re-declaring the SAME key from a later generation is exactly\n// the \"route props into the existing instance\" case this exists for.\nexport function behavior<P>(\n key: string,\n attach: BehaviorAttach<P>,\n props: P,\n): PartialElement {\n return { _behaviors: { [key]: { attach, props } } };\n}\n","import type { ElementNode } from \"./classes/ElementNode.js\";\nimport { getConfig } from \"./config.js\";\nimport { HtmlTags } from \"./constants/HtmlTags.js\";\nimport { eventNameMap } from \"./types/EventProperties.js\";\nimport type {\n DomphyElement,\n HookMap,\n PartialElement,\n TagName,\n} from \"./types.js\";\nimport { merge } from \"./utils.js\";\n\nexport function addHook<K extends keyof HookMap>(\n partial: PartialElement,\n hookName: K,\n handler: HookMap[K],\n): void {\n const hookProperty = `_on${hookName}` as keyof PartialElement;\n const current = partial[hookProperty];\n\n if (typeof current === \"function\") {\n (partial as any)[hookProperty] = (...args: any[]) => {\n (current as Function)(...args);\n (handler as Function)(...args);\n };\n } else {\n (partial as any)[hookProperty] = handler;\n }\n}\n\nexport function addEvent<K extends keyof HTMLElementEventMap>(\n attributes: PartialElement,\n eventName: K,\n handler: (event: HTMLElementEventMap[K], node: ElementNode) => void,\n): void {\n const eventProperty = eventNameMap[eventName];\n if (!eventProperty) {\n throw Error(`invalid event name \"${eventName}\"`);\n }\n const current = (attributes as any)[eventProperty];\n\n if (typeof current === \"function\") {\n (attributes as any)[eventProperty] = (\n event: HTMLElementEventMap[K],\n node: ElementNode,\n ) => {\n current(event, node);\n handler(event, node);\n };\n } else {\n (attributes as any)[eventProperty] = handler;\n }\n}\n\nexport function deepClone(value: any, seen = new WeakMap()): any {\n if (value === null || typeof value !== \"object\") return value;\n if (typeof value === \"function\") return value;\n if (seen.has(value)) return seen.get(value);\n\n let clone: any;\n\n if (Array.isArray(value)) {\n clone = [];\n seen.set(value, clone);\n for (const v of value) clone.push(deepClone(v, seen));\n return clone;\n }\n\n // These built-in types must be checked BEFORE the class-instance bailout\n // below, otherwise their prototype (not Object.prototype) makes the\n // bailout return them by reference and these branches become dead code.\n if (value instanceof Date) return new Date(value);\n if (value instanceof RegExp) return new RegExp(value);\n if (value instanceof Map) {\n clone = new Map();\n seen.set(value, clone);\n for (const [k, v] of value)\n clone.set(deepClone(k, seen), deepClone(v, seen));\n return clone;\n }\n if (value instanceof Set) {\n clone = new Set();\n seen.set(value, clone);\n for (const v of value) clone.add(deepClone(v, seen));\n return clone;\n }\n if (ArrayBuffer.isView(value)) {\n return new (value as any).constructor(value);\n }\n if (value instanceof ArrayBuffer) {\n return value.slice(0);\n }\n\n const proto = Object.getPrototypeOf(value);\n if (proto !== Object.prototype) return value; // ignore class instance (State, ElementNode, ...)\n\n clone = Object.create(proto);\n seen.set(value, clone);\n\n for (const key of Reflect.ownKeys(value)) {\n clone[key] = deepClone(value[key], seen);\n }\n\n return clone;\n}\n\nexport function validate(\n element: DomphyElement | PartialElement,\n asPartial = false,\n): boolean {\n if (Object.prototype.toString.call(element) !== \"[object Object]\") {\n throw Error(`typeof ${element} is invalid DomphyElement`);\n }\n const keys = Object.keys(element);\n if (keys.length === 0 && !asPartial) {\n throw Error(\"element object has no tag key\");\n }\n for (let i = 0; i < keys.length; i++) {\n const key = keys[i];\n const val = element[key as keyof typeof element];\n if (i === 0 && !HtmlTags.includes(key) && !asPartial) {\n throw Error(`key ${key} is not valid HTML tag name`);\n } else if (\n key === \"style\" &&\n val &&\n Object.prototype.toString.call(val) !== \"[object Object]\"\n ) {\n throw Error(`\"style\" must be a object`);\n } else if (key === \"$\") {\n element.$!.forEach((v) => validate(v as PartialElement, true));\n } else if (key.startsWith(\"_on\") && typeof val !== \"function\") {\n throw Error(`hook ${key} value \"${val}\" must be a function `);\n } else if (key.startsWith(\"on\") && typeof val !== \"function\") {\n throw Error(`event ${key} value \"${val}\" must be a function `);\n } else if (key === \"_portal\" && typeof val !== \"function\") {\n throw Error(`\"_portal\" must be a function return HTMLElement`);\n } else if (\n key === \"_context\" &&\n Object.prototype.toString.call(val) !== \"[object Object]\"\n ) {\n throw Error(`\"_context\" must be a object`);\n } else if (\n key === \"_metadata\" &&\n Object.prototype.toString.call(val) !== \"[object Object]\"\n ) {\n throw Error(`\"_metadata\" must be a object`);\n } else if (\n key === \"_key\" &&\n typeof val !== \"string\" &&\n typeof val !== \"number\"\n ) {\n throw Error(`\"_key\" must be a string or number`);\n }\n }\n return true;\n}\n\nexport function isHTML(str: string): boolean {\n // `s` (dotAll) flag: `.` must also match newlines, otherwise a paired-tag\n // string with content spanning multiple lines (e.g. \"<div>\\nfoo\\n</div>\")\n // fails to match and falls through to the plain-text/escaped path.\n return /<([a-z][\\w-]*)(\\s[^>]*)?>.*<\\/\\1>|<([a-z][\\w-]*)(\\s[^>]*)?\\/>/is.test(\n str.trim(),\n );\n}\n\n// Strip <script> elements, event-handler attributes, and javascript: URLs\n// from an HTML string. Works in both SSR (no DOM) and client contexts. Not a\n// full sanitizer — it removes the most common XSS vectors so user-generated\n// strings passed as inline HTML content can't execute arbitrary code.\nexport function sanitizeHTMLString(html: string): string {\n // Remove <script>...</script> elements entirely (paired form), including\n // multi-line bodies. Case-insensitive: the tag name is case-insensitive.\n let result = html.replace(/<script\\b[^>]*>[\\s\\S]*?<\\/script\\s*>/gi, \"\");\n // Self-closing form (e.g. <script src=\"evil.js\"/>) — not valid HTML5 but\n // strip it defensively before the unclosed catch-all below, otherwise the\n // catch-all would swallow everything after it too.\n result = result.replace(/<script\\b[^>]*\\/>/gi, \"\");\n // Unclosed form (opening tag with no matching </script>) — strip from the\n // tag to the end of the string since the real extent is unknowable.\n result = result.replace(/<script\\b[^>]*>[\\s\\S]*$/gi, \"\");\n // Remove on* event handler attributes (onclick, onerror, onload, …).\n // Case-insensitive: HTML attribute names are case-insensitive, so\n // ONERROR=/OnClick= must be stripped too, not just lowercase.\n result = result.replace(\n /\\s+on[a-zA-Z][\\w-]*\\s*=\\s*(?:\"[^\"]*\"|'[^']*'|[^\\s>]*)/gi,\n \"\",\n );\n // Also strip on* when preceded by \"/\" (e.g. <svg/onload=…>)\n result = result.replace(\n /\\/on[a-zA-Z][\\w-]*\\s*=\\s*(?:\"[^\"]*\"|'[^']*'|[^\\s>]*)/gi,\n \"/\",\n );\n // Neutralise javascript: scheme in URL attributes\n result = result.replace(\n /((?:href|src|action|formaction)\\s*=\\s*)([\"']?)[\\s]*javascript:[^\"'\\s>]*/gi,\n \"$1$2#\",\n );\n return result;\n}\n\nexport function escapeHTML(str: string): string {\n return str\n .replace(/&/g, \"&\")\n .replace(/</g, \"<\")\n .replace(/>/g, \">\")\n .replace(/\"/g, \""\")\n .replace(/'/g, \"'\");\n}\n\nexport function addClass(element: PartialElement, className: string): void {\n if (typeof element.class === \"function\") {\n const reactive = element.class;\n element.class = (listener) => `${String(reactive(listener))} ${className}`;\n } else {\n const current = element.class || \"\";\n const split = String(current).split(\" \");\n split.push(className);\n element.class = split.filter((e) => e).join(\" \");\n }\n}\n\nexport function removeClass(element: PartialElement, className: string): void {\n if (typeof element.class === \"function\") {\n const reactive = element.class;\n element.class = (listener) => {\n const split = String(reactive(listener)).split(\" \");\n return split.filter((e) => e !== className).join(\" \");\n };\n } else {\n // Normalize BEFORE stringifying, otherwise a missing `class` stringifies\n // to the literal \"undefined\" and pollutes the resulting class list.\n element.class ||= \"\";\n const split = String(element.class).split(\" \");\n element.class = split.filter((e) => e !== className).join(\" \");\n }\n}\n\nexport function toggleClass(element: PartialElement, className: string): void {\n if (typeof element.class === \"function\") {\n const reactive = element.class;\n element.class = (listener) => {\n const split = String(reactive(listener)).split(\" \");\n return split.includes(className)\n ? split.filter((e) => e !== className).join(\" \")\n : split.concat([className]).join(\" \");\n };\n } else {\n // Normalize BEFORE stringifying, otherwise a missing `class` stringifies\n // to the literal \"undefined\" and pollutes the resulting class list.\n element.class ||= \"\";\n const split = String(element.class).split(\" \");\n element.class = split.includes(className)\n ? split.filter((e) => e !== className).join(\" \")\n : split.concat([className]).join(\" \");\n }\n}\n\nexport function getTagName(element: DomphyElement): TagName | undefined {\n return Object.keys(element).find((e) => HtmlTags.includes(e)) as\n | TagName\n | undefined;\n}\n\nexport function camelToKebab(str: string): string {\n return str.replace(/([a-z0-9])([A-Z])/g, \"$1-$2\").toLowerCase();\n}\n\nexport function selectorSplitter(selectors: string) {\n if (selectors.indexOf(\"@\") === 0) {\n return [selectors];\n }\n var splitted = [];\n var parens = 0;\n var angulars = 0;\n var soFar = \"\";\n for (var i = 0, len = selectors.length; i < len; i++) {\n var char = selectors[i];\n if (char === \"(\") {\n parens += 1;\n } else if (char === \")\") {\n parens -= 1;\n } else if (char === \"[\") {\n angulars += 1;\n } else if (char === \"]\") {\n angulars -= 1;\n } else if (char === \",\") {\n if (!parens && !angulars) {\n splitted.push(soFar.trim());\n soFar = \"\";\n continue;\n }\n }\n soFar += char;\n }\n splitted.push(soFar.trim());\n return splitted;\n}\n\nexport function normalizeSelectorKey(selectorText: string): string {\n const text = selectorText.trim();\n // At-rule headers (@media, @keyframes, @supports...) are matched\n // whitespace-insensitive because CSSOM reformats them unpredictably.\n if (text.startsWith(\"@\")) return text.replace(/\\s+/g, \"\");\n return text\n .replace(/\\s*([>+~,])\\s*/g, \"$1\") // tighten combinators and selector lists\n .replace(/\\s+/g, \" \") // collapse descendant-combinator whitespace\n .replace(/\\(\\s*odd\\s*\\)/g, \"(2n+1)\") // CSSOM serializes :nth-child(odd) as (2n+1)\n .replace(/\\(\\s*even\\s*\\)/g, \"(2n)\")\n .trim();\n}\n\nexport function collectCSSRules(\n rules: CSSRuleList,\n map: Map<string, CSSRule>,\n): Map<string, CSSRule> {\n for (let i = 0; i < rules.length; i++) {\n const rule = rules[i] as any;\n let key: string | null = null;\n if (typeof rule.selectorText === \"string\") {\n key = normalizeSelectorKey(rule.selectorText);\n } else if (\n typeof rule.cssText === \"string\" &&\n rule.cssText.startsWith(\"@\")\n ) {\n key = normalizeSelectorKey(rule.cssText.split(\"{\")[0]);\n }\n if (key && !map.has(key)) map.set(key, rule as CSSRule);\n }\n return map;\n}\n\nexport function ensureDomStyle(\n styleParent: HTMLHeadElement | ShadowRoot,\n nonce?: string,\n): HTMLStyleElement {\n let domStyle = styleParent.querySelector(\n \"#domphy-style\",\n ) as HTMLStyleElement | null;\n\n if (!domStyle) {\n domStyle = document.createElement(\"style\");\n domStyle.id = \"domphy-style\";\n const resolvedNonce = nonce ?? getConfig().cspNonce;\n if (resolvedNonce) domStyle.nonce = resolvedNonce;\n styleParent.appendChild(domStyle);\n }\n\n if (domStyle.dataset.domphyBase !== \"true\") {\n domStyle.sheet?.insertRule(\"[hidden] { display: none !important; }\", 0);\n domStyle.dataset.domphyBase = \"true\";\n }\n\n return domStyle;\n}\n\nexport const mergePartial = (\n partial: PartialElement | DomphyElement,\n): typeof partial => {\n if (Array.isArray(partial.$)) {\n const part: typeof partial = {};\n partial.$.forEach((p) => merge(part, mergePartial(p)));\n delete partial.$;\n merge(part, partial); // native win\n\n return part;\n } else {\n return partial;\n }\n};\n","import {\n BooleanAttributes,\n CamelAttributes,\n HtmlAttributeNames,\n} from \"../constants.js\";\nimport { camelToKebab, escapeHTML } from \"../helpers.js\";\nimport type { AttributeValue } from \"../types.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\nimport { Notifier } from \"./Notifier.js\";\n\n// Enumerated (not boolean) HTML attributes whose missing-value default is the\n// truthy state — unlike BooleanAttributes, omitting them does NOT mean \"off\",\n// so a `true`/`false` input must map to the real keyword instead of being\n// dropped from the DOM.\nconst EnumeratedBooleanAttributes: Record<string, readonly [string, string]> =\n {\n translate: [\"yes\", \"no\"],\n autoCapitalize: [\"on\", \"off\"],\n };\n\nexport class ElementAttribute {\n readonly name: string;\n readonly isBoolean: boolean;\n private readonly enumeratedBoolean?: readonly [string, string];\n value: any;\n // The value exactly as declared by the caller, kept verbatim (a reactive\n // function stays a function here) — unlike `value`, which always holds the\n // current RESOLVED primitive. AttributeList.addClass() reads this to detect\n // whether the existing \"class\" binding is reactive and, if so, to compose\n // with the original function instead of freezing at its last-resolved\n // string.\n declaredValue: AttributeValue = undefined;\n parent: ElementNode;\n _notifier = new Notifier();\n // Release handles for the reactive listener's state subscriptions, so a\n // re-set (e.g. patch() replacing a reactive value) can drop the old listener\n // instead of leaking it on the long-lived State until node removal.\n private _releases: (() => void)[] = [];\n // Whether the BeforeRemove hook that drains _releases has been registered.\n // It must register at most ONCE per attribute: patch() re-sets every\n // reactive attribute on every reuse, and ElementNode.addHook COMPOSES hooks,\n // so an unguarded registration would grow the node's BeforeRemove chain by\n // one closure per subscription per patch for the node's whole life.\n private _removeHooked = false;\n\n constructor(name: string, value: any, parent: any) {\n this.parent = parent;\n this.isBoolean = (BooleanAttributes as readonly string[]).includes(name);\n this.enumeratedBoolean = EnumeratedBooleanAttributes[name];\n if (CamelAttributes.includes(name)) {\n this.name = name;\n } else if (Object.hasOwn(HtmlAttributeNames, name)) {\n this.name = HtmlAttributeNames[name];\n } else {\n this.name = camelToKebab(name);\n }\n this.value = undefined;\n this.set(value);\n }\n\n private normalize(value: any): any {\n if (this.enumeratedBoolean && typeof value === \"boolean\") {\n return value ? this.enumeratedBoolean[0] : this.enumeratedBoolean[1];\n }\n return value;\n }\n\n render(): void {\n if (!this.parent || !this.parent.domElement) return;\n const domElement = this.parent.domElement;\n\n const mutateAttrs = [\"value\"];\n if (this.isBoolean) {\n if (this.value === false || this.value == null) {\n domElement.removeAttribute(this.name);\n } else {\n domElement.setAttribute(\n this.name,\n this.value === true ? \"\" : this.value,\n );\n }\n } else if (this.value == null) {\n domElement.removeAttribute(this.name);\n } else if (mutateAttrs.includes(this.name)) {\n (domElement as any)[this.name] = this.value;\n } else {\n domElement.setAttribute(this.name, this.value);\n }\n }\n\n set(value: AttributeValue): void {\n const prev = this.value;\n this.declaredValue = value;\n\n // Drop any previous reactive subscription before (re)binding.\n if (this._releases.length) {\n for (const release of this._releases) release();\n this._releases = [];\n }\n\n if (value == null) {\n this.value = null;\n } else if (typeof value === \"function\") {\n let listener: any = () => {\n if (!this.parent || this.parent._disposed) return;\n const p = this.value;\n // Re-pass `listener` so states read only on a later run (conditional\n // dependencies) get subscribed too — matching children/style paths.\n this.value = this.isBoolean\n ? Boolean((value as Function)(listener))\n : this.normalize((value as Function)(listener));\n this.render();\n if (p !== this.value) this._notifier.notify(this.name, this.value);\n };\n\n listener.elementNode = this.parent!;\n listener.debug = `class:${this.parent?.tagName}_${this.parent?.nodeId} attribute:${this.name}`;\n\n listener.onSubscribe = (release: () => void) => {\n this._releases.push(release);\n // One hook per attribute (see _removeHooked) — it drains whatever the\n // CURRENT release list holds at removal time, so a single registration\n // covers every later re-set/subscription.\n if (this.parent && !this._removeHooked) {\n this._removeHooked = true;\n this.parent.addHook(\"BeforeRemove\", () => {\n for (const releaseSubscription of this._releases) {\n releaseSubscription();\n }\n this._releases = [];\n listener = null;\n });\n }\n };\n\n this.value = this.isBoolean\n ? Boolean(value(listener))\n : this.normalize(value(listener));\n } else {\n this.value = this.isBoolean ? Boolean(value) : this.normalize(value);\n }\n\n this.render();\n if (prev !== this.value) this._notifier.notify(this.name, this.value);\n }\n\n addListener(callback: (value: any) => void): void {\n const handler = callback as any;\n handler.onSubscribe = (release: () => void) =>\n this.parent?.addHook(\"BeforeRemove\", release);\n this._notifier.addListener(this.name, handler);\n }\n\n remove(): void {\n if (this.parent && this.parent.attributes) {\n this.parent.attributes.remove(this.name);\n }\n this._dispose();\n }\n\n _dispose(): void {\n // Release state subscriptions immediately — an attribute removed\n // individually (AttributeList.remove) must not stay subscribed until the\n // whole node's eventual removal.\n for (const releaseSubscription of this._releases) releaseSubscription();\n this._releases = [];\n this._notifier._dispose();\n this.value = null;\n this.parent = null as any;\n }\n\n generateHTML(): string {\n const { name, value } = this;\n if (this.isBoolean) {\n return value ? `${name}` : \"\";\n }\n // Match render()'s live-DOM behavior (removeAttribute on null/undefined):\n // an attribute whose reactive value resolves to null/undefined is OMITTED,\n // not stringified as the literal text \"null\"/\"undefined\" — that literal\n // text is a real value to a screen reader (e.g. any non-token\n // aria-current is read as \"true\"), so it must never be emitted.\n if (value == null) return \"\";\n const val = Array.isArray(value) ? JSON.stringify(value) : value;\n return `${name}=\"${escapeHTML(String(val))}\"`;\n }\n}\n","import { BooleanAttributes } from \"../constants.js\";\nimport type { AttributeValue, Listener } from \"../types.js\";\nimport { ElementAttribute } from \"./ElementAttribute.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\n\nexport class AttributeList {\n items: Record<string, ElementAttribute> | null = {};\n parent: ElementNode | null;\n\n constructor(parent: ElementNode) {\n this.parent = parent;\n }\n\n generateHTML(): string {\n if (!this.items) return \"\";\n const str = Object.values(this.items)\n .map((attr) => attr.generateHTML())\n .filter(Boolean) // an omitted (null/undefined-valued) attribute emits \"\"\n .join(\" \");\n return str ? ` ${str}` : \"\";\n }\n\n get(name: string): any {\n if (!this.items) return undefined;\n return this.items[name]?.value;\n }\n\n set(name: string, value: AttributeValue): void {\n if (!this.items || !this.parent) return;\n if (this.items[name]) {\n this.items[name].set(value);\n } else {\n this.items[name] = new ElementAttribute(name, value, this.parent);\n }\n }\n\n addListener(name: string, callback: (value: string | number) => void): void {\n if (this.has(name)) {\n this.items![name].addListener(callback);\n }\n }\n\n has(name: string): boolean {\n if (!this.items) return false;\n return Object.hasOwn(this.items, name);\n }\n\n remove(name: string): void {\n if (!this.items) return;\n\n // Resolve the canonical DOM-facing name (e.g. \"ariaCurrent\" -> \"aria-current\")\n // BEFORE disposing the ElementAttribute — removeAttribute() must use the\n // same name render()/setAttribute() used, or the real DOM attribute is\n // left stuck forever for any name camelToKebab()/HtmlAttributeNames changed.\n const domName = this.items[name]?.name ?? name;\n\n if (this.items[name]) {\n this.items[name]._dispose();\n delete this.items[name];\n }\n\n if (\n this.parent &&\n this.parent.domElement &&\n this.parent.domElement instanceof Element\n ) {\n this.parent.domElement.removeAttribute(domName);\n }\n }\n\n _dispose(): void {\n if (this.items) {\n for (const key in this.items) {\n this.items[key]._dispose();\n }\n }\n this.items = null;\n this.parent = null;\n }\n\n toggle(name: string, force?: boolean): void {\n if (\n !BooleanAttributes.includes(name as (typeof BooleanAttributes)[number])\n ) {\n throw Error(`${name} is not a boolean attribute`);\n }\n if (force === true) {\n this.set(name, true);\n } else if (force === false) {\n this.remove(name);\n } else {\n this.has(name) ? this.remove(name) : this.set(name, true);\n }\n }\n\n addClass(className: string | ((listener: Listener) => string)): void {\n if (!className) return;\n if (typeof className !== \"string\" && typeof className !== \"function\") return;\n\n const add = (classes: string, newClass: string) => {\n const list = (classes || \"\").split(\" \").filter((e: string) => e);\n !list.includes(newClass) && list.push(newClass);\n return list.join(\" \");\n };\n\n // Read the declared value (not the resolved `.value`) to detect whether\n // the existing \"class\" binding is reactive — ElementAttribute.set()\n // always invokes a function value immediately and stores only the\n // resolved string as `.value`, so `.get(\"class\")` can never itself be a\n // function; `declaredValue` preserves the original reactive function.\n const declared = this.items?.[\"class\"]?.declaredValue;\n const currentIsFn = typeof declared === \"function\";\n const current = currentIsFn ? declared : this.get(\"class\");\n const nextIsFn = typeof className === \"function\";\n\n // Neither side is reactive — merge as a plain string, same as before.\n if (!currentIsFn && !nextIsFn) {\n this.set(\"class\", add(current, className as string));\n return;\n }\n\n // Either side is reactive: the merged class must itself be a function so\n // it re-resolves on every listener tick, threading the SAME listener\n // through both sides so each one's own state dependencies (if any) are\n // tracked. Calling a reactive side with no listener (the previous bug\n // here) both breaks its dependency tracking and, at the ElementNode.merge\n // call site, silently drops the auto-generated per-node style class —\n // the element's own `style: {}` object then never reaches the DOM.\n this.set(\"class\", (listener: Listener) =>\n add(\n currentIsFn ? (current as (l: Listener) => string)(listener) : current,\n nextIsFn\n ? (className as (l: Listener) => string)(listener)\n : (className as string),\n ),\n );\n }\n\n hasClass(className: string): boolean {\n if (!className || typeof className !== \"string\") return false;\n const current = this.get(\"class\") || \"\";\n const list = current.split(\" \").filter((e: string) => e);\n return list.includes(className);\n }\n\n toggleClass(className: string): void {\n if (!className || typeof className !== \"string\") return;\n this.hasClass(className)\n ? this.removeClass(className)\n : this.addClass(className);\n }\n\n removeClass(className: string): void {\n if (!className || typeof className !== \"string\") return;\n const current = this.get(\"class\") || \"\";\n const list: string[] = current.split(\" \").filter((e: string) => e);\n const updated = list.filter((cls) => cls !== className);\n updated.length > 0\n ? this.set(\"class\", updated.join(\" \"))\n : this.remove(\"class\");\n }\n\n replaceClass(oldClass: string, newClass: string): void {\n if (\n !oldClass ||\n !newClass ||\n typeof oldClass !== \"string\" ||\n typeof newClass !== \"string\"\n )\n return;\n if (this.hasClass(oldClass)) {\n this.removeClass(oldClass);\n this.addClass(newClass);\n }\n }\n}\n","declare const process: { env: Record<string, string | undefined> } | undefined;\n\n// Dev-only warning guard. A consumer bundler (Vite / webpack / esbuild)\n// statically replaces `process.env.NODE_ENV`, so production builds fold this to\n// `false` and tree-shake the guarded warnings out entirely. The `typeof process`\n// check keeps the IIFE/CDN build (and embedded runtimes such as SketchUp's CEF,\n// which have no `process`) from throwing at load time — there it stays `false`,\n// so warnings simply never fire. In a bundler's dev mode (or a test runner where\n// NODE_ENV is \"test\"/unset) it is `true`, surfacing the warnings during\n// development without any runtime cost in production.\nexport const __DEV__: boolean =\n typeof process !== \"undefined\" &&\n process.env != null &&\n process.env.NODE_ENV !== \"production\";\n","import { PrefixCSS } from \"../constants.js\";\nimport { camelToKebab } from \"../helpers.js\";\nimport type { Listener, StyleValue } from \"../types.js\";\nimport type { StyleRule } from \"./StyleRule.js\";\n\nexport class StyleProperty {\n name: string;\n cssName: string;\n value: StyleValue = \"\";\n parentRule: StyleRule;\n // Release handles for the reactive listener's state subscriptions, so a\n // re-set (e.g. StyleList.patchCSS() replacing a reactive value on a reused\n // node) can drop the old listener(s) instead of leaking them on the\n // long-lived State(s) until node removal. A single reactive style function\n // can subscribe to MULTIPLE states in one evaluation (e.g.\n // `transform: (l) => \\`translate(${x.get(l)}px, ${y.get(l)}px)\\``), so\n // onSubscribe can fire more than once per set() call -- every release must\n // be kept, not just the last one. Mirrors ElementAttribute's `_releases`\n // array pattern.\n private _releases: (() => void)[] = [];\n\n constructor(name: string, value: StyleValue, parentRule: StyleRule) {\n this.name = name;\n // CSS custom properties (`--fooBar`) are case-sensitive and never\n // kebab-cased by the platform itself — running one through\n // camelToKebab() would mangle it (e.g. \"--siteHeaderHeight\" ->\n // \"--site-header-height\"), silently breaking every `var(--siteHeaderHeight)`\n // reference elsewhere in the same style tree.\n this.cssName = name.startsWith(\"--\") ? name : camelToKebab(name);\n this.parentRule = parentRule;\n this.set(value);\n }\n\n _domUpdate(): void {\n if (!this.parentRule) return;\n const domRule = this.parentRule.domRule;\n\n if (domRule && (domRule as CSSStyleRule).style) {\n const style: CSSStyleDeclaration = (domRule as CSSStyleRule).style;\n style.setProperty(this.cssName, String(this.value));\n\n if (PrefixCSS[this.name]) {\n PrefixCSS[this.name].forEach((prefix) => {\n style.setProperty(`-${prefix}-${this.cssName}`, String(this.value));\n });\n }\n }\n }\n _dispose(): void {\n if (this._releases.length) {\n for (const release of this._releases) release();\n this._releases = [];\n }\n this.value = \"\";\n this.parentRule = null as any;\n }\n\n set(value: StyleValue): void {\n // Drop any previous reactive subscription(s) before (re)binding.\n if (this._releases.length) {\n for (const release of this._releases) release();\n this._releases = [];\n }\n\n if (typeof value === \"function\") {\n let listener = (() => {\n if (!this.parentRule || this.parentRule.parentNode?._disposed) return;\n this.value = value(listener);\n this._domUpdate();\n }) as unknown as Listener;\n\n listener.onSubscribe = (release: () => void) => {\n this._releases.push(release);\n };\n\n listener.elementNode = this.parentRule!.root!;\n listener.debug = `class:${this.parentRule?.root?.tagName}_${this.parentRule?.root?.nodeId} style:${this.name}`;\n this.value = value(listener);\n } else {\n this.value = value;\n }\n\n this._domUpdate();\n }\n\n remove(): void {\n if (!this.parentRule) return;\n\n if (this.parentRule.domRule instanceof CSSStyleRule) {\n const domStyle = this.parentRule.domRule.style;\n domStyle.removeProperty(this.cssName);\n\n if (PrefixCSS[this.name]) {\n PrefixCSS[this.name].forEach((prefix) => {\n domStyle.removeProperty(`-${prefix}-${this.cssName}`);\n });\n }\n }\n delete this.parentRule.styleBlock![this.name];\n this._dispose();\n }\n\n cssText(): string {\n let str = `${this.cssName}: ${this.value}`;\n if (PrefixCSS[this.name]) {\n PrefixCSS[this.name].forEach((prefix) => {\n str += `; -${prefix}-${this.cssName}: ${this.value}`;\n });\n }\n return str;\n }\n}\n","import type { ElementNode } from \"./ElementNode.js\";\nimport { StyleList } from \"./StyleList.js\";\nimport { StyleProperty } from \"./StyleProperty.js\";\n\nexport class StyleRule {\n selectorText: string;\n domRule: CSSRule | CSSMediaRule | CSSKeyframesRule | null = null;\n styleList: StyleList | null;\n styleBlock: Record<string, StyleProperty> | null = {};\n parent: StyleRule | ElementNode | null;\n\n constructor(selectorText: string, parent: StyleRule | ElementNode) {\n this.selectorText = selectorText;\n this.styleList = new StyleList(this);\n this.parent = parent;\n }\n\n _dispose(): void {\n if (this.styleBlock) {\n for (const prop of Object.values(this.styleBlock)) {\n prop._dispose();\n }\n }\n\n if (this.styleList) {\n this.styleList._dispose();\n }\n\n this.styleBlock = null;\n this.styleList = null;\n this.domRule = null;\n this.parent = null;\n }\n\n get root() {\n let node = this.parent;\n while (node instanceof StyleRule) {\n node = node.parent;\n }\n return node;\n }\n\n get parentNode(): ElementNode | null {\n let root: any = this.parent;\n while (root && root instanceof StyleRule) {\n root = root.parent;\n }\n return root as ElementNode;\n }\n\n insertStyle(name: string, val: any): void {\n if (!this.styleBlock) return;\n if (this.styleBlock[name]) {\n this.styleBlock[name].set(val);\n } else {\n this.styleBlock[name] = new StyleProperty(name, val, this);\n }\n }\n\n removeStyle(name: string): void {\n if (!this.styleBlock) return;\n if (this.styleBlock[name]) {\n this.styleBlock[name].remove();\n }\n }\n\n cssText(): string {\n if (!this.styleBlock || !this.styleList) return \"\";\n const styleStr = Object.values(this.styleBlock)\n .map((decl) => decl.cssText())\n .join(\";\");\n const nested = this.styleList.cssText();\n return `${this.selectorText} { ${styleStr} ${nested} } `;\n }\n\n mount(domRule: CSSRule | CSSKeyframesRule): void {\n if (!domRule || !this.styleList) return;\n this.domRule = domRule;\n if (\"cssRules\" in domRule) {\n this.styleList.mount(domRule.cssRules as CSSRuleList);\n }\n }\n\n remove(): void {\n if (this.domRule && this.domRule.parentStyleSheet) {\n const sheet = this.domRule.parentStyleSheet;\n const rules = sheet.cssRules;\n for (let i = 0; i < rules.length; i++) {\n if (rules[i] === this.domRule) {\n sheet.deleteRule(i);\n break;\n }\n }\n }\n this._dispose();\n }\n\n render(domSheet: CSSStyleSheet | CSSGroupingRule) {\n if (!this.styleBlock || !this.styleList) return;\n const styleStr = Object.values(this.styleBlock)\n .map((decl) => decl.cssText())\n .join(\";\");\n try {\n if (!this.selectorText.startsWith(\"@\")) {\n const css = `${this.selectorText} { ${styleStr} }`;\n const index = domSheet.insertRule(css, domSheet.cssRules.length);\n const domRule = domSheet.cssRules[index];\n if (domRule && \"selectorText\" in domRule) {\n this.mount(domRule);\n }\n } else if (\n /^@(media|supports|container|layer)\\b/.test(this.selectorText)\n ) {\n const index = domSheet.insertRule(\n `${this.selectorText} {}`,\n domSheet.cssRules.length,\n );\n const domRule = domSheet.cssRules[index];\n if (\"cssRules\" in domRule) {\n this.mount(domRule as CSSGroupingRule);\n this.styleList.render(domRule as CSSGroupingRule);\n }\n } else if (\n this.selectorText.startsWith(\"@keyframes\") ||\n this.selectorText.startsWith(\"@font-face\")\n ) {\n const css = this.cssText();\n const index = domSheet.insertRule(css, domSheet.cssRules.length);\n const domRule = domSheet.cssRules[index];\n this.mount(domRule);\n }\n } catch (err) {\n console.warn(\"Failed to insert rule:\", this.selectorText, err);\n }\n }\n}\n","import { normalizeSelectorKey, selectorSplitter } from \"../helpers.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\nimport { StyleRule } from \"./StyleRule.js\";\n\nexport class StyleList {\n parent: StyleRule | ElementNode | null;\n items: StyleRule[] = [];\n domStyle: HTMLStyleElement | null = null;\n\n constructor(parent: StyleRule | ElementNode) {\n this.parent = parent;\n }\n\n get parentNode(): ElementNode | null {\n let root: any = this.parent;\n while (root && root instanceof StyleRule) {\n root = root.parent;\n }\n return root as ElementNode;\n }\n\n addCSS(obj: Record<string, any>, parentSelector: string = \"\"): void {\n if (!this.items || !this.parent) return;\n const basic: Record<string, any> = {};\n // Conditional at-rules (@media/@container/@supports/@layer) must be inserted\n // AFTER the base property block so that same-specificity rules in the at-rule\n // override the base when the condition matches (later rules win in the cascade).\n const conditionalRules: StyleRule[] = [];\n\n function getSelector(selector: string, prev: string): string {\n return selector.startsWith(\"&\")\n ? `${prev}${selector.slice(1)}`\n : `${prev} ${selector}`;\n }\n\n for (const selector in obj) {\n const value = obj[selector];\n const splitKeys = selectorSplitter(selector);\n for (const key of splitKeys) {\n const currentSelector = getSelector(key, parentSelector);\n if (/^@(container|layer|supports|media)\\b/.test(key)) {\n if (typeof value === \"object\" && value != null) {\n const rule = new StyleRule(key, this.parent);\n rule.styleList!.addCSS(value, parentSelector);\n conditionalRules.push(rule);\n }\n } else if (key.startsWith(\"@keyframes\")) {\n const rule = new StyleRule(key, this.parent);\n rule.styleList!.addCSS(value, \"\");\n this.items.push(rule);\n } else if (key.startsWith(\"@font-face\")) {\n const rule = new StyleRule(key, this.parent);\n for (const k in value) rule.insertStyle(k, value[k]);\n this.items.push(rule);\n } else if (typeof value === \"object\" && value != null) {\n const rule = new StyleRule(currentSelector, this.parent);\n this.items.push(rule);\n for (const [k, v] of Object.entries(value)) {\n if (typeof v === \"object\" && v != null) {\n // A further-nested selector block (whether it starts with '&'\n // or is a plain descendant selector like \".icon\") must be\n // flattened as a sibling rule at THIS level, not re-processed\n // as a rule nested inside `rule` -- `rule.styleList` is never\n // rendered for a plain (non-@) selector (see StyleRule.render()),\n // so inserting there silently drops the rule from the live\n // stylesheet on client render, and re-running addCSS against the\n // same already-fully-resolved `newSelector` duplicated the\n // selector text inside itself. `getSelector` already joins `k`\n // onto `currentSelector` correctly for both cases (concat for\n // '&', descendant-space otherwise), so both cases resolve the\n // same way: recurse on `this` with the fully-resolved selector.\n const newSelector = getSelector(k, currentSelector);\n this.addCSS(v, newSelector);\n } else {\n rule.insertStyle(k, v);\n }\n }\n } else {\n basic[key] = value;\n }\n }\n }\n\n if (Object.keys(basic).length) {\n const rule = new StyleRule(parentSelector, this.parent);\n for (const key in basic) rule.insertStyle(key, basic[key]);\n this.items.push(rule);\n }\n\n for (const rule of conditionalRules) {\n this.items.push(rule);\n }\n }\n\n cssText(): string {\n if (!this.items) return \"\";\n return this.items.map((rule) => rule.cssText()).join(\"\");\n }\n\n // Reconcile this node's own FLAT (non-selector, non-at-rule) style properties\n // in place: update/add properties present in `obj`, remove properties that\n // were present before and are gone now. Used by ElementNode.patch() when list\n // reconciliation reuses a live node, so a freshly-computed static style object\n // (e.g. from a factory function like `FilterButton(...)` called again with new\n // args) actually reaches the DOM instead of being silently dropped — `addCSS`\n // itself is append-only and would duplicate CSSOM rules if called again.\n //\n // Nested selector blocks (&:hover, @media/@supports/@container/@layer,\n // @keyframes, @font-face) are NOT reconciled here — they are set once at\n // construction and assumed stable across reuse. A value that must change\n // after construction under a nested selector needs its own reactive function\n // (`color: (l) => …`), same as it already did before this method existed.\n patchCSS(obj: Record<string, any>, parentSelector: string = \"\"): void {\n if (!this.items || !this.parent) return;\n\n const basic: Record<string, any> = {};\n for (const key in obj) {\n const value = obj[key];\n if (typeof value === \"object\" && value != null) continue; // nested/@rule block\n basic[key] = value;\n }\n\n let rule = this.items.find((r) => r.selectorText === parentSelector);\n if (!rule) {\n rule = new StyleRule(parentSelector, this.parent);\n this.items.push(rule);\n }\n\n const seen = new Set(Object.keys(basic));\n for (const key in basic) rule.insertStyle(key, basic[key]);\n\n if (rule.styleBlock) {\n for (const existingKey of Object.keys(rule.styleBlock)) {\n if (!seen.has(existingKey)) rule.removeStyle(existingKey);\n }\n }\n\n // A brand-new rule has no live CSSOM binding yet — insert it now if this\n // node is already mounted (addCSS's construction-time path relies on a\n // single later styles.render() call that already ran for a reused node).\n const sheet = this.domStyle?.sheet;\n if (!rule.domRule && sheet) rule.render(sheet);\n }\n\n insertRule(selector: string): StyleRule {\n if (!this.items || !this.parent) return null as any;\n let rule = this.items.find((rule) => rule.selectorText === selector);\n if (!rule) {\n rule = new StyleRule(selector, this.parent);\n this.items.push(rule);\n }\n return rule;\n }\n\n hydrate(domRuleMap: Map<string, CSSRule>): void {\n if (!this.items) return;\n for (const rule of this.items) {\n const domRule = domRuleMap.get(normalizeSelectorKey(rule.selectorText));\n if (domRule) rule.mount(domRule as CSSRule);\n }\n }\n\n mount(domRuleList: CSSRuleList): void {\n if (!this.items) return;\n if (!domRuleList) throw Error(\"Require domRuleList argument\");\n let wrongCount = 0;\n const fixOddEven = (css: string) =>\n css.replace(\"(odd)\", \"(2n+1)\").replace(\"(even)\", \"(2n)\");\n\n this.items.forEach((rule, i) => {\n const index = i - wrongCount;\n const domRule = domRuleList[index];\n if (!domRule) return;\n if (\n rule.selectorText.startsWith(\"@\") &&\n domRule instanceof CSSKeyframesRule\n ) {\n rule.mount(domRule);\n } else if (\"keyText\" in domRule) {\n rule.mount(domRule);\n } else if (\"selectorText\" in domRule) {\n if (domRule.selectorText !== fixOddEven(rule.selectorText)) {\n wrongCount += 1;\n } else {\n rule.mount(domRule);\n }\n } else if (\"cssRules\" in domRule) {\n rule.mount(domRule as CSSMediaRule);\n }\n });\n }\n\n render(dom: HTMLStyleElement | CSSGroupingRule) {\n if (dom instanceof HTMLStyleElement) {\n this.domStyle = dom;\n this.items.forEach((rule) => rule.render(dom.sheet!));\n } else if (dom instanceof CSSGroupingRule) {\n this.items.forEach((rule) => rule.render(dom));\n }\n }\n\n _dispose(): void {\n if (this.items) {\n for (let i = 0; i < this.items.length; i++) {\n this.items[i]._dispose();\n }\n }\n\n this.items = [];\n this.parent = null;\n this.domStyle = null;\n }\n}\n","import { SvgTags, VoidTags } from \"../constants.js\";\nimport { __DEV__ } from \"../dev.js\";\nimport {\n collectCSSRules,\n deepClone,\n ensureDomStyle,\n getTagName,\n mergePartial,\n validate,\n} from \"../helpers.js\";\nimport type {\n BehaviorInstance,\n BehaviorSpec,\n DomphyElement,\n EventName,\n HookMap,\n Listener,\n PartialElement,\n TagName,\n} from \"../types.js\";\nimport { hashString, merge } from \"../utils.js\";\nimport { AttributeList } from \"./AttributeList.js\";\nimport { ElementList } from \"./ElementList.js\";\nimport { StyleList } from \"./StyleList.js\";\n\nexport class ElementNode {\n _disposed = false;\n _beforeRemoveFired = false;\n // True when inserted imperatively (a direct children.insert() by app/patch\n // code, e.g. a floating panel or an _onInit-inserted subtree) rather than by\n // declared-inputs reconciliation — see ElementList.update()/insert().\n _imperative = false;\n type = \"ElementNode\";\n parent: ElementNode | null = null;\n _childrenRelease?: () => void;\n // Whether the BeforeRemove hook that releases `_childrenRelease` has been\n // registered for this node. It must register at most ONCE per node: patch()\n // re-runs _setupFunctionChildren on every reuse, and addHook COMPOSES hooks,\n // so an unguarded registration would grow the hook chain by one closure per\n // patch for the node's whole life.\n _childrenReleaseHooked = false;\n _portal?: (root: ElementNode) => HTMLElement;\n // Per-node behavior contract (see `behavior()` in utils.ts). Attached\n // instances, keyed the same as their declaring `_behaviors` record.\n _behaviorInstances = new Map<string, BehaviorInstance>();\n // Specs declared before the DOM element exists (construction-time merge()),\n // held until the Mount hook can actually attach them.\n _pendingBehaviors = new Map<string, BehaviorSpec>();\n _behaviorMountHooked = false;\n _behaviorTeardownHooked = false;\n tagName: TagName;\n children = new ElementList(this);\n styles = new StyleList(this);\n attributes = new AttributeList(this);\n domElement?: HTMLElement | null = null;\n _hooks: HookMap = {};\n _events?:\n | { [K in EventName]?: (event: Event, node: ElementNode) => void }\n | null = null;\n _boundEvents = new Set<EventName>();\n _context?: Record<string, any> = {};\n _metadata?: Record<string, any> = {};\n key?: string | number | null = null;\n nodeId: string;\n\n constructor(\n domphyElement: DomphyElement,\n _parent: ElementNode | null = null,\n index = 0,\n ) {\n domphyElement = deepClone(domphyElement);\n validate(domphyElement);\n domphyElement.style = domphyElement.style || {};\n this.parent = _parent;\n this.tagName = getTagName(domphyElement) as TagName;\n domphyElement = mergePartial(domphyElement) as DomphyElement;\n\n this.key = (domphyElement as any)._key ?? null;\n this._context = domphyElement._context || {};\n this._metadata = domphyElement._metadata || {};\n\n const tempPath = `${this.parent?.nodeId}.${index}`;\n const str = JSON.stringify(domphyElement.style || {}, (_k, v) =>\n typeof v === \"function\" ? tempPath : v,\n );\n this.nodeId = hashString(tempPath + str);\n\n this.attributes!.addClass(`${this.tagName}_${this.nodeId}`);\n if (domphyElement._onSchedule)\n domphyElement._onSchedule(this, domphyElement);\n\n this.merge(domphyElement);\n\n const children = (domphyElement as any)[this.tagName];\n\n if (children != null) {\n if (typeof children === \"function\") {\n this._setupFunctionChildren(children);\n } else {\n this.children!.update(Array.isArray(children) ? children : [children]);\n }\n }\n this._hooks.Init && this._hooks.Init(this);\n }\n\n _setupFunctionChildren(fn: (listener: any) => any): void {\n let listener: any = () => {\n if (this._disposed) return;\n try {\n const input = fn(listener);\n this.children!.update(Array.isArray(input) ? input : [input]);\n } catch (error) {\n this._handleError(error);\n }\n };\n listener!.elementNode = this;\n listener!.debug = `class:${this.tagName}_${this.nodeId} children`;\n // onSubscribe fires once per Notifier the listener subscribes to — a\n // children function reading N states yields N release handles. Keeping\n // only the last one leaked the others: the stale subscriptions kept\n // re-running an OLD generation's closure after patch() re-setup.\n const releases: Array<() => void> = [];\n listener!.onSubscribe = (release: () => void) => {\n releases.push(release);\n this._childrenRelease = () => {\n for (const releaseSubscription of releases) releaseSubscription();\n releases.length = 0;\n listener = null;\n };\n // Register the releasing hook once per NODE, not once per subscription\n // or per patch() re-setup — addHook composes, so repeats would grow the\n // BeforeRemove chain unboundedly on frequently re-rendered nodes. The\n // hook body reads the CURRENT _childrenRelease dynamically, so one\n // registration covers every later re-setup.\n if (!this._childrenReleaseHooked) {\n this._childrenReleaseHooked = true;\n this.addHook(\"BeforeRemove\", () => {\n this._childrenRelease?.();\n this._childrenRelease = undefined;\n });\n }\n };\n listener();\n }\n\n _createDOMNode() {\n const svgNamespace = \"http://www.w3.org/2000/svg\";\n const node = SvgTags.includes(this.tagName)\n ? document.createElementNS(svgNamespace, this.tagName)\n : document.createElement(this.tagName);\n\n this.domElement = node as HTMLElement;\n\n if (this._events) {\n for (const key in this._events) this._bindEvent(key as EventName);\n }\n\n if (this.attributes) {\n Object.values(this.attributes.items!).forEach((attr) => attr.render());\n }\n return node;\n }\n\n // Bind a DOM listener that dispatches LIVE from this._events, so patch() can\n // swap the handler (e.g. a list item's onClick closure after its data changes)\n // without detaching/reattaching the DOM listener.\n _bindEvent(eventName: EventName): void {\n if (!this.domElement || this._boundEvents.has(eventName)) return;\n this._boundEvents.add(eventName);\n let fn: any = (event: Event) => this._events?.[eventName]?.(event, this);\n this.domElement.addEventListener(eventName, fn);\n this.addHook(\"BeforeRemove\", (n) => {\n n.domElement?.removeEventListener(eventName, fn);\n fn = null;\n });\n }\n\n _dispose(): void {\n if (this._disposed) return;\n this._disposed = true;\n\n // Fire BeforeRemove so reactive-listener releases (registered as BeforeRemove\n // hooks via onSubscribe) actually run for this node. Descendants are torn\n // down through this recursive _dispose — not through ElementList.remove — so\n // without this their subscriptions to long-lived State/RecordState leak.\n // Skip if the async-removal path in ElementList already fired it.\n if (!this._beforeRemoveFired) {\n this._beforeRemoveFired = true;\n this._hooks.BeforeRemove?.(this, () => {});\n }\n\n if (this.children) {\n this.children._dispose();\n }\n\n if (this.styles) {\n this.styles.items!.forEach((rule) => rule.remove());\n this.styles._dispose();\n }\n\n if (this.attributes) {\n this.attributes._dispose();\n }\n\n // _onRemove fires for every node in the subtree, not just the directly-removed one.\n this._hooks.Remove?.(this);\n\n this.domElement = null;\n this._hooks = {};\n this._events = null;\n this._context = {};\n this._metadata = {};\n this.parent = null;\n }\n merge(part: PartialElement) {\n merge(this._context, part._context);\n merge(this._metadata, part._metadata);\n this._processBehaviors(part._behaviors);\n\n const keys = Object.keys(part);\n for (let i = 0; i < keys.length; i++) {\n const originalKey = keys[i];\n const value = (part as any)[originalKey];\n if (\n [\n \"$\",\n \"_onSchedule\",\n \"_key\",\n \"_context\",\n \"_metadata\",\n \"_behaviors\",\n \"style\",\n this.tagName,\n ].includes(originalKey)\n ) {\n } else if (\n [\n \"_onInit\",\n \"_onInsert\",\n \"_onMount\",\n \"_onBeforeUpdate\",\n \"_onUpdate\",\n \"_onBeforeRemove\",\n \"_onRemove\",\n \"_onError\",\n ].includes(originalKey)\n ) {\n this.addHook(originalKey.substring(3) as keyof HookMap, value);\n } else if (originalKey.startsWith(\"on\")) {\n this.addEvent(\n originalKey.substring(2).toLowerCase() as EventName,\n value,\n );\n } else if (originalKey === \"_portal\") {\n this._portal = value;\n } else if (originalKey === \"class\") {\n // A `class` must MERGE with (not replace) the auto-generated per-node\n // style class set at construction (line ~67) — replacing it outright\n // orphans this element's own `style: {}` object, since the CSS rule\n // is scoped to that auto class name. This applies to string/function\n // values (via AttributeList.addClass) AND to a nullish value (e.g. an\n // element passing through `class: props.className` with `className`\n // left unset) — the latter must be a no-op, NOT fall through to the\n // generic `attributes.set(\"class\", undefined)` below, which clears\n // the attribute and silently drops the auto class token.\n if (typeof value === \"string\" || typeof value === \"function\") {\n this.attributes!.addClass(value);\n }\n } else {\n this.attributes!.set(originalKey, value);\n }\n }\n if (part.style) {\n this.styles.addCSS(\n part.style || {},\n `.${`${this.tagName}_${this.nodeId}`}`,\n );\n }\n }\n\n // Update this live node IN PLACE from a fresh element description, preserving\n // its DOM element (and thus focus/scroll/selection/uncontrolled value) and its\n // children's identity. Used by list reconciliation to reuse a node by key\n // (keyed) or position (unkeyed) while reflecting new data, instead of\n // destroying and recreating the DOM. Flat style properties ARE reconciled (see\n // styles.patchCSS below) — a reused node's newly-computed static style must\n // reach the DOM, e.g. a factory function like `FilterButton(label, active,\n // onClick)` called again with new args from a reactive parent. Nested selector\n // blocks (&:hover, @media, …) are NOT reconciled — set once at construction,\n // assumed stable across reuse. Lifecycle hooks are NOT re-run (reused items\n // share structure; hooks already ran). Reactive content (a function child)\n // keeps its own listener and is left untouched.\n patch(rawElement: DomphyElement): void {\n let element: any = deepClone(rawElement);\n element.style = element.style || {};\n element = mergePartial(element);\n\n // Children / content — recurse so grandchildren are reused/patched too.\n // Reactive function always wins: release old binding and re-setup with the\n // new closure so the node reflects the new data source, not the stale one.\n // Nullish content means \"no children declared\" — same as the constructor —\n // NOT \"remove all children\". Treating it as [] here used to wipe children\n // that a patch inserted imperatively (node.children.insert in _onInit, e.g.\n // selectBox/combobox's inner tag list + input) on every ancestor re-render,\n // since lifecycle hooks don't re-run on a reused node to put them back.\n const content = element[this.tagName];\n if (typeof content === \"function\") {\n this._childrenRelease?.();\n this._childrenRelease = undefined;\n this._setupFunctionChildren(content);\n } else if (content != null) {\n const next = Array.isArray(content) ? content : [content];\n this.children.update(next, !!this.domElement, true);\n }\n\n if (element._context) merge(this._context, element._context);\n if (element._metadata) merge(this._metadata, element._metadata);\n this._processBehaviors(element._behaviors);\n\n this.styles.patchCSS(element.style || {}, `.${this.tagName}_${this.nodeId}`);\n\n // Rebuild attributes and events. Events are replaced (live dispatch in\n // _bindEvent reads this._events, so swapping the map is enough); attributes\n // present before but absent now are removed; the auto scope class is kept.\n const autoClass = `${this.tagName}_${this.nodeId}`;\n const reserved = [\n \"$\",\n \"_onSchedule\",\n \"_key\",\n \"_context\",\n \"_metadata\",\n \"_behaviors\",\n \"style\",\n this.tagName,\n ];\n const hookKeys = [\n \"_onInit\",\n \"_onInsert\",\n \"_onMount\",\n \"_onBeforeUpdate\",\n \"_onUpdate\",\n \"_onBeforeRemove\",\n \"_onRemove\",\n \"_onError\",\n ];\n const keep = new Set<string>([\"class\"]);\n let userClass: string | ((listener: Listener) => string) | null = null;\n\n this._events = {};\n for (const key of Object.keys(element)) {\n if (reserved.includes(key) || hookKeys.includes(key) || key === \"_portal\")\n continue;\n const value = element[key];\n if (key.startsWith(\"on\") && typeof value === \"function\") {\n this.addEvent(key.substring(2).toLowerCase() as EventName, value);\n } else if (\n key === \"class\" &&\n (typeof value === \"string\" || typeof value === \"function\")\n ) {\n userClass = value;\n } else {\n this.attributes!.set(key, value);\n keep.add(key);\n }\n }\n\n // A reactive userClass must stay reactive here too — a plain string\n // combine (as if it were static) would freeze it at whatever the\n // function happened to return on this one patch call, and never update\n // again since patch() doesn't re-run per listener tick.\n if (typeof userClass === \"function\") {\n const userClassFn = userClass;\n this.attributes!.set(\n \"class\",\n (listener: Listener) => `${autoClass} ${userClassFn(listener)}`,\n );\n } else {\n this.attributes!.set(\n \"class\",\n userClass ? `${autoClass} ${userClass}` : autoClass,\n );\n }\n\n if (this.attributes!.items) {\n for (const name of Object.keys(this.attributes!.items)) {\n if (!keep.has(name)) this.attributes!.remove(name);\n }\n }\n\n if (this._events) {\n for (const key in this._events) this._bindEvent(key as EventName);\n }\n }\n\n // Walk ancestors to find the nearest Error hook. The boundary node receives\n // the error and a `reset` callback that clears its children (allowing it to\n // re-render with fresh data or a fallback). If no handler is found, log to\n // console so errors in reactive children are never silently swallowed.\n _handleError(error: unknown): void {\n let node: ElementNode | null = this;\n while (node) {\n if (node._hooks.Error) {\n const boundary = node;\n node._hooks.Error(boundary, error, () => {\n boundary.children.update([]);\n });\n return;\n }\n node = node.parent;\n }\n console.error(\"[Domphy] Unhandled error in reactive child:\", error);\n }\n\n addEvent(\n name: EventName,\n callback: (event: Event, node: ElementNode) => void,\n ): void {\n this._events = this._events || {};\n\n const current = this._events[name];\n if (typeof current === \"function\") {\n this._events[name] = (event: Event, node: ElementNode) => {\n current!(event, node);\n callback(event, node);\n };\n } else {\n this._events[name] = callback;\n }\n }\n\n addHook<K extends keyof HookMap>(name: K, callback: HookMap[K]): void {\n const current = this._hooks[name];\n\n if (typeof current === \"function\") {\n const composed = ((...args: any[]) => {\n (current as Function)(...args);\n (callback as Function)(...args);\n }) as HookMap[K];\n // Preserve the maximum declared arity across composed hooks. Removal logic\n // inspects BeforeRemove.length (>= 2 means the hook owns `done()`, e.g. an\n // exit animation); a naive (...args) wrapper would report 0 and break that.\n try {\n Object.defineProperty(composed, \"length\", {\n value: Math.max(\n (current as Function).length,\n (callback as Function).length,\n ),\n configurable: true,\n });\n } catch {\n /* length non-configurable on some engines — best effort */\n }\n this._hooks[name] = composed;\n } else {\n this._hooks[name] = callback;\n }\n }\n getRoot(): ElementNode {\n let root: ElementNode = this;\n while (root && root instanceof ElementNode && root.parent) {\n root = root.parent;\n }\n return root;\n }\n\n // Route a `_behaviors` record declared by THIS generation's PartialElement\n // into their per-node instances: an already-attached key gets its fresh\n // `props` forwarded via update() (the cross-generation fix — the instance,\n // not the closure that declared it, is what persists); a not-yet-attached\n // key attaches immediately if the DOM element already exists (the patch()/\n // reused-node path), or is queued for the node's one-time Mount hook\n // (the merge()/construction path, where domElement doesn't exist yet).\n _processBehaviors(behaviors?: Record<string, BehaviorSpec>): void {\n if (!behaviors) return;\n for (const key of Object.keys(behaviors)) {\n const spec = behaviors[key];\n const instance = this._behaviorInstances.get(key);\n if (instance) {\n instance.update?.(spec.props);\n } else if (this.domElement) {\n this._attachBehaviorNow(key, spec);\n } else {\n this._pendingBehaviors.set(key, spec);\n this._ensureBehaviorMountHook();\n }\n }\n }\n\n _attachBehaviorNow(key: string, spec: BehaviorSpec): void {\n const instance = spec.attach(this, spec.props) || {};\n this._behaviorInstances.set(key, instance);\n this._ensureBehaviorTeardownHook();\n }\n\n // Registered at most once per node (Mount itself only ever fires once per\n // real DOM node) — flushes whatever was queued by merge() at construction,\n // by then reading domElement/getRoot() safely.\n _ensureBehaviorMountHook(): void {\n if (this._behaviorMountHooked) return;\n this._behaviorMountHooked = true;\n this.addHook(\"Mount\", () => {\n if (this._pendingBehaviors.size === 0) return;\n const pending = this._pendingBehaviors;\n this._pendingBehaviors = new Map();\n pending.forEach((spec, key) => this._attachBehaviorNow(key, spec));\n });\n }\n\n // Registered at most once per node — addHook COMPOSES, so a per-attach\n // registration would grow the BeforeRemove chain by one closure per\n // behavior key. The body reads the CURRENT instance map dynamically, so\n // one registration covers every key attached over the node's whole life.\n _ensureBehaviorTeardownHook(): void {\n if (this._behaviorTeardownHooked) return;\n this._behaviorTeardownHooked = true;\n this.addHook(\"BeforeRemove\", () => {\n this._behaviorInstances.forEach((instance) => instance.destroy?.());\n this._behaviorInstances.clear();\n });\n }\n\n // Look up a behavior instance by key, walking up from this node through its\n // ancestors (same pattern as getContext/getMetadata) — a behavior is\n // declared on the element that owns the concern (e.g. a combobox's outer\n // anchor), but the event that needs it often fires on a DESCENDANT (e.g.\n // the combobox's inner input on focus). Returns undefined if the key was\n // never declared on this node or an ancestor, or was declared but hasn't\n // attached yet (construction-time, pre-Mount).\n getBehavior<T extends BehaviorInstance = BehaviorInstance>(\n key: string,\n ): T | undefined {\n let node: ElementNode | null = this;\n while (node) {\n const instance = node._behaviorInstances.get(key);\n if (instance) return instance as T;\n node = node.parent;\n }\n return undefined;\n }\n\n getContext(name: string): any {\n let node: ElementNode | null = this;\n while (node && (!node._context || !Object.hasOwn(node._context, name))) {\n node = node.parent;\n }\n return node && node._context ? node._context[name] : undefined;\n }\n\n setContext(name: string, value: any) {\n this._context = this._context || {};\n this._context[name] = value;\n }\n\n getMetadata(name: string): any {\n return this._metadata ? this._metadata[name] : undefined;\n }\n\n setMetadata(key: string, value: any) {\n this._metadata = this._metadata || {};\n this._metadata[key] = value;\n }\n\n generateCSS(): string {\n if (!this.styles || !this.children) return \"\";\n let css = this.styles.cssText();\n css += this.children.items\n .map((child) => (child instanceof ElementNode ? child.generateCSS() : \"\"))\n .join(\"\");\n return css;\n }\n\n generateHTML(): string {\n if (!this.children || !this.attributes) return \"\";\n const attributes = this.attributes.generateHTML();\n // Void elements must not emit a closing tag — `<br></br>` is parsed by the\n // HTML tokenizer as two <br>, which corrupts hydration child alignment.\n if ((VoidTags as readonly string[]).includes(this.tagName)) {\n return `<${this.tagName}${attributes}>`;\n }\n const content = this.children.generateHTML();\n return `<${this.tagName}${attributes}>${content}</${this.tagName}>`;\n }\n\n mount(domElement: HTMLElement, domStyle?: HTMLStyleElement): void {\n if (!domElement) throw new Error(\"Missing dom node on bind\");\n if (\n __DEV__ &&\n !domStyle &&\n this.parent === null &&\n domElement.childNodes.length > 0\n ) {\n console.warn(\n \"[Domphy] mount() was called without a style element on already-rendered DOM. Reactive style updates after hydration will be dropped — pass the server-rendered <style> element as the second argument to mount().\",\n );\n }\n this.domElement = domElement;\n\n if (this._events) {\n for (const key in this._events) this._bindEvent(key as EventName);\n }\n\n if (this.children) {\n this.children.items.forEach((child, i) => {\n const childNode = domElement.childNodes[i];\n if (!childNode) return;\n if (child instanceof ElementNode) {\n child.mount(childNode as HTMLElement);\n } else {\n // Bind the server-rendered text/inline-HTML node so that reactive\n // child updates after hydration can locate and replace it.\n child.domText = childNode;\n }\n });\n }\n\n // Attach reactive style declarations to the server-rendered stylesheet so\n // post-hydration updates mutate the existing CSSOM rules instead of being\n // silently dropped (StyleProperty._domUpdate needs a bound domRule). Done\n // once from the call that received the style element, walking the whole\n // subtree because per-node selectors are globally unique.\n if (domStyle) {\n const sheet = domStyle.sheet;\n if (sheet)\n this._hydrateStyles(collectCSSRules(sheet.cssRules, new Map()));\n }\n\n this._hooks.Mount && this._hooks.Mount(this);\n }\n\n _hydrateStyles(domRuleMap: Map<string, CSSRule>): void {\n this.styles?.hydrate(domRuleMap);\n if (this.children) {\n for (const child of this.children.items) {\n if (child instanceof ElementNode) child._hydrateStyles(domRuleMap);\n }\n }\n }\n\n render(\n domElement: HTMLElement | SVGElement | DocumentFragment,\n ): HTMLElement | SVGElement {\n const newNode = this._createDOMNode();\n domElement.appendChild(newNode);\n this._hooks.Mount && this._hooks.Mount(this);\n let domStyle = this.getRoot().styles.domStyle;\n const root = domElement.getRootNode();\n const styleParent = root instanceof ShadowRoot ? root : document.head;\n domStyle ||= ensureDomStyle(styleParent);\n this.styles.render(domStyle as HTMLStyleElement);\n this.children.items.forEach((child) => {\n if (child instanceof ElementNode && child._portal) {\n const dom = child._portal!(this.getRoot());\n dom && child.render(dom);\n } else {\n child.render(newNode);\n }\n });\n return newNode;\n }\n\n remove() {\n if (this.parent) {\n this.parent.children.remove(this);\n } else {\n // Root removal must also run BeforeRemove/Remove (and release reactive\n // subscriptions across the whole tree via _dispose), honoring async done().\n const done = () => {\n this.domElement?.remove();\n this._dispose();\n };\n if (this._hooks.BeforeRemove && this.domElement) {\n let called = false;\n const once = () => {\n if (!called) {\n called = true;\n done();\n }\n };\n // Capture the hook reference (and thus its arity) before calling it — a\n // synchronous 2-arg hook (e.g. `motion()` with no `exit` frame) may call\n // `once()` inline, which runs `done()` -> `_dispose()` -> clears\n // `this._hooks` to `{}` before this line would otherwise re-read it.\n const beforeRemoveHook = this._hooks.BeforeRemove;\n this._beforeRemoveFired = true;\n beforeRemoveHook(this, once);\n if ((beforeRemoveHook as Function).length < 2 && !called) once();\n else if (__DEV__ && !called) {\n setTimeout(() => {\n if (!called)\n console.warn(\n \"[Domphy] _onBeforeRemove declared a `done` parameter but did not call it within 5s — the element will stay in the DOM. Call done() when cleanup finishes.\",\n );\n }, 5000);\n }\n } else {\n done();\n }\n }\n }\n}\n","import { escapeHTML, isHTML, sanitizeHTMLString } from \"../helpers.js\";\nimport type { ElementNode } from \"./ElementNode.js\";\n\nexport class TextNode {\n type = \"TextNode\";\n // True when inserted imperatively (a direct children.insert()) rather than\n // by declared-inputs reconciliation — see ElementList.update()/insert().\n _imperative = false;\n parent: ElementNode;\n text: string;\n domText?: ChildNode;\n\n constructor(textContent: string | number, parent: ElementNode) {\n this.parent = parent;\n this.text = textContent === \"\" ? \"\\u200B\" : String(textContent);\n }\n _createDOMNode() {\n let newNode: ChildNode;\n if (isHTML(this.text)) {\n const tpl = document.createElement(\"template\");\n tpl.innerHTML = this.text.trim();\n // Strip event-handler attributes and javascript: URLs from all elements.\n tpl.content.querySelectorAll(\"*\").forEach((el) => {\n for (const attr of Array.from(el.attributes)) {\n if (/^on/i.test(attr.name)) {\n el.removeAttribute(attr.name);\n } else if (\n /^(?:href|src|action|formaction)$/i.test(attr.name) &&\n /^\\s*javascript:/i.test(attr.value)\n ) {\n el.setAttribute(attr.name, \"#\");\n }\n }\n });\n newNode = tpl.content.firstChild || document.createTextNode(\"\");\n } else {\n newNode = document.createTextNode(this.text);\n }\n this.domText = newNode;\n return newNode;\n }\n\n // Update the text content in place. When the node is a plain DOM text node and\n // stays plain text, mutate `nodeValue` directly (cheap, preserves the node) —\n // this is what lets reactive text like `(l) => \"Count: \" + n.get(l)` patch the\n // existing text node instead of recreating it every change. Crossing the\n // plain/inline-HTML boundary (or a non-text node) rebuilds the node.\n setText(textContent: string | number): void {\n const next =\n textContent === \"\" ? String.fromCharCode(0x200b) : String(textContent);\n if (next === this.text && this.domText) return;\n const wasHTML = isHTML(this.text);\n this.text = next;\n if (!this.domText) return;\n if (!wasHTML && !isHTML(next) && this.domText.nodeType === 3) {\n this.domText.nodeValue = next;\n return;\n }\n const old = this.domText;\n const fresh = this._createDOMNode();\n old.parentNode?.replaceChild(fresh, old);\n }\n\n _dispose(): void {\n this.domText = undefined;\n this.text = \"\";\n }\n\n generateHTML(): string {\n if (this.text === \"\\u200B\") return \"​\";\n // Mirror _createDOMNode: a single-root HTML string is intentional inline\n // HTML, anything else is plain text and must be escaped so the server\n // output is XSS-safe and parses back to the same text node the client\n // builds (otherwise hydration child alignment drifts).\n return isHTML(this.text)\n ? sanitizeHTMLString(this.text)\n : escapeHTML(this.text);\n }\n\n render(domText: ChildNode | DocumentFragment | HTMLElement): void {\n const newNode = this._createDOMNode();\n domText.appendChild(newNode);\n }\n}\n","import { __DEV__ } from \"../dev.js\";\nimport { ensureDomStyle, getTagName } from \"../helpers.js\";\nimport type { DomphyElement } from \"../types.js\";\nimport { ElementNode } from \"./ElementNode.js\";\nimport { TextNode } from \"./TextNode.js\";\n\ntype ElementInput = DomphyElement | null | undefined | number | string;\ntype NodeItem = ElementNode | TextNode;\n\n// DEV-only: call-sites that have already emitted the missing-`_key` reactive-list\n// warning, so it fires at most once per site instead of every reactive frame.\n// Keyed by the owner node's stable nodeId (same call-site → same id).\nconst _warnedKeylessSites = new Set<string>();\n\n// Test-only: clear the once-per-site throttle so each test starts clean.\nexport function _resetKeylessWarnings(): void {\n _warnedKeylessSites.clear();\n}\n\nexport class ElementList {\n items: NodeItem[] = [];\n owner: ElementNode;\n _nextKey: number = 0;\n\n constructor(parent: ElementNode) {\n this.owner = parent;\n }\n\n _createNode(element: ElementInput | DomphyElement): NodeItem {\n return typeof element === \"object\" && element !== null\n ? new ElementNode(element, this.owner, this._nextKey++)\n : new TextNode(element == null ? \"\" : String(element), this.owner);\n }\n\n // Resolve the first item at or after `index` whose DOM node is an ACTUAL\n // child of the owner's DOM element, for use as an insertBefore reference.\n // The logical `items` array and the real DOM child list diverge: a portal\n // item occupies a logical slot while its DOM lives wherever _portal() routed\n // it, so a positional `childNodes[i]` (or a blind `items[i].domElement`)\n // reference either points outside the owner (insertBefore throws\n // NotFoundError) or drifts by the number of preceding portals (silently\n // misplacing the node). Returns null when no such item exists (append).\n _domReferenceAfter(index: number): Node | null {\n const dom = this.owner.domElement;\n if (!dom) return null;\n for (let i = index; i < this.items.length; i++) {\n const item = this.items[i];\n const el = item instanceof ElementNode ? item.domElement : item.domText;\n if (el && el.parentNode === dom) return el;\n }\n return null;\n }\n\n _moveDomElement(node: NodeItem, index: number) {\n if (!this.owner || !this.owner.domElement) return;\n const dom = this.owner.domElement;\n\n const el = node instanceof ElementNode ? node.domElement : node.domText;\n if (!el) return;\n // `el` still occupies its old DOM slot when this runs, so a positional\n // `childNodes[index]` reference is off by one for a forward move. Reference\n // the node that should FOLLOW `el` in the new logical order by identity\n // instead — direction-agnostic and correct for forward and backward moves\n // (and for a move to the last slot, where there is no following node).\n const ref = this._domReferenceAfter(index + 1);\n if (el !== ref) dom.insertBefore(el, ref);\n }\n\n _swapDomElement(aNode: NodeItem, bNode: NodeItem) {\n if (!this.owner || !this.owner.domElement) return;\n const parent = this.owner.domElement;\n\n const a = aNode instanceof ElementNode ? aNode.domElement : aNode.domText;\n const b = bNode instanceof ElementNode ? bNode.domElement : bNode.domText;\n if (!a || !b) return;\n\n const aNext = a.nextSibling;\n const bNext = b.nextSibling;\n\n parent.insertBefore(a, bNext);\n parent.insertBefore(b, aNext);\n }\n\n update(inputs: ElementInput[], updateDom = true, silent = false): void {\n // Imperatively-inserted nodes (a direct children.insert() by app/patch\n // code — e.g. a floating panel portaled under the root, or selectBox's\n // inner tag list) are NOT part of the declared `inputs` and must survive\n // reconciliation: from this method's point of view they'd otherwise be\n // indistinguishable from stale leftovers and get pruned by the extras\n // cleanup below on the very next unrelated re-render. Park them at the\n // logical tail so positional reuse and the extras slice only ever see\n // declared nodes (their real DOM position is untouched — logical order is\n // an internal bookkeeping detail for them).\n if (this.items.some((item) => item._imperative)) {\n const declared = this.items.filter((item) => !item._imperative);\n const imperative = this.items.filter((item) => item._imperative);\n this.items = declared.concat(imperative);\n }\n\n const oldItems = this.items.slice(); // snapshot for cleanup\n\n // Keyed lookup from old list. Skip imperative nodes (never reconciled) and\n // nodes whose async removal is still in flight (_beforeRemoveFired — an\n // exit animation awaiting done()): \"resurrecting\" a mid-removal node by\n // key would let the original deferred done() later rip the reused node out\n // of the live list and dispose it. A re-added key gets a FRESH node while\n // the old one finishes exiting.\n const keyed = new Map<string | number, NodeItem>();\n for (const item of oldItems) {\n if (\n item instanceof ElementNode &&\n item.key !== null &&\n item.key !== undefined &&\n !item._imperative &&\n !item._beforeRemoveFired\n ) {\n keyed.set(item.key, item);\n }\n }\n\n if (!silent && this.owner.domElement)\n this.owner._hooks?.BeforeUpdate?.(this.owner, inputs);\n\n const oldSet = new Set<NodeItem>(oldItems);\n const claimed = new Set<NodeItem>();\n\n // DEV-only footgun detection (warn-only — does NOT change reconciliation).\n // An unkeyed list that grows or shrinks may pair the wrong node with the\n // wrong data slot (DOM ordering issue). A fixed-length unkeyed list is safe.\n let unkeyedObjectInputs = 0;\n const lengthChanged =\n __DEV__ && oldItems.length > 0\n ? inputs.length !== oldItems.length\n : false;\n\n // build target order using existing ops (mutating this.items)\n for (let i = 0; i < inputs.length; i++) {\n const input = inputs[i];\n const isObj = typeof input === \"object\" && input !== null;\n const key = isObj ? (input as any)._key : undefined;\n const tag = isObj ? getTagName(input as DomphyElement) : undefined;\n if (__DEV__ && isObj && key === undefined) unkeyedObjectInputs++;\n\n // Keyed reuse: same key + same tag → reuse the node and patch it in place\n // (preserves DOM identity/state while reflecting new data).\n if (key !== undefined) {\n const reused = keyed.get(key);\n if (reused instanceof ElementNode && reused.tagName === tag) {\n keyed.delete(key);\n const cur = this.items.indexOf(reused);\n if (cur !== i && cur >= 0) {\n const isPortal = !!reused._portal;\n this.move(cur, i, isPortal ? false : updateDom, true);\n }\n reused.parent = this.owner as any;\n reused.patch(input as DomphyElement);\n claimed.add(reused);\n continue;\n }\n // key present but no tag-compatible match → fall through to insert; any\n // stale keyed node keeps its slot in `keyed` and is removed below.\n } else if (isObj) {\n // Unkeyed positional reuse: reuse the old unkeyed element already sitting\n // at this slot if its tag matches — this is what preserves focus, scroll,\n // selection, IME and uncontrolled input values across plain list updates.\n const at = this.items[i];\n if (\n at instanceof ElementNode &&\n at.key == null &&\n at.tagName === tag &&\n oldSet.has(at) &&\n !claimed.has(at) &&\n !at._imperative &&\n !at._beforeRemoveFired\n ) {\n at.parent = this.owner as any;\n at.patch(input as DomphyElement);\n claimed.add(at);\n continue;\n }\n } else {\n // Text positional reuse: a string/number at this slot whose old node is a\n // TextNode is patched in place (mutate nodeValue) instead of recreating\n // the DOM text node — this keeps reactive text like `(l) => \"n:\" +\n // s.get(l)` cheap and stable across updates.\n const at = this.items[i];\n if (\n at instanceof TextNode &&\n oldSet.has(at) &&\n !claimed.has(at) &&\n !at._imperative\n ) {\n at.setText(input == null ? \"\" : (input as string | number));\n claimed.add(at);\n continue;\n }\n }\n\n claimed.add(this.insert(input, i, updateDom, true, true));\n }\n\n // Remove leftover nodes beyond the new length. Iterate a SNAPSHOT (not a\n // `while length > inputs.length` loop): a removal may defer (async exit\n // animation), leaving the node in `items`, so a length-based loop would spin.\n // Imperative nodes (parked at the tail above) are exempt — they are managed\n // by whoever inserted them, not by this declared-inputs reconciliation.\n const extras = this.items.slice(inputs.length);\n for (const node of extras) {\n if (!node._imperative) this.remove(node, updateDom, true);\n }\n keyed.forEach((node) => this.remove(node, updateDom, true));\n\n // Warn (once per call-site) when an unkeyed list changes length — positional\n // reuse may pair the wrong DOM node with the wrong data slot (focus, scroll,\n // input value drift). A fixed-length unkeyed list never trips this.\n // Skips the first render (gated on oldItems.length > 0) and keyed lists.\n if (\n __DEV__ &&\n oldItems.length > 0 &&\n unkeyedObjectInputs > 0 &&\n lengthChanged\n ) {\n const siteId = this.owner.nodeId;\n if (!_warnedKeylessSites.has(siteId)) {\n _warnedKeylessSites.add(siteId);\n const msg = `[domphy] unkeyed list length changed — DOM nodes reused by position may not match their data slot (focus/scroll/input-value drift). Add _key to each item. (parent <${this.owner.tagName}>, ${unkeyedObjectInputs} unkeyed item${unkeyedObjectInputs === 1 ? \"\" : \"s\"})`;\n console.warn(msg);\n }\n }\n\n if (!silent) this.owner._hooks?.Update?.(this.owner);\n }\n\n insert(\n input: ElementInput,\n index?: number,\n updateDom = true,\n silent = false,\n declared = false,\n ): NodeItem {\n const length = this.items.length;\n const finalIndex =\n typeof index !== \"number\" ||\n Number.isNaN(index) ||\n index < 0 ||\n index > length\n ? length\n : index;\n const item = this._createNode(input);\n // A node inserted by anything other than update()'s declared-inputs\n // reconciliation (`declared` is only ever passed by update) is imperative:\n // reconciliation must neither positionally reuse it nor prune it as a\n // stale extra — see update().\n item._imperative = !declared;\n this.items.splice(finalIndex, 0, item);\n\n if (item instanceof ElementNode) {\n //Parent always insert/mount before children\n item._hooks.Insert && item._hooks.Insert(item);\n\n const domElement = this.owner.domElement;\n if (updateDom && domElement) {\n if (item._portal) {\n const domElement = item._portal!(this.owner.getRoot());\n domElement && item.render(domElement);\n } else {\n const domNode = item._createDOMNode();\n // Reference by logical successor, not childNodes[finalIndex] — a\n // portal item earlier in `items` has no DOM slot here, so a raw\n // positional index drifts and silently misplaces the new node.\n const ref = this._domReferenceAfter(finalIndex + 1);\n domElement.insertBefore(domNode, ref);\n const root = domElement.getRootNode();\n const styleParent = root instanceof ShadowRoot ? root : document.head;\n const domStyle = ensureDomStyle(styleParent);\n item.styles.render(domStyle as HTMLStyleElement);\n item._hooks.Mount && item._hooks.Mount(item);\n item.children.items.forEach((child) => {\n if (child instanceof ElementNode && child._portal) {\n const dom = child._portal!(child.getRoot());\n dom && child.render(dom);\n } else {\n child.render(domNode);\n }\n });\n }\n }\n } else {\n const domElement = this.owner.domElement;\n if (updateDom && domElement) {\n const domNode = item._createDOMNode();\n const ref = this._domReferenceAfter(finalIndex + 1);\n domElement.insertBefore(domNode, ref);\n }\n }\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n return item;\n }\n\n remove(item: NodeItem, updateDom = true, silent = false): void {\n const index = this.items.indexOf(item);\n if (index < 0) return;\n\n if (item instanceof ElementNode) {\n // Guard against re-entrant removal of a node whose (deferred) removal is\n // already in flight — otherwise update()'s extras + keyed passes could\n // fire its BeforeRemove/animation twice. Synchronous removals are already\n // guarded by the indexOf check above (the node is spliced before re-entry).\n if (item._beforeRemoveFired) return;\n const done = () => {\n const el = item.domElement;\n // Re-resolve position at completion time — a deferred (animated) removal\n // may run after other inserts/removes have shifted indices.\n const i = this.items.indexOf(item);\n if (i >= 0) this.items.splice(i, 1);\n updateDom && el && el.remove();\n item._dispose(); // _dispose fires Remove + releases subscriptions for the whole subtree\n };\n if (item._hooks.BeforeRemove && item.domElement) {\n let doneCalled = false;\n const onceDone = () => {\n if (!doneCalled) {\n doneCalled = true;\n done();\n }\n };\n // Capture the hook reference (and thus its arity) before calling it — a\n // synchronous 2-arg hook (e.g. `motion()` with no `exit` frame) may call\n // `onceDone()` inline, which runs `done()` -> `item._dispose()` -> clears\n // `item._hooks` to `{}` before this line would otherwise re-read it.\n const beforeRemoveHook = item._hooks.BeforeRemove;\n item._beforeRemoveFired = true; // prevent _dispose from re-firing BeforeRemove\n beforeRemoveHook(item, onceDone);\n // Auto-complete only for sync cleanup hooks. A hook that declares `done`\n // (arity >= 2, e.g. an exit animation) owns completion and defers removal.\n if ((beforeRemoveHook as Function).length < 2 && !doneCalled)\n onceDone();\n else if (__DEV__ && !doneCalled) {\n setTimeout(() => {\n if (!doneCalled)\n console.warn(\n \"[Domphy] _onBeforeRemove declared a `done` parameter (e.g. an exit animation) but did not call it within 5s — the element will stay in the DOM. Call done() when cleanup finishes.\",\n );\n }, 5000);\n }\n } else {\n done();\n }\n } else {\n const el = item.domText;\n this.items.splice(index, 1);\n updateDom && el && el.remove();\n item._dispose();\n }\n\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n clear(updateDom = true, silent = false): void {\n if (this.items.length === 0) return;\n const snapshot = this.items.slice();\n\n for (const item of snapshot) {\n this.remove(item, updateDom, true);\n }\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n _dispose(): void {\n this.items.forEach((child) => child._dispose());\n this.items = [];\n }\n\n swap(aIndex: number, bIndex: number, updateDom = true, silent = false) {\n if (\n aIndex < 0 ||\n bIndex < 0 ||\n aIndex >= this.items.length ||\n bIndex >= this.items.length ||\n aIndex === bIndex\n )\n return;\n\n const itemA = this.items[aIndex];\n const itemB = this.items[bIndex];\n\n this.items[aIndex] = itemB;\n this.items[bIndex] = itemA;\n\n if (updateDom) this._swapDomElement(itemA, itemB);\n\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n move(\n fromIndex: number,\n toIndex: number,\n updateDom = true,\n silent = false,\n ): void {\n if (\n fromIndex < 0 ||\n fromIndex >= this.items.length ||\n toIndex < 0 ||\n toIndex >= this.items.length ||\n fromIndex === toIndex\n )\n return;\n\n const item = this.items[fromIndex];\n\n this.items.splice(fromIndex, 1);\n this.items.splice(toIndex, 0, item);\n\n if (updateDom) this._moveDomElement(item, toIndex);\n\n !silent &&\n this.owner.domElement &&\n this.owner._hooks.Update &&\n this.owner._hooks.Update(this.owner);\n }\n\n generateHTML(): string {\n let html = \"\";\n for (const item of this.items) html += item.generateHTML();\n return html;\n }\n}\n","import {\n activeCollector,\n Collector,\n runUntracked,\n runWithCollector,\n} from \"./Collector.js\";\nimport { __DEV__ } from \"../dev.js\";\nimport {\n _microtask,\n flushPendingNotifiers,\n hasPendingNotifiers,\n Notifier,\n runBatched,\n} from \"./Notifier.js\";\nimport type { ReadableState, ValueListener } from \"./State.js\";\n\n// Derived-reactivity layer built ON TOP of State/RecordState + Notifier. Nothing\n// here forks a parallel reactivity system: every dependency is tracked by\n// subscribing a Collector's handler through the same Notifier.addListener path a\n// plain `state.get(listener)` uses, and every downstream notification goes\n// through Notifier.notify (so `_chain` cycle detection still applies).\n\n// ----------------------------------------------------------------------------\n// Reaction scheduler\n// ----------------------------------------------------------------------------\n//\n// An effect/computed subscribes its Collector handler to EACH of its\n// dependencies' Notifiers. When several dependencies change in one tick (or in\n// one `batch`), each dependency Notifier flushes in its own microtask and would\n// invoke the handler once per dependency. To re-run a reaction at most ONCE per\n// burst, the handler does not run its work inline; it enqueues a deduplicated\n// job. A single microtask drains the queue, and jobs enqueued while draining\n// (e.g. a downstream computed reacting) are processed in the same drain — so a\n// `batch` of writes collapses into a single downstream flush.\n\n// Reuses the shared `_microtask` scheduler from Notifier (same `queueMicrotask`\n// fallback for older embedded Chromium runtimes that predate it).\n\nconst REACTION_QUEUE: Set<() => void> = new Set();\nlet reactionDrainScheduled = false;\n\nfunction scheduleReaction(job: () => void): void {\n REACTION_QUEUE.add(job);\n if (reactionDrainScheduled) return;\n reactionDrainScheduled = true;\n _microtask(drainReactions);\n}\n\nfunction drainReactions(): void {\n reactionDrainScheduled = false;\n // Drain in passes: a job may enqueue more jobs (a computed re-running pushes to\n // its downstream computeds). Process until the queue settles.\n while (REACTION_QUEUE.size > 0) {\n const jobs = [...REACTION_QUEUE];\n REACTION_QUEUE.clear();\n for (const job of jobs) {\n try {\n job();\n } catch (e) {\n console.error(\"[Domphy] Uncaught error in effect:\", e);\n }\n }\n }\n}\n\n// Synchronously flush all pending reactivity: state-change notifications (DOM\n// attribute/style bindings and computed/effect dependency signals) AND the\n// deduplicated effect/computed reaction queue. Alternates between the two\n// because a notifier flush can queue reactions and a reaction can write state\n// (which queues more notifier flushes); it loops until both settle. Useful in\n// tests and imperative code that must observe the DOM right after `.set()`\n// instead of waiting for the next microtask. Inside `batch()` it does not touch\n// the batched writes — those still flush when the batch ends.\nexport function flushSync(): void {\n let guard = 0;\n while (hasPendingNotifiers() || REACTION_QUEUE.size > 0) {\n if (guard++ > 10000) {\n console.error(\"[Domphy] flushSync did not settle\");\n break;\n }\n flushPendingNotifiers();\n drainReactions();\n }\n}\n\n// ----------------------------------------------------------------------------\n// Scopes\n// ----------------------------------------------------------------------------\n\n// Disposer registered to a scope. A computed/effect/listener created inside a\n// scope's `run` adds its teardown here so `stop()` can release the whole graph\n// of a removed subtree in one call.\ntype Disposer = () => void;\n\n// Stack of active scopes. Nested scopes register into the innermost one, and a\n// child scope is itself registered into its parent so stopping the parent stops\n// the child too.\nconst SCOPE_STACK: EffectScope[] = [];\n\nfunction activeScope(): EffectScope | null {\n return SCOPE_STACK.length ? SCOPE_STACK[SCOPE_STACK.length - 1] : null;\n}\n\nfunction registerDisposer(dispose: Disposer): void {\n const scope = activeScope();\n if (scope) scope._add(dispose);\n}\n\nexport interface EffectScopeHandle {\n // Run `fn` with this scope active; anything reactive created inside is owned\n // by the scope. Returns whatever `fn` returns.\n run<T>(fn: () => T): T;\n // Dispose everything created inside this scope (and inside nested scopes).\n stop(): void;\n}\n\nclass EffectScope implements EffectScopeHandle {\n private _disposers: Set<Disposer> = new Set();\n private _stopped = false;\n\n // Register a teardown owned by this scope. Called by effect/computed/listener\n // creation and by nested-scope creation.\n _add(dispose: Disposer): void {\n if (this._stopped) {\n // The scope is already stopped; tear the new resource down immediately so\n // a late creation cannot leak.\n dispose();\n return;\n }\n this._disposers.add(dispose);\n }\n\n run<T>(fn: () => T): T {\n if (this._stopped) {\n // The scope is already stopped: pushing it back onto SCOPE_STACK would\n // make every effect/computed created inside `fn` register into `_add`,\n // which disposes late resources immediately (see above) BEFORE their\n // first run — a permanently inert effect that never executes even once,\n // with no error or warning. Instead, run `fn` without pushing this scope\n // so any reactive resource created inside registers to whatever scope is\n // currently enclosing (or the global/no scope), staying disposable.\n if (__DEV__) {\n console.warn(\n \"[Domphy] effectScope.run() called after stop() — resources created inside are registered to the enclosing scope instead of this stopped one.\",\n );\n }\n return fn();\n }\n SCOPE_STACK.push(this);\n try {\n return fn();\n } finally {\n SCOPE_STACK.pop();\n }\n }\n\n stop(): void {\n if (this._stopped) return;\n this._stopped = true;\n for (const dispose of this._disposers) dispose();\n this._disposers.clear();\n }\n}\n\n// Create an effect scope. Used so a removed subtree can dispose its reactive\n// graph in one `stop()` call. Nested scopes are owned by the enclosing scope.\nexport function effectScope(): EffectScopeHandle {\n const scope = new EffectScope();\n registerDisposer(() => scope.stop());\n return scope;\n}\n\n// ----------------------------------------------------------------------------\n// Effect\n// ----------------------------------------------------------------------------\n\n// Run `fn` immediately, auto-tracking every reactive read inside it, and re-run\n// it whenever any tracked dependency changes. Returns a `dispose()` that releases\n// all current subscriptions. Each run re-collects dependencies, so reads no\n// longer reached (e.g. behind a branch) are dropped.\nexport function effect(fn: () => void): () => void {\n let disposed = false;\n // `running` guards against an effect whose `fn` writes a state it also reads,\n // which would otherwise re-enter `run` mid-run.\n let running = false;\n\n // A dependency changed: schedule a single deduplicated re-run. The job is the\n // SAME function reference each time, so the reaction queue's Set collapses\n // notifications from multiple dependencies (and from a batch) into one re-run.\n const job = (): void => {\n if (disposed) return;\n run();\n };\n const collector = new Collector(() => {\n if (disposed) return;\n scheduleReaction(job);\n });\n\n const run = (): void => {\n if (disposed || running) return;\n running = true;\n // Drop the previous run's dependencies so only deps read on THIS run remain\n // subscribed (stale-dep collection).\n collector.reset();\n try {\n runWithCollector(collector, fn);\n } finally {\n running = false;\n }\n };\n\n const dispose = (): void => {\n if (disposed) return;\n disposed = true;\n collector.reset();\n REACTION_QUEUE.delete(job);\n };\n\n registerDisposer(dispose);\n run(); // initial run is synchronous + immediate\n return dispose;\n}\n\n// ----------------------------------------------------------------------------\n// Computed\n// ----------------------------------------------------------------------------\n\n// Read-only, State-like derived value. Subscribe to it exactly like a State:\n// `c.get()` for the current value, `c.get(listener)` to be notified on change,\n// and inside an element `(l) => c.get(l)` to bind the DOM.\nexport interface Computed<T> {\n readonly _isState: true;\n // The computed's own Notifier (downstream subscriptions live here). Exposed,\n // like State._notifier, so subscription/leak inspection works uniformly.\n readonly _notifier: Notifier;\n get(listener?: ValueListener<T>): T;\n}\n\n// Lazy + cached derived value. `fn` is evaluated on first read and the result is\n// cached; it re-evaluates ONLY after a tracked dependency changes (a dirty flag),\n// never on every read. When a dependency changes, the computed recomputes and, if\n// the new value differs by `===` from the cached one, notifies its own\n// downstream listeners; an identical value short-circuits (no downstream churn).\nexport function computed<T>(fn: () => T): Computed<T> {\n // The computed publishes its own changes through a private Notifier (the same\n // machinery State uses), so anything subscribing to the computed participates\n // in the normal flush + cycle detection.\n const EVENT = \"computed\";\n const notifier = new Notifier();\n\n let cachedValue: T = undefined as unknown as T;\n let dirty = true;\n let hasValue = false;\n\n // A dependency changed: schedule a single deduplicated reaction. Marking dirty\n // is immediate (so a synchronous read after the change recomputes); the\n // observed-path recompute+notify is deferred to the drain so multiple changing\n // dependencies (and a batch) collapse into one recompute.\n const job = (): void => {\n if (!dirty) return;\n // If nothing is observing this computed, stay lazy — the next read recomputes.\n // If there ARE downstream listeners, recompute now to apply the equality\n // short-circuit and push the new value through this computed's own Notifier.\n if (notifier.listenerCount(EVENT) > 0) recomputeAndNotify();\n };\n const collector = new Collector(() => {\n if (dirty) return;\n dirty = true;\n scheduleReaction(job);\n });\n\n const recompute = (): void => {\n collector.reset();\n cachedValue = runWithCollector(collector, fn);\n dirty = false;\n hasValue = true;\n };\n\n const recomputeAndNotify = (): void => {\n const previous = cachedValue;\n const had = hasValue;\n recompute();\n // Equality short-circuit: an unchanged value must not notify downstream.\n if (had && cachedValue === previous) return;\n notifier.notify(EVENT, cachedValue);\n };\n\n const get = (listener?: ValueListener<T>): T => {\n if (listener) {\n notifier.addListener(EVENT, listener);\n } else {\n // Auto-tracking: reading a computed inside another computed/effect makes\n // the outer computation depend on this one. Reusing State's collector path\n // means a chain of computeds composes through one Notifier graph.\n const outer = activeCollector();\n if (outer) notifier.addListener(EVENT, outer.handler);\n }\n if (dirty) {\n // A dirty read while downstream listeners exist must notify them, not\n // just refresh the cache: a plain recompute() here flips `dirty` off, so\n // the queued job() becomes a no-op and already-subscribed listeners\n // (e.g. a DOM binding) would NEVER learn the value changed — any code\n // reading the computed between a dependency write and the reaction\n // drain (an untracked .get() in a state listener, or flushSync) would\n // permanently swallow the update. recomputeAndNotify keeps the equality\n // short-circuit, so an unchanged value still stays silent. The initial\n // lazy compute (hasValue === false) must NOT notify — subscribers\n // already receive the value as this call's return.\n if (hasValue && notifier.listenerCount(EVENT) > 0) recomputeAndNotify();\n else recompute();\n }\n return cachedValue;\n };\n\n const dispose = (): void => {\n collector.reset();\n REACTION_QUEUE.delete(job);\n notifier._dispose();\n };\n registerDisposer(dispose);\n\n return { _isState: true, _notifier: notifier, get } as Computed<T>;\n}\n\n// ----------------------------------------------------------------------------\n// batch / untrack\n// ----------------------------------------------------------------------------\n\n// Run `fn`, coalescing all State/RecordState/computed writes inside into a SINGLE\n// downstream flush after `fn` returns. Composes with the existing microtask flush\n// without double-flushing (see Notifier.runBatched). Returns `fn`'s result.\nexport function batch<T>(fn: () => T): T {\n return runBatched(fn);\n}\n\n// Run `fn` and return its result WITHOUT registering any reads into the currently\n// active collector. Useful to read a state inside an effect/computed without\n// making it a dependency.\nexport function untrack<T>(fn: () => T): T {\n return runUntracked(fn);\n}\n\n// ----------------------------------------------------------------------------\n// watch\n// ----------------------------------------------------------------------------\n\n// A reactive source for `watch`: a State/Computed (anything with `.get()`) or a\n// getter function. The latter composes multiple reads — `() => a.get() + b.get()`\n// — into a single watched expression.\nexport type WatchSource<T> = ReadableState<T> | (() => T);\n\nexport interface WatchOptions {\n // If true, invoke the callback immediately with the initial value (oldValue\n // will be `undefined` on that first call). Default: false.\n immediate?: boolean;\n}\n\n// Imperative watcher: tracks `source`, and whenever it produces a new value\n// (by `===` change) calls `callback(newValue, oldValue)`. The callback receives\n// both the new value and the previous one — which plain `effect` cannot provide.\n//\n// Returns a `dispose()` that stops watching and releases subscriptions.\n//\n// Examples:\n// const count = toState(0)\n// const stop = watch(count, (n, prev) => console.log(n, prev))\n// const stop2 = watch(() => a.get() + b.get(), (sum) => console.log(sum))\nexport function watch<T>(\n source: WatchSource<T>,\n callback: (newValue: T, oldValue: T | undefined) => void,\n options?: WatchOptions,\n): () => void {\n let oldValue: T | undefined = undefined;\n let firstRun = true;\n\n // `effect` runs synchronously on setup (initial collection), then re-runs\n // whenever a tracked dependency changes. We suppress the callback on the\n // first (setup) run unless `immediate` is set.\n return effect(() => {\n const newValue =\n typeof source === \"function\" ? source() : source.get();\n\n if (!firstRun || options?.immediate) {\n callback(newValue, oldValue);\n }\n\n oldValue = newValue;\n firstRun = false;\n });\n}\n\n// ----------------------------------------------------------------------------\n// nextTick\n// ----------------------------------------------------------------------------\n\n// Returns a Promise that resolves on the next microtask — after all currently\n// scheduled reactive effects/computed re-runs have been processed. Useful when\n// you need to read state or the DOM immediately AFTER a reactive update settles\n// without calling the synchronous (and potentially expensive) `flushSync()`.\n//\n// Optionally pass a callback to be invoked when the microtask fires:\n// await nextTick() // wait for reactive flush\n// nextTick(() => doSomething()) // callback style\nexport function nextTick(): Promise<void>;\nexport function nextTick(fn: () => void): Promise<void>;\nexport function nextTick(fn?: () => void): Promise<void> {\n // A resolved Promise's `.then` schedules a microtask via the same checkpoint\n // that `_microtask` uses internally, so it runs in the same microtask queue\n // position as scheduled effect re-runs — after them when called synchronously.\n return fn ? Promise.resolve().then(fn) : Promise.resolve();\n}\n","import { activeCollector } from \"./Collector.js\";\nimport { Notifier } from \"./Notifier.js\";\n\ntype Listener = (...args: any[]) => void;\n\nexport class RecordState<T extends Record<string, any> = Record<string, any>> {\n private _notifier = new Notifier();\n private _record: T;\n readonly initialRecord: T;\n\n constructor(record: T) {\n this.initialRecord = { ...record };\n this._record = { ...record };\n }\n\n get<K extends keyof T>(key: K, l?: Listener): T[K] {\n if (l) {\n this._notifier.addListener(key as string, l);\n } else {\n // Auto-tracking: with no explicit listener, subscribe the active\n // collector for THIS key so a running computed/effect re-runs only\n // when this specific key changes. With no collector active the read\n // is untracked — the original behavior is preserved exactly.\n const collector = activeCollector();\n if (collector)\n this._notifier.addListener(key as string, collector.handler);\n }\n return this._record[key];\n }\n\n set<K extends keyof T>(key: K, value: T[K]): void {\n this._record[key] = value;\n this._notifier.notify(key as string, value);\n }\n\n addListener<K extends keyof T>(key: K, fn: Listener): () => void {\n return this._notifier.addListener(key as string, fn);\n }\n\n removeListener<K extends keyof T>(key: K, fn: Listener): void {\n this._notifier.removeListener(key as string, fn);\n }\n\n reset<K extends keyof T>(key: K): void {\n this.set(key, this.initialRecord[key]);\n }\n\n _dispose(): void {\n this._notifier._dispose();\n }\n}\n","import type { ThemeInput } from \"./types.js\";\n\nconst light: ThemeInput = {\n direction: \"darken\",\n colors: {\n primary: [\n \"#ffffff\",\n \"#e3ecff\",\n \"#c6daff\",\n \"#aac8ff\",\n \"#8fb6ff\",\n \"#76a3ff\",\n \"#5f91fc\",\n \"#4a7ff4\",\n \"#386ee7\",\n \"#2a5ed7\",\n \"#1e4ec2\",\n \"#1440aa\",\n \"#0c3290\",\n \"#072674\",\n \"#041a57\",\n \"#020f38\",\n \"#010419\",\n \"#000000\",\n ],\n secondary: [\n \"#ffffff\",\n \"#fce6ea\",\n \"#faced6\",\n \"#f7b5c2\",\n \"#f29db0\",\n \"#ec859e\",\n \"#e36e8d\",\n \"#d8597d\",\n \"#ca456e\",\n \"#b93460\",\n \"#a42351\",\n \"#8e1643\",\n \"#770b36\",\n \"#5f0529\",\n \"#46031d\",\n \"#2d0210\",\n \"#130104\",\n \"#000000\",\n ],\n info: [\n \"#ffffff\",\n \"#dcf0f9\",\n \"#b7e1f6\",\n \"#90d2f1\",\n \"#6ac3eb\",\n \"#42b4e2\",\n \"#16a4d5\",\n \"#0094c4\",\n \"#0084b2\",\n \"#00739e\",\n \"#00638a\",\n \"#005476\",\n \"#004461\",\n \"#00354d\",\n \"#002638\",\n \"#001623\",\n \"#00070d\",\n \"#000000\",\n ],\n success: [\n \"#ffffff\",\n \"#e3f3dc\",\n \"#c6e8b8\",\n \"#a9dd94\",\n \"#8ed171\",\n \"#75c450\",\n \"#61b635\",\n \"#51a51f\",\n \"#429304\",\n \"#358100\",\n \"#2a7000\",\n \"#215f00\",\n \"#194d00\",\n \"#123c00\",\n \"#0b2b00\",\n \"#051a00\",\n \"#010900\",\n \"#000000\",\n ],\n warning: [\n \"#ffffff\",\n \"#ffeada\",\n \"#ffd3b3\",\n \"#ffbd8d\",\n \"#ffa96b\",\n \"#ff9853\",\n \"#ec8640\",\n \"#d77531\",\n \"#c16523\",\n \"#aa5718\",\n \"#944a0f\",\n \"#7e3d09\",\n \"#673106\",\n \"#512504\",\n \"#3b1a03\",\n \"#250e02\",\n \"#0e0401\",\n \"#000000\",\n ],\n attention: [\n \"#ffffff\",\n \"#ffeada\",\n \"#ffd3b3\",\n \"#ffbd8d\",\n \"#ffa96b\",\n \"#ff9853\",\n \"#ec8640\",\n \"#d77531\",\n \"#c16523\",\n \"#aa5718\",\n \"#944a0f\",\n \"#7e3d09\",\n \"#673106\",\n \"#512504\",\n \"#3b1a03\",\n \"#250e02\",\n \"#0e0401\",\n \"#000000\",\n ],\n error: [\n \"#ffffff\",\n \"#fce7e4\",\n \"#fbcfca\",\n \"#f8b7b0\",\n \"#f59f96\",\n \"#ef877e\",\n \"#e86f67\",\n \"#de5852\",\n \"#d3403e\",\n \"#c5282c\",\n \"#b30a1b\",\n \"#9e000b\",\n \"#860001\",\n \"#6c0000\",\n \"#510000\",\n \"#340000\",\n \"#170000\",\n \"#000000\",\n ],\n danger: [\n \"#ffffff\",\n \"#fce7e4\",\n \"#fbcfca\",\n \"#f8b7b0\",\n \"#f59f96\",\n \"#ef877e\",\n \"#e86f67\",\n \"#de5852\",\n \"#d3403e\",\n \"#c5282c\",\n \"#b30a1b\",\n \"#9e000b\",\n \"#860001\",\n \"#6c0000\",\n \"#510000\",\n \"#340000\",\n \"#170000\",\n \"#000000\",\n ],\n highlight: [\n \"#ffffff\",\n \"#f9f5cd\",\n \"#f4eb95\",\n \"#efe05a\",\n \"#e6d427\",\n \"#d3c100\",\n \"#bfad00\",\n \"#ab9b00\",\n \"#988900\",\n \"#857700\",\n \"#736600\",\n \"#615600\",\n \"#4f4600\",\n \"#3e3600\",\n \"#2c2700\",\n \"#1b1700\",\n \"#090700\",\n \"#000000\",\n ],\n neutral: [\n \"#ffffff\",\n \"#ededed\",\n \"#dbdbdb\",\n \"#cacaca\",\n \"#bababa\",\n \"#ababab\",\n \"#9b9b9b\",\n \"#8d8d8d\",\n \"#7e7e7e\",\n \"#707070\",\n \"#636363\",\n \"#565656\",\n \"#484848\",\n \"#383838\",\n \"#282828\",\n \"#181818\",\n \"#080808\",\n \"#000000\",\n ],\n },\n baseTones: {\n highlight: 5,\n warning: 6,\n attention: 6,\n error: 8,\n danger: 8,\n secondary: 8,\n primary: 9,\n info: 8,\n success: 8,\n neutral: 8,\n },\n fontSizes: [\n \"0.75rem\",\n \"0.875rem\",\n \"1rem\",\n \"1.25rem\",\n \"1.5625rem\",\n \"1.9375rem\",\n \"2.4375rem\",\n \"3.0625rem\",\n ],\n densities: [0.75, 1, 1.5, 2, 2.5],\n darkBias: 1,\n custom: {},\n};\n\nexport default light;\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport light from \"./light.js\";\nimport type { PartialThemeInput, ThemeInput, ThemeVars } from \"./types.js\";\n\n// JSON clone (not structuredClone) so the build runs in older embedded\n// browsers like SketchUp 2022's CEF, which predates Chromium 98.\n// ThemeInput is plain JSON (no Map/Set/Date/typed arrays).\nconst clone = <T>(v: T): T => JSON.parse(JSON.stringify(v));\n\n// Custom-token keys may contain CSS-illegal characters (e.g. \"radius/sm/lg\").\n// Map every illegal char to \"_\" so the declared property name and the var()\n// reference always agree and stay valid CSS.\nconst escapeKey = (k: string): string => k.replace(/[^a-zA-Z0-9_-]/g, \"_\");\n\nconst themes: Record<string, ThemeInput> = {\n light: clone(light),\n dark: createDark(light),\n};\n\n// Memo caches. themeVars() depends only on the theme STRUCTURE (color names,\n// tone steps, custom keys) — it emits `var(--…)` references, never resolved\n// values — so its result is stable until setTheme() changes that structure.\n// themeTokens() returns resolved values per theme, cached per name. Both are\n// invalidated in setTheme(). Callers must treat the returned objects as\n// read-only (they are shared).\nlet _themeVarsCache: ThemeVars | null = null;\nconst _themeTokensCache = new Map<string, Record<string, any>>();\n\nfunction colorSteps(input: ThemeInput): number {\n const firstColor = Object.keys(input.colors)[0];\n return firstColor ? input.colors[firstColor].length : 0;\n}\n\n// --- Validation ---\n\nfunction validateTheme(partial: PartialThemeInput): void {\n for (const key in partial) {\n if (!Object.keys(light).includes(key as keyof ThemeInput)) {\n throw new Error(`Invalid key: ${key}`);\n }\n }\n if (partial.fontSizes && !Array.isArray(partial.fontSizes)) {\n throw new Error(`fontSize must be array of string`);\n }\n if (partial.densities) {\n if (\n !Array.isArray(partial.densities) ||\n partial.densities.some((v) => typeof v !== \"number\")\n ) {\n throw new Error(`densities must be array of number`);\n }\n }\n if (\"custom\" in partial) {\n const custom = partial.custom!;\n if (typeof custom !== \"object\" || custom === null) {\n throw new Error(`Invalid custom property: must be an object`);\n }\n }\n if (\"colors\" in partial) {\n const colors = partial.colors!;\n const valid =\n typeof colors === \"object\" &&\n colors !== null &&\n Object.values(colors).every(\n (v) => Array.isArray(v) && v.every((c) => typeof c === \"string\"),\n );\n if (!valid) {\n throw new Error(`colors must be an object of string[]`);\n }\n }\n if (\"baseTones\" in partial) {\n const baseTones = partial.baseTones!;\n const valid =\n typeof baseTones === \"object\" &&\n baseTones !== null &&\n Object.values(baseTones).every((v) => typeof v === \"number\");\n if (!valid) {\n throw new Error(`baseTones must be an object of number`);\n }\n }\n if (\"direction\" in partial) {\n if (partial.direction !== \"lighten\" && partial.direction !== \"darken\") {\n throw new Error(`direction must be \"lighten\" or \"darken\"`);\n }\n }\n}\n\n// --- Deep Merge ---\n\nfunction deepMerge(target: any, source: any): void {\n // Guard against prototype pollution: a JSON.parse'd payload (e.g. a custom\n // theme loaded from an API response) can carry an own enumerable\n // \"__proto__\" key, which `for...in` picks up unlike object-literal syntax.\n // Must run at every recursion depth — the key can appear inside any\n // nested Record-typed field (custom, colors, baseTones), not just the top.\n for (const key of Object.keys(source)) {\n if (key === \"__proto__\" || key === \"constructor\" || key === \"prototype\") {\n continue;\n }\n if (\n source[key] &&\n typeof source[key] === \"object\" &&\n !Array.isArray(source[key])\n ) {\n target[key] ??= {};\n deepMerge(target[key], source[key]);\n } else {\n target[key] = source[key];\n }\n }\n}\n\n// --- Builders (pure functions) ---\n\nfunction buildThemeCSS(name: string, input: ThemeInput): string {\n const styles: Record<string, string | number> = {};\n const toneSteps = colorSteps(input);\n\n for (const key in input) {\n const value = input[key as keyof ThemeInput];\n\n if (key === \"colors\") {\n for (const colorName in input.colors) {\n [...Array(toneSteps).keys()].forEach(\n (i) => (styles[`--${colorName}-${i}`] = input.colors[colorName][i]),\n );\n }\n } else if (key === \"fontSizes\") {\n [...Array(8).keys()].forEach(\n (i) => (styles[`--fontSize-${i}`] = input.fontSizes[i]),\n );\n } else if (key === \"custom\") {\n if (value && typeof value === \"object\") {\n for (const k in value as Record<string, string>) {\n styles[`--custom-${escapeKey(k)}`] = (\n value as Record<string, string>\n )[k];\n }\n }\n }\n // densities / baseTones / direction / darkBias are not CSS custom properties\n }\n\n let text = \"\";\n for (const prop in styles) {\n text += ` ${prop}: ${styles[prop]};\\n`;\n }\n return `[data-theme=\"${name}\"] {\\n${text}}`;\n}\n\n// --- Public API ---\n\nexport function getTheme(name: string): ThemeInput {\n if (!themes[name]) throw Error(`Theme \"${name}\" not found`);\n return themes[name];\n}\n\nexport function setTheme(name: string, input: PartialThemeInput): void {\n validateTheme(input);\n if (!themes[name]) themes[name] = clone(light);\n deepMerge(themes[name], input);\n // Structure/values may have changed → drop memoized derivations.\n _themeVarsCache = null;\n _themeTokensCache.clear();\n}\n\nfunction createDark(source: ThemeInput): ThemeInput {\n const dark = clone(source);\n dark.direction = \"lighten\";\n for (const name in dark.colors) {\n dark.colors[name].reverse();\n dark.baseTones[name] = dark.colors[name].length - 1 - dark.baseTones[name];\n }\n return dark;\n}\n\nexport function themeTokens(name: string): Record<string, any> {\n const cached = _themeTokensCache.get(name);\n if (cached) return cached;\n const input = getTheme(name);\n const toneSteps = colorSteps(input);\n const tokens: Record<string, any> = {};\n\n for (const key in input) {\n const value = input[key as keyof ThemeInput];\n\n if (key === \"colors\") {\n for (const name in input.colors) {\n const colorTones = {} as Partial<Record<number, string>>;\n [...Array(toneSteps).keys()].forEach(\n (i) => (colorTones[i] = input.colors[name][i]),\n );\n tokens[name] = colorTones as Record<number, string>;\n }\n } else if (key === \"fontSizes\") {\n tokens.fontSizes = input.fontSizes;\n } else if (key === \"densities\") {\n tokens.densities = input.densities;\n } else if (key === \"custom\") {\n tokens.custom = {};\n if (value && typeof value === \"object\") {\n for (const k in value as Record<string, string>) {\n tokens.custom[k] = (value as Record<string, string>)[k];\n }\n }\n }\n // baseTones / direction / darkBias are metadata — reachable via getTheme(), not tokens\n }\n\n _themeTokensCache.set(name, tokens);\n return tokens;\n}\n\nexport function themeVars(): ThemeVars {\n if (_themeVarsCache) return _themeVarsCache;\n const input = getTheme(\"light\");\n const toneSteps = colorSteps(input);\n const theme = {} as ThemeVars;\n\n for (const key in input) {\n const value = input[key as keyof ThemeInput];\n\n if (key === \"colors\") {\n for (const name in input.colors) {\n const colorTones = {} as Partial<Record<number, string>>;\n [...Array(toneSteps).keys()].forEach(\n (i) => (colorTones[i] = `var(--${name}-${i})`),\n );\n theme[name] = colorTones as Record<number, string>;\n }\n } else if (key === \"fontSizes\") {\n theme.fontSizes = [...Array(8).keys()].map((i) => `var(--fontSize-${i})`);\n } else if (key === \"custom\") {\n theme.custom = {} as Record<string, string>;\n if (value && typeof value === \"object\") {\n for (const k in value as Record<string, string>) {\n theme.custom[k] = `var(--custom-${escapeKey(k)})`;\n }\n }\n }\n // densities / baseTones / direction / darkBias are not exposed as CSS vars\n }\n\n _themeVarsCache = theme;\n return theme;\n}\n\nexport function themeCSS(): string {\n return Object.entries(themes)\n .map(([name, input]) => buildThemeCSS(name, input))\n .join(\"\\n\");\n}\n\nexport function themeApply(el?: HTMLStyleElement): void {\n if (typeof document === \"undefined\") return;\n if (el) {\n el.textContent = themeCSS();\n return;\n } else {\n el =\n (document.getElementById(\"domphy-themes\") as HTMLStyleElement) ??\n Object.assign(document.createElement(\"style\"), { id: \"domphy-themes\" });\n el.textContent = themeCSS();\n document.head.appendChild(el);\n }\n}\n\nexport function themeSpacing(n: number) {\n return `calc(${n / 4}em)`;\n}\n\n// Fluid spacing using CSS clamp(). Returns a value that scales linearly\n// between themeSpacing(min) and themeSpacing(max) across a viewport width\n// range (default 320px → 1280px). Use for structural spacing that should\n// grow with the viewport — not for bounded-control padding (use density for that).\n//\n// Example: themeFluidSpacing(4, 16) → \"clamp(1em, 0.3125vw, 4em)\"\n// (1em at 320px viewport, 4em at 1280px, scales linearly between)\nexport function themeFluidSpacing(\n min: number,\n max: number,\n viewportMin = 320,\n viewportMax = 1280,\n): string {\n const minEm = min / 4;\n const maxEm = max / 4;\n const slope = ((maxEm - minEm) / (viewportMax - viewportMin)) * 100;\n const intercept = minEm - (slope * viewportMin) / 100;\n const interceptRounded = parseFloat(intercept.toFixed(4));\n const preferred =\n interceptRounded === 0\n ? `${slope.toFixed(4)}vw`\n : `${intercept.toFixed(4)}em + ${slope.toFixed(4)}vw`;\n return `clamp(${minEm}em, ${preferred}, ${maxEm}em)`;\n}\n\n// System theme detection helper. Reads window.matchMedia and/or a saved\n// localStorage preference, sets data-theme on targetEl (default: <html>),\n// then listens for OS-level changes. Returns a cleanup function.\n//\n// Usage:\n// const cleanup = applySystemTheme() // one-liner on client startup\n// const cleanup = applySystemTheme(document.documentElement, { storageKey: \"my-theme\" })\n//\n// When the user manually changes the theme, call:\n// localStorage.setItem(storageKey, \"dark\") // applySystemTheme will honour it on reload\n// element.setAttribute(\"data-theme\", \"dark\") // update DOM immediately\n//\n// For SSR: call only on the client (typeof window !== \"undefined\").\nexport function applySystemTheme(\n targetEl: Element = document.documentElement,\n options: {\n /** Persist the resolved theme in localStorage so it survives reloads. Default: true. */\n persist?: boolean;\n /** localStorage key. Default: \"dp-theme\". */\n storageKey?: string;\n } = {},\n): () => void {\n const { persist = true, storageKey = \"dp-theme\" } = options;\n\n const resolve = (): \"light\" | \"dark\" => {\n if (persist) {\n const saved = localStorage.getItem(storageKey);\n if (saved === \"light\" || saved === \"dark\") return saved;\n }\n return window.matchMedia(\"(prefers-color-scheme: dark)\").matches\n ? \"dark\"\n : \"light\";\n };\n\n targetEl.setAttribute(\"data-theme\", resolve());\n\n const mql = window.matchMedia(\"(prefers-color-scheme: dark)\");\n const handler = (event: MediaQueryListEvent) => {\n // Only follow the OS change when there is no user-saved preference.\n if (!persist || !localStorage.getItem(storageKey)) {\n targetEl.setAttribute(\"data-theme\", event.matches ? \"dark\" : \"light\");\n }\n };\n mql.addEventListener(\"change\", handler);\n\n return () => mql.removeEventListener(\"change\", handler);\n}\n\nexport function themeName(object: ElementNode | Listener) {\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataTheme\"))) {\n node = node.parent as ElementNode;\n }\n\n let themeName = \"light\";\n\n if (node && node.attributes && node.attributes.has(\"dataTheme\")) {\n themeName = node.attributes.get(\"dataTheme\");\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataTheme\", object);\n }\n return themeName;\n}\n\n// The 10 semantic roles every built-in theme (light/dark) ships — single source\n// of truth for both the runtime list (icons, docs demos, e.g. ThemeBuilder's\n// color-picker sidebar) and the ColorRole type below. `ThemeInput.colors` stays\n// a plain string-indexed record (custom themes may register their own role\n// names via setTheme/generateTheme), so this is deliberately NOT presented as\n// an exhaustive runtime constraint anywhere it's consumed.\nexport const COLOR_ROLES = [\n \"neutral\",\n \"primary\",\n \"secondary\",\n \"info\",\n \"success\",\n \"warning\",\n \"attention\",\n \"error\",\n \"danger\",\n \"highlight\",\n] as const;\n\nexport type ColorRole = (typeof COLOR_ROLES)[number];\n\n// `ColorRole | (string & {})` — NOT plain `string` and NOT a strict `ColorRole`\n// union. `ThemeInput.colors` being a generic Record (see above) means a strict\n// union would reject valid custom-role code. But every prior version of this\n// type (`keyof ThemeInput[\"colors\"]`, which TS widens to plain `string` for a\n// generic Record) gave editors/AI codegen ZERO signal about the 10 built-in\n// role names — a typo'd role (e.g. \"accent\", not a real role) type-checked fine\n// and only surfaced as an unhandled runtime throw from themeColor(). The\n// `string & {}` branch preserves full acceptance of arbitrary custom-role\n// strings while `ColorRole` still ranks first in autocomplete/hover — this is\n// the standard \"loose autocomplete\" pattern (TS does not support \"reject unknown\n// literals but allow an explicit escape hatch\" any more precisely than this).\nexport type ThemeColor = ColorRole | (string & {});\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport { getTheme, themeName } from \"./theme.js\";\n\nconst ElementDensities = [\"inherit\"];\n\n[...Array(5).keys()].forEach((i) => {\n ElementDensities.push(`decrease-${i}`);\n ElementDensities.push(`increase-${i}`);\n});\n\nexport type ElementDensity = (typeof ElementDensities)[number];\n\nfunction offsetDensity(\n origin: number,\n density: ElementDensity = \"inherit\",\n): number {\n if (!ElementDensities.includes(density!)) {\n throw Error(`density name \"${density}\" invalid`);\n }\n let resultDensity: number;\n if (density === \"inherit\") {\n resultDensity = origin as number;\n } else if (density?.startsWith(\"increase-\")) {\n const offset = parseInt(density.replace(\"increase-\", \"\"), 10);\n resultDensity = origin + offset;\n } else if (density?.startsWith(\"decrease-\")) {\n const offset = parseInt(density.replace(\"decrease-\", \"\"), 10);\n resultDensity = origin - offset;\n } else {\n resultDensity = origin;\n }\n return Math.max(0, Math.min(4, resultDensity));\n}\n\nfunction contextDensity(object: ElementNode | Listener | null): number {\n if (!object) return 2;\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataDensity\"))) {\n node = node.parent as ElementNode;\n }\n\n let density = 2;\n\n if (node && node.attributes && node.attributes.has(\"dataDensity\")) {\n density = offsetDensity(density, node.attributes.get(\"dataDensity\"));\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataDensity\", object);\n }\n return density;\n}\n\nexport function themeDensity(object: ElementNode | Listener | null): number {\n const index = contextDensity(object);\n return getTheme(object ? themeName(object) : \"light\").densities[index];\n}\n","import { calcDeltaE2000, generateRamp, hexToRgb, rgbToLab } from \"@domphy/palette\";\nimport type { PartialThemeInput, ThemeInput } from \"./types.js\";\n\nexport type GenerateThemeOptions = {\n /** Ramp length. Must match `@domphy/theme`'s tone scale (18 steps: shift-0..shift-17). */\n steps?: number;\n direction?: ThemeInput[\"direction\"];\n fontSizes?: string[];\n densities?: number[];\n darkBias?: number;\n custom?: Record<string, string | number>;\n};\n\nconst DEFAULT_FONT_SIZES = [\n \"0.75rem\",\n \"0.875rem\",\n \"1rem\",\n \"1.25rem\",\n \"1.5625rem\",\n \"1.9375rem\",\n \"2.4375rem\",\n \"3.0625rem\",\n];\nconst DEFAULT_DENSITIES = [0.75, 1, 1.5, 2, 2.5];\n\n// The step whose color is perceptually closest (CIEDE2000) to the caller's\n// original base color — the ramp's \"base tone\" is not always the mathematical\n// center, since the warp curve does not distribute steps symmetrically.\nfunction nearestStepIndex(ramp: string[], baseHex: string): number {\n const baseLab = rgbToLab(hexToRgb(baseHex));\n let best = 0;\n let bestDist = Infinity;\n for (let i = 0; i < ramp.length; i++) {\n const dist = calcDeltaE2000(baseLab, rgbToLab(hexToRgb(ramp[i])));\n if (dist < bestDist) {\n bestDist = dist;\n best = i;\n }\n }\n return best;\n}\n\n/**\n * Generate a complete `ThemeInput` from one base hex color per semantic role,\n * using `@domphy/palette`'s `generateRamp` (Oklab, WCAG-span-optimized) for\n * every color family. Each family's `baseTones` entry is the step nearest\n * (CIEDE2000) to the caller's original input, so `themeColor(l, \"base\", name)`\n * still resolves to (approximately) the exact brand color that was passed in.\n *\n * ```ts\n * const theme = generateTheme({\n * primary: \"#4a7ff4\",\n * secondary: \"#d8597d\",\n * neutral: \"#8d8d8d\",\n * })\n * ```\n *\n * Roles not passed are simply absent from the result — merge with an existing\n * `ThemeInput`/`PartialThemeInput` (e.g. spread over `light` from\n * `@domphy/theme`) to fill in the rest.\n */\nexport function generateTheme(\n baseColors: Record<string, string>,\n options: GenerateThemeOptions = {},\n): PartialThemeInput {\n const steps = options.steps ?? 18;\n const colors: Record<string, string[]> = {};\n const baseTones: Record<string, number> = {};\n\n for (const [name, hex] of Object.entries(baseColors)) {\n const ramp = generateRamp(hex, steps);\n colors[name] = ramp;\n baseTones[name] = nearestStepIndex(ramp, hex);\n }\n\n return {\n direction: options.direction ?? \"darken\",\n colors,\n baseTones,\n fontSizes: options.fontSizes ?? DEFAULT_FONT_SIZES,\n densities: options.densities ?? DEFAULT_DENSITIES,\n darkBias: options.darkBias ?? 1,\n custom: options.custom ?? {},\n };\n}\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport { themeVars } from \"./theme.js\";\n\nconst ElementSizes = [\"inherit\"];\n\n[...Array(8).keys()].forEach((i) => {\n ElementSizes.push(`decrease-${i}`);\n ElementSizes.push(`increase-${i}`);\n});\n\nexport type ElementSize = (typeof ElementSizes)[number];\n\nfunction offsetSize(origin: number, size: ElementSize = \"inherit\"): number {\n if (!ElementSizes.includes(size!)) {\n throw Error(`size name \"${size}\" invalid`);\n }\n let resultSize: number;\n if (size === \"inherit\") {\n resultSize = origin as number;\n } else if (size?.startsWith(\"increase-\")) {\n const offset = parseInt(size.replace(\"increase-\", \"\"), 10);\n resultSize = origin + offset;\n } else if (size?.startsWith(\"decrease-\")) {\n const offset = parseInt(size.replace(\"decrease-\", \"\"), 10);\n resultSize = origin - offset;\n } else {\n resultSize = origin;\n }\n return Math.max(0, Math.min(7, resultSize));\n}\n\nfunction contextSize(object: ElementNode | Listener | null): number {\n if (!object) return 2;\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataSize\"))) {\n node = node.parent as ElementNode;\n }\n\n let size = 2;\n\n if (node && node.attributes && node.attributes.has(\"dataSize\")) {\n size = offsetSize(size, node.attributes.get(\"dataSize\"));\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataSize\", object);\n }\n return size;\n}\n\nexport function themeSize(\n object: ElementNode | Listener,\n size: ElementSize = \"inherit\",\n): string {\n const index = offsetSize(contextSize(object), size);\n return themeVars().fontSizes[index];\n}\n","import type { ElementNode, Listener } from \"@domphy/core\";\nimport light from \"./light.js\";\nimport { getTheme, themeName, themeTokens, themeVars } from \"./theme.js\";\n\nconst TONE_STEPS = light.colors.neutral.length;\n\n// Semantic tone aliases, resolved through the shift-N machinery below so they\n// stay context-aware (dataTone) and correct in both light and dark themes.\n// Mapping derived from stock @domphy/ui patch usage (packages/ui/src/patches)\n// and cross-checked against consumer usage frequency:\n// surface -> shift-1 subtle raised background (e.g. inputFile drop zone)\n// hover -> shift-2 hover/active background (e.g. button, menu, list)\n// border -> shift-3 subtle hairline divider (e.g. card footer separator)\n// border-strong -> shift-4 control outline (e.g. button, input, card boundary)\n// muted -> shift-8 secondary/disabled text\n// text -> shift-9 default/primary text\nconst ToneAliases: Record<string, string> = {\n surface: \"shift-1\",\n hover: \"shift-2\",\n border: \"shift-3\",\n \"border-strong\": \"shift-4\",\n muted: \"shift-8\",\n text: \"shift-9\",\n};\n\n// Exported as a value (not just a type) so tooling — @domphy/doctor, the MCP\n// server, generated `tones.json` — can validate tone names without parsing TS.\nexport const ElementTones = [\"inherit\", \"base\", ...Object.keys(ToneAliases)];\n\n[...Array(TONE_STEPS).keys()].forEach((i) => {\n ElementTones.push(`decrease-${i}`);\n ElementTones.push(`increase-${i}`);\n ElementTones.push(`shift-${i}`);\n});\n\nexport type ElementTone = (typeof ElementTones)[number];\n\nfunction adjustTone(tone: number, level: number): number {\n if (tone < 0 || tone > TONE_STEPS - 1) return tone;\n let newIndex = tone + level;\n newIndex = Math.max(0, Math.min(TONE_STEPS - 1, newIndex));\n return newIndex;\n}\n\nfunction shiftTone(tone: number, level: number): number {\n if (tone < 0 || tone > TONE_STEPS - 1) return tone;\n const midpoint = Math.floor((TONE_STEPS - 1) / 2);\n let newIndex = tone <= midpoint ? tone + level : tone - level;\n // Clamp overshoot to the near boundary. (Negating an out-of-range index, as\n // a prior version did, flips it to the opposite extreme — e.g. shift past\n // the dark end would land on the lightest tone.)\n newIndex = Math.max(0, Math.min(TONE_STEPS - 1, newIndex));\n return newIndex;\n}\n\nfunction offsetTone(originTone: number, tone: ElementTone = \"inherit\"): number {\n if (typeof tone === \"number\") return tone;\n\n if (tone === \"inherit\") return originTone;\n\n if (!ElementTones.includes(tone!)) {\n throw Error(`tone name \"${tone}\" invalid`);\n }\n\n if (tone in ToneAliases) {\n tone = ToneAliases[tone];\n }\n\n if (tone.startsWith(\"increase-\")) {\n const offset = parseInt(tone.replace(\"increase-\", \"\"), 10);\n return adjustTone(originTone, offset);\n } else if (tone.startsWith(\"decrease-\")) {\n const offset = parseInt(tone.replace(\"decrease-\", \"\"), 10);\n return adjustTone(originTone, -offset);\n } else if (tone.startsWith(\"shift-\")) {\n const offset = parseInt(tone.replace(\"shift-\", \"\"), 10);\n return shiftTone(originTone, offset);\n } else {\n return originTone;\n }\n}\n\nfunction contextTone(object: ElementNode | Listener | null): number {\n if (!object) return 0;\n const elementNode = (\n typeof object === \"function\" ? object.elementNode : object\n ) as ElementNode;\n let node: ElementNode = elementNode;\n while (node && (!node.attributes || !node.attributes.get(\"dataTone\"))) {\n node = node.parent as ElementNode;\n }\n\n let tone = 0;\n\n if (node && node.attributes && node.attributes.has(\"dataTone\")) {\n tone = offsetTone(tone, node.attributes.get(\"dataTone\"));\n typeof object === \"function\" &&\n node.attributes.addListener(\"dataTone\", object);\n }\n return tone;\n}\n\nfunction _themeTone(\n object: ElementNode | Listener,\n tone: ElementTone = \"inherit\",\n): number {\n return offsetTone(contextTone(object), tone);\n}\n\nfunction biasContext(context: number, direction: string, bias: number): number {\n if (bias <= 0) return context;\n if (direction === \"lighten\" && context === 0) return bias;\n if (direction === \"darken\" && context === TONE_STEPS - 1)\n return TONE_STEPS - 1 - bias;\n return context;\n}\n\nexport function themeColor(\n object: ElementNode | Listener | null,\n tone: ElementTone = \"inherit\",\n color: string = \"inherit\",\n): string {\n const themeColor = color === \"inherit\" ? \"neutral\" : color;\n\n if (!object) {\n // No node context implies the light theme (themeVars reads getTheme(\"light\")).\n const colors = themeVars()[themeColor];\n if (!colors) {\n throw Error(`color \"${themeColor}\" not found on theme \"light\"`);\n }\n if (tone === \"base\") return colors[getTheme(\"light\").baseTones[themeColor]];\n return colors[offsetTone(0, tone)];\n }\n\n const name = themeName(object);\n let resultTone: number;\n if (tone === \"base\") {\n resultTone = getTheme(name).baseTones[themeColor];\n } else {\n const theme = getTheme(name);\n const context = biasContext(\n contextTone(object),\n theme.direction,\n theme.darkBias,\n );\n resultTone = offsetTone(context, tone);\n }\n const colors = themeVars()[themeColor];\n if (!colors) {\n throw Error(`color \"${themeColor}\" not found on theme \"${name}\"`);\n }\n const resultColor = colors[resultTone];\n\n return resultColor;\n}\n\nexport function themeColorToken(\n object: ElementNode | Listener | null,\n tone: ElementTone = \"inherit\",\n color: string = \"inherit\",\n): string {\n const colorName = color === \"inherit\" ? \"neutral\" : color;\n const name = object ? themeName(object as ElementNode | Listener) : \"light\";\n const tokens = themeTokens(name);\n const colorTokens = tokens[colorName];\n if (!colorTokens) {\n throw Error(`color \"${colorName}\" not found on theme \"${name}\"`);\n }\n\n if (!object) {\n if (tone === \"base\")\n return colorTokens[getTheme(\"light\").baseTones[colorName]];\n return colorTokens[offsetTone(0, tone)];\n }\n\n let resultTone: number;\n if (tone === \"base\") {\n resultTone = getTheme(name).baseTones[colorName];\n } else {\n const theme = getTheme(name);\n const context = biasContext(\n contextTone(object),\n theme.direction,\n theme.darkBias,\n );\n resultTone = offsetTone(context, tone);\n }\n\n return colorTokens[resultTone];\n}\n","/** Gamma-encode linear RGB (0-1) to 8-bit sRGB channels (0-255). */\nconst lrgbToSrgb = (rgb: number[]) => {\n const toSRGB = (c: number) => {\n const clamped = Math.max(0, Math.min(1, c));\n const s = clamped <= 0.0031308 ? 12.92 * clamped : 1.055 * Math.pow(clamped, 1 / 2.4) - 0.055;\n return Math.max(0, Math.min(255, Math.round(s * 255)));\n };\n return rgb.map(toSRGB);\n}\n\nconst srgbToLrgb = (rgb: number[]) => {\n const toLRGB = (c: number) => (c > 0.04045 ? Math.pow((c + 0.055) / 1.055, 2.4) : c / 12.92);\n return rgb.map(toLRGB);\n}\n\n/** Convert linear RGB to sRGB Hex string. */\nexport const rgbToHex = (rgb: number[]): string => {\n\n let [r, g, b] = lrgbToSrgb(rgb) as any[]\n r = r.toString(16).padStart(2, \"0\");\n g = g.toString(16).padStart(2, \"0\");\n b = b.toString(16).padStart(2, \"0\");\n return `#${r}${g}${b}`;\n};\n\n/** Convert sRGB Hex string to linear RGB. */\nexport const hexToRgb = (hex: string): number[] => {\n const r = parseInt(hex.slice(1, 3), 16) / 255;\n const g = parseInt(hex.slice(3, 5), 16) / 255;\n const b = parseInt(hex.slice(5, 7), 16) / 255;\n\n return srgbToLrgb([r, g, b])\n};\n\n/** Converts linear RGB to Oklab color space. */\n/** Specification: Björn Ottosson (2020). */\nexport const rgbToOklab = (rgb: number[]): number[] => {\n const l = 0.4122214708 * rgb[0] + 0.5363325363 * rgb[1] + 0.0514459929 * rgb[2];\n const m = 0.2119034982 * rgb[0] + 0.6806995451 * rgb[1] + 0.1073969566 * rgb[2];\n const s = 0.0883024619 * rgb[0] + 0.2817188376 * rgb[1] + 0.6299787005 * rgb[2];\n const l_ = Math.cbrt(l), m_ = Math.cbrt(m), s_ = Math.cbrt(s);\n return [\n 0.2104542553 * l_ + 0.793617785 * m_ - 0.0040720468 * s_,\n 1.9779984951 * l_ - 2.428592205 * m_ + 0.4505937099 * s_,\n 0.0259040371 * l_ + 0.7827717662 * m_ - 0.808675766 * s_\n ];\n};\n\n/** Converts Oklab color space to linear RGB. */\n/** Specification: Björn Ottosson (2020). */\nexport const oklabToRgb = (lab: number[]): number[] => {\n const [L, a, b] = lab;\n const l_ = L + 0.3963377774 * a + 0.2158037573 * b;\n const m_ = L - 0.1055613458 * a - 0.0638541728 * b;\n const s_ = L - 0.0894841775 * a - 1.291485548 * b;\n const l = l_ * l_ * l_, m = m_ * m_ * m_, s = s_ * s_ * s_;\n return [\n 4.0767416621 * l - 3.3077115913 * m + 0.2309699292 * s,\n -1.2684380046 * l + 2.6097574011 * m - 0.3413193965 * s,\n -0.0041960863 * l - 0.7034186147 * m + 1.707614701 * s\n ];\n};\n\n/** Calculate Equivalent Achromatic Lightness (L_EAL) using High et al. (2023). */\nexport const toLightnessEAL = (lab: number[]): number => {\n const [L, a, b] = lab;\n const C = Math.sqrt(a * a + b * b);\n const hRad = Math.atan2(b, a);\n const hDeg = (hRad * 180 / Math.PI + 360) % 360;\n\n const k1 = 0.1644, k2 = 0.0603, k3 = 0.1307, k4 = 0.0060;\n const fBYh = k1 * Math.abs(Math.sin(((hDeg - 90) / 2) * (Math.PI / 180))) + k2;\n\n let fRh = 0;\n if (hDeg <= 90 || hDeg >= 270) {\n fRh = k3 * Math.abs(Math.cos(hDeg * (Math.PI / 180))) + k4;\n }\n return L + (fBYh + fRh) * C;\n};\n\n/** Reverse L_EAL to get CIELAB Lightness (L). */\nexport const fromLightnessEAL = (brightness: number, lab: number[]): number => {\n const [, a, b] = lab;\n const C = Math.sqrt(a * a + b * b);\n const hRad = Math.atan2(b, a);\n const hDeg = (hRad * 180 / Math.PI + 360) % 360;\n\n const k1 = 0.1644, k2 = 0.0603, k3 = 0.1307, k4 = 0.0060;\n const fBYh = k1 * Math.abs(Math.sin(((hDeg - 90) / 2) * (Math.PI / 180))) + k2;\n\n let fRh = 0;\n if (hDeg <= 90 || hDeg >= 270) {\n fRh = k3 * Math.abs(Math.cos(hDeg * (Math.PI / 180))) + k4;\n }\n return Math.max(0, brightness - (fBYh + fRh) * C);\n};\n\n\n/** Convert LCH to CIELAB coordinates. */\nexport const lchToLab = (lch: number[]): number[] => {\n const [L, C, h] = lch;\n const hRad = (h * Math.PI) / 180;\n return [L, C * Math.cos(hRad), C * Math.sin(hRad)];\n};\n\n/** Convert linear sRGB to CIELAB (D65) */\nexport const rgbToLab = (rgb: number[]): number[] => {\n const [r, g, b] = rgb;\n\n // sRGB → XYZ (D65)\n const x = 0.4124564 * r + 0.3575761 * g + 0.1804375 * b;\n const y = 0.2126729 * r + 0.7151522 * g + 0.0721750 * b;\n const z = 0.0193339 * r + 0.1191920 * g + 0.9503041 * b;\n\n // D65 reference white\n const Xn = 0.95047;\n const Yn = 1.00000;\n const Zn = 1.08883;\n\n const f = (t: number) =>\n t > 0.008856 ? Math.cbrt(t) : (7.787 * t + 16 / 116);\n\n const fx = f(x / Xn);\n const fy = f(y / Yn);\n const fz = f(z / Zn);\n\n return [\n 116 * fy - 16,\n 500 * (fx - fy),\n 200 * (fy - fz),\n ];\n};\n\n/** Convert CIELAB (D65) to linear sRGB */\nexport const labToRgb = (lab: number[]): number[] => {\n const [L, a, b] = lab;\n\n const fy = (L + 16) / 116;\n const fx = a / 500 + fy;\n const fz = fy - b / 200;\n\n const fInv = (t: number) =>\n t ** 3 > 0.008856 ? t ** 3 : (t - 16 / 116) / 7.787;\n\n // D65 reference white\n const Xn = 0.95047;\n const Yn = 1.00000;\n const Zn = 1.08883;\n\n const x = fInv(fx) * Xn;\n const y = fInv(fy) * Yn;\n const z = fInv(fz) * Zn;\n\n // XYZ (D65) → sRGB\n return [\n 3.2404542 * x - 1.5371385 * y - 0.4985314 * z,\n -0.9692660 * x + 1.8760108 * y + 0.0415560 * z,\n 0.0556434 * x - 0.2040259 * y + 1.0572252 * z,\n ];\n};\n\n/** Convert CIELAB to LCH coordinates. */\nexport const labToLch = (lab: number[]): number[] => {\n const [L, a, b] = lab;\n const C = Math.sqrt(a * a + b * b);\n if (C < 0.0001) return [L, 0, 0];\n\n const hRad = Math.atan2(b, a);\n let hDeg = (hRad * 180 / Math.PI + 360) % 360;\n if (hDeg >= 359.9999) hDeg = 0;\n\n return [L, C, hDeg];\n};\n/** Calculate color difference using CIEDE2000 formula. */\nexport const calcDeltaE2000 = (lab1: number[], lab2: number[]): number => {\n const [L1, a1, b1] = lab1, [L2, a2, b2] = lab2;\n const avgL = (L1 + L2) / 2;\n const C1 = Math.sqrt(a1 * a1 + b1 * b1), C2 = Math.sqrt(a2 * a2 + b2 * b2);\n const avgC = (C1 + C2) / 2;\n const G = 0.5 * (1 - Math.sqrt(Math.pow(avgC, 7) / (Math.pow(avgC, 7) + Math.pow(25, 7))));\n const a1p = a1 * (1 + G), a2p = a2 * (1 + G);\n const C1p = Math.sqrt(a1p * a1p + b1 * b1), C2p = Math.sqrt(a2p * a2p + b2 * b2);\n const avgCp = (C1p + C2p) / 2;\n const h1p = Math.atan2(b1, a1p) * 180 / Math.PI + (Math.atan2(b1, a1p) < 0 ? 360 : 0);\n const h2p = Math.atan2(b2, a2p) * 180 / Math.PI + (Math.atan2(b2, a2p) < 0 ? 360 : 0);\n let dhp = h2p - h1p;\n if (Math.abs(dhp) > 180) dhp += (h2p <= h1p ? 360 : -360);\n const avgHp = Math.abs(h1p - h2p) > 180 ? (h1p + h2p + 360) / 2 : (h1p + h2p) / 2;\n const T = 1 - 0.17 * Math.cos((avgHp - 30) * Math.PI / 180) + 0.24 * Math.cos(2 * avgHp * Math.PI / 180) + 0.32 * Math.cos((3 * avgHp + 6) * Math.PI / 180) - 0.2 * Math.cos((4 * avgHp - 63) * Math.PI / 180);\n const dLp = L2 - L1, dCp = C2p - C1p;\n const dHp = 2 * Math.sqrt(C1p * C2p) * Math.sin(dhp / 2 * Math.PI / 180);\n const SL = 1 + (0.015 * Math.pow(avgL - 50, 2)) / Math.sqrt(20 + Math.pow(avgL - 50, 2));\n const SC = 1 + 0.045 * avgCp, SH = 1 + 0.015 * avgCp * T;\n const dtheta = 30 * Math.exp(-Math.pow((avgHp - 275) / 25, 2));\n const RC = 2 * Math.sqrt(Math.pow(avgCp, 7) / (Math.pow(avgCp, 7) + Math.pow(25, 7)));\n const RT = -RC * Math.sin(2 * dtheta * Math.PI / 180);\n return Math.sqrt(Math.pow(dLp / SL, 2) + Math.pow(dCp / SC, 2) + Math.pow(dHp / SH, 2) + RT * (dCp / SC) * (dHp / SH));\n};\n\n/** Convert CSS rgb() string to linear RGB. */\nexport const cssRgbToRgb = (css: string): number[] => {\n const m = css.match(/\\d+(\\.\\d+)?/g);\n if (!m || m.length < 3) throw new Error(\"Invalid CSS rgb()\");\n\n const toLinear = (c: number) => {\n const v = c / 255;\n return v <= 0.04045 ? v / 12.92 : Math.pow((v + 0.055) / 1.055, 2.4);\n };\n return [toLinear(Number(m[0])), toLinear(Number(m[1])), toLinear(Number(m[2]))];\n};\n\n\n\n/**\n * Create a Monotone Cubic Hermite Interpolator.\n * Ensures monotonicity is preserved between points.\n * Fritsch, F. N., & Carlson, R. E. (1980). Monotone piecewise cubic interpolation. *SIAM Journal on Numerical Analysis*, 17(2), 238–246.\n */\n\nexport const createMonotone = (points: number[][]) => {\n if (points.length < 1) return (_t: number) => 0;\n\n const sorted = [...points].sort((a, b) => a[0] - b[0]);\n const uniquePoints: number[][] = [];\n\n for (let i = 0; i < sorted.length; i++) {\n if (i === 0 || sorted[i][0] !== sorted[i - 1][0]) {\n uniquePoints.push(sorted[i]);\n }\n }\n\n const n = uniquePoints.length;\n if (n === 1) return (_t: number) => uniquePoints[0][1];\n\n const x = uniquePoints.map(p => p[0]);\n const y = uniquePoints.map(p => p[1]);\n const h: number[] = [];\n const secants: number[] = [];\n\n for (let i = 0; i < n - 1; i++) {\n h[i] = x[i + 1] - x[i];\n secants[i] = (y[i + 1] - y[i]) / h[i];\n }\n\n const m: number[] = new Array(n);\n m[0] = secants[0];\n m[n - 1] = secants[n - 2];\n\n for (let i = 1; i < n - 1; i++) {\n const d0 = secants[i - 1];\n const d1 = secants[i];\n if (d0 * d1 <= 0) {\n m[i] = 0;\n } else {\n const alpha = (1 + h[i] / (h[i - 1] + h[i])) / 3;\n m[i] = (d0 * d1) / ((1 - alpha) * d0 + alpha * d1);\n }\n }\n\n return (t: number): number => {\n if (t <= x[0]) return y[0];\n if (t >= x[n - 1]) return y[n - 1];\n\n let low = 0;\n let high = n - 2;\n let i = 0;\n while (low <= high) {\n const mid = Math.floor((low + high) / 2);\n if (t >= x[mid] && t <= x[mid + 1]) {\n i = mid;\n break;\n }\n if (t < x[mid]) high = mid - 1;\n else low = mid + 1;\n }\n\n const dx = h[i];\n const s = (t - x[i]) / dx;\n const s2 = s * s;\n const s3 = s2 * s;\n const m0 = m[i] * dx;\n const m1 = m[i + 1] * dx;\n\n return (2 * s3 - 3 * s2 + 1) * y[i] +\n (s3 - 2 * s2 + s) * m0 +\n (-2 * s3 + 3 * s2) * y[i + 1] +\n (s3 - s2) * m1;\n };\n};\n\n/** Calculate Root Mean Square (RMS) of an array. */\nexport function rootMeanSquare(values: number[]): number {\n const n = values.length;\n if (n === 0) return 0;\n\n let sumSq = 0;\n for (let i = 0; i < n; i++) {\n sumSq += values[i] * values[i];\n }\n return Math.sqrt(sumSq / n);\n}\n\n/** Calculate min, max, and average of an array. */\nexport const calcStatistics = (array: number[]) => {\n const n = array.length;\n if (n === 0) return { min: 0, max: 0, avg: 0 };\n\n let min = array[0];\n let max = array[0];\n let sum = 0;\n\n for (let i = 0; i < n; i++) {\n const v = array[i];\n if (v < min) min = v;\n if (v > max) max = v;\n sum += v;\n }\n\n return { min, max, avg: sum / n };\n};\n\n/** Calculate geometric mean score (0-100) from metrics. */\nexport const calcScore = (metrics: number[]): number => {\n const n = metrics.length;\n if (n === 0) return 0;\n\n const eps = 1e-6;\n const product = metrics.reduce((acc, score) => acc * (score + eps), 1);\n const globalScore = Math.pow(product, 1 / n);\n const result = Math.max(0, Math.min(1, globalScore));\n return parseFloat((result * 100).toFixed(2));\n};\n\n/**\n * Compute WCAG 2.1 contrast ratio between two hex colors.\n * Returns a value >= 1. Passes WCAG AA at >= 4.5, AAA at >= 7.\n */\nexport const contrastRatio = (hex1: string, hex2: string): number => {\n const [r1, g1, b1] = hexToRgb(hex1);\n const [r2, g2, b2] = hexToRgb(hex2);\n const l1 = 0.2126 * r1 + 0.7152 * g1 + 0.0722 * b1;\n const l2 = 0.2126 * r2 + 0.7152 * g2 + 0.0722 * b2;\n const lighter = Math.max(l1, l2);\n const darker = Math.min(l1, l2);\n return (lighter + 0.05) / (darker + 0.05);\n};\n\n/**\n * Mix two hex colors. `ratio` controls how much of the second color is used\n * (0 = all hex1, 1 = all hex2, default 0.5). Interpolation happens in\n * the given `space` — defaults to `oklab` (perceptually uniform).\n */\nexport const mix = (\n hex1: string,\n hex2: string,\n ratio = 0.5,\n space: 'oklab' | 'lab' | 'rgb' = 'oklab'\n): string => {\n const t = Math.max(0, Math.min(1, ratio));\n const rgb1 = hexToRgb(hex1);\n const rgb2 = hexToRgb(hex2);\n\n if (space === 'rgb') {\n return rgbToHex(rgb1.map((c, i) => c + t * (rgb2[i] - c)));\n }\n\n if (space === 'lab') {\n const lab1 = rgbToLab(rgb1);\n const lab2 = rgbToLab(rgb2);\n return rgbToHex(labToRgb(lab1.map((c, i) => c + t * (lab2[i] - c))));\n }\n\n // Default: oklab\n const ok1 = rgbToOklab(rgb1);\n const ok2 = rgbToOklab(rgb2);\n return rgbToHex(oklabToRgb(ok1.map((c, i) => c + t * (ok2[i] - c))));\n};\n\n/**\n * Generate a `steps`-step gradient across `colors` (2 or more anchors).\n * Interpolation is in Oklab for perceptual uniformity.\n * Returns hex strings from the first to the last anchor.\n */\nexport const scale = (colors: string[], steps: number): string[] => {\n if (colors.length < 2) throw new Error(\"scale() requires at least 2 colors\");\n if (steps < 1) return [];\n if (steps === 1) return [colors[0]];\n\n const oklabs = colors.map(hex => rgbToOklab(hexToRgb(hex)));\n const segments = oklabs.length - 1;\n const result: string[] = [];\n\n for (let i = 0; i < steps; i++) {\n const t = i / (steps - 1);\n const pos = t * segments;\n const seg = Math.min(Math.floor(pos), segments - 1);\n const localT = pos - seg;\n const ok1 = oklabs[seg];\n const ok2 = oklabs[seg + 1];\n result.push(rgbToHex(oklabToRgb(ok1.map((c, j) => c + localT * (ok2[j] - c)))));\n }\n\n return result;\n};\n","import { hexToRgb, labToLch, rgbToLab, toLightnessEAL } from \"./utils\";\n\nexport class Swatch {\n readonly hex: string;\n\n constructor(hex: string) {\n this.hex = hex;\n }\n\n get rgb() {\n return hexToRgb(this.hex);\n }\n\n get lab() {\n return rgbToLab(this.rgb);\n }\n\n get lch() {\n return labToLch(this.lab);\n }\n\n get lightness() {\n // Equivalent Achromatic Lightness (High et al., 2023). Delegates to the\n // shared toLightnessEAL() so the formula lives in exactly one place.\n return toLightnessEAL(this.lab);\n }\n\n get chroma() {\n return this.lch[1];\n }\n\n get hue() {\n return this.lch[2];\n }\n\n get luminance() {\n const [r, g, b] = this.rgb;\n return 0.2126 * r + 0.7152 * g + 0.0722 * b;\n }\n}\n","import { Swatch } from \"./Swatch\";\nimport { calcDeltaE2000, calcScore, createMonotone } from \"./utils\";\n\nexport type ContrastValue = {\n efficiency: number;\n target: number;\n span: number;\n value: number;\n};\n\nexport type WcagContrasts = Record<30 | 45 | 70, ContrastValue>;\nexport type ApcaContrasts = Record<45 | 60 | 75, ContrastValue>;\n\nexport class Ramp {\n swatches: Swatch[];\n name: string;\n\n constructor(colors: string[] = [], name = \"brand\") {\n this.swatches = colors.map((hex) => new Swatch(hex));\n this.name = name;\n }\n\n get colors() {\n return this.swatches.map((swatch) => swatch.hex);\n }\n\n get peakChroma() {\n const colors = this.colors.slice(2, -2);\n let bestHex = \"\";\n let bestChroma = -Infinity;\n\n for (const hex of colors) {\n const swatch = new Swatch(hex);\n if (swatch.chroma > bestChroma) {\n bestChroma = swatch.chroma;\n bestHex = hex;\n }\n }\n if (bestChroma < 6) return this.colors[Math.ceil(this.steps / 2)];\n\n return bestHex;\n }\n\n get steps() {\n return this.colors.length;\n }\n\n get baseColor() {\n if (this.colors.length === 0) return \"\";\n return this.peakChroma || this.colors[Math.floor(this.colors.length / 2)];\n }\n\n get baseIndex() {\n if (this.colors.length === 0) return -1;\n return this.colors.findIndex((hex) => hex.toLowerCase() === this.baseColor.toLowerCase());\n }\n\n get wcag(): WcagContrasts {\n const swatches = this.swatches;\n const total = swatches.length;\n const maxGap = total - 1;\n const contrasts = {} as WcagContrasts;\n\n if (total <= 1) {\n for (const level of [30, 45, 70] as const) {\n contrasts[level] = { efficiency: 1, target: level / 10, span: 0, value: 0 };\n }\n return contrasts;\n }\n\n for (const level of [30, 45, 70] as const) {\n const target = level / 10;\n let span = maxGap;\n let value = 0;\n\n for (let k = 1; k < total; k++) {\n let currentKMin = Infinity;\n\n for (let i = 0; i < total - k; i++) {\n const l1 = swatches[i].luminance;\n const l2 = swatches[i + k].luminance;\n const result = (Math.max(l1, l2) + 0.05) / (Math.min(l1, l2) + 0.05);\n if (result < currentKMin) currentKMin = result;\n }\n\n if (currentKMin >= target) {\n span = k;\n value = currentKMin;\n break;\n }\n\n if (k === maxGap) value = currentKMin;\n }\n\n contrasts[level] = {\n efficiency: span / maxGap,\n target,\n span,\n value,\n };\n }\n\n return contrasts;\n }\n\n get apca(): ApcaContrasts {\n const swatches = this.swatches;\n const total = swatches.length;\n const maxGap = total - 1;\n const contrasts = {} as ApcaContrasts;\n\n if (total <= 1) {\n for (const level of [45, 60, 75] as const) {\n contrasts[level] = { efficiency: 1, target: level, span: 0, value: 0 };\n }\n return contrasts;\n }\n\n const apcaContrast = (yText: number, yBg: number) => {\n const Bc = 0.022, Bl = 1.414;\n const txt = yText < Bc ? yText + Math.pow(Bc - yText, Bl) : yText;\n const bg = yBg < Bc ? yBg + Math.pow(Bc - yBg, Bl) : yBg;\n\n let lc = bg >= txt\n ? (Math.pow(bg, 0.56) - Math.pow(txt, 0.57)) * 114\n : (Math.pow(bg, 0.65) - Math.pow(txt, 0.62)) * 114;\n\n if (Math.abs(lc) < 10) return 0;\n lc = lc > 0 ? lc - 2.7 : lc + 2.7;\n return Math.round(lc);\n };\n\n for (const level of [45, 60, 75] as const) {\n const target = level;\n let span = maxGap;\n let value = 0;\n\n for (let k = 1; k < total; k++) {\n let currentKMin = Infinity;\n\n for (let i = 0; i < total - k; i++) {\n const bg = swatches[i].luminance > swatches[i + k].luminance ? swatches[i].luminance : swatches[i + k].luminance;\n const text = swatches[i].luminance > swatches[i + k].luminance ? swatches[i + k].luminance : swatches[i].luminance;\n const result = Math.abs(apcaContrast(text, bg));\n if (result < currentKMin) currentKMin = result;\n }\n\n if (currentKMin >= target) {\n span = k;\n value = currentKMin;\n break;\n }\n\n if (k === maxGap) value = currentKMin;\n }\n\n contrasts[level] = {\n efficiency: span / maxGap,\n target,\n span,\n value,\n };\n }\n\n return contrasts;\n }\n\n get deltaECurve() {\n const values = [0];\n\n for (let i = 1; i < this.swatches.length; i++) {\n const de00 = calcDeltaE2000(this.swatches[i - 1].lab, this.swatches[i].lab);\n values.push(values[i - 1] + de00);\n }\n\n return values;\n }\n\n get unwrapHues() {\n const hues = this.swatches.map((swatch) => swatch.hue).slice(1, -1);\n if (hues.length === 0) return [];\n\n const result = [hues[0]];\n for (let i = 1; i < hues.length; i++) {\n let diff = hues[i] - hues[i - 1];\n if (diff > 180) diff -= 360;\n else if (diff < -180) diff += 360;\n result.push(result[i - 1] + diff);\n }\n return result;\n }\n\n get lightnessLinearity() {\n const values = this.swatches.map((swatch) => swatch.lightness);\n const n = values.length;\n if (n < 2) return 1;\n\n let sumX = 0, sumY = 0, sumXY = 0, sumXX = 0;\n for (let i = 0; i < n; i++) {\n sumX += i;\n sumY += values[i];\n sumXY += i * values[i];\n sumXX += i * i;\n }\n\n const denominator = n * sumXX - sumX * sumX;\n if (Math.abs(denominator) < 1e-10) return 1;\n\n const slope = (n * sumXY - sumX * sumY) / denominator;\n const intercept = (sumY - slope * sumX) / n;\n const fitRange = Math.abs(slope * (n - 1));\n if (fitRange < 1e-3) return 1;\n\n let sumSqError = 0;\n let sumSqMaxError = 0;\n for (let i = 0; i < n; i++) {\n const target = slope * i + intercept;\n const error = values[i] - target;\n sumSqError += error * error;\n\n const maxDiff = Math.max(\n target - Math.min(intercept, slope * (n - 1) + intercept),\n Math.max(intercept, slope * (n - 1) + intercept) - target\n );\n sumSqMaxError += maxDiff * maxDiff;\n }\n\n return Math.max(0, Math.min(1, 1 - (Math.sqrt(sumSqError / n) / Math.sqrt(sumSqMaxError / n))));\n }\n\n get chromaSmoothness() {\n const values = this.swatches.map((swatch) => swatch.chroma);\n const n = values.length;\n if (n < 3) return 1;\n\n const cRef = 133.8;\n const cMaxInput = Math.max(...values);\n if (cMaxInput <= 1e-2) return 1;\n\n const normalized = values.map((value) => (value / cMaxInput) * cRef);\n const cMin = Math.min(...normalized);\n const cMax = Math.max(...normalized);\n const peakIndex = normalized.findIndex((value) => value === cMax);\n const spline = createMonotone([[0, normalized[0]], [peakIndex, cMax], [n - 1, normalized[n - 1]]]);\n\n let sumSqErr = 0;\n let sumSqMaxErr = 0;\n for (let i = 0; i < n; i++) {\n const target = spline(i);\n const err = normalized[i] - target;\n sumSqErr += err * err;\n sumSqMaxErr += Math.pow(Math.max(target - cMin, cMax - target), 2);\n }\n\n return Math.max(0, Math.min(1, 1 - (Math.sqrt(sumSqErr / n) / Math.sqrt(sumSqMaxErr / n))));\n }\n\n get spacingUniformity() {\n const values = this.deltaECurve;\n const n = values.length;\n if (n < 2) return 1;\n\n const deltas: number[] = [];\n for (let i = 1; i < n; i++) {\n const d = values[i] - values[i - 1];\n if (d < 0) return 0;\n deltas.push(d);\n }\n\n const mean = deltas.reduce((a, b) => a + b, 0) / deltas.length;\n if (mean <= 1e-6) return 0;\n\n let sumSq = 0;\n for (const d of deltas) sumSq += Math.pow(d - mean, 2);\n\n const cv = Math.sqrt(sumSq / deltas.length) / mean;\n return Math.max(0, Math.min(1, 1 / (1 + cv)));\n }\n\n get hueStability() {\n const values = this.unwrapHues;\n const n = values.length;\n if (n < 2) return 1;\n\n const ref = values[this.baseIndex - 1] ?? this.swatches[this.baseIndex]?.hue ?? 0;\n\n let sumSqError = 0;\n let sumSqMaxError = 0;\n for (let i = 0; i < n; i++) {\n let d = Math.abs(values[i] - ref) % 360;\n if (d > 180) d = 360 - d;\n sumSqError += d * d;\n const maxD = (i / (n - 1)) * 180;\n sumSqMaxError += maxD * maxD;\n }\n\n return Math.max(0, Math.min(1, 1 - (Math.sqrt(sumSqError / n) / (Math.sqrt(sumSqMaxError / n) || 1))));\n }\n\n get contrastEfficiency() {\n const span = this.wcag[45].span;\n const steps = this.steps;\n if (steps <= 1) return 1;\n\n const lambda = 0.501;\n const density = span / (steps - 1);\n\n if (density <= lambda) return 1;\n if (density >= 1) return 0;\n\n return 1 - (density - lambda) / (1 - lambda);\n }\n\n get metrics() {\n return {\n lightnessLinearity: this.lightnessLinearity,\n chromaSmoothness: this.chromaSmoothness,\n spacingUniformity: this.spacingUniformity,\n hueStability: this.hueStability,\n contrastEfficiency: this.contrastEfficiency,\n };\n }\n\n get score() {\n return calcScore(Object.values(this.metrics));\n }\n}\n","import { Ramp, type ApcaContrasts, type WcagContrasts } from \"./Ramp\";\nimport { calcScore, rootMeanSquare } from \"./utils\";\n\nexport type PaletteColors = Record<string, string[]>;\n\nexport class Palette {\n ramps: Ramp[];\n name: string;\n\n constructor(colors: PaletteColors = {}, name = \"Collection 1\") {\n this.ramps = Object.entries(colors).map(([rampName, rampColors]) => new Ramp(rampColors, rampName));\n this.name = name;\n }\n\n get colors(): PaletteColors {\n return Object.fromEntries(this.ramps.map((ramp) => [ramp.name, ramp.colors]));\n }\n\n get steps() {\n return this.ramps[0]?.steps || 0;\n }\n\n get wcag(): WcagContrasts {\n const contrasts = {} as WcagContrasts;\n const steps = this.steps;\n\n for (const level of [30, 45, 70] as const) {\n const rampContrasts = this.ramps.map((ramp) => ramp.wcag[level]);\n const span = Math.max(0, ...rampContrasts.map((contrast) => contrast?.span || 0));\n const sum = rampContrasts.reduce((acc, contrast) => acc + (contrast?.value || 0), 0);\n\n contrasts[level] = {\n target: level / 10,\n span,\n value: sum / (this.ramps.length || 1),\n efficiency: steps > 1 ? span / (steps - 1) : 0,\n };\n }\n\n return contrasts;\n }\n\n get apca(): ApcaContrasts {\n const contrasts = {} as ApcaContrasts;\n const steps = this.steps;\n\n for (const level of [45, 60, 75] as const) {\n const rampContrasts = this.ramps.map((ramp) => ramp.apca[level]);\n const span = Math.max(0, ...rampContrasts.map((contrast) => contrast?.span || 0));\n const sum = rampContrasts.reduce((acc, contrast) => acc + (contrast?.value || 0), 0);\n\n contrasts[level] = {\n target: level,\n span,\n value: sum / (this.ramps.length || 1),\n efficiency: steps > 1 ? span / (steps - 1) : 0,\n };\n }\n\n return contrasts;\n }\n\n get contrastEfficiency() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.contrastEfficiency));\n }\n\n get lightnessLinearity() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.lightnessLinearity));\n }\n\n get chromaSmoothness() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.chromaSmoothness));\n }\n\n get hueStability() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.hueStability));\n }\n\n get spacingUniformity() {\n return rootMeanSquare(this.ramps.map((ramp) => ramp.spacingUniformity));\n }\n\n get score() {\n return calcScore([\n this.contrastEfficiency,\n this.lightnessLinearity,\n this.chromaSmoothness,\n this.hueStability,\n this.spacingUniformity,\n ]);\n }\n}\n","import { createMonotone, hexToRgb, oklabToRgb, rgbToHex, rgbToOklab } from \"./utils.js\";\n\n/**\n * Rational-function warp/unwarp pair used to bend the ramp's interpolation\n * parameter so that, once sliced into N discrete steps, the resulting WCAG\n * contrast pairs land as close as possible to the theoretically ideal\n * contrast span K_ideal = ceil(0.501 * (N - 1)) (see the Contrast Efficiency\n * metric in Ramp.ts / the chromametry paper). P and Q were fit by grid search\n * + local refinement against 600 synthetic base colors sampled from the\n * hardest hue regions for perceptual uniformity (green, blue-green/cyan),\n * jointly optimizing the composite quality SCORE and how often the generated\n * ramp's actual span matches K_ideal exactly. At P=0.605, Q=0.685 the search\n * converged to ~90.6 average SCORE, ~95.9% of ramps with span <= K_ideal, and\n * ~88.5% exact span match.\n */\nconst P = 0.605;\nconst Q = 0.685;\n\nfunction warp(t: number): number {\n const tn = Math.pow(t, P);\n return tn / (1 + Q * (1 - tn));\n}\n\nfunction unwarp(y: number): number {\n const xn = (y * (1 + Q)) / (1 + y * Q);\n return Math.pow(xn, 1 / P);\n}\n\nfunction euclidean3(v1: number[], v2: number[]): number {\n return Math.sqrt(\n Math.pow(v1[0] - v2[0], 2) +\n Math.pow(v1[1] - v2[1], 2) +\n Math.pow(v1[2] - v2[2], 2),\n );\n}\n\n// Builds a continuous color-at-parameter function over Oklab-space anchors\n// (black, ...baseColors, white), sorted by lightness. The anchors' positions\n// along the polyline are placed in \"warped\" parameter space via `unwarp`\n// (cumulative Oklab arc length -> normalized distance -> unwarp), so that a\n// linearly-sampled output parameter `t`, once passed back through `warp`,\n// re-lands on the correct anchor position — same mechanism as Ramp.ts's\n// contrastEfficiency metric, run in reverse to CONSTRUCT a ramp instead of\n// SCORING one. Lightness is linearly interpolated per Oklab segment; a and b\n// (chroma channels) use a monotone cubic spline across ALL anchors for a\n// smooth, single-peak chroma trajectory (matches the Chroma Smoothness metric's\n// ideal trajectory assumption).\nfunction sequentialInterpolator(rgbs: number[][]) {\n const fullRgbs = [[0, 0, 0], ...rgbs, [1, 1, 1]];\n const anchors = fullRgbs.map((rgb) => rgbToOklab(rgb)).sort((a, b) => a[0] - b[0]);\n\n const L = anchors.map((v) => v[0]);\n const A = anchors.map((v) => v[1]);\n const B = anchors.map((v) => v[2]);\n\n const cumulativeDistances: number[] = [0];\n let totalDist = 0;\n for (let i = 1; i < anchors.length; i++) {\n totalDist += euclidean3(anchors[i], anchors[i - 1]);\n cumulativeDistances.push(totalDist);\n }\n\n const allParams = cumulativeDistances.map((d) => unwarp(totalDist > 0 ? d / totalDist : 0));\n\n const tMin = rgbs.length === 1 ? 0 : allParams[1];\n const tMax = rgbs.length === 1 ? 1 : allParams[allParams.length - 2];\n\n const aInterpolator = createMonotone(allParams.map((p, i) => [p, A[i]]));\n const bInterpolator = createMonotone(allParams.map((p, i) => [p, B[i]]));\n\n const colorAtParam = (t: number): number[] => {\n const tWarped = warp(t);\n const tMapped = tMin + tWarped * (tMax - tMin);\n\n let i = 0;\n for (let j = 0; j < allParams.length - 1; j++) {\n if (tMapped <= allParams[j + 1]) {\n i = j;\n break;\n }\n }\n\n const dStart = allParams[i];\n const dEnd = allParams[i + 1];\n const ratio = (tMapped - dStart) / (dEnd - dStart || 1);\n const l = L[i] + ratio * (L[i + 1] - L[i]);\n const a = aInterpolator(tMapped);\n const b = bInterpolator(tMapped);\n\n return oklabToRgb([l, a, b]);\n };\n\n return {\n colorAtParam,\n parameters: allParams.slice(1, -1).map((v) => (v - tMin) / (tMax - tMin)),\n };\n}\n\n/**\n * Generate a WCAG-optimized sequential monochromatic ramp from one or more\n * anchor colors, black and white implicitly bracketing the ramp. When more\n * than one anchor color is given, each becomes a fixed waypoint the ramp\n * passes through (e.g. a specific brand color pinned at a specific step),\n * still connected by the same warped Oklab interpolation.\n *\n * Output is ordered light-to-dark (index 0 lightest, last index darkest) to\n * match `@domphy/theme`'s `ThemeInput.colors[name]` convention (`light.ts`'s\n * arrays start `#ffffff`, end `#000000`) — the result can be assigned there\n * directly.\n *\n * @param hexs one hex color, or several ordered by intended position\n * @param stepsCount number of output steps (18 matches the tone scale in\n * `@domphy/theme`'s `ElementTones` — `shift-0`..`shift-17`)\n * @returns `stepsCount` hex colors, lightest first\n */\nexport function generateRamp(hexs: string | string[], stepsCount: number): string[] {\n const anchors = Array.isArray(hexs) ? hexs : [hexs];\n if (anchors.length === 0) throw new Error(\"generateRamp requires at least one anchor color\");\n if (stepsCount <= 0) return [];\n if (stepsCount === 1) return [anchors[0]];\n\n const { colorAtParam, parameters } = sequentialInterpolator(anchors.map(hexToRgb));\n const colors: string[] = [];\n\n const fullParams = [0, ...parameters, 1];\n const anchorIdx = fullParams.map((v) => Math.round(v * (stepsCount - 1)));\n\n let segment = 0;\n for (let k = 0; k < stepsCount; k++) {\n while (segment < anchorIdx.length - 2 && k > anchorIdx[segment + 1]) segment++;\n\n const startIdx = anchorIdx[segment];\n const endIdx = anchorIdx[segment + 1];\n const startParam = fullParams[segment];\n const endParam = fullParams[segment + 1];\n\n let t: number;\n if (endIdx <= startIdx) {\n t = startParam;\n } else {\n const ratio = (k - startIdx) / (endIdx - startIdx);\n t = startParam + ratio * (endParam - startParam);\n }\n\n colors.push(rgbToHex(colorAtParam(t)));\n }\n\n // sequentialInterpolator walks dark (t=0) -> light (t=1); reverse to match\n // @domphy/theme's light-first convention.\n return colors.reverse();\n}\n","export * from \"./classes.js\";\nexport * from \"./patches.js\";\nexport * from \"./types.js\";\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles an abbreviation/acronym with a dotted underline and a \"help\" cursor,\n * shifting to the accent color on hover. Apply to an `<abbr>` element.\n *\n * @hostTag abbr\n * @param props.color - Base text/decoration color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @param props.accentColor - Hover color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { abbr: \"HTML\", title: \"HyperText Markup Language\", $: [abbreviation({ accentColor: \"primary\" })] }\n */\nfunction abbreviation(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"abbr\") {\n console.warn(`\"abbreviation\" primitive patch must use abbr tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n textDecorationLine: \"underline\",\n textDecorationStyle: \"dotted\",\n textDecorationColor: (listener) =>\n themeColor(listener, \"shift-7\", color.get(listener)),\n textUnderlineOffset: themeSpacing(0.72),\n cursor: \"help\",\n \"&:hover\": {\n color: (listener) =>\n themeColor(listener, \"shift-11\", accentColor.get(listener)),\n textDecorationColor: (listener) =>\n themeColor(listener, \"shift-9\", accentColor.get(listener)),\n },\n },\n };\n}\n\nexport { abbreviation };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Container patch that groups `<details>` elements into a bordered accordion.\n * In `type: \"single\"` mode (default), opening one item closes all siblings.\n *\n * @param props.type - `\"single\"` (default) or `\"multiple\"`. Single mode auto-closes siblings.\n * @param props.color - Theme color tone for borders and backgrounds. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color for focus outlines on summary. Defaults to `\"primary\"`.\n * @example\n * { div: [\n * { details: [{ summary: \"Section A\" }, { p: \"Content A\" }], $: [details()] },\n * { details: [{ summary: \"Section B\" }, { p: \"Content B\" }], $: [details()] },\n * ], $: [accordion()] }\n */\nfunction accordion(\n props: {\n type?: \"single\" | \"multiple\";\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { type = \"single\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onMount: (node) => {\n if (type !== \"single\") return;\n\n const el = node.domElement;\n if (!el) return;\n const handler = (event: Event) => {\n const summary = (event.target as Element).closest(\"summary\");\n if (!summary) return;\n const item = summary.closest(\"details\") as HTMLDetailsElement | null;\n if (!item || item.parentElement !== el) return;\n if (!item.open) {\n Array.from(el.querySelectorAll(\":scope > details\")).forEach(\n (detail) => {\n if (detail !== item) (detail as HTMLDetailsElement).open = false;\n },\n );\n }\n };\n el.addEventListener(\"click\", handler);\n node.addHook(\"Remove\", () => el.removeEventListener(\"click\", handler));\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n outlineOffset: \"-1px\",\n overflow: \"hidden\",\n \"& > details\": {\n borderBottom: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n },\n \"& > details:last-child\": {\n borderBottom: \"none\",\n },\n \"& > details > summary:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n },\n };\n}\n\nexport { accordion };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A semantic alert surface block with a colored inset bar, padding, and\n * `role=\"alert\"`. Typically applied to a `<div>` (any block container).\n *\n * @param props.color - Surface/accent color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { div: \"Saved successfully\", $: [alert({ color: \"success\" })] }\n */\nfunction alert(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n\n return {\n role: \"alert\",\n // Alert is a semantic surface block, so it should shift the local surface context.\n dataTone: \"shift-2\",\n style: {\n display: \"flex\",\n alignItems: \"flex-start\",\n gap: themeSpacing(3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n boxShadow: (listener) =>\n `inset ${themeSpacing(1)} 0 0 0 ${themeColor(listener, \"shift-8\", color.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n },\n };\n}\n\nexport { alert };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A circular avatar container that centers initials/text and cover-fits any\n * child `<img>`. Typically applied to an inline-flex container such as a `<span>`.\n *\n * @param props.color - Background/foreground color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { span: \"JD\", $: [avatar({ color: \"primary\" })] }\n */\nfunction avatar(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n style: {\n position: \"relative\",\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n overflow: \"hidden\",\n borderRadius: \"50%\",\n flexShrink: 0,\n width: themeSpacing(9),\n height: themeSpacing(9),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontWeight: \"600\",\n userSelect: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n \"& img\": {\n position: \"absolute\",\n inset: 0,\n width: \"100%\",\n height: \"100%\",\n objectFit: \"cover\",\n },\n },\n };\n}\n\nexport { avatar };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Renders a small count/label bubble pinned to the top-right corner of its host\n * (via a `::after` pseudo-element). Typically applied to an inline container such\n * as a `<span>` wrapping an icon or element.\n *\n * @param props.color - Badge color tone. Optional `ValueOrState<ThemeColor>`, default \"danger\".\n * @param props.label - Text/number shown in the badge. Optional `ValueOrState<string | number>`, default 999.\n * @example { span: \"🔔\", $: [badge({ label: 3, color: \"danger\" })] }\n */\nfunction badge(\n props: {\n color?: ValueOrState<ThemeColor>;\n label?: ValueOrState<string | number>;\n } = {},\n): PartialElement {\n const { label = 999 } = props;\n const state = toState(label);\n const color = toState(props.color ?? \"danger\", \"color\");\n return {\n style: {\n position: \"relative\",\n \"&::after\": {\n content: (l) => `\"${state.get(l)}\"`,\n position: \"absolute\",\n top: 0,\n right: 0,\n transform: \"translate(50%,-50%)\",\n paddingInline: themeSpacing(1),\n minWidth: themeSpacing(6),\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: (l) => themeSize(l, \"decrease-1\"),\n borderRadius: themeSpacing(999),\n backgroundColor: (l) => themeColor(l, \"shift-9\", color.get(l)),\n color: (l) => themeColor(l, \"shift-0\", color.get(l)),\n },\n },\n };\n}\n\nexport { badge };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a quotation block with a colored inset side bar, padded surface, and\n * shifted tone. Apply to a `<blockquote>` element.\n *\n * @hostTag blockquote\n * @param props.color - Surface/bar color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { blockquote: \"Design is how it works.\", $: [blockquote({ color: \"primary\" })] }\n */\nfunction blockquote(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"blockquote\") {\n console.warn(`\"blockquote\" primitive patch must use blockquote tag`);\n }\n },\n dataTone: \"shift-2\",\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n boxShadow: (listener) =>\n `inset ${themeSpacing(1)} 0 0 0 ${themeColor(listener, \"shift-4\", color.get(listener))}`,\n border: \"none\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n margin: 0,\n },\n };\n}\n\nexport { blockquote };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A horizontal breadcrumb navigation that lays out its children with a\n * separator between items and highlights the `[aria-current=page]` item.\n * Apply to a `<nav>` element.\n *\n * @hostTag nav\n * @param props.color - Color tone for links/separators. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @param props.separator - String inserted between items via `::after`. Optional `string`, default \"/\".\n * @example { nav: null, $: [breadcrumb({ separator: \"›\" })] }\n */\nfunction breadcrumb(\n props: { color?: ValueOrState<ThemeColor>; separator?: string } = {},\n): PartialElement {\n const { separator = \"/\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"nav\")\n console.warn('\"breadcrumb\" patch must use nav tag');\n },\n ariaLabel: \"breadcrumb\",\n style: {\n display: \"flex\",\n alignItems: \"center\",\n flexWrap: \"wrap\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n gap: themeSpacing(1),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n \"& > *\": {\n display: \"inline-flex\",\n alignItems: \"center\",\n color: (listener) => themeColor(listener, \"muted\", color.get(listener)),\n },\n \"& > *:not(:last-child)::after\": {\n content: `\"${separator}\"`,\n color: (listener) =>\n themeColor(listener, \"shift-4\", color.get(listener)),\n paddingInlineStart: themeSpacing(1),\n },\n \"& > [aria-current=page]\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { breadcrumb };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * An ellipsis trigger button for collapsed breadcrumb items, with hover and\n * focus-visible states. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.color - Color tone for the trigger. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { button: \"…\", $: [breadcrumbEllipsis({ color: \"neutral\" })] }\n */\nfunction breadcrumbEllipsis(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn('\"breadcrumbEllipsis\" patch must use button tag');\n }\n },\n ariaLabel: \"More breadcrumb items\",\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n paddingInline: themeSpacing(1),\n border: \"none\",\n background: \"none\",\n cursor: \"pointer\",\n color: (listener) => themeColor(listener, \"muted\", color.get(listener)),\n borderRadius: themeSpacing(1),\n \"&:hover\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", color.get(listener))}`,\n outlineOffset: themeSpacing(0.5),\n },\n },\n };\n}\n\nexport { breadcrumbEllipsis };\n","/**\n * The `fontSize` step for `button()`/`buttonGhost()`'s `size` prop. Padding stays\n * per-component (button and buttonGhost start from different base paddings) so\n * only the part that's genuinely identical — the font-size step — lives here.\n */\nconst BUTTON_SIZE_FONT = {\n small: \"decrease-1\",\n medium: \"inherit\",\n large: \"increase-1\",\n} as const;\n\ntype ButtonSize = keyof typeof BUTTON_SIZE_FONT;\n\nexport { BUTTON_SIZE_FONT };\nexport type { ButtonSize };\n","import type { Listener } from \"@domphy/core\";\nimport { type ThemeColor, themeColor } from \"@domphy/theme\";\n\n/**\n * Shared `:focus-visible` ring: a 2px halo in the given accent tone, drawn via\n * box-shadow so it composes with a control's own outline-based resting border\n * instead of replacing it. Used across interactive patches (button, inputs,\n * select, textarea, segmented, tabs, toggleGroup, rating, pagination) so focus\n * reads the same way everywhere instead of each patch picking its own style.\n */\nfunction focusRing(listener: Listener, color: ThemeColor = \"primary\"): string {\n return `0 0 0 2px ${themeColor(listener, \"shift-6\", color)}`;\n}\n\nexport { focusRing };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { BUTTON_SIZE_FONT, type ButtonSize } from \"../utils/buttonSize.js\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nconst PADDING_STEPS: Record<ButtonSize, number> = {\n small: 0.5,\n medium: 1,\n large: 1.5,\n};\n\n/**\n * A transparent button with no border or background — suitable for icon\n * actions, inline controls, and delete/close triggers. Apply to a `<button>`\n * element.\n *\n * @hostTag button\n * @param props.color - Text color tone. Optional `ValueOrState<ThemeColor>`, defaults to `\"neutral\"`.\n * @param props.size - Button size preset. Optional `\"small\" | \"medium\" | \"large\"`, defaults to `\"medium\"`.\n * @example { button: \"×\", $: [buttonGhost()] }\n * @example { button: { span: null, $: [icon({ name: \"trash\" })] }, $: [buttonGhost({ color: \"error\" })] }\n */\nfunction buttonGhost(\n props: { color?: ValueOrState<ThemeColor>; size?: ButtonSize } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const padding = PADDING_STEPS[props.size ?? \"medium\"];\n const fontSize = BUTTON_SIZE_FONT[props.size ?? \"medium\"];\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn(`\"buttonGhost\" primitive patch must use button tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontSize: (listener) => themeSize(listener, fontSize),\n paddingBlock: (listener) =>\n themeSpacing(themeDensity(listener) * padding),\n paddingInline: (listener) =>\n themeSpacing(themeDensity(listener) * padding),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n display: \"inline-flex\",\n justifyContent: \"center\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 1),\n userSelect: \"none\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n border: \"none\",\n background: \"none\",\n outline: \"none\",\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n color: (listener) => themeColor(listener, \"shift-6\", color.get(listener)),\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"border-strong\", \"neutral\"),\n },\n \"&[aria-busy=true]\": {\n opacity: 0.7,\n cursor: \"wait\",\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { buttonGhost };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { BUTTON_SIZE_FONT, type ButtonSize } from \"../utils/buttonSize.js\";\nimport { focusRing } from \"../utils/focusRing.js\";\nimport { buttonGhost } from \"./buttonGhost.js\";\n\ntype ButtonVariant = \"solid\" | \"outline\" | \"ghost\";\n\nconst PADDING_STEPS: Record<ButtonSize, { block: number; inline: number }> = {\n small: { block: 0.5, inline: 2 },\n medium: { block: 1, inline: 3 },\n large: { block: 1.5, inline: 4 },\n};\n\n/**\n * A themed button control with density-aware padding/radius and hover, focus-visible,\n * `[disabled]`, and `[aria-busy=true]` states. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.color - Button color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @param props.variant - Visual style: `\"outline\"` (tinted background + outline, default,\n * backward compatible), `\"solid\"` (filled background, readable contrast text), or `\"ghost\"`\n * (no background/border — delegates to `buttonGhost()` so the two stay visually identical).\n * @param props.size - Button size preset. Optional `\"small\" | \"medium\" | \"large\"`, defaults to `\"medium\"`.\n * @example { button: \"Save\", $: [button({ color: \"primary\" })] }\n * @example { button: \"Delete\", $: [button({ color: \"error\", variant: \"solid\" })] }\n */\nfunction button(\n props: {\n color?: ValueOrState<ThemeColor>;\n variant?: ButtonVariant;\n size?: ButtonSize;\n } = {},\n): PartialElement {\n const variant = props.variant ?? \"outline\";\n if (variant === \"ghost\") {\n return buttonGhost({ color: props.color, size: props.size });\n }\n\n const color = toState(props.color ?? \"primary\", \"color\");\n const isSolid = variant === \"solid\";\n const padding = PADDING_STEPS[props.size ?? \"medium\"];\n const fontSize = BUTTON_SIZE_FONT[props.size ?? \"medium\"];\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn(`\"button\" primitive patch must use button tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontSize: (listener) => themeSize(listener, fontSize),\n // Single-line bounded control: block/radius = 1D, inline = 3D.\n paddingBlock: (listener) =>\n themeSpacing(themeDensity(listener) * padding.block),\n paddingInline: (listener) =>\n themeSpacing(themeDensity(listener) * padding.inline),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n width: \"fit-content\",\n display: \"flex\",\n justifyContent: \"center\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 1),\n userSelect: \"none\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n border: \"none\",\n outlineOffset: \"-1px\",\n outlineWidth: \"1px\",\n outline: isSolid\n ? \"none\"\n : (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-0\", color.get(listener))\n : themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-9\", color.get(listener))\n : themeColor(listener, \"inherit\", color.get(listener)),\n transition:\n \"background-color 140ms ease, color 140ms ease, border-color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n color: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-0\", color.get(listener))\n : themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) =>\n isSolid\n ? themeColor(listener, \"shift-10\", color.get(listener))\n : themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n \"&[aria-busy=true]\": {\n opacity: 0.7,\n cursor: \"wait\",\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { button };\nexport type { ButtonVariant };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A pill-shaped toggle switch with `role=\"switch\"`; clicking flips the bound\n * `checked` state and slides the thumb. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.checked - Toggle state. Optional `ValueOrState<boolean>`, default false.\n * @param props.accentColor - Color tone when checked (on). Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @param props.color - Color tone when unchecked (off track). Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { button: { span: null }, $: [buttonSwitch({ checked: true })] }\n */\nfunction buttonSwitch(\n props: {\n checked?: ValueOrState<boolean>;\n accentColor?: ValueOrState<ThemeColor>;\n color?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { checked = false } = props;\n\n const check = toState(checked);\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onSchedule: (node) => {\n if (node.tagName !== \"button\") {\n console.warn(`\"buttonSwitch\" primitive patch must use button tag`);\n }\n },\n role: \"switch\",\n ariaChecked: (listener) => check.get(listener),\n dataTone: \"shift-2\",\n onClick: () => check.set(!check.get()),\n style: {\n position: \"relative\",\n display: \"inline-flex\",\n alignItems: \"center\",\n fontSize: (listener) => themeSize(listener),\n border: \"none\",\n outlineWidth: \"1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color.get(listener))}`,\n minWidth: themeSpacing(12),\n minHeight: themeSpacing(6),\n borderRadius: themeSpacing(999),\n paddingLeft: themeSpacing(7),\n paddingRight: themeSpacing(2),\n transition: \"padding-left 0.3s, padding-right 0.3s\",\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n \"& > :first-child\": {\n content: '\"\"',\n position: \"absolute\",\n display: \"inline-flex\",\n alignItems: \"center\",\n left: themeSpacing(0.5),\n top: \"50%\",\n transform: \"translateY(-50%)\",\n transition: \"left 0.3s\",\n width: themeSpacing(5),\n height: themeSpacing(5),\n borderRadius: themeSpacing(999),\n color: (listener) => themeColor(listener, \"text\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"decrease-2\", color.get(listener)),\n },\n \"&[aria-checked=true]\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"increase-3\", accentColor.get(listener)),\n outline: \"none\",\n color: (listener) => themeColor(listener, \"decrease-2\"),\n paddingLeft: themeSpacing(2),\n paddingRight: themeSpacing(7),\n },\n \"&[aria-checked=true] > :first-child\": {\n left: `calc(100% - ${themeSpacing(5.5)})`,\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n };\n}\n\nexport { buttonSwitch };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A grid-based card surface that auto-places known child elements into named\n * regions: `<img>` (image), headings (title), `<p>` (description), `<aside>`\n * (aside), `<div>` (content), and `<footer>` (footer). Typically applied to a\n * `<div>` (any block container).\n *\n * @param props.color - Surface/border color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { div: { h3: \"Title\", p: \"Body\" }, $: [card({ color: \"neutral\" })] }\n */\nfunction card(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n return {\n style: {\n display: \"grid\",\n gridTemplateColumns: \"1fr auto\",\n gridTemplateAreas:\n '\"image image\" \"title aside\" \"desc aside\" \"content content\" \"footer footer\"',\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n outlineOffset: \"-1px\",\n overflow: \"hidden\",\n \"& > img\": {\n gridArea: \"image\",\n width: \"100%\",\n height: \"auto\",\n display: \"block\",\n },\n \"& > :is(h1,h2,h3,h4,h5,h6)\": {\n gridArea: \"title\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n fontWeight: \"600\",\n margin: 0,\n },\n \"& > p\": {\n gridArea: \"desc\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n margin: 0,\n },\n \"& > aside\": {\n gridArea: \"aside\",\n alignSelf: \"center\",\n padding: (listener) => themeSpacing(themeDensity(listener) * 2),\n height: \"auto\",\n },\n \"& > div\": {\n gridArea: \"content\",\n padding: (listener) => themeSpacing(themeDensity(listener) * 4),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n },\n \"& > footer\": {\n gridArea: \"footer\",\n display: \"flex\",\n gap: themeSpacing(2),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n borderTop: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color.get(listener))}`,\n },\n },\n };\n}\n\nexport { card };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles an inline code snippet with a subtle surface background, rounded corners,\n * and shifted tone. Apply to a `<code>` element.\n *\n * @hostTag code\n * @param props.color - Surface/text color tone. Optional `ValueOrState<ThemeColor>`, default \"neutral\".\n * @example { code: \"npm install\", $: [code({ color: \"neutral\" })] }\n */\nfunction code(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInsert: (node) => {\n if (node.tagName !== \"code\") {\n console.warn(`\"code\" primitive patch must use code tag`);\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n whiteSpace: \"nowrap\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n height: themeSpacing(6),\n paddingInline: themeSpacing(1.5),\n borderRadius: themeSpacing(1),\n },\n };\n}\n\nexport { code };\n","/** Named elevation levels for floating/raised surfaces. */\ntype ElevationLevel = \"low\" | \"medium\" | \"high\";\n\n// Layered soft shadows (a tight contact shadow + a broad ambient one), black at\n// low alpha so the same value reads correctly on both light and dark surfaces\n// without a theme/context lookup.\nconst SHADOWS: Record<ElevationLevel, string> = {\n low: \"0 1px 2px rgba(0,0,0,0.08), 0 4px 10px rgba(0,0,0,0.10)\",\n medium: \"0 2px 4px rgba(0,0,0,0.10), 0 10px 24px rgba(0,0,0,0.14)\",\n high: \"0 6px 12px rgba(0,0,0,0.14), 0 24px 48px rgba(0,0,0,0.20)\",\n};\n\n/**\n * Shared box-shadow value for a named elevation level. Used by floating/raised\n * surface patches (popover, menu, dialog, drawer, toast, tooltip, combobox/\n * selectBox dropdown, datePicker popup, fab) so elevation reads consistently\n * across the library instead of each patch picking its own shadow.\n */\nfunction elevation(level: ElevationLevel): string {\n return SHADOWS[level];\n}\n\nexport { elevation };\nexport type { ElevationLevel };\n","type Prettify<T> = {\n [K in keyof T]: T[K];\n} & {};\n\nexport type Alignment = 'start' | 'end';\nexport type Side = 'top' | 'right' | 'bottom' | 'left';\nexport type AlignedPlacement = `${Side}-${Alignment}`;\nexport type Placement = Prettify<Side | AlignedPlacement>;\nexport type Strategy = 'absolute' | 'fixed';\nexport type Axis = 'x' | 'y';\nexport type Coords = {[key in Axis]: number};\nexport type Length = 'width' | 'height';\nexport type Dimensions = {[key in Length]: number};\nexport type SideObject = {[key in Side]: number};\nexport type Rect = Prettify<Coords & Dimensions>;\nexport type Padding = number | Prettify<Partial<SideObject>>;\nexport type ClientRectObject = Prettify<Rect & SideObject>;\n\nexport interface ElementRects {\n reference: Rect;\n floating: Rect;\n}\n\n/**\n * Custom positioning reference element.\n * @see https://floating-ui.com/docs/virtual-elements\n */\nexport interface VirtualElement {\n getBoundingClientRect(): ClientRectObject;\n getClientRects?(): Array<ClientRectObject>;\n contextElement?: any;\n}\n\nexport const sides: Side[] = ['top', 'right', 'bottom', 'left'];\nexport const alignments: Alignment[] = ['start', 'end'];\nexport const placements: Placement[] = sides.reduce(\n (acc: Placement[], side) =>\n acc.concat(side, `${side}-${alignments[0]}`, `${side}-${alignments[1]}`),\n [],\n);\n\nexport const min = Math.min;\nexport const max = Math.max;\nexport const round = Math.round;\nexport const floor = Math.floor;\nexport const createCoords = (v: number) => ({x: v, y: v});\n\nconst oppositeSideMap = {\n left: 'right',\n right: 'left',\n bottom: 'top',\n top: 'bottom',\n};\n\nexport function clamp(start: number, value: number, end: number): number {\n return max(start, min(value, end));\n}\n\nexport function evaluate<T, P>(value: T | ((param: P) => T), param: P): T {\n return typeof value === 'function'\n ? (value as (param: P) => T)(param)\n : value;\n}\n\nexport function getSide(placement: Placement): Side {\n return placement.split('-')[0] as Side;\n}\n\nexport function getAlignment(placement: Placement): Alignment | undefined {\n return placement.split('-')[1] as Alignment | undefined;\n}\n\nexport function getOppositeAxis(axis: Axis): Axis {\n return axis === 'x' ? 'y' : 'x';\n}\n\nexport function getAxisLength(axis: Axis): Length {\n return axis === 'y' ? 'height' : 'width';\n}\n\nexport function getSideAxis(placement: Placement): Axis {\n const firstChar = placement[0];\n return firstChar === 't' || firstChar === 'b' ? 'y' : 'x';\n}\n\nexport function getAlignmentAxis(placement: Placement): Axis {\n return getOppositeAxis(getSideAxis(placement));\n}\n\nexport function getAlignmentSides(\n placement: Placement,\n rects: ElementRects,\n rtl = false,\n): [Side, Side] {\n const alignment = getAlignment(placement);\n const alignmentAxis = getAlignmentAxis(placement);\n const length = getAxisLength(alignmentAxis);\n\n let mainAlignmentSide: Side =\n alignmentAxis === 'x'\n ? alignment === (rtl ? 'end' : 'start')\n ? 'right'\n : 'left'\n : alignment === 'start'\n ? 'bottom'\n : 'top';\n\n if (rects.reference[length] > rects.floating[length]) {\n mainAlignmentSide = getOppositePlacement(mainAlignmentSide);\n }\n\n return [mainAlignmentSide, getOppositePlacement(mainAlignmentSide)];\n}\n\nexport function getExpandedPlacements(placement: Placement): Array<Placement> {\n const oppositePlacement = getOppositePlacement(placement);\n\n return [\n getOppositeAlignmentPlacement(placement),\n oppositePlacement,\n getOppositeAlignmentPlacement(oppositePlacement),\n ];\n}\n\nexport function getOppositeAlignmentPlacement<T extends string>(\n placement: T,\n): T {\n return placement.includes('start')\n ? (placement.replace('start', 'end') as T)\n : (placement.replace('end', 'start') as T);\n}\n\nconst lrPlacement: Placement[] = ['left', 'right'];\nconst rlPlacement: Placement[] = ['right', 'left'];\nconst tbPlacement: Placement[] = ['top', 'bottom'];\nconst btPlacement: Placement[] = ['bottom', 'top'];\n\nfunction getSideList(side: Side, isStart: boolean, rtl?: boolean): Placement[] {\n switch (side) {\n case 'top':\n case 'bottom':\n if (rtl) return isStart ? rlPlacement : lrPlacement;\n return isStart ? lrPlacement : rlPlacement;\n case 'left':\n case 'right':\n return isStart ? tbPlacement : btPlacement;\n default:\n return [];\n }\n}\n\nexport function getOppositeAxisPlacements(\n placement: Placement,\n flipAlignment: boolean,\n direction: 'none' | Alignment,\n rtl?: boolean,\n): Placement[] {\n const alignment = getAlignment(placement);\n let list = getSideList(getSide(placement), direction === 'start', rtl);\n\n if (alignment) {\n list = list.map((side) => `${side}-${alignment}` as Placement);\n\n if (flipAlignment) {\n list = list.concat(list.map(getOppositeAlignmentPlacement));\n }\n }\n\n return list;\n}\n\nexport function getOppositePlacement<T extends string>(placement: T): T {\n const side = getSide(placement as Placement);\n return (oppositeSideMap[side] + placement.slice(side.length)) as T;\n}\n\nexport function expandPaddingObject(padding: Partial<SideObject>): SideObject {\n return {top: 0, right: 0, bottom: 0, left: 0, ...padding};\n}\n\nexport function getPaddingObject(padding: Padding): SideObject {\n return typeof padding !== 'number'\n ? expandPaddingObject(padding)\n : {top: padding, right: padding, bottom: padding, left: padding};\n}\n\nexport function rectToClientRect(rect: Rect): ClientRectObject {\n const {x, y, width, height} = rect;\n return {\n width,\n height,\n top: y,\n left: x,\n right: x + width,\n bottom: y + height,\n x,\n y,\n };\n}\n","import type {Coords, ElementRects, Placement} from '@floating-ui/utils';\nimport {\n getAlignment,\n getAlignmentAxis,\n getAxisLength,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nexport function computeCoordsFromPlacement(\n {reference, floating}: ElementRects,\n placement: Placement,\n rtl?: boolean,\n): Coords {\n const sideAxis = getSideAxis(placement);\n const alignmentAxis = getAlignmentAxis(placement);\n const alignLength = getAxisLength(alignmentAxis);\n const side = getSide(placement);\n const isVertical = sideAxis === 'y';\n\n const commonX = reference.x + reference.width / 2 - floating.width / 2;\n const commonY = reference.y + reference.height / 2 - floating.height / 2;\n const commonAlign = reference[alignLength] / 2 - floating[alignLength] / 2;\n\n let coords: Coords;\n switch (side) {\n case 'top':\n coords = {x: commonX, y: reference.y - floating.height};\n break;\n case 'bottom':\n coords = {x: commonX, y: reference.y + reference.height};\n break;\n case 'right':\n coords = {x: reference.x + reference.width, y: commonY};\n break;\n case 'left':\n coords = {x: reference.x - floating.width, y: commonY};\n break;\n default:\n coords = {x: reference.x, y: reference.y};\n }\n\n switch (getAlignment(placement)) {\n case 'start':\n coords[alignmentAxis] -= commonAlign * (rtl && isVertical ? -1 : 1);\n break;\n case 'end':\n coords[alignmentAxis] += commonAlign * (rtl && isVertical ? -1 : 1);\n break;\n default:\n }\n\n return coords;\n}\n","import type {Padding, SideObject} from '@floating-ui/utils';\nimport {evaluate, getPaddingObject, rectToClientRect} from '@floating-ui/utils';\n\nimport type {\n Boundary,\n Derivable,\n ElementContext,\n MiddlewareState,\n RootBoundary,\n} from './types';\n\nexport interface DetectOverflowOptions {\n /**\n * The clipping element(s) or area in which overflow will be checked.\n * @default 'clippingAncestors'\n */\n boundary?: Boundary;\n /**\n * The root clipping area in which overflow will be checked.\n * @default 'viewport'\n */\n rootBoundary?: RootBoundary;\n /**\n * The element in which overflow is being checked relative to a boundary.\n * @default 'floating'\n */\n elementContext?: ElementContext;\n /**\n * Whether to check for overflow using the alternate element's boundary\n * (`clippingAncestors` boundary only).\n * @default false\n */\n altBoundary?: boolean;\n /**\n * Virtual padding for the resolved overflow detection offsets.\n * @default 0\n */\n padding?: Padding;\n}\n\n/**\n * Resolves with an object of overflow side offsets that determine how much the\n * element is overflowing a given clipping boundary on each side.\n * - positive = overflowing the boundary by that number of pixels\n * - negative = how many pixels left before it will overflow\n * - 0 = lies flush with the boundary\n * @see https://floating-ui.com/docs/detectOverflow\n */\nexport async function detectOverflow(\n state: MiddlewareState,\n options: DetectOverflowOptions | Derivable<DetectOverflowOptions> = {},\n): Promise<SideObject> {\n const {x, y, platform, rects, elements, strategy} = state;\n\n const {\n boundary = 'clippingAncestors',\n rootBoundary = 'viewport',\n elementContext = 'floating',\n altBoundary = false,\n padding = 0,\n } = evaluate(options, state);\n\n const paddingObject = getPaddingObject(padding);\n const altContext = elementContext === 'floating' ? 'reference' : 'floating';\n const element = elements[altBoundary ? altContext : elementContext];\n\n const clippingClientRect = rectToClientRect(\n await platform.getClippingRect({\n element:\n (await platform.isElement?.(element)) ?? true\n ? element\n : element.contextElement ||\n (await platform.getDocumentElement?.(elements.floating)),\n boundary,\n rootBoundary,\n strategy,\n }),\n );\n\n const rect =\n elementContext === 'floating'\n ? {x, y, width: rects.floating.width, height: rects.floating.height}\n : rects.reference;\n\n const offsetParent = await platform.getOffsetParent?.(elements.floating);\n const offsetScale = (await platform.isElement?.(offsetParent))\n ? (await platform.getScale?.(offsetParent)) || {x: 1, y: 1}\n : {x: 1, y: 1};\n\n const elementClientRect = rectToClientRect(\n platform.convertOffsetParentRelativeRectToViewportRelativeRect\n ? await platform.convertOffsetParentRelativeRectToViewportRelativeRect({\n elements,\n rect,\n offsetParent,\n strategy,\n })\n : rect,\n );\n\n return {\n top:\n (clippingClientRect.top - elementClientRect.top + paddingObject.top) /\n offsetScale.y,\n bottom:\n (elementClientRect.bottom -\n clippingClientRect.bottom +\n paddingObject.bottom) /\n offsetScale.y,\n left:\n (clippingClientRect.left - elementClientRect.left + paddingObject.left) /\n offsetScale.x,\n right:\n (elementClientRect.right -\n clippingClientRect.right +\n paddingObject.right) /\n offsetScale.x,\n };\n}\n","import {computeCoordsFromPlacement} from './computeCoordsFromPlacement';\nimport {detectOverflow} from './detectOverflow';\nimport type {\n ComputePosition,\n Middleware,\n MiddlewareData,\n Platform,\n} from './types';\n\n// Maximum number of resets that can occur before bailing to avoid infinite reset loops.\nconst MAX_RESET_COUNT = 50;\n\n/**\n * Computes the `x` and `y` coordinates that will place the floating element\n * next to a given reference element.\n *\n * This export does not have any `platform` interface logic. You will need to\n * write one for the platform you are using Floating UI with.\n */\nexport const computePosition: ComputePosition = async (\n reference,\n floating,\n config,\n) => {\n const {\n placement = 'bottom',\n strategy = 'absolute',\n middleware = [],\n platform,\n } = config;\n\n const platformWithDetectOverflow = (\n platform.detectOverflow ? platform : {...platform, detectOverflow}\n ) as Platform & {detectOverflow: typeof detectOverflow};\n const rtl = await platform.isRTL?.(floating);\n\n let rects = await platform.getElementRects({reference, floating, strategy});\n let {x, y} = computeCoordsFromPlacement(rects, placement, rtl);\n let statefulPlacement = placement;\n let resetCount = 0;\n\n const middlewareData: MiddlewareData = {};\n\n for (let i = 0; i < middleware.length; i++) {\n const currentMiddleware = middleware[i] as Middleware | undefined;\n\n if (!currentMiddleware) {\n continue;\n }\n\n const {name, fn} = currentMiddleware;\n\n const {\n x: nextX,\n y: nextY,\n data,\n reset,\n } = await fn({\n x,\n y,\n initialPlacement: placement,\n placement: statefulPlacement,\n strategy,\n middlewareData,\n rects,\n platform: platformWithDetectOverflow,\n elements: {reference, floating},\n });\n\n x = nextX ?? x;\n y = nextY ?? y;\n\n middlewareData[name] = {\n ...middlewareData[name],\n ...data,\n };\n\n if (reset && resetCount < MAX_RESET_COUNT) {\n resetCount++;\n\n if (typeof reset === 'object') {\n if (reset.placement) {\n statefulPlacement = reset.placement;\n }\n\n if (reset.rects) {\n rects =\n reset.rects === true\n ? await platform.getElementRects({reference, floating, strategy})\n : reset.rects;\n }\n\n ({x, y} = computeCoordsFromPlacement(rects, statefulPlacement, rtl));\n }\n\n i = -1;\n }\n }\n\n return {\n x,\n y,\n placement: statefulPlacement,\n strategy,\n middlewareData,\n };\n};\n","import type {Padding} from '@floating-ui/utils';\nimport {\n clamp,\n evaluate,\n getAlignment,\n getAlignmentAxis,\n getAxisLength,\n getPaddingObject,\n min as mathMin,\n} from '@floating-ui/utils';\n\nimport type {Derivable, Middleware} from '../types';\n\nexport interface ArrowOptions {\n /**\n * The arrow element to be positioned.\n * @default undefined\n */\n element: any;\n /**\n * The padding between the arrow element and the floating element edges.\n * Useful when the floating element has rounded corners.\n * @default 0\n */\n padding?: Padding;\n}\n\n/**\n * Provides data to position an inner element of the floating element so that it\n * appears centered to the reference element.\n * @see https://floating-ui.com/docs/arrow\n */\nexport const arrow = (\n options: ArrowOptions | Derivable<ArrowOptions>,\n): Middleware => ({\n name: 'arrow',\n options,\n async fn(state) {\n const {x, y, placement, rects, platform, elements, middlewareData} = state;\n // Since `element` is required, we don't Partial<> the type.\n const {element, padding = 0} = evaluate(options, state) || {};\n\n if (element == null) {\n return {};\n }\n\n const paddingObject = getPaddingObject(padding);\n const coords = {x, y};\n const axis = getAlignmentAxis(placement);\n const length = getAxisLength(axis);\n const arrowDimensions = await platform.getDimensions(element);\n const isYAxis = axis === 'y';\n const minProp = isYAxis ? 'top' : 'left';\n const maxProp = isYAxis ? 'bottom' : 'right';\n const clientProp = isYAxis ? 'clientHeight' : 'clientWidth';\n\n const endDiff =\n rects.reference[length] +\n rects.reference[axis] -\n coords[axis] -\n rects.floating[length];\n const startDiff = coords[axis] - rects.reference[axis];\n\n const arrowOffsetParent = await platform.getOffsetParent?.(element);\n let clientSize = arrowOffsetParent ? arrowOffsetParent[clientProp] : 0;\n\n // DOM platform can return `window` as the `offsetParent`.\n if (!clientSize || !(await platform.isElement?.(arrowOffsetParent))) {\n clientSize = elements.floating[clientProp] || rects.floating[length];\n }\n\n const centerToReference = endDiff / 2 - startDiff / 2;\n\n // If the padding is large enough that it causes the arrow to no longer be\n // centered, modify the padding so that it is centered.\n const largestPossiblePadding =\n clientSize / 2 - arrowDimensions[length] / 2 - 1;\n const minPadding = mathMin(paddingObject[minProp], largestPossiblePadding);\n const maxPadding = mathMin(paddingObject[maxProp], largestPossiblePadding);\n\n // Make sure the arrow doesn't overflow the floating element if the center\n // point is outside the floating element's bounds.\n const min = minPadding;\n const max = clientSize - arrowDimensions[length] - maxPadding;\n const center =\n clientSize / 2 - arrowDimensions[length] / 2 + centerToReference;\n const offset = clamp(min, center, max);\n\n // If the reference is small enough that the arrow's padding causes it to\n // to point to nothing for an aligned placement, adjust the offset of the\n // floating element itself. To ensure `shift()` continues to take action,\n // a single reset is performed when this is true.\n const shouldAddOffset =\n !middlewareData.arrow &&\n getAlignment(placement) != null &&\n center !== offset &&\n rects.reference[length] / 2 -\n (center < min ? minPadding : maxPadding) -\n arrowDimensions[length] / 2 <\n 0;\n const alignmentOffset = shouldAddOffset\n ? center < min\n ? center - min\n : center - max\n : 0;\n\n return {\n [axis]: coords[axis] + alignmentOffset,\n data: {\n [axis]: offset,\n centerOffset: center - offset - alignmentOffset,\n ...(shouldAddOffset && {alignmentOffset}),\n },\n reset: shouldAddOffset,\n };\n },\n});\n","import type {Alignment, Placement} from '@floating-ui/utils';\nimport {\n evaluate,\n getAlignment,\n getAlignmentSides,\n getOppositeAlignmentPlacement,\n getSide,\n placements as ALL_PLACEMENTS,\n} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware} from '../types';\n\nexport function getPlacementList(\n alignment: Alignment | null,\n autoAlignment: boolean,\n allowedPlacements: Array<Placement>,\n) {\n const allowedPlacementsSortedByAlignment = alignment\n ? [\n ...allowedPlacements.filter(\n (placement) => getAlignment(placement) === alignment,\n ),\n ...allowedPlacements.filter(\n (placement) => getAlignment(placement) !== alignment,\n ),\n ]\n : allowedPlacements.filter((placement) => getSide(placement) === placement);\n\n return allowedPlacementsSortedByAlignment.filter((placement) => {\n if (alignment) {\n return (\n getAlignment(placement) === alignment ||\n (autoAlignment\n ? getOppositeAlignmentPlacement(placement) !== placement\n : false)\n );\n }\n\n return true;\n });\n}\n\nexport interface AutoPlacementOptions extends DetectOverflowOptions {\n /**\n * The axis that runs along the alignment of the floating element. Determines\n * whether to check for most space along this axis.\n * @default false\n */\n crossAxis?: boolean;\n /**\n * Choose placements with a particular alignment.\n * @default undefined\n */\n alignment?: Alignment | null;\n /**\n * Whether to choose placements with the opposite alignment if the preferred\n * alignment does not fit.\n * @default true\n */\n autoAlignment?: boolean;\n /**\n * Which placements are allowed to be chosen. Placements must be within the\n * `alignment` option if explicitly set.\n * @default allPlacements (variable)\n */\n allowedPlacements?: Array<Placement>;\n}\n\n/**\n * Optimizes the visibility of the floating element by choosing the placement\n * that has the most space available automatically, without needing to specify a\n * preferred placement. Alternative to `flip`.\n * @see https://floating-ui.com/docs/autoPlacement\n */\nexport const autoPlacement = (\n options: AutoPlacementOptions | Derivable<AutoPlacementOptions> = {},\n): Middleware => ({\n name: 'autoPlacement',\n options,\n async fn(state) {\n const {rects, middlewareData, placement, platform, elements} = state;\n\n const {\n crossAxis = false,\n alignment,\n allowedPlacements = ALL_PLACEMENTS,\n autoAlignment = true,\n ...detectOverflowOptions\n } = evaluate(options, state);\n\n const placements =\n alignment !== undefined || allowedPlacements === ALL_PLACEMENTS\n ? getPlacementList(alignment || null, autoAlignment, allowedPlacements)\n : allowedPlacements;\n\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n\n const currentIndex = middlewareData.autoPlacement?.index || 0;\n const currentPlacement = placements[currentIndex];\n\n if (currentPlacement == null) {\n return {};\n }\n\n const alignmentSides = getAlignmentSides(\n currentPlacement,\n rects,\n await platform.isRTL?.(elements.floating),\n );\n\n // Make `computeCoords` start from the right place.\n if (placement !== currentPlacement) {\n return {\n reset: {\n placement: placements[0],\n },\n };\n }\n\n const currentOverflows = [\n overflow[getSide(currentPlacement)],\n overflow[alignmentSides[0]],\n overflow[alignmentSides[1]],\n ];\n\n const allOverflows = [\n ...(middlewareData.autoPlacement?.overflows || []),\n {placement: currentPlacement, overflows: currentOverflows},\n ];\n\n const nextPlacement = placements[currentIndex + 1];\n\n // There are more placements to check.\n if (nextPlacement) {\n return {\n data: {\n index: currentIndex + 1,\n overflows: allOverflows,\n },\n reset: {\n placement: nextPlacement,\n },\n };\n }\n\n const placementsSortedByMostSpace = allOverflows\n .map((d) => {\n const alignment = getAlignment(d.placement);\n return [\n d.placement,\n alignment && crossAxis\n ? // Check along the mainAxis and main crossAxis side.\n d.overflows.slice(0, 2).reduce((acc, v) => acc + v, 0)\n : // Check only the mainAxis.\n d.overflows[0],\n d.overflows,\n ] as const;\n })\n .sort((a, b) => a[1] - b[1]);\n\n const placementsThatFitOnEachSide = placementsSortedByMostSpace.filter(\n (d) =>\n d[2]\n .slice(\n 0,\n // Aligned placements should not check their opposite crossAxis\n // side.\n getAlignment(d[0]) ? 2 : 3,\n )\n .every((v) => v <= 0),\n );\n\n const resetPlacement =\n placementsThatFitOnEachSide[0]?.[0] || placementsSortedByMostSpace[0][0];\n\n if (resetPlacement !== placement) {\n return {\n data: {\n index: currentIndex + 1,\n overflows: allOverflows,\n },\n reset: {\n placement: resetPlacement,\n },\n };\n }\n\n return {};\n },\n});\n","import type {Placement} from '@floating-ui/utils';\nimport {\n evaluate,\n getAlignmentSides,\n getExpandedPlacements,\n getOppositeAxisPlacements,\n getOppositePlacement,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware} from '../types';\n\nexport interface FlipOptions extends DetectOverflowOptions {\n /**\n * The axis that runs along the side of the floating element. Determines\n * whether overflow along this axis is checked to perform a flip.\n * @default true\n */\n mainAxis?: boolean;\n /**\n * The axis that runs along the alignment of the floating element. Determines\n * whether overflow along this axis is checked to perform a flip.\n * - `true`: Whether to check cross axis overflow for both side and alignment flipping.\n * - `false`: Whether to disable all cross axis overflow checking.\n * - `'alignment'`: Whether to check cross axis overflow for alignment flipping only.\n * @default true\n */\n crossAxis?: boolean | 'alignment';\n /**\n * Placements to try sequentially if the preferred `placement` does not fit.\n * @default [oppositePlacement] (computed)\n */\n fallbackPlacements?: Array<Placement>;\n /**\n * What strategy to use when no placements fit.\n * @default 'bestFit'\n */\n fallbackStrategy?: 'bestFit' | 'initialPlacement';\n /**\n * Whether to allow fallback to the perpendicular axis of the preferred\n * placement, and if so, which side direction along the axis to prefer.\n * @default 'none' (disallow fallback)\n */\n fallbackAxisSideDirection?: 'none' | 'start' | 'end';\n /**\n * Whether to flip to placements with the opposite alignment if they fit\n * better.\n * @default true\n */\n flipAlignment?: boolean;\n}\n\n/**\n * Optimizes the visibility of the floating element by flipping the `placement`\n * in order to keep it in view when the preferred placement(s) will overflow the\n * clipping boundary. Alternative to `autoPlacement`.\n * @see https://floating-ui.com/docs/flip\n */\nexport const flip = (\n options: FlipOptions | Derivable<FlipOptions> = {},\n): Middleware => ({\n name: 'flip',\n options,\n async fn(state) {\n const {\n placement,\n middlewareData,\n rects,\n initialPlacement,\n platform,\n elements,\n } = state;\n\n const {\n mainAxis: checkMainAxis = true,\n crossAxis: checkCrossAxis = true,\n fallbackPlacements: specifiedFallbackPlacements,\n fallbackStrategy = 'bestFit',\n fallbackAxisSideDirection = 'none',\n flipAlignment = true,\n ...detectOverflowOptions\n } = evaluate(options, state);\n\n // If a reset by the arrow was caused due to an alignment offset being\n // added, we should skip any logic now since `flip()` has already done its\n // work.\n // https://github.com/floating-ui/floating-ui/issues/2549#issuecomment-1719601643\n if (middlewareData.arrow?.alignmentOffset) {\n return {};\n }\n\n const side = getSide(placement);\n const initialSideAxis = getSideAxis(initialPlacement);\n const isBasePlacement = getSide(initialPlacement) === initialPlacement;\n const rtl = await platform.isRTL?.(elements.floating);\n\n const fallbackPlacements =\n specifiedFallbackPlacements ||\n (isBasePlacement || !flipAlignment\n ? [getOppositePlacement(initialPlacement)]\n : getExpandedPlacements(initialPlacement));\n\n const hasFallbackAxisSideDirection = fallbackAxisSideDirection !== 'none';\n\n if (!specifiedFallbackPlacements && hasFallbackAxisSideDirection) {\n fallbackPlacements.push(\n ...getOppositeAxisPlacements(\n initialPlacement,\n flipAlignment,\n fallbackAxisSideDirection,\n rtl,\n ),\n );\n }\n\n const placements = [initialPlacement, ...fallbackPlacements];\n\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n\n const overflows = [];\n let overflowsData = middlewareData.flip?.overflows || [];\n\n if (checkMainAxis) {\n overflows.push(overflow[side]);\n }\n\n if (checkCrossAxis) {\n const sides = getAlignmentSides(placement, rects, rtl);\n overflows.push(overflow[sides[0]], overflow[sides[1]]);\n }\n\n overflowsData = [...overflowsData, {placement, overflows}];\n\n // One or more sides is overflowing.\n if (!overflows.every((side) => side <= 0)) {\n const nextIndex = (middlewareData.flip?.index || 0) + 1;\n const nextPlacement = placements[nextIndex];\n\n if (nextPlacement) {\n const ignoreCrossAxisOverflow =\n checkCrossAxis === 'alignment'\n ? initialSideAxis !== getSideAxis(nextPlacement)\n : false;\n\n if (\n !ignoreCrossAxisOverflow ||\n // We leave the current main axis only if every placement on that axis\n // overflows the main axis.\n overflowsData.every((d) =>\n getSideAxis(d.placement) === initialSideAxis\n ? d.overflows[0] > 0\n : true,\n )\n ) {\n // Try next placement and re-run the lifecycle.\n return {\n data: {\n index: nextIndex,\n overflows: overflowsData,\n },\n reset: {\n placement: nextPlacement,\n },\n };\n }\n }\n\n // First, find the candidates that fit on the mainAxis side of overflow,\n // then find the placement that fits the best on the main crossAxis side.\n let resetPlacement = overflowsData\n .filter((d) => d.overflows[0] <= 0)\n .sort((a, b) => a.overflows[1] - b.overflows[1])[0]?.placement;\n\n // Otherwise fallback.\n if (!resetPlacement) {\n switch (fallbackStrategy) {\n case 'bestFit': {\n const placement = overflowsData\n .filter((d) => {\n if (hasFallbackAxisSideDirection) {\n const currentSideAxis = getSideAxis(d.placement);\n return (\n currentSideAxis === initialSideAxis ||\n // Create a bias to the `y` side axis due to horizontal\n // reading directions favoring greater width.\n currentSideAxis === 'y'\n );\n }\n return true;\n })\n .map(\n (d) =>\n [\n d.placement,\n d.overflows\n .filter((overflow) => overflow > 0)\n .reduce((acc, overflow) => acc + overflow, 0),\n ] as const,\n )\n .sort((a, b) => a[1] - b[1])[0]?.[0];\n if (placement) {\n resetPlacement = placement;\n }\n break;\n }\n case 'initialPlacement':\n resetPlacement = initialPlacement;\n break;\n default:\n }\n }\n\n if (placement !== resetPlacement) {\n return {\n reset: {\n placement: resetPlacement,\n },\n };\n }\n }\n\n return {};\n },\n});\n","import type {Rect, SideObject} from '@floating-ui/utils';\nimport {evaluate, sides} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware} from '../types';\n\nfunction getSideOffsets(overflow: SideObject, rect: Rect) {\n return {\n top: overflow.top - rect.height,\n right: overflow.right - rect.width,\n bottom: overflow.bottom - rect.height,\n left: overflow.left - rect.width,\n };\n}\n\nfunction isAnySideFullyClipped(overflow: SideObject) {\n return sides.some((side) => overflow[side] >= 0);\n}\n\nexport interface HideOptions extends DetectOverflowOptions {\n /**\n * The strategy used to determine when to hide the floating element.\n */\n strategy?: 'referenceHidden' | 'escaped';\n}\n\n/**\n * Provides data to hide the floating element in applicable situations, such as\n * when it is not in the same clipping context as the reference element.\n * @see https://floating-ui.com/docs/hide\n */\nexport const hide = (\n options: HideOptions | Derivable<HideOptions> = {},\n): Middleware => ({\n name: 'hide',\n options,\n async fn(state) {\n const {rects, platform} = state;\n\n const {strategy = 'referenceHidden', ...detectOverflowOptions} = evaluate(\n options,\n state,\n );\n\n switch (strategy) {\n case 'referenceHidden': {\n const overflow = await platform.detectOverflow(state, {\n ...detectOverflowOptions,\n elementContext: 'reference',\n });\n const offsets = getSideOffsets(overflow, rects.reference);\n return {\n data: {\n referenceHiddenOffsets: offsets,\n referenceHidden: isAnySideFullyClipped(offsets),\n },\n };\n }\n case 'escaped': {\n const overflow = await platform.detectOverflow(state, {\n ...detectOverflowOptions,\n altBoundary: true,\n });\n const offsets = getSideOffsets(overflow, rects.floating);\n return {\n data: {\n escapedOffsets: offsets,\n escaped: isAnySideFullyClipped(offsets),\n },\n };\n }\n default: {\n return {};\n }\n }\n },\n});\n","import type {ClientRectObject, Padding} from '@floating-ui/utils';\nimport {\n evaluate,\n getPaddingObject,\n getSide,\n getSideAxis,\n max,\n min,\n rectToClientRect,\n} from '@floating-ui/utils';\n\nimport type {Derivable, Middleware} from '../types';\n\nfunction getBoundingRect(rects: Array<ClientRectObject>) {\n const minX = min(...rects.map((rect) => rect.left));\n const minY = min(...rects.map((rect) => rect.top));\n const maxX = max(...rects.map((rect) => rect.right));\n const maxY = max(...rects.map((rect) => rect.bottom));\n return {\n x: minX,\n y: minY,\n width: maxX - minX,\n height: maxY - minY,\n };\n}\n\nexport function getRectsByLine(rects: Array<ClientRectObject>) {\n const sortedRects = rects.slice().sort((a, b) => a.y - b.y);\n const groups = [];\n let prevRect: ClientRectObject | null = null;\n for (let i = 0; i < sortedRects.length; i++) {\n const rect = sortedRects[i];\n if (!prevRect || rect.y - prevRect.y > prevRect.height / 2) {\n groups.push([rect]);\n } else {\n groups[groups.length - 1].push(rect);\n }\n prevRect = rect;\n }\n return groups.map((rect) => rectToClientRect(getBoundingRect(rect)));\n}\n\nexport interface InlineOptions {\n /**\n * Viewport-relative `x` coordinate to choose a `ClientRect`.\n * @default undefined\n */\n x?: number;\n /**\n * Viewport-relative `y` coordinate to choose a `ClientRect`.\n * @default undefined\n */\n y?: number;\n /**\n * Represents the padding around a disjoined rect when choosing it.\n * @default 2\n */\n padding?: Padding;\n}\n\n/**\n * Provides improved positioning for inline reference elements that can span\n * over multiple lines, such as hyperlinks or range selections.\n * @see https://floating-ui.com/docs/inline\n */\nexport const inline = (\n options: InlineOptions | Derivable<InlineOptions> = {},\n): Middleware => ({\n name: 'inline',\n options,\n async fn(state) {\n const {placement, elements, rects, platform, strategy} = state;\n // A MouseEvent's client{X,Y} coords can be up to 2 pixels off a\n // ClientRect's bounds, despite the event listener being triggered. A\n // padding of 2 seems to handle this issue.\n const {padding = 2, x, y} = evaluate(options, state);\n\n const nativeClientRects = Array.from(\n (await platform.getClientRects?.(elements.reference)) || [],\n );\n\n const clientRects = getRectsByLine(nativeClientRects);\n const fallback = rectToClientRect(getBoundingRect(nativeClientRects));\n const paddingObject = getPaddingObject(padding);\n\n function getBoundingClientRect() {\n // There are two rects and they are disjoined.\n if (\n clientRects.length === 2 &&\n clientRects[0].left > clientRects[1].right &&\n x != null &&\n y != null\n ) {\n // Find the first rect in which the point is fully inside.\n return (\n clientRects.find(\n (rect) =>\n x > rect.left - paddingObject.left &&\n x < rect.right + paddingObject.right &&\n y > rect.top - paddingObject.top &&\n y < rect.bottom + paddingObject.bottom,\n ) || fallback\n );\n }\n\n // There are 2 or more connected rects.\n if (clientRects.length >= 2) {\n if (getSideAxis(placement) === 'y') {\n const firstRect = clientRects[0];\n const lastRect = clientRects[clientRects.length - 1];\n const isTop = getSide(placement) === 'top';\n\n const top = firstRect.top;\n const bottom = lastRect.bottom;\n const left = isTop ? firstRect.left : lastRect.left;\n const right = isTop ? firstRect.right : lastRect.right;\n const width = right - left;\n const height = bottom - top;\n\n return {\n top,\n bottom,\n left,\n right,\n width,\n height,\n x: left,\n y: top,\n };\n }\n\n const isLeftSide = getSide(placement) === 'left';\n const maxRight = max(...clientRects.map((rect) => rect.right));\n const minLeft = min(...clientRects.map((rect) => rect.left));\n const measureRects = clientRects.filter((rect) =>\n isLeftSide ? rect.left === minLeft : rect.right === maxRight,\n );\n\n const top = measureRects[0].top;\n const bottom = measureRects[measureRects.length - 1].bottom;\n const left = minLeft;\n const right = maxRight;\n const width = right - left;\n const height = bottom - top;\n\n return {\n top,\n bottom,\n left,\n right,\n width,\n height,\n x: left,\n y: top,\n };\n }\n\n return fallback;\n }\n\n const resetRects = await platform.getElementRects({\n reference: {getBoundingClientRect},\n floating: elements.floating,\n strategy,\n });\n\n if (\n rects.reference.x !== resetRects.reference.x ||\n rects.reference.y !== resetRects.reference.y ||\n rects.reference.width !== resetRects.reference.width ||\n rects.reference.height !== resetRects.reference.height\n ) {\n return {\n reset: {\n rects: resetRects,\n },\n };\n }\n\n return {};\n },\n});\n","export const originSides = new Set(['left', 'top']);\n","import {\n type Coords,\n evaluate,\n getAlignment,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nimport {originSides} from '../constants';\nimport type {Derivable, Middleware, MiddlewareState} from '../types';\n\ntype OffsetValue =\n | number\n | {\n /**\n * The axis that runs along the side of the floating element. Represents\n * the distance (gutter or margin) between the reference and floating\n * element.\n * @default 0\n */\n mainAxis?: number;\n /**\n * The axis that runs along the alignment of the floating element.\n * Represents the skidding between the reference and floating element.\n * @default 0\n */\n crossAxis?: number;\n /**\n * The same axis as `crossAxis` but applies only to aligned placements\n * and inverts the `end` alignment. When set to a number, it overrides the\n * `crossAxis` value.\n *\n * A positive number will move the floating element in the direction of\n * the opposite edge to the one that is aligned, while a negative number\n * the reverse.\n * @default null\n */\n alignmentAxis?: number | null;\n };\n\n// For type backwards-compatibility, the `OffsetOptions` type was also\n// Derivable.\nexport type OffsetOptions = OffsetValue | Derivable<OffsetValue>;\n\nexport async function convertValueToCoords(\n state: MiddlewareState,\n options: OffsetOptions,\n): Promise<Coords> {\n const {placement, platform, elements} = state;\n const rtl = await platform.isRTL?.(elements.floating);\n\n const side = getSide(placement);\n const alignment = getAlignment(placement);\n const isVertical = getSideAxis(placement) === 'y';\n const mainAxisMulti = originSides.has(side) ? -1 : 1;\n const crossAxisMulti = rtl && isVertical ? -1 : 1;\n const rawValue = evaluate(options, state);\n\n // eslint-disable-next-line prefer-const\n let {mainAxis, crossAxis, alignmentAxis} =\n typeof rawValue === 'number'\n ? {mainAxis: rawValue, crossAxis: 0, alignmentAxis: null}\n : {\n mainAxis: rawValue.mainAxis || 0,\n crossAxis: rawValue.crossAxis || 0,\n alignmentAxis: rawValue.alignmentAxis,\n };\n\n if (alignment && typeof alignmentAxis === 'number') {\n crossAxis = alignment === 'end' ? alignmentAxis * -1 : alignmentAxis;\n }\n\n return isVertical\n ? {x: crossAxis * crossAxisMulti, y: mainAxis * mainAxisMulti}\n : {x: mainAxis * mainAxisMulti, y: crossAxis * crossAxisMulti};\n}\n\n/**\n * Modifies the placement by translating the floating element along the\n * specified axes.\n * A number (shorthand for `mainAxis` or distance), or an axes configuration\n * object may be passed.\n * @see https://floating-ui.com/docs/offset\n */\nexport const offset = (options: OffsetOptions = 0): Middleware => ({\n name: 'offset',\n options,\n async fn(state) {\n const {x, y, placement, middlewareData} = state;\n const diffCoords = await convertValueToCoords(state, options);\n\n // If the placement is the same and the arrow caused an alignment offset\n // then we don't need to change the positioning coordinates.\n if (\n placement === middlewareData.offset?.placement &&\n middlewareData.arrow?.alignmentOffset\n ) {\n return {};\n }\n\n return {\n x: x + diffCoords.x,\n y: y + diffCoords.y,\n data: {\n ...diffCoords,\n placement,\n },\n };\n },\n});\n","import {\n type Coords,\n clamp,\n evaluate,\n getOppositeAxis,\n getSide,\n getSideAxis,\n} from '@floating-ui/utils';\n\nimport {originSides} from '../constants';\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware, MiddlewareState} from '../types';\n\nexport interface ShiftOptions extends DetectOverflowOptions {\n /**\n * The axis that runs along the alignment of the floating element. Determines\n * whether overflow along this axis is checked to perform shifting.\n * @default true\n */\n mainAxis?: boolean;\n /**\n * The axis that runs along the side of the floating element. Determines\n * whether overflow along this axis is checked to perform shifting.\n * @default false\n */\n crossAxis?: boolean;\n /**\n * Accepts a function that limits the shifting done in order to prevent\n * detachment.\n */\n limiter?: {\n fn: (state: MiddlewareState) => Coords;\n options?: any;\n };\n}\n\n/**\n * Optimizes the visibility of the floating element by shifting it in order to\n * keep it in view when it will overflow the clipping boundary.\n * @see https://floating-ui.com/docs/shift\n */\nexport const shift = (\n options: ShiftOptions | Derivable<ShiftOptions> = {},\n): Middleware => ({\n name: 'shift',\n options,\n async fn(state) {\n const {x, y, placement, platform} = state;\n\n const {\n mainAxis: checkMainAxis = true,\n crossAxis: checkCrossAxis = false,\n limiter = {fn: ({x, y}: Coords) => ({x, y})},\n ...detectOverflowOptions\n } = evaluate(options, state);\n\n const coords = {x, y};\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n const crossAxis = getSideAxis(getSide(placement));\n const mainAxis = getOppositeAxis(crossAxis);\n\n let mainAxisCoord = coords[mainAxis];\n let crossAxisCoord = coords[crossAxis];\n\n if (checkMainAxis) {\n const minSide = mainAxis === 'y' ? 'top' : 'left';\n const maxSide = mainAxis === 'y' ? 'bottom' : 'right';\n const min = mainAxisCoord + overflow[minSide];\n const max = mainAxisCoord - overflow[maxSide];\n\n mainAxisCoord = clamp(min, mainAxisCoord, max);\n }\n\n if (checkCrossAxis) {\n const minSide = crossAxis === 'y' ? 'top' : 'left';\n const maxSide = crossAxis === 'y' ? 'bottom' : 'right';\n const min = crossAxisCoord + overflow[minSide];\n const max = crossAxisCoord - overflow[maxSide];\n\n crossAxisCoord = clamp(min, crossAxisCoord, max);\n }\n\n const limitedCoords = limiter.fn({\n ...state,\n [mainAxis]: mainAxisCoord,\n [crossAxis]: crossAxisCoord,\n });\n\n return {\n ...limitedCoords,\n data: {\n x: limitedCoords.x - x,\n y: limitedCoords.y - y,\n enabled: {\n [mainAxis]: checkMainAxis,\n [crossAxis]: checkCrossAxis,\n },\n },\n };\n },\n});\n\ntype LimitShiftOffset =\n | number\n | {\n /**\n * Offset the limiting of the axis that runs along the alignment of the\n * floating element.\n */\n mainAxis?: number;\n /**\n * Offset the limiting of the axis that runs along the side of the\n * floating element.\n */\n crossAxis?: number;\n };\n\nexport interface LimitShiftOptions {\n /**\n * Offset when limiting starts. `0` will limit when the opposite edges of the\n * reference and floating elements are aligned.\n * - positive = start limiting earlier\n * - negative = start limiting later\n */\n offset?: LimitShiftOffset | Derivable<LimitShiftOffset>;\n /**\n * Whether to limit the axis that runs along the alignment of the floating\n * element.\n */\n mainAxis?: boolean;\n /**\n * Whether to limit the axis that runs along the side of the floating element.\n */\n crossAxis?: boolean;\n}\n\n/**\n * Built-in `limiter` that will stop `shift()` at a certain point.\n */\nexport const limitShift = (\n options: LimitShiftOptions | Derivable<LimitShiftOptions> = {},\n): {\n options: any;\n fn: (state: MiddlewareState) => Coords;\n} => ({\n options,\n fn(state) {\n const {x, y, placement, rects, middlewareData} = state;\n\n const {\n offset = 0,\n mainAxis: checkMainAxis = true,\n crossAxis: checkCrossAxis = true,\n } = evaluate(options, state);\n\n const coords = {x, y};\n const crossAxis = getSideAxis(placement);\n const mainAxis = getOppositeAxis(crossAxis);\n\n let mainAxisCoord = coords[mainAxis];\n let crossAxisCoord = coords[crossAxis];\n\n const rawOffset = evaluate(offset, state);\n const computedOffset =\n typeof rawOffset === 'number'\n ? {mainAxis: rawOffset, crossAxis: 0}\n : {mainAxis: 0, crossAxis: 0, ...rawOffset};\n\n if (checkMainAxis) {\n const len = mainAxis === 'y' ? 'height' : 'width';\n const limitMin =\n rects.reference[mainAxis] -\n rects.floating[len] +\n computedOffset.mainAxis;\n const limitMax =\n rects.reference[mainAxis] +\n rects.reference[len] -\n computedOffset.mainAxis;\n\n if (mainAxisCoord < limitMin) {\n mainAxisCoord = limitMin;\n } else if (mainAxisCoord > limitMax) {\n mainAxisCoord = limitMax;\n }\n }\n\n if (checkCrossAxis) {\n const len = mainAxis === 'y' ? 'width' : 'height';\n const isOriginSide = originSides.has(getSide(placement));\n const limitMin =\n rects.reference[crossAxis] -\n rects.floating[len] +\n (isOriginSide ? middlewareData.offset?.[crossAxis] || 0 : 0) +\n (isOriginSide ? 0 : computedOffset.crossAxis);\n const limitMax =\n rects.reference[crossAxis] +\n rects.reference[len] +\n (isOriginSide ? 0 : middlewareData.offset?.[crossAxis] || 0) -\n (isOriginSide ? computedOffset.crossAxis : 0);\n\n if (crossAxisCoord < limitMin) {\n crossAxisCoord = limitMin;\n } else if (crossAxisCoord > limitMax) {\n crossAxisCoord = limitMax;\n }\n }\n\n return {\n [mainAxis]: mainAxisCoord,\n [crossAxis]: crossAxisCoord,\n } as Coords;\n },\n});\n","import {\n evaluate,\n getAlignment,\n getSide,\n getSideAxis,\n max,\n min,\n} from '@floating-ui/utils';\n\nimport type {DetectOverflowOptions} from '../detectOverflow';\nimport type {Derivable, Middleware, MiddlewareState} from '../types';\n\nexport interface SizeOptions extends DetectOverflowOptions {\n /**\n * Function that is called to perform style mutations to the floating element\n * to change its size.\n * @default undefined\n */\n apply?(\n args: MiddlewareState & {\n availableWidth: number;\n availableHeight: number;\n },\n ): void | Promise<void>;\n}\n\n/**\n * Provides data that allows you to change the size of the floating element —\n * for instance, prevent it from overflowing the clipping boundary or match the\n * width of the reference element.\n * @see https://floating-ui.com/docs/size\n */\nexport const size = (\n options: SizeOptions | Derivable<SizeOptions> = {},\n): Middleware => ({\n name: 'size',\n options,\n async fn(state) {\n const {placement, rects, platform, elements} = state;\n\n const {apply = () => {}, ...detectOverflowOptions} = evaluate(\n options,\n state,\n );\n\n const overflow = await platform.detectOverflow(\n state,\n detectOverflowOptions,\n );\n const side = getSide(placement);\n const alignment = getAlignment(placement);\n const isYAxis = getSideAxis(placement) === 'y';\n const {width, height} = rects.floating;\n\n let heightSide: 'top' | 'bottom';\n let widthSide: 'left' | 'right';\n\n if (side === 'top' || side === 'bottom') {\n heightSide = side;\n widthSide =\n alignment ===\n ((await platform.isRTL?.(elements.floating)) ? 'start' : 'end')\n ? 'left'\n : 'right';\n } else {\n widthSide = side;\n heightSide = alignment === 'end' ? 'top' : 'bottom';\n }\n\n const maximumClippingHeight = height - overflow.top - overflow.bottom;\n const maximumClippingWidth = width - overflow.left - overflow.right;\n\n const overflowAvailableHeight = min(\n height - overflow[heightSide],\n maximumClippingHeight,\n );\n const overflowAvailableWidth = min(\n width - overflow[widthSide],\n maximumClippingWidth,\n );\n\n const noShift = !state.middlewareData.shift;\n\n let availableHeight = overflowAvailableHeight;\n let availableWidth = overflowAvailableWidth;\n\n if (state.middlewareData.shift?.enabled.x) {\n availableWidth = maximumClippingWidth;\n }\n if (state.middlewareData.shift?.enabled.y) {\n availableHeight = maximumClippingHeight;\n }\n\n if (noShift && !alignment) {\n const xMin = max(overflow.left, 0);\n const xMax = max(overflow.right, 0);\n const yMin = max(overflow.top, 0);\n const yMax = max(overflow.bottom, 0);\n\n if (isYAxis) {\n availableWidth =\n width -\n 2 *\n (xMin !== 0 || xMax !== 0\n ? xMin + xMax\n : max(overflow.left, overflow.right));\n } else {\n availableHeight =\n height -\n 2 *\n (yMin !== 0 || yMax !== 0\n ? yMin + yMax\n : max(overflow.top, overflow.bottom));\n }\n }\n\n await apply({...state, availableWidth, availableHeight});\n\n const nextDimensions = await platform.getDimensions(elements.floating);\n\n if (width !== nextDimensions.width || height !== nextDimensions.height) {\n return {\n reset: {\n rects: true,\n },\n };\n }\n\n return {};\n },\n});\n","type OverflowAncestors = Array<Element | Window | VisualViewport>;\n\nfunction hasWindow() {\n return typeof window !== 'undefined';\n}\n\nexport function getNodeName(node: Node | Window): string {\n if (isNode(node)) {\n return (node.nodeName || '').toLowerCase();\n }\n // Mocked nodes in testing environments may not be instances of Node. By\n // returning `#document` an infinite loop won't occur.\n // https://github.com/floating-ui/floating-ui/issues/2317\n return '#document';\n}\n\nexport function getWindow(node: any): typeof window {\n return node?.ownerDocument?.defaultView || window;\n}\n\nexport function getDocumentElement(node: Node | Window): HTMLElement {\n return (\n (isNode(node) ? node.ownerDocument : node.document) || window.document\n )?.documentElement;\n}\n\nexport function isNode(value: unknown): value is Node {\n if (!hasWindow()) {\n return false;\n }\n\n return value instanceof Node || value instanceof getWindow(value).Node;\n}\n\nexport function isElement(value: unknown): value is Element {\n if (!hasWindow()) {\n return false;\n }\n\n return value instanceof Element || value instanceof getWindow(value).Element;\n}\n\nexport function isHTMLElement(value: unknown): value is HTMLElement {\n if (!hasWindow()) {\n return false;\n }\n\n return (\n value instanceof HTMLElement ||\n value instanceof getWindow(value).HTMLElement\n );\n}\n\nexport function isShadowRoot(value: unknown): value is ShadowRoot {\n if (!hasWindow() || typeof ShadowRoot === 'undefined') {\n return false;\n }\n\n return (\n value instanceof ShadowRoot || value instanceof getWindow(value).ShadowRoot\n );\n}\n\nexport function isOverflowElement(element: Element): boolean {\n const {overflow, overflowX, overflowY, display} = getComputedStyle(element);\n return (\n /auto|scroll|overlay|hidden|clip/.test(overflow + overflowY + overflowX) &&\n display !== 'inline' &&\n display !== 'contents'\n );\n}\n\nexport function isTableElement(element: Element): boolean {\n return /^(table|td|th)$/.test(getNodeName(element));\n}\n\nexport function isTopLayer(element: Element): boolean {\n try {\n if (element.matches(':popover-open')) {\n return true;\n }\n } catch (_e) {\n // no-op\n }\n\n try {\n return element.matches(':modal');\n } catch (_e) {\n return false;\n }\n}\n\nconst willChangeRe = /transform|translate|scale|rotate|perspective|filter/;\nconst containRe = /paint|layout|strict|content/;\nconst isNotNone = (value: string) => !!value && value !== 'none';\nlet isWebKitValue: boolean | undefined;\n\nexport function isContainingBlock(\n elementOrCss: Element | CSSStyleDeclaration,\n): boolean {\n const css = isElement(elementOrCss)\n ? getComputedStyle(elementOrCss)\n : elementOrCss;\n\n // https://developer.mozilla.org/en-US/docs/Web/CSS/Containing_block#identifying_the_containing_block\n // https://drafts.csswg.org/css-transforms-2/#individual-transforms\n return (\n isNotNone(css.transform) ||\n isNotNone(css.translate) ||\n isNotNone(css.scale) ||\n isNotNone(css.rotate) ||\n isNotNone(css.perspective) ||\n (!isWebKit() && (isNotNone(css.backdropFilter) || isNotNone(css.filter))) ||\n willChangeRe.test(css.willChange || '') ||\n containRe.test(css.contain || '')\n );\n}\n\nexport function getContainingBlock(element: Element): HTMLElement | null {\n let currentNode: Node | null = getParentNode(element);\n\n while (isHTMLElement(currentNode) && !isLastTraversableNode(currentNode)) {\n if (isContainingBlock(currentNode)) {\n return currentNode;\n } else if (isTopLayer(currentNode)) {\n return null;\n }\n\n currentNode = getParentNode(currentNode);\n }\n\n return null;\n}\n\nexport function isWebKit(): boolean {\n if (isWebKitValue == null) {\n isWebKitValue =\n typeof CSS !== 'undefined' &&\n CSS.supports &&\n CSS.supports('-webkit-backdrop-filter', 'none');\n }\n\n return isWebKitValue;\n}\n\nexport function isLastTraversableNode(node: Node): boolean {\n return /^(html|body|#document)$/.test(getNodeName(node));\n}\n\nexport function getComputedStyle(element: Element): CSSStyleDeclaration {\n return getWindow(element).getComputedStyle(element);\n}\n\nexport function getNodeScroll(element: Element | Window): {\n scrollLeft: number;\n scrollTop: number;\n} {\n if (isElement(element)) {\n return {\n scrollLeft: element.scrollLeft,\n scrollTop: element.scrollTop,\n };\n }\n\n return {\n scrollLeft: element.scrollX,\n scrollTop: element.scrollY,\n };\n}\n\nexport function getParentNode(node: Node): Node {\n if (getNodeName(node) === 'html') {\n return node;\n }\n\n const result =\n // Step into the shadow DOM of the parent of a slotted node.\n (node as any).assignedSlot ||\n // DOM Element detected.\n node.parentNode ||\n // ShadowRoot detected.\n (isShadowRoot(node) && node.host) ||\n // Fallback.\n getDocumentElement(node);\n\n return isShadowRoot(result) ? result.host : result;\n}\n\nexport function getNearestOverflowAncestor(node: Node): HTMLElement {\n const parentNode = getParentNode(node);\n\n if (isLastTraversableNode(parentNode)) {\n return node.ownerDocument\n ? node.ownerDocument.body\n : (node as Document).body;\n }\n\n if (isHTMLElement(parentNode) && isOverflowElement(parentNode)) {\n return parentNode;\n }\n\n return getNearestOverflowAncestor(parentNode);\n}\n\nexport function getOverflowAncestors(\n node: Node,\n list: OverflowAncestors = [],\n traverseIframes = true,\n): OverflowAncestors {\n const scrollableAncestor = getNearestOverflowAncestor(node);\n const isBody = scrollableAncestor === node.ownerDocument?.body;\n const win = getWindow(scrollableAncestor);\n\n if (isBody) {\n const frameElement = getFrameElement(win);\n return list.concat(\n win,\n win.visualViewport || [],\n isOverflowElement(scrollableAncestor) ? scrollableAncestor : [],\n frameElement && traverseIframes ? getOverflowAncestors(frameElement) : [],\n );\n } else {\n return list.concat(\n scrollableAncestor,\n getOverflowAncestors(scrollableAncestor, [], traverseIframes),\n );\n }\n}\n\nexport function getFrameElement(win: Window): Element | null {\n return win.parent && Object.getPrototypeOf(win.parent)\n ? win.frameElement\n : null;\n}\n","import type {Dimensions} from '@floating-ui/core';\nimport {round} from '@floating-ui/utils';\nimport {getComputedStyle, isHTMLElement} from '@floating-ui/utils/dom';\n\nexport function getCssDimensions(element: Element): Dimensions & {$: boolean} {\n const css = getComputedStyle(element);\n // In testing environments, the `width` and `height` properties are empty\n // strings for SVG elements, returning NaN. Fallback to `0` in this case.\n let width = parseFloat(css.width) || 0;\n let height = parseFloat(css.height) || 0;\n const hasOffset = isHTMLElement(element);\n const offsetWidth = hasOffset ? element.offsetWidth : width;\n const offsetHeight = hasOffset ? element.offsetHeight : height;\n const shouldFallback =\n round(width) !== offsetWidth || round(height) !== offsetHeight;\n\n if (shouldFallback) {\n width = offsetWidth;\n height = offsetHeight;\n }\n\n return {\n width,\n height,\n $: shouldFallback,\n };\n}\n","import {isElement} from '../platform/isElement';\nimport type {VirtualElement} from '../types';\n\nexport function unwrapElement(element: Element | VirtualElement) {\n return !isElement(element) ? element.contextElement : element;\n}\n","import type {Coords} from '@floating-ui/core';\nimport {createCoords, round} from '@floating-ui/utils';\nimport {isHTMLElement} from '@floating-ui/utils/dom';\n\nimport type {VirtualElement} from '../types';\nimport {getCssDimensions} from '../utils/getCssDimensions';\nimport {unwrapElement} from '../utils/unwrapElement';\n\nexport function getScale(element: Element | VirtualElement): Coords {\n const domElement = unwrapElement(element);\n\n if (!isHTMLElement(domElement)) {\n return createCoords(1);\n }\n\n const rect = domElement.getBoundingClientRect();\n const {width, height, $} = getCssDimensions(domElement);\n let x = ($ ? round(rect.width) : rect.width) / width;\n let y = ($ ? round(rect.height) : rect.height) / height;\n\n // 0, NaN, or Infinity should always fallback to 1.\n\n if (!x || !Number.isFinite(x)) {\n x = 1;\n }\n\n if (!y || !Number.isFinite(y)) {\n y = 1;\n }\n\n return {\n x,\n y,\n };\n}\n","import type {Coords} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {getWindow, isWebKit} from '@floating-ui/utils/dom';\n\nconst noOffsets = createCoords(0);\n\nexport function getVisualOffsets(element: Element | undefined): Coords {\n const win = getWindow(element);\n\n if (!isWebKit() || !win.visualViewport) {\n return noOffsets;\n }\n\n return {\n x: win.visualViewport.offsetLeft,\n y: win.visualViewport.offsetTop,\n };\n}\n\nexport function shouldAddVisualOffsets(\n element: Element | undefined,\n isFixed = false,\n floatingOffsetParent?: Element | Window | undefined,\n): boolean {\n if (\n !floatingOffsetParent ||\n (isFixed && floatingOffsetParent !== getWindow(element))\n ) {\n return false;\n }\n\n return isFixed;\n}\n","import type {ClientRectObject} from '@floating-ui/core';\nimport {rectToClientRect} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {getComputedStyle, getWindow} from '@floating-ui/utils/dom';\n\nimport {getScale} from '../platform/getScale';\nimport {isElement} from '../platform/isElement';\nimport {getVisualOffsets, shouldAddVisualOffsets} from './getVisualOffsets';\nimport {unwrapElement} from './unwrapElement';\nimport type {VirtualElement} from '../types';\nimport {getFrameElement} from '@floating-ui/utils/dom';\n\nexport function getBoundingClientRect(\n element: Element | VirtualElement,\n includeScale = false,\n isFixedStrategy = false,\n offsetParent?: Element | Window,\n): ClientRectObject {\n const clientRect = element.getBoundingClientRect();\n const domElement = unwrapElement(element);\n\n let scale = createCoords(1);\n if (includeScale) {\n if (offsetParent) {\n if (isElement(offsetParent)) {\n scale = getScale(offsetParent);\n }\n } else {\n scale = getScale(element);\n }\n }\n\n const visualOffsets = shouldAddVisualOffsets(\n domElement,\n isFixedStrategy,\n offsetParent,\n )\n ? getVisualOffsets(domElement)\n : createCoords(0);\n\n let x = (clientRect.left + visualOffsets.x) / scale.x;\n let y = (clientRect.top + visualOffsets.y) / scale.y;\n let width = clientRect.width / scale.x;\n let height = clientRect.height / scale.y;\n\n if (domElement) {\n const win = getWindow(domElement);\n const offsetWin =\n offsetParent && isElement(offsetParent)\n ? getWindow(offsetParent)\n : offsetParent;\n\n let currentWin = win;\n let currentIFrame = getFrameElement(currentWin);\n while (currentIFrame && offsetParent && offsetWin !== currentWin) {\n const iframeScale = getScale(currentIFrame);\n const iframeRect = currentIFrame.getBoundingClientRect();\n const css = getComputedStyle(currentIFrame);\n const left =\n iframeRect.left +\n (currentIFrame.clientLeft + parseFloat(css.paddingLeft)) *\n iframeScale.x;\n const top =\n iframeRect.top +\n (currentIFrame.clientTop + parseFloat(css.paddingTop)) * iframeScale.y;\n\n x *= iframeScale.x;\n y *= iframeScale.y;\n width *= iframeScale.x;\n height *= iframeScale.y;\n\n x += left;\n y += top;\n\n currentWin = getWindow(currentIFrame);\n currentIFrame = getFrameElement(currentWin);\n }\n }\n\n return rectToClientRect({width, height, x, y});\n}\n","import {getNodeScroll} from '@floating-ui/utils/dom';\n\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getBoundingClientRect} from './getBoundingClientRect';\n\n// If <html> has a CSS width greater than the viewport, then this will be\n// incorrect for RTL.\nexport function getWindowScrollBarX(element: Element, rect?: DOMRect): number {\n const leftScroll = getNodeScroll(element).scrollLeft;\n\n if (!rect) {\n return getBoundingClientRect(getDocumentElement(element)).left + leftScroll;\n }\n\n return rect.left + leftScroll;\n}\n","import type {NodeScroll} from '../types';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\n\nexport function getHTMLOffset(\n documentElement: HTMLElement,\n scroll: NodeScroll,\n) {\n const htmlRect = documentElement.getBoundingClientRect();\n const x =\n htmlRect.left +\n scroll.scrollLeft -\n getWindowScrollBarX(documentElement, htmlRect);\n const y = htmlRect.top + scroll.scrollTop;\n\n return {\n x,\n y,\n };\n}\n","import type {Elements, Rect, Strategy} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {\n getDocumentElement,\n getNodeName,\n getNodeScroll,\n isHTMLElement,\n isOverflowElement,\n isTopLayer,\n} from '@floating-ui/utils/dom';\n\nimport {getBoundingClientRect} from '../utils/getBoundingClientRect';\nimport {getScale} from './getScale';\nimport {getHTMLOffset} from '../utils/getHTMLOffset';\n\nexport function convertOffsetParentRelativeRectToViewportRelativeRect({\n elements,\n rect,\n offsetParent,\n strategy,\n}: {\n elements?: Elements;\n rect: Rect;\n offsetParent: Element | Window;\n strategy: Strategy;\n}): Rect {\n const isFixed = strategy === 'fixed';\n const documentElement = getDocumentElement(offsetParent);\n const topLayer = elements ? isTopLayer(elements.floating) : false;\n\n if (offsetParent === documentElement || (topLayer && isFixed)) {\n return rect;\n }\n\n let scroll = {scrollLeft: 0, scrollTop: 0};\n let scale = createCoords(1);\n const offsets = createCoords(0);\n const isOffsetParentAnElement = isHTMLElement(offsetParent);\n\n if (isOffsetParentAnElement || (!isOffsetParentAnElement && !isFixed)) {\n if (\n getNodeName(offsetParent) !== 'body' ||\n isOverflowElement(documentElement)\n ) {\n scroll = getNodeScroll(offsetParent);\n }\n\n if (isOffsetParentAnElement) {\n const offsetRect = getBoundingClientRect(offsetParent);\n scale = getScale(offsetParent);\n offsets.x = offsetRect.x + offsetParent.clientLeft;\n offsets.y = offsetRect.y + offsetParent.clientTop;\n }\n }\n\n const htmlOffset =\n documentElement && !isOffsetParentAnElement && !isFixed\n ? getHTMLOffset(documentElement, scroll)\n : createCoords(0);\n\n return {\n width: rect.width * scale.x,\n height: rect.height * scale.y,\n x:\n rect.x * scale.x - scroll.scrollLeft * scale.x + offsets.x + htmlOffset.x,\n y: rect.y * scale.y - scroll.scrollTop * scale.y + offsets.y + htmlOffset.y,\n };\n}\n","export function getClientRects(element: Element) {\n return Array.from(element.getClientRects());\n}\n","import type {Rect} from '@floating-ui/core';\nimport {max} from '@floating-ui/utils';\nimport {getComputedStyle, getNodeScroll} from '@floating-ui/utils/dom';\n\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\n\n// Gets the entire size of the scrollable document area, even extending outside\n// of the `<html>` and `<body>` rect bounds if horizontally scrollable.\nexport function getDocumentRect(element: HTMLElement): Rect {\n const html = getDocumentElement(element);\n const scroll = getNodeScroll(element);\n const body = element.ownerDocument.body;\n\n const width = max(\n html.scrollWidth,\n html.clientWidth,\n body.scrollWidth,\n body.clientWidth,\n );\n const height = max(\n html.scrollHeight,\n html.clientHeight,\n body.scrollHeight,\n body.clientHeight,\n );\n\n let x = -scroll.scrollLeft + getWindowScrollBarX(element);\n const y = -scroll.scrollTop;\n\n if (getComputedStyle(body).direction === 'rtl') {\n x += max(html.clientWidth, body.clientWidth) - width;\n }\n\n return {\n width,\n height,\n x,\n y,\n };\n}\n","import type {Rect, Strategy} from '@floating-ui/core';\nimport {getWindow, isWebKit} from '@floating-ui/utils/dom';\n\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\n\n// Safety check: ensure the scrollbar space is reasonable in case this\n// calculation is affected by unusual styles.\n// Most scrollbars leave 15-18px of space.\nconst SCROLLBAR_MAX = 25;\n\nexport function getViewportRect(element: Element, strategy: Strategy): Rect {\n const win = getWindow(element);\n const html = getDocumentElement(element);\n const visualViewport = win.visualViewport;\n\n let width = html.clientWidth;\n let height = html.clientHeight;\n let x = 0;\n let y = 0;\n\n if (visualViewport) {\n width = visualViewport.width;\n height = visualViewport.height;\n\n const visualViewportBased = isWebKit();\n\n if (!visualViewportBased || (visualViewportBased && strategy === 'fixed')) {\n x = visualViewport.offsetLeft;\n y = visualViewport.offsetTop;\n }\n }\n\n const windowScrollbarX = getWindowScrollBarX(html);\n // <html> `overflow: hidden` + `scrollbar-gutter: stable` reduces the\n // visual width of the <html> but this is not considered in the size\n // of `html.clientWidth`.\n if (windowScrollbarX <= 0) {\n const doc = html.ownerDocument;\n const body = doc.body;\n const bodyStyles = getComputedStyle(body);\n const bodyMarginInline =\n doc.compatMode === 'CSS1Compat'\n ? parseFloat(bodyStyles.marginLeft) +\n parseFloat(bodyStyles.marginRight) || 0\n : 0;\n const clippingStableScrollbarWidth = Math.abs(\n html.clientWidth - body.clientWidth - bodyMarginInline,\n );\n\n if (clippingStableScrollbarWidth <= SCROLLBAR_MAX) {\n width -= clippingStableScrollbarWidth;\n }\n } else if (windowScrollbarX <= SCROLLBAR_MAX) {\n // If the <body> scrollbar is on the left, the width needs to be extended\n // by the scrollbar amount so there isn't extra space on the right.\n width += windowScrollbarX;\n }\n\n return {\n width,\n height,\n x,\n y,\n };\n}\n","import type {\n Boundary,\n ClientRectObject,\n Rect,\n RootBoundary,\n Strategy,\n} from '@floating-ui/core';\nimport {rectToClientRect} from '@floating-ui/core';\nimport {createCoords, max, min} from '@floating-ui/utils';\nimport {\n getComputedStyle,\n getDocumentElement,\n getNodeName,\n getOverflowAncestors,\n getParentNode,\n isContainingBlock,\n isHTMLElement,\n isLastTraversableNode,\n isOverflowElement,\n isTopLayer,\n} from '@floating-ui/utils/dom';\n\nimport type {Platform, ReferenceElement} from '../types';\nimport {getBoundingClientRect} from '../utils/getBoundingClientRect';\nimport {getDocumentRect} from '../utils/getDocumentRect';\nimport {getViewportRect} from '../utils/getViewportRect';\nimport {getVisualOffsets} from '../utils/getVisualOffsets';\nimport {getScale} from './getScale';\nimport {isElement} from './isElement';\n\ntype PlatformWithCache = Platform & {\n _c: Map<ReferenceElement, Element[]>;\n};\n\n// Returns the inner client rect, subtracting scrollbars if present.\nfunction getInnerBoundingClientRect(\n element: Element,\n strategy: Strategy,\n): Rect {\n const clientRect = getBoundingClientRect(element, true, strategy === 'fixed');\n const top = clientRect.top + element.clientTop;\n const left = clientRect.left + element.clientLeft;\n const scale = isHTMLElement(element) ? getScale(element) : createCoords(1);\n const width = element.clientWidth * scale.x;\n const height = element.clientHeight * scale.y;\n const x = left * scale.x;\n const y = top * scale.y;\n\n return {\n width,\n height,\n x,\n y,\n };\n}\n\nfunction getClientRectFromClippingAncestor(\n element: Element,\n clippingAncestor: Element | RootBoundary,\n strategy: Strategy,\n): ClientRectObject {\n let rect: Rect;\n\n if (clippingAncestor === 'viewport') {\n rect = getViewportRect(element, strategy);\n } else if (clippingAncestor === 'document') {\n rect = getDocumentRect(getDocumentElement(element));\n } else if (isElement(clippingAncestor)) {\n rect = getInnerBoundingClientRect(clippingAncestor, strategy);\n } else {\n const visualOffsets = getVisualOffsets(element);\n rect = {\n x: clippingAncestor.x - visualOffsets.x,\n y: clippingAncestor.y - visualOffsets.y,\n width: clippingAncestor.width,\n height: clippingAncestor.height,\n };\n }\n\n return rectToClientRect(rect);\n}\n\nfunction hasFixedPositionAncestor(element: Element, stopNode: Node): boolean {\n const parentNode = getParentNode(element);\n if (\n parentNode === stopNode ||\n !isElement(parentNode) ||\n isLastTraversableNode(parentNode)\n ) {\n return false;\n }\n\n return (\n getComputedStyle(parentNode).position === 'fixed' ||\n hasFixedPositionAncestor(parentNode, stopNode)\n );\n}\n\n// A \"clipping ancestor\" is an `overflow` element with the characteristic of\n// clipping (or hiding) child elements. This returns all clipping ancestors\n// of the given element up the tree.\nfunction getClippingElementAncestors(\n element: Element,\n cache: PlatformWithCache['_c'],\n): Array<Element> {\n const cachedResult = cache.get(element);\n if (cachedResult) {\n return cachedResult;\n }\n\n let result = getOverflowAncestors(element, [], false).filter(\n (el) => isElement(el) && getNodeName(el) !== 'body',\n ) as Array<Element>;\n let currentContainingBlockComputedStyle: CSSStyleDeclaration | null = null;\n const elementIsFixed = getComputedStyle(element).position === 'fixed';\n let currentNode: Node | null = elementIsFixed\n ? getParentNode(element)\n : element;\n\n // https://developer.mozilla.org/en-US/docs/Web/CSS/Containing_block#identifying_the_containing_block\n while (isElement(currentNode) && !isLastTraversableNode(currentNode)) {\n const computedStyle = getComputedStyle(currentNode);\n const currentNodeIsContaining = isContainingBlock(currentNode);\n\n if (!currentNodeIsContaining && computedStyle.position === 'fixed') {\n currentContainingBlockComputedStyle = null;\n }\n\n const shouldDropCurrentNode = elementIsFixed\n ? !currentNodeIsContaining && !currentContainingBlockComputedStyle\n : (!currentNodeIsContaining &&\n computedStyle.position === 'static' &&\n !!currentContainingBlockComputedStyle &&\n (currentContainingBlockComputedStyle.position === 'absolute' ||\n currentContainingBlockComputedStyle.position === 'fixed')) ||\n (isOverflowElement(currentNode) &&\n !currentNodeIsContaining &&\n hasFixedPositionAncestor(element, currentNode));\n\n if (shouldDropCurrentNode) {\n // Drop non-containing blocks.\n result = result.filter((ancestor) => ancestor !== currentNode);\n } else {\n // Record last containing block for next iteration.\n currentContainingBlockComputedStyle = computedStyle;\n }\n\n currentNode = getParentNode(currentNode);\n }\n\n cache.set(element, result);\n\n return result;\n}\n\n// Gets the maximum area that the element is visible in due to any number of\n// clipping ancestors.\nexport function getClippingRect(\n this: PlatformWithCache,\n {\n element,\n boundary,\n rootBoundary,\n strategy,\n }: {\n element: Element;\n boundary: Boundary;\n rootBoundary: RootBoundary;\n strategy: Strategy;\n },\n): Rect {\n const elementClippingAncestors =\n boundary === 'clippingAncestors'\n ? isTopLayer(element)\n ? []\n : getClippingElementAncestors(element, this._c)\n : [].concat(boundary);\n const clippingAncestors = [...elementClippingAncestors, rootBoundary];\n\n const firstRect = getClientRectFromClippingAncestor(\n element,\n clippingAncestors[0],\n strategy,\n );\n let top = firstRect.top;\n let right = firstRect.right;\n let bottom = firstRect.bottom;\n let left = firstRect.left;\n\n for (let i = 1; i < clippingAncestors.length; i++) {\n const rect = getClientRectFromClippingAncestor(\n element,\n clippingAncestors[i],\n strategy,\n );\n top = max(rect.top, top);\n right = min(rect.right, right);\n bottom = min(rect.bottom, bottom);\n left = max(rect.left, left);\n }\n\n return {\n width: right - left,\n height: bottom - top,\n x: left,\n y: top,\n };\n}\n","import type {Dimensions} from '@floating-ui/core';\n\nimport {getCssDimensions} from '../utils/getCssDimensions';\n\nexport function getDimensions(element: Element): Dimensions {\n const {width, height} = getCssDimensions(element);\n return {width, height};\n}\n","import type {Rect, Strategy} from '@floating-ui/core';\nimport {createCoords} from '@floating-ui/utils';\nimport {\n getNodeName,\n getNodeScroll,\n isHTMLElement,\n isOverflowElement,\n} from '@floating-ui/utils/dom';\n\nimport type {VirtualElement} from '../types';\nimport {getDocumentElement} from '../platform/getDocumentElement';\nimport {getBoundingClientRect} from './getBoundingClientRect';\nimport {getWindowScrollBarX} from './getWindowScrollBarX';\nimport {getHTMLOffset} from './getHTMLOffset';\n\nexport function getRectRelativeToOffsetParent(\n element: Element | VirtualElement,\n offsetParent: Element | Window,\n strategy: Strategy,\n): Rect {\n const isOffsetParentAnElement = isHTMLElement(offsetParent);\n const documentElement = getDocumentElement(offsetParent);\n const isFixed = strategy === 'fixed';\n const rect = getBoundingClientRect(element, true, isFixed, offsetParent);\n\n let scroll = {scrollLeft: 0, scrollTop: 0};\n const offsets = createCoords(0);\n\n // If the <body> scrollbar appears on the left (e.g. RTL systems). Use\n // Firefox with layout.scrollbar.side = 3 in about:config to test this.\n function setLeftRTLScrollbarOffset() {\n offsets.x = getWindowScrollBarX(documentElement);\n }\n\n if (isOffsetParentAnElement || (!isOffsetParentAnElement && !isFixed)) {\n if (\n getNodeName(offsetParent) !== 'body' ||\n isOverflowElement(documentElement)\n ) {\n scroll = getNodeScroll(offsetParent);\n }\n\n if (isOffsetParentAnElement) {\n const offsetRect = getBoundingClientRect(\n offsetParent,\n true,\n isFixed,\n offsetParent,\n );\n offsets.x = offsetRect.x + offsetParent.clientLeft;\n offsets.y = offsetRect.y + offsetParent.clientTop;\n } else if (documentElement) {\n setLeftRTLScrollbarOffset();\n }\n }\n\n if (isFixed && !isOffsetParentAnElement && documentElement) {\n setLeftRTLScrollbarOffset();\n }\n\n const htmlOffset =\n documentElement && !isOffsetParentAnElement && !isFixed\n ? getHTMLOffset(documentElement, scroll)\n : createCoords(0);\n\n const x = rect.left + scroll.scrollLeft - offsets.x - htmlOffset.x;\n const y = rect.top + scroll.scrollTop - offsets.y - htmlOffset.y;\n\n return {\n x,\n y,\n width: rect.width,\n height: rect.height,\n };\n}\n","import {getComputedStyle} from '@floating-ui/utils/dom';\n\nexport function isStaticPositioned(element: Element): boolean {\n return getComputedStyle(element).position === 'static';\n}\n","import {\n getComputedStyle,\n getContainingBlock,\n getDocumentElement,\n getParentNode,\n getWindow,\n isContainingBlock,\n isElement,\n isHTMLElement,\n isLastTraversableNode,\n isTableElement,\n isTopLayer,\n} from '@floating-ui/utils/dom';\nimport {isStaticPositioned} from '../utils/isStaticPositioned';\n\ntype Polyfill = (element: HTMLElement) => Element | null;\n\nfunction getTrueOffsetParent(\n element: Element,\n polyfill: Polyfill | undefined,\n): Element | null {\n if (\n !isHTMLElement(element) ||\n getComputedStyle(element).position === 'fixed'\n ) {\n return null;\n }\n\n if (polyfill) {\n return polyfill(element);\n }\n\n let rawOffsetParent = element.offsetParent;\n\n // Firefox returns the <html> element as the offsetParent if it's non-static,\n // while Chrome and Safari return the <body> element. The <body> element must\n // be used to perform the correct calculations even if the <html> element is\n // non-static.\n if (getDocumentElement(element) === rawOffsetParent) {\n rawOffsetParent = rawOffsetParent.ownerDocument.body;\n }\n\n return rawOffsetParent;\n}\n\n// Gets the closest ancestor positioned element. Handles some edge cases,\n// such as table ancestors and cross browser bugs.\nexport function getOffsetParent(\n element: Element,\n polyfill?: Polyfill,\n): Element | Window {\n const win = getWindow(element);\n\n if (isTopLayer(element)) {\n return win;\n }\n\n if (!isHTMLElement(element)) {\n let svgOffsetParent = getParentNode(element);\n while (svgOffsetParent && !isLastTraversableNode(svgOffsetParent)) {\n if (isElement(svgOffsetParent) && !isStaticPositioned(svgOffsetParent)) {\n return svgOffsetParent;\n }\n svgOffsetParent = getParentNode(svgOffsetParent);\n }\n return win;\n }\n\n let offsetParent = getTrueOffsetParent(element, polyfill);\n\n while (\n offsetParent &&\n isTableElement(offsetParent) &&\n isStaticPositioned(offsetParent)\n ) {\n offsetParent = getTrueOffsetParent(offsetParent, polyfill);\n }\n\n if (\n offsetParent &&\n isLastTraversableNode(offsetParent) &&\n isStaticPositioned(offsetParent) &&\n !isContainingBlock(offsetParent)\n ) {\n return win;\n }\n\n return offsetParent || getContainingBlock(element) || win;\n}\n","import type {Platform} from '../types';\nimport {getRectRelativeToOffsetParent} from '../utils/getRectRelativeToOffsetParent';\nimport {getOffsetParent} from './getOffsetParent';\n\nexport const getElementRects: Platform['getElementRects'] = async function (\n this: Platform,\n data,\n) {\n const getOffsetParentFn = this.getOffsetParent || getOffsetParent;\n const getDimensionsFn = this.getDimensions;\n const floatingDimensions = await getDimensionsFn(data.floating);\n\n return {\n reference: getRectRelativeToOffsetParent(\n data.reference,\n await getOffsetParentFn(data.floating),\n data.strategy,\n ),\n floating: {\n x: 0,\n y: 0,\n width: floatingDimensions.width,\n height: floatingDimensions.height,\n },\n };\n};\n","import {getComputedStyle} from '@floating-ui/utils/dom';\n\nexport function isRTL(element: Element) {\n return getComputedStyle(element).direction === 'rtl';\n}\n","import {convertOffsetParentRelativeRectToViewportRelativeRect} from './platform/convertOffsetParentRelativeRectToViewportRelativeRect';\nimport {getClientRects} from './platform/getClientRects';\nimport {getClippingRect} from './platform/getClippingRect';\nimport {getDimensions} from './platform/getDimensions';\nimport {getDocumentElement} from './platform/getDocumentElement';\nimport {getElementRects} from './platform/getElementRects';\nimport {getOffsetParent} from './platform/getOffsetParent';\nimport {getScale} from './platform/getScale';\nimport {isElement} from './platform/isElement';\nimport {isRTL} from './platform/isRTL';\nimport type {Platform} from './types';\n\nexport const platform: Platform = {\n convertOffsetParentRelativeRectToViewportRelativeRect,\n getDocumentElement,\n getClippingRect,\n getOffsetParent,\n getElementRects,\n getClientRects,\n getDimensions,\n getScale,\n isElement,\n isRTL,\n};\n","import type {ClientRectObject} from '@floating-ui/core';\n\nexport function rectsAreEqual(a: ClientRectObject, b: ClientRectObject) {\n return (\n a.x === b.x && a.y === b.y && a.width === b.width && a.height === b.height\n );\n}\n","import {floor, max, min} from '@floating-ui/utils';\nimport {getDocumentElement, getOverflowAncestors} from '@floating-ui/utils/dom';\n\nimport type {FloatingElement, ReferenceElement} from './types';\nimport {getBoundingClientRect} from './utils/getBoundingClientRect';\nimport {unwrapElement} from './utils/unwrapElement';\nimport {rectsAreEqual} from './utils/rectsAreEqual';\n\nexport interface AutoUpdateOptions {\n /**\n * Whether to update the position when an overflow ancestor is scrolled.\n * @default true\n */\n ancestorScroll?: boolean;\n /**\n * Whether to update the position when an overflow ancestor is resized. This\n * uses the native `resize` event.\n * @default true\n */\n ancestorResize?: boolean;\n /**\n * Whether to update the position when either the reference or floating\n * elements resized. This uses a `ResizeObserver`.\n * @default true\n */\n elementResize?: boolean;\n /**\n * Whether to update the position when the reference relocated on the screen\n * due to layout shift.\n * @default true\n */\n layoutShift?: boolean;\n /**\n * Whether to update on every animation frame if necessary. Only use if you\n * need to update the position in response to an animation using transforms.\n * @default false\n */\n animationFrame?: boolean;\n}\n\n// https://samthor.au/2021/observing-dom/\nfunction observeMove(element: Element, onMove: () => void) {\n let io: IntersectionObserver | null = null;\n let timeoutId: NodeJS.Timeout;\n\n const root = getDocumentElement(element);\n\n function cleanup() {\n clearTimeout(timeoutId);\n io?.disconnect();\n io = null;\n }\n\n function refresh(skip = false, threshold = 1) {\n cleanup();\n\n const elementRectForRootMargin = element.getBoundingClientRect();\n const {left, top, width, height} = elementRectForRootMargin;\n\n if (!skip) {\n onMove();\n }\n\n if (!width || !height) {\n return;\n }\n\n const insetTop = floor(top);\n const insetRight = floor(root.clientWidth - (left + width));\n const insetBottom = floor(root.clientHeight - (top + height));\n const insetLeft = floor(left);\n const rootMargin = `${-insetTop}px ${-insetRight}px ${-insetBottom}px ${-insetLeft}px`;\n\n const options = {\n rootMargin,\n threshold: max(0, min(1, threshold)) || 1,\n };\n\n let isFirstUpdate = true;\n\n function handleObserve(entries: IntersectionObserverEntry[]) {\n const ratio = entries[0].intersectionRatio;\n\n if (ratio !== threshold) {\n if (!isFirstUpdate) {\n return refresh();\n }\n\n if (!ratio) {\n // If the reference is clipped, the ratio is 0. Throttle the refresh\n // to prevent an infinite loop of updates.\n timeoutId = setTimeout(() => {\n refresh(false, 1e-7);\n }, 1000);\n } else {\n refresh(false, ratio);\n }\n }\n\n if (\n ratio === 1 &&\n !rectsAreEqual(\n elementRectForRootMargin,\n element.getBoundingClientRect(),\n )\n ) {\n // It's possible that even though the ratio is reported as 1, the\n // element is not actually fully within the IntersectionObserver's root\n // area anymore. This can happen under performance constraints. This may\n // be a bug in the browser's IntersectionObserver implementation. To\n // work around this, we compare the element's bounding rect now with\n // what it was at the time we created the IntersectionObserver. If they\n // are not equal then the element moved, so we refresh.\n refresh();\n }\n\n isFirstUpdate = false;\n }\n\n // Older browsers don't support a `document` as the root and will throw an\n // error.\n try {\n io = new IntersectionObserver(handleObserve, {\n ...options,\n // Handle <iframe>s\n root: root.ownerDocument,\n });\n } catch (_e) {\n io = new IntersectionObserver(handleObserve, options);\n }\n\n io.observe(element);\n }\n\n refresh(true);\n\n return cleanup;\n}\n\n/**\n * Automatically updates the position of the floating element when necessary.\n * Should only be called when the floating element is mounted on the DOM or\n * visible on the screen.\n * @returns cleanup function that should be invoked when the floating element is\n * removed from the DOM or hidden from the screen.\n * @see https://floating-ui.com/docs/autoUpdate\n */\nexport function autoUpdate(\n reference: ReferenceElement,\n floating: FloatingElement | null,\n update: () => void,\n options: AutoUpdateOptions = {},\n) {\n const {\n ancestorScroll = true,\n ancestorResize = true,\n elementResize = typeof ResizeObserver === 'function',\n layoutShift = typeof IntersectionObserver === 'function',\n animationFrame = false,\n } = options;\n\n const referenceEl = unwrapElement(reference);\n\n const ancestors =\n ancestorScroll || ancestorResize\n ? [\n ...(referenceEl ? getOverflowAncestors(referenceEl) : []),\n ...(floating ? getOverflowAncestors(floating) : []),\n ]\n : [];\n\n ancestors.forEach((ancestor) => {\n ancestorScroll &&\n ancestor.addEventListener('scroll', update, {passive: true});\n ancestorResize && ancestor.addEventListener('resize', update);\n });\n\n const cleanupIo =\n referenceEl && layoutShift ? observeMove(referenceEl, update) : null;\n\n let reobserveFrame = -1;\n let resizeObserver: ResizeObserver | null = null;\n\n if (elementResize) {\n resizeObserver = new ResizeObserver(([firstEntry]) => {\n if (\n firstEntry &&\n firstEntry.target === referenceEl &&\n resizeObserver &&\n floating\n ) {\n // Prevent update loops when using the `size` middleware.\n // https://github.com/floating-ui/floating-ui/issues/1740\n resizeObserver.unobserve(floating);\n cancelAnimationFrame(reobserveFrame);\n reobserveFrame = requestAnimationFrame(() => {\n resizeObserver?.observe(floating);\n });\n }\n update();\n });\n\n if (referenceEl && !animationFrame) {\n resizeObserver.observe(referenceEl);\n }\n\n if (floating) {\n resizeObserver.observe(floating);\n }\n }\n\n let frameId: number;\n let prevRefRect = animationFrame ? getBoundingClientRect(reference) : null;\n\n if (animationFrame) {\n frameLoop();\n }\n\n function frameLoop() {\n const nextRefRect = getBoundingClientRect(reference);\n\n if (prevRefRect && !rectsAreEqual(prevRefRect, nextRefRect)) {\n update();\n }\n\n prevRefRect = nextRefRect;\n frameId = requestAnimationFrame(frameLoop);\n }\n\n update();\n\n return () => {\n ancestors.forEach((ancestor) => {\n ancestorScroll && ancestor.removeEventListener('scroll', update);\n ancestorResize && ancestor.removeEventListener('resize', update);\n });\n\n cleanupIo?.();\n resizeObserver?.disconnect();\n resizeObserver = null;\n\n if (animationFrame) {\n cancelAnimationFrame(frameId);\n }\n };\n}\n","// createFloating — Popper.js-equivalent imperative manager for @domphy/floating.\r\n//\r\n// Wraps `computePosition` + `autoUpdate` into a stateful handle so callers do\r\n// not have to manage the cleanup function themselves or re-implement the\r\n// \"call computePosition on every autoUpdate tick\" loop.\r\n//\r\n// Intentionally framework-agnostic: no @domphy/core dependency. Wire it to\r\n// any lifecycle system — Domphy `_onMount`/`_onBeforeRemove`, vanilla JS, or\r\n// plain event listeners.\r\n\r\nimport {computePosition as computePositionCore} from '@floating-ui/core';\r\nimport type {MiddlewareData, Placement, Strategy} from '@floating-ui/core';\r\n\r\nimport {autoUpdate} from './autoUpdate.js';\r\nimport {platform} from './platform.js';\r\nimport type {\r\n AutoUpdateOptions,\r\n ComputePositionConfig,\r\n FloatingElement,\r\n ReferenceElement,\r\n} from './types.js';\r\n\r\n/**\r\n * The position result from the most recent `computePosition` call. Mirrors\r\n * the shape returned by `computePosition` for easy destructuring.\r\n */\r\nexport interface FloatingPosition {\r\n /** Left offset in pixels — apply as `style.left`. */\r\n x: number;\r\n /** Top offset in pixels — apply as `style.top`. */\r\n y: number;\r\n /**\r\n * The resolved placement after all middleware ran. May differ from the\r\n * preferred placement when `flip` or `autoPlacement` changed it.\r\n */\r\n placement: Placement;\r\n /**\r\n * CSS position strategy. Matches the `strategy` option passed to\r\n * `computePosition` and must match `style.position` on the floating element.\r\n */\r\n strategy: Strategy;\r\n /** Per-middleware output (arrow offsets, hide flags, size data, …). */\r\n middlewareData: MiddlewareData;\r\n}\r\n\r\n/**\r\n * Stateful floating-element manager returned by `createFloating`.\r\n *\r\n * Popper.js equivalences:\r\n * - `connect(reference, floating)` → `createPopper(reference, popper, options)`\r\n * - `disconnect()` → `popper.destroy()`\r\n * - `onUpdate(callback)` → subscribe to position state changes\r\n * - `position` → equivalent of `popper.state`\r\n */\r\nexport interface FloatingHandle {\r\n /**\r\n * Wire the reference and floating DOM elements together and start\r\n * `autoUpdate`. Call this once both elements are in the DOM (e.g. from a\r\n * Domphy `_onMount` lifecycle hook). Calling `connect` while already\r\n * connected first tears down the previous auto-update.\r\n */\r\n connect(\r\n reference: ReferenceElement,\r\n floating: FloatingElement,\r\n updateOptions?: AutoUpdateOptions,\r\n ): void;\r\n /**\r\n * Stop `autoUpdate` and release element references. Call from\r\n * `_onBeforeRemove` — or when the floating element is hidden if it stays\r\n * mounted and you want to pause updates.\r\n */\r\n disconnect(): void;\r\n /**\r\n * The last computed position, or `null` before the first `computePosition`\r\n * call completes.\r\n */\r\n readonly position: FloatingPosition | null;\r\n /**\r\n * Subscribe to position updates. The callback is called synchronously\r\n * after each `computePosition` resolves with the new position. Returns an\r\n * unsubscribe function — call it to remove the listener.\r\n *\r\n * Typical Domphy usage: call `onUpdate` once and write the `x`/`y` values\r\n * to the floating element's style inside the callback.\r\n */\r\n onUpdate(callback: (position: FloatingPosition) => void): () => void;\r\n}\r\n\r\n/**\r\n * Create a stateful floating-element manager. Equivalent to `createPopper()`\r\n * from Popper.js, but built on the Floating UI primitives vendored by\r\n * `@domphy/floating`.\r\n *\r\n * ```ts\r\n * import { createFloating, offset, flip, shift } from \"@domphy/floating\"\r\n *\r\n * const handle = createFloating({\r\n * placement: \"bottom\",\r\n * middleware: [offset(8), flip(), shift()],\r\n * strategy: \"fixed\",\r\n * })\r\n *\r\n * // In _onMount (once both elements are available):\r\n * handle.connect(referenceEl, floatingEl)\r\n * handle.onUpdate(({ x, y }) => {\r\n * Object.assign(floatingEl.style, { left: `${x}px`, top: `${y}px` })\r\n * })\r\n *\r\n * // In _onBeforeRemove:\r\n * handle.disconnect()\r\n * ```\r\n */\r\nexport function createFloating(\r\n config: Partial<ComputePositionConfig> = {},\r\n): FloatingHandle {\r\n let cleanupAutoUpdate: (() => void) | null = null;\r\n let currentReference: ReferenceElement | null = null;\r\n let currentFloating: FloatingElement | null = null;\r\n let position: FloatingPosition | null = null;\r\n const listeners = new Set<(position: FloatingPosition) => void>();\r\n\r\n function runUpdate(): void {\r\n if (!currentReference || !currentFloating) return;\r\n const reference = currentReference;\r\n const floating = currentFloating;\r\n\r\n // Mirror the cache strategy from computePosition in dom/index.ts: one Map\r\n // per update call so middleware can de-dupe expensive ancestor lookups\r\n // within the same computation without leaking between calls.\r\n const cache = new Map<ReferenceElement, Array<Element>>();\r\n const mergedOptions = {platform, ...config};\r\n const platformWithCache = {...mergedOptions.platform, _c: cache};\r\n\r\n computePositionCore(reference, floating, {\r\n ...mergedOptions,\r\n platform: platformWithCache,\r\n })\r\n .then((result) => {\r\n // Guard against a late-resolving promise after disconnect() — or a\r\n // connect() to a different pair — happened while this call was in\r\n // flight. Identity (not just nullity) check avoids a stale\r\n // computation for an old reference/floating pair overwriting a\r\n // newer one.\r\n if (currentReference !== reference || currentFloating !== floating) {\r\n return;\r\n }\r\n position = result as FloatingPosition;\r\n for (const listener of listeners) {\r\n try {\r\n listener(position);\r\n } catch (error) {\r\n console.error(error);\r\n }\r\n }\r\n })\r\n .catch((error) => {\r\n console.error(error);\r\n });\r\n }\r\n\r\n return {\r\n connect(reference, floating, updateOptions) {\r\n // Tear down any prior auto-update before wiring new elements.\r\n cleanupAutoUpdate?.();\r\n currentReference = reference;\r\n currentFloating = floating;\r\n runUpdate();\r\n cleanupAutoUpdate = autoUpdate(\r\n reference,\r\n floating,\r\n runUpdate,\r\n updateOptions,\r\n );\r\n },\r\n\r\n disconnect() {\r\n cleanupAutoUpdate?.();\r\n cleanupAutoUpdate = null;\r\n currentReference = null;\r\n currentFloating = null;\r\n },\r\n\r\n get position() {\r\n return position;\r\n },\r\n\r\n onUpdate(callback) {\r\n listeners.add(callback);\r\n return () => {\r\n listeners.delete(callback);\r\n };\r\n },\r\n };\r\n}\r\n","import type {\n Coords,\n InlineOptions,\n LimitShiftOptions,\n SideObject,\n} from '@floating-ui/core';\nimport {\n arrow as arrowCore,\n autoPlacement as autoPlacementCore,\n detectOverflow as detectOverflowCore,\n flip as flipCore,\n hide as hideCore,\n inline as inlineCore,\n limitShift as limitShiftCore,\n offset as offsetCore,\n shift as shiftCore,\n size as sizeCore,\n} from '@floating-ui/core';\n\nimport type {\n ArrowOptions,\n AutoPlacementOptions,\n Derivable,\n DetectOverflowOptions,\n FlipOptions,\n HideOptions,\n Middleware,\n MiddlewareState,\n OffsetOptions,\n ShiftOptions,\n SizeOptions,\n} from './types';\n\n/**\n * Resolves with an object of overflow side offsets that determine how much the\n * element is overflowing a given clipping boundary on each side.\n * - positive = overflowing the boundary by that number of pixels\n * - negative = how many pixels left before it will overflow\n * - 0 = lies flush with the boundary\n * @see https://floating-ui.com/docs/detectOverflow\n */\nexport const detectOverflow: (\n state: MiddlewareState,\n options?: DetectOverflowOptions | Derivable<DetectOverflowOptions>,\n) => Promise<SideObject> = detectOverflowCore;\n\n/**\n * Modifies the placement by translating the floating element along the\n * specified axes.\n * A number (shorthand for `mainAxis` or distance), or an axes configuration\n * object may be passed.\n * @see https://floating-ui.com/docs/offset\n */\nexport const offset: (options?: OffsetOptions) => Middleware = offsetCore;\n\n/**\n * Optimizes the visibility of the floating element by choosing the placement\n * that has the most space available automatically, without needing to specify a\n * preferred placement. Alternative to `flip`.\n * @see https://floating-ui.com/docs/autoPlacement\n */\nexport const autoPlacement: (\n options?: AutoPlacementOptions | Derivable<AutoPlacementOptions>,\n) => Middleware = autoPlacementCore;\n\n/**\n * Optimizes the visibility of the floating element by shifting it in order to\n * keep it in view when it will overflow the clipping boundary.\n * @see https://floating-ui.com/docs/shift\n */\nexport const shift: (\n options?: ShiftOptions | Derivable<ShiftOptions>,\n) => Middleware = shiftCore;\n\n/**\n * Optimizes the visibility of the floating element by flipping the `placement`\n * in order to keep it in view when the preferred placement(s) will overflow the\n * clipping boundary. Alternative to `autoPlacement`.\n * @see https://floating-ui.com/docs/flip\n */\nexport const flip: (\n options?: FlipOptions | Derivable<FlipOptions>,\n) => Middleware = flipCore;\n\n/**\n * Provides data that allows you to change the size of the floating element —\n * for instance, prevent it from overflowing the clipping boundary or match the\n * width of the reference element.\n * @see https://floating-ui.com/docs/size\n */\nexport const size: (\n options?: SizeOptions | Derivable<SizeOptions>,\n) => Middleware = sizeCore;\n\n/**\n * Provides data to hide the floating element in applicable situations, such as\n * when it is not in the same clipping context as the reference element.\n * @see https://floating-ui.com/docs/hide\n */\nexport const hide: (\n options?: HideOptions | Derivable<HideOptions>,\n) => Middleware = hideCore;\n\n/**\n * Provides data to position an inner element of the floating element so that it\n * appears centered to the reference element.\n * @see https://floating-ui.com/docs/arrow\n */\nexport const arrow: (\n options: ArrowOptions | Derivable<ArrowOptions>,\n) => Middleware = arrowCore;\n\n/**\n * Provides improved positioning for inline reference elements that can span\n * over multiple lines, such as hyperlinks or range selections.\n * @see https://floating-ui.com/docs/inline\n */\nexport const inline: (\n options?: InlineOptions | Derivable<InlineOptions>,\n) => Middleware = inlineCore;\n\n/**\n * Built-in `limiter` that will stop `shift()` at a certain point.\n */\nexport const limitShift: (\n options?: LimitShiftOptions | Derivable<LimitShiftOptions>,\n) => {\n options: any;\n fn: (state: MiddlewareState) => Coords;\n} = limitShiftCore;\n","import {computePosition as computePositionCore} from '@floating-ui/core';\n\nimport {platform} from './platform';\nimport type {\n ComputePositionConfig,\n FloatingElement,\n ReferenceElement,\n} from './types';\n\n/**\n * Computes the `x` and `y` coordinates that will place the floating element\n * next to a given reference element.\n */\nexport const computePosition = (\n reference: ReferenceElement,\n floating: FloatingElement,\n options?: Partial<ComputePositionConfig>,\n) => {\n // This caches the expensive `getClippingElementAncestors` function so that\n // multiple lifecycle resets re-use the same result. It only lives for a\n // single call. If other functions become expensive, we can add them as well.\n const cache = new Map<ReferenceElement, Array<Element>>();\n const mergedOptions = {platform, ...options};\n const platformWithCache = {...mergedOptions.platform, _c: cache};\n return computePositionCore(reference, floating, {\n ...mergedOptions,\n platform: platformWithCache,\n });\n};\n\nexport {autoUpdate} from './autoUpdate';\nexport {createFloating} from './createFloating';\nexport type {FloatingHandle, FloatingPosition} from './createFloating';\nexport {\n arrow,\n autoPlacement,\n detectOverflow,\n flip,\n hide,\n inline,\n limitShift,\n offset,\n shift,\n size,\n} from './middleware';\nexport {platform} from './platform';\nexport type {\n ArrowOptions,\n AutoPlacementOptions,\n AutoUpdateOptions,\n Boundary,\n ComputePositionConfig,\n Derivable,\n DetectOverflowOptions,\n Elements,\n FlipOptions,\n FloatingElement,\n HideOptions,\n Middleware,\n MiddlewareArguments,\n MiddlewareState,\n NodeScroll,\n OffsetOptions,\n Platform,\n ReferenceElement,\n ShiftOptions,\n SizeOptions,\n VirtualElement,\n} from './types';\nexport type {\n AlignedPlacement,\n Alignment,\n Axis,\n ClientRectObject,\n ComputePositionReturn,\n Coords,\n Dimensions,\n ElementContext,\n ElementRects,\n InlineOptions,\n Length,\n LimitShiftOptions,\n MiddlewareData,\n MiddlewareReturn,\n Padding,\n Placement,\n Rect,\n RootBoundary,\n Side,\n SideObject,\n Strategy,\n} from '@floating-ui/core';\n// This export exists only for backwards compatibility. It will be removed in\n// the next major version.\nexport {getOverflowAncestors} from '@floating-ui/utils/dom';\n","import {\n behavior,\n type BehaviorInstance,\n type DomphyElement,\n type ElementNode,\n merge,\n type PartialElement,\n type State,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n autoUpdate,\n computePosition,\n flip,\n offset,\n type Placement,\n shift,\n} from \"@domphy/floating\";\n\ntype FloatingProps = {\n openState: State<boolean>;\n placement: State<Placement>;\n content: DomphyElement;\n // popover's openOn === \"hover\" case: hovering the floating PANEL itself\n // (not just the anchor) must keep it open, so the pointer can travel from\n // trigger to panel without the debounced hide() firing first.\n keepOpenOnContentHover: boolean;\n};\n\ntype FloatingInstance = BehaviorInstance<FloatingProps> & {\n show: () => void;\n hide: () => void;\n};\n\n// The per-anchor persistent state a floating component needs (position\n// cleanup, the inserted panel node, debounce timer) used to live in\n// createFloating()'s own closure — but that closure is recreated fresh every\n// time a reactive ancestor re-renders the anchor (popover()/tooltip() called\n// again on the SAME reused DOM element). Only the FIRST-ever generation's\n// _onMount ever fires (ElementNode hooks run once per node), so imperative,\n// document-level listeners (outside-click, Escape-inside-panel) that closed\n// over that generation's `openState`/`reference`/`floating` kept acting on an\n// orphaned copy forever, while live-rebound trigger events (onClick etc.)\n// moved on to whatever generation was actually current — the trigger opened\n// the panel, but nothing could ever close it again from outside.\n//\n// Fixed by moving all of this into ONE `behavior()` instance per (anchor,\n// kind): `attach` runs once, and every later generation's `show`/`hide`\n// calls and `_behaviors` re-declaration route into that SAME instance via\n// `getBehavior`/`update()` — so there is exactly one canonical `openState`/\n// `reference`/`floating` for the anchor's whole lifetime, not one per\n// generation.\nfunction attachFloating(\n node: ElementNode,\n initialProps: FloatingProps,\n): FloatingInstance {\n let { openState, placement, content, keepOpenOnContentHover } =\n initialProps;\n\n let timer: ReturnType<typeof setTimeout> | null = null;\n let cleanup: (() => void) | null = null;\n let floating: HTMLElement | null = null;\n let floatingNode: ElementNode | null = null;\n let mounted = false;\n\n const reference = node.domElement as HTMLElement;\n const rootNode = node.getRoot();\n\n const floatingPartial: PartialElement = {\n style: {\n position: \"fixed\",\n pointerEvents: \"auto\",\n visibility: (listener) =>\n openState.get(listener) ? \"visible\" : \"hidden\",\n },\n // Escape must dismiss the panel from INSIDE it too: the content is\n // portaled as a DOM sibling of the anchor, so a keydown on a focused\n // element within the panel (menu item, calendar cell, footer button)\n // never bubbles to the anchor's own Escape handler.\n onKeyDown: (event) => {\n if ((event as KeyboardEvent).key === \"Escape\") hide();\n },\n onMouseEnter: () => keepOpenOnContentHover && show(),\n onMouseLeave: () => keepOpenOnContentHover && hide(),\n _onMount: (mountedNode) => {\n floating = mountedNode.domElement as HTMLElement;\n // Propagate data-theme from the trigger's ancestor so floating content\n // inherits CSS variable scope. Stamped on the PANEL, not the shared\n // overlay: the one overlay serves every floating component under the\n // root, so an overlay-level stamp would let whichever anchor opened\n // FIRST permanently impose its theme on later panels anchored under a\n // different [data-theme] scope. Skipped when the content declares its\n // own data-theme.\n if (reference && floating && !floating.hasAttribute(\"data-theme\")) {\n const dataTheme = reference\n .closest(\"[data-theme]\")\n ?.getAttribute(\"data-theme\");\n if (dataTheme) floating.setAttribute(\"data-theme\", dataTheme);\n }\n },\n _portal: (rNode) => {\n let overlay = rNode.domElement!.querySelector(`#domphy-floating`);\n if (!overlay) {\n const overlayEle: DomphyElement<\"div\"> = {\n div: [],\n id: `domphy-floating`,\n style: {\n position: \"fixed\",\n inset: 0,\n zIndex: 20,\n pointerEvents: \"none\",\n },\n };\n const overlayNode = rNode.children!.insert(overlayEle) as ElementNode;\n overlay = overlayNode.domElement!;\n }\n return overlay;\n },\n };\n\n // Later generations declare their OWN fresh `content` object (a new object\n // literal at the popover()/tooltip() call site) — wire it every time, not\n // just at attach, so the panel wiring (theming, portal, dismiss handlers)\n // is present regardless of which generation's content ends up mounted.\n const wireContent = (target: DomphyElement) => merge(target, floatingPartial);\n wireContent(content);\n\n const ensureMounted = () => {\n if (mounted) return;\n mounted = true;\n floatingNode = rootNode.children!.insert(content) as ElementNode;\n };\n\n const instantShow = () => {\n ensureMounted();\n if (reference && floating) {\n cleanup?.();\n cleanup = autoUpdate(reference, floating, () => {\n computePosition(reference as HTMLElement, floating as HTMLElement, {\n placement: placement.get() as Placement,\n middleware: [offset(12), flip(), shift()],\n strategy: \"fixed\",\n }).then(({ x, y, placement: resolved }) => {\n // Teardown can run while computePosition's async work is in\n // flight (it nulls `floating` and removes the panel) — skip the\n // late positioning instead of dereferencing null.\n if (!floating) return;\n Object.assign(floating.style, {\n left: `${x}px`,\n top: `${y}px`,\n });\n placement.set(resolved);\n });\n });\n openState.set(true);\n }\n };\n // Fully unmounts (not just CSS-hides) the panel — mirrors show()'s own\n // insert-on-demand: a closed floating component holds no DOM/listeners.\n // ensureMounted() re-inserts a fresh panel node next time show() runs.\n const instantHide = () => {\n cleanup?.();\n cleanup = null;\n if (floatingNode) {\n floatingNode.remove();\n floatingNode = null;\n }\n floating = null;\n mounted = false;\n openState.set(false);\n };\n const show = () => {\n timer && clearTimeout(timer);\n timer = setTimeout(instantShow, 100);\n };\n const hide = () => {\n timer && clearTimeout(timer);\n timer = setTimeout(instantHide, 100);\n };\n\n const handleOutside = (event: MouseEvent) => {\n if (!openState.get() || !reference || !floating) return;\n const target = event.target as Node;\n if (!reference.contains(target) && !floating.contains(target)) hide();\n };\n rootNode.domElement?.addEventListener(\"click\", handleOutside);\n\n return {\n show,\n hide,\n update(props) {\n openState = props.openState;\n placement = props.placement;\n content = props.content;\n keepOpenOnContentHover = props.keepOpenOnContentHover;\n wireContent(content);\n // Reflect the new generation's declared content into the already-\n // mounted panel in place (same DOM node, no flicker/teardown) — the\n // ordinary reused-node \"patch, don't recreate\" contract, applied to\n // the imperatively-inserted panel too.\n if (floatingNode) floatingNode.patch(content);\n },\n destroy() {\n if (timer) clearTimeout(timer);\n cleanup?.();\n floatingNode?.remove();\n rootNode.domElement?.removeEventListener(\"click\", handleOutside);\n },\n };\n}\n\nfunction createFloating(props: {\n kind: string;\n open?: ValueOrState<boolean>;\n placement: State<Placement>;\n content: DomphyElement;\n keepOpenOnContentHover?: boolean;\n}) {\n const { kind, open = false, placement } = props;\n const openState = toState(open);\n const behaviorKey = `floating:${kind}`;\n\n // Trigger event handlers ARE live-rebound on every patch and already\n // receive the current ElementNode as their 2nd argument (unlike lifecycle\n // hooks) — so show(node)/hide(node) just forward to whatever instance is\n // attached there, regardless of which generation's closure is calling.\n const show = (node?: ElementNode) =>\n node?.getBehavior<FloatingInstance>(behaviorKey)?.show();\n const hide = (node?: ElementNode) =>\n node?.getBehavior<FloatingInstance>(behaviorKey)?.hide();\n\n // Plain spread, NOT merge(): merge() defensively deep-clones its `target`\n // argument, which would snapshot `props.content` right now — but the\n // caller (popover()/tooltip()) hasn't finished mutating it yet (it pushes\n // its OWN partial onto `content.$` right after this call returns). A\n // premature clone silently drops that later mutation, so the panel loses\n // its role/style/dismiss wiring. Spread keeps the `_behaviors` record's\n // `props.content` a live reference to the SAME object the caller mutates.\n const anchorPartial: PartialElement = {\n onKeyDown: (e: Event, node: ElementNode) =>\n (e as KeyboardEvent).key === \"Escape\" && hide(node),\n ...behavior<FloatingProps>(behaviorKey, attachFloating, {\n openState,\n placement,\n content: props.content,\n keepOpenOnContentHover: !!props.keepOpenOnContentHover,\n }),\n };\n\n return { show, hide, anchorPartial };\n}\n\nexport { createFloating };\n","import type { DomphyElement, PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\nconst xSvg = `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"currentColor\"><path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/><path d=\"M6.707 5.293l5.293 5.292l5.293 -5.292a1 1 0 0 1 1.414 1.414l-5.292 5.293l5.292 5.293a1 1 0 0 1 -1.414 1.414l-5.293 -5.292l-5.293 5.292a1 1 0 1 1 -1.414 -1.414l5.292 -5.293l-5.292 -5.293a1 1 0 0 1 1.414 -1.414\" /></svg>`;\n\n/**\n * Styles an inline chip/tag (rounded, bordered, optional remove button).\n * No host tag check; typically applied to a `<span>`. When `removable` is true,\n * a close button is inserted that removes the host node on click.\n *\n * @hostTag span\n * @param props.color - Theme color for the chip background/border/text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @param props.removable - When true, renders a remove (x) button that removes the tag on click. Optional. Defaults to `false`.\n * @example { span: \"Label\", $: [tag({ removable: true })] }\n */\nfunction tag(\n props: { color?: ValueOrState<ThemeColor>; removable?: boolean } = {},\n): PartialElement {\n const { removable = false } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInit: (node) => {\n const removeBtn: DomphyElement<\"span\"> = {\n span: xSvg,\n onClick: (e) => {\n (e as Event).stopPropagation();\n node.remove();\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n cursor: \"pointer\",\n borderRadius: themeSpacing(1),\n width: themeSpacing(4),\n height: themeSpacing(4),\n flexShrink: 0,\n \"&:hover\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", color.get(listener)),\n },\n },\n };\n\n removable && node.children.insert(removeBtn);\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n whiteSpace: \"nowrap\",\n userSelect: \"none\",\n height: themeSpacing(6),\n paddingBlock: 0,\n borderRadius: themeSpacing(1),\n paddingInlineStart: themeSpacing(2),\n paddingInlineEnd: removable ? themeSpacing(1) : themeSpacing(2),\n gap: themeSpacing(2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n },\n };\n}\n\nexport { tag };\n","import {\n type DomphyElement,\n merge,\n type PartialElement,\n type StyleObject,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\nimport { tag } from \"./tag.js\";\n\n/**\n * A combobox/multi-select control: renders selected options as removable tags\n * plus an input, and shows a floating popover (`content`) anchored to the host.\n * Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props.multiple - Allow selecting multiple values (popover stays open on click). Optional `boolean`, default false.\n * @param props.value - Selected value(s). Optional `ValueOrState<Array<number | string | null | undefined> | number | string | null | undefined>`, no default.\n * @param props.options - Available `{ label, value }` options used to render selected tags. Optional `Array<{ label: string; value: string }>`, default `[]`.\n * @param props.placement - Floating popover placement. Optional `ValueOrState<Placement>`, default \"bottom\".\n * @param props.content - The floating popover content element. Required `DomphyElement`.\n * @param props.color - Color tone for the control. Optional `ThemeColor`, default \"neutral\".\n * @param props.open - Whether the popover is open. Optional `ValueOrState<boolean>`, default false.\n * @param props.input - Custom input element; when omitted a default `<input>` is created. Optional `DomphyElement`.\n * @example { div: null, $: [combobox({ options: [{ label: \"A\", value: \"a\" }], content: { div: null } })] }\n */\nfunction combobox(props: {\n multiple?: boolean;\n value?: ValueOrState<\n | Array<number | string | null | undefined>\n | number\n | string\n | null\n | undefined\n >;\n options?: Array<{ label: string; value: string }>;\n placement?: ValueOrState<Placement>;\n content: DomphyElement;\n color?: ThemeColor;\n open?: ValueOrState<boolean>;\n input?: DomphyElement;\n}): PartialElement {\n const {\n options = [],\n placement = \"bottom\",\n color = \"neutral\",\n open = false,\n multiple = false,\n } = props;\n\n const state = toState(props.value);\n const openState = toState(open);\n const { show, hide, anchorPartial } = createFloating({\n kind: \"combobox\",\n open: openState,\n placement: toState(placement),\n content: props.content,\n });\n\n const popoverPartial: PartialElement = {\n onClick: (_e, node) => !multiple && hide(node),\n dataTone: \"shift-14\",\n style: {\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\")}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n };\n\n merge(props.content, popoverPartial);\n\n const inputStyle: StyleObject = {\n border: \"none\",\n outline: \"none\",\n padding: 0,\n margin: 0,\n flex: 1,\n height: themeSpacing(6),\n marginInlineStart: themeSpacing(2),\n fontSize: (listener: any) => themeSize(listener, \"inherit\"),\n color: (listener: any) => themeColor(listener, \"text\", color),\n backgroundColor: (listener: any) => themeColor(listener, \"inherit\", color),\n };\n\n let inputElement: DomphyElement;\n if (props.input) {\n const inputPartial: PartialElement = {\n onFocus: (_e, node) => show(node),\n style: inputStyle,\n _key: \"combobox-input\",\n };\n merge(props.input, inputPartial);\n inputElement = props.input;\n } else {\n inputElement = {\n input: null,\n onFocus: (_e, node) => show(node),\n value: (listener: any) => {\n state.get(listener);\n return \"\";\n },\n style: inputStyle,\n _key: \"combobox-input\",\n };\n }\n\n const wrap: DomphyElement<\"div\"> = {\n div: (listener) => {\n const val = state.get(listener);\n const vals = Array.isArray(val) ? val : [val];\n const opts = options.filter((opt) => vals.includes(opt.value));\n const items: DomphyElement[] = opts.map((opt) => {\n return {\n span: opt.label,\n $: [tag({ color, removable: true })],\n _key: opt.value,\n _onRemove: (_node) => {\n const cur = state.get();\n const curVals = Array.isArray(cur) ? cur : [cur];\n const filter = curVals.filter((v) => v !== opt.value);\n multiple ? state.set(filter as any) : state.set(filter[0] as any);\n },\n };\n });\n items.push(inputElement);\n return items;\n },\n style: {\n display: \"flex\",\n flexWrap: \"wrap\",\n gap: themeSpacing(1),\n },\n };\n\n const partial: PartialElement = {\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"combobox\" primitive patch must use div tag`);\n }\n },\n _onInit: (node) => node.children.insert(wrap),\n style: {\n minWidth: themeSpacing(32),\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n },\n };\n\n merge(anchorPartial, partial);\n return anchorPartial;\n}\n\nexport { combobox };\n","import { merge, type PartialElement, toState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Command-palette container patch. Sets up a vertical flex column and provides a\n * shared `command` context (a query State) consumed by `commandSearch` and\n * `commandItem` descendants to filter the list. Typically applied to a `<div>`.\n *\n * @example { div: [...], $: [command()] }\n */\nfunction command(): PartialElement {\n return {\n _onSchedule: (_node, element) => {\n merge(element, {\n _context: {\n command: {\n query: toState(\"\"),\n },\n },\n });\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n overflow: \"hidden\",\n },\n };\n}\n\n/**\n * Search input for a command palette. Wires the input's value into the parent\n * `command` context's query State so descendant `commandItem`s filter live.\n * Apply to an `<input>` element used inside a `command()`.\n *\n * @hostTag input\n * @param props.color - Base theme color tone. Defaults to \"neutral\".\n * @param props.accentColor - Accent color used for the focus border. Defaults to \"primary\".\n * @example { input: \"\", $: [commandSearch({ accentColor: \"primary\" })] }\n */\nfunction commandSearch(\n props: { color?: ThemeColor; accentColor?: ThemeColor } = {},\n): PartialElement {\n const { color = \"neutral\", accentColor = \"primary\" } = props;\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"commandSearch\" patch must use input tag`);\n }\n },\n _onMount: (node) => {\n const ctx = node.getContext(\"command\");\n if (!ctx) {\n console.warn(`\"commandSearch\" patch must be used inside a \"command\"`);\n return;\n }\n const input = node.domElement as HTMLInputElement;\n const onInput = () => ctx.query.set(input.value);\n input.addEventListener(\"input\", onInput);\n node.addHook(\"Remove\", () => input.removeEventListener(\"input\", onInput));\n },\n style: {\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n border: \"none\",\n borderBottom: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color)}`,\n outline: \"none\",\n color: (listener) => themeColor(listener, \"shift-10\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n \"&::placeholder\": {\n color: (listener) => themeColor(listener, \"shift-7\"),\n },\n \"&:focus-visible\": {\n borderBottomColor: (listener) =>\n themeColor(listener, \"shift-6\", accentColor),\n },\n },\n };\n}\n\n/**\n * Selectable item (`role=\"option\"`) in a command palette. On mount, immediately\n * hides itself if the current query doesn't match its text content, and subscribes\n * to future query changes — so items added dynamically after a search is typed are\n * correctly filtered. Typically applied to a `<button>` (or any clickable element)\n * used inside a `command()`.\n *\n * @param props.color - Base theme color tone. Defaults to \"neutral\".\n * @param props.accentColor - Accent color used for the focus outline. Defaults to \"primary\".\n * @example { button: \"Open file\", $: [commandItem({ color: \"neutral\" })] }\n */\nfunction commandItem(\n props: { color?: ThemeColor; accentColor?: ThemeColor } = {},\n): PartialElement {\n const { color = \"neutral\", accentColor = \"primary\" } = props;\n return {\n role: \"option\",\n _onMount: (node) => {\n const ctx = node.getContext(\"command\");\n if (!ctx) {\n console.warn(`\"commandItem\" patch must be used inside a \"command\"`);\n return;\n }\n const el = node.domElement as HTMLElement;\n const text = el.textContent?.toLowerCase() ?? \"\";\n const applyFilter = (q: string) => {\n el.hidden = q.length > 0 && !text.includes(q.toLowerCase());\n };\n applyFilter(ctx.query.get());\n const release = ctx.query.addListener(applyFilter);\n node.addHook(\"Remove\", release);\n },\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n width: \"100%\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n border: \"none\",\n outline: \"none\",\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener) => themeColor(listener, \"hover\", color),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor)}`,\n outlineOffset: `-${themeSpacing(0.5)}`,\n },\n },\n };\n}\n\nexport { command, commandSearch, commandItem };\n","import {\n type DomphyElement,\n type ElementNode,\n type Listener,\n merge,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\n\n/** A single date selection, or a `[start, end]` tuple in range mode. */\nexport type DatePickerValue = Date | null | [Date | null, Date | null];\n\nexport interface DatePickerProps {\n /** Controlled value: a `Date` in single mode, a `[start, end]` tuple in range mode. */\n value?: ValueOrState<DatePickerValue>;\n /** Selection mode. */\n mode?: \"single\" | \"range\";\n /** Also pick hour + minute. The chosen time applies to the selected date(s). */\n time?: boolean;\n /** Earliest selectable day (inclusive). */\n min?: Date;\n /** Latest selectable day (inclusive). */\n max?: Date;\n /** Disable arbitrary days. */\n disabledDate?: (date: Date) => boolean;\n /** BCP-47 locale for month/weekday names, first-day-of-week, and formatting. */\n locale?: string;\n /** Override the first day of the week (0 = Sunday … 6 = Saturday). */\n weekStartsOn?: number;\n /** Override the input display string. */\n format?: (value: DatePickerValue) => string;\n /** Called whenever the selection changes. */\n onChange?: (value: DatePickerValue) => void;\n /** Accent color for the selected/active days. */\n accentColor?: ValueOrState<ThemeColor>;\n /** Popover placement relative to the input. */\n placement?: ValueOrState<Placement>;\n}\n\n// --- date helpers (no third-party library) -----------------------------------\n\nconst atMidnight = (date: Date): Date =>\n new Date(date.getFullYear(), date.getMonth(), date.getDate());\nconst addDays = (date: Date, count: number): Date =>\n new Date(date.getFullYear(), date.getMonth(), date.getDate() + count);\nconst addMonths = (date: Date, count: number): Date =>\n new Date(date.getFullYear(), date.getMonth() + count, date.getDate());\nconst sameDay = (a: Date | null, b: Date | null): boolean =>\n !!a &&\n !!b &&\n a.getFullYear() === b.getFullYear() &&\n a.getMonth() === b.getMonth() &&\n a.getDate() === b.getDate();\nconst isoOf = (date: Date): string =>\n `${date.getFullYear()}-${String(date.getMonth() + 1).padStart(2, \"0\")}-${String(\n date.getDate(),\n ).padStart(2, \"0\")}`;\nconst startOfWeek = (date: Date, weekStart: number): Date =>\n addDays(date, -((date.getDay() - weekStart + 7) % 7));\n\n/** Resolves the locale's first day of week, falling back to Sunday. */\nfunction localeWeekStart(locale: string): number {\n try {\n const localeObject = new Intl.Locale(locale) as Intl.Locale & {\n weekInfo?: { firstDay: number };\n getWeekInfo?: () => { firstDay: number };\n };\n const info = localeObject.getWeekInfo?.() ?? localeObject.weekInfo;\n if (info?.firstDay) return info.firstDay % 7; // Intl uses 1=Mon … 7=Sun\n } catch {\n // unsupported locale or engine — fall through to Sunday\n }\n return 0;\n}\n\n/**\n * A native, themeable date picker patch for an `<input>`. Opens a calendar\n * popover (rendered with Domphy elements, positioned via `@domphy/floating`)\n * supporting single/range selection, optional time, min/max + disabled days,\n * localized names, and keyboard navigation. The input is read-only and shows the\n * formatted selection; compose with `inputText()` for the input's look.\n *\n * @hostTag input\n * @param props.value - Controlled value (`ValueOrState<DatePickerValue>`): a `Date`/`null` in single mode, a `[start, end]` tuple in range mode.\n * @param props.mode - Selection mode, \"single\" | \"range\". Defaults to \"single\".\n * @param props.time - When true, also pick hour + minute (applied to the selected date(s)). Defaults to false.\n * @param props.min - Earliest selectable day (inclusive), a `Date`.\n * @param props.max - Latest selectable day (inclusive), a `Date`.\n * @param props.disabledDate - Predicate `(date: Date) => boolean` to disable arbitrary days.\n * @param props.locale - BCP-47 locale for names/first-day-of-week/formatting. Defaults to `navigator.language` (or \"en-US\" in non-browser).\n * @param props.weekStartsOn - Override first day of week (0 = Sunday … 6 = Saturday). Defaults to the locale's first day.\n * @param props.format - Override the input display string, `(value: DatePickerValue) => string`.\n * @param props.onChange - Called with the new value whenever the selection changes, `(value: DatePickerValue) => void`.\n * @param props.accentColor - Accent color (`ValueOrState<ThemeColor>`) for selected/active days. Defaults to \"primary\".\n * @param props.placement - Popover placement (`ValueOrState<Placement>`) relative to the input. Defaults to \"bottom-start\".\n * @example { input: \"\", $: [inputText(), datePicker({ mode: \"range\" })] }\n */\nfunction datePicker(props: DatePickerProps = {}): PartialElement {\n const {\n mode = \"single\",\n time = false,\n min,\n max,\n disabledDate,\n locale = typeof navigator !== \"undefined\" ? navigator.language : \"en-US\",\n format,\n onChange,\n } = props;\n\n const weekStart = props.weekStartsOn ?? localeWeekStart(locale);\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n const placeState = toState(props.placement ?? \"bottom-start\");\n\n const selection = toState<DatePickerValue>(\n props.value ?? (mode === \"range\" ? [null, null] : null),\n );\n const releaseOnChange = onChange\n ? selection.addListener((value) => onChange(value))\n : null;\n\n const primaryDate = ((): Date => {\n const current = selection.get();\n const base =\n mode === \"range\" ? (current as [Date | null, Date | null])?.[0] : current;\n return base instanceof Date ? base : new Date();\n })();\n\n const viewYear = toState(primaryDate.getFullYear(), \"viewYear\");\n const viewMonth = toState(primaryDate.getMonth(), \"viewMonth\");\n const focused = toState<Date>(atMidnight(primaryDate), \"focused\");\n const hovered = toState<Date | null>(null, \"hovered\");\n const hour = toState(primaryDate.getHours(), \"hour\");\n const minute = toState(primaryDate.getMinutes(), \"minute\");\n\n let contentElement: HTMLElement | null = null;\n\n // --- formatting -----------------------------------------------------------\n const dateFormatter = new Intl.DateTimeFormat(locale, {\n dateStyle: \"medium\",\n ...(time ? { timeStyle: \"short\" as const } : {}),\n });\n const monthFormatter = new Intl.DateTimeFormat(locale, {\n month: \"long\",\n year: \"numeric\",\n });\n const weekdayFormatter = new Intl.DateTimeFormat(locale, {\n weekday: \"short\",\n });\n const fullDateFormatter = new Intl.DateTimeFormat(locale, {\n dateStyle: \"full\",\n });\n\n const formatOne = (date: Date | null): string =>\n date ? dateFormatter.format(date) : \"\";\n const formatDisplay = (value: DatePickerValue): string => {\n if (format) return format(value);\n if (mode === \"range\") {\n const [start, end] = (value as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n return start ? `${formatOne(start)} – ${formatOne(end)}` : \"\";\n }\n return formatOne(value as Date | null);\n };\n\n // 2023-01-01 is a Sunday, so index 0 maps to Sunday before the week-start shift.\n const weekdayNames = Array.from({ length: 7 }, (_unused, index) =>\n weekdayFormatter.format(new Date(2023, 0, 1 + ((index + weekStart) % 7))),\n );\n\n // --- selection logic ------------------------------------------------------\n const isDisabled = (date: Date): boolean =>\n (!!min && atMidnight(date) < atMidnight(min)) ||\n (!!max && atMidnight(date) > atMidnight(max)) ||\n (!!disabledDate && disabledDate(date));\n\n const withTime = (date: Date): Date => {\n if (!time) return atMidnight(date);\n const result = atMidnight(date);\n result.setHours(hour.get(), minute.get(), 0, 0);\n return result;\n };\n\n const selectDate = (date: Date): void => {\n if (isDisabled(date)) return;\n if (mode === \"single\") {\n selection.set(withTime(date));\n if (!time) instantHideRef();\n return;\n }\n const [start, end] = (selection.get() as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n if (!start || (start && end)) {\n selection.set([withTime(date), null]);\n } else if (atMidnight(date) < atMidnight(start)) {\n selection.set([withTime(date), withTime(start)]);\n if (!time) instantHideRef();\n } else {\n selection.set([start, withTime(date)]);\n if (!time) instantHideRef();\n }\n };\n\n const reapplyTime = (): void => {\n if (!time) return;\n if (mode === \"single\") {\n const current = selection.get() as Date | null;\n if (current) selection.set(withTime(current));\n } else {\n const [start, end] = (selection.get() as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n selection.set([\n start ? withTime(start) : start,\n end ? withTime(end) : end,\n ]);\n }\n };\n\n const inSelectedRange = (date: Date, listener?: Listener): boolean => {\n if (mode !== \"range\") return false;\n const [start, end] = (selection.get(listener) as [\n Date | null,\n Date | null,\n ]) ?? [null, null];\n const tail = end ?? hovered.get(listener);\n if (!start || !tail) return false;\n const low = atMidnight(start) <= atMidnight(tail) ? start : tail;\n const high = atMidnight(start) <= atMidnight(tail) ? tail : start;\n const day = atMidnight(date);\n return day >= atMidnight(low) && day <= atMidnight(high);\n };\n\n const isSelectedEnd = (date: Date, listener?: Listener): boolean => {\n const current = selection.get(listener);\n if (mode === \"range\") {\n const [start, end] = (current as [Date | null, Date | null]) ?? [\n null,\n null,\n ];\n return sameDay(date, start) || sameDay(date, end);\n }\n return sameDay(date, current as Date | null);\n };\n\n // --- view navigation ------------------------------------------------------\n const goToDate = (date: Date): void => {\n viewYear.set(date.getFullYear());\n viewMonth.set(date.getMonth());\n };\n const shiftMonth = (delta: number): void => {\n const next = addMonths(new Date(viewYear.get(), viewMonth.get(), 1), delta);\n goToDate(next);\n };\n const shiftYear = (delta: number): void =>\n viewYear.set(viewYear.get() + delta);\n\n const focusActiveCell = (): void => {\n setTimeout(() => {\n contentElement\n ?.querySelector<HTMLElement>(`[data-date=\"${isoOf(focused.get())}\"]`)\n ?.focus();\n }, 0);\n };\n\n // --- floating popover ------------------------------------------------------\n const calendar = buildCalendar();\n const { show, hide, anchorPartial } = createFloating({\n kind: \"datePicker\",\n open: false,\n placement: placeState,\n content: calendar,\n });\n // selectDate calls this before `createFloating` returns `hide`, so route through a ref.\n function instantHideRef(): void {\n hide();\n }\n\n // Move focus into the grid when the popover opens.\n anchorPartial.onClick = () => {};\n const triggerPartial: PartialElement = {\n type: \"text\",\n readonly: true,\n value: (listener) => formatDisplay(selection.get(listener)),\n ariaHaspopup: \"dialog\",\n ariaLabel: \"Choose date\",\n style: { cursor: \"pointer\" },\n onClick: (_e, node) => {\n openAndFocus(node);\n },\n onFocus: (_e, node) => {\n openAndFocus(node);\n },\n onKeyDown: (event, node) => {\n const key = (event as KeyboardEvent).key;\n if (key === \"ArrowDown\" || key === \"Enter\") {\n event.preventDefault();\n openAndFocus(node);\n }\n },\n _onMount: (node) =>\n releaseOnChange &&\n node.addHook(\"Remove\", () => {\n releaseOnChange();\n }),\n };\n function openAndFocus(node?: ElementNode): void {\n const current = isSelectedPrimary() ?? new Date();\n focused.set(atMidnight(current));\n goToDate(current);\n show(node);\n focusActiveCell();\n }\n function isSelectedPrimary(): Date | null {\n const current = selection.get();\n if (mode === \"range\")\n return (current as [Date | null, Date | null])?.[0] ?? null;\n return (current as Date | null) ?? null;\n }\n merge(anchorPartial, triggerPartial);\n return anchorPartial;\n\n // --- calendar builder -----------------------------------------------------\n function buildCalendar(): DomphyElement<\"div\"> {\n const navButton = (label: string, ariaLabel: string, onClick: () => void) =>\n ({\n button: label,\n type: \"button\",\n ariaLabel,\n onClick,\n style: navButtonStyle(),\n }) as DomphyElement;\n\n const header: DomphyElement<\"div\"> = {\n div: [\n navButton(\"«\", \"Previous year\", () => shiftYear(-1)),\n navButton(\"‹\", \"Previous month\", () => shiftMonth(-1)),\n {\n div: (listener) =>\n monthFormatter.format(\n new Date(viewYear.get(listener), viewMonth.get(listener), 1),\n ),\n ariaLive: \"polite\",\n style: {\n flex: \"1\",\n textAlign: \"center\",\n fontWeight: \"600\",\n fontSize: (listener) => themeSize(listener),\n },\n },\n navButton(\"›\", \"Next month\", () => shiftMonth(1)),\n navButton(\"»\", \"Next year\", () => shiftYear(1)),\n ],\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(1),\n marginBottom: themeSpacing(2),\n },\n };\n\n const weekdayHeader: DomphyElement<\"div\"> = {\n div: weekdayNames.map((name, index) => ({\n div: name,\n style: {\n textAlign: \"center\",\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n fontWeight: \"600\",\n color: (listener) => themeColor(listener, \"shift-7\"),\n paddingBlock: themeSpacing(1),\n },\n _key: index,\n })),\n role: \"row\",\n style: gridRowStyle(),\n };\n\n const grid: DomphyElement<\"div\"> = {\n div: (listener) => buildWeeks(listener),\n role: \"grid\",\n ariaLabel: \"Calendar\",\n onKeyDown: onGridKey,\n onMouseLeave: () => mode === \"range\" && hovered.set(null),\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: themeSpacing(0.5),\n },\n };\n\n const children: DomphyElement[] = [header, weekdayHeader, grid];\n if (time) children.push(buildTimeRow());\n children.push(buildFooter());\n\n return {\n div: children,\n role: \"dialog\",\n ariaModal: \"false\",\n _onMount: (node) => {\n contentElement = node.domElement as HTMLElement;\n },\n style: {\n minWidth: themeSpacing(70),\n padding: themeSpacing(3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n backgroundColor: (listener) => themeColor(listener, \"base\"),\n color: (listener) => themeColor(listener, \"shift-10\"),\n border: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\")}`,\n boxShadow: elevation(\"medium\"),\n },\n };\n }\n\n function buildWeeks(listener: Listener): DomphyElement[] {\n const first = new Date(viewYear.get(listener), viewMonth.get(listener), 1);\n const month = viewMonth.get(listener);\n const start = startOfWeek(first, weekStart);\n const weeks: DomphyElement[] = [];\n for (let week = 0; week < 6; week++) {\n const cells: DomphyElement[] = [];\n for (let day = 0; day < 7; day++) {\n const date = addDays(start, week * 7 + day);\n cells.push(buildDayCell(date, month, listener));\n }\n weeks.push({\n div: cells,\n role: \"row\",\n style: gridRowStyle(),\n _key: week,\n });\n }\n return weeks;\n }\n\n function buildDayCell(\n date: Date,\n month: number,\n listener: Listener,\n ): DomphyElement {\n const disabled = isDisabled(date);\n const selected = isSelectedEnd(date, listener);\n const within = inSelectedRange(date, listener);\n const outside = date.getMonth() !== month;\n const isFocused = sameDay(date, focused.get(listener));\n const isToday = sameDay(date, new Date());\n\n return {\n button: String(date.getDate()),\n type: \"button\",\n role: \"gridcell\",\n tabIndex: isFocused ? 0 : -1,\n ariaSelected: selected,\n ariaDisabled: disabled,\n disabled,\n ariaLabel: fullDateFormatter.format(date),\n dataDate: isoOf(date),\n onClick: () => selectDate(date),\n onMouseEnter: () => mode === \"range\" && hovered.set(date),\n style: {\n appearance: \"none\",\n border: \"none\",\n cursor: disabled ? \"not-allowed\" : \"pointer\",\n aspectRatio: \"1\",\n borderRadius: themeSpacing(1),\n fontSize: (l: Listener) => themeSize(l),\n fontFamily: \"inherit\",\n opacity: disabled ? 0.35 : outside ? 0.5 : 1,\n backgroundColor: (l: Listener) =>\n selected\n ? themeColor(l, \"shift-7\", accentColor.get(l))\n : within\n ? themeColor(l, \"hover\", accentColor.get(l))\n : \"transparent\",\n color: (l: Listener) =>\n selected\n ? themeColor(l, \"shift-0\", accentColor.get(l))\n : themeColor(l, \"text\"),\n outline: isToday\n ? (l: Listener) =>\n `1px solid ${themeColor(l, \"shift-6\", accentColor.get(l))}`\n : \"none\",\n outlineOffset: \"-2px\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (l: Listener) =>\n selected\n ? themeColor(l, \"shift-7\", accentColor.get(l))\n : themeColor(l, \"shift-3\", accentColor.get(l)),\n },\n \"&:focus-visible\": {\n outline: (l: Listener) =>\n `2px solid ${themeColor(l, \"shift-6\", accentColor.get(l))}`,\n },\n },\n _key: isoOf(date),\n } as DomphyElement;\n }\n\n function buildTimeRow(): DomphyElement<\"div\"> {\n const numberSelect = (\n count: number,\n state: ReturnType<typeof toState<number>>,\n ariaLabel: string,\n ): DomphyElement => ({\n select: Array.from({ length: count }, (_unused, value) => ({\n option: String(value).padStart(2, \"0\"),\n value: String(value),\n selected: (listener) => state.get(listener) === value,\n _key: value,\n })) as DomphyElement[],\n ariaLabel,\n onChange: (event) => {\n state.set(Number((event.target as HTMLSelectElement).value));\n reapplyTime();\n },\n style: timeSelectStyle(),\n });\n\n return {\n div: [\n numberSelect(24, hour, \"Hour\"),\n { span: \":\", style: { fontWeight: \"600\" } },\n numberSelect(60, minute, \"Minute\"),\n ],\n style: {\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n gap: themeSpacing(1),\n marginTop: themeSpacing(3),\n },\n };\n }\n\n function buildFooter(): DomphyElement<\"div\"> {\n const action = (label: string, onClick: () => void): DomphyElement => ({\n button: label,\n type: \"button\",\n onClick,\n style: {\n appearance: \"none\",\n border: \"none\",\n background: \"transparent\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n fontSize: (l: Listener) => themeSize(l, \"decrease-1\"),\n color: (l: Listener) => themeColor(l, \"muted\", accentColor.get(l)),\n padding: themeSpacing(1),\n },\n });\n return {\n div: [\n action(\"Today\", () => {\n const today = new Date();\n focused.set(atMidnight(today));\n goToDate(today);\n focusActiveCell();\n }),\n action(\"Clear\", () => {\n selection.set(mode === \"range\" ? [null, null] : null);\n hovered.set(null);\n }),\n ],\n style: {\n display: \"flex\",\n justifyContent: \"space-between\",\n marginTop: themeSpacing(2),\n paddingTop: themeSpacing(2),\n borderTop: (l: Listener) => `1px solid ${themeColor(l, \"border\")}`,\n },\n };\n }\n\n function onGridKey(event: Event): void {\n const keyboard = event as KeyboardEvent;\n const current = focused.get();\n let next: Date | null = null;\n switch (keyboard.key) {\n case \"ArrowLeft\":\n next = addDays(current, -1);\n break;\n case \"ArrowRight\":\n next = addDays(current, 1);\n break;\n case \"ArrowUp\":\n next = addDays(current, -7);\n break;\n case \"ArrowDown\":\n next = addDays(current, 7);\n break;\n case \"Home\":\n next = startOfWeek(current, weekStart);\n break;\n case \"End\":\n next = addDays(startOfWeek(current, weekStart), 6);\n break;\n case \"PageUp\":\n next = addMonths(current, keyboard.shiftKey ? -12 : -1);\n break;\n case \"PageDown\":\n next = addMonths(current, keyboard.shiftKey ? 12 : 1);\n break;\n case \"Enter\":\n case \" \":\n keyboard.preventDefault();\n selectDate(current);\n return;\n default:\n return;\n }\n keyboard.preventDefault();\n focused.set(next);\n goToDate(next);\n focusActiveCell();\n }\n}\n\n// --- shared style fragments --------------------------------------------------\n\nfunction gridRowStyle() {\n return {\n display: \"grid\",\n gridTemplateColumns: \"repeat(7, 1fr)\",\n gap: themeSpacing(0.5),\n };\n}\n\nfunction navButtonStyle() {\n return {\n appearance: \"none\" as const,\n border: \"none\",\n background: \"transparent\",\n cursor: \"pointer\",\n fontFamily: \"inherit\",\n fontSize: (l: Listener) => themeSize(l),\n color: (l: Listener) => themeColor(l, \"muted\"),\n width: themeSpacing(7),\n height: themeSpacing(7),\n borderRadius: themeSpacing(1),\n \"&:hover\": {\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\"),\n },\n };\n}\n\nfunction timeSelectStyle() {\n return {\n fontFamily: \"inherit\",\n fontSize: (l: Listener) => themeSize(l),\n padding: themeSpacing(1),\n borderRadius: themeSpacing(1),\n border: (l: Listener) => `1px solid ${themeColor(l, \"border-strong\")}`,\n backgroundColor: (l: Listener) => themeColor(l, \"base\"),\n color: (l: Listener) => themeColor(l, \"text\"),\n };\n}\n\nexport { datePicker };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a description list as a two-column grid (terms in the first column,\n * descriptions in the second), theming the nested `<dt>`/`<dd>` elements.\n * Apply to a `<dl>` element.\n *\n * @hostTag dl\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the term/description text. Defaults to \"neutral\".\n * @example { dl: [{ dt: \"Name\" }, { dd: \"Domphy\" }], $: [descriptionList()] }\n */\nfunction descriptionList(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"dl\") {\n console.warn(`\"descriptionList\" primitive patch must use dl tag`);\n }\n },\n style: {\n display: \"grid\",\n gridTemplateColumns: `minmax(${themeSpacing(24)}, max-content) 1fr`,\n columnGap: themeSpacing(4),\n margin: 0,\n \"& dt\": {\n margin: 0,\n fontWeight: 600,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n },\n \"& dd\": {\n margin: 0,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n },\n };\n}\n\nexport { descriptionList };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a native disclosure widget: a themed `<summary>` header with an\n * animated rotating chevron and an expand/collapse transition on the body\n * content. Apply to a `<details>` element.\n *\n * @hostTag details\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the body/summary. Defaults to \"neutral\".\n * @param props.accentColor - Accent color (`ValueOrState<ThemeColor>`) for the summary's focus outline. Defaults to \"primary\".\n * @param props.duration - Open/close transition duration in milliseconds. Defaults to 240.\n * @example { details: [{ summary: \"More\" }, { div: \"Body\" }], $: [details()] }\n */\nfunction details(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n duration?: number;\n } = {},\n): PartialElement {\n const { duration = 240 } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"details\") {\n console.warn(`\"details\" primitive patch must use details tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n\n overflow: \"hidden\",\n \"& > summary\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", color.get(listener)),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n listStyle: \"none\",\n display: \"flex\",\n justifyContent: \"space-between\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n cursor: \"pointer\",\n userSelect: \"none\",\n fontWeight: 500,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n height: themeSpacing(10),\n },\n \"& > summary::-webkit-details-marker\": {\n display: \"none\",\n },\n \"& > summary::marker\": {\n content: `\"\"`,\n },\n \"& > summary::after\": {\n content: `\"\"`,\n width: themeSpacing(2),\n height: themeSpacing(2),\n flexShrink: 0,\n marginTop: `-${themeSpacing(0.5)}`,\n borderInlineEnd: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-9\", color.get(listener))}`,\n borderBottom: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-9\", color.get(listener))}`,\n transform: \"rotate(45deg)\",\n transition: `transform ${duration}ms ease`,\n },\n \"&[open] > summary::after\": {\n transform: \"rotate(-135deg)\",\n },\n \"& > summary:hover\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n },\n \"& > summary:focus-visible\": {\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n outlineOffset: `-${themeSpacing(0.5)}`,\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"& > :not(summary)\": {\n maxHeight: 0,\n opacity: 0,\n overflow: \"hidden\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingTop: 0,\n paddingBottom: 0,\n transition: `max-height ${duration}ms ease, opacity ${duration}ms ease, padding ${duration}ms ease`,\n },\n \"&[open] > :not(summary)\": {\n maxHeight: themeSpacing(250),\n opacity: 1,\n paddingTop: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingBottom: (listener) => themeSpacing(themeDensity(listener) * 3),\n },\n },\n };\n}\n\nexport { details };\n","// Shared page-scroll lock for modal-like patches (dialog, drawer). A\n// module-level counter (not a plain boolean) is required because two\n// overlays can be open at once (e.g. a dialog opened from within a drawer);\n// without a counter, closing the inner one would clear `overflow` while the\n// outer one is still open.\nlet lockCount = 0;\n\nfunction lockScroll(): void {\n lockCount++;\n if (lockCount === 1) document.body.style.overflow = \"hidden\";\n}\n\nfunction unlockScroll(): void {\n lockCount = Math.max(0, lockCount - 1);\n if (lockCount === 0) document.body.style.overflow = \"\";\n}\n\n// Test-only: reset the module-level counter so a test that unmounts its tree\n// via `document.body.innerHTML = \"\"` (skipping the Remove hook / unlockScroll\n// call) doesn't leak a locked count into the next test.\nfunction _resetScrollLock(): void {\n lockCount = 0;\n}\n\nexport { lockScroll, unlockScroll, _resetScrollLock };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { lockScroll, unlockScroll } from \"../utils/scrollLock.js\";\n\nconst FOCUSABLE =\n 'button:not([disabled]), [href], input:not([disabled]), select:not([disabled]), textarea:not([disabled]), details, [tabindex]:not([tabindex=\"-1\"])';\n\n/**\n * Modal dialog patch driven by an `open` State. Calls `showModal()`/`close()`,\n * fades via opacity, locks page scroll while open, traps Tab focus within the\n * dialog, restores focus to the previously focused element on close, sets\n * `aria-modal`, and closes on outside (backdrop) click. Apply to a `<dialog>`.\n *\n * @hostTag dialog\n * @param props.color - Theme color tone for the dialog surface. Defaults to \"neutral\".\n * @param props.open - Open state (`ValueOrState<boolean>`); set it to true/false to show/hide. Defaults to false.\n * @example { dialog: [...], $: [dialog({ open })] }\n */\nfunction dialog(\n props: { color?: ThemeColor; open?: ValueOrState<boolean> } = {},\n): PartialElement {\n const { color = \"neutral\", open = false } = props;\n const state = toState(open);\n let previousFocus: HTMLElement | null = null;\n let closing = false;\n let scrollLocked = false;\n\n const finalizeClose = (dlg: HTMLDialogElement) => {\n closing = false;\n // Guard for environments with HTMLDialogElement but no close()\n // implementation (e.g. jsdom in tests).\n if (typeof dlg.close === \"function\") dlg.close();\n // visibility/pointer-events (not just opacity) must reflect the closed\n // state: opacity alone leaves a closed dialog's content fully reachable\n // by Tab and exposed to the accessibility tree (opacity, unlike\n // visibility, never removes an element from either) — and a consumer\n // that sets its own `style: { display: ... }` on the dialog (a common\n // pattern for centering content) overrides the UA stylesheet's\n // `dialog:not([open]) { display: none }`, so `dlg.close()` alone doesn't\n // reliably hide it either. Set INLINE so it always wins regardless of\n // what the consumer's own style object declares.\n dlg.style.visibility = \"hidden\";\n dlg.style.pointerEvents = \"none\";\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n previousFocus?.focus();\n previousFocus = null;\n };\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"dialog\") {\n console.warn(`\"dialog\" primitive patch must use dialog tag`);\n }\n },\n onClick: (e: MouseEvent, node) => {\n if (e.target !== node.domElement) return;\n const r = node.domElement!.getBoundingClientRect();\n const inside =\n e.clientX >= r.left &&\n e.clientX <= r.right &&\n e.clientY >= r.top &&\n e.clientY <= r.bottom;\n if (!inside) state.set(false);\n },\n onTransitionEnd: (e, node) => {\n if (!closing) return;\n // Guard against bubbled transitionend from nested content (e.g. an\n // accordion/details transition inside the dialog) prematurely\n // triggering close-finalization.\n if (e.target !== node.domElement) return;\n if (e.propertyName !== \"opacity\") return;\n finalizeClose(node.domElement as HTMLDialogElement);\n },\n _onMount: (node) => {\n const dlg = node.domElement as HTMLDialogElement;\n dlg.setAttribute(\"aria-modal\", \"true\");\n let closeTimer: ReturnType<typeof setTimeout> | null = null;\n\n const trapFocus = (e: KeyboardEvent) => {\n if (e.key !== \"Tab\") return;\n const focusables = Array.from(\n dlg.querySelectorAll<HTMLElement>(FOCUSABLE),\n ).filter(\n (el) =>\n !el.closest(\"[aria-hidden='true']\") && el.offsetParent !== null,\n );\n if (!focusables.length) {\n e.preventDefault();\n return;\n }\n const first = focusables[0];\n const last = focusables[focusables.length - 1];\n if (e.shiftKey) {\n if (\n document.activeElement === first ||\n document.activeElement === dlg\n ) {\n e.preventDefault();\n last.focus();\n }\n } else {\n if (document.activeElement === last) {\n e.preventDefault();\n first.focus();\n }\n }\n };\n\n const onCancel = (e: Event) => {\n e.preventDefault();\n state.set(false);\n };\n dlg.addEventListener(\"cancel\", onCancel);\n\n const update = (val: boolean) => {\n if (val) {\n previousFocus = document.activeElement as HTMLElement;\n dlg.style.visibility = \"visible\";\n dlg.style.pointerEvents = \"auto\";\n // Guard for environments with HTMLDialogElement but no showModal()\n // implementation (e.g. jsdom in tests).\n if (typeof dlg.showModal === \"function\") dlg.showModal();\n if (!scrollLocked) {\n lockScroll();\n scrollLocked = true;\n }\n dlg.addEventListener(\"keydown\", trapFocus);\n requestAnimationFrame(() => {\n dlg.style.opacity = \"1\";\n const focusable = dlg.querySelector<HTMLElement>(FOCUSABLE);\n focusable?.focus();\n });\n } else {\n closing = true;\n dlg.style.opacity = \"0\";\n dlg.removeEventListener(\"keydown\", trapFocus);\n // Fallback: if transitionend never fires (reduced-motion, display:none),\n // unblock close after the transition duration + buffer.\n closeTimer = setTimeout(() => {\n closeTimer = null;\n if (!closing) return;\n finalizeClose(dlg);\n }, 350);\n }\n };\n update(state.get());\n const release = state.addListener(update);\n node.addHook(\"Remove\", () => {\n if (closeTimer) {\n clearTimeout(closeTimer);\n closeTimer = null;\n }\n release();\n dlg.removeEventListener(\"cancel\", onCancel);\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n dlg.removeEventListener(\"keydown\", trapFocus);\n previousFocus?.focus();\n previousFocus = null;\n });\n },\n style: {\n opacity: \"0\",\n // Matches finalizeClose's inline defaults — a dialog that mounts\n // already-closed (the common case: `open` defaults to false) must\n // start out of the tab order/accessibility tree from first paint, not\n // just after its first open->close cycle runs finalizeClose.\n visibility: \"hidden\",\n pointerEvents: \"none\",\n transition: \"opacity 200ms ease\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"shift-10\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n border: \"none\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n padding: (listener) => themeSpacing(themeDensity(listener) * 3),\n boxShadow: elevation(\"high\"),\n \"&::backdrop\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n opacity: 0.75,\n },\n },\n };\n}\n\nexport { dialog };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A horizontal separator (`role=\"separator\"`) with a line on each side of its\n * content, suitable for labelled dividers (\"or\"). Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the label text and rules. Defaults to \"neutral\".\n * @example { div: \"or\", $: [divider()] }\n */\nfunction divider(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n role: \"separator\",\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"divider\" patch should be used with <div>`);\n }\n },\n style: {\n display: \"flex\",\n justifyContent: \"center\",\n alignItems: \"baseline\",\n gap: themeSpacing(2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n minHeight: \"1lh\",\n \"&::before\": {\n content: `\"\"`,\n flex: 1,\n borderColor: (listener) =>\n themeColor(listener, \"border-strong\", color.get(listener)),\n borderWidth: \"1px\",\n borderBottomStyle: \"solid\",\n },\n \"&::after\": {\n content: `\"\"`,\n flex: 1,\n borderColor: (listener) =>\n themeColor(listener, \"border-strong\", color.get(listener)),\n borderWidth: \"1px\",\n borderBottomStyle: \"solid\",\n },\n },\n };\n}\n\nexport { divider };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { lockScroll, unlockScroll } from \"../utils/scrollLock.js\";\n\ntype PhysicalPlacement = \"left\" | \"right\" | \"top\" | \"bottom\";\ntype Placement = PhysicalPlacement | \"start\" | \"end\";\n\nconst translateOut: Record<PhysicalPlacement, string> = {\n left: \"translateX(-100%)\",\n right: \"translateX(100%)\",\n top: \"translateY(-100%)\",\n bottom: \"translateY(100%)\",\n};\n\nconst marginMap: Record<PhysicalPlacement, string> = {\n left: \"0 auto 0 0\",\n right: \"0 0 0 auto\",\n top: \"0 0 auto 0\",\n bottom: \"auto 0 0 0\",\n};\n\nconst isVertical = (p: PhysicalPlacement) => p === \"left\" || p === \"right\";\n\nfunction resolvePhysical(\n placement: Placement,\n isRTL: boolean,\n): PhysicalPlacement {\n if (placement === \"start\") return isRTL ? \"right\" : \"left\";\n if (placement === \"end\") return isRTL ? \"left\" : \"right\";\n return placement;\n}\n\n/**\n * Edge-anchored modal drawer driven by an `open` State. Slides in/out from a\n * chosen edge via a 250 ms transform transition, calls `showModal()`/`close()`,\n * locks page scroll while open, and closes on backdrop click. A 350 ms fallback\n * ensures `close()` is always called even when `transitionend` doesn't fire\n * (reduced-motion, `display:none`, detached element). Apply to a `<dialog>`.\n *\n * Because the patch uses the native `<dialog>` `showModal()` API, the browser\n * traps focus inside the drawer while it is open and restores focus to the\n * previously focused element when `close()` is called. Sets `aria-modal=\"true\"`.\n * Escape key closes the drawer via the animated state path (not immediate close).\n *\n * `\"start\"` and `\"end\"` placements resolve to left/right based on the\n * document's `dir` attribute at mount time, enabling RTL-aware drawers:\n * `\"start\"` → left (LTR) / right (RTL); `\"end\"` → right (LTR) / left (RTL).\n *\n * @hostTag dialog\n * @param props.color - Theme color tone for the drawer surface. Defaults to \"neutral\".\n * @param props.open - Open state (`ValueOrState<boolean>`); set true/false to show/hide. Defaults to false.\n * @param props.placement - Edge to anchor to. \"left\" | \"right\" | \"top\" | \"bottom\" | \"start\" | \"end\". Defaults to \"end\".\n * @param props.size - CSS length for the drawer's width (left/right/start/end) or height (top/bottom). Defaults to themeSpacing(80) for left/right, themeSpacing(64) for top/bottom.\n * @example { dialog: [...], $: [drawer({ open, placement: \"start\" })] }\n */\nfunction drawer(\n props: {\n color?: ThemeColor;\n open?: ValueOrState<boolean>;\n placement?: Placement;\n size?: string;\n } = {},\n): PartialElement {\n const { color = \"neutral\", open = false, placement = \"end\", size } = props;\n const state = toState(open);\n const isLogical = placement === \"start\" || placement === \"end\";\n\n // For static rendering / SSR assume LTR as fallback; corrected at mount time.\n const physicalFallback = resolvePhysical(placement, false);\n const defaultSize = isVertical(physicalFallback)\n ? themeSpacing(80)\n : themeSpacing(64);\n const drawerSize = size ?? defaultSize;\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"dialog\") {\n console.warn(`\"drawer\" patch must use dialog tag`);\n }\n },\n onClick: (e: MouseEvent, node) => {\n if (e.target !== node.domElement) return;\n state.set(false);\n },\n _onMount: (node) => {\n const dlg = node.domElement as HTMLDialogElement;\n dlg.setAttribute(\"aria-modal\", \"true\");\n\n const onCancel = (e: Event) => {\n e.preventDefault();\n state.set(false);\n };\n dlg.addEventListener(\"cancel\", onCancel);\n\n // Resolve logical placements at mount time using document direction.\n const isRTL =\n isLogical &&\n (dlg.ownerDocument.documentElement.dir === \"rtl\" ||\n dlg.ownerDocument.dir === \"rtl\");\n const physical = resolvePhysical(placement, isRTL);\n\n // Correct initial styles for logical placements whose physical direction\n // may differ from the LTR fallback used in the static style block.\n if (isLogical) {\n dlg.style.transform = translateOut[physical];\n dlg.style.margin = marginMap[physical];\n dlg.style.width = isVertical(physical) ? drawerSize : \"100dvw\";\n dlg.style.height = isVertical(physical) ? \"100dvh\" : drawerSize;\n }\n\n let closing = false;\n let scrollLocked = false;\n let closeTimer: ReturnType<typeof setTimeout> | null = null;\n const finishClose = () => {\n closeTimer = null;\n if (!closing) return;\n closing = false;\n // Guard for environments with HTMLDialogElement but no close()\n // implementation (e.g. jsdom in tests).\n if (typeof dlg.close === \"function\") dlg.close();\n // Same fix as dialog.ts: the closed state was only ever represented\n // by an off-screen `transform`, never visibility/pointer-events — a\n // closed drawer stayed fully reachable by Tab and exposed to the\n // accessibility tree (a CSS transform, like opacity, does neither),\n // and a consumer's own `style: { display: ... }` overrides the UA\n // stylesheet's `dialog:not([open])` rule anyway. Set INLINE so it\n // always wins.\n dlg.style.visibility = \"hidden\";\n dlg.style.pointerEvents = \"none\";\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n };\n\n const onTransitionEnd = (e: Event) => {\n if (e.target !== dlg) return;\n if ((e as TransitionEvent).propertyName !== \"transform\") return;\n finishClose();\n };\n dlg.addEventListener(\"transitionend\", onTransitionEnd);\n\n const update = (val: boolean) => {\n if (val) {\n closing = false;\n dlg.style.visibility = \"visible\";\n dlg.style.pointerEvents = \"auto\";\n // Guard for environments with HTMLDialogElement but no showModal()\n // implementation (e.g. jsdom in tests).\n if (typeof dlg.showModal === \"function\") dlg.showModal();\n if (!scrollLocked) {\n lockScroll();\n scrollLocked = true;\n }\n requestAnimationFrame(() => {\n dlg.style.transform = \"translate(0, 0)\";\n });\n } else {\n closing = true;\n dlg.style.transform = translateOut[physical];\n closeTimer = setTimeout(finishClose, 350);\n }\n };\n update(state.get());\n const release = state.addListener(update);\n node.addHook(\"Remove\", () => {\n if (closeTimer) {\n clearTimeout(closeTimer);\n closeTimer = null;\n }\n release();\n dlg.removeEventListener(\"cancel\", onCancel);\n dlg.removeEventListener(\"transitionend\", onTransitionEnd);\n if (scrollLocked) {\n unlockScroll();\n scrollLocked = false;\n }\n });\n },\n style: {\n transform: translateOut[physicalFallback],\n // Matches finishClose's inline defaults — a drawer that mounts\n // already-closed (the common case) must start out of the tab\n // order/accessibility tree from first paint, not just after its first\n // open->close cycle runs finishClose.\n visibility: \"hidden\",\n pointerEvents: \"none\",\n transition: \"transform 0.25s ease\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"shift-10\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n border: \"none\",\n padding: (listener) => themeSpacing(themeDensity(listener) * 3),\n margin: marginMap[physicalFallback],\n width: isVertical(physicalFallback) ? drawerSize : \"100dvw\",\n height: isVertical(physicalFallback) ? \"100dvh\" : drawerSize,\n maxWidth: \"100dvw\",\n maxHeight: \"100dvh\",\n boxShadow: elevation(\"high\"),\n \"&::backdrop\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n opacity: 0.75,\n },\n },\n };\n}\n\nexport { drawer };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Italic emphasized inline text. Apply to an `<em>` element.\n *\n * @hostTag em\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the text. Defaults to \"neutral\".\n * @example { em: \"important\", $: [emphasis()] }\n */\nfunction emphasis(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"em\") {\n console.warn(`\"emphasis\" primitive patch must use em tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontStyle: \"italic\",\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n },\n };\n}\n\nexport { emphasis };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a container as an empty-state placeholder: centered flex column with\n * muted coloring and comfortable padding. Provide the icon, title, and\n * description as child elements.\n *\n * @param props.color - Theme color tone for the muted text/icon. Defaults to `\"neutral\"`.\n * @example\n * { div: [\n * { span: \"📭\" },\n * { p: \"No items yet\", $: [paragraph()] },\n * { span: \"Add your first item to get started\", $: [small()] },\n * ], $: [empty()] }\n */\nfunction empty(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n alignItems: \"center\",\n justifyContent: \"center\",\n gap: themeSpacing(3),\n paddingBlock: themeSpacing(12),\n paddingInline: themeSpacing(6),\n textAlign: \"center\",\n color: (listener) => themeColor(listener, \"shift-6\", color.get(listener)),\n // First child (icon area): more muted color to visually recede behind the text\n \"& > :first-child\": {\n color: (listener) =>\n themeColor(listener, \"shift-5\", color.get(listener)),\n },\n },\n };\n}\n\nexport { empty };\n","import type { DomphyElement, PartialElement } from \"@domphy/core\";\n\n/**\n * Catches errors thrown inside reactive child expressions and renders a\n * fallback element instead of crashing the whole tree. Apply to any container.\n *\n * Only errors in *reactive* children (functions returning element arrays) are\n * caught. Errors during static construction propagate normally — those are\n * programming errors, not runtime data errors.\n *\n * @hostTag any\n * @param props.fallback - Fallback element or factory `(error, reset) => element`. Defaults to a plain error message div.\n * @param props.onError - Optional callback for logging/telemetry.\n * @example { div: (l) => renderUserContent(l), $: [errorBoundary({ fallback: { p: \"Something went wrong.\" } })] }\n */\nfunction errorBoundary(\n props: {\n fallback?:\n | DomphyElement\n | ((error: unknown, reset: () => void) => DomphyElement);\n onError?: (error: unknown) => void;\n } = {},\n): PartialElement {\n return {\n _onError: (node, error, reset) => {\n props.onError?.(error);\n const fallbackEl =\n typeof props.fallback === \"function\"\n ? props.fallback(error, reset)\n : (props.fallback ??\n ({ div: \"An error occurred.\" } as DomphyElement));\n node.children.update([fallbackEl]);\n },\n };\n}\n\nexport { errorBoundary };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nconst SIZE_MAP = { small: 8, medium: 10, large: 14 } as const;\n\n/**\n * Floating Action Button — a circular elevated button typically used for the\n * primary action on a screen. Apply to a `<button>` element.\n *\n * @hostTag button\n * @param props.color - Button color tone. Optional `ValueOrState<ThemeColor>`, defaults to `\"primary\"`.\n * @param props.size - Button size preset. Optional `\"small\" | \"medium\" | \"large\"`, defaults to `\"medium\"`.\n * @example { button: \"+\", $: [fab()] }\n * @example { button: \"+\", $: [fab({ size: \"small\", color: \"neutral\" })] }\n */\nfunction fab(\n props: {\n color?: ValueOrState<ThemeColor>;\n size?: \"small\" | \"medium\" | \"large\";\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n const dim = themeSpacing(SIZE_MAP[props.size ?? \"medium\"]);\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"button\") {\n console.warn('\"fab\" patch must use button tag');\n }\n },\n style: {\n appearance: \"none\",\n border: \"none\",\n cursor: \"pointer\",\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n flexShrink: 0,\n width: dim,\n height: dim,\n borderRadius: \"50%\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-9\", color.get(listener)),\n color: (listener) => themeColor(listener, \"shift-0\", color.get(listener)),\n boxShadow: elevation(\"low\"),\n transition: \"background-color 200ms ease, box-shadow 200ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n boxShadow: elevation(\"medium\"),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) =>\n `${elevation(\"medium\")}, ${focusRing(listener, color.get(listener))}`,\n },\n \"&[disabled]\": { opacity: 0.5, cursor: \"not-allowed\" },\n },\n };\n}\n\nexport { fab };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Lays out a figure as a column with block-level media (img/svg/video/canvas)\n * and a themed `<figcaption>`. Apply to a `<figure>` element.\n *\n * @hostTag figure\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the figure/caption text. Defaults to \"neutral\".\n * @example { figure: [{ img: \"\", src }, { figcaption: \"A caption\" }], $: [figure()] }\n */\nfunction figure(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"figure\") {\n console.warn(`\"figure\" primitive patch must use figure tag`);\n }\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: themeSpacing(2),\n marginInline: 0,\n marginTop: themeSpacing(3),\n marginBottom: themeSpacing(3),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n \"& img, & svg, & video, & canvas\": {\n display: \"block\",\n maxWidth: \"100%\",\n borderRadius: themeSpacing(2),\n },\n \"& figcaption\": {\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n color: (listener) => themeColor(listener, \"muted\", color.get(listener)),\n lineHeight: 1.45,\n },\n },\n };\n}\n\nexport { figure };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Layout patch for a group of form fields. Arranges a `<legend>`, `<label>`s,\n * controls, and helper `<p>`s in a grid — labels beside controls (horizontal)\n * or stacked above them (vertical). Apply to a `<fieldset>` element.\n *\n * @hostTag fieldset\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for legend/text/surface. Defaults to \"neutral\".\n * @param props.layout - Field arrangement, \"horizontal\" (label beside control) | \"vertical\" (label above). Defaults to \"horizontal\".\n * @example { fieldset: [{ legend: \"Profile\" }, { label: \"Name\" }, { input: \"\" }], $: [formGroup({ layout: \"vertical\" })] }\n */\nfunction formGroup(\n props: {\n color?: ValueOrState<ThemeColor>;\n layout?: \"horizontal\" | \"vertical\";\n } = {},\n): PartialElement {\n const { layout = \"horizontal\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n const isVertical = layout === \"vertical\";\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"fieldset\") {\n console.warn(`\"formGroup\" patch must use fieldset tag`);\n }\n },\n style: {\n margin: 0,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 3),\n border: \"none\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n display: \"grid\",\n gridTemplateColumns: isVertical\n ? `minmax(0, 1fr)`\n : `max-content minmax(0, 1fr)`,\n columnGap: themeSpacing(4),\n rowGap: themeSpacing(3),\n alignItems: \"start\",\n \"& > legend\": {\n gridColumn: \"1 / -1\",\n margin: 0,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontWeight: 600,\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n },\n \"& > label\": {\n gridColumn: \"1\",\n alignSelf: \"start\",\n margin: 0,\n paddingBlock: (listener) =>\n isVertical ? 0 : themeSpacing(themeDensity(listener) * 1),\n },\n \"& > label:has(+ :not(legend, label, p) + p)\": {\n gridRow: isVertical ? \"auto\" : \"span 2\",\n },\n \"& > :not(legend, label, p)\": {\n gridColumn: isVertical ? \"1\" : \"2\",\n minWidth: 0,\n width: \"100%\",\n boxSizing: \"border-box\",\n },\n \"& > p\": {\n gridColumn: isVertical ? \"1\" : \"2\",\n minWidth: 0,\n margin: 0,\n marginBlockStart: `calc(${themeSpacing(2)} * -1)`,\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n },\n };\n}\n\nexport { formGroup };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\nconst HeadingShift: Record<string, string> = {\n h6: \"decrease-1\",\n h5: \"inherit\",\n h4: \"increase-1\",\n h3: \"increase-2\",\n h2: \"increase-3\",\n h1: \"increase-4\",\n};\n\n/**\n * Styles a heading, scaling its font size by level (h1 largest … h6 smallest)\n * relative to the theme base size. Apply to a heading element `<h1>`–`<h6>`.\n *\n * @hostTag h1\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the heading text. Defaults to \"neutral\".\n * @example { h2: \"Section title\", $: [heading()] }\n */\nfunction heading(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (![\"h1\", \"h2\", \"h3\", \"h4\", \"h5\", \"h6\"].includes(node.tagName)) {\n console.warn(\n `\"heading\" primitive patch must use heading tags [h1...h6]`,\n );\n }\n },\n style: {\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n marginTop: 0,\n marginBottom: themeSpacing(2),\n fontSize: (listener) => {\n const offset = HeadingShift[listener.elementNode.tagName] || \"inherit\";\n return themeSize(listener, offset);\n },\n },\n };\n}\n\nexport { heading };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * A thematic break rendered as a thin 1px themed line with vertical margin.\n * Apply to an `<hr>` element.\n *\n * @hostTag hr\n * @param props.color - Theme color tone (`ValueOrState<ThemeColor>`) for the rule. Defaults to \"neutral\".\n * @example { hr: \"\", $: [horizontalRule()] }\n */\nfunction horizontalRule(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"hr\") {\n console.warn(`\"horizontalRule\" primitive patch must use hr tag`);\n }\n },\n style: {\n border: 0,\n height: \"1px\",\n marginInline: 0,\n marginTop: themeSpacing(3),\n marginBottom: themeSpacing(3),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", color.get(listener)),\n },\n };\n}\n\nexport { horizontalRule };\n","import type { PartialElement } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles an inline icon container: square box that centers its content and\n * applies the themed icon color. Apply to a `<span>` element.\n *\n * @hostTag span\n * @param props.color - Optional theme color tone for the icon (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @example { span: null, $: [icon()] }\n */\nfunction icon(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"span\") {\n console.warn(`\"icon\" primitive patch should use span tag`);\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n alignSelf: \"center\",\n justifySelf: \"center\",\n verticalAlign: \"middle\",\n width: themeSpacing(4),\n height: themeSpacing(4),\n flexShrink: \"0\",\n fontSize: (listener) => themeSize(listener),\n backgroundColor: \"transparent\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { icon };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a responsive image: full-width, cover-fit, rounded corners with a\n * themed placeholder background. Apply to an `<img>` element.\n *\n * @hostTag img\n * @param props.color - Optional theme color tone for the placeholder background (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @example { img: null, src: \"photo.jpg\", alt: \"Photo\", $: [image()] }\n */\nfunction image(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInsert: (node) => {\n if (node.tagName !== \"img\") {\n console.warn(`\"image\" primitive patch must use img tag`);\n }\n },\n style: {\n display: \"block\",\n width: \"100%\",\n maxWidth: \"100%\",\n height: \"auto\",\n objectFit: \"cover\",\n borderRadius: themeSpacing(2),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n },\n };\n}\n\nexport { image };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a custom checkbox with themed box, check mark, indeterminate state,\n * hover, focus and disabled styling. Apply to an `<input>` element of\n * type `checkbox` (the patch sets `type: \"checkbox\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for the box/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the checked/indeterminate fill and focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"checkbox\", $: [inputCheckbox()] }\n */\nfunction inputCheckbox(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"checkbox\",\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputCheckbox\" primitive patch must use input tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n display: \"inline-flex\",\n position: \"relative\",\n width: themeSpacing(6),\n height: themeSpacing(6),\n justifyContent: \"center\",\n alignItems: \"center\",\n transition: \"background-color 300ms, outline-color 300ms\",\n margin: 0,\n padding: 0,\n \"&::before\": {\n content: `\"\"`,\n display: \"block\",\n borderRadius: themeSpacing(1),\n lineHeight: 1,\n cursor: \"pointer\",\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n width: themeSpacing(4),\n height: themeSpacing(4),\n },\n \"&:hover::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:checked::before\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-8\", accentColor.get(listener)),\n },\n \"&:checked:hover:not([disabled])::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-7\", accentColor.get(listener)),\n },\n \"&:checked::after\": {\n content: `\"\"`,\n display: \"block\",\n position: \"absolute\",\n top: \"25%\",\n insetInlineStart: \"37%\",\n width: \"20%\",\n height: \"30%\",\n border: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"inherit\", accentColor.get(listener))}`,\n borderTop: 0,\n borderInlineStart: 0,\n transform: \"rotate(45deg)\",\n },\n \"&:indeterminate::before\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", accentColor.get(listener)),\n },\n \"&:indeterminate::after\": {\n content: `\"\"`,\n position: \"absolute\",\n inset: \"30%\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-8\", accentColor.get(listener)),\n },\n \"&:indeterminate:hover:not([disabled])::after\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-7\", accentColor.get(listener)),\n },\n \"&:focus-visible\": {\n borderRadius: themeSpacing(1.5),\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&[disabled]\": {\n cursor: \"not-allowed\",\n },\n \"&[disabled]::before, &[disabled]::after\": {\n outline: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", \"neutral\"),\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { inputCheckbox };\n","import type { PartialElement, ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a native color picker swatch with themed padding, rounded swatch and\n * disabled styling. Apply to an `<input>` element of type `color` (the patch\n * sets `type: \"color\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone used for the disabled state (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"color\", $: [inputColor()] }\n */\nfunction inputColor(\n _props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n return {\n type: \"color\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputColor\" primitive patch must use input tag`);\n }\n (element as any).type = \"color\";\n },\n style: {\n appearance: \"none\",\n border: \"none\",\n cursor: \"pointer\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 1),\n blockSize: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n inlineSize: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n backgroundColor: \"transparent\",\n \"&::-webkit-color-swatch-wrapper\": {\n margin: 0,\n padding: 0,\n },\n \"&::-webkit-color-swatch\": {\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n },\n },\n };\n}\n\nexport { inputColor };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\ntype InputDateTimeMode = \"date\" | \"time\" | \"week\" | \"month\" | \"datetime-local\";\n\n/**\n * Styles a native date/time input with themed border, padding, hover, focus,\n * invalid and disabled states. The `mode` selects the input `type`. Apply to\n * an `<input>` element (the patch sets `type` to the chosen `mode`).\n *\n * @hostTag input\n * @param props.mode - Input mode selecting the host `type`: `\"date\" | \"time\" | \"week\" | \"month\" | \"datetime-local\"`. Defaults to `\"datetime-local\"`.\n * @param props.color - Optional theme color tone for text/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"datetime-local\", $: [inputDateTime()] }\n */\nfunction inputDateTime(\n props: {\n mode?: InputDateTimeMode;\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { mode = \"datetime-local\" } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: mode,\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputDateTime\" primitive patch must use input tag`);\n }\n (element as any).type = mode;\n },\n style: {\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::-webkit-calendar-picker-indicator\": {\n cursor: \"pointer\",\n opacity: 0.85,\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n },\n \"&:invalid\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"error\")}`,\n },\n },\n };\n}\n\nexport { inputDateTime };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a native file input with a themed upload button, border, hover, focus\n * and disabled states. Apply to an `<input>` element of type `file` (the patch\n * sets `type: \"file\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for text/border and the upload button (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"file\", $: [inputFile()] }\n */\nfunction inputFile(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"file\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputFile\" primitive patch must use input tag`);\n }\n (element as any).type = \"file\";\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 1),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::-webkit-file-upload-button\": {\n marginTop: (listener) => themeSpacing(themeDensity(listener)),\n fontFamily: \"inherit\",\n fontSize: \"inherit\",\n border: \"none\",\n borderRadius: themeSpacing(1),\n height: themeSpacing(6),\n paddingInline: themeSpacing(2),\n cursor: \"pointer\",\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"surface\", color.get(listener)),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.8,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"surface\", \"neutral\"),\n },\n \"&[disabled]::-webkit-file-upload-button\": {\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", \"neutral\"),\n },\n },\n };\n}\n\nexport { inputFile };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a native number input with themed border, padding, visible spin\n * buttons, hover, focus and disabled states. Apply to an `<input>` element of\n * type `number` (the patch sets `type: \"number\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for text/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"number\", $: [inputNumber()] }\n */\nfunction inputNumber(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"number\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputNumber\" primitive patch must use input tag`);\n }\n (element as any).type = \"number\";\n },\n style: {\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n minWidth: themeSpacing(10),\n paddingInlineStart: (listener) =>\n themeSpacing(themeDensity(listener) * 3),\n paddingInlineEnd: (listener) =>\n themeSpacing(themeDensity(listener) * 1.5),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::-webkit-inner-spin-button, &::-webkit-outer-spin-button\": {\n opacity: 1,\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { inputNumber };\n","import type { DomphyElement, PartialElement, StyleObject } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n// Tabler Icons (MIT) — eye and eye-off outlines.\nconst EYE_SVG =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"none\" ` +\n `stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" ` +\n `width=\"1em\" height=\"1em\">` +\n `<path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/>` +\n `<path d=\"M10 12a2 2 0 1 0 4 0a2 2 0 0 0 -4 0\"/>` +\n `<path d=\"M21 12c-2.4 4 -5.4 6 -9 6c-3.6 0 -6.6 -2 -9 -6c2.4 -4 5.4 -6 9 -6c3.6 0 6.6 2 9 6\"/>` +\n `</svg>`;\n\nconst EYE_OFF_SVG =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"none\" ` +\n `stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" ` +\n `width=\"1em\" height=\"1em\">` +\n `<path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/>` +\n `<path d=\"M10.585 10.587a2 2 0 0 0 2.829 2.828\"/>` +\n `<path d=\"M16.681 16.673a8.717 8.717 0 0 1 -4.681 1.327c-3.6 0 -6.6 -2 -9 -6` +\n `c1.272 -2.12 2.712 -3.678 4.32 -4.674m2.86 -1.146a9.055 9.055 0 0 1 1.82 -.18` +\n `c3.6 0 6.6 2 9 6c-.666 1.11 -1.379 2.067 -2.138 2.87\"/>` +\n `<path d=\"M3 3l18 18\"/>` +\n `</svg>`;\n\n/**\n * Password input wrapper: a styled `<div>` that inserts an `<input type=\"password\">`\n * and a show/hide toggle button. The outer div carries the focus-ring outline via\n * `:focus-within`. Apply to an empty `<div>`.\n *\n * @hostTag div\n * @param props.color - Base color tone for border/background/text. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent outline color on focus-within. Defaults to `\"primary\"`.\n * @example { div: null, $: [inputPassword()] }\n */\nfunction inputPassword(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const colorState = toState(props.color ?? \"neutral\", \"color\");\n const accentState = toState(props.accentColor ?? \"primary\", \"accentColor\");\n const visibleState = toState(false);\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn('\"inputPassword\" patch must use div tag');\n }\n },\n // Build the input/toggle as real child elements (not imperative DOM\n // mutation in _onMount) so generateHTML()/SSR emits the actual markup.\n _onInit: (node) => {\n const field: DomphyElement<\"input\"> = {\n input: null,\n type: (l) => (visibleState.get(l) ? \"text\" : \"password\"),\n style: {\n flex: 1,\n minWidth: 0,\n border: \"none\",\n outline: \"none\",\n backgroundColor: \"transparent\",\n padding: 0,\n margin: 0,\n font: \"inherit\",\n color: \"inherit\",\n },\n };\n\n const toggle: DomphyElement<\"button\"> = {\n button: (l) => (visibleState.get(l) ? EYE_OFF_SVG : EYE_SVG),\n type: \"button\",\n ariaLabel: (l) =>\n visibleState.get(l) ? \"Hide password\" : \"Show password\",\n onClick: () => visibleState.set(!visibleState.get()),\n style: {\n background: \"none\",\n border: \"none\",\n padding: 0,\n margin: 0,\n cursor: \"pointer\",\n color: \"inherit\",\n display: \"flex\",\n alignItems: \"center\",\n flexShrink: 0,\n opacity: 0.6,\n },\n };\n\n node.children.insert(field);\n node.children.insert(toggle);\n },\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: (l) => themeSpacing(themeDensity(l) * 1),\n paddingBlock: (l) => themeSpacing(themeDensity(l) * 1),\n paddingInline: (l) => themeSpacing(themeDensity(l) * 3),\n borderRadius: (l) => themeSpacing(themeDensity(l) * 1.5),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (l) =>\n `1px solid ${themeColor(l, \"border-strong\", colorState.get(l))}`,\n color: (l) => themeColor(l, \"text\", colorState.get(l)),\n backgroundColor: (l) => themeColor(l, \"inherit\", colorState.get(l)),\n fontSize: (l) => themeSize(l, \"inherit\"),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not(:has([disabled])):not(:focus-within)\": {\n outline: (l) =>\n `1px solid ${themeColor(l, \"shift-5\", accentState.get(l))}`,\n },\n \"&:focus-within\": {\n boxShadow: (l) => focusRing(l, accentState.get(l)),\n },\n } as StyleObject,\n };\n}\n\nexport { inputPassword };\n","import type { PartialElement } from \"@domphy/core\";\nimport { themeSpacing } from \"@domphy/theme\";\n\n/**\n * Lays out a one-time-password container as a horizontal row of inputs and\n * wires keyboard navigation: auto-advance on input, backspace/arrow movement,\n * and paste distribution across the child inputs. Apply to a container element\n * (e.g. `<div>`) whose direct children are the OTP `<input>` boxes. Takes no\n * props.\n *\n * @example { div: null, $: [inputOTP()], children: [{ input: null }, { input: null }] }\n */\nfunction inputOTP(): PartialElement {\n return {\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n \"& > *\": {\n minWidth: `${themeSpacing(9)}!important`,\n },\n },\n _onMount: (node) => {\n const container = node.domElement as HTMLElement;\n const getInputs = () =>\n Array.from(container.querySelectorAll(\"input\")) as HTMLInputElement[];\n\n const onInput = (e: Event) => {\n const inputs = getInputs();\n const target = e.target as HTMLInputElement;\n const idx = inputs.indexOf(target);\n if (target.value && idx < inputs.length - 1) {\n inputs[idx + 1].focus();\n }\n };\n\n const onKeydown = (e: KeyboardEvent) => {\n const inputs = getInputs();\n const target = e.target as HTMLInputElement;\n const idx = inputs.indexOf(target);\n if (e.key === \"Backspace\" && !target.value && idx > 0) {\n inputs[idx - 1].focus();\n }\n if (e.key === \"ArrowLeft\" && idx > 0) inputs[idx - 1].focus();\n if (e.key === \"ArrowRight\" && idx < inputs.length - 1)\n inputs[idx + 1].focus();\n };\n\n const onPaste = (e: ClipboardEvent) => {\n e.preventDefault();\n const text = e.clipboardData?.getData(\"text\") ?? \"\";\n const inputs = getInputs();\n const found = inputs.indexOf(e.target as HTMLInputElement);\n const startIdx = found === -1 ? 0 : found;\n [...text].forEach((char, i) => {\n if (inputs[startIdx + i]) inputs[startIdx + i].value = char;\n });\n const lastFilled = Math.min(\n startIdx + text.length - 1,\n inputs.length - 1,\n );\n inputs[lastFilled]?.focus();\n };\n\n container.addEventListener(\"input\", onInput);\n container.addEventListener(\"keydown\", onKeydown as EventListener);\n container.addEventListener(\"paste\", onPaste as EventListener);\n\n node.addHook(\"Remove\", () => {\n container.removeEventListener(\"input\", onInput);\n container.removeEventListener(\"keydown\", onKeydown as EventListener);\n container.removeEventListener(\"paste\", onPaste as EventListener);\n });\n },\n };\n}\n\nexport { inputOTP };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a custom radio button with a themed circular box, checked dot, hover,\n * focus and disabled states. Apply to an `<input>` element of type `radio`\n * (the patch sets `type: \"radio\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for the box/border (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the checked dot and focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"radio\", $: [inputRadio()] }\n */\nfunction inputRadio(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"radio\",\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(\n `\"inputRadio\" primitive patch must use input tag and radio type`,\n );\n return;\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n appearance: \"none\",\n display: \"inline-flex\",\n position: \"relative\",\n width: themeSpacing(6),\n height: themeSpacing(6),\n justifyContent: \"center\",\n alignItems: \"center\",\n transition: \"background-color 300ms, outline-color 300ms\",\n margin: 0,\n padding: 0,\n \"&::before\": {\n content: `\"\"`,\n display: \"block\",\n borderRadius: \"50%\",\n lineHeight: 1,\n cursor: \"pointer\",\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n width: themeSpacing(4),\n height: themeSpacing(4),\n },\n \"&:hover::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:checked::before\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&:checked::after\": {\n content: `\"\"`,\n position: \"absolute\",\n inset: \"30%\",\n borderRadius: \"50%\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-8\", accentColor.get(listener)),\n },\n \"&:checked:hover:not([disabled])::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-7\", accentColor.get(listener)),\n },\n \"&:focus-visible\": {\n borderRadius: \"50%\",\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&[disabled]\": {\n cursor: \"not-allowed\",\n },\n \"&[disabled]::before, &[disabled]::after\": {\n outline: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-4\", \"neutral\"),\n pointerEvents: \"none\",\n },\n },\n };\n}\n\nexport { inputRadio };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a range slider with a themed track and thumb, hover, focus and\n * disabled states. Apply to an `<input>` element of type `range` (the patch\n * sets `type: \"range\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for the slider track (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the thumb and focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"range\", $: [inputRange()] }\n */\nfunction inputRange(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"range\",\n _onInsert: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputRange\" primitive patch must use input tag`);\n }\n },\n style: {\n appearance: \"none\",\n width: \"100%\",\n margin: 0,\n padding: 0,\n height: themeSpacing(4),\n background: \"transparent\",\n cursor: \"pointer\",\n \"&::-webkit-slider-runnable-track\": {\n height: themeSpacing(1.5),\n borderRadius: themeSpacing(999),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n },\n \"&::-webkit-slider-thumb\": {\n appearance: \"none\",\n width: themeSpacing(4),\n height: themeSpacing(4),\n borderRadius: themeSpacing(999),\n border: \"none\",\n marginTop: `calc((${themeSpacing(1.5)} - ${themeSpacing(4)}) / 2)`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-9\", accentColor.get(listener)),\n },\n \"&:hover:not([disabled])::-webkit-slider-thumb\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-10\", accentColor.get(listener)),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n outlineOffset: themeSpacing(1),\n borderRadius: themeSpacing(2),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n };\n}\n\nexport { inputRange };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a search input with themed border, padding, placeholder color, native\n * search decorations, hover, focus and disabled states. Apply to an `<input>`\n * element of type `search` (the patch sets `type: \"search\"`).\n *\n * @hostTag input\n * @param props.color - Optional theme color tone for text/border/placeholder (`ValueOrState<ThemeColor>`). Defaults to `\"neutral\"`.\n * @param props.accentColor - Optional theme color tone for the hover/focus ring (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"search\", $: [inputSearch()] }\n */\nfunction inputSearch(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"search\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputSearch\" primitive patch must use input tag`);\n }\n (element as any).type = \"search\";\n },\n style: {\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n minWidth: themeSpacing(32),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::placeholder\": {\n color: (listener) =>\n themeColor(listener, \"shift-7\", color.get(listener)),\n },\n \"&::-webkit-search-decoration\": {\n display: \"none\",\n },\n \"&::-webkit-search-cancel-button\": {\n cursor: \"pointer\",\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n },\n },\n };\n}\n\nexport { inputSearch };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a checkbox as a toggle switch: themed track and sliding knob that\n * animates and recolors on checked, plus a disabled state. Apply to an\n * `<input>` element of type `checkbox` (the patch sets `type: \"checkbox\"`).\n *\n * @hostTag input\n * @param props.accentColor - Optional theme color tone for the checked track (`ValueOrState<ThemeColor>`). Defaults to `\"primary\"`.\n * @example { input: null, type: \"checkbox\", $: [inputSwitch()] }\n */\nfunction inputSwitch(\n props: { accentColor?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n role: \"switch\",\n dataTone: \"shift-2\",\n type: \"checkbox\",\n _onSchedule: (node) => {\n if (node.tagName !== \"input\") {\n console.warn(`\"inputSwitch\" primitive patch must use input tag`);\n return;\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n appearance: \"none\",\n position: \"relative\",\n display: \"inline-flex\",\n width: themeSpacing(9),\n height: themeSpacing(6),\n cursor: \"pointer\",\n margin: `0`,\n paddingBlock: themeSpacing(1),\n \"&:checked\": {\n \"&::before\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"increase-3\", accentColor.get(listener)),\n },\n \"&::after\": {\n left: `calc(100% - ${themeSpacing(3.5)})`,\n },\n },\n \"&::after\": {\n content: `\"\"`,\n aspectRatio: `1/1`,\n position: \"absolute\",\n width: themeSpacing(3),\n height: themeSpacing(3),\n borderRadius: themeSpacing(999),\n left: themeSpacing(0.5),\n top: \"50%\",\n transform: \"translateY(-50%)\",\n transition: \"left 0.3s\",\n backgroundColor: (listener) => themeColor(listener, \"decrease-3\"),\n },\n \"&::before\": {\n content: '\"\"',\n width: \"100%\",\n borderRadius: themeSpacing(999),\n display: \"inline-block\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: 1,\n backgroundColor: (listener) => themeColor(listener),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n };\n}\n\nexport { inputSwitch };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Themed single-line text input primitive. Sets `type=\"text\"` and styles the\n * field with themed border, focus ring, placeholder, disabled and validation\n * (`data-status`) states. Apply to an `<input>` element.\n *\n * @hostTag input\n * @param props - Optional configuration.\n * @param props.color - Base color tone for text/border/background. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color tone for the hover/focus outline. Defaults to `\"primary\"`.\n * @example { input: \"\", type: \"text\", placeholder: \"Name\", $: [inputText()] }\n */\nfunction inputText(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n type: \"text\",\n _onSchedule: (node, element) => {\n if (node.tagName !== \"input\") {\n console.warn(\n `\"inputText\" primitive patch must use input tag and text type`,\n );\n }\n (element as any).type = \"text\";\n },\n style: {\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n minWidth: themeSpacing(10),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::placeholder\": {\n color: (listener) => themeColor(listener, \"shift-7\"),\n },\n \"&:not(:placeholder-shown)\": {\n color: (listener) => themeColor(listener, \"shift-10\"),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n \"&:invalid:not(:placeholder-shown)\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"error\")}`,\n },\n \"&[data-status=error]\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"error\")}`,\n },\n \"&[data-status=warning]\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", \"warning\")}`,\n },\n },\n };\n}\n\nexport { inputText };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Renders keyboard-key styling (themed background, border and padding) for a\n * keystroke hint. Apply to a `<kbd>` element.\n *\n * @hostTag kbd\n * @param props - Optional configuration.\n * @param props.color - Color tone for text/background/border. Defaults to `\"neutral\"`.\n * @example { kbd: \"Ctrl\", $: [keyboard()] }\n */\nfunction keyboard(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"kbd\") {\n console.warn(`\"keyboard\" primitive patch must use kbd tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n paddingBlock: themeSpacing(0.5),\n paddingInline: themeSpacing(1.5),\n borderRadius: themeSpacing(1),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n },\n };\n}\n\nexport { keyboard };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed form-label primitive: inline-flex layout with gap, themed text color,\n * focus-within highlighting and a disabled (`aria-disabled`) state. Apply to a\n * `<label>` element.\n *\n * @hostTag label\n * @param props - Optional configuration.\n * @param props.color - Base color tone for the label text. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color tone applied on focus-within. Defaults to `\"primary\"`.\n * @example { label: \"Email\", htmlFor: \"email\", $: [label()] }\n */\nfunction label(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"label\") {\n console.warn(`\"label\" primitive patch must use label tag`);\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n cursor: \"pointer\",\n \"&:focus-within\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", accentColor.get(listener)),\n },\n \"&[aria-disabled=true]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { label };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed hyperlink primitive: styles text color, hover underline, visited,\n * focus ring and a disabled state. Apply to an `<a>` element.\n *\n * @hostTag a\n * @param props - Optional configuration.\n * @param props.color - Base color tone for the link text. Defaults to `\"primary\"`.\n * @param props.accentColor - Accent color tone for visited/focus states. Defaults to `\"secondary\"`.\n * @example { a: \"Home\", href: \"/\", $: [link()] }\n */\nfunction link(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n const accentColor = toState(props.accentColor ?? \"secondary\", \"accentColor\");\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"a\") {\n console.warn(`\"link\" primitive patch must use a tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n textDecoration: \"none\",\n \"&:visited\": {\n color: (listener) =>\n themeColor(listener, \"text\", accentColor.get(listener)),\n },\n \"&:hover:not([disabled])\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n textDecoration: \"underline\",\n },\n \"&:focus-visible\": {\n borderRadius: themeSpacing(1),\n outlineOffset: themeSpacing(1),\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor.get(listener))}`,\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { link };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * An `<a>` element styled to look like a button — same visual appearance as\n * `button()` but preserves link semantics (href, middle-click, right-click).\n * Apply to an `<a>` element.\n *\n * @hostTag a\n * @param props.color - Button color tone. Optional `ValueOrState<ThemeColor>`, default \"primary\".\n * @example { a: \"Open app\", href: \"/app\", $: [linkButton({ color: \"primary\" })] }\n */\nfunction linkButton(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"primary\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"a\") {\n console.warn(`\"linkButton\" primitive patch must use a tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n textDecoration: \"none\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n width: \"fit-content\",\n display: \"inline-flex\",\n justifyContent: \"center\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 1),\n userSelect: \"none\",\n cursor: \"pointer\",\n outlineOffset: \"-1px\",\n outlineWidth: \"1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n \"&:hover\": {\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color.get(listener)),\n },\n \"&[aria-disabled=true]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n pointerEvents: \"none\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n },\n },\n };\n}\n\nexport { linkButton };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a navigation/display list container. Sets `list-style: none` and\n * zero padding; pairs with `listItem` and `listItemButton`. Apply to `<ul>`.\n *\n * @hostTag ul\n * @param props.color - Surface color tone. Optional `ThemeColor`, defaults to `\"neutral\"`.\n * @example { ul: [...], $: [list()] }\n */\nfunction list(_props: { color?: ThemeColor } = {}): PartialElement {\n return {\n style: {\n listStyle: \"none\",\n margin: 0,\n padding: 0,\n display: \"flex\",\n flexDirection: \"column\",\n },\n };\n}\n\n/**\n * A non-interactive list row. Typically wraps an icon + text. Apply to `<li>`.\n *\n * @hostTag li\n * @param props.dense - Reduce vertical padding. Optional `boolean`, defaults to `false`.\n * @example { li: \"Item\", $: [listItem()] }\n */\nfunction listItem(props: { dense?: boolean } = {}): PartialElement {\n const { dense = false } = props;\n return {\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBlock: (listener) =>\n themeSpacing(dense ? 1 : themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n },\n };\n}\n\n/**\n * An interactive (clickable) list row with hover/focus-visible states. Apply\n * to `<button>` or `<a>` inside an `<li>`.\n *\n * @param props.color - Color tone. Optional `ValueOrState<ThemeColor>`, defaults to `\"neutral\"`.\n * @param props.accentColor - Focus/active accent. Optional `ThemeColor`, defaults to `\"primary\"`.\n * @param props.dense - Reduce vertical padding. Optional `boolean`, defaults to `false`.\n * @example { button: \"Action\", $: [listItemButton()] }\n */\nfunction listItemButton(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ThemeColor;\n dense?: boolean;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = props.accentColor ?? \"primary\";\n const { dense = false } = props;\n\n return {\n style: {\n cursor: \"pointer\",\n appearance: \"none\",\n border: \"none\",\n background: \"transparent\",\n textDecoration: \"none\",\n textAlign: \"left\",\n display: \"flex\",\n alignItems: \"center\",\n width: \"100%\",\n gap: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBlock: (listener) =>\n themeSpacing(dense ? 1 : themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n transition: \"background-color 150ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"hover\", color.get(listener)),\n },\n \"&[aria-current=page], &[aria-selected=true]\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", accentColor),\n color: (listener) => themeColor(listener, \"shift-12\", accentColor),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `2px solid ${themeColor(listener, \"shift-6\", accentColor)}`,\n outlineOffset: \"-2px\",\n },\n \"&[disabled]\": { opacity: 0.5, cursor: \"not-allowed\" },\n },\n };\n}\n\nexport { list, listItem, listItemButton };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed highlight primitive: gives marked/highlighted inline text a tinted\n * background, rounded corners and padding. Apply to a `<mark>` element.\n *\n * @hostTag mark\n * @param props - Optional configuration.\n * @param props.accentColor - Accent color tone for the highlight fill and text. Defaults to `\"highlight\"`.\n * @example { mark: \"important\", $: [mark()] }\n */\nfunction mark(\n props: { accentColor?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const accentColor = toState(props.accentColor ?? \"highlight\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"mark\") {\n console.warn(`\"mark\" primitive patch must use mark tag`);\n }\n },\n dataTone: \"shift-2\",\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) =>\n themeColor(listener, \"text\", accentColor.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", accentColor.get(listener)),\n height: themeSpacing(6),\n borderRadius: themeSpacing(1),\n paddingInline: themeSpacing(1.5),\n },\n };\n}\n\nexport { mark };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\n\n/** One item inside a menu. */\ntype MenuItem = {\n /** Button label — plain string (auto-wrapped) or any DomphyElement (e.g. icon + text). */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index. */\n key?: string | number;\n /** Called when the item is clicked. */\n onClick?: () => void;\n};\n\n/**\n * All-in-one vertical menu. Generates `<button>` `[role=menuitem]` elements\n * from the `items` array with keyboard navigation (Arrow/Home/End/Enter/Space).\n * Apply to any wrapper element (`div`, `ul`, …).\n *\n * @param props.items - Item definitions `{ label, key?, onClick? }`. Pass `[]`\n * to keep the wrapper's own children (escape hatch for fully custom rows —\n * only the menu container styling and `role=\"menu\"` semantics apply then).\n * @param props.activeKey - Currently selected key (value or State). Defaults to `null`.\n * @param props.selectable - Whether items track and update the active selection. Defaults to `true`.\n * @param props.color - Background color tone for the menu. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color for the active/focus item. Defaults to `\"primary\"`.\n * @example\n * { div: null, $: [menu({ items: [\n * { label: \"Profile\", key: \"profile\", onClick: () => navigate(\"/profile\") },\n * { label: \"Settings\", key: \"settings\", onClick: () => navigate(\"/settings\") },\n * ] })] }\n */\nfunction menu(\n props: {\n items: MenuItem[];\n activeKey?: ValueOrState<number | string | null>;\n selectable?: boolean;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const {\n items = [],\n selectable = true,\n color = \"neutral\",\n accentColor = \"primary\",\n } = props;\n const activeKey = toState(props.activeKey ?? null);\n\n return {\n role: \"menu\",\n dataTone: \"shift-17\",\n _onSchedule: (node, element) => {\n // Empty items = the caller renders its own rows; leave children alone.\n if (items.length === 0) return;\n const id = node.nodeId;\n\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? index;\n\n return {\n button:\n typeof item.label === \"string\"\n ? [{ span: item.label } as DomphyElement<\"span\">]\n : [item.label],\n _key: key,\n type: \"button\",\n id: `menuitem${id}${key}`,\n role: \"menuitem\",\n ...(selectable\n ? {\n ariaCurrent: (l: Listener) =>\n activeKey.get(l) === key || undefined,\n }\n : {}),\n onClick: () => {\n if (selectable) activeKey.set(key);\n item.onClick?.();\n },\n onKeyDown: (e: Event) => {\n const k = (e as KeyboardEvent).key;\n if (k === \"Enter\" || k === \" \") {\n e.preventDefault();\n (e.target as HTMLElement).click();\n return;\n }\n if (![\"ArrowDown\", \"ArrowUp\", \"Home\", \"End\"].includes(k)) return;\n e.preventDefault();\n const keys = items.map((it, i) => it.key ?? i);\n const idx = keys.indexOf(key);\n let next = idx;\n if (k === \"ArrowDown\") next = (idx + 1) % keys.length;\n else if (k === \"ArrowUp\")\n next = (idx - 1 + keys.length) % keys.length;\n else if (k === \"Home\") next = 0;\n else if (k === \"End\") next = keys.length - 1;\n (\n document.getElementById(\n `menuitem${id}${keys[next]}`,\n ) as HTMLElement\n )?.focus();\n },\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(2),\n width: \"100%\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: (l: Listener) => themeSpacing(6 + themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 3),\n border: \"none\",\n outline: \"none\",\n color: (l: Listener) => themeColor(l, \"text\", color),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n transition: \"background-color 140ms ease\",\n \"&:hover:not([disabled]):not([aria-current=true])\": {\n backgroundColor: (l: Listener) => themeColor(l, \"hover\", color),\n },\n \"&[aria-current=true]\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-3\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-10\"),\n },\n \"&:focus-visible\": {\n outline: (l: Listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(l, \"shift-6\", accentColor)}`,\n outlineOffset: `-${themeSpacing(0.5)}`,\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n (element as any)[node.tagName] = buttons;\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n paddingBlock: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n borderRadius: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n outline: (l: Listener) =>\n `1px solid ${themeColor(l, \"border-strong\", color)}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n };\n}\n\nexport { menu };\nexport type { MenuItem };\n","import type { PartialElement, State } from \"@domphy/core\";\n\n/**\n * One keyframe. Shorthands `x`/`y` (px), `scale`, `rotate` (deg) compose into a\n * single `transform`; any other key is a raw CSS property (e.g. `opacity`,\n * `backgroundColor`).\n */\nexport type MotionKeyframe = {\n x?: number | string;\n y?: number | string;\n scale?: number | string;\n rotate?: number | string;\n} & Record<string, string | number>;\n\nexport interface MotionProps {\n /** Starting keyframe applied before the enter animation. */\n initial?: MotionKeyframe;\n /** Target keyframe. Pass a `State` to re-animate whenever it changes. */\n animate?: MotionKeyframe | State<MotionKeyframe>;\n /** Keyframe animated to before the element is removed. */\n exit?: MotionKeyframe;\n transition?: {\n /** ms, default 300. */\n duration?: number;\n /** ms, default 0. */\n delay?: number;\n /** CSS easing, default \"ease\". */\n easing?: string;\n iterations?: number;\n };\n}\n\nconst isState = (value: unknown): value is State<MotionKeyframe> =>\n !!value &&\n typeof (value as State<MotionKeyframe>).get === \"function\" &&\n (value as { _isState?: boolean })._isState === true;\n\nconst toStyles = (frame: MotionKeyframe): Keyframe => {\n const out: Record<string, string | number> = {};\n const transforms: string[] = [];\n for (const key in frame) {\n const value = frame[key];\n if (key === \"x\") {\n transforms.push(\n `translateX(${typeof value === \"number\" ? `${value}px` : value})`,\n );\n } else if (key === \"y\") {\n transforms.push(\n `translateY(${typeof value === \"number\" ? `${value}px` : value})`,\n );\n } else if (key === \"scale\") {\n transforms.push(`scale(${value})`);\n } else if (key === \"rotate\") {\n transforms.push(\n `rotate(${typeof value === \"number\" ? `${value}deg` : value})`,\n );\n } else {\n out[key] = value;\n }\n }\n if (transforms.length) out.transform = transforms.join(\" \");\n return out as Keyframe;\n};\n\n/**\n * Animation primitive driven by the Web Animations API. Runs an enter\n * animation on mount (`initial` -> `animate`), re-animates whenever `animate`\n * is a `State` that changes, and plays the `exit` keyframe before removal.\n * Has no host-tag restriction; apply to any element you want to animate.\n *\n * @param props - Optional configuration (see {@link MotionProps}).\n * @param props.initial - Starting keyframe applied before the enter animation.\n * @param props.animate - Target keyframe, or a `State` to re-animate on change.\n * @param props.exit - Keyframe animated to before the element is removed.\n * @param props.transition - Timing options.\n * @param props.transition.duration - Duration in ms. Defaults to `300`.\n * @param props.transition.delay - Delay in ms. Defaults to `0`.\n * @param props.transition.easing - CSS easing. Defaults to `\"ease\"`.\n * @param props.transition.iterations - Number of iterations. Defaults to `1`.\n * @example { div: \"Hello\", $: [motion({ initial: { opacity: 0 }, animate: { opacity: 1 } })] }\n */\nfunction motion(props: MotionProps = {}): PartialElement {\n const { initial, animate, exit, transition = {} } = props;\n const options: KeyframeAnimationOptions = {\n duration: transition.duration ?? 300,\n delay: transition.delay ?? 0,\n easing: transition.easing ?? \"ease\",\n iterations: transition.iterations ?? 1,\n fill: \"both\",\n };\n\n return {\n _onMount: (node) => {\n const el = node.domElement as HTMLElement | null;\n if (!el || typeof el.animate !== \"function\") return;\n const target = isState(animate) ? animate.get() : animate;\n if (target) {\n el.animate(\n initial ? [toStyles(initial), toStyles(target)] : [toStyles(target)],\n options,\n );\n } else if (initial) {\n Object.assign(el.style, toStyles(initial));\n }\n if (isState(animate)) {\n const release = animate.addListener((next: MotionKeyframe) => {\n el.animate([toStyles(next)], options);\n });\n node.setMetadata(\"motionRelease\", release);\n }\n },\n _onBeforeRemove: (node, done) => {\n const el = node.domElement as HTMLElement | null;\n if (!el || !exit || typeof el.animate !== \"function\") return done();\n el.animate([toStyles(exit)], options).finished.then(done, done);\n },\n _onRemove: (node) => {\n const release = node.getMetadata(\"motionRelease\") as\n | (() => void)\n | undefined;\n release?.();\n },\n };\n}\n\nexport { motion };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Themed ordered-list primitive: decimal markers positioned outside, reset\n * margins and themed text color. Apply to an `<ol>` element.\n *\n * @hostTag ol\n * @param props - Optional configuration.\n * @param props.color - Color tone for the list text. Defaults to `\"neutral\"`.\n * @example { ol: \"\", $: [orderedList()], children: [{ li: \"First\" }] }\n */\nfunction orderedList(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"ol\") {\n console.warn(`\"orderedList\" primitive patch must use ol tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n marginTop: 0,\n marginBottom: 0,\n paddingLeft: themeSpacing(3),\n listStyleType: \"decimal\",\n listStylePosition: \"outside\",\n },\n };\n}\n\nexport { orderedList };\n","import {\n type DomphyElement,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nfunction getPages(current: number, total: number): (number | \"...\")[] {\n if (total <= 7) return Array.from({ length: total }, (_, i) => i + 1);\n const pages: (number | \"...\")[] = [1];\n if (current > 3) pages.push(\"...\");\n const start = Math.max(2, current - 1);\n const end = Math.min(total - 1, current + 1);\n for (let i = start; i <= end; i++) pages.push(i);\n if (current < total - 2) pages.push(\"...\");\n pages.push(total);\n return pages;\n}\n\n/**\n * Themed pagination control. Renders previous/next buttons plus truncated page\n * numbers (with ellipses), tracks the current page in a `State`, and updates it\n * on click. Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props - Configuration.\n * @param props.total - Required. Total number of pages.\n * @param props.value - Current page, accepts a value or `State`. Defaults to `1`.\n * @param props.color - Base color tone for the page buttons. Defaults to `\"neutral\"`.\n * @param props.accentColor - Accent color tone for the active page. Defaults to `\"primary\"`.\n * @example { div: \"\", $: [pagination({ total: 10, value: 1 })] }\n */\nfunction pagination(props: {\n value?: ValueOrState<number>;\n total: number;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n}): PartialElement {\n const { total, color = \"neutral\", accentColor = \"primary\" } = props;\n const state = toState(props.value ?? 1);\n\n const btnBase = {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n minWidth: (listener: any) => themeSpacing(6 + themeDensity(listener) * 2),\n height: (listener: any) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener: any) => themeSpacing(themeDensity(listener) * 2),\n borderRadius: (listener: any) => themeSpacing(themeDensity(listener) * 1.5),\n border: \"none\",\n cursor: \"pointer\",\n fontSize: (listener: any) => themeSize(listener, \"inherit\"),\n backgroundColor: \"transparent\",\n color: (listener: any) => themeColor(listener, \"text\", color),\n transition: \"background-color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener: any) => themeColor(listener, \"hover\", color),\n },\n \"&:focus-visible\": {\n boxShadow: (listener: any) => focusRing(listener, accentColor),\n },\n \"&[disabled]\": {\n opacity: 0.4,\n cursor: \"not-allowed\",\n },\n };\n\n const activeStyle = {\n ...btnBase,\n backgroundColor: (listener: any) =>\n themeColor(listener, \"shift-6\", accentColor),\n color: (listener: any) => themeColor(listener, \"shift-11\", accentColor),\n fontWeight: \"600\",\n cursor: \"default\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (listener: any) =>\n themeColor(listener, \"shift-6\", accentColor),\n },\n };\n\n return {\n role: \"navigation\",\n ariaLabel: \"Pagination\",\n _onInsert: (node) => {\n if (node.tagName !== \"div\")\n console.warn('\"pagination\" patch must use div tag');\n },\n _onInit: (node) => {\n const content: DomphyElement<\"div\"> = {\n div: (listener) => {\n const page = state.get(listener);\n const items: DomphyElement[] = [];\n\n // Prev button\n items.push({\n button: \"‹\",\n _key: \"prev\",\n type: \"button\",\n ariaLabel: \"Previous page\",\n disabled: page <= 1,\n onClick: () => page > 1 && state.set(page - 1),\n style: btnBase,\n });\n\n // Page buttons. Keyed by page number (or a running ellipsis index —\n // there can be up to two \"...\" spans) so the list survives length\n // changes across pages without the unkeyed-reuse footgun.\n let ellipsisIndex = 0;\n for (const p of getPages(page, total)) {\n if (p === \"...\") {\n items.push({\n span: \"…\",\n _key: `ellipsis-${ellipsisIndex++}`,\n ariaHidden: \"true\",\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n paddingInline: (listener: any) =>\n themeSpacing(themeDensity(listener) * 2),\n color: (listener: any) =>\n themeColor(listener, \"shift-7\", color),\n },\n });\n } else {\n const isActive = p === page;\n items.push({\n button: String(p),\n _key: `page-${p}`,\n type: \"button\",\n ariaLabel: `Page ${p}`,\n ariaCurrent: isActive ? \"page\" : undefined,\n disabled: isActive,\n onClick: () => state.set(p),\n style: isActive ? activeStyle : btnBase,\n });\n }\n }\n\n // Next button\n items.push({\n button: \"›\",\n _key: \"next\",\n type: \"button\",\n ariaLabel: \"Next page\",\n disabled: page >= total,\n onClick: () => page < total && state.set(page + 1),\n style: btnBase,\n });\n\n return items;\n },\n style: {\n display: \"flex\",\n alignItems: \"center\",\n gap: themeSpacing(1),\n },\n };\n node.children.insert(content);\n },\n style: {\n display: \"inline-flex\",\n },\n };\n}\n\nexport { pagination };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A padded section for side-panel/inspector UIs — density-aware padding on\n * all sides, with an optional bottom divider for sections stacked one after\n * another. A thin wrapper: it does not impose flex layout on its children —\n * pair it with `stack()` or `row()` for that. No host-tag check; apply to\n * any block element.\n *\n * @param props.padding - Spacing multiplier for padding on all sides (default 4 = 1em at density 1).\n * @param props.divider - Adds a bottom border, for sections stacked one after another. Defaults to `false`.\n * @param props.color - Theme color tone for the divider border. Defaults to `\"neutral\"`.\n * @example { div: [{ h3: \"Parameters\" }, { p: \"...\" }], $: [panelSection()] }\n * @example\n * { div: [\n * { div: \"Section A\", $: [panelSection({ divider: true })] },\n * { div: \"Section B\", $: [panelSection()] },\n * ], $: [stack({ gap: 0 })] }\n */\nfunction panelSection(\n props: {\n padding?: number;\n divider?: boolean;\n color?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const { padding = 4, divider = false } = props;\n const color = toState(props.color ?? \"neutral\", \"color\");\n return {\n style: {\n padding: (listener) => themeSpacing(themeDensity(listener) * padding),\n ...(divider\n ? {\n borderBottom: (listener) =>\n `1px solid ${themeColor(listener, \"border\", color.get(listener))}`,\n }\n : {}),\n },\n };\n}\n\nexport { panelSection };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Themed paragraph primitive: comfortable line-height, reset margins and themed\n * text color. Apply to a `<p>` element.\n *\n * @hostTag p\n * @param props - Optional configuration.\n * @param props.color - Color tone for the paragraph text. Defaults to `\"neutral\"`.\n * @example { p: \"Hello world\", $: [paragraph()] }\n */\nfunction paragraph(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"p\") {\n console.warn(`\"paragraph\" primitive patch must use p tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n lineHeight: 1.5,\n marginTop: 0,\n marginBottom: 0,\n },\n };\n}\n\nexport { paragraph };\n","import {\n type DomphyElement,\n type Listener,\n merge,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport { themeColor, themeDensity, themeSpacing } from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\n\n/**\n * Floating popover primitive. Attaches to its host as the anchor/trigger and\n * shows a floating `content` element (with `role=\"dialog\"`) on click or hover,\n * positioned via `@domphy/floating`. Returns the anchor partial, which merges\n * trigger wiring (haspopup/expanded, focus/blur dismissal). Apply to the\n * trigger element you want the popover anchored to.\n *\n * @param props - Configuration.\n * @param props.openOn - Interaction that opens the popover: `\"click\"` or `\"hover\"`. Defaults to `\"click\"`.\n * @param props.open - Open state, accepts a value or `State`. Defaults to `false`.\n * @param props.placement - Floating placement (e.g. `\"bottom\"`, `\"top-start\"`), value or `State`. Defaults to `\"bottom\"`.\n * @param props.content - The floating content element to display.\n * @example { button: \"Open\", $: [popover({ openOn: \"click\", content: { div: \"Hi\" } })] }\n */\nfunction popover(props: {\n openOn?: \"click\" | \"hover\";\n open?: ValueOrState<boolean>;\n placement?: ValueOrState<Placement>;\n content: DomphyElement;\n}): PartialElement {\n const { open = false, placement = \"bottom\", openOn = \"click\" } = props;\n\n let popoverId: string | null = null;\n const openState = toState(open);\n const placeState = toState(placement);\n\n const { show, hide, anchorPartial } = createFloating({\n kind: \"popover\",\n open: openState,\n placement: placeState,\n content: props.content,\n // Hovering the panel itself (not just the trigger) must keep it open —\n // handled generically inside floating.ts's behavior instance.\n keepOpenOnContentHover: openOn === \"hover\",\n });\n\n const popoverPartial: PartialElement = {\n role: \"dialog\",\n dataTone: \"shift-14\",\n style: {\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\"),\n borderRadius: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n outline: (l: Listener) => `1px solid ${themeColor(l, \"border-strong\")}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n _onInsert: (node) => {\n const id = node.attributes.get(\"id\");\n popoverId = id || node.nodeId;\n !id && node.attributes.set(\"id\", popoverId);\n },\n };\n\n props.content.$ ||= [];\n props.content.$.push(popoverPartial);\n\n const triggerPartial: PartialElement = {\n ariaHaspopup: \"dialog\",\n ariaExpanded: (listener) => openState.get(listener),\n onMouseEnter: (_e, node) => openOn === \"hover\" && show(node),\n onMouseLeave: (_e, node) => openOn === \"hover\" && hide(node),\n onClick: (_e, node) => {\n if (openOn === \"click\") {\n if (openState.get()) {\n hide(node);\n } else {\n show(node);\n }\n }\n },\n onKeyDown: (e, node) => {\n if ((e as KeyboardEvent).key === \"Escape\" && openState.get()) hide(node);\n },\n onFocus: (_e, node) => openOn === \"hover\" && show(node),\n onBlur: (e, node) => {\n const related = (e as FocusEvent).relatedTarget as Node | null;\n const root = node.getRoot().domElement as Element;\n const floatingEl = popoverId\n ? root.querySelector(`#${CSS.escape(popoverId)}`)\n : null;\n if (related && floatingEl?.contains(related)) return;\n hide(node);\n },\n _onMount: (node) =>\n popoverId && node.attributes.set(\"ariaControls\", popoverId),\n };\n merge(anchorPartial, triggerPartial);\n\n return anchorPartial;\n}\n\nexport { popover };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Renders a small rotated arrow (via a `::after` pseudo-element) that points from a\n * popover/tooltip toward its anchor, positioned and oriented based on the floating placement.\n * The arrow direction is computed by flipping the given placement. No host-tag check is\n * performed; apply it to the popover container element.\n *\n * @param props.placement - Floating placement the popover sits at; the arrow is drawn on the\n * opposite (flipped) side. Accepts a value or reactive state. Defaults to `\"bottom-end\"`.\n * One of: `top` | `bottom` | `left` | `right` | `top-start` | `top-end` | `bottom-start` |\n * `bottom-end` | `left-start` | `left-end` | `right-start` | `right-end`.\n * @param props.sideOffset - CSS length used to offset the arrow toward the start/end edge.\n * Defaults to `themeSpacing(6)`.\n * @param props.color - Theme color tone for the arrow fill and border. Defaults to `\"neutral\"`.\n * @param props.bordered - Whether the arrow draws a 1px border (set to `0px` when false).\n * Defaults to `true`.\n * @example { div: [...], $: [popoverArrow({ placement: \"top\" })] }\n */\nfunction popoverArrow(\n props: {\n placement?: ValueOrState<Placement>;\n sideOffset?: string;\n color?: ThemeColor;\n bordered?: boolean;\n } = {},\n): PartialElement {\n const {\n placement = \"bottom-end\",\n color = \"neutral\",\n sideOffset = themeSpacing(6),\n bordered = true,\n } = props;\n\n const place = toState(placement);\n\n const flipMap: Record<Placement, Placement> = {\n top: \"bottom\",\n bottom: \"top\",\n left: \"right\",\n right: \"left\",\n \"top-start\": \"bottom-end\",\n \"top-end\": \"bottom-start\",\n \"bottom-start\": \"top-end\",\n \"bottom-end\": \"top-start\",\n \"left-start\": \"right-end\",\n \"left-end\": \"right-start\",\n \"right-start\": \"left-end\",\n \"right-end\": \"left-start\",\n };\n\n const getFlipped = (listener: any) =>\n flipMap[place.get(listener)] ?? flipMap[\"bottom-end\"];\n const start = (pos: string) =>\n pos.includes(\"start\") ? sideOffset : pos.includes(\"end\") ? \"auto\" : \"50%\";\n const end = (pos: string) =>\n pos.includes(\"end\") ? sideOffset : pos.includes(\"start\") ? \"auto\" : \"50%\";\n\n return {\n style: {\n fontSize: (listener) => themeSize(listener),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color),\n position: \"relative\",\n \"&::after\": {\n content: `\"\"`,\n position: \"absolute\",\n width: themeSpacing(1.5),\n height: themeSpacing(1.5),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n borderWidth: bordered ? \"1px\" : 0,\n borderColor: (listener) => themeColor(listener, \"inherit\", color),\n borderTopStyle: (listener) => {\n const pos = getFlipped(listener);\n\n return pos.includes(\"top\") || pos.includes(\"right\")\n ? `solid`\n : \"none\";\n },\n borderBottomStyle: (listener) => {\n const pos = getFlipped(listener);\n\n return pos.includes(\"bottom\") || pos.includes(\"left\")\n ? `solid`\n : \"none\";\n },\n borderLeftStyle: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"top\") || pos.includes(\"left\") ? `solid` : \"none\";\n },\n borderRightStyle: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"bottom\") || pos.includes(\"right\")\n ? `solid`\n : \"none\";\n },\n top: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"top\")\n ? 0\n : pos.includes(\"bottom\")\n ? \"auto\"\n : start(pos);\n },\n right: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"right\")\n ? 0\n : pos.includes(\"left\")\n ? \"auto\"\n : end(pos);\n },\n bottom: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"bottom\")\n ? 0\n : pos.includes(\"top\")\n ? \"auto\"\n : end(pos);\n },\n left: (listener) => {\n const pos = getFlipped(listener);\n return pos.includes(\"left\")\n ? 0\n : pos.includes(\"right\")\n ? \"auto\"\n : start(pos);\n },\n transform: (listener) => {\n const pos = getFlipped(listener);\n const x =\n pos.includes(\"right\") ||\n (pos.includes(\"end\") && !pos.includes(\"left\"))\n ? \"50%\"\n : \"-50%\";\n const y =\n pos.includes(\"bottom\") ||\n (pos.includes(\"end\") && !pos.includes(\"top\"))\n ? \"50%\"\n : \"-50%\";\n return `translate(${x},${y}) rotate(45deg)`;\n },\n },\n },\n };\n}\n\nexport { popoverArrow };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a preformatted text block: inherited font size, themed foreground/background,\n * no border, density-scaled padding and rounded corners.\n *\n * @hostTag pre\n * @param props.color - Theme color tone for text and background. Accepts a value or reactive\n * state. Defaults to `\"neutral\"`.\n * @example { pre: \"const x = 1\", $: [preformated()] }\n */\nfunction preformated(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n dataTone: \"shift-2\",\n _onInsert: (node) => {\n if (node.tagName !== \"pre\") {\n console.warn(`\"preformated\" primitive patch must use pre tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n border: \"none\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n },\n };\n}\n\nexport { preformated };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Styles a native progress bar: full-width, pill-shaped track with a themed fill,\n * including the WebKit progress-bar/value pseudo-elements and a width transition.\n *\n * @hostTag progress\n * @param props.color - Theme color tone for the track/background. Accepts a value or reactive\n * state. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color tone for the filled value. Accepts a value or reactive\n * state. Defaults to `\"primary\"`.\n * @example { progress: null, value: 40, max: 100, $: [progress()] }\n */\nfunction progress(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"progress\") {\n console.warn(`\"progress\" primitive patch must use progress tag`);\n }\n },\n style: {\n appearance: \"none\",\n width: \"100%\",\n height: themeSpacing(2),\n border: 0,\n borderRadius: themeSpacing(999),\n overflow: \"hidden\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n \"&::-webkit-progress-bar\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color.get(listener)),\n borderRadius: themeSpacing(999),\n },\n \"&::-webkit-progress-value\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-9\", accentColor.get(listener)),\n borderRadius: themeSpacing(999),\n transition: \"width 220ms ease\",\n },\n },\n };\n}\n\nexport { progress };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\nconst STAR_FILLED =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"currentColor\" width=\"1em\" height=\"1em\">` +\n `<path d=\"M12 17.27L18.18 21l-1.64-7.03L22 9.24l-7.19-.61L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21z\"/>` +\n `</svg>`;\nconst STAR_EMPTY =\n `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"currentColor\" width=\"1em\" height=\"1em\">` +\n `<path d=\"M22 9.24l-7.19-.62L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21 12 17.27 18.18 21l-1.63-7.03L22 9.24zM12 15.4l-3.76 2.27 1-4.28-3.32-2.88 4.38-.38L12 6.1l1.71 4.04 4.38.38-3.32 2.88 1 4.28L12 15.4z\"/>` +\n `</svg>`;\n\n/**\n * Interactive star rating applied to a container `<div>`. Manages its own star\n * children: click to set, Arrow keys to adjust, hover to preview. In `readOnly`\n * mode stars are non-interactive. Apply to a `<div>` element.\n *\n * @hostTag div\n * @param props.value - Current rating (0 – max). `ValueOrState<number>`, defaults to `0`.\n * @param props.max - Total number of stars. Optional `number`, defaults to `5`.\n * @param props.onChange - Called with the new value when the user picks a star.\n * @param props.readOnly - Disable interaction. Optional `boolean`, defaults to `false`.\n * @param props.color - Star color tone. Optional `ThemeColor`, defaults to `\"warning\"`.\n * @example { div: null, $: [rating({ value: ratingState, onChange: (v) => ratingState.set(v) })] }\n */\nfunction rating(\n props: {\n value?: ValueOrState<number>;\n max?: number;\n onChange?: (value: number) => void;\n readOnly?: boolean;\n color?: ThemeColor;\n } = {},\n): PartialElement {\n const { max = 5, readOnly = false, onChange } = props;\n const color = props.color ?? \"warning\";\n const valueState = toState(props.value ?? 0);\n // Hover preview only — never reported via onChange, only affects display.\n const hoveredState = toState(0);\n\n const activeCount = (listener: Listener) => {\n const hovered = hoveredState.get(listener);\n return hovered > 0 ? hovered : valueState.get(listener);\n };\n\n return {\n role: \"group\",\n ariaLabel: \"Rating\",\n style: {\n display: \"inline-flex\",\n gap: themeSpacing(0.5),\n fontSize: \"1.5rem\",\n cursor: readOnly ? \"default\" : \"pointer\",\n color: (listener) => themeColor(listener, \"muted\", color),\n },\n // Build stars as real child elements (not imperative DOM mutation in\n // _onMount) so generateHTML()/SSR emits the actual star markup.\n _onInit: (node) => {\n for (let i = 1; i <= max; i++) {\n const index = i;\n const interactive = readOnly\n ? {}\n : {\n onClick: () => {\n const next = index === valueState.get() ? 0 : index;\n valueState.set(next);\n onChange?.(next);\n hoveredState.set(0);\n },\n onMouseEnter: () => hoveredState.set(index),\n onMouseLeave: () => hoveredState.set(0),\n onKeyDown: (e: KeyboardEvent) => {\n const current = valueState.get();\n let next = current;\n if (e.key === \"ArrowRight\" || e.key === \"ArrowUp\") {\n next = Math.min(max, current + 1);\n e.preventDefault();\n } else if (e.key === \"ArrowLeft\" || e.key === \"ArrowDown\") {\n next = Math.max(0, current - 1);\n e.preventDefault();\n } else {\n return;\n }\n valueState.set(next);\n onChange?.(next);\n const target = next > 0 ? next - 1 : 0;\n (node.domElement?.children[target] as HTMLElement)?.focus();\n },\n };\n\n const star: DomphyElement<\"button\"> = {\n button: (listener) =>\n index <= activeCount(listener) ? STAR_FILLED : STAR_EMPTY,\n _key: index,\n type: \"button\",\n ariaLabel: `${index} star${index > 1 ? \"s\" : \"\"}`,\n ...interactive,\n style: {\n background: \"none\",\n border: \"none\",\n outline: \"none\",\n borderRadius: themeSpacing(1),\n padding: 0,\n cursor: \"inherit\",\n color: \"inherit\",\n fontSize: \"inherit\",\n display: \"flex\",\n alignItems: \"center\",\n transition: \"box-shadow 140ms ease\",\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, color),\n },\n },\n };\n node.children.insert(star);\n }\n },\n };\n}\n\nexport { rating };\n","import type { PartialElement, StyleObject } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Circular ring progress indicator rendered via CSS `conic-gradient` and a\n * circular `mask`. Progress starts at 12 o'clock and advances clockwise.\n * Exposes `role=\"progressbar\"` with `aria-valuenow/min/max`. Apply to a `<div>`.\n *\n * @hostTag div\n * @param props.value - Progress percentage 0–100. Accepts a value or reactive state. Defaults to `0`.\n * @param props.color - Theme color for the filled arc. Accepts a value or reactive state. Defaults to `\"primary\"`.\n * @param props.trackColor - Theme color for the background track. Accepts a value or reactive state. Defaults to `\"neutral\"`.\n * @param props.size - Diameter in `themeSpacing` units. Defaults to `16` (= `4em`).\n * @param props.thickness - Ring stroke as a fraction of the radius (0–0.5). Defaults to `0.25`.\n * @example { div: null, $: [ringProgress({ value: 65 })] }\n * @example { div: null, $: [ringProgress({ value: loadingState, color: \"success\", size: 20 })] }\n */\nfunction ringProgress(\n props: {\n value?: ValueOrState<number>;\n color?: ValueOrState<ThemeColor>;\n trackColor?: ValueOrState<ThemeColor>;\n size?: number;\n thickness?: number;\n } = {},\n): PartialElement {\n const { size = 16, thickness = 0.25 } = props;\n const value = toState(props.value ?? 0, \"value\");\n const color = toState(props.color ?? \"primary\", \"color\");\n const trackColor = toState(props.trackColor ?? \"neutral\", \"trackColor\");\n\n // Mask cuts the center to create a donut shape.\n // Uses `closest-side` so the gradient circle matches the visible element circle\n // exactly, making `holePercent` directly represent the fraction of outer radius.\n const holePercent = Math.round((1 - thickness) * 100);\n const mask = `radial-gradient(circle closest-side, transparent ${holePercent}%, black ${holePercent}%)`;\n\n return {\n role: \"progressbar\",\n ariaValuenow: (l) => String(Math.round(value.get(l))),\n ariaValuemin: \"0\",\n ariaValuemax: \"100\",\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn('\"ringProgress\" patch must use div tag');\n }\n },\n style: {\n display: \"inline-flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: themeSpacing(size),\n height: themeSpacing(size),\n borderRadius: \"50%\",\n // Fill arc from 12 o'clock clockwise; `from -90deg` rotates the start point.\n background: (l) =>\n `conic-gradient(from -90deg, ${themeColor(l, \"shift-9\", color.get(l))} ${value.get(l)}%, ${themeColor(l, \"shift-3\", trackColor.get(l))} 0%)`,\n WebkitMask: mask,\n mask,\n } as StyleObject,\n };\n}\n\nexport { ringProgress };\n","import type { PartialElement } from \"@domphy/core\";\nimport { themeDensity, themeSpacing } from \"@domphy/theme\";\nimport type { FlexAlign } from \"./stack.js\";\n\ntype FlexJustify =\n | \"flex-start\"\n | \"center\"\n | \"flex-end\"\n | \"space-between\"\n | \"space-around\"\n | \"space-evenly\";\n\n/**\n * A horizontal flex row with spacing between children, vertically centered by\n * default. The general-purpose primitive for icon+label rows, field rows,\n * and button groups — instead of hand-rolling `display: flex; alignItems:\n * center; gap: ...`. `toolbar()` is a semantic alias of this same shape for\n * headers/nav bars. Styles the host only; apply to any block element.\n *\n * @param props.gap - Spacing multiplier for gap between items (default 4 = 1em at density 1).\n * @param props.align - Cross-axis alignment (`alignItems`). Defaults to `\"center\"`.\n * @param props.justify - Main-axis distribution (`justifyContent`). Unset by default (flex-start).\n * @param props.wrap - Allow items to wrap onto multiple lines. Defaults to `false`.\n * @example { div: [{ span: \"Icon\" }, { span: \"Label\" }], $: [row()] }\n * @example { div: [...], $: [row({ justify: \"space-between\", wrap: true })] }\n */\nfunction row(\n props: {\n gap?: number;\n align?: FlexAlign;\n justify?: FlexJustify;\n wrap?: boolean;\n } = {},\n): PartialElement {\n const { gap = 4, align = \"center\", justify, wrap = false } = props;\n return {\n style: {\n display: \"flex\",\n alignItems: align,\n gap: (listener) => themeSpacing(themeDensity(listener) * gap),\n ...(justify ? { justifyContent: justify } : {}),\n ...(wrap ? { flexWrap: \"wrap\" } : {}),\n },\n };\n}\n\nexport { row };\nexport type { FlexJustify };\n","import type { PartialElement, StyleObject } from \"@domphy/core\";\nimport { toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Applies thin, themed overlay scrollbars to any scrollable container.\n * Covers WebKit (Chrome/Safari/Edge) via `::-webkit-scrollbar` pseudo-elements\n * and Firefox via `scrollbar-width`/`scrollbar-color`. Sets `overflow: auto`.\n * No host-tag check; apply to any block element.\n *\n * @param props.color - Theme color for the scrollbar thumb. Accepts a value or\n * reactive state. Defaults to `\"neutral\"`.\n * @example { div: [...], style: { maxHeight: \"300px\" }, $: [scrollArea()] }\n */\nfunction scrollArea(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n style: {\n overflow: \"auto\",\n \"&::-webkit-scrollbar\": {\n width: themeSpacing(2),\n height: themeSpacing(2),\n },\n \"&::-webkit-scrollbar-track\": {\n background: \"transparent\",\n },\n \"&::-webkit-scrollbar-thumb\": {\n backgroundColor: (l) => themeColor(l, \"shift-5\", color.get(l)),\n borderRadius: themeSpacing(999),\n // Transparent border creates visual padding around the thumb.\n border: `${themeSpacing(0.5)} solid transparent`,\n backgroundClip: \"content-box\",\n },\n \"&::-webkit-scrollbar-thumb:hover\": {\n backgroundColor: (l) => themeColor(l, \"shift-7\", color.get(l)),\n },\n // Firefox thin scrollbar with matching thumb/track colors.\n scrollbarWidth: \"thin\",\n scrollbarColor: (l) =>\n `${themeColor(l, \"shift-5\", color.get(l))} transparent`,\n } as StyleObject,\n };\n}\n\nexport { scrollArea };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/** One item inside a segmented control. */\ntype SegmentedItem = {\n /** Button label — plain string (auto-wrapped) or any DomphyElement. */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index. */\n key?: string;\n};\n\n/**\n * All-in-one single-select segmented control. Generates `<button>` option\n * elements from the `items` array. Apply to any wrapper element.\n *\n * @param props.items - Item definitions `{ label, key? }`.\n * @param props.value - Initially selected key (value or State). Defaults to the first item's key.\n * @param props.color - Theme color for the control background. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for the selected item. Defaults to `\"primary\"`.\n * @example\n * { div: null, $: [segmented({ items: [\n * { label: \"Day\", key: \"day\" },\n * { label: \"Month\", key: \"month\" },\n * { label: \"Year\", key: \"year\" },\n * ] })] }\n */\nfunction segmented(\n props: {\n items: SegmentedItem[];\n value?: ValueOrState<string>;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const { items = [], color = \"neutral\", accentColor = \"primary\" } = props;\n const value = toState(props.value ?? items[0]?.key ?? \"\");\n\n return {\n role: \"radiogroup\",\n // Expose value in context so segmentedItem() escape-hatch still works.\n _context: { segmented: { value } },\n _onSchedule: (node, element) => {\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? String(index);\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n button: [labelEl],\n _key: key,\n type: \"button\",\n role: \"radio\",\n ariaChecked: (l: Listener) => value.get(l) === key,\n onClick: () => value.set(key),\n style: {\n cursor: \"pointer\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: themeSpacing(6),\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(3),\n border: \"none\",\n borderRadius: themeSpacing(10),\n color: (l: Listener) => themeColor(l, \"text\", color),\n backgroundColor: \"transparent\",\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled]):not([aria-checked=true])\": {\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n },\n \"&[aria-checked=true]\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-0\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-10\", accentColor),\n },\n \"&:focus-visible\": {\n boxShadow: (l: Listener) => focusRing(l, accentColor),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n (element as any)[node.tagName] = buttons;\n },\n style: {\n display: \"inline-flex\",\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(1),\n gap: themeSpacing(0.5),\n borderRadius: themeSpacing(10),\n backgroundColor: (l: Listener) => themeColor(l, \"shift-2\", color),\n },\n };\n}\n\nexport { segmented };\nexport type { SegmentedItem };\n","import type { Listener, PartialElement } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeColorToken,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a native `<select>` control: removes the default appearance, applies themed\n * colors, outline, density-scaled padding/radius, a custom chevron background icon, and\n * hover/focus/disabled/optgroup/option states.\n *\n * @hostTag select\n * @param props.color - Theme color tone for text, background and outline. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color tone for hover/focus outlines. Defaults to `\"primary\"`.\n * @example { select: [{ option: \"A\" }], $: [select()] }\n */\nfunction select(\n props: { color?: ThemeColor; accentColor?: ThemeColor } = {},\n): PartialElement {\n const { color = \"neutral\", accentColor = \"primary\" } = props;\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"select\") {\n console.warn(`\"select\" primitive patch must use select tag`);\n }\n },\n style: {\n appearance: \"none\",\n fontFamily: \"inherit\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n lineHeight: \"inherit\",\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n border: \"none\",\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color)}`,\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingLeft: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingRight: (listener) => themeSpacing(themeDensity(listener) * 5),\n backgroundImage: (l: Listener) => {\n const svg = `<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 10 6\"><path d=\"M1 1l4 4 4-4\" stroke=\"${themeColorToken(l, \"shift-7\")}\" stroke-width=\"1.5\" fill=\"none\" stroke-linecap=\"round\" stroke-linejoin=\"round\"/></svg>`;\n return `url(\"data:image/svg+xml,${encodeURIComponent(svg)}\")`;\n },\n backgroundRepeat: \"no-repeat\",\n backgroundPosition: `right ${themeSpacing(2)} center`,\n backgroundSize: `${themeSpacing(2.5)} ${themeSpacing(1.5)}`,\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&:not([multiple])\": {\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor)}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor),\n },\n \"& optgroup\": {\n color: (listener) => themeColor(listener, \"shift-11\", color),\n },\n \"& option[disabled]\": {\n color: (listener) => themeColor(listener, \"shift-7\", \"neutral\"),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n },\n },\n };\n}\n\nexport { select };\n","import {\n type DomphyElement,\n merge,\n type PartialElement,\n type StyleObject,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\nimport { tag } from \"./tag.js\";\n\n/**\n * A clickable select trigger box that renders the currently selected option(s) as removable\n * tags and toggles a floating popover (the dropdown content) anchored to itself. Selected\n * labels are derived from `options` matching the bound `value`; removing a tag updates the value.\n *\n * @hostTag div\n * @param props.multiple - Whether multiple selection is allowed (renders removable tags and\n * keeps the popover open on click). Defaults to `false`.\n * @param props.value - Bound selection value(s). Accepts a value or reactive state of an array of\n * `number | string | null | undefined`, or a single `number | string | null | undefined`.\n * @param props.options - List of `{ label, value }` options used to resolve selected labels.\n * Defaults to `[]`.\n * @param props.placement - Floating placement of the dropdown popover. Accepts a value or\n * reactive state. Defaults to `\"bottom\"`.\n * @param props.content - Required. The popover/dropdown content element shown when open.\n * @param props.color - Theme color tone for the box text/background. Defaults to `\"neutral\"`.\n * @param props.open - Whether the popover is open. Accepts a value or reactive state. Defaults to `false`.\n * @example { div: null, $: [selectBox({ content: { div: [...] }, options: [{ label: \"A\", value: \"a\" }] })] }\n */\nfunction selectBox(props: {\n multiple?: boolean;\n value?: ValueOrState<\n | Array<number | string | null | undefined>\n | number\n | string\n | null\n | undefined\n >;\n options?: Array<{ label: string; value: string }>;\n placement?: ValueOrState<Placement>;\n content: DomphyElement;\n color?: ThemeColor;\n open?: ValueOrState<boolean>;\n}): PartialElement {\n const {\n options = [],\n placement = \"bottom\",\n color = \"neutral\",\n open = false,\n multiple = false,\n } = props;\n\n const state = toState(props.value);\n const openState = toState(open);\n const { show, hide, anchorPartial } = createFloating({\n kind: \"selectBox\",\n open: openState,\n placement: toState(placement),\n content: props.content,\n });\n\n const popoverPartial: PartialElement = {\n onClick: (_e, node) => !multiple && hide(node),\n dataTone: \"shift-14\",\n style: {\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\")}`,\n outlineOffset: \"-1px\",\n boxShadow: elevation(\"medium\"),\n },\n };\n\n merge(props.content, popoverPartial);\n\n const wrap: DomphyElement<\"div\"> = {\n div: (listener) => {\n const val = state.get(listener);\n const vals = Array.isArray(val) ? val : [val];\n const opts = options.filter((opt) => vals.includes(opt.value));\n return opts.map((opt) => ({\n span: opt.label,\n $: [tag({ color, removable: multiple })],\n _key: opt.value,\n _onRemove: (_node) => {\n const cur = state.get();\n const curVals = Array.isArray(cur) ? cur : [cur];\n const filter = curVals.filter((v) => v !== opt.value);\n multiple ? state.set(filter as any) : state.set(filter[0] as any);\n },\n })) as DomphyElement<\"span\">[];\n },\n style: {\n display: \"flex\",\n flexWrap: \"wrap\",\n gap: themeSpacing(1),\n flex: 1,\n } as StyleObject,\n };\n\n const partial: PartialElement = {\n _onInsert: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"selectBox\" patch must use div tag`);\n }\n },\n _onInit: (node) => node.children.insert(wrap),\n onClick: (_e, node) => (openState.get() ? hide(node) : show(node)),\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n minHeight: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n minWidth: themeSpacing(32),\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 2),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n },\n };\n\n merge(anchorPartial, partial);\n return anchorPartial;\n}\n\nexport { selectBox };\n","import type { PartialElement } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A single selectable option row (`role=\"option\"`) for use inside a `selectList`. Reads the\n * `select` context to reflect/toggle selection: it sets `aria-selected` from the bound value and\n * toggles the value (single or multiple) on click. Styles hover/selected/focus states.\n *\n * @hostTag div\n * @param props.accentColor - Theme color tone for the selected/focus state. Defaults to `\"primary\"`.\n * @param props.color - Theme color tone for text/background. Defaults to `\"neutral\"`.\n * @param props.value - The option value compared against and written to the select state.\n * Defaults to `null`.\n * @example { div: \"Option A\", $: [selectItem({ value: \"a\" })] }\n */\nfunction selectItem(\n props: {\n accentColor?: ThemeColor;\n color?: ThemeColor;\n value?: number | string;\n } = {},\n): PartialElement {\n const { accentColor = \"primary\", color = \"neutral\", value = null } = props;\n\n const partial: PartialElement = {\n role: \"option\",\n _onInit: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"selectItem\" patch must use div tag`);\n }\n const select = node.getContext(\"select\");\n if (select) {\n const state = select.value;\n node.attributes.set(\"ariaSelected\", (listener) => {\n const val = state.get(listener);\n return select.multiple ? val.includes(value) : val === value;\n });\n node.addEvent(\"click\", () => {\n const val = state.get();\n if (select.multiple) {\n val.includes(value)\n ? state.set(val.filter((v: number | string) => v !== value))\n : state.set(val.concat([value]));\n } else {\n val !== value && state.set(value);\n }\n });\n }\n },\n style: {\n cursor: \"pointer\",\n display: \"flex\",\n alignItems: \"center\",\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n height: (listener) => themeSpacing(6 + themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n border: \"none\",\n outline: \"none\",\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n \"&:hover:not([disabled]):not([aria-selected=true])\": {\n backgroundColor: (listener) => themeColor(listener, \"hover\", color),\n },\n \"&[aria-selected=true]\": {\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-6\", accentColor),\n color: (listener) => themeColor(listener, \"shift-11\"),\n },\n \"&:focus-visible\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-6\", accentColor)}`,\n outlineOffset: `-${themeSpacing(0.5)}`,\n },\n },\n };\n return partial;\n}\n\nexport { selectItem };\n","import {\n type DomphyElement,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Container for a list of `selectItem`s that owns the selection state. It exposes a `select`\n * context (`{ value, multiple }`) consumed by child items, and injects hidden `<input>`(s)\n * carrying the selected value(s) under `name` for form submission.\n *\n * @hostTag div\n * @param props.multiple - Whether multiple selection is allowed; also sets the default empty\n * value (`[]` vs `null`). Defaults to `false`.\n * @param props.value - Bound selection value(s). Accepts a value or reactive state of an array of\n * `number | string | null`, or a single `number | string | null`. Defaults to `[]` when\n * `multiple`, otherwise `null`.\n * @param props.color - Theme color tone for the background. Defaults to `\"neutral\"`.\n * @param props.name - Name attribute for the hidden inputs (form field name).\n * @example { div: [{ div: \"A\", $: [selectItem({ value: \"a\" })] }], $: [selectList({ name: \"pick\" })] }\n */\nfunction selectList(\n props: {\n multiple?: boolean;\n value?: ValueOrState<\n Array<number | string | null> | number | string | null\n >;\n color?: ThemeColor;\n name?: string;\n } = {},\n): PartialElement {\n const { color = \"neutral\", multiple = false } = props;\n const state = toState(props.value ?? (multiple ? [] : null));\n\n const inputs: DomphyElement<\"div\"> = {\n div: (listener) => {\n const val = state.get(listener);\n const vals = Array.isArray(val) ? val : [val];\n return vals.map((v) => ({\n input: null,\n name: props.name,\n // Preserve a legitimate numeric 0 (and other falsy-but-valid values);\n // `v || \"\"` would drop them.\n value: v == null ? \"\" : String(v),\n }));\n },\n hidden: true,\n };\n\n const partial: PartialElement = {\n dataTone: \"shift-17\",\n _context: {\n select: {\n value: state,\n multiple,\n },\n },\n _onInit: (node) => {\n if (node.tagName !== \"div\") {\n console.warn(`\"selectList\" patch must use a div tag`);\n }\n node.children.insert(inputs);\n },\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n },\n };\n return partial;\n}\n\nexport { selectList };\n","import {\n hashString,\n type PartialElement,\n type StyleObject,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * A loading placeholder block with a pulsing opacity animation. Marked `aria-hidden`, themed\n * background/foreground, fixed height, slight rounding. No host-tag check; typically applied\n * to a block-level element such as a `div` or `span`.\n *\n * @param props.color - Theme color tone for the placeholder. Accepts a value or reactive state.\n * Defaults to `\"neutral\"`.\n * @example { div: null, $: [skeleton()] }\n */\nfunction skeleton(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n const keyframes = {\n \"0%,100%\": { opacity: 1 },\n \"50%\": { opacity: 0.4 },\n };\n const animationName = hashString(JSON.stringify(keyframes));\n return {\n ariaHidden: \"true\",\n dataTone: \"shift-2\",\n style: {\n fontSize: (listener) => themeSize(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n height: themeSpacing(6),\n display: \"block\",\n borderRadius: themeSpacing(1),\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n animation: `${animationName} 1.5s ease-in-out infinite`,\n [`@keyframes ${animationName}`]: keyframes,\n } as StyleObject,\n };\n}\n\nexport { skeleton };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Styles small/secondary text: one step smaller font size (`data-size=\"decrease-1\"`) with a\n * themed foreground color.\n *\n * @hostTag small\n * @param props.color - Theme color tone for the text. Accepts a value or reactive state.\n * Defaults to `\"neutral\"`.\n * @example { small: \"fine print\", $: [small()] }\n */\nfunction small(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"small\") {\n console.warn('\"small\" patch must use small tag');\n }\n },\n dataSize: \"decrease-1\",\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { small };\n","import type { PartialElement, StyleObject } from \"@domphy/core\";\nimport { hashString, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\nconst keyframes = { to: { transform: \"rotate(360deg)\" } };\nconst animationName = hashString(JSON.stringify(keyframes));\n\n/**\n * A circular loading spinner: a themed ring with a contrasting top border that rotates\n * continuously. Marked `role=\"status\"` with `aria-label=\"loading\"`.\n *\n * @hostTag span\n * @param props.color - Theme color tone for the ring/highlight. Accepts a value or reactive\n * state. Defaults to `\"neutral\"`.\n * @example { span: null, $: [spinner()] }\n */\nfunction spinner(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n role: \"status\",\n ariaLabel: \"loading\",\n _onInsert: (node) => {\n if (node.tagName !== \"span\") {\n console.warn(`\"spinner\" patch must use span tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n display: \"inline-block\",\n margin: 0,\n flexShrink: 0,\n width: themeSpacing(6),\n height: themeSpacing(6),\n borderRadius: \"50%\",\n border: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n borderTopColor: (listener) =>\n themeColor(listener, \"shift-9\", color.get(listener)),\n boxSizing: \"border-box\",\n padding: 0,\n animation: `${animationName} 0.7s linear infinite`,\n [`@keyframes ${animationName}`]: keyframes,\n } as StyleObject,\n };\n}\n\nexport { spinner };\n","import { merge, type PartialElement, toState } from \"@domphy/core\";\nimport { themeColor, themeSpacing } from \"@domphy/theme\";\n\n/**\n * Root of a resizable split layout. Lays out children as a flex row (horizontal) or column\n * (vertical) and provides a `splitter` context (`{ direction, size, min, max }`) consumed by\n * `splitterPanel` and `splitterHandle`. `size` is a reactive state holding the first panel's\n * percentage. No host-tag check; typically applied to a `div`.\n *\n * @param props.direction - Split orientation, `\"horizontal\"` | `\"vertical\"`. Defaults to `\"horizontal\"`.\n * @param props.defaultSize - Initial size (percentage) of the resizable panel. Defaults to `50`.\n * @param props.min - Minimum panel size (percentage). Defaults to `10`.\n * @param props.max - Maximum panel size (percentage). Defaults to `90`.\n * @example { div: [...], $: [splitter({ direction: \"vertical\" })] }\n */\nfunction splitter(\n props: {\n direction?: \"horizontal\" | \"vertical\";\n defaultSize?: number;\n min?: number;\n max?: number;\n } = {},\n): PartialElement {\n const {\n direction = \"horizontal\",\n defaultSize = 50,\n min = 10,\n max = 90,\n } = props;\n return {\n _onSchedule: (_node, element) => {\n merge(element, {\n _context: {\n splitter: {\n direction,\n size: toState(defaultSize),\n min,\n max,\n // Mutable bookkeeping (not reactive state) so splitterPanel can\n // tell the first panel from later ones — see its own comment.\n panelCount: 0,\n },\n },\n });\n },\n style: {\n display: \"flex\",\n flexDirection: direction === \"horizontal\" ? \"row\" : \"column\",\n overflow: \"hidden\",\n },\n };\n}\n\n/**\n * The resizable panel inside a `splitter`. Reads the `splitter` context and binds its\n * width (horizontal) or height (vertical) to the context `size` state, updating reactively as\n * the handle is dragged. Intended for exactly two panels either side of one `splitterHandle`:\n * the first `splitterPanel` mounted takes `size`%, and the second takes the complementary\n * `100 - size`% — so the pair always sums to the full width/height instead of both tracking\n * the same number (which would make them grow and shrink together instead of trading space).\n * Warns if used outside a `splitter`. Takes no props.\n *\n * @example { div: [...], $: [splitterPanel()] }\n */\nfunction splitterPanel(): PartialElement {\n return {\n _onMount: (node) => {\n const ctx = node.getContext(\"splitter\");\n if (!ctx) {\n console.warn(`\"splitterPanel\" patch must be used inside a \"splitter\"`);\n return;\n }\n const el = node.domElement as HTMLElement;\n const prop = ctx.direction === \"horizontal\" ? \"width\" : \"height\";\n const isFirst = ctx.panelCount++ === 0;\n\n const apply = (size: number) => {\n el.style[prop] = `${isFirst ? size : 100 - size}%`;\n };\n apply(ctx.size.get());\n el.style.flexShrink = \"0\";\n el.style.overflow = \"auto\";\n\n const release = ctx.size.addListener(apply);\n node.addHook(\"Remove\", release);\n },\n };\n}\n\n/**\n * The draggable divider inside a `splitter`. Reads the `splitter` context, shows the\n * appropriate resize cursor, and updates the context `size` state (clamped to `min`/`max`)\n * via mouse drag or keyboard: Arrow keys move by 1%, Home/End jump to min/max, hold Shift\n * for 10× step. Sets `role=\"separator\"`, `tabindex=\"0\"`, and `aria-value*` attributes.\n * Warns if used outside a `splitter`. Takes no props.\n *\n * @example { div: null, $: [splitterHandle()] }\n */\nfunction splitterHandle(): PartialElement {\n return {\n role: \"separator\",\n tabindex: 0,\n _onMount: (node) => {\n const ctx = node.getContext(\"splitter\");\n if (!ctx) {\n console.warn(`\"splitterHandle\" patch must be used inside a \"splitter\"`);\n return;\n }\n const handle = node.domElement as HTMLElement;\n const isHorizontal = ctx.direction === \"horizontal\";\n\n handle.style.cursor = isHorizontal ? \"col-resize\" : \"row-resize\";\n handle.setAttribute(\n \"aria-orientation\",\n isHorizontal ? \"vertical\" : \"horizontal\",\n );\n handle.setAttribute(\"aria-valuemin\", String(ctx.min));\n handle.setAttribute(\"aria-valuemax\", String(ctx.max));\n handle.setAttribute(\"aria-valuenow\", String(Math.round(ctx.size.get())));\n\n const releaseAriaValue = ctx.size.addListener((size: number) => {\n handle.setAttribute(\"aria-valuenow\", String(Math.round(size)));\n });\n\n const onKeydown = (e: KeyboardEvent) => {\n const step = e.shiftKey ? 10 : 1;\n let next: number | null = null;\n if (isHorizontal) {\n if (e.key === \"ArrowRight\")\n next = Math.min(ctx.size.get() + step, ctx.max);\n else if (e.key === \"ArrowLeft\")\n next = Math.max(ctx.size.get() - step, ctx.min);\n } else {\n if (e.key === \"ArrowDown\")\n next = Math.min(ctx.size.get() + step, ctx.max);\n else if (e.key === \"ArrowUp\")\n next = Math.max(ctx.size.get() - step, ctx.min);\n }\n if (e.key === \"Home\") next = ctx.min;\n else if (e.key === \"End\") next = ctx.max;\n if (next !== null) {\n e.preventDefault();\n ctx.size.set(next);\n }\n };\n\n let cancelDrag: (() => void) | null = null;\n\n const onMousedown = (e: MouseEvent) => {\n e.preventDefault();\n const container = handle.parentElement!;\n\n const onMousemove = (e: MouseEvent) => {\n const rect = container.getBoundingClientRect();\n const raw = isHorizontal\n ? ((e.clientX - rect.left) / rect.width) * 100\n : ((e.clientY - rect.top) / rect.height) * 100;\n ctx.size.set(Math.min(Math.max(raw, ctx.min), ctx.max));\n };\n\n const onMouseup = () => {\n document.removeEventListener(\"mousemove\", onMousemove);\n document.removeEventListener(\"mouseup\", onMouseup);\n cancelDrag = null;\n };\n\n cancelDrag = () => {\n document.removeEventListener(\"mousemove\", onMousemove);\n document.removeEventListener(\"mouseup\", onMouseup);\n cancelDrag = null;\n };\n\n document.addEventListener(\"mousemove\", onMousemove);\n document.addEventListener(\"mouseup\", onMouseup);\n };\n\n handle.addEventListener(\"keydown\", onKeydown);\n handle.addEventListener(\"mousedown\", onMousedown);\n node.addHook(\"Remove\", () => {\n cancelDrag?.();\n releaseAriaValue();\n handle.removeEventListener(\"keydown\", onKeydown);\n handle.removeEventListener(\"mousedown\", onMousedown);\n });\n },\n style: {\n flexShrink: 0,\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n backgroundColor: (listener) => themeColor(listener, \"shift-2\"),\n \"&:hover\": {\n backgroundColor: (listener) => themeColor(listener, \"shift-3\"),\n },\n \"&:focus-visible\": {\n outline: (listener) => `2px solid ${themeColor(listener, \"shift-6\")}`,\n outlineOffset: \"2px\",\n },\n \"&::after\": {\n content: '\"\"',\n // A small grip dot so the handle is visibly draggable. Without an\n // explicit size the pseudo-element collapses to 0x0 and is invisible.\n width: themeSpacing(1),\n height: themeSpacing(1),\n borderRadius: themeSpacing(999),\n backgroundColor: (listener) => themeColor(listener, \"shift-4\"),\n },\n },\n };\n}\n\nexport { splitter, splitterPanel, splitterHandle };\n","import type { PartialElement } from \"@domphy/core\";\nimport { themeDensity, themeSpacing } from \"@domphy/theme\";\n\ntype FlexAlign = \"flex-start\" | \"center\" | \"flex-end\" | \"stretch\" | \"baseline\";\n\n/**\n * A vertical flex column with spacing between children. The general-purpose\n * primitive for stacking blocks — form sections, panel content, card bodies —\n * instead of hand-rolling `display: flex; flexDirection: column; gap: ...`.\n * Styles the host only; apply to any block element.\n *\n * @param props.gap - Spacing multiplier for gap between children (default 3 = 0.75em at density 1).\n * @param props.align - Cross-axis alignment (`alignItems`). Unset by default (flex default, stretch).\n * @example { div: [{ h3: \"Title\" }, { p: \"Body\" }], $: [stack()] }\n * @example { div: [...], $: [stack({ gap: 2, align: \"center\" })] }\n */\nfunction stack(props: { gap?: number; align?: FlexAlign } = {}): PartialElement {\n const { gap = 3, align } = props;\n return {\n style: {\n display: \"flex\",\n flexDirection: \"column\",\n gap: (listener) => themeSpacing(themeDensity(listener) * gap),\n ...(align ? { alignItems: align } : {}),\n },\n };\n}\n\nexport { stack };\nexport type { FlexAlign };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/** One step entry. */\ntype StepItem = {\n /** Step label — plain string (auto-wrapped) or any DomphyElement. */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index. */\n key?: string | number;\n};\n\n/**\n * All-in-one step-progress indicator. Generates `<li>` step elements from the\n * `items` array. Apply to an `<ol>` or `<ul>` element.\n *\n * @param props.items - Step definitions `{ label, key? }`.\n * @param props.current - Zero-based index of the active step (value or State). Defaults to `0`.\n * @param props.direction - `\"horizontal\"` (default) or `\"vertical\"` layout.\n * @param props.color - Theme color for pending/track elements. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for active/completed elements. Defaults to `\"primary\"`.\n * @example\n * { ol: null, $: [steps({ current: 1, items: [\n * { label: \"Cart\" },\n * { label: \"Shipping\" },\n * { label: \"Payment\" },\n * ] })] }\n */\nfunction steps(\n props: {\n items: StepItem[];\n current?: ValueOrState<number>;\n direction?: \"horizontal\" | \"vertical\";\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const {\n items = [],\n direction = \"horizontal\",\n color = \"neutral\",\n accentColor = \"primary\",\n } = props;\n const current = toState(props.current ?? 0);\n\n return {\n // Expose state in context so stepItem() escape-hatch still works.\n _context: { steps: { current, direction, color, accentColor } },\n _onSchedule: (node, element) => {\n const stepEls: DomphyElement<\"li\">[] = items.map((item, index) => {\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n li: [labelEl],\n _key: item.key ?? index,\n dataStep: String(index + 1),\n dataStatus: (l: Listener) => {\n const cur = current.get(l);\n if (index < cur) return \"done\";\n if (index === cur) return \"active\";\n return \"pending\";\n },\n ariaCurrent: (l: Listener) =>\n current.get(l) === index ? \"step\" : undefined,\n style: {\n position: \"relative\",\n display: \"flex\",\n flexDirection: \"column\",\n alignItems: \"center\",\n gap: themeSpacing(1),\n flex: \"1\",\n fontSize: (l: Listener) => themeSize(l, \"decrease-1\"),\n textAlign: \"center\",\n \"&::before\": {\n content: \"attr(data-step)\",\n display: \"flex\",\n alignItems: \"center\",\n justifyContent: \"center\",\n width: themeSpacing(6),\n height: themeSpacing(6),\n borderRadius: themeSpacing(999),\n fontSize: (l: Listener) => themeSize(l, \"decrease-1\"),\n fontWeight: \"600\",\n flexShrink: \"0\",\n border: (l: Listener) =>\n `2px solid ${themeColor(l, \"border-strong\", color)}`,\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\"),\n color: (l: Listener) => themeColor(l, \"muted\"),\n transition:\n \"background-color 200ms ease, color 200ms ease, border-color 200ms ease\",\n zIndex: \"1\",\n },\n \"&:not(:first-child)::after\": {\n content: '\"\"',\n position: \"absolute\",\n top: themeSpacing(3),\n right: `calc(50% + ${themeSpacing(3)})`,\n left: `calc(-50% + ${themeSpacing(3)})`,\n height: \"2px\",\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n zIndex: \"0\",\n },\n \"&[data-status=active]::before\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-6\", accentColor),\n borderColor: (l: Listener) =>\n themeColor(l, \"shift-6\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-15\", accentColor),\n },\n \"&[data-status=done]::before\": {\n content: '\"✓\"',\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n borderColor: (l: Listener) => themeColor(l, \"border\", color),\n color: (l: Listener) => themeColor(l, \"text\", color),\n },\n \"&[data-status=done]:not(:first-child)::after\": {\n backgroundColor: (l: Listener) => themeColor(l, \"shift-3\", color),\n },\n \"&[data-status=active]:not(:first-child)::after\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-6\", accentColor),\n },\n \"&[data-status=pending]\": {\n color: (l: Listener) => themeColor(l, \"shift-7\"),\n },\n \"&[data-status=active]\": {\n color: (l: Listener) => themeColor(l, \"shift-10\"),\n fontWeight: \"600\",\n },\n \"&[data-status=done]\": {\n color: (l: Listener) => themeColor(l, \"muted\"),\n },\n },\n } as DomphyElement<\"li\">;\n });\n\n (element as any)[node.tagName] = stepEls;\n },\n style: {\n display: \"flex\",\n flexDirection: direction === \"vertical\" ? \"column\" : \"row\",\n alignItems: direction === \"vertical\" ? \"flex-start\" : \"center\",\n gap: themeSpacing(2),\n listStyle: \"none\",\n margin: \"0\",\n padding: \"0\",\n },\n };\n}\n\nexport { steps };\nexport type { StepItem };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Styles strongly emphasized (bold) text: inherited font size, `font-weight: 700`, and a\n * themed foreground color.\n *\n * @hostTag strong\n * @param props.color - Theme color tone for the text. Accepts a value or reactive state.\n * Defaults to `\"neutral\"`.\n * @example { strong: \"important\", $: [strong()] }\n */\nfunction strong(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"strong\") {\n console.warn(`\"strong\" primitive patch must use strong tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n fontWeight: 700,\n color: (listener) =>\n themeColor(listener, \"shift-11\", color.get(listener)),\n backgroundColor: (listener) => themeColor(listener),\n },\n };\n}\n\nexport { strong };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Renders subscript text (shrunk, baseline-lowered) for the host `<sub>` element.\n *\n * @hostTag sub\n * @param props.color - Theme color for the text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { sub: \"2\", $: [subscript()] }\n */\nfunction subscript(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"sub\") {\n console.warn(`\"subscript\" primitive patch must use sub tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n verticalAlign: \"sub\",\n lineHeight: 0,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { subscript };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport { type ThemeColor, themeColor, themeSize } from \"@domphy/theme\";\n\n/**\n * Renders superscript text (shrunk, baseline-raised) for the host `<sup>` element.\n *\n * @hostTag sup\n * @param props.color - Theme color for the text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { sup: \"2\", $: [superscript()] }\n */\nfunction superscript(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"sup\") {\n console.warn(`\"superscript\" primitive patch must use sup tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"decrease-1\"),\n verticalAlign: \"super\",\n lineHeight: 0,\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n },\n };\n}\n\nexport { superscript };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a data table (header/body/footer cells, caption, row hover, borders)\n * on the host `<table>` element.\n *\n * @hostTag table\n * @param props.color - Theme color applied across cells and text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { table: null, $: [table()] }\n */\nfunction table(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"table\") {\n console.warn(`\"table\" primitive patch must use table tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n width: \"100%\",\n borderCollapse: \"collapse\",\n \"& caption\": {\n captionSide: \"bottom\",\n },\n \"& th, & thead td\": {\n textAlign: \"left\",\n fontWeight: 500,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n color: (listener) =>\n themeColor(listener, \"shift-10\", color.get(listener)),\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n },\n \"& td\": {\n textAlign: \"left\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n boxShadow: (listener) =>\n `inset 0 1px 0 ${themeColor(listener, \"shift-3\", color.get(listener))}`,\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n },\n \"& tfoot th, & tfoot td\": {\n textAlign: \"left\",\n fontWeight: 500,\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n color: (l) => themeColor(l, \"shift-10\", color.get(l)),\n backgroundColor: (l) => themeColor(l, \"inherit\"),\n boxShadow: (l) =>\n `inset 0 -1px 0 ${themeColor(l, \"shift-4\", color.get(l))}`,\n },\n \"& tr\": {\n backgroundColor: (listener) => themeColor(listener, \"inherit\"),\n },\n\n // No !important needed: \".scope tbody tr:hover\" (two classes + two\n // elements) already out-specifies any row's own auto-scope class rule.\n \"& tbody tr:hover\": {\n backgroundColor: (listener) => themeColor(listener, \"hover\"),\n },\n },\n };\n}\n\nexport { table };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/** One tab entry: a trigger label and its panel content. */\ntype TabItem = {\n /** Tab button label — a plain string (auto-wrapped in span) or any DomphyElement. */\n label: string | DomphyElement;\n /** Panel content rendered when this tab is active. */\n content: DomphyElement;\n /** Stable identity key. Defaults to the item's zero-based index. */\n key?: string | number;\n};\n\n/**\n * All-in-one tabs patch. Generates a `[role=tablist]` button row and\n * `[role=tabpanel]` panels from the `items` array. Apply to any wrapper\n * element (`div`, `section`, …). No companion `tab()` / `tabPanel()` needed.\n *\n * To control the active tab programmatically, pass an external `State` as\n * `activeKey` and call `.set()` on it from outside.\n *\n * @param props.items - Tab definitions `{ label, content, key? }`.\n * @param props.activeKey - Initially active key (value or State). Defaults to the first item's key.\n * @param props.accentColor - Theme color for the active underline indicator. Defaults to `\"primary\"`.\n * @param props.color - Theme color for the resting underline. Defaults to `\"neutral\"`.\n * @example\n * { div: null, $: [tabs({ items: [\n * { label: \"Overview\", content: { p: \"Overview content\" } },\n * { label: \"API\", content: { p: \"API content\" } },\n * ] })] }\n */\nfunction tabs(\n props: {\n items: TabItem[];\n activeKey?: ValueOrState<string | number>;\n accentColor?: ThemeColor;\n color?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const { items = [], accentColor = \"primary\", color = \"neutral\" } = props;\n const activeKey = toState(props.activeKey ?? items[0]?.key ?? 0);\n\n return {\n _onSchedule: (node, element) => {\n const id = node.nodeId;\n\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? index;\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n button: [labelEl],\n _key: key,\n type: \"button\",\n role: \"tab\",\n id: `tab${id}${key}`,\n ariaControls: `panel${id}${key}`,\n ariaSelected: (l: Listener) => activeKey.get(l) === key,\n onClick: () => activeKey.set(key),\n onKeyDown: (e: Event) => {\n const k = (e as KeyboardEvent).key;\n if (![\"ArrowLeft\", \"ArrowRight\", \"Home\", \"End\"].includes(k)) return;\n e.preventDefault();\n const keys = items.map((it, i) => it.key ?? i);\n const idx = keys.indexOf(key);\n let next = idx;\n if (k === \"ArrowRight\") next = (idx + 1) % keys.length;\n else if (k === \"ArrowLeft\")\n next = (idx - 1 + keys.length) % keys.length;\n else if (k === \"Home\") next = 0;\n else if (k === \"End\") next = keys.length - 1;\n activeKey.set(keys[next]);\n },\n style: {\n cursor: \"pointer\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: (l: Listener) => themeSpacing(6 + themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 4),\n border: \"none\",\n outline: \"none\",\n color: (l: Listener) => themeColor(l, \"text\"),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\"),\n boxShadow: (l: Listener) =>\n `inset 0 -${themeSpacing(0.5)} 0 0 ${themeColor(l, \"shift-1\", color)}`,\n transition: \"box-shadow 140ms ease, color 140ms ease\",\n \"&:hover:not([disabled])\": {\n boxShadow: (l: Listener) =>\n `inset 0 -${themeSpacing(0.5)} 0 0 ${themeColor(l, \"shift-2\", color)}`,\n },\n \"&[aria-selected=true]:not([disabled])\": {\n boxShadow: (l: Listener) =>\n `inset 0 -${themeSpacing(0.5)} 0 0 ${themeColor(l, \"shift-6\", accentColor)}`,\n },\n \"&:focus-visible\": {\n boxShadow: (l: Listener) => focusRing(l, accentColor),\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n const tablist: DomphyElement<\"div\"> = {\n div: buttons,\n role: \"tablist\",\n ariaOrientation: \"horizontal\",\n style: { display: \"flex\" },\n } as DomphyElement<\"div\">;\n\n const panels: DomphyElement<\"div\">[] = items.map((item, index) => {\n const key = item.key ?? index;\n return {\n div: [item.content],\n _key: key,\n role: \"tabpanel\",\n id: `panel${id}${key}`,\n ariaLabelledby: `tab${id}${key}`,\n hidden: (l: Listener) => activeKey.get(l) !== key,\n style: {\n paddingBlock: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n paddingInline: (l: Listener) => themeSpacing(themeDensity(l) * 2),\n },\n } as DomphyElement<\"div\">;\n });\n\n // Inject generated structure into the host element's children slot.\n (element as any)[node.tagName] = [tablist, ...panels];\n },\n };\n}\n\nexport { tabs };\nexport type { TabItem };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/**\n * Styles a multi-line text input (border, focus/hover/invalid/disabled states)\n * on the host `<textarea>` element, with optional auto-resize to content.\n *\n * @hostTag textarea\n * @param props.color - Theme color for the border and text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for hover/focus outline. Optional, accepts a value or state. Defaults to `\"primary\"`.\n * @param props.autoResize - When true, grows the textarea height to fit its content on input. Optional. Defaults to `false`.\n * @example { textarea: null, $: [textarea({ autoResize: true })] }\n */\nfunction textarea(\n props: {\n color?: ValueOrState<ThemeColor>;\n accentColor?: ValueOrState<ThemeColor>;\n autoResize?: boolean;\n } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n const accentColor = toState(props.accentColor ?? \"primary\", \"accentColor\");\n const { autoResize = false } = props;\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"textarea\") {\n console.warn(`\"textarea\" primitive patch must use textarea tag`);\n }\n },\n _onMount: (node) => {\n if (autoResize) {\n const el = node.domElement as HTMLTextAreaElement;\n el.style.overflow = \"hidden\";\n const resize = () => {\n el.style.height = \"auto\";\n el.style.height = `${el.scrollHeight}px`;\n };\n el.addEventListener(\"input\", resize);\n resize();\n node.addHook(\"Remove\", () => el.removeEventListener(\"input\", resize));\n }\n },\n style: {\n fontFamily: \"inherit\",\n lineHeight: \"inherit\",\n resize: \"vertical\",\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n border: \"none\",\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n outlineOffset: \"-1px\",\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", color.get(listener))}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"inherit\", color.get(listener)),\n transition: \"outline-color 140ms ease, box-shadow 140ms ease\",\n \"&::placeholder\": {\n color: (listener) => themeColor(listener, \"shift-7\"),\n },\n \"&:hover:not([disabled]):not([aria-busy=true])\": {\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"shift-5\", accentColor.get(listener))}`,\n },\n \"&:focus-visible\": {\n boxShadow: (listener) => focusRing(listener, accentColor.get(listener)),\n },\n \"&:invalid\": {\n outline: (listener) =>\n `${themeSpacing(0.5)} solid ${themeColor(listener, \"shift-5\", \"error\")}`,\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n color: (listener) => themeColor(listener, \"muted\", \"neutral\"),\n outline: (listener) =>\n `1px solid ${themeColor(listener, \"border-strong\", \"neutral\")}`,\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-2\", \"neutral\"),\n },\n },\n };\n}\n\nexport { textarea };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Container for a vertical timeline. Sets list reset styles. Apply to `<ol>` or `<ul>`.\n *\n * @example { ol: [...], $: [timeline()] }\n */\nfunction timeline(): PartialElement {\n return {\n style: {\n listStyle: \"none\",\n margin: 0,\n padding: 0,\n display: \"flex\",\n flexDirection: \"column\",\n },\n };\n}\n\n/**\n * A single event row in a `timeline`. Uses a 2-column grid: the left column holds\n * a dot (`::before`) and optional connector line (`::after`); the right column holds\n * the user's content. Apply to `<li>`.\n *\n * @param props.active - Full-opacity dot (accent color). `ValueOrState<boolean>`, defaults to `false`.\n * @param props.last - Suppress the vertical connector below this item. `boolean`, defaults to `false`.\n * @param props.color - Dot/connector color tone. `ThemeColor`, defaults to `\"neutral\"`.\n * @param props.accentColor - Active dot color tone. `ThemeColor`, defaults to `\"primary\"`.\n * @example { li: [{ b: \"2024\" }, { p: \"Event\" }], $: [timelineItem({ active: true })] }\n */\nfunction timelineItem(\n props: {\n active?: ValueOrState<boolean>;\n last?: boolean;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = {},\n): PartialElement {\n const { last = false } = props;\n const color = props.color ?? \"neutral\";\n const accentColor = props.accentColor ?? \"primary\";\n const activeState = toState(props.active ?? false);\n\n return {\n style: {\n display: \"grid\",\n gridTemplateColumns: \"2rem 1fr\",\n columnGap: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingBottom: (listener) =>\n last ? \"0\" : themeSpacing(themeDensity(listener) * 4),\n position: \"relative\",\n\n // Dot\n \"&::before\": {\n content: '\"\"',\n display: \"block\",\n width: \"0.75rem\",\n height: \"0.75rem\",\n borderRadius: \"50%\",\n justifySelf: \"center\",\n marginTop: \"0.25em\",\n transition: \"background-color 200ms ease, opacity 200ms ease\",\n backgroundColor: (listener) =>\n themeColor(\n listener,\n \"shift-8\",\n activeState.get(listener) ? accentColor : color,\n ),\n opacity: (listener) => (activeState.get(listener) ? \"1\" : \"0.4\"),\n },\n\n // Vertical connector to the next item\n ...(last\n ? {}\n : {\n \"&::after\": {\n content: '\"\"',\n position: \"absolute\",\n left: \"calc(1rem - 1px)\",\n top: \"1.25rem\",\n bottom: (listener) =>\n `-${themeSpacing(themeDensity(listener) * 4)}`,\n width: \"2px\",\n backgroundColor: (listener) =>\n themeColor(listener, \"shift-3\", color),\n },\n }),\n },\n };\n}\n\nexport { timeline, timelineItem };\n","import type { DomphyElement, ElementNode, PartialElement } from \"@domphy/core\";\nimport { toState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\n\ntype ToastPosition =\n | \"top-left\"\n | \"top-center\"\n | \"top-right\"\n | \"bottom-left\"\n | \"bottom-center\"\n | \"bottom-right\";\n\n/**\n * Renders a transient notification surface as a fixed-position overlay (portaled\n * into a corner stack), animating in on mount and out before removal. No host\n * tag check; typically applied to a `<div>`.\n *\n * @param props.position - Corner of the screen for the toast stack. Optional, one of `\"top-left\" | \"top-center\" | \"top-right\" | \"bottom-left\" | \"bottom-center\" | \"bottom-right\"`. Defaults to `\"top-center\"`.\n * @param props.color - Theme color for the toast surface. Optional. Defaults to `\"neutral\"`.\n * @example { div: \"Saved!\", $: [toast({ position: \"top-right\" })] }\n */\nfunction toast(\n props: { position?: ToastPosition; color?: ThemeColor } = {},\n): PartialElement {\n const { position = \"top-center\", color = \"neutral\" } = props;\n const state = toState(false);\n\n const isTop = position.startsWith(\"top\");\n const isCenter = position.endsWith(\"center\");\n const isRight = position.endsWith(\"right\");\n\n const overlayEle: DomphyElement<\"div\"> = {\n div: [],\n id: `domphy-toast-${position}`,\n style: {\n position: \"fixed\",\n display: \"flex\",\n flexDirection: isTop ? \"column\" : \"column-reverse\",\n alignItems: isCenter ? \"center\" : isRight ? \"end\" : \"start\",\n inset: 0,\n gap: themeSpacing(4),\n zIndex: 30,\n padding: themeSpacing(6),\n pointerEvents: \"none\",\n },\n };\n\n return {\n _portal: (rootNode) => {\n let overlay = rootNode.domElement!.querySelector(\n `#domphy-toast-${position}`,\n );\n if (!overlay) {\n const overlayNode = rootNode.children!.insert(\n overlayEle,\n ) as ElementNode;\n overlay = overlayNode.domElement!;\n }\n return overlay;\n },\n role: \"status\",\n ariaAtomic: \"true\",\n // Toast is rendered as an overlay surface, so it uses the inverted branch.\n dataTone: \"shift-17\",\n style: {\n minWidth: themeSpacing(32),\n pointerEvents: \"auto\",\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 2),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 4),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 2),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n color: (listener) => themeColor(listener, \"text\", color),\n backgroundColor: (listener) => themeColor(listener, \"inherit\", color),\n boxShadow: elevation(\"medium\"),\n opacity: (listener) => Number(state.get(listener)),\n transform: (listener) =>\n state.get(listener)\n ? \"translateY(0)\"\n : isTop\n ? \"translateY(-100%)\"\n : \"translateY(100%)\",\n transition: \"opacity 300ms ease, transform 300ms ease\",\n },\n _onMount: () => requestAnimationFrame(() => state.set(true)),\n _onBeforeRemove: (node, done) => {\n let finished = false;\n let timer: ReturnType<typeof setTimeout> | null = null;\n const finish = () => {\n if (finished) return;\n finished = true;\n if (timer) {\n clearTimeout(timer);\n timer = null;\n }\n node.domElement!.removeEventListener(\"transitionend\", onEnd);\n done();\n };\n const onEnd = (e: Event) => {\n if ((e as TransitionEvent).propertyName === \"transform\") finish();\n };\n node.domElement!.addEventListener(\"transitionend\", onEnd);\n // Fallback: if transitionend never fires (reduced-motion, display:none,\n // early detach), unblock removal after the transition duration + buffer.\n timer = setTimeout(finish, 350);\n // If the node is detached before the exit animation settles, clear the\n // pending fallback timer and the transitionend listener so they cannot\n // fire on a removed node.\n node.addHook(\"Remove\", () => {\n if (timer) {\n clearTimeout(timer);\n timer = null;\n }\n node.domElement?.removeEventListener(\"transitionend\", onEnd);\n });\n state.set(false);\n },\n };\n}\n\nexport { toast };\n","import {\n type DomphyElement,\n type Listener,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { focusRing } from \"../utils/focusRing.js\";\n\n/** One item inside a toggle group. */\ntype ToggleItem = {\n /** Button label — plain string (auto-wrapped) or any DomphyElement. */\n label: string | DomphyElement;\n /** Stable key. Defaults to the item's zero-based index as a string. */\n key?: string;\n};\n\n/**\n * All-in-one toggle group — single or multi-select button group. Generates\n * `<button>` toggle elements from the `items` array. Apply to any wrapper element.\n *\n * @param props.items - Item definitions `{ label, key? }`.\n * @param props.value - Selected key(s) (value or State). Defaults to `[]` (multiple) or `\"\"` (single).\n * @param props.multiple - Allow multiple items selected at once. Defaults to `false`.\n * @param props.color - Theme color for the group background/border. Defaults to `\"neutral\"`.\n * @param props.accentColor - Theme color for the pressed state. Defaults to `\"primary\"`.\n * @example\n * { div: null, $: [toggleGroup({ multiple: true, items: [\n * { label: \"Bold\", key: \"bold\" },\n * { label: \"Italic\", key: \"italic\" },\n * ] })] }\n */\nfunction toggleGroup(\n props: {\n items: ToggleItem[];\n value?: ValueOrState<string | string[]>;\n multiple?: boolean;\n color?: ThemeColor;\n accentColor?: ThemeColor;\n } = { items: [] },\n): PartialElement {\n const {\n items = [],\n multiple = false,\n color = \"neutral\",\n accentColor = \"primary\",\n } = props;\n const value = toState(props.value ?? (multiple ? [] : \"\"));\n\n return {\n role: \"group\",\n // Expose value + multiple in context so toggle() escape-hatch still works.\n _context: { toggleGroup: { value, multiple } },\n _onSchedule: (node, element) => {\n const buttons: DomphyElement<\"button\">[] = items.map((item, index) => {\n const key = item.key ?? String(index);\n const labelEl: DomphyElement =\n typeof item.label === \"string\"\n ? ({ span: item.label } as DomphyElement<\"span\">)\n : item.label;\n\n return {\n button: [labelEl],\n _key: key,\n type: \"button\",\n role: \"button\",\n ariaPressed: (l: Listener) => {\n const val = value.get(l);\n return Array.isArray(val) ? val.includes(key) : val === key;\n },\n onClick: () => {\n const val = value.get();\n if (multiple) {\n const arr = Array.isArray(val) ? [...val] : [];\n value.set(\n arr.includes(key)\n ? arr.filter((v) => v !== key)\n : [...arr, key],\n );\n } else {\n value.set(val === key ? \"\" : key);\n }\n },\n style: {\n cursor: \"pointer\",\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n height: themeSpacing(6),\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(2),\n border: \"none\",\n borderRadius: themeSpacing(1.5),\n color: (l: Listener) => themeColor(l, \"text\", color),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n transition:\n \"background-color 140ms ease, color 140ms ease, box-shadow 140ms ease\",\n \"&:hover:not([disabled])\": {\n backgroundColor: (l: Listener) => themeColor(l, \"hover\", color),\n },\n \"&[aria-pressed=true]\": {\n backgroundColor: (l: Listener) =>\n themeColor(l, \"shift-3\", accentColor),\n color: (l: Listener) => themeColor(l, \"shift-12\", accentColor),\n },\n \"&:focus-visible\": {\n boxShadow: (l: Listener) => focusRing(l, accentColor),\n },\n \"&[disabled]\": {\n opacity: 0.7,\n cursor: \"not-allowed\",\n },\n },\n } as DomphyElement<\"button\">;\n });\n\n (element as any)[node.tagName] = buttons;\n },\n style: {\n display: \"flex\",\n paddingBlock: themeSpacing(1),\n paddingInline: themeSpacing(1),\n gap: themeSpacing(1),\n borderRadius: themeSpacing(2),\n fontSize: (l: Listener) => themeSize(l, \"inherit\"),\n backgroundColor: (l: Listener) => themeColor(l, \"inherit\", color),\n outline: (l: Listener) => `1px solid ${themeColor(l, \"border\", color)}`,\n outlineOffset: \"-1px\",\n },\n };\n}\n\nexport { toggleGroup };\nexport type { ToggleItem };\n","import type { DomphyElement, PartialElement } from \"@domphy/core\";\nimport { row } from \"./row.js\";\n\n/**\n * A horizontal flex row with vertically centered items. Useful for headers,\n * toolbars, navigation bars, and action strips. A semantic alias of `row()`\n * at its default alignment — reach for `row()` directly for `justify`/`wrap`/\n * `align` beyond this shape.\n *\n * @param props.gap - Spacing multiplier for gap between items (default 4 = 1em).\n * @example { header: [...], $: [toolbar()] }\n * @example { nav: [...], $: [toolbar({ gap: 3 })] }\n */\nfunction toolbar(props: { gap?: number } = {}): PartialElement {\n return row({ gap: props.gap });\n}\n\n/**\n * A flex spacer that expands to fill available space in a toolbar, pushing\n * subsequent items to the far end.\n *\n * @example { header: [logo, toolbarSpacer(), nav, actions], $: [toolbar()] }\n */\nfunction toolbarSpacer(): DomphyElement {\n return { div: null, style: { flex: \"1 1 0\" } };\n}\n\nexport { toolbar, toolbarSpacer };\n","import {\n type DomphyElement,\n merge,\n type PartialElement,\n toState,\n type ValueOrState,\n} from \"@domphy/core\";\nimport type { Placement } from \"@domphy/floating\";\nimport {\n themeColor,\n themeDensity,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\nimport { elevation } from \"../utils/elevation.js\";\nimport { createFloating } from \"../utils/floating.js\";\nimport { popoverArrow } from \"./popoverArrow.js\";\n\n/**\n * Attaches a floating tooltip to the host element, shown on hover/focus and\n * hidden on leave/blur/Escape. Returns the anchor (trigger) partial; the tooltip\n * surface is positioned via the floating utility and linked with\n * `aria-describedby`. No host tag check; applied to the trigger element.\n *\n * @param props.open - Controlled open state. Optional, accepts a value or state. Defaults to `false`.\n * @param props.placement - Floating placement relative to the trigger. Optional, accepts a value or state (`Placement`). Defaults to `\"top\"`.\n * @param props.content - Tooltip text content. Optional, accepts a value or state (string only). Defaults to `\"Tooltip Content\"`.\n * @example { button: \"Hover me\", $: [tooltip({ content: \"Help text\" })] }\n */\nfunction tooltip(\n props: {\n open?: ValueOrState<boolean>;\n placement?: ValueOrState<Placement>;\n content?: ValueOrState<string>;\n } = {},\n): PartialElement {\n const {\n open = false,\n placement = \"top\",\n content = \"Tooltip Content\",\n } = props;\n\n const placeState = toState(placement);\n const contentState = toState(content);\n\n // Pre-generate ID so the trigger can reference it via aria-describedby\n // before the tooltip content element is first inserted into the DOM.\n const tooltipId = `domphy-tt-${Math.random().toString(36).slice(2, 9)}`;\n\n const contentElement: DomphyElement<\"span\"> = {\n span: (listener) => contentState.get(listener),\n id: tooltipId,\n };\n\n const { show, hide, anchorPartial } = createFloating({\n kind: \"tooltip\",\n open,\n placement: placeState,\n content: contentElement,\n });\n\n const tooltipPartial: PartialElement = {\n role: \"tooltip\",\n dataSize: \"decrease-1\",\n dataTone: \"shift-17\",\n style: {\n paddingBlock: (listener) => themeSpacing(themeDensity(listener) * 1),\n paddingInline: (listener) => themeSpacing(themeDensity(listener) * 3),\n borderRadius: (listener) => themeSpacing(themeDensity(listener) * 1.5),\n color: (listener) => themeColor(listener, \"text\"),\n backgroundColor: (listener) => themeColor(listener),\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n boxShadow: elevation(\"low\"),\n },\n $: [popoverArrow({ placement: placeState, bordered: false })],\n };\n contentElement.$ ||= [];\n contentElement.$.push(tooltipPartial);\n\n const triggerPartial: PartialElement = {\n ariaDescribedby: tooltipId,\n onMouseEnter: (_e, node) => show(node),\n onMouseLeave: (_e, node) => hide(node),\n onFocus: (_e, node) => show(node),\n onBlur: (_e, node) => hide(node),\n onKeyDown: (e, node) => (e as KeyboardEvent).key === \"Escape\" && hide(node),\n };\n\n merge(anchorPartial, triggerPartial);\n\n return anchorPartial;\n}\n\nexport { tooltip };\n","import { ElementNode, type PartialElement } from \"@domphy/core\";\n\ntype RectMap = Map<string, DOMRect>;\n\nfunction getItemId(node: ElementNode, index: number): string {\n if (node.key !== undefined && node.key !== null) {\n return String(node.key);\n }\n return `index-${index}`;\n}\n\n/**\n * Animates child reordering using the FLIP technique: records each child's\n * position before an update and smoothly transitions it from its old to new\n * position afterward. No host tag check; applied to the list container.\n *\n * @param props.duration - Transition duration in milliseconds. Optional. Defaults to `300`.\n * @param props.delay - Transition delay in milliseconds. Optional. Defaults to `0`.\n * @example { ul: null, $: [transitionGroup({ duration: 300 })] }\n */\nfunction transitionGroup(\n props: { duration?: number; delay?: number } = {},\n): PartialElement {\n const { duration = 300, delay = 0 } = props;\n\n let previousRects: RectMap = new Map();\n // Cancels any in-flight animation for a given DOM element before starting a new one.\n const cancelMap = new Map<HTMLElement, () => void>();\n // Pending fallback timers and queued rAF callbacks, tracked so a removal of\n // the container mid-animation can clear them instead of firing on a detached node.\n const pendingTimers = new Set<ReturnType<typeof setTimeout>>();\n const pendingFrames = new Set<number>();\n\n return {\n _onMount: (node) => {\n node.addHook(\"Remove\", () => {\n // Stop every in-flight animation: removes transitionend listeners.\n for (const cancel of Array.from(cancelMap.values())) cancel();\n cancelMap.clear();\n // Clear queued fallback timers.\n for (const timer of pendingTimers) clearTimeout(timer);\n pendingTimers.clear();\n // Cancel queued animation frames.\n for (const frame of pendingFrames) cancelAnimationFrame(frame);\n pendingFrames.clear();\n });\n },\n _onBeforeUpdate: (node) => {\n previousRects = new Map();\n node.children.items.forEach((item, index) => {\n if (!(item instanceof ElementNode)) return;\n const dom = item.domElement as HTMLElement | undefined;\n if (!dom) return;\n previousRects.set(getItemId(item, index), dom.getBoundingClientRect());\n });\n },\n _onUpdate: (node) => {\n node.children.items.forEach((item, index) => {\n if (!(item instanceof ElementNode)) return;\n const dom = item.domElement as HTMLElement | undefined;\n if (!dom) return;\n\n const key = getItemId(item, index);\n const prev = previousRects.get(key);\n if (!prev) return;\n\n const next = dom.getBoundingClientRect();\n const deltaX = prev.left - next.left;\n const deltaY = prev.top - next.top;\n if (Math.abs(deltaX) < 0.5 && Math.abs(deltaY) < 0.5) return;\n\n // Cancel any in-flight animation on this element before starting a new one.\n cancelMap.get(dom)?.();\n\n dom.style.transition = \"none\";\n dom.style.transform = `translate(${deltaX}px, ${deltaY}px)`;\n dom.getBoundingClientRect();\n\n const frame = requestAnimationFrame(() => {\n pendingFrames.delete(frame);\n dom.style.transition = `transform ${duration}ms ease ${delay}ms`;\n dom.style.transform = \"translate(0px, 0px)\";\n });\n pendingFrames.add(frame);\n\n let cancelled = false;\n let timer: ReturnType<typeof setTimeout> | null = null;\n const finish = () => {\n if (cancelled) return;\n cancelled = true;\n if (timer) {\n pendingTimers.delete(timer);\n timer = null;\n }\n cancelMap.delete(dom);\n dom.removeEventListener(\"transitionend\", onEnd);\n dom.style.transition = \"\";\n dom.style.transform = \"\";\n };\n\n const onEnd = (event: Event) => {\n if ((event as TransitionEvent).propertyName === \"transform\") finish();\n };\n\n cancelMap.set(dom, () => {\n cancelled = true;\n if (timer) {\n clearTimeout(timer);\n pendingTimers.delete(timer);\n timer = null;\n }\n cancelMap.delete(dom);\n dom.removeEventListener(\"transitionend\", onEnd);\n });\n\n dom.addEventListener(\"transitionend\", onEnd);\n timer = setTimeout(finish, duration + delay + 34);\n pendingTimers.add(timer);\n });\n previousRects.clear();\n },\n };\n}\n\nexport { transitionGroup };\n","import { type PartialElement, toState, type ValueOrState } from \"@domphy/core\";\nimport {\n type ThemeColor,\n themeColor,\n themeSize,\n themeSpacing,\n} from \"@domphy/theme\";\n\n/**\n * Styles a bulleted list (disc markers, reset margins, themed text) on the host\n * `<ul>` element.\n *\n * @hostTag ul\n * @param props.color - Theme color for the list text. Optional, accepts a value or state. Defaults to `\"neutral\"`.\n * @example { ul: null, $: [unorderedList()] }\n */\nfunction unorderedList(\n props: { color?: ValueOrState<ThemeColor> } = {},\n): PartialElement {\n const color = toState(props.color ?? \"neutral\", \"color\");\n\n return {\n _onInsert: (node) => {\n if (node.tagName !== \"ul\") {\n console.warn(`\"unorderedList\" primitive patch must use ul tag`);\n }\n },\n style: {\n fontSize: (listener) => themeSize(listener, \"inherit\"),\n backgroundColor: (listener) => themeColor(listener),\n color: (listener) => themeColor(listener, \"text\", color.get(listener)),\n marginTop: 0,\n marginBottom: 0,\n paddingLeft: themeSpacing(3),\n listStyleType: \"disc\",\n listStylePosition: \"outside\",\n },\n };\n}\n\nexport { unorderedList };\n"],"mappings":"kzBAAA,IAAAA,GAAA,GAAAC,GAAAD,GAAA,UAAAE,GAAA,UAAAA,GAAA,OAAAC,s8BCAaC,GAAoB,CAC/B,kBACA,QACA,YACA,WACA,UACA,UACA,kBACA,WACA,UACA,UACA,QACA,WACA,iBACA,SACA,QACA,YACA,OACA,WACA,QACA,SACA,UACA,aACA,OACA,cACA,WACA,WACA,WACA,SACA,WACA,WACA,YACA,gBACA,QACA,aACA,QACA,WACA,WACA,SACA,sBACF,ECxCaC,GAA4B,CACvC,UACA,sBACA,oBACA,gBACA,eACA,cACA,YACA,YACA,eACA,cACA,cACA,OACA,OACA,sBACA,mBACA,eACA,cACA,iBACA,mBACA,gBACA,mBACA,YACA,gBACA,aACA,mBACA,mBACA,eACA,4BACA,YACF,ECjBaC,GAA6C,CAExD,QAAS,MAGT,gBAAiB,kBACjB,UAAW,YACX,SAAU,WACV,gBAAiB,kBACjB,eAAgB,iBAChB,MAAO,QACP,UAAW,YACX,OAAQ,SACR,QAAS,UACT,WAAY,aACZ,YAAa,cACb,UAAW,YACX,cAAe,gBACf,WAAY,aACZ,SAAU,WACV,qBAAsB,uBAGtB,eAAgB,iBAGhB,UAAW,YACX,aAAc,eACd,UAAW,YACX,OAAQ,SACR,SAAU,WACV,QAAS,UACT,SAAU,WACV,SAAU,WACV,mBAAoB,qBAGpB,QAAS,UACT,SAAU,WACV,YAAa,cACb,MAAO,QACP,QAAS,UACT,MAAO,QACP,WAAY,aACZ,YAAa,cACb,WAAY,aACZ,WAAY,aACZ,cAAe,gBACf,oBAAqB,sBACrB,oBAAqB,sBACrB,eAAgB,iBAChB,YAAa,cACb,SAAU,WACV,aAAc,eACd,YAAa,cACb,eAAgB,iBAChB,OAAQ,SACR,OAAQ,SACR,cAAe,gBACf,OAAQ,SACR,QAAS,UACT,OAAQ,SACR,OAAQ,SACR,QAAS,UACT,WAAY,aACZ,YAAa,cACb,QAAS,UACT,SAAU,WACV,SAAU,WACV,UAAW,YACX,mBAAoB,qBACpB,yBAA0B,2BAC1B,eAAgB,iBAChB,QAAS,UACT,QAAS,UACT,OAAQ,SACR,OAAQ,SACR,QAAS,UACT,UAAW,YACX,UAAW,YACX,aAAc,eACd,QAAS,UACT,SAAU,UACZ,EChGaC,GAAW,CACtB,IACA,OACA,UACA,UACA,QACA,QACA,IACA,OACA,aACA,KACA,SACA,SACA,UACA,OACA,OACA,MACA,WACA,OACA,WACA,KACA,MACA,UACA,MACA,SACA,MACA,KACA,KACA,KACA,WACA,aACA,SACA,SACA,OACA,KACA,KACA,KACA,KACA,KACA,KACA,SACA,SACA,IACA,SACA,MACA,QACA,MACA,MACA,QACA,SACA,KACA,OACA,MACA,OACA,OACA,QACA,MACA,WACA,SACA,KACA,WACA,SACA,SACA,IACA,QACA,UACA,MACA,WACA,IACA,KACA,KACA,OACA,IACA,OACA,UACA,SACA,OACA,QACA,SACA,OACA,SACA,MACA,UACA,MACA,QACA,QACA,KACA,WACA,WACA,QACA,KACA,QACA,OACA,QACA,KACA,QACA,IACA,KACA,MACA,QACA,MACA,MACA,MACA,OACA,OACA,SACA,OACA,QACA,KACA,UACA,gBACA,mBACA,SACA,WACA,SACA,OACA,OACA,UACA,UACA,gBACA,sBACA,cACA,mBACA,oBACA,oBACA,iBACA,eACA,UACA,UACA,UACA,UACA,UACA,iBACA,UACA,UACA,cACA,eACA,WACA,eACA,qBACA,cACA,SACA,eACA,SACA,gBACA,IACA,QACA,OACA,iBACA,SACA,OACA,WACA,QACA,OACA,UACA,UACA,WACA,WACA,iBACA,OACA,MACA,aACA,OACA,MACA,SACA,SACA,SACA,OACA,WACA,QACA,MACA,MACF,EC3KaC,GAAsC,CACjD,UAAW,CAAC,SAAU,IAAI,EAC1B,WAAY,CAAC,SAAU,IAAI,EAC3B,UAAW,CAAC,QAAQ,EACpB,WAAY,CAAC,SAAU,IAAI,EAC3B,cAAe,CAAC,SAAU,IAAI,EAC9B,SAAU,CAAC,SAAU,IAAI,EACzB,eAAgB,CAAC,SAAU,IAAI,EAC/B,WAAY,CAAC,SAAU,IAAI,EAC3B,UAAW,CAAC,SAAU,IAAI,EAC1B,MAAO,CAAC,SAAU,IAAI,EACtB,SAAU,CAAC,SAAU,IAAI,EACzB,WAAY,CAAC,SAAU,IAAI,EAC3B,UAAW,CAAC,SAAU,IAAI,EAC1B,QAAS,CAAC,QAAQ,EAClB,YAAa,CAAC,QAAQ,EACtB,UAAW,CAAC,QAAQ,EACpB,WAAY,CAAC,QAAQ,EACrB,YAAa,CAAC,QAAQ,EACtB,UAAW,CAAC,QAAQ,EACpB,WAAY,CAAC,SAAU,KAAK,EAC5B,OAAQ,CAAC,QAAQ,EACjB,eAAgB,CAAC,QAAQ,EACzB,SAAU,CAAC,QAAQ,EACnB,KAAM,CAAC,QAAQ,EACf,UAAW,CAAC,QAAQ,EACpB,eAAgB,CAAC,SAAU,IAAI,EAC/B,QAAS,CAAC,SAAU,IAAI,EACxB,YAAa,CAAC,SAAU,IAAI,EAC5B,oBAAqB,CAAC,IAAI,EAC1B,iBAAkB,CAAC,IAAI,EACvB,gBAAiB,CAAC,IAAI,EACtB,aAAc,CAAC,IAAI,EACnB,WAAY,CAAC,IAAI,EACjB,QAAS,CAAC,IAAI,EACd,kBAAmB,CAAC,QAAQ,EAC5B,gBAAiB,CAAC,QAAQ,EAC1B,mBAAoB,CAAC,QAAQ,EAC7B,iBAAkB,CAAC,QAAQ,EAC3B,cAAe,CAAC,QAAQ,EACxB,cAAe,CAAC,QAAQ,EACxB,aAAc,CAAC,QAAQ,EACvB,aAAc,CAAC,QAAQ,EACvB,WAAY,CAAC,QAAQ,EACrB,UAAW,CAAC,QAAQ,EACpB,QAAS,CAAC,KAAK,EACf,mBAAoB,CAAC,SAAU,IAAI,EACnC,YAAa,CAAC,IAAI,EAClB,OAAQ,CAAC,QAAQ,EACjB,iBAAkB,CAAC,QAAQ,EAC3B,eAAgB,CAAC,QAAQ,EACzB,mBAAoB,CAAC,QAAQ,EAC7B,kBAAmB,CAAC,QAAQ,CAC9B,ECtDaC,GAAU,CACrB,MACA,SACA,OACA,OACA,UACA,OACA,WACA,UACA,IACA,OACA,MACA,SACA,iBACA,iBACA,OACA,WACA,OACA,SACA,OACA,QACA,WACA,QACA,UACA,SACA,UACA,mBACA,gBACA,iBACA,cACA,gBACA,UACA,cACA,WACA,UACA,UACA,eACA,oBACA,sBACA,UACA,UACA,UACA,UACA,eACF,EC5CaC,GAAW,CACtB,OACA,OACA,KACA,MACA,QACA,KACA,MACA,QACA,OACA,OACA,SACA,QACA,KACF,ECVMC,GAAwB,CAAC,EAExB,SAASC,GAAUC,EAAsC,CAC9D,OAAO,OAAOF,GAASE,CAAO,CAChC,CAEO,SAASC,IAAoC,CAClD,OAAOH,EACT,CCZO,IAAMI,GAAkB,CAC7B,UACA,aACA,gBACA,iBACA,SACA,WACA,YACA,mBACA,WACA,UACA,UACA,gBACA,gBACA,oBACA,SACA,cACA,QACA,aACA,SACA,YACA,cACA,cACA,aACA,cACA,SACA,mBACA,YACA,UACA,UACA,UACA,aACA,UACA,YACA,YACA,aACA,UACA,SACA,eACA,mBACA,cACA,cACA,eACA,eACA,cACA,aACA,cACA,YACA,UACA,UACA,SACA,YACA,aACA,eACA,UACA,WACA,WACA,cACA,4BACA,WACA,YACA,WACA,eACA,YACA,WACA,YACA,eACA,WACA,iBACA,YACA,UACA,eACA,cACA,aACA,gBACA,gBACA,gBACA,cACA,kBACA,iBACA,iBACA,gBACA,eACA,sBACA,uBACA,qBACA,sBACA,mBACA,kBACA,oBACA,mBACA,iBACA,uBACA,qBACA,oBACA,YACA,YACF,EAEaC,GAAeD,GAAgB,OAC1C,CAACE,EAAKC,IAAO,CACX,IAAMC,EAAMD,EAAG,MAAM,CAAC,EAAE,YAAY,EACpC,OAAAD,EAAIE,CAAG,EAAID,EACJD,CACT,EACA,CAAC,CAGH,EChGaG,GAAN,KAAgB,CAOrB,YAAYC,EAAgC,CAF5C,KAAQ,UAA6B,IAAI,IAGvC,IAAMC,GAAW,IAAMD,EAAmB,GAG1CC,EAAQ,YAAeC,GAAwB,CAC7C,KAAK,UAAU,IAAIA,CAAO,CAC5B,EACA,KAAK,QAAUD,CACjB,CAKA,OAAc,CACZ,QAAWC,KAAW,KAAK,UAAWA,EAAQ,EAC9C,KAAK,UAAU,MAAM,CACvB,CAEA,IAAI,iBAA0B,CAC5B,OAAO,KAAK,UAAU,IACxB,CACF,EAKMC,GAA+B,CAAC,EAIlCC,GAAgB,EAIb,SAASC,IAAoC,CAClD,OAAID,GAAgB,EAAU,KACvBD,GAAgB,OACnBA,GAAgBA,GAAgB,OAAS,CAAC,EAC1C,IACN,CAIO,SAASG,GAAoBC,EAAsBC,EAAgB,CACxEL,GAAgB,KAAKI,CAAS,EAC9B,GAAI,CACF,OAAOC,EAAG,CACZ,QAAA,CACEL,GAAgB,IAAI,CACtB,CACF,CAGO,SAASM,GAAgBD,EAAgB,CAC9CJ,KACA,GAAI,CACF,OAAOI,EAAG,CACZ,QAAA,CACEJ,IACF,CACF,CC1EA,IAAIM,GAAuB,CAAC,EAQfC,GACX,OAAO,gBAAmB,WACtB,eACCC,GAAO,CACN,QAAQ,QAAQ,EACb,KAAKA,CAAE,EACP,MAAOC,GAAM,CACZ,WAAW,IAAM,CACf,MAAMA,CACR,EAAG,CAAC,CACN,CAAC,CACL,EAKAC,GAAkB,IASpBC,GAAc,EACdC,GAAmC,IAAI,IAKrCC,GAAqC,IAAI,IAKxC,SAASC,GAAcV,EAAgB,CAC5CO,KACA,GAAI,CACF,OAAOP,EAAG,CACZ,QAAA,CAEE,GADAO,KACIA,KAAgB,EAAG,CACrB,IAAMI,EAAYH,GAClBA,GAAoB,IAAI,IACxB,QAAWI,KAAYD,EAAWC,EAAS,eAAe,CAC5D,CACF,CACF,CAEO,IAAMC,GAAN,KAAe,CAAf,aAAA,CAKL,KAAQ,WAAkD,OAAO,OAC/D,IACF,EACA,KAAQ,SACN,IAAI,IACN,KAAQ,WAAa,GAErB,KAAQ,UAAoC,IAAI,IAEhD,KAAQ,WAAa,CAAA,CAErB,UAAiB,CACf,GAAI,KAAK,WACP,QAAWC,KAAS,KAAK,WACvB,KAAK,WAAWA,CAAK,EAAE,MAAM,EAGjC,KAAK,WAAa,IACpB,CAEA,YAAYA,EAAeC,EAA+B,CACxD,GAAI,CAAC,KAAK,WAAY,MAAO,IAAM,CAAC,EAEpC,GAAI,OAAOD,GAAU,UAAY,OAAOC,GAAa,WACnD,MAAM,IAAI,MACR,0DACF,EAGG,KAAK,WAAWD,CAAK,IACxB,KAAK,WAAWA,CAAK,EAAI,IAAI,KAG/B,IAAMpB,EAAU,IAAM,KAAK,eAAeoB,EAAOC,CAAQ,EAEzD,OAAI,KAAK,WAAWD,CAAK,EAAE,IAAIC,CAAQ,IAEvC,KAAK,WAAWD,CAAK,EAAE,IAAIC,CAAQ,EAC/B,OAAOA,EAAS,aAAgB,YAClCA,EAAS,YAAYrB,CAAO,GAGvBA,CACT,CAEA,eAAeoB,EAAeC,EAAyB,CACrD,GAAI,CAAC,KAAK,WAAY,OAEtB,IAAMC,EAAY,KAAK,WAAWF,CAAK,EACnCE,GAAaA,EAAU,IAAID,CAAQ,IACrCC,EAAU,OAAOD,CAAQ,EACrBC,EAAU,OAAS,GACrB,OAAO,KAAK,WAAWF,CAAK,EAGlC,CAKA,cAAcA,EAAuB,CAhIvC,IAAAG,EAAAC,EAAAC,EAiII,OAAOA,GAAAD,GAAAD,EAAA,KAAK,aAAL,KAAA,OAAAA,EAAkBH,CAAAA,IAAlB,KAAA,OAAAI,EAA0B,OAA1B,KAAAC,EAAkC,CAC3C,CAEA,OAAOL,KAAkBM,EAAuB,CAE9C,GADI,CAAC,KAAK,YACN,CAAC,KAAK,WAAWN,CAAK,EAAG,OAM7B,IAAMO,EAAMnB,GAAO,OAASA,GAAOA,GAAO,OAAS,CAAC,EAAI,KAGxD,GAFsBmB,GAAOA,EAAI,CAAC,IAAM,MAAQA,EAAI,CAAC,IAAMP,EAE1C,CACf,IAAMQ,EAAW,KAAK,UAAU,IAAIR,CAAK,EAEzC,GAAIQ,GAAYA,EAAS,CAAC,IAAMF,EAAK,CAAC,EAAG,OACzC,GAAI,KAAK,YAAcd,GAAiB,CACtC,QAAQ,MACN,oCAAoCQ,CAAK,0BAAqBR,EAAe,aAC/E,EACA,MACF,CACA,KAAK,aACL,KAAK,SAAS,IAAIQ,EAAO,CAAE,KAAAM,EAAM,MAAO,CAAC,CAAE,CAAC,CAC9C,KAAO,CACL,GAAI,KAAK,YAAYN,CAAK,EAAG,OAC7B,KAAK,SAAS,IAAIA,EAAO,CAAE,KAAAM,EAAM,MAAO,CAAC,GAAGlB,EAAM,CAAE,CAAC,CACvD,CAKIK,GAAc,EAChBC,GAAkB,IAAI,IAAI,EAE1B,KAAK,eAAe,CAExB,CAKA,gBAAuB,CACjB,KAAK,aACT,KAAK,WAAa,GAClBC,GAAoB,IAAI,IAAI,EAC5BN,GAAW,IAAM,KAAK,UAAU,CAAC,EACnC,CAEQ,YAAYW,EAAwB,CAC1C,IAAMS,EAAMrB,GAAO,UAAU,CAAC,CAACsB,EAAGnB,CAAC,IAAMmB,IAAM,MAAQnB,IAAMS,CAAK,EAClE,GAAIS,IAAQ,GAAI,MAAO,GAEvB,IAAME,EAAQ,CAAC,GAAGvB,GAAO,MAAMqB,CAAG,EAAE,IAAI,CAAC,CAAC,CAAElB,CAAC,IAAMA,CAAC,EAAGS,CAAK,EAC5D,OAAA,QAAQ,MACN;IAA6CW,EAAM,KAAK,UAAK,CAAC,EAChE,EACO,EACT,CAEA,WAAkB,CAChB,KAAK,WAAa,GAClBhB,GAAoB,OAAO,IAAI,EAC/B,IAAMiB,EAAU,KAAK,SACrB,KAAK,SAAW,IAAI,IAEpB,OAAW,CAACZ,EAAO,CAAE,KAAAM,EAAM,MAAAO,CAAM,CAAC,IAAKD,EACrCxB,GAASyB,EACT,KAAK,OAAOb,EAAOM,CAAI,EAEzBlB,GAAS,CAAC,EAEN,KAAK,SAAS,OAAS,IAAG,KAAK,WAAa,EAClD,CAEQ,OAAOY,EAAeM,EAAuB,CACnD,GAAI,CAAC,KAAK,WAAY,OACtB,IAAMJ,EAAY,KAAK,WAAWF,CAAK,EACvC,GAAKE,EAEL,CAAAd,GAAO,KAAK,CAAC,KAAMY,CAAK,CAAC,EACzB,KAAK,UAAU,IAAIA,EAAOM,CAAI,EAE9B,QAAWL,IAAY,CAAC,GAAGC,CAAS,EAClC,GAAKA,EAAU,IAAID,CAAQ,EAC3B,GAAI,CACFA,EAAS,GAAGK,CAAI,CAClB,OAASf,EAAG,CACV,QAAQ,MAAMA,CAAC,CACjB,CAGF,KAAK,UAAU,OAAOS,CAAK,EAC3BZ,GAAO,IAAI,CAAA,CACb,CACF,EAIO,SAAS0B,IAA+B,CAC7C,OAAOnB,GAAoB,KAAO,CACpC,CAKO,SAASoB,IAA8B,CAC5C,IAAIC,EAAQ,EACZ,KAAOrB,GAAoB,KAAO,GAAG,CACnC,GAAIqB,IAAU,IAAO,CACnB,QAAQ,MAAM,mDAAmD,EACjE,KACF,CACA,IAAMnB,EAAY,CAAC,GAAGF,EAAmB,EACzCA,GAAoB,MAAM,EAC1B,QAAWG,KAAYD,EAAWC,EAAS,UAAU,CACvD,CACF,CC7OO,IAAMmB,GAAN,KAAe,CAMpB,YACEC,EACSC,EAAe,OAAOD,EAC/B,CADS,KAAA,KAAAC,EAPX,KAAS,SAAW,GAGpB,KAAQ,UAA6B,IAAIpB,GAMvC,KAAK,aAAemB,EACpB,KAAK,OAASA,CAChB,CAEA,IAAIjB,EAAgC,CAClC,GAAIA,EACF,KAAK,YAAYA,CAAQ,MACpB,CAKL,IAAMhB,EAAYF,GAAgB,EAC9BE,GAAW,KAAK,YAAYA,EAAU,OAA2B,CACvE,CACA,OAAO,KAAK,MACd,CAEA,IAAImC,EAAmB,CAChB,KAAK,YACV,KAAK,OAASA,EACd,KAAK,UAAU,OAAO,KAAK,KAAMA,CAAQ,EAC3C,CAEA,OAAc,CACZ,KAAK,IAAI,KAAK,YAAY,CAC5B,CAEA,YAAYnB,EAAwC,CAClD,OAAK,KAAK,UACH,KAAK,UAAU,YAAY,KAAK,KAAMA,CAAQ,EADzB,IAAM,CAAC,CAErC,CAEA,eAAeA,EAAkC,CAC1C,KAAK,WACV,KAAK,UAAU,eAAe,KAAK,KAAMA,CAAQ,CACnD,CAEA,UAAiB,CACX,KAAK,YACP,KAAK,UAAU,SAAS,EACxB,KAAK,UAAY,KAErB,CACF,ECtDO,SAASoB,EACdC,EAA8B,CAAC,EAC/BC,EAA8B,CAAC,EACV,CACrB,IAAMC,EAAQ,CACZ,YACA,aACA,YACA,aACA,aACA,YACF,EACMC,EAAQ,CAAC,QAAS,MAAO,YAAa,gBAAiB,SAAS,EAChEC,EAAW,CAAC,SAAS,EAEzB,OAAO,UAAU,SAAS,KAAKH,CAAM,IAAM,mBAC3C,OAAO,eAAeA,CAAM,IAAM,OAAO,YAGzCA,EAASI,GAAUJ,CAAM,GAG3B,QAAW/C,KAAO+C,EAAQ,CACxB,IAAMK,EAAQL,EAAO/C,CAAG,EACxB,GAAI,EAAuBoD,GAAU,MAAQA,IAAU,IAEvD,GAAI,OAAOA,GAAU,UAAY,CAAC,MAAM,QAAQA,CAAK,EAC/C,OAAON,EAAO9C,CAAG,GAAM,SACzB8C,EAAO9C,CAAG,EAAI6C,EAAMC,EAAO9C,CAAG,EAAGoD,CAAK,EAEtCN,EAAO9C,CAAG,EAAIoD,UAGZJ,EAAM,SAAShD,CAAG,EACpB,GAAI,OAAO8C,EAAO9C,CAAG,GAAM,YAAc,OAAOoD,GAAU,WAAY,CACpE,IAAMC,EAAMP,EAAO9C,CAAG,EACtB8C,EAAO9C,CAAG,EAAKyB,GAAsB,CACnC,IAAM6B,EAAO,OAAOD,GAAQ,WAAaA,EAAI5B,CAAQ,EAAI4B,EACnDE,EAAO,OAAOH,GAAU,WAAaA,EAAM3B,CAAQ,EAAI2B,EAC7D,MAAO,CAACE,EAAMC,CAAI,EAAE,OAAQxC,GAAMA,CAAC,EAAE,KAAK,IAAI,CAChD,CACF,MACE+B,EAAO9C,CAAG,EAAI,CAAC8C,EAAO9C,CAAG,EAAGoD,CAAK,EAAE,OAAQrC,GAAMA,CAAC,EAAE,KAAK,IAAI,UAEtDmC,EAAS,SAASlD,CAAG,EAC9B,GAAI,OAAO8C,EAAO9C,CAAG,GAAM,YAAc,OAAOoD,GAAU,WAAY,CACpE,IAAMC,EAAMP,EAAO9C,CAAG,EACtB8C,EAAO9C,CAAG,EAAKyB,GAAsB,CACnC,IAAM6B,EAAO,OAAOD,GAAQ,WAAaA,EAAI5B,CAAQ,EAAI4B,EACnDE,EAAO,OAAOH,GAAU,WAAaA,EAAM3B,CAAQ,EAAI2B,EAC7D,MAAO,CAACE,EAAMC,CAAI,EAAE,OAAQxC,GAAMA,CAAC,EAAE,KAAK,EAAE,CAC9C,CACF,MACE+B,EAAO9C,CAAG,EAAI,CAAC8C,EAAO9C,CAAG,EAAGoD,CAAK,EAAE,OAAQrC,GAAMA,CAAC,EAAE,KAAK,EAAE,UAEpDkC,EAAM,SAASjD,CAAG,EAC3B,GAAI,OAAO8C,EAAO9C,CAAG,GAAM,YAAc,OAAOoD,GAAU,WAAY,CACpE,IAAMC,EAAMP,EAAO9C,CAAG,EACtB8C,EAAO9C,CAAG,EAAKyB,GAAsB,CACnC,IAAM6B,EAAO,OAAOD,GAAQ,WAAaA,EAAI5B,CAAQ,EAAI4B,EACnDE,EAAO,OAAOH,GAAU,WAAaA,EAAM3B,CAAQ,EAAI2B,EAC7D,MAAO,CAACE,EAAMC,CAAI,EAAE,OAAQxC,GAAMA,CAAC,EAAE,KAAK,GAAG,CAC/C,CACF,MACE+B,EAAO9C,CAAG,EAAI,CAAC8C,EAAO9C,CAAG,EAAGoD,CAAK,EAAE,OAAQrC,GAAMA,CAAC,EAAE,KAAK,GAAG,UAErDf,EAAI,WAAW,IAAI,EAAG,CAC/B,IAAM2C,EAAO3C,EAAI,QAAQ,KAAM,EAAE,EAAE,YAAY,EAC/CwD,GAASV,EAAyBH,EAAMS,CAAK,CAC/C,SAAWpD,EAAI,WAAW,KAAK,EAAG,CAChC,IAAM2C,EAAO3C,EAAI,QAAQ,MAAO,EAAE,EAClCyD,GAAQX,EAAyBH,EAAMS,CAAK,CAC9C,MACEN,EAAO9C,CAAG,EAAIoD,CAGpB,CACA,OAAON,CACT,CAEO,SAASY,GAAWC,EAAc,GAAY,CACnD,IAAIC,EAAO,WACX,QAASC,EAAI,EAAGA,EAAIF,EAAI,OAAQE,IAC9BD,GAAQD,EAAI,WAAWE,CAAC,EACxBD,EAAQA,EAAO,WAAgB,EAEjC,OAAO,OAAO,aAAa,GAAMA,EAAO,EAAG,EAAIA,EAAK,SAAS,EAAE,CACjE,CAcO,SAASE,EACdC,EACApB,EACU,CACV,OAAOoB,aAAetB,IAAUsB,GAAA,MAAAA,EAAa,SACxCA,EACD,IAAItB,GAASsB,EAAUpB,CAAI,CACjC,CAUO,SAASqB,GAAqBZ,EAA2C,CAC9E,OACE,OAAOA,GAAU,UACjBA,IAAU,MACTA,EAAc,WAAa,EAEhC,CASO,SAASa,GAAYnB,EAA4C,CACtE,MAAO,CACL,SAAU,GACV,IAAIrB,EAAgC,CAClC,OAAOqB,EAAO,IAAIrB,CAAQ,CAC5B,CACF,CACF,CAyBO,SAASyC,GACdlE,EACAmE,EACAC,EACgB,CAChB,MAAO,CAAE,WAAY,CAAE,CAACpE,CAAG,EAAG,CAAE,OAAAmE,EAAQ,MAAAC,CAAM,CAAE,CAAE,CACpD,CC1KO,SAASX,GACdY,EACAC,EACAnE,EACM,CACN,IAAMoE,EAAe,MAAMD,CAAQ,GAC7BE,EAAUH,EAAQE,CAAY,EAEhC,OAAOC,GAAY,WACpBH,EAAgBE,CAAY,EAAI,IAAIzC,IAAgB,CAClD0C,EAAqB,GAAG1C,CAAI,EAC5B3B,EAAqB,GAAG2B,CAAI,CAC/B,EAECuC,EAAgBE,CAAY,EAAIpE,CAErC,CAEO,SAASqD,GACdiB,EACAC,EACAvE,EACM,CACN,IAAMwE,EAAgB9E,GAAa6E,CAAS,EAC5C,GAAI,CAACC,EACH,MAAM,MAAM,uBAAuBD,CAAS,GAAG,EAEjD,IAAMF,EAAWC,EAAmBE,CAAa,EAE7C,OAAOH,GAAY,WACpBC,EAAmBE,CAAa,EAAI,CACnCnD,EACAoD,IACG,CACHJ,EAAQhD,EAAOoD,CAAI,EACnBzE,EAAQqB,EAAOoD,CAAI,CACrB,EAECH,EAAmBE,CAAa,EAAIxE,CAEzC,CAEO,SAASgD,GAAUC,EAAYyB,EAAO,IAAI,QAAgB,CAE/D,GADIzB,IAAU,MAAQ,OAAOA,GAAU,UACnC,OAAOA,GAAU,WAAY,OAAOA,EACxC,GAAIyB,EAAK,IAAIzB,CAAK,EAAG,OAAOyB,EAAK,IAAIzB,CAAK,EAE1C,IAAI0B,EAEJ,GAAI,MAAM,QAAQ1B,CAAK,EAAG,CACxB0B,EAAQ,CAAC,EACTD,EAAK,IAAIzB,EAAO0B,CAAK,EACrB,QAAWC,KAAK3B,EAAO0B,EAAM,KAAK3B,GAAU4B,EAAGF,CAAI,CAAC,EACpD,OAAOC,CACT,CAKA,GAAI1B,aAAiB,KAAM,OAAO,IAAI,KAAKA,CAAK,EAChD,GAAIA,aAAiB,OAAQ,OAAO,IAAI,OAAOA,CAAK,EACpD,GAAIA,aAAiB,IAAK,CACxB0B,EAAQ,IAAI,IACZD,EAAK,IAAIzB,EAAO0B,CAAK,EACrB,OAAW,CAACE,EAAGD,CAAC,IAAK3B,EACnB0B,EAAM,IAAI3B,GAAU6B,EAAGH,CAAI,EAAG1B,GAAU4B,EAAGF,CAAI,CAAC,EAClD,OAAOC,CACT,CACA,GAAI1B,aAAiB,IAAK,CACxB0B,EAAQ,IAAI,IACZD,EAAK,IAAIzB,EAAO0B,CAAK,EACrB,QAAWC,KAAK3B,EAAO0B,EAAM,IAAI3B,GAAU4B,EAAGF,CAAI,CAAC,EACnD,OAAOC,CACT,CACA,GAAI,YAAY,OAAO1B,CAAK,EAC1B,OAAO,IAAKA,EAAc,YAAYA,CAAK,EAE7C,GAAIA,aAAiB,YACnB,OAAOA,EAAM,MAAM,CAAC,EAGtB,IAAM6B,EAAQ,OAAO,eAAe7B,CAAK,EACzC,GAAI6B,IAAU,OAAO,UAAW,OAAO7B,EAEvC0B,EAAQ,OAAO,OAAOG,CAAK,EAC3BJ,EAAK,IAAIzB,EAAO0B,CAAK,EAErB,QAAW9E,KAAO,QAAQ,QAAQoD,CAAK,EACrC0B,EAAM9E,CAAG,EAAImD,GAAUC,EAAMpD,CAAG,EAAG6E,CAAI,EAGzC,OAAOC,CACT,CAEO,SAASI,GACdC,EACAC,EAAY,GACH,CACT,GAAI,OAAO,UAAU,SAAS,KAAKD,CAAO,IAAM,kBAC9C,MAAM,MAAM,UAAUA,CAAO,2BAA2B,EAE1D,IAAME,EAAO,OAAO,KAAKF,CAAO,EAChC,GAAIE,EAAK,SAAW,GAAK,CAACD,EACxB,MAAM,MAAM,+BAA+B,EAE7C,QAASvB,EAAI,EAAGA,EAAIwB,EAAK,OAAQxB,IAAK,CACpC,IAAM7D,EAAMqF,EAAKxB,CAAC,EACZE,EAAMoB,EAAQnF,CAA2B,EAC/C,GAAI6D,IAAM,GAAK,CAACzE,GAAS,SAASY,CAAG,GAAK,CAACoF,EACzC,MAAM,MAAM,OAAOpF,CAAG,6BAA6B,EAC9C,GACLA,IAAQ,SACR+D,GACA,OAAO,UAAU,SAAS,KAAKA,CAAG,IAAM,kBAExC,MAAM,MAAM,0BAA0B,EACjC,GAAI/D,IAAQ,IACjBmF,EAAQ,EAAG,QAASJ,GAAMG,GAASH,EAAqB,EAAI,CAAC,MACxD,CAAA,GAAI/E,EAAI,WAAW,KAAK,GAAK,OAAO+D,GAAQ,WACjD,MAAM,MAAM,QAAQ/D,CAAG,WAAW+D,CAAG,uBAAuB,EACvD,GAAI/D,EAAI,WAAW,IAAI,GAAK,OAAO+D,GAAQ,WAChD,MAAM,MAAM,SAAS/D,CAAG,WAAW+D,CAAG,uBAAuB,EACxD,GAAI/D,IAAQ,WAAa,OAAO+D,GAAQ,WAC7C,MAAM,MAAM,iDAAiD,EACxD,GACL/D,IAAQ,YACR,OAAO,UAAU,SAAS,KAAK+D,CAAG,IAAM,kBAExC,MAAM,MAAM,6BAA6B,EACpC,GACL/D,IAAQ,aACR,OAAO,UAAU,SAAS,KAAK+D,CAAG,IAAM,kBAExC,MAAM,MAAM,8BAA8B,EACrC,GACL/D,IAAQ,QACR,OAAO+D,GAAQ,UACf,OAAOA,GAAQ,SAEf,MAAM,MAAM,mCAAmC,CAAA,CAEnD,CACA,MAAO,EACT,CAEO,SAASuB,GAAO3B,EAAsB,CAI3C,OAAO,IAAA,OAAC,uEAA8D,IAAE,EAAC,KACvEA,EAAI,KAAK,CACX,CACF,CAMO,SAAS4B,GAAmBC,EAAsB,CAGvD,IAAIC,EAASD,EAAK,QAAQ,yCAA0C,EAAE,EAItE,OAAAC,EAASA,EAAO,QAAQ,sBAAuB,EAAE,EAGjDA,EAASA,EAAO,QAAQ,4BAA6B,EAAE,EAIvDA,EAASA,EAAO,QACd,0DACA,EACF,EAEAA,EAASA,EAAO,QACd,yDACA,GACF,EAEAA,EAASA,EAAO,QACd,4EACA,OACF,EACOA,CACT,CAEO,SAASC,GAAW/B,EAAqB,CAC9C,OAAOA,EACJ,QAAQ,KAAM,OAAO,EACrB,QAAQ,KAAM,MAAM,EACpB,QAAQ,KAAM,MAAM,EACpB,QAAQ,KAAM,QAAQ,EACtB,QAAQ,KAAM,OAAO,CAC1B,CAkDO,SAASgC,GAAWR,EAA6C,CACtE,OAAO,OAAO,KAAKA,CAAO,EAAE,KAAMpE,GAAM3B,GAAS,SAAS2B,CAAC,CAAC,CAG9D,CAEO,SAAS6E,GAAajC,EAAqB,CAChD,OAAOA,EAAI,QAAQ,qBAAsB,OAAO,EAAE,YAAY,CAChE,CAEO,SAASkC,GAAiBC,EAAmB,CAClD,GAAIA,EAAU,QAAQ,GAAG,IAAM,EAC7B,MAAO,CAACA,CAAS,EAMnB,QAJIC,EAAW,CAAC,EACZC,EAAS,EACTC,EAAW,EACXC,EAAQ,GACHrC,EAAI,EAAGsC,EAAML,EAAU,OAAQjC,EAAIsC,EAAKtC,IAAK,CACpD,IAAIuC,EAAON,EAAUjC,CAAC,EACtB,GAAIuC,IAAS,IACXJ,GAAU,UACDI,IAAS,IAClBJ,GAAU,UACDI,IAAS,IAClBH,GAAY,UACHG,IAAS,IAClBH,GAAY,UACHG,IAAS,KACd,CAACJ,GAAU,CAACC,EAAU,CACxBF,EAAS,KAAKG,EAAM,KAAK,CAAC,EAC1BA,EAAQ,GACR,QACF,CAEFA,GAASE,CACX,CACA,OAAAL,EAAS,KAAKG,EAAM,KAAK,CAAC,EACnBH,CACT,CAEO,SAASM,GAAqBC,EAA8B,CACjE,IAAMC,EAAOD,EAAa,KAAK,EAG/B,OAAIC,EAAK,WAAW,GAAG,EAAUA,EAAK,QAAQ,OAAQ,EAAE,EACjDA,EACJ,QAAQ,kBAAmB,IAAI,EAC/B,QAAQ,OAAQ,GAAG,EACnB,QAAQ,iBAAkB,QAAQ,EAClC,QAAQ,kBAAmB,MAAM,EACjC,KAAK,CACV,CAEO,SAASC,GACdC,EACAC,EACsB,CACtB,QAAS7C,EAAI,EAAGA,EAAI4C,EAAM,OAAQ5C,IAAK,CACrC,IAAM8C,EAAOF,EAAM5C,CAAC,EAChB7D,EAAqB,KACrB,OAAO2G,EAAK,cAAiB,SAC/B3G,EAAMqG,GAAqBM,EAAK,YAAY,EAE5C,OAAOA,EAAK,SAAY,UACxBA,EAAK,QAAQ,WAAW,GAAG,IAE3B3G,EAAMqG,GAAqBM,EAAK,QAAQ,MAAM,GAAG,EAAE,CAAC,CAAC,GAEnD3G,GAAO,CAAC0G,EAAI,IAAI1G,CAAG,GAAG0G,EAAI,IAAI1G,EAAK2G,CAAe,CACxD,CACA,OAAOD,CACT,CAEO,SAASE,GACdC,EACAC,EACkB,CA/UpB,IAAAnF,EAgVE,IAAIoF,EAAWF,EAAY,cACzB,eACF,EAEA,GAAI,CAACE,EAAU,CACbA,EAAW,SAAS,cAAc,OAAO,EACzCA,EAAS,GAAK,eACd,IAAMC,EAAgBF,GAAA,KAAAA,EAASnH,GAAU,EAAE,SACvCqH,IAAeD,EAAS,MAAQC,GACpCH,EAAY,YAAYE,CAAQ,CAClC,CAEA,OAAIA,EAAS,QAAQ,aAAe,UAClCpF,EAAAoF,EAAS,QAAT,MAAApF,EAAgB,WAAW,yCAA0C,CAAA,EACrEoF,EAAS,QAAQ,WAAa,QAGzBA,CACT,CAEO,IAAME,GACX5C,GACmB,CACnB,GAAI,MAAM,QAAQA,EAAQ,CAAC,EAAG,CAC5B,IAAM6C,EAAuB,CAAC,EAC9B,OAAA7C,EAAQ,EAAE,QAAS8C,GAAMtE,EAAMqE,EAAMD,GAAaE,CAAC,CAAC,CAAC,EACrD,OAAO9C,EAAQ,EACfxB,EAAMqE,EAAM7C,CAAO,EAEZ6C,CACT,KACE,QAAO7C,CAEX,ECnWM+C,GACJ,CACE,UAAW,CAAC,MAAO,IAAI,EACvB,eAAgB,CAAC,KAAM,KAAK,CAC9B,EAEWC,GAAN,KAAuB,CAyB5B,YAAY1E,EAAcS,EAAYkE,EAAa,CAdnD,KAAA,cAAgC,OAEhC,KAAA,UAAY,IAAI/F,GAIhB,KAAQ,UAA4B,CAAC,EAMrC,KAAQ,cAAgB,GAGtB,KAAK,OAAS+F,EACd,KAAK,UAAarI,GAAwC,SAAS0D,CAAI,EACvE,KAAK,kBAAoByE,GAA4BzE,CAAI,EACrDzD,GAAgB,SAASyD,CAAI,EAC/B,KAAK,KAAOA,EACH,OAAO,OAAOxD,GAAoBwD,CAAI,EAC/C,KAAK,KAAOxD,GAAmBwD,CAAI,EAEnC,KAAK,KAAOiD,GAAajD,CAAI,EAE/B,KAAK,MAAQ,OACb,KAAK,IAAIS,CAAK,CAChB,CAEQ,UAAUA,EAAiB,CACjC,OAAI,KAAK,mBAAqB,OAAOA,GAAU,UACtCA,EAAQ,KAAK,kBAAkB,CAAC,EAAI,KAAK,kBAAkB,CAAC,EAE9DA,CACT,CAEA,QAAe,CACb,GAAI,CAAC,KAAK,QAAU,CAAC,KAAK,OAAO,WAAY,OAC7C,IAAMmE,EAAa,KAAK,OAAO,WAEzBC,EAAc,CAAC,OAAO,EACxB,KAAK,UACH,KAAK,QAAU,IAAS,KAAK,OAAS,KACxCD,EAAW,gBAAgB,KAAK,IAAI,EAEpCA,EAAW,aACT,KAAK,KACL,KAAK,QAAU,GAAO,GAAK,KAAK,KAClC,EAEO,KAAK,OAAS,KACvBA,EAAW,gBAAgB,KAAK,IAAI,EAC3BC,EAAY,SAAS,KAAK,IAAI,EACtCD,EAAmB,KAAK,IAAI,EAAI,KAAK,MAEtCA,EAAW,aAAa,KAAK,KAAM,KAAK,KAAK,CAEjD,CAEA,IAAInE,EAA6B,CA1FnC,IAAAzB,EAAAC,EA2FI,IAAM6F,EAAO,KAAK,MAIlB,GAHA,KAAK,cAAgBrE,EAGjB,KAAK,UAAU,OAAQ,CACzB,QAAWhD,KAAW,KAAK,UAAWA,EAAQ,EAC9C,KAAK,UAAY,CAAC,CACpB,CAEA,GAAIgD,GAAS,KACX,KAAK,MAAQ,aACJ,OAAOA,GAAU,WAAY,CACtC,IAAI3B,EAAgB,IAAM,CACxB,GAAI,CAAC,KAAK,QAAU,KAAK,OAAO,UAAW,OAC3C,IAAM0F,EAAI,KAAK,MAGf,KAAK,MAAQ,KAAK,UACd,CAAA,CAAS/D,EAAmB3B,CAAQ,EACpC,KAAK,UAAW2B,EAAmB3B,CAAQ,CAAC,EAChD,KAAK,OAAO,EACR0F,IAAM,KAAK,OAAO,KAAK,UAAU,OAAO,KAAK,KAAM,KAAK,KAAK,CACnE,EAEA1F,EAAS,YAAc,KAAK,OAC5BA,EAAS,MAAQ,UAASE,EAAA,KAAK,SAAL,KAAA,OAAAA,EAAa,OAAO,KAAIC,EAAA,KAAK,SAAL,KAAA,OAAAA,EAAa,MAAM,cAAc,KAAK,IAAI,GAE5FH,EAAS,YAAerB,GAAwB,CAC9C,KAAK,UAAU,KAAKA,CAAO,EAIvB,KAAK,QAAU,CAAC,KAAK,gBACvB,KAAK,cAAgB,GACrB,KAAK,OAAO,QAAQ,eAAgB,IAAM,CACxC,QAAWsH,KAAuB,KAAK,UACrCA,EAAoB,EAEtB,KAAK,UAAY,CAAC,EAClBjG,EAAW,IACb,CAAC,EAEL,EAEA,KAAK,MAAQ,KAAK,UACd,CAAA,CAAQ2B,EAAM3B,CAAQ,EACtB,KAAK,UAAU2B,EAAM3B,CAAQ,CAAC,CACpC,MACE,KAAK,MAAQ,KAAK,UAAY,CAAA,CAAQ2B,EAAS,KAAK,UAAUA,CAAK,EAGrE,KAAK,OAAO,EACRqE,IAAS,KAAK,OAAO,KAAK,UAAU,OAAO,KAAK,KAAM,KAAK,KAAK,CACtE,CAEA,YAAYE,EAAsC,CAChD,IAAMxH,EAAUwH,EAChBxH,EAAQ,YAAeC,GAAqB,CApJhD,IAAAuB,EAqJM,OAAAA,EAAA,KAAK,SAAL,KAAA,OAAAA,EAAa,QAAQ,eAAgBvB,CAAAA,CAAAA,EACvC,KAAK,UAAU,YAAY,KAAK,KAAMD,CAAO,CAC/C,CAEA,QAAe,CACT,KAAK,QAAU,KAAK,OAAO,YAC7B,KAAK,OAAO,WAAW,OAAO,KAAK,IAAI,EAEzC,KAAK,SAAS,CAChB,CAEA,UAAiB,CAIf,QAAWuH,KAAuB,KAAK,UAAWA,EAAoB,EACtE,KAAK,UAAY,CAAC,EAClB,KAAK,UAAU,SAAS,EACxB,KAAK,MAAQ,KACb,KAAK,OAAS,IAChB,CAEA,cAAuB,CACrB,GAAM,CAAE,KAAA/E,EAAM,MAAAS,CAAM,EAAI,KACxB,GAAI,KAAK,UACP,OAAOA,EAAQ,GAAGT,CAAI,GAAK,GAO7B,GAAIS,GAAS,KAAM,MAAO,GAC1B,IAAMW,EAAM,MAAM,QAAQX,CAAK,EAAI,KAAK,UAAUA,CAAK,EAAIA,EAC3D,MAAO,GAAGT,CAAI,KAAK+C,GAAW,OAAO3B,CAAG,CAAC,CAAC,GAC5C,CACF,ECpLa6D,GAAN,KAAoB,CAIzB,YAAYN,EAAqB,CAHjC,KAAA,MAAiD,CAAC,EAIhD,KAAK,OAASA,CAChB,CAEA,cAAuB,CACrB,GAAI,CAAC,KAAK,MAAO,MAAO,GACxB,IAAM3D,EAAM,OAAO,OAAO,KAAK,KAAK,EACjC,IAAKkE,GAASA,EAAK,aAAa,CAAC,EACjC,OAAO,OAAO,EACd,KAAK,GAAG,EACX,OAAOlE,EAAM,IAAIA,CAAG,GAAK,EAC3B,CAEA,IAAIhB,EAAmB,CAtBzB,IAAAhB,EAuBI,GAAK,KAAK,MACV,OAAOA,EAAA,KAAK,MAAMgB,CAAI,IAAf,KAAA,OAAAhB,EAAkB,KAC3B,CAEA,IAAIgB,EAAcS,EAA6B,CACzC,CAAC,KAAK,OAAS,CAAC,KAAK,SACrB,KAAK,MAAMT,CAAI,EACjB,KAAK,MAAMA,CAAI,EAAE,IAAIS,CAAK,EAE1B,KAAK,MAAMT,CAAI,EAAI,IAAI0E,GAAiB1E,EAAMS,EAAO,KAAK,MAAM,EAEpE,CAEA,YAAYT,EAAcgF,EAAkD,CACtE,KAAK,IAAIhF,CAAI,GACf,KAAK,MAAOA,CAAI,EAAE,YAAYgF,CAAQ,CAE1C,CAEA,IAAIhF,EAAuB,CACzB,OAAK,KAAK,MACH,OAAO,OAAO,KAAK,MAAOA,CAAI,EADb,EAE1B,CAEA,OAAOA,EAAoB,CA/C7B,IAAAhB,EAAAC,EAgDI,GAAI,CAAC,KAAK,MAAO,OAMjB,IAAMkG,GAAUlG,GAAAD,EAAA,KAAK,MAAMgB,CAAI,IAAf,KAAA,OAAAhB,EAAkB,OAAlB,KAAAC,EAA0Be,EAEtC,KAAK,MAAMA,CAAI,IACjB,KAAK,MAAMA,CAAI,EAAE,SAAS,EAC1B,OAAO,KAAK,MAAMA,CAAI,GAItB,KAAK,QACL,KAAK,OAAO,YACZ,KAAK,OAAO,sBAAsB,SAElC,KAAK,OAAO,WAAW,gBAAgBmF,CAAO,CAElD,CAEA,UAAiB,CACf,GAAI,KAAK,MACP,QAAW9H,KAAO,KAAK,MACrB,KAAK,MAAMA,CAAG,EAAE,SAAS,EAG7B,KAAK,MAAQ,KACb,KAAK,OAAS,IAChB,CAEA,OAAO2C,EAAcoF,EAAuB,CAC1C,GACE,CAAC9I,GAAkB,SAAS0D,CAA0C,EAEtE,MAAM,MAAM,GAAGA,CAAI,6BAA6B,EAE9CoF,IAAU,GACZ,KAAK,IAAIpF,EAAM,EAAI,EACVoF,IAAU,GACnB,KAAK,OAAOpF,CAAI,EAEhB,KAAK,IAAIA,CAAI,EAAI,KAAK,OAAOA,CAAI,EAAI,KAAK,IAAIA,EAAM,EAAI,CAE5D,CAEA,SAASqF,EAA4D,CA/FvE,IAAArG,EAAAC,EAiGI,GADI,CAACoG,GACD,OAAOA,GAAc,UAAY,OAAOA,GAAc,WAAY,OAEtE,IAAMC,EAAM,CAACC,EAAiBC,IAAqB,CACjD,IAAMC,GAAQF,GAAW,IAAI,MAAM,GAAG,EAAE,OAAQnH,GAAcA,CAAC,EAC/D,MAAA,CAACqH,EAAK,SAASD,CAAQ,GAAKC,EAAK,KAAKD,CAAQ,EACvCC,EAAK,KAAK,GAAG,CACtB,EAOMC,GAAWzG,GAAAD,EAAA,KAAK,QAAL,KAAA,OAAAA,EAAa,QAAb,KAAA,OAAAC,EAAuB,cAClC0G,EAAc,OAAOD,GAAa,WAClC7D,EAAU8D,EAAcD,EAAW,KAAK,IAAI,OAAO,EACnDE,EAAW,OAAOP,GAAc,WAGtC,GAAI,CAACM,GAAe,CAACC,EAAU,CAC7B,KAAK,IAAI,QAASN,EAAIzD,EAASwD,CAAmB,CAAC,EACnD,MACF,CASA,KAAK,IAAI,QAAUvG,GACjBwG,EACEK,EAAe9D,EAAoC/C,CAAQ,EAAI+C,EAC/D+D,EACKP,EAAsCvG,CAAQ,EAC9CuG,CACP,CACF,CACF,CAEA,SAASA,EAA4B,CACnC,MAAI,CAACA,GAAa,OAAOA,GAAc,SAAiB,IACxC,KAAK,IAAI,OAAO,GAAK,IAChB,MAAM,GAAG,EAAE,OAAQjH,GAAcA,CAAC,EAC3C,SAASiH,CAAS,CAChC,CAEA,YAAYA,EAAyB,CAC/B,CAACA,GAAa,OAAOA,GAAc,WACvC,KAAK,SAASA,CAAS,EACnB,KAAK,YAAYA,CAAS,EAC1B,KAAK,SAASA,CAAS,EAC7B,CAEA,YAAYA,EAAyB,CACnC,GAAI,CAACA,GAAa,OAAOA,GAAc,SAAU,OAGjD,IAAMQ,GAFU,KAAK,IAAI,OAAO,GAAK,IACN,MAAM,GAAG,EAAE,OAAQzH,GAAcA,CAAC,EAC5C,OAAQ0H,GAAQA,IAAQT,CAAS,EACtDQ,EAAQ,OAAS,EACb,KAAK,IAAI,QAASA,EAAQ,KAAK,GAAG,CAAC,EACnC,KAAK,OAAO,OAAO,CACzB,CAEA,aAAaE,EAAkBP,EAAwB,CAEnD,CAACO,GACD,CAACP,GACD,OAAOO,GAAa,UACpB,OAAOP,GAAa,UAGlB,KAAK,SAASO,CAAQ,IACxB,KAAK,YAAYA,CAAQ,EACzB,KAAK,SAASP,CAAQ,EAE1B,CACF,ECrKaQ,GACX,OAAO,SAAY,aACnB,QAAQ,KAAO,MACf,QAAQ,IAAI,WAAa,aCRdC,GAAN,KAAoB,CAgBzB,YAAYjG,EAAcS,EAAmByF,EAAuB,CAbpE,KAAA,MAAoB,GAWpB,KAAQ,UAA4B,CAAC,EAGnC,KAAK,KAAOlG,EAMZ,KAAK,QAAUA,EAAK,WAAW,IAAI,EAAIA,EAAOiD,GAAajD,CAAI,EAC/D,KAAK,WAAakG,EAClB,KAAK,IAAIzF,CAAK,CAChB,CAEA,YAAmB,CACjB,GAAI,CAAC,KAAK,WAAY,OACtB,IAAM0F,EAAU,KAAK,WAAW,QAEhC,GAAIA,GAAYA,EAAyB,MAAO,CAC9C,IAAMC,EAA8BD,EAAyB,MAC7DC,EAAM,YAAY,KAAK,QAAS,OAAO,KAAK,KAAK,CAAC,EAE9C1J,GAAU,KAAK,IAAI,GACrBA,GAAU,KAAK,IAAI,EAAE,QAAS2J,GAAW,CACvCD,EAAM,YAAY,IAAIC,CAAM,IAAI,KAAK,OAAO,GAAI,OAAO,KAAK,KAAK,CAAC,CACpE,CAAC,CAEL,CACF,CACA,UAAiB,CACf,GAAI,KAAK,UAAU,OAAQ,CACzB,QAAW5I,KAAW,KAAK,UAAWA,EAAQ,EAC9C,KAAK,UAAY,CAAC,CACpB,CACA,KAAK,MAAQ,GACb,KAAK,WAAa,IACpB,CAEA,IAAIgD,EAAyB,CAzD/B,IAAAzB,EAAAC,EAAAC,EAAAoH,EA2DI,GAAI,KAAK,UAAU,OAAQ,CACzB,QAAW7I,KAAW,KAAK,UAAWA,EAAQ,EAC9C,KAAK,UAAY,CAAC,CACpB,CAEA,GAAI,OAAOgD,GAAU,WAAY,CAC/B,IAAI3B,GAAY,IAAM,CAjE5B,IAAAE,EAkEY,CAAC,KAAK,aAAcA,EAAA,KAAK,WAAW,aAAhB,MAAAA,EAA4B,YACpD,KAAK,MAAQyB,EAAM3B,CAAQ,EAC3B,KAAK,WAAW,EAClB,GAEAA,EAAS,YAAerB,GAAwB,CAC9C,KAAK,UAAU,KAAKA,CAAO,CAC7B,EAEAqB,EAAS,YAAc,KAAK,WAAY,KACxCA,EAAS,MAAQ,UAASG,GAAAD,EAAA,KAAK,aAAL,KAAA,OAAAA,EAAiB,OAAjB,KAAA,OAAAC,EAAuB,OAAO,KAAIqH,GAAApH,EAAA,KAAK,aAAL,KAAA,OAAAA,EAAiB,OAAjB,KAAA,OAAAoH,EAAuB,MAAM,UAAU,KAAK,IAAI,GAC5G,KAAK,MAAQ7F,EAAM3B,CAAQ,CAC7B,MACE,KAAK,MAAQ2B,EAGf,KAAK,WAAW,CAClB,CAEA,QAAe,CACb,GAAK,KAAK,WAEV,CAAA,GAAI,KAAK,WAAW,mBAAmB,aAAc,CACnD,IAAM2D,EAAW,KAAK,WAAW,QAAQ,MACzCA,EAAS,eAAe,KAAK,OAAO,EAEhC1H,GAAU,KAAK,IAAI,GACrBA,GAAU,KAAK,IAAI,EAAE,QAAS2J,GAAW,CACvCjC,EAAS,eAAe,IAAIiC,CAAM,IAAI,KAAK,OAAO,EAAE,CACtD,CAAC,CAEL,CACA,OAAO,KAAK,WAAW,WAAY,KAAK,IAAI,EAC5C,KAAK,SAAS,CAAA,CAChB,CAEA,SAAkB,CAChB,IAAIrF,EAAM,GAAG,KAAK,OAAO,KAAK,KAAK,KAAK,GACxC,OAAItE,GAAU,KAAK,IAAI,GACrBA,GAAU,KAAK,IAAI,EAAE,QAAS2J,GAAW,CACvCrF,GAAO,MAAMqF,CAAM,IAAI,KAAK,OAAO,KAAK,KAAK,KAAK,EACpD,CAAC,EAEIrF,CACT,CACF,EC3GauF,GAAN,MAAMC,EAAU,CAOrB,YAAY7C,EAAsBgB,EAAiC,CALnE,KAAA,QAA4D,KAE5D,KAAA,WAAmD,CAAC,EAIlD,KAAK,aAAehB,EACpB,KAAK,UAAY,IAAI8C,GAAU,IAAI,EACnC,KAAK,OAAS9B,CAChB,CAEA,UAAiB,CACf,GAAI,KAAK,WACP,QAAW+B,KAAQ,OAAO,OAAO,KAAK,UAAU,EAC9CA,EAAK,SAAS,EAId,KAAK,WACP,KAAK,UAAU,SAAS,EAG1B,KAAK,WAAa,KAClB,KAAK,UAAY,KACjB,KAAK,QAAU,KACf,KAAK,OAAS,IAChB,CAEA,IAAI,MAAO,CACT,IAAIzE,EAAO,KAAK,OAChB,KAAOA,aAAgBuE,IACrBvE,EAAOA,EAAK,OAEd,OAAOA,CACT,CAEA,IAAI,YAAiC,CACnC,IAAI0E,EAAY,KAAK,OACrB,KAAOA,GAAQA,aAAgBH,IAC7BG,EAAOA,EAAK,OAEd,OAAOA,CACT,CAEA,YAAY3G,EAAcoB,EAAgB,CACnC,KAAK,aACN,KAAK,WAAWpB,CAAI,EACtB,KAAK,WAAWA,CAAI,EAAE,IAAIoB,CAAG,EAE7B,KAAK,WAAWpB,CAAI,EAAI,IAAIiG,GAAcjG,EAAMoB,EAAK,IAAI,EAE7D,CAEA,YAAYpB,EAAoB,CACzB,KAAK,YACN,KAAK,WAAWA,CAAI,GACtB,KAAK,WAAWA,CAAI,EAAE,OAAO,CAEjC,CAEA,SAAkB,CAChB,GAAI,CAAC,KAAK,YAAc,CAAC,KAAK,UAAW,MAAO,GAChD,IAAM4G,EAAW,OAAO,OAAO,KAAK,UAAU,EAC3C,IAAKC,GAASA,EAAK,QAAQ,CAAC,EAC5B,KAAK,GAAG,EACLC,EAAS,KAAK,UAAU,QAAQ,EACtC,MAAO,GAAG,KAAK,YAAY,MAAMF,CAAQ,IAAIE,CAAM,KACrD,CAEA,MAAMX,EAA2C,CAC3C,CAACA,GAAW,CAAC,KAAK,YACtB,KAAK,QAAUA,EACX,aAAcA,GAChB,KAAK,UAAU,MAAMA,EAAQ,QAAuB,EAExD,CAEA,QAAe,CACb,GAAI,KAAK,SAAW,KAAK,QAAQ,iBAAkB,CACjD,IAAMY,EAAQ,KAAK,QAAQ,iBACrBjD,EAAQiD,EAAM,SACpB,QAAS7F,EAAI,EAAGA,EAAI4C,EAAM,OAAQ5C,IAChC,GAAI4C,EAAM5C,CAAC,IAAM,KAAK,QAAS,CAC7B6F,EAAM,WAAW7F,CAAC,EAClB,KACF,CAEJ,CACA,KAAK,SAAS,CAChB,CAEA,OAAO8F,EAA2C,CAChD,GAAI,CAAC,KAAK,YAAc,CAAC,KAAK,UAAW,OACzC,IAAMJ,EAAW,OAAO,OAAO,KAAK,UAAU,EAC3C,IAAKC,GAASA,EAAK,QAAQ,CAAC,EAC5B,KAAK,GAAG,EACX,GAAI,CACF,GAAK,KAAK,aAAa,WAAW,GAAG,GAO9B,GACL,uCAAuC,KAAK,KAAK,YAAY,EAC7D,CACA,IAAMI,EAAQD,EAAS,WACrB,GAAG,KAAK,YAAY,MACpBA,EAAS,SAAS,MACpB,EACMb,EAAUa,EAAS,SAASC,CAAK,EACnC,aAAcd,IAChB,KAAK,MAAMA,CAA0B,EACrC,KAAK,UAAU,OAAOA,CAA0B,EAEpD,SACE,KAAK,aAAa,WAAW,YAAY,GACzC,KAAK,aAAa,WAAW,YAAY,EACzC,CACA,IAAMe,EAAM,KAAK,QAAQ,EACnBD,EAAQD,EAAS,WAAWE,EAAKF,EAAS,SAAS,MAAM,EACzDb,EAAUa,EAAS,SAASC,CAAK,EACvC,KAAK,MAAMd,CAAO,CACpB,MA3BwC,CACtC,IAAMe,EAAM,GAAG,KAAK,YAAY,MAAMN,CAAQ,KACxCK,EAAQD,EAAS,WAAWE,EAAKF,EAAS,SAAS,MAAM,EACzDb,EAAUa,EAAS,SAASC,CAAK,EACnCd,GAAW,iBAAkBA,GAC/B,KAAK,MAAMA,CAAO,CAEtB,CAqBF,OAASgB,EAAK,CACZ,QAAQ,KAAK,yBAA0B,KAAK,aAAcA,CAAG,CAC/D,CACF,CACF,ECnIaV,GAAN,KAAgB,CAKrB,YAAY9B,EAAiC,CAH7C,KAAA,MAAqB,CAAC,EACtB,KAAA,SAAoC,KAGlC,KAAK,OAASA,CAChB,CAEA,IAAI,YAAiC,CACnC,IAAIgC,EAAY,KAAK,OACrB,KAAOA,GAAQA,aAAgBJ,IAC7BI,EAAOA,EAAK,OAEd,OAAOA,CACT,CAEA,OAAOS,EAA0BC,EAAyB,GAAU,CAClE,GAAI,CAAC,KAAK,OAAS,CAAC,KAAK,OAAQ,OACjC,IAAMC,EAA6B,CAAC,EAI9BC,EAAgC,CAAC,EAEvC,SAASC,EAAYC,EAAkB3C,EAAsB,CAC3D,OAAO2C,EAAS,WAAW,GAAG,EAC1B,GAAG3C,CAAI,GAAG2C,EAAS,MAAM,CAAC,CAAC,GAC3B,GAAG3C,CAAI,IAAI2C,CAAQ,EACzB,CAEA,QAAWA,KAAYL,EAAK,CAC1B,IAAM3G,EAAQ2G,EAAIK,CAAQ,EACpBC,EAAYxE,GAAiBuE,CAAQ,EAC3C,QAAWpK,KAAOqK,EAAW,CAC3B,IAAMC,EAAkBH,EAAYnK,EAAKgK,CAAc,EACvD,GAAI,uCAAuC,KAAKhK,CAAG,GACjD,GAAI,OAAOoD,GAAU,UAAYA,GAAS,KAAM,CAC9C,IAAMuD,EAAO,IAAIuC,GAAUlJ,EAAK,KAAK,MAAM,EAC3C2G,EAAK,UAAW,OAAOvD,EAAO4G,CAAc,EAC5CE,EAAiB,KAAKvD,CAAI,CAC5B,UACS3G,EAAI,WAAW,YAAY,EAAG,CACvC,IAAM2G,EAAO,IAAIuC,GAAUlJ,EAAK,KAAK,MAAM,EAC3C2G,EAAK,UAAW,OAAOvD,EAAO,EAAE,EAChC,KAAK,MAAM,KAAKuD,CAAI,CACtB,SAAW3G,EAAI,WAAW,YAAY,EAAG,CACvC,IAAM2G,EAAO,IAAIuC,GAAUlJ,EAAK,KAAK,MAAM,EAC3C,QAAWgF,KAAK5B,EAAOuD,EAAK,YAAY3B,EAAG5B,EAAM4B,CAAC,CAAC,EACnD,KAAK,MAAM,KAAK2B,CAAI,CACtB,SAAW,OAAOvD,GAAU,UAAYA,GAAS,KAAM,CACrD,IAAMuD,EAAO,IAAIuC,GAAUoB,EAAiB,KAAK,MAAM,EACvD,KAAK,MAAM,KAAK3D,CAAI,EACpB,OAAW,CAAC3B,EAAGD,CAAC,IAAK,OAAO,QAAQ3B,CAAK,EACvC,GAAI,OAAO2B,GAAM,UAAYA,GAAK,KAAM,CAatC,IAAMwF,EAAcJ,EAAYnF,EAAGsF,CAAe,EAClD,KAAK,OAAOvF,EAAGwF,CAAW,CAC5B,MACE5D,EAAK,YAAY3B,EAAGD,CAAC,CAG3B,MACEkF,EAAMjK,CAAG,EAAIoD,CAEjB,CACF,CAEA,GAAI,OAAO,KAAK6G,CAAK,EAAE,OAAQ,CAC7B,IAAMtD,EAAO,IAAIuC,GAAUc,EAAgB,KAAK,MAAM,EACtD,QAAWhK,KAAOiK,EAAOtD,EAAK,YAAY3G,EAAKiK,EAAMjK,CAAG,CAAC,EACzD,KAAK,MAAM,KAAK2G,CAAI,CACtB,CAEA,QAAWA,KAAQuD,EACjB,KAAK,MAAM,KAAKvD,CAAI,CAExB,CAEA,SAAkB,CAChB,OAAK,KAAK,MACH,KAAK,MAAM,IAAKA,GAASA,EAAK,QAAQ,CAAC,EAAE,KAAK,EAAE,EAD/B,EAE1B,CAeA,SAASoD,EAA0BC,EAAyB,GAAU,CAhHxE,IAAArI,EAiHI,GAAI,CAAC,KAAK,OAAS,CAAC,KAAK,OAAQ,OAEjC,IAAMsI,EAA6B,CAAC,EACpC,QAAWjK,KAAO+J,EAAK,CACrB,IAAM3G,EAAQ2G,EAAI/J,CAAG,EACjB,OAAOoD,GAAU,UAAYA,GAAS,OAC1C6G,EAAMjK,CAAG,EAAIoD,EACf,CAEA,IAAIuD,EAAO,KAAK,MAAM,KAAM6D,GAAMA,EAAE,eAAiBR,CAAc,EAC9DrD,IACHA,EAAO,IAAIuC,GAAUc,EAAgB,KAAK,MAAM,EAChD,KAAK,MAAM,KAAKrD,CAAI,GAGtB,IAAM9B,EAAO,IAAI,IAAI,OAAO,KAAKoF,CAAK,CAAC,EACvC,QAAWjK,KAAOiK,EAAOtD,EAAK,YAAY3G,EAAKiK,EAAMjK,CAAG,CAAC,EAEzD,GAAI2G,EAAK,WACP,QAAW8D,KAAe,OAAO,KAAK9D,EAAK,UAAU,EAC9C9B,EAAK,IAAI4F,CAAW,GAAG9D,EAAK,YAAY8D,CAAW,EAO5D,IAAMf,GAAQ/H,EAAA,KAAK,WAAL,KAAA,OAAAA,EAAe,MACzB,CAACgF,EAAK,SAAW+C,GAAO/C,EAAK,OAAO+C,CAAK,CAC/C,CAEA,WAAWU,EAA6B,CACtC,GAAI,CAAC,KAAK,OAAS,CAAC,KAAK,OAAQ,OAAO,KACxC,IAAIzD,EAAO,KAAK,MAAM,KAAMA,GAASA,EAAK,eAAiByD,CAAQ,EACnE,OAAKzD,IACHA,EAAO,IAAIuC,GAAUkB,EAAU,KAAK,MAAM,EAC1C,KAAK,MAAM,KAAKzD,CAAI,GAEfA,CACT,CAEA,QAAQ+D,EAAwC,CAC9C,GAAK,KAAK,MACV,QAAW/D,KAAQ,KAAK,MAAO,CAC7B,IAAMmC,EAAU4B,EAAW,IAAIrE,GAAqBM,EAAK,YAAY,CAAC,EAClEmC,GAASnC,EAAK,MAAMmC,CAAkB,CAC5C,CACF,CAEA,MAAM6B,EAAgC,CACpC,GAAI,CAAC,KAAK,MAAO,OACjB,GAAI,CAACA,EAAa,MAAM,MAAM,8BAA8B,EAC5D,IAAIC,EAAa,EACXC,EAAchB,GAClBA,EAAI,QAAQ,QAAS,QAAQ,EAAE,QAAQ,SAAU,MAAM,EAEzD,KAAK,MAAM,QAAQ,CAAClD,EAAM9C,IAAM,CAC9B,IAAM+F,EAAQ/F,EAAI+G,EACZ9B,EAAU6B,EAAYf,CAAK,EAC5Bd,IAEHnC,EAAK,aAAa,WAAW,GAAG,GAChCmC,aAAmB,kBAGV,YAAaA,EADtBnC,EAAK,MAAMmC,CAAO,EAGT,iBAAkBA,EACvBA,EAAQ,eAAiB+B,EAAWlE,EAAK,YAAY,EACvDiE,GAAc,EAEdjE,EAAK,MAAMmC,CAAO,EAEX,aAAcA,GACvBnC,EAAK,MAAMmC,CAAuB,EAEtC,CAAC,CACH,CAEA,OAAOgC,EAAyC,CAC1CA,aAAe,kBACjB,KAAK,SAAWA,EAChB,KAAK,MAAM,QAASnE,GAASA,EAAK,OAAOmE,EAAI,KAAM,CAAC,GAC3CA,aAAe,iBACxB,KAAK,MAAM,QAASnE,GAASA,EAAK,OAAOmE,CAAG,CAAC,CAEjD,CAEA,UAAiB,CACf,GAAI,KAAK,MACP,QAASjH,EAAI,EAAGA,EAAI,KAAK,MAAM,OAAQA,IACrC,KAAK,MAAMA,CAAC,EAAE,SAAS,EAI3B,KAAK,MAAQ,CAAC,EACd,KAAK,OAAS,KACd,KAAK,SAAW,IAClB,CACF,EC3LakH,EAAN,MAAMC,EAAY,CAwCvB,YACEC,EACAC,EAA8B,KAC9BtB,EAAQ,EACR,CA3CF,KAAA,UAAY,GACZ,KAAA,mBAAqB,GAIrB,KAAA,YAAc,GACd,KAAA,KAAO,cACP,KAAA,OAA6B,KAO7B,KAAA,uBAAyB,GAIzB,KAAA,mBAAqB,IAAI,IAGzB,KAAA,kBAAoB,IAAI,IACxB,KAAA,qBAAuB,GACvB,KAAA,wBAA0B,GAE1B,KAAA,SAAW,IAAIuB,GAAY,IAAI,EAC/B,KAAA,OAAS,IAAI/B,GAAU,IAAI,EAC3B,KAAA,WAAa,IAAIxB,GAAc,IAAI,EACnC,KAAA,WAAkC,KAClC,KAAA,OAAkB,CAAC,EACnB,KAAA,QAEW,KACX,KAAA,aAAe,IAAI,IACnB,KAAA,SAAiC,CAAC,EAClC,KAAA,UAAkC,CAAC,EACnC,KAAA,IAA+B,KA9DjC,IAAAjG,EAAAC,EAsEIqJ,EAAgB9H,GAAU8H,CAAa,EACvC/F,GAAS+F,CAAa,EACtBA,EAAc,MAAQA,EAAc,OAAS,CAAC,EAC9C,KAAK,OAASC,EACd,KAAK,QAAUvF,GAAWsF,CAAa,EACvCA,EAAgBhE,GAAagE,CAAa,EAE1C,KAAK,KAAOtJ,EAAAsJ,EAAsB,OAAtB,KAAAtJ,EAA8B,KAC1C,KAAK,SAAWsJ,EAAc,UAAY,CAAC,EAC3C,KAAK,UAAYA,EAAc,WAAa,CAAC,EAE7C,IAAMG,EAAW,IAAGxJ,EAAA,KAAK,SAAL,KAAA,OAAAA,EAAa,MAAM,IAAIgI,CAAK,GAC1CjG,EAAM,KAAK,UAAUsH,EAAc,OAAS,CAAC,EAAG,CAACI,EAAItG,IACzD,OAAOA,GAAM,WAAaqG,EAAWrG,CACvC,EACA,KAAK,OAASrB,GAAW0H,EAAWzH,CAAG,EAEvC,KAAK,WAAY,SAAS,GAAG,KAAK,OAAO,IAAI,KAAK,MAAM,EAAE,EACtDsH,EAAc,aAChBA,EAAc,YAAY,KAAMA,CAAa,EAE/C,KAAK,MAAMA,CAAa,EAExB,IAAMK,EAAYL,EAAsB,KAAK,OAAO,EAEhDK,GAAY,OACV,OAAOA,GAAa,WACtB,KAAK,uBAAuBA,CAAQ,EAEpC,KAAK,SAAU,OAAO,MAAM,QAAQA,CAAQ,EAAIA,EAAW,CAACA,CAAQ,CAAC,GAGzE,KAAK,OAAO,MAAQ,KAAK,OAAO,KAAK,IAAI,CAC3C,CAEA,uBAAuB5K,EAAkC,CACvD,IAAIe,EAAgB,IAAM,CACxB,GAAI,CAAA,KAAK,UACT,GAAI,CACF,IAAM8J,EAAQ7K,EAAGe,CAAQ,EACzB,KAAK,SAAU,OAAO,MAAM,QAAQ8J,CAAK,EAAIA,EAAQ,CAACA,CAAK,CAAC,CAC9D,OAASC,EAAO,CACd,KAAK,aAAaA,CAAK,CACzB,CACF,EACA/J,EAAU,YAAc,KACxBA,EAAU,MAAQ,SAAS,KAAK,OAAO,IAAI,KAAK,MAAM,YAKtD,IAAMgK,EAA8B,CAAC,EACrChK,EAAU,YAAerB,GAAwB,CAC/CqL,EAAS,KAAKrL,CAAO,EACrB,KAAK,iBAAmB,IAAM,CAC5B,QAAWsH,KAAuB+D,EAAU/D,EAAoB,EAChE+D,EAAS,OAAS,EAClBhK,EAAW,IACb,EAMK,KAAK,yBACR,KAAK,uBAAyB,GAC9B,KAAK,QAAQ,eAAgB,IAAM,CAxI3C,IAAAE,GAyIUA,EAAA,KAAK,mBAAL,MAAAA,EAAA,KAAA,IAAA,EACA,KAAK,iBAAmB,MAC1B,CAAC,EAEL,EACAF,EAAS,CACX,CAEA,gBAAiB,CAEf,IAAMmD,EAAOtF,GAAQ,SAAS,KAAK,OAAO,EACtC,SAAS,gBAFQ,6BAEsB,KAAK,OAAO,EACnD,SAAS,cAAc,KAAK,OAAO,EAIvC,GAFA,KAAK,WAAasF,EAEd,KAAK,QACP,QAAW5E,KAAO,KAAK,QAAS,KAAK,WAAWA,CAAgB,EAGlE,OAAI,KAAK,YACP,OAAO,OAAO,KAAK,WAAW,KAAM,EAAE,QAAS6H,GAASA,EAAK,OAAO,CAAC,EAEhEjD,CACT,CAKA,WAAWF,EAA4B,CACrC,GAAI,CAAC,KAAK,YAAc,KAAK,aAAa,IAAIA,CAAS,EAAG,OAC1D,KAAK,aAAa,IAAIA,CAAS,EAC/B,IAAIhE,EAAWc,GAAc,CAzKjC,IAAAG,EAAAC,EAyKoC,OAAAA,GAAAD,EAAA,KAAK,UAAL,KAAA,OAAAA,EAAe+C,CAAAA,IAAf,KAAA,OAAA9C,EAAA,KAAAD,EAA4BH,EAAO,IAAA,CAAA,EACnE,KAAK,WAAW,iBAAiBkD,EAAWhE,CAAE,EAC9C,KAAK,QAAQ,eAAiBwB,GAAM,CA3KxC,IAAAP,GA4KMA,EAAAO,EAAE,aAAF,MAAAP,EAAc,oBAAoB+C,EAAWhE,CAAAA,EAC7CA,EAAK,IACP,CAAC,CACH,CAEA,UAAiB,CAjLnB,IAAAiB,EAAAC,EAAAC,EAAAoH,EAkLQ,KAAK,YACT,KAAK,UAAY,GAOZ,KAAK,qBACR,KAAK,mBAAqB,IAC1BrH,GAAAD,EAAA,KAAK,QAAO,eAAZ,MAAAC,EAAA,KAAAD,EAA2B,KAAM,IAAM,CAAC,CAAA,GAGtC,KAAK,UACP,KAAK,SAAS,SAAS,EAGrB,KAAK,SACP,KAAK,OAAO,MAAO,QAASgF,GAASA,EAAK,OAAO,CAAC,EAClD,KAAK,OAAO,SAAS,GAGnB,KAAK,YACP,KAAK,WAAW,SAAS,GAI3BsC,GAAApH,EAAA,KAAK,QAAO,SAAZ,MAAAoH,EAAA,KAAApH,EAAqB,IAAA,EAErB,KAAK,WAAa,KAClB,KAAK,OAAS,CAAC,EACf,KAAK,QAAU,KACf,KAAK,SAAW,CAAC,EACjB,KAAK,UAAY,CAAC,EAClB,KAAK,OAAS,KAChB,CACA,MAAMqF,EAAsB,CAC1BrE,EAAM,KAAK,SAAUqE,EAAK,QAAQ,EAClCrE,EAAM,KAAK,UAAWqE,EAAK,SAAS,EACpC,KAAK,kBAAkBA,EAAK,UAAU,EAEtC,IAAM7B,EAAO,OAAO,KAAK6B,CAAI,EAC7B,QAASrD,EAAI,EAAGA,EAAIwB,EAAK,OAAQxB,IAAK,CACpC,IAAM6H,EAAcrG,EAAKxB,CAAC,EACpBT,EAAS8D,EAAawE,CAAW,EAErC,CACE,IACA,cACA,OACA,WACA,YACA,aACA,QACA,KAAK,OACP,EAAE,SAASA,CAAW,IAGtB,CACE,UACA,YACA,WACA,kBACA,YACA,kBACA,YACA,UACF,EAAE,SAASA,CAAW,EAEtB,KAAK,QAAQA,EAAY,UAAU,CAAC,EAAoBtI,CAAK,EACpDsI,EAAY,WAAW,IAAI,EACpC,KAAK,SACHA,EAAY,UAAU,CAAC,EAAE,YAAY,EACrCtI,CACF,EACSsI,IAAgB,UACzB,KAAK,QAAUtI,EACNsI,IAAgB,SAUrB,OAAOtI,GAAU,UAAY,OAAOA,GAAU,aAChD,KAAK,WAAY,SAASA,CAAK,EAGjC,KAAK,WAAY,IAAIsI,EAAatI,CAAK,EAE3C,CACI8D,EAAK,OACP,KAAK,OAAO,OACVA,EAAK,OAAS,CAAC,EACf,IAAI,GAAG,KAAK,OAAO,IAAI,KAAK,MAAM,EAAE,EACtC,CAEJ,CAcA,MAAMyE,EAAiC,CApSzC,IAAAhK,EAqSI,IAAIwD,EAAehC,GAAUwI,CAAU,EACvCxG,EAAQ,MAAQA,EAAQ,OAAS,CAAC,EAClCA,EAAU8B,GAAa9B,CAAO,EAU9B,IAAMyG,EAAUzG,EAAQ,KAAK,OAAO,EACpC,GAAI,OAAOyG,GAAY,YACrBjK,EAAA,KAAK,mBAAL,MAAAA,EAAA,KAAA,IAAA,EACA,KAAK,iBAAmB,OACxB,KAAK,uBAAuBiK,CAAO,UAC1BA,GAAW,KAAM,CAC1B,IAAMC,EAAO,MAAM,QAAQD,CAAO,EAAIA,EAAU,CAACA,CAAO,EACxD,KAAK,SAAS,OAAOC,EAAM,CAAC,CAAC,KAAK,WAAY,EAAI,CACpD,CAEI1G,EAAQ,UAAUtC,EAAM,KAAK,SAAUsC,EAAQ,QAAQ,EACvDA,EAAQ,WAAWtC,EAAM,KAAK,UAAWsC,EAAQ,SAAS,EAC9D,KAAK,kBAAkBA,EAAQ,UAAU,EAEzC,KAAK,OAAO,SAASA,EAAQ,OAAS,CAAC,EAAG,IAAI,KAAK,OAAO,IAAI,KAAK,MAAM,EAAE,EAK3E,IAAM2G,EAAY,GAAG,KAAK,OAAO,IAAI,KAAK,MAAM,GAC1CC,EAAW,CACf,IACA,cACA,OACA,WACA,YACA,aACA,QACA,KAAK,OACP,EACMC,EAAW,CACf,UACA,YACA,WACA,kBACA,YACA,kBACA,YACA,UACF,EACMC,EAAO,IAAI,IAAY,CAAC,OAAO,CAAC,EAClCC,EAA8D,KAElE,KAAK,QAAU,CAAC,EAChB,QAAWlM,KAAO,OAAO,KAAKmF,CAAO,EAAG,CACtC,GAAI4G,EAAS,SAAS/L,CAAG,GAAKgM,EAAS,SAAShM,CAAG,GAAKA,IAAQ,UAC9D,SACF,IAAMoD,EAAQ+B,EAAQnF,CAAG,EACrBA,EAAI,WAAW,IAAI,GAAK,OAAOoD,GAAU,WAC3C,KAAK,SAASpD,EAAI,UAAU,CAAC,EAAE,YAAY,EAAgBoD,CAAK,EAEhEpD,IAAQ,UACP,OAAOoD,GAAU,UAAY,OAAOA,GAAU,YAE/C8I,EAAY9I,GAEZ,KAAK,WAAY,IAAIpD,EAAKoD,CAAK,EAC/B6I,EAAK,IAAIjM,CAAG,EAEhB,CAMA,GAAI,OAAOkM,GAAc,WAAY,CACnC,IAAMC,EAAcD,EACpB,KAAK,WAAY,IACf,QACCzK,GAAuB,GAAGqK,CAAS,IAAIK,EAAY1K,CAAQ,CAAC,EAC/D,CACF,MACE,KAAK,WAAY,IACf,QACAyK,EAAY,GAAGJ,CAAS,IAAII,CAAS,GAAKJ,CAC5C,EAGF,GAAI,KAAK,WAAY,MACnB,QAAWnJ,KAAQ,OAAO,KAAK,KAAK,WAAY,KAAK,EAC9CsJ,EAAK,IAAItJ,CAAI,GAAG,KAAK,WAAY,OAAOA,CAAI,EAIrD,GAAI,KAAK,QACP,QAAW3C,KAAO,KAAK,QAAS,KAAK,WAAWA,CAAgB,CAEpE,CAMA,aAAawL,EAAsB,CACjC,IAAI5G,EAA2B,KAC/B,KAAOA,GAAM,CACX,GAAIA,EAAK,OAAO,MAAO,CACrB,IAAMwH,EAAWxH,EACjBA,EAAK,OAAO,MAAMwH,EAAUZ,EAAO,IAAM,CACvCY,EAAS,SAAS,OAAO,CAAC,CAAC,CAC7B,CAAC,EACD,MACF,CACAxH,EAAOA,EAAK,MACd,CACA,QAAQ,MAAM,8CAA+C4G,CAAK,CACpE,CAEA,SACE7I,EACAgF,EACM,CACN,KAAK,QAAU,KAAK,SAAW,CAAC,EAEhC,IAAMnD,EAAU,KAAK,QAAQ7B,CAAI,EAC7B,OAAO6B,GAAY,WACrB,KAAK,QAAQ7B,CAAI,EAAI,CAACnB,EAAcoD,IAAsB,CACxDJ,EAAShD,EAAOoD,CAAI,EACpB+C,EAASnG,EAAOoD,CAAI,CACtB,EAEA,KAAK,QAAQjC,CAAI,EAAIgF,CAEzB,CAEA,QAAiChF,EAASgF,EAA4B,CACpE,IAAMnD,EAAU,KAAK,OAAO7B,CAAI,EAEhC,GAAI,OAAO6B,GAAY,WAAY,CACjC,IAAM6H,GAAY,IAAIvK,IAAgB,CACnC0C,EAAqB,GAAG1C,CAAI,EAC5B6F,EAAsB,GAAG7F,CAAI,CAChC,GAIA,GAAI,CACF,OAAO,eAAeuK,EAAU,SAAU,CACxC,MAAO,KAAK,IACT7H,EAAqB,OACrBmD,EAAsB,MACzB,EACA,aAAc,EAChB,CAAC,CACH,OAAQ5G,EAAA,CAER,CACA,KAAK,OAAO4B,CAAI,EAAI0J,CACtB,MACE,KAAK,OAAO1J,CAAI,EAAIgF,CAExB,CACA,SAAuB,CACrB,IAAI2B,EAAoB,KACxB,KAAOA,GAAQA,aAAgB0B,IAAe1B,EAAK,QACjDA,EAAOA,EAAK,OAEd,OAAOA,CACT,CASA,kBAAkBgD,EAAgD,CAxdpE,IAAA3K,EAydI,GAAK2K,EACL,QAAWtM,KAAO,OAAO,KAAKsM,CAAS,EAAG,CACxC,IAAMC,EAAOD,EAAUtM,CAAG,EACpBwM,EAAW,KAAK,mBAAmB,IAAIxM,CAAG,EAC5CwM,GACF7K,EAAA6K,EAAS,SAAT,MAAA7K,EAAA,KAAA6K,EAAkBD,EAAK,KAAA,EACd,KAAK,WACd,KAAK,mBAAmBvM,EAAKuM,CAAI,GAEjC,KAAK,kBAAkB,IAAIvM,EAAKuM,CAAI,EACpC,KAAK,yBAAyB,EAElC,CACF,CAEA,mBAAmBvM,EAAauM,EAA0B,CACxD,IAAMC,EAAWD,EAAK,OAAO,KAAMA,EAAK,KAAK,GAAK,CAAC,EACnD,KAAK,mBAAmB,IAAIvM,EAAKwM,CAAQ,EACzC,KAAK,4BAA4B,CACnC,CAKA,0BAAiC,CAC3B,KAAK,uBACT,KAAK,qBAAuB,GAC5B,KAAK,QAAQ,QAAS,IAAM,CAC1B,GAAI,KAAK,kBAAkB,OAAS,EAAG,OACvC,IAAMpK,EAAU,KAAK,kBACrB,KAAK,kBAAoB,IAAI,IAC7BA,EAAQ,QAAQ,CAACmK,EAAMvM,IAAQ,KAAK,mBAAmBA,EAAKuM,CAAI,CAAC,CACnE,CAAC,EACH,CAMA,6BAAoC,CAC9B,KAAK,0BACT,KAAK,wBAA0B,GAC/B,KAAK,QAAQ,eAAgB,IAAM,CACjC,KAAK,mBAAmB,QAASC,GAAU,CApgBjD,IAAA7K,EAogBoD,OAAAA,EAAA6K,EAAS,UAAT,KAAA,OAAA7K,EAAA,KAAA6K,CAAAA,CAAAA,CAAoB,EAClE,KAAK,mBAAmB,MAAM,CAChC,CAAC,EACH,CASA,YACExM,EACe,CACf,IAAI4E,EAA2B,KAC/B,KAAOA,GAAM,CACX,IAAM4H,EAAW5H,EAAK,mBAAmB,IAAI5E,CAAG,EAChD,GAAIwM,EAAU,OAAOA,EACrB5H,EAAOA,EAAK,MACd,CAEF,CAEA,WAAWjC,EAAmB,CAC5B,IAAIiC,EAA2B,KAC/B,KAAOA,IAAS,CAACA,EAAK,UAAY,CAAC,OAAO,OAAOA,EAAK,SAAUjC,CAAI,IAClEiC,EAAOA,EAAK,OAEd,OAAOA,GAAQA,EAAK,SAAWA,EAAK,SAASjC,CAAI,EAAI,MACvD,CAEA,WAAWA,EAAcS,EAAY,CACnC,KAAK,SAAW,KAAK,UAAY,CAAC,EAClC,KAAK,SAAST,CAAI,EAAIS,CACxB,CAEA,YAAYT,EAAmB,CAC7B,OAAO,KAAK,UAAY,KAAK,UAAUA,CAAI,EAAI,MACjD,CAEA,YAAY3C,EAAaoD,EAAY,CACnC,KAAK,UAAY,KAAK,WAAa,CAAC,EACpC,KAAK,UAAUpD,CAAG,EAAIoD,CACxB,CAEA,aAAsB,CACpB,GAAI,CAAC,KAAK,QAAU,CAAC,KAAK,SAAU,MAAO,GAC3C,IAAIyG,EAAM,KAAK,OAAO,QAAQ,EAC9B,OAAAA,GAAO,KAAK,SAAS,MAClB,IAAK4C,GAAWA,aAAiBzB,GAAcyB,EAAM,YAAY,EAAI,EAAG,EACxE,KAAK,EAAE,EACH5C,CACT,CAEA,cAAuB,CACrB,GAAI,CAAC,KAAK,UAAY,CAAC,KAAK,WAAY,MAAO,GAC/C,IAAMpF,EAAa,KAAK,WAAW,aAAa,EAGhD,GAAKlF,GAA+B,SAAS,KAAK,OAAO,EACvD,MAAO,IAAI,KAAK,OAAO,GAAGkF,CAAU,IAEtC,IAAMmH,EAAU,KAAK,SAAS,aAAa,EAC3C,MAAO,IAAI,KAAK,OAAO,GAAGnH,CAAU,IAAImH,CAAO,KAAK,KAAK,OAAO,GAClE,CAEA,MAAMrE,EAAyBR,EAAmC,CAChE,GAAI,CAACQ,EAAY,MAAM,IAAI,MAAM,0BAA0B,EAa3D,GAXEoB,IACA,CAAC5B,GACD,KAAK,SAAW,MAChBQ,EAAW,WAAW,OAAS,GAE/B,QAAQ,KACN,wNACF,EAEF,KAAK,WAAaA,EAEd,KAAK,QACP,QAAWvH,KAAO,KAAK,QAAS,KAAK,WAAWA,CAAgB,EAsBlE,GAnBI,KAAK,UACP,KAAK,SAAS,MAAM,QAAQ,CAACyM,EAAO,IAAM,CACxC,IAAMC,EAAYnF,EAAW,WAAW,CAAC,EACpCmF,IACDD,aAAiBzB,GACnByB,EAAM,MAAMC,CAAwB,EAIpCD,EAAM,QAAUC,EAEpB,CAAC,EAQC3F,EAAU,CACZ,IAAM2C,EAAQ3C,EAAS,MACnB2C,GACF,KAAK,eAAelD,GAAgBkD,EAAM,SAAU,IAAI,GAAK,CAAC,CAClE,CAEA,KAAK,OAAO,OAAS,KAAK,OAAO,MAAM,IAAI,CAC7C,CAEA,eAAegB,EAAwC,CArnBzD,IAAA/I,EAunBI,IADAA,EAAA,KAAK,SAAL,MAAAA,EAAa,QAAQ+I,CAAAA,EACjB,KAAK,SACP,QAAW+B,KAAS,KAAK,SAAS,MAC5BA,aAAiBzB,IAAayB,EAAM,eAAe/B,CAAU,CAGvE,CAEA,OACEnD,EAC0B,CAC1B,IAAMoF,EAAU,KAAK,eAAe,EACpCpF,EAAW,YAAYoF,CAAO,EAC9B,KAAK,OAAO,OAAS,KAAK,OAAO,MAAM,IAAI,EAC3C,IAAI5F,EAAW,KAAK,QAAQ,EAAE,OAAO,SAC/BuC,EAAO/B,EAAW,YAAY,EAC9BV,EAAcyC,aAAgB,WAAaA,EAAO,SAAS,KACjE,OAAAvC,IAAAA,EAAaH,GAAeC,CAAW,GACvC,KAAK,OAAO,OAAOE,CAA4B,EAC/C,KAAK,SAAS,MAAM,QAAS0F,GAAU,CACrC,GAAIA,aAAiBzB,IAAeyB,EAAM,QAAS,CACjD,IAAM3B,EAAM2B,EAAM,QAAS,KAAK,QAAQ,CAAC,EACzC3B,GAAO2B,EAAM,OAAO3B,CAAG,CACzB,MACE2B,EAAM,OAAOE,CAAO,CAExB,CAAC,EACMA,CACT,CAEA,QAAS,CACP,GAAI,KAAK,OACP,KAAK,OAAO,SAAS,OAAO,IAAI,MAC3B,CAGL,IAAMC,EAAO,IAAM,CA1pBzB,IAAAjL,GA2pBQA,EAAA,KAAK,aAAL,MAAAA,EAAiB,OAAA,EACjB,KAAK,SAAS,CAChB,EACA,GAAI,KAAK,OAAO,cAAgB,KAAK,WAAY,CAC/C,IAAIkL,EAAS,GACPC,EAAO,IAAM,CACZD,IACHA,EAAS,GACTD,EAAK,EAET,EAKMG,EAAmB,KAAK,OAAO,aACrC,KAAK,mBAAqB,GAC1BA,EAAiB,KAAMD,CAAI,EACtBC,EAA8B,OAAS,GAAK,CAACF,EAAQC,EAAK,EACtDnE,IAAW,CAACkE,GACnB,WAAW,IAAM,CACVA,GACH,QAAQ,KACN,gKACF,CACJ,EAAG,GAAI,CAEX,MACED,EAAK,CAET,CACF,CACF,ECxrBaI,GAAN,KAAe,CASpB,YAAYC,EAA8B3F,EAAqB,CAR/D,KAAA,KAAO,WAGP,KAAA,YAAc,GAMZ,KAAK,OAASA,EACd,KAAK,KAAO2F,IAAgB,GAAK,SAAW,OAAOA,CAAW,CAChE,CACA,gBAAiB,CACf,IAAIN,EACJ,GAAIrH,GAAO,KAAK,IAAI,EAAG,CACrB,IAAM4H,EAAM,SAAS,cAAc,UAAU,EAC7CA,EAAI,UAAY,KAAK,KAAK,KAAK,EAE/BA,EAAI,QAAQ,iBAAiB,GAAG,EAAE,QAASC,GAAO,CAChD,QAAWtF,KAAQ,MAAM,KAAKsF,EAAG,UAAU,EACrC,OAAO,KAAKtF,EAAK,IAAI,EACvBsF,EAAG,gBAAgBtF,EAAK,IAAI,EAE5B,oCAAoC,KAAKA,EAAK,IAAI,GAClD,mBAAmB,KAAKA,EAAK,KAAK,GAElCsF,EAAG,aAAatF,EAAK,KAAM,GAAG,CAGpC,CAAC,EACD8E,EAAUO,EAAI,QAAQ,YAAc,SAAS,eAAe,EAAE,CAChE,MACEP,EAAU,SAAS,eAAe,KAAK,IAAI,EAE7C,OAAA,KAAK,QAAUA,EACRA,CACT,CAOA,QAAQM,EAAoC,CA/C9C,IAAAtL,EAgDI,IAAMkK,EACJoB,IAAgB,GAAK,SAA8B,OAAOA,CAAW,EACvE,GAAIpB,IAAS,KAAK,MAAQ,KAAK,QAAS,OACxC,IAAMuB,EAAU9H,GAAO,KAAK,IAAI,EAEhC,GADA,KAAK,KAAOuG,EACR,CAAC,KAAK,QAAS,OACnB,GAAI,CAACuB,GAAW,CAAC9H,GAAOuG,CAAI,GAAK,KAAK,QAAQ,WAAa,EAAG,CAC5D,KAAK,QAAQ,UAAYA,EACzB,MACF,CACA,IAAMxI,EAAM,KAAK,QACXgK,EAAQ,KAAK,eAAe,GAClC1L,EAAA0B,EAAI,aAAJ,MAAA1B,EAAgB,aAAa0L,EAAOhK,CAAAA,CACtC,CAEA,UAAiB,CACf,KAAK,QAAU,OACf,KAAK,KAAO,EACd,CAEA,cAAuB,CACrB,OAAI,KAAK,OAAS,SAAiB,UAK5BiC,GAAO,KAAK,IAAI,EACnBC,GAAmB,KAAK,IAAI,EAC5BG,GAAW,KAAK,IAAI,CAC1B,CAEA,OAAO4H,EAA2D,CAChE,IAAMX,EAAU,KAAK,eAAe,EACpCW,EAAQ,YAAYX,CAAO,CAC7B,CACF,ECvEMY,GAAsB,IAAI,IAGzB,SAASC,IAA8B,CAC5CD,GAAoB,MAAM,CAC5B,CAEO,IAAMpC,GAAN,KAAkB,CAKvB,YAAY7D,EAAqB,CAJjC,KAAA,MAAoB,CAAC,EAErB,KAAA,SAAmB,EAGjB,KAAK,MAAQA,CACf,CAEA,YAAYnC,EAAiD,CAC3D,OAAO,OAAOA,GAAY,UAAYA,IAAY,KAC9C,IAAI4F,EAAY5F,EAAS,KAAK,MAAO,KAAK,UAAU,EACpD,IAAI6H,GAAS7H,GAAW,KAAO,GAAK,OAAOA,CAAO,EAAG,KAAK,KAAK,CACrE,CAUA,mBAAmByE,EAA4B,CAC7C,IAAMkB,EAAM,KAAK,MAAM,WACvB,GAAI,CAACA,EAAK,OAAO,KACjB,QAASjH,EAAI+F,EAAO/F,EAAI,KAAK,MAAM,OAAQA,IAAK,CAC9C,IAAM4J,EAAO,KAAK,MAAM5J,CAAC,EACnBsJ,EAAKM,aAAgB1C,EAAc0C,EAAK,WAAaA,EAAK,QAChE,GAAIN,GAAMA,EAAG,aAAerC,EAAK,OAAOqC,CAC1C,CACA,OAAO,IACT,CAEA,gBAAgBvI,EAAgBgF,EAAe,CAC7C,GAAI,CAAC,KAAK,OAAS,CAAC,KAAK,MAAM,WAAY,OAC3C,IAAMkB,EAAM,KAAK,MAAM,WAEjBqC,EAAKvI,aAAgBmG,EAAcnG,EAAK,WAAaA,EAAK,QAChE,GAAI,CAACuI,EAAI,OAMT,IAAMO,EAAM,KAAK,mBAAmB9D,EAAQ,CAAC,EACzCuD,IAAOO,GAAK5C,EAAI,aAAaqC,EAAIO,CAAG,CAC1C,CAEA,gBAAgBC,EAAiBC,EAAiB,CAChD,GAAI,CAAC,KAAK,OAAS,CAAC,KAAK,MAAM,WAAY,OAC3C,IAAMtG,EAAS,KAAK,MAAM,WAEpBuG,EAAIF,aAAiB5C,EAAc4C,EAAM,WAAaA,EAAM,QAC5DG,EAAIF,aAAiB7C,EAAc6C,EAAM,WAAaA,EAAM,QAClE,GAAI,CAACC,GAAK,CAACC,EAAG,OAEd,IAAMC,EAAQF,EAAE,YACVG,EAAQF,EAAE,YAEhBxG,EAAO,aAAauG,EAAGG,CAAK,EAC5B1G,EAAO,aAAawG,EAAGC,CAAK,CAC9B,CAEA,OAAOE,EAAwBC,EAAY,GAAMC,EAAS,GAAa,CAnFzE,IAAAxM,EAAAC,EAAAC,EAAAoH,EA6FI,GAAI,KAAK,MAAM,KAAMwE,GAASA,EAAK,WAAW,EAAG,CAC/C,IAAMpF,EAAW,KAAK,MAAM,OAAQoF,GAAS,CAACA,EAAK,WAAW,EACxDW,EAAa,KAAK,MAAM,OAAQX,GAASA,EAAK,WAAW,EAC/D,KAAK,MAAQpF,EAAS,OAAO+F,CAAU,CACzC,CAEA,IAAMC,EAAW,KAAK,MAAM,MAAM,EAQ5BC,EAAQ,IAAI,IAClB,QAAWb,KAAQY,EAEfZ,aAAgB1C,GAChB0C,EAAK,MAAQ,MACbA,EAAK,MAAQ,QACb,CAACA,EAAK,aACN,CAACA,EAAK,oBAENa,EAAM,IAAIb,EAAK,IAAKA,CAAI,EAIxB,CAACU,GAAU,KAAK,MAAM,cACxBvM,GAAAD,EAAA,KAAK,MAAM,SAAX,KAAA,OAAAA,EAAmB,eAAnB,MAAAC,EAAA,KAAAD,EAAkC,KAAK,MAAOsM,CAAAA,GAEhD,IAAMM,EAAS,IAAI,IAAcF,CAAQ,EACnCG,EAAU,IAAI,IAKhBC,EAAsB,EACpBC,EACJ/F,IAAW0F,EAAS,OAAS,EACzBJ,EAAO,SAAWI,EAAS,OAC3B,GAGN,QAASxK,EAAI,EAAGA,EAAIoK,EAAO,OAAQpK,IAAK,CACtC,IAAM0H,EAAQ0C,EAAOpK,CAAC,EAChB8K,EAAQ,OAAOpD,GAAU,UAAYA,IAAU,KAC/CvL,EAAM2O,EAASpD,EAAc,KAAO,OACpCqD,EAAMD,EAAQhJ,GAAW4F,CAAsB,EAAI,OAKzD,GAJI5C,IAAWgG,GAAS3O,IAAQ,QAAWyO,IAIvCzO,IAAQ,OAAW,CACrB,IAAM6O,EAASP,EAAM,IAAItO,CAAG,EAC5B,GAAI6O,aAAkB9D,GAAe8D,EAAO,UAAYD,EAAK,CAC3DN,EAAM,OAAOtO,CAAG,EAChB,IAAM8O,EAAM,KAAK,MAAM,QAAQD,CAAM,EACrC,GAAIC,IAAQjL,GAAKiL,GAAO,EAAG,CACzB,IAAMC,EAAW,CAAC,CAACF,EAAO,QAC1B,KAAK,KAAKC,EAAKjL,EAAGkL,EAAW,GAAQb,EAAW,EAAI,CACtD,CACAW,EAAO,OAAS,KAAK,MACrBA,EAAO,MAAMtD,CAAsB,EACnCiD,EAAQ,IAAIK,CAAM,EAClB,QACF,CAGF,SAAWF,EAAO,CAIhB,IAAMK,EAAK,KAAK,MAAMnL,CAAC,EACvB,GACEmL,aAAcjE,GACdiE,EAAG,KAAO,MACVA,EAAG,UAAYJ,GACfL,EAAO,IAAIS,CAAE,GACb,CAACR,EAAQ,IAAIQ,CAAE,GACf,CAACA,EAAG,aACJ,CAACA,EAAG,mBACJ,CACAA,EAAG,OAAS,KAAK,MACjBA,EAAG,MAAMzD,CAAsB,EAC/BiD,EAAQ,IAAIQ,CAAE,EACd,QACF,CACF,KAAO,CAKL,IAAMA,EAAK,KAAK,MAAMnL,CAAC,EACvB,GACEmL,aAAchC,IACduB,EAAO,IAAIS,CAAE,GACb,CAACR,EAAQ,IAAIQ,CAAE,GACf,CAACA,EAAG,YACJ,CACAA,EAAG,QAAQzD,GAAS,KAAO,GAAMA,CAAyB,EAC1DiD,EAAQ,IAAIQ,CAAE,EACd,QACF,CACF,CAEAR,EAAQ,IAAI,KAAK,OAAOjD,EAAO1H,EAAGqK,EAAW,GAAM,EAAI,CAAC,CAC1D,CAOA,IAAMe,EAAS,KAAK,MAAM,MAAMhB,EAAO,MAAM,EAC7C,QAAWrJ,KAAQqK,EACZrK,EAAK,aAAa,KAAK,OAAOA,EAAMsJ,EAAW,EAAI,EAQ1D,GANAI,EAAM,QAAS1J,GAAS,KAAK,OAAOA,EAAMsJ,EAAW,EAAI,CAAC,EAOxDvF,IACA0F,EAAS,OAAS,GAClBI,EAAsB,GACtBC,EACA,CACA,IAAMQ,EAAS,KAAK,MAAM,OAC1B,GAAI,CAAC3B,GAAoB,IAAI2B,CAAM,EAAG,CACpC3B,GAAoB,IAAI2B,CAAM,EAC9B,IAAMC,EAAM,4KAAuK,KAAK,MAAM,OAAO,MAAMV,CAAmB,gBAAgBA,IAAwB,EAAI,GAAK,GAAG,IAClR,QAAQ,KAAKU,CAAG,CAClB,CACF,CAEKhB,IAAQlF,GAAApH,EAAA,KAAK,MAAM,SAAX,KAAA,OAAAA,EAAmB,SAAnB,MAAAoH,EAAA,KAAApH,EAA4B,KAAK,KAAA,CAChD,CAEA,OACE0J,EACA3B,EACAsE,EAAY,GACZC,EAAS,GACT9F,EAAW,GACD,CACV,IAAM+G,EAAS,KAAK,MAAM,OACpBC,EACJ,OAAOzF,GAAU,UACjB,OAAO,MAAMA,CAAK,GAClBA,EAAQ,GACRA,EAAQwF,EACJA,EACAxF,EACA6D,EAAO,KAAK,YAAYlC,CAAK,EAQnC,GAHAkC,EAAK,YAAc,CAACpF,EACpB,KAAK,MAAM,OAAOgH,EAAY,EAAG5B,CAAI,EAEjCA,aAAgB1C,EAAa,CAE/B0C,EAAK,OAAO,QAAUA,EAAK,OAAO,OAAOA,CAAI,EAE7C,IAAMlG,EAAa,KAAK,MAAM,WAC9B,GAAI2G,GAAa3G,EACf,GAAIkG,EAAK,QAAS,CAChB,IAAMlG,EAAakG,EAAK,QAAS,KAAK,MAAM,QAAQ,CAAC,EACrDlG,GAAckG,EAAK,OAAOlG,CAAU,CACtC,KAAO,CACL,IAAM+H,EAAU7B,EAAK,eAAe,EAI9BC,EAAM,KAAK,mBAAmB2B,EAAa,CAAC,EAClD9H,EAAW,aAAa+H,EAAS5B,CAAG,EACpC,IAAMpE,EAAO/B,EAAW,YAAY,EAC9BV,EAAcyC,aAAgB,WAAaA,EAAO,SAAS,KAC3DvC,EAAWH,GAAeC,CAAW,EAC3C4G,EAAK,OAAO,OAAO1G,CAA4B,EAC/C0G,EAAK,OAAO,OAASA,EAAK,OAAO,MAAMA,CAAI,EAC3CA,EAAK,SAAS,MAAM,QAAShB,GAAU,CACrC,GAAIA,aAAiB1B,GAAe0B,EAAM,QAAS,CACjD,IAAM3B,EAAM2B,EAAM,QAASA,EAAM,QAAQ,CAAC,EAC1C3B,GAAO2B,EAAM,OAAO3B,CAAG,CACzB,MACE2B,EAAM,OAAO6C,CAAO,CAExB,CAAC,CACH,CAEJ,KAAO,CACL,IAAM/H,EAAa,KAAK,MAAM,WAC9B,GAAI2G,GAAa3G,EAAY,CAC3B,IAAM+H,EAAU7B,EAAK,eAAe,EAC9BC,EAAM,KAAK,mBAAmB2B,EAAa,CAAC,EAClD9H,EAAW,aAAa+H,EAAS5B,CAAG,CACtC,CACF,CACA,MAAA,CAACS,GACC,KAAK,MAAM,YACX,KAAK,MAAM,OAAO,QAClB,KAAK,MAAM,OAAO,OAAO,KAAK,KAAK,EAC9BV,CACT,CAEA,OAAOA,EAAgBS,EAAY,GAAMC,EAAS,GAAa,CAC7D,IAAMvE,EAAQ,KAAK,MAAM,QAAQ6D,CAAI,EACrC,GAAI,EAAA7D,EAAQ,GAEZ,CAAA,GAAI6D,aAAgB1C,EAAa,CAK/B,GAAI0C,EAAK,mBAAoB,OAC7B,IAAMb,EAAO,IAAM,CACjB,IAAMO,EAAKM,EAAK,WAGV5J,EAAI,KAAK,MAAM,QAAQ4J,CAAI,EAC7B5J,GAAK,GAAG,KAAK,MAAM,OAAOA,EAAG,CAAC,EAClCqK,GAAaf,GAAMA,EAAG,OAAO,EAC7BM,EAAK,SAAS,CAChB,EACA,GAAIA,EAAK,OAAO,cAAgBA,EAAK,WAAY,CAC/C,IAAI8B,EAAa,GACXC,EAAW,IAAM,CAChBD,IACHA,EAAa,GACb3C,EAAK,EAET,EAKMG,EAAmBU,EAAK,OAAO,aACrCA,EAAK,mBAAqB,GAC1BV,EAAiBU,EAAM+B,CAAQ,EAG1BzC,EAA8B,OAAS,GAAK,CAACwC,EAChDC,EAAS,EACF7G,IAAW,CAAC4G,GACnB,WAAW,IAAM,CACVA,GACH,QAAQ,KACN,yLACF,CACJ,EAAG,GAAI,CAEX,MACE3C,EAAK,CAET,KAAO,CACL,IAAMO,EAAKM,EAAK,QAChB,KAAK,MAAM,OAAO7D,EAAO,CAAC,EAC1BsE,GAAaf,GAAMA,EAAG,OAAO,EAC7BM,EAAK,SAAS,CAChB,CAEA,CAACU,GACC,KAAK,MAAM,YACX,KAAK,MAAM,OAAO,QAClB,KAAK,MAAM,OAAO,OAAO,KAAK,KAAK,CAAA,CACvC,CAEA,MAAMD,EAAY,GAAMC,EAAS,GAAa,CAC5C,GAAI,KAAK,MAAM,SAAW,EAAG,OAC7B,IAAMsB,EAAW,KAAK,MAAM,MAAM,EAElC,QAAWhC,KAAQgC,EACjB,KAAK,OAAOhC,EAAMS,EAAW,EAAI,EAEnC,CAACC,GACC,KAAK,MAAM,YACX,KAAK,MAAM,OAAO,QAClB,KAAK,MAAM,OAAO,OAAO,KAAK,KAAK,CACvC,CAEA,UAAiB,CACf,KAAK,MAAM,QAAS1B,GAAUA,EAAM,SAAS,CAAC,EAC9C,KAAK,MAAQ,CAAC,CAChB,CAEA,KAAKiD,EAAgBC,EAAgBzB,EAAY,GAAMC,EAAS,GAAO,CACrE,GACEuB,EAAS,GACTC,EAAS,GACTD,GAAU,KAAK,MAAM,QACrBC,GAAU,KAAK,MAAM,QACrBD,IAAWC,EAEX,OAEF,IAAMC,EAAQ,KAAK,MAAMF,CAAM,EACzBG,EAAQ,KAAK,MAAMF,CAAM,EAE/B,KAAK,MAAMD,CAAM,EAAIG,EACrB,KAAK,MAAMF,CAAM,EAAIC,EAEjB1B,GAAW,KAAK,gBAAgB0B,EAAOC,CAAK,EAEhD,CAAC1B,GACC,KAAK,MAAM,YACX,KAAK,MAAM,OAAO,QAClB,KAAK,MAAM,OAAO,OAAO,KAAK,KAAK,CACvC,CAEA,KACE2B,EACAC,EACA7B,EAAY,GACZC,EAAS,GACH,CACN,GACE2B,EAAY,GACZA,GAAa,KAAK,MAAM,QACxBC,EAAU,GACVA,GAAW,KAAK,MAAM,QACtBD,IAAcC,EAEd,OAEF,IAAMtC,EAAO,KAAK,MAAMqC,CAAS,EAEjC,KAAK,MAAM,OAAOA,EAAW,CAAC,EAC9B,KAAK,MAAM,OAAOC,EAAS,EAAGtC,CAAI,EAE9BS,GAAW,KAAK,gBAAgBT,EAAMsC,CAAO,EAEjD,CAAC5B,GACC,KAAK,MAAM,YACX,KAAK,MAAM,OAAO,QAClB,KAAK,MAAM,OAAO,OAAO,KAAK,KAAK,CACvC,CAEA,cAAuB,CACrB,IAAI3I,EAAO,GACX,QAAWiI,KAAQ,KAAK,MAAOjI,GAAQiI,EAAK,aAAa,EACzD,OAAOjI,CACT,CACF,ECjZMwK,GAAkC,IAAI,IACxCC,GAAyB,GAE7B,SAASC,GAAiBC,EAAuB,CAC/CH,GAAe,IAAIG,CAAG,EAClB,CAAAF,KACJA,GAAyB,GACzBpP,GAAWuP,EAAc,EAC3B,CAEA,SAASA,IAAuB,CAI9B,IAHAH,GAAyB,GAGlBD,GAAe,KAAO,GAAG,CAC9B,IAAMK,EAAO,CAAC,GAAGL,EAAc,EAC/BA,GAAe,MAAM,EACrB,QAAWG,KAAOE,EAChB,GAAI,CACFF,EAAI,CACN,OAASpP,EAAG,CACV,QAAQ,MAAM,qCAAsCA,CAAC,CACvD,CAEJ,CACF,CAUO,SAASuP,IAAkB,CAChC,IAAI9N,EAAQ,EACZ,KAAOF,GAAoB,GAAK0N,GAAe,KAAO,GAAG,CACvD,GAAIxN,IAAU,IAAO,CACnB,QAAQ,MAAM,mCAAmC,EACjD,KACF,CACAD,GAAsB,EACtB6N,GAAe,CACjB,CACF,CAcA,IAAMG,GAA6B,CAAC,EAEpC,SAASC,IAAkC,CACzC,OAAOD,GAAY,OAASA,GAAYA,GAAY,OAAS,CAAC,EAAI,IACpE,CAEA,SAASE,GAAiBC,EAAyB,CACjD,IAAMC,EAAQH,GAAY,EACtBG,GAAOA,EAAM,KAAKD,CAAO,CAC/B,CAUA,IAAME,GAAN,KAA+C,CAA/C,aAAA,CACE,KAAQ,WAA4B,IAAI,IACxC,KAAQ,SAAW,EAAA,CAInB,KAAKF,EAAyB,CAC5B,GAAI,KAAK,SAAU,CAGjBA,EAAQ,EACR,MACF,CACA,KAAK,WAAW,IAAIA,CAAO,CAC7B,CAEA,IAAOhQ,EAAgB,CACrB,GAAI,KAAK,SAQP,OAAIiI,IACF,QAAQ,KACN,mJACF,EAEKjI,EAAG,EAEZ6P,GAAY,KAAK,IAAI,EACrB,GAAI,CACF,OAAO7P,EAAG,CACZ,QAAA,CACE6P,GAAY,IAAI,CAClB,CACF,CAEA,MAAa,CACX,GAAI,CAAA,KAAK,SACT,CAAA,KAAK,SAAW,GAChB,QAAWG,KAAW,KAAK,WAAYA,EAAQ,EAC/C,KAAK,WAAW,MAAM,CAAA,CACxB,CACF,EAIO,SAASG,IAAiC,CAC/C,IAAMF,EAAQ,IAAIC,GAClB,OAAAH,GAAiB,IAAME,EAAM,KAAK,CAAC,EAC5BA,CACT,CAUO,SAASG,GAAOpQ,EAA4B,CACjD,IAAIqQ,EAAW,GAGXC,EAAU,GAKRb,EAAM,IAAY,CAClBY,GACJE,EAAI,CACN,EACMxQ,EAAY,IAAIR,GAAU,IAAM,CAChC8Q,GACJb,GAAiBC,CAAG,CACtB,CAAC,EAEKc,EAAM,IAAY,CACtB,GAAI,EAAAF,GAAYC,GAChB,CAAAA,EAAU,GAGVvQ,EAAU,MAAM,EAChB,GAAI,CACFD,GAAiBC,EAAWC,CAAE,CAChC,QAAA,CACEsQ,EAAU,EACZ,CAAA,CACF,EAEMN,EAAU,IAAY,CACtBK,IACJA,EAAW,GACXtQ,EAAU,MAAM,EAChBuP,GAAe,OAAOG,CAAG,EAC3B,EAEA,OAAAM,GAAiBC,CAAO,EACxBO,EAAI,EACGP,CACT,CAsBO,SAASQ,GAAYxQ,EAA0B,CAIpD,IAAMyQ,EAAQ,WACR7P,EAAW,IAAIC,GAEjB6P,EACAC,EAAQ,GACRC,EAAW,GAMTnB,EAAM,IAAY,CACjBkB,GAID/P,EAAS,cAAc6P,CAAK,EAAI,GAAGI,EAAmB,CAC5D,EACM9Q,EAAY,IAAIR,GAAU,IAAM,CAChCoR,IACJA,EAAQ,GACRnB,GAAiBC,CAAG,EACtB,CAAC,EAEKqB,EAAY,IAAY,CAC5B/Q,EAAU,MAAM,EAChB2Q,EAAc5Q,GAAiBC,EAAWC,CAAE,EAC5C2Q,EAAQ,GACRC,EAAW,EACb,EAEMC,EAAqB,IAAY,CACrC,IAAME,EAAWL,EACXM,EAAMJ,EACZE,EAAU,EAEN,EAAAE,GAAON,IAAgBK,IAC3BnQ,EAAS,OAAO6P,EAAOC,CAAW,CACpC,EAEMO,EAAOlQ,GAAmC,CAC9C,GAAIA,EACFH,EAAS,YAAY6P,EAAO1P,CAAQ,MAC/B,CAIL,IAAMmQ,EAAQrR,GAAgB,EAC1BqR,GAAOtQ,EAAS,YAAY6P,EAAOS,EAAM,OAAO,CACtD,CACA,OAAIP,IAWEC,GAAYhQ,EAAS,cAAc6P,CAAK,EAAI,EAAGI,EAAmB,EACjEC,EAAU,GAEVJ,CACT,EAOA,OAAAX,GALgB,IAAY,CAC1BhQ,EAAU,MAAM,EAChBuP,GAAe,OAAOG,CAAG,EACzB7O,EAAS,SAAS,CACpB,CACwB,EAEjB,CAAE,SAAU,GAAM,UAAWA,EAAU,IAAAqQ,CAAI,CACpD,CASO,SAASE,GAASnR,EAAgB,CACvC,OAAOU,GAAWV,CAAE,CACtB,CAKO,SAASoR,GAAWpR,EAAgB,CACzC,OAAOC,GAAaD,CAAE,CACxB,CA2BO,SAASqR,GACdjP,EACA6E,EACAjI,EACY,CACZ,IAAIsS,EACAC,EAAW,GAKf,OAAOnB,GAAO,IAAM,CAClB,IAAMlO,EACJ,OAAOE,GAAW,WAAaA,EAAO,EAAIA,EAAO,IAAI,GAEnD,CAACmP,GAAYvS,GAAA,MAAAA,EAAS,YACxBiI,EAAS/E,EAAUoP,CAAQ,EAG7BA,EAAWpP,EACXqP,EAAW,EACb,CAAC,CACH,CAgBO,SAASC,GAASxR,EAAgC,CAIvD,OAAOA,EAAK,QAAQ,QAAQ,EAAE,KAAKA,CAAE,EAAI,QAAQ,QAAQ,CAC3D,CCrZO,IAAMyR,GAAN,KAAuE,CAK5E,YAAYC,EAAW,CAJvB,KAAQ,UAAY,IAAI7Q,GAKtB,KAAK,cAAgB8Q,GAAA,CAAA,EAAKD,CAAAA,EAC1B,KAAK,QAAUC,GAAA,CAAA,EAAKD,CAAAA,CACtB,CAEA,IAAuBpS,EAAQsS,EAAoB,CACjD,GAAIA,EACF,KAAK,UAAU,YAAYtS,EAAesS,CAAC,MACtC,CAKL,IAAM7R,EAAYF,GAAgB,EAC9BE,GACF,KAAK,UAAU,YAAYT,EAAeS,EAAU,OAAO,CAC/D,CACA,OAAO,KAAK,QAAQT,CAAG,CACzB,CAEA,IAAuBA,EAAQoD,EAAmB,CAChD,KAAK,QAAQpD,CAAG,EAAIoD,EACpB,KAAK,UAAU,OAAOpD,EAAeoD,CAAK,CAC5C,CAEA,YAA+BpD,EAAQU,EAA0B,CAC/D,OAAO,KAAK,UAAU,YAAYV,EAAeU,CAAE,CACrD,CAEA,eAAkCV,EAAQU,EAAoB,CAC5D,KAAK,UAAU,eAAeV,EAAeU,CAAE,CACjD,CAEA,MAAyBV,EAAc,CACrC,KAAK,IAAIA,EAAK,KAAK,cAAcA,CAAG,CAAC,CACvC,CAEA,UAAiB,CACf,KAAK,UAAU,SAAS,CAC1B,CACF,EChDA,IAAAuS,GAAA,GAAAC,GAAAD,GAAA,iBAAAE,GAAA,iBAAAC,GAAA,qBAAAC,GAAA,kBAAAC,GAAA,aAAAC,GAAA,aAAAC,GAAA,eAAAC,GAAA,aAAAC,GAAA,eAAAC,EAAA,oBAAAC,GAAA,iBAAAC,EAAA,sBAAAC,GAAA,cAAAC,GAAA,cAAAC,EAAA,iBAAAC,EAAA,gBAAAC,GAAA,cAAAC,KMDA,IAAMC,GAAcC,GAAkB,CAClC,IAAMC,EAAUC,GAAc,CAC1B,IAAMC,EAAU,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGD,CAAC,CAAC,EACpCE,EAAID,GAAW,SAAY,MAAQA,EAAU,MAAQ,KAAK,IAAIA,EAAS,EAAI,GAAG,EAAI,KACxF,OAAO,KAAK,IAAI,EAAG,KAAK,IAAI,IAAK,KAAK,MAAMC,EAAI,GAAG,CAAC,CAAC,CACzD,EACA,OAAOJ,EAAI,IAAIC,CAAM,CACzB,EAEMI,GAAcL,GAAkB,CAClC,IAAMM,EAAUJ,GAAeA,EAAI,OAAU,KAAK,KAAKA,EAAI,MAAS,MAAO,GAAG,EAAIA,EAAI,MACtF,OAAOF,EAAI,IAAIM,CAAM,CACzB,EAGaC,GAAYP,GAA0B,CAE/C,GAAI,CAACQ,EAAGC,EAAGC,CAAC,EAAIX,GAAWC,CAAG,EAC9B,OAAAQ,EAAIA,EAAE,SAAS,EAAE,EAAE,SAAS,EAAG,GAAG,EAClCC,EAAIA,EAAE,SAAS,EAAE,EAAE,SAAS,EAAG,GAAG,EAClCC,EAAIA,EAAE,SAAS,EAAE,EAAE,SAAS,EAAG,GAAG,EAC3B,IAAIF,CAAC,GAAGC,CAAC,GAAGC,CAAC,EACxB,EAGaC,GAAYC,GAA0B,CAC/C,IAAMJ,EAAI,SAASI,EAAI,MAAM,EAAG,CAAC,EAAG,EAAE,EAAI,IACpCH,EAAI,SAASG,EAAI,MAAM,EAAG,CAAC,EAAG,EAAE,EAAI,IACpCF,EAAI,SAASE,EAAI,MAAM,EAAG,CAAC,EAAG,EAAE,EAAI,IAE1C,OAAOP,GAAW,CAACG,EAAGC,EAAGC,CAAC,CAAC,CAC/B,EAIaG,GAAcb,GAA4B,CACnD,IAAMc,EAAI,YAAed,EAAI,CAAC,EAAI,YAAeA,EAAI,CAAC,EAAI,YAAeA,EAAI,CAAC,EACxEe,EAAI,YAAef,EAAI,CAAC,EAAI,YAAeA,EAAI,CAAC,EAAI,YAAeA,EAAI,CAAC,EACxEI,EAAI,YAAeJ,EAAI,CAAC,EAAI,YAAeA,EAAI,CAAC,EAAI,YAAeA,EAAI,CAAC,EACxEgB,EAAK,KAAK,KAAKF,CAAC,EAAGG,EAAK,KAAK,KAAKF,CAAC,EAAGG,EAAK,KAAK,KAAKd,CAAC,EAC5D,MAAO,CACH,YAAeY,EAAK,WAAcC,EAAK,YAAeC,EACtD,aAAeF,EAAK,YAAcC,EAAK,YAAeC,EACtD,YAAeF,EAAK,YAAeC,EAAK,WAAcC,CAC1D,CACJ,EAIaC,GAAcC,GAA4B,CACnD,GAAM,CAACC,EAAGC,EAAGZ,CAAC,EAAIU,EACZJ,EAAKK,EAAI,YAAeC,EAAI,YAAeZ,EAC3CO,EAAKI,EAAI,YAAeC,EAAI,YAAeZ,EAC3CQ,EAAKG,EAAI,YAAeC,EAAI,YAAcZ,EAC1CI,EAAIE,EAAKA,EAAKA,EAAID,EAAIE,EAAKA,EAAKA,EAAIb,EAAIc,EAAKA,EAAKA,EACxD,MAAO,CACH,aAAeJ,EAAI,aAAeC,EAAI,YAAeX,EACrD,cAAgBU,EAAI,aAAeC,EAAI,YAAeX,EACtD,aAAgBU,EAAI,YAAeC,EAAI,YAAcX,CACzD,CACJ,EA5DA,IAyGamB,GAAYC,GAA4B,CACjD,GAAM,CAACC,EAAGC,EAAGC,CAAC,EAAIH,EAGZI,EAAI,SAAYH,EAAI,SAAYC,EAAI,SAAYC,EAChDE,EAAI,SAAYJ,EAAI,SAAYC,EAAI,QAAYC,EAChDG,EAAI,SAAYL,EAAI,QAAYC,EAAI,SAAYC,EAGhDI,EAAK,OACLC,EAAK,EACLC,EAAK,QAELC,EAAKC,GACPA,EAAI,QAAW,KAAK,KAAKA,CAAC,EAAK,MAAQA,EAAI,GAAK,IAE9CC,EAAKF,EAAEN,EAAIG,CAAE,EACbM,EAAKH,EAAEL,EAAIG,CAAE,EACbM,EAAKJ,EAAEJ,EAAIG,CAAE,EAEnB,MAAO,CACH,IAAMI,EAAK,GACX,KAAOD,EAAKC,GACZ,KAAOA,EAAKC,EAChB,CACJ,EAlIA,IA6KaC,GAAiB,CAACC,EAAgBC,IAA2B,CACtE,GAAM,CAACC,EAAIC,EAAIC,CAAE,EAAIJ,EAAM,CAACK,EAAIC,EAAIC,CAAE,EAAIN,EACpCO,GAAQN,EAAKG,GAAM,EACnBI,EAAK,KAAK,KAAKN,EAAKA,EAAKC,EAAKA,CAAE,EAAGM,EAAK,KAAK,KAAKJ,EAAKA,EAAKC,EAAKA,CAAE,EACnEI,GAAQF,EAAKC,GAAM,EACnBE,EAAI,IAAO,EAAI,KAAK,KAAK,KAAK,IAAID,EAAM,CAAC,GAAK,KAAK,IAAIA,EAAM,CAAC,EAAI,KAAK,IAAI,GAAI,CAAC,EAAE,GAClFE,EAAMV,GAAM,EAAIS,GAAIE,EAAMR,GAAM,EAAIM,GACpCG,EAAM,KAAK,KAAKF,EAAMA,EAAMT,EAAKA,CAAE,EAAGY,EAAM,KAAK,KAAKF,EAAMA,EAAMP,EAAKA,CAAE,EACzEU,GAASF,EAAMC,GAAO,EACtBE,EAAM,KAAK,MAAMd,EAAIS,CAAG,EAAI,IAAM,KAAK,IAAM,KAAK,MAAMT,EAAIS,CAAG,EAAI,EAAI,IAAM,GAC7EM,EAAM,KAAK,MAAMZ,EAAIO,CAAG,EAAI,IAAM,KAAK,IAAM,KAAK,MAAMP,EAAIO,CAAG,EAAI,EAAI,IAAM,GAC/EM,EAAMD,EAAMD,EACZ,KAAK,IAAIE,CAAG,EAAI,MAAKA,GAAQD,GAAOD,EAAM,IAAM,MACpD,IAAMG,EAAQ,KAAK,IAAIH,EAAMC,CAAG,EAAI,KAAOD,EAAMC,EAAM,KAAO,GAAKD,EAAMC,GAAO,EAC1EG,EAAI,EAAI,IAAO,KAAK,KAAKD,EAAQ,IAAM,KAAK,GAAK,GAAG,EAAI,IAAO,KAAK,IAAI,EAAIA,EAAQ,KAAK,GAAK,GAAG,EAAI,IAAO,KAAK,KAAK,EAAIA,EAAQ,GAAK,KAAK,GAAK,GAAG,EAAI,GAAM,KAAK,KAAK,EAAIA,EAAQ,IAAM,KAAK,GAAK,GAAG,EACvME,EAAMlB,EAAKH,EAAIsB,EAAMR,EAAMD,EAC3BU,EAAM,EAAI,KAAK,KAAKV,EAAMC,CAAG,EAAI,KAAK,IAAII,EAAM,EAAI,KAAK,GAAK,GAAG,EACjEM,EAAK,EAAK,KAAQ,KAAK,IAAIlB,EAAO,GAAI,CAAC,EAAK,KAAK,KAAK,GAAK,KAAK,IAAIA,EAAO,GAAI,CAAC,CAAC,EACjFmB,GAAK,EAAI,KAAQV,EAAOW,GAAK,EAAI,KAAQX,EAAQK,EACjDO,GAAS,GAAK,KAAK,IAAI,CAAC,KAAK,KAAKR,EAAQ,KAAO,GAAI,CAAC,CAAC,EAEvDS,EAAK,EADA,EAAI,KAAK,KAAK,KAAK,IAAIb,EAAO,CAAC,GAAK,KAAK,IAAIA,EAAO,CAAC,EAAI,KAAK,IAAI,GAAI,CAAC,EAAE,GACnE,KAAK,IAAI,EAAIY,GAAS,KAAK,GAAK,GAAG,EACpD,OAAO,KAAK,KAAK,KAAK,IAAIN,EAAMG,EAAI,CAAC,EAAI,KAAK,IAAIF,EAAMG,GAAI,CAAC,EAAI,KAAK,IAAIF,EAAMG,GAAI,CAAC,EAAIE,GAAMN,EAAMG,KAAOF,EAAMG,GAAG,CACzH,EApMA,IA0NaG,GAAkBC,GAAuB,CAClD,GAAIA,EAAO,OAAS,EAAG,OAAQC,GAAe,EAE9C,IAAMC,EAAS,CAAC,GAAGF,CAAM,EAAE,KAAK,CAACG,EAAGC,IAAMD,EAAE,CAAC,EAAIC,EAAE,CAAC,CAAC,EAC/CC,EAA2B,CAAC,EAElC,QAASC,EAAI,EAAGA,EAAIJ,EAAO,OAAQI,KAC3BA,IAAM,GAAKJ,EAAOI,CAAC,EAAE,CAAC,IAAMJ,EAAOI,EAAI,CAAC,EAAE,CAAC,IAC3CD,EAAa,KAAKH,EAAOI,CAAC,CAAC,EAInC,IAAMC,EAAIF,EAAa,OACvB,GAAIE,IAAM,EAAG,OAAQN,GAAeI,EAAa,CAAC,EAAE,CAAC,EAErD,IAAMG,EAAIH,EAAa,IAAII,GAAKA,EAAE,CAAC,CAAC,EAC9BC,EAAIL,EAAa,IAAII,GAAKA,EAAE,CAAC,CAAC,EAC9BE,EAAc,CAAC,EACfC,EAAoB,CAAC,EAE3B,QAASN,EAAI,EAAGA,EAAIC,EAAI,EAAGD,IACvBK,EAAEL,CAAC,EAAIE,EAAEF,EAAI,CAAC,EAAIE,EAAEF,CAAC,EACrBM,EAAQN,CAAC,GAAKI,EAAEJ,EAAI,CAAC,EAAII,EAAEJ,CAAC,GAAKK,EAAEL,CAAC,EAGxC,IAAMO,EAAc,IAAI,MAAMN,CAAC,EAC/BM,EAAE,CAAC,EAAID,EAAQ,CAAC,EAChBC,EAAEN,EAAI,CAAC,EAAIK,EAAQL,EAAI,CAAC,EAExB,QAASD,EAAI,EAAGA,EAAIC,EAAI,EAAGD,IAAK,CAC5B,IAAMQ,EAAKF,EAAQN,EAAI,CAAC,EAClBS,EAAKH,EAAQN,CAAC,EACpB,GAAIQ,EAAKC,GAAM,EACXF,EAAEP,CAAC,EAAI,MACJ,CACH,IAAMU,GAAS,EAAIL,EAAEL,CAAC,GAAKK,EAAEL,EAAI,CAAC,EAAIK,EAAEL,CAAC,IAAM,EAC/CO,EAAEP,CAAC,EAAKQ,EAAKC,IAAQ,EAAIC,GAASF,EAAKE,EAAQD,EACnD,CACJ,CAEA,OAAQE,GAAsB,CAC1B,GAAIA,GAAKT,EAAE,CAAC,EAAG,OAAOE,EAAE,CAAC,EACzB,GAAIO,GAAKT,EAAED,EAAI,CAAC,EAAG,OAAOG,EAAEH,EAAI,CAAC,EAEjC,IAAIW,EAAM,EACNC,EAAOZ,EAAI,EACXD,EAAI,EACR,KAAOY,GAAOC,GAAM,CAChB,IAAMC,EAAM,KAAK,OAAOF,EAAMC,GAAQ,CAAC,EACvC,GAAIF,GAAKT,EAAEY,CAAG,GAAKH,GAAKT,EAAEY,EAAM,CAAC,EAAG,CAChCd,EAAIc,EACJ,KACJ,CACIH,EAAIT,EAAEY,CAAG,EAAGD,EAAOC,EAAM,EACxBF,EAAME,EAAM,CACrB,CAEA,IAAMC,EAAKV,EAAEL,CAAC,EACRgB,GAAKL,EAAIT,EAAEF,CAAC,GAAKe,EACjBE,EAAKD,EAAIA,EACTE,EAAKD,EAAKD,EACVG,EAAKZ,EAAEP,CAAC,EAAIe,EACZK,EAAKb,EAAEP,EAAI,CAAC,EAAIe,EAEtB,OAAQ,EAAIG,EAAK,EAAID,EAAK,GAAKb,EAAEJ,CAAC,GAC7BkB,EAAK,EAAID,EAAKD,GAAKG,GACnB,GAAKD,EAAK,EAAID,GAAMb,EAAEJ,EAAI,CAAC,GAC3BkB,EAAKD,GAAMG,CACpB,CACJ,EIjRA,IAAMC,GAAI,KACJC,GAAI,KAEV,SAASC,GAAKC,EAAmB,CAC7B,IAAMC,EAAK,KAAK,IAAID,EAAGH,EAAC,EACxB,OAAOI,GAAM,EAAIH,IAAK,EAAIG,GAC9B,CAEA,SAASC,GAAOC,EAAmB,CAC/B,IAAMC,EAAMD,GAAK,EAAIL,KAAO,EAAIK,EAAIL,IACpC,OAAO,KAAK,IAAIM,EAAI,EAAIP,EAAC,CAC7B,CAEA,SAASQ,GAAWC,EAAcC,EAAsB,CACpD,OAAO,KAAK,KACR,KAAK,IAAID,EAAG,CAAC,EAAIC,EAAG,CAAC,EAAG,CAAC,EACzB,KAAK,IAAID,EAAG,CAAC,EAAIC,EAAG,CAAC,EAAG,CAAC,EACzB,KAAK,IAAID,EAAG,CAAC,EAAIC,EAAG,CAAC,EAAG,CAAC,CAC7B,CACJ,CAaA,SAASC,GAAuBC,EAAkB,CAE9C,IAAMC,EADW,CAAC,CAAC,EAAG,EAAG,CAAC,EAAG,GAAGD,EAAM,CAAC,EAAG,EAAG,CAAC,CAAC,EACtB,IAAKE,GAAQC,GAAWD,CAAG,CAAC,EAAE,KAAK,CAACE,EAAGC,IAAMD,EAAE,CAAC,EAAIC,EAAE,CAAC,CAAC,EAE3EC,EAAIL,EAAQ,IAAKM,GAAMA,EAAE,CAAC,CAAC,EAC3BC,EAAIP,EAAQ,IAAKM,GAAMA,EAAE,CAAC,CAAC,EAC3BE,EAAIR,EAAQ,IAAKM,GAAMA,EAAE,CAAC,CAAC,EAE3BG,EAAgC,CAAC,CAAC,EACpCC,EAAY,EAChB,QAASC,EAAI,EAAGA,EAAIX,EAAQ,OAAQW,IAChCD,GAAaf,GAAWK,EAAQW,CAAC,EAAGX,EAAQW,EAAI,CAAC,CAAC,EAClDF,EAAoB,KAAKC,CAAS,EAGtC,IAAME,EAAYH,EAAoB,IAAKI,GAAMrB,GAAOkB,EAAY,EAAIG,EAAIH,EAAY,CAAC,CAAC,EAEpFI,EAAOf,EAAK,SAAW,EAAI,EAAIa,EAAU,CAAC,EAC1CG,EAAOhB,EAAK,SAAW,EAAI,EAAIa,EAAUA,EAAU,OAAS,CAAC,EAE7DI,EAAgBC,GAAeL,EAAU,IAAI,CAACM,EAAGP,IAAM,CAACO,EAAGX,EAAEI,CAAC,CAAC,CAAC,CAAC,EACjEQ,EAAgBF,GAAeL,EAAU,IAAI,CAACM,EAAGP,IAAM,CAACO,EAAGV,EAAEG,CAAC,CAAC,CAAC,CAAC,EAwBvE,MAAO,CACH,aAvBkBrB,GAAwB,CAC1C,IAAM8B,EAAU/B,GAAKC,CAAC,EAChB+B,EAAUP,EAAOM,GAAWL,EAAOD,GAErCH,EAAI,EACR,QAASW,EAAI,EAAGA,EAAIV,EAAU,OAAS,EAAGU,IACtC,GAAID,GAAWT,EAAUU,EAAI,CAAC,EAAG,CAC7BX,EAAIW,EACJ,KACJ,CAGJ,IAAMC,EAASX,EAAUD,CAAC,EACpBa,EAAOZ,EAAUD,EAAI,CAAC,EACtBc,GAASJ,EAAUE,IAAWC,EAAOD,GAAU,GAC/CG,EAAIrB,EAAEM,CAAC,EAAIc,GAASpB,EAAEM,EAAI,CAAC,EAAIN,EAAEM,CAAC,GAClCR,EAAIa,EAAcK,CAAO,EACzBjB,EAAIe,EAAcE,CAAO,EAE/B,OAAOM,GAAW,CAACD,EAAGvB,EAAGC,CAAC,CAAC,CAC/B,EAII,WAAYQ,EAAU,MAAM,EAAG,EAAE,EAAE,IAAKN,IAAOA,EAAIQ,IAASC,EAAOD,EAAK,CAC5E,CACJ,CAmBO,SAASc,GAAaC,EAAyBC,EAA8B,CAChF,IAAM9B,EAAU,MAAM,QAAQ6B,CAAI,EAAIA,EAAO,CAACA,CAAI,EAClD,GAAI7B,EAAQ,SAAW,EAAG,MAAM,IAAI,MAAM,iDAAiD,EAC3F,GAAI8B,GAAc,EAAG,MAAO,CAAC,EAC7B,GAAIA,IAAe,EAAG,MAAO,CAAC9B,EAAQ,CAAC,CAAC,EAExC,GAAM,CAAE,aAAA+B,EAAc,WAAAC,CAAW,EAAIlC,GAAuBE,EAAQ,IAAIiC,EAAQ,CAAC,EAC3EC,EAAmB,CAAC,EAEpBC,EAAa,CAAC,EAAG,GAAGH,EAAY,CAAC,EACjCI,EAAYD,EAAW,IAAK7B,GAAM,KAAK,MAAMA,GAAKwB,EAAa,EAAE,CAAC,EAEpEO,EAAU,EACd,QAASC,EAAI,EAAGA,EAAIR,EAAYQ,IAAK,CACjC,KAAOD,EAAUD,EAAU,OAAS,GAAKE,EAAIF,EAAUC,EAAU,CAAC,GAAGA,IAErE,IAAME,EAAWH,EAAUC,CAAO,EAC5BG,EAASJ,EAAUC,EAAU,CAAC,EAC9BI,EAAaN,EAAWE,CAAO,EAC/BK,EAAWP,EAAWE,EAAU,CAAC,EAEnC/C,EACJ,GAAIkD,GAAUD,EACVjD,EAAImD,MACD,CACH,IAAMhB,GAASa,EAAIC,IAAaC,EAASD,GACzCjD,EAAImD,EAAahB,GAASiB,EAAWD,EACzC,CAEAP,EAAO,KAAKS,GAASZ,EAAazC,CAAC,CAAC,CAAC,CACzC,CAIA,OAAO4C,EAAO,QAAQ,CAC1B,CVpJA,IAAMU,GAAoB,CACxB,UAAW,SACX,OAAQ,CACN,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,UAAW,CACT,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,KAAM,CACJ,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,UAAW,CACT,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,MAAO,CACL,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,OAAQ,CACN,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,UAAW,CACT,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,EACA,QAAS,CACP,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,UACA,SACF,CACF,EACA,UAAW,CACT,UAAW,EACX,QAAS,EACT,UAAW,EACX,MAAO,EACP,OAAQ,EACR,UAAW,EACX,QAAS,EACT,KAAM,EACN,QAAS,EACT,QA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","names":["global_exports","__export","dist_exports","src_exports","BooleanAttributes","CamelAttributes","HtmlAttributeNames","HtmlTags","PrefixCSS","SvgTags","VoidTags","_config","configure","options","getConfig","EventProperties","eventNameMap","acc","ev","key","Collector","onDependencyChange","handler","release","COLLECTOR_STACK","UNTRACK_DEPTH","activeCollector","runWithCollector","collector","fn","runUntracked","_chain","_microtask","cb","e","SELF_NOTIFY_CAP","_batchDepth","_batchedNotifiers","_scheduledNotifiers","runBatched","notifiers","notifier","Notifier","event","listener","listeners","_a","_b","_c","args","top","inflight","idx","n","names","pending","chain","hasPendingNotifiers","flushPendingNotifiers","guard","State","initialValue","name","newValue","merge","source","target","comma","space","adjacent","deepClone","value","old","val1","val2","addEvent","addHook","hashString","str","hash","i","toState","val","isState","readonly","behavior","attach","props","partial","hookName","hookProperty","current","attributes","eventName","eventProperty","node","seen","clone","v","k","proto","validate","element","asPartial","keys","isHTML","sanitizeHTMLString","html","result","escapeHTML","getTagName","camelToKebab","selectorSplitter","selectors","splitted","parens","angulars","soFar","len","char","normalizeSelectorKey","selectorText","text","collectCSSRules","rules","map","rule","ensureDomStyle","styleParent","nonce","domStyle","resolvedNonce","mergePartial","part","p","EnumeratedBooleanAttributes","ElementAttribute","parent","domElement","mutateAttrs","prev","releaseSubscription","callback","AttributeList","attr","domName","force","className","add","classes","newClass","list","declared","currentIsFn","nextIsFn","updated","cls","oldClass","__DEV__","StyleProperty","parentRule","domRule","style","prefix","_d","StyleRule","_StyleRule","StyleList","prop","root","styleStr","decl","nested","sheet","domSheet","index","css","err","obj","parentSelector","basic","conditionalRules","getSelector","selector","splitKeys","currentSelector","newSelector","r","existingKey","domRuleMap","domRuleList","wrongCount","fixOddEven","dom","ElementNode","_ElementNode","domphyElement","_parent","ElementList","tempPath","_k","children","input","error","releases","originalKey","rawElement","content","next","autoClass","reserved","hookKeys","keep","userClass","userClassFn","boundary","composed","behaviors","spec","instance","child","childNode","newNode","done","called","once","beforeRemoveHook","TextNode","textContent","tpl","el","wasHTML","fresh","domText","_warnedKeylessSites","_resetKeylessWarnings","item","ref","aNode","bNode","a","b","aNext","bNext","inputs","updateDom","silent","imperative","oldItems","keyed","oldSet","claimed","unkeyedObjectInputs","lengthChanged","isObj","tag","reused","cur","isPortal","at","extras","siteId","msg","length","finalIndex","domNode","doneCalled","onceDone","snapshot","aIndex","bIndex","itemA","itemB","fromIndex","toIndex","REACTION_QUEUE","reactionDrainScheduled","scheduleReaction","job","drainReactions","jobs","flushSync","SCOPE_STACK","activeScope","registerDisposer","dispose","scope","EffectScope","effectScope","effect","disposed","running","run","computed","EVENT","cachedValue","dirty","hasValue","recomputeAndNotify","recompute","previous","had","get","outer","batch","untrack","watch","oldValue","firstRun","nextTick","RecordState","record","__spreadValues","l","dist_exports","__export","se","g","oe","ue","m","ee","te","L","ge","Te","ae","re","p","he","ne","O","h","lrgbToSrgb","rgb","toSRGB","c","clamped","s","srgbToLrgb","toLRGB","rgbToHex","r","g","b","hexToRgb","hex","rgbToOklab","l","m","l_","m_","s_","oklabToRgb","lab","L","a","rgbToLab","rgb","r","g","b","x","y","z","Xn","Yn","Zn","f","t","fx","fy","fz","calcDeltaE2000","lab1","lab2","L1","a1","b1","L2","a2","b2","avgL","C1","C2","avgC","G","a1p","a2p","C1p","C2p","avgCp","h1p","h2p","dhp","avgHp","T","dLp","dCp","dHp","SL","SC","SH","dtheta","RT","createMonotone","points","_t","sorted","a","b","uniquePoints","i","n","x","p","y","h","secants","m","d0","d1","alpha","t","low","high","mid","dx","s","s2","s3","m0","m1","P","Q","warp","t","tn","unwarp","y","xn","euclidean3","v1","v2","sequentialInterpolator","rgbs","anchors","rgb","rgbToOklab","a","b","L","v","A","B","cumulativeDistances","totalDist","i","allParams","d","tMin","tMax","aInterpolator","createMonotone","p","bInterpolator","tWarped","tMapped","j","dStart","dEnd","ratio","l","oklabToRgb","generateRamp","hexs","stepsCount","colorAtParam","parameters","hexToRgb","colors","fullParams","anchorIdx","segment","k","startIdx","endIdx","startParam","endParam","rgbToHex","light","light_default","clone","v","escapeKey","k","themes","createDark","_themeVarsCache","_themeTokensCache","colorSteps","input","firstColor","validateTheme","partial","key","custom","colors","c","baseTones","deepMerge","target","source","_a","buildThemeCSS","name","styles","toneSteps","value","colorName","i","text","prop","getTheme","setTheme","dark","themeTokens","cached","tokens","colorTones","themeVars","theme","themeCSS","themeApply","el","themeSpacing","n","themeFluidSpacing","min","max","viewportMin","viewportMax","minEm","maxEm","slope","intercept","preferred","applySystemTheme","targetEl","options","persist","storageKey","resolve","saved","mql","handler","event","themeName","object","node","COLOR_ROLES","ElementDensities","offsetDensity","origin","density","resultDensity","offset","contextDensity","themeDensity","index","DEFAULT_FONT_SIZES","DEFAULT_DENSITIES","nearestStepIndex","ramp","baseHex","baseLab","rgbToLab","hexToRgb","best","bestDist","dist","calcDeltaE2000","generateTheme","baseColors","_b","_c","_d","_e","_f","steps","hex","generateRamp","ElementSizes","offsetSize","size","resultSize","contextSize","themeSize","TONE_STEPS","ToneAliases","ElementTones","adjustTone","tone","level","newIndex","shiftTone","midpoint","offsetTone","originTone","contextTone","biasContext","context","direction","bias","themeColor","color","resultTone","themeColorToken","colorTokens","src_exports","__export","abbreviation","accordion","alert","avatar","badge","blockquote","breadcrumb","breadcrumbEllipsis","button","buttonGhost","buttonSwitch","card","code","combobox","command","commandItem","commandSearch","datePicker","descriptionList","details","dialog","divider","drawer","emphasis","empty","errorBoundary","fab","figure","formGroup","heading","horizontalRule","icon","image","inputCheckbox","inputColor","inputDateTime","inputFile","inputNumber","inputOTP","inputPassword","inputRadio","inputRange","inputSearch","inputSwitch","inputText","keyboard","label","link","linkButton","list","listItem","listItemButton","mark","menu","motion","orderedList","pagination","panelSection","paragraph","popover","popoverArrow","preformated","progress","rating","ringProgress","row","scrollArea","segmented","select","selectBox","selectItem","selectList","skeleton","small","spinner","splitter","splitterHandle","splitterPanel","stack","steps","strong","subscript","superscript","table","tabs","tag","textarea","timeline","timelineItem","toast","toggleGroup","toolbar","toolbarSpacer","tooltip","transitionGroup","unorderedList","abbreviation","props","_a","_b","color","nt","accentColor","node","listener","he","ge","ne","accordion","props","_a","_b","type","color","nt","accentColor","node","el","handler","event","summary","item","detail","listener","ne","ae","ge","alert","props","_a","color","nt","ne","listener","ae","ge","he","avatar","props","_a","color","nt","ne","listener","he","ge","badge","props","_a","label","state","nt","color","l","ne","he","ge","blockquote","props","_a","color","nt","node","listener","he","ge","ne","ae","breadcrumb","props","_a","separator","color","nt","node","listener","he","ne","ge","breadcrumbEllipsis","props","_a","color","nt","node","listener","he","ne","ge","BUTTON_SIZE_FONT","focusRing","listener","color","ge","PADDING_STEPS","buttonGhost","props","_a","_b","_c","color","nt","padding","fontSize","BUTTON_SIZE_FONT","node","listener","he","ne","ae","ge","focusRing","PADDING_STEPS","button","props","_a","_b","_c","_d","variant","buttonGhost","color","nt","isSolid","padding","fontSize","BUTTON_SIZE_FONT","node","listener","he","ne","ae","ge","focusRing","buttonSwitch","props","_a","_b","checked","check","nt","color","accentColor","node","listener","he","ge","ne","card","props","_a","color","nt","listener","ne","ae","ge","code","props","_a","color","nt","node","listener","he","ge","ne","SHADOWS","elevation","level","sides","alignments","placements","acc","side","min","max","round","floor","createCoords","v","oppositeSideMap","clamp","start","value","end","evaluate","param","getSide","placement","getAlignment","getOppositeAxis","axis","getAxisLength","getSideAxis","firstChar","getAlignmentAxis","getAlignmentSides","rects","rtl","alignment","alignmentAxis","length","mainAlignmentSide","getOppositePlacement","getExpandedPlacements","oppositePlacement","getOppositeAlignmentPlacement","lrPlacement","rlPlacement","tbPlacement","btPlacement","getSideList","isStart","getOppositeAxisPlacements","flipAlignment","direction","list","expandPaddingObject","padding","__spreadValues","getPaddingObject","rectToClientRect","rect","x","y","width","height","computeCoordsFromPlacement","reference","floating","sideAxis","alignLength","isVertical","commonX","commonY","commonAlign","coords","detectOverflow","_0","__async","state","options","_a","_b","_c","_d","_e","_f","platform","elements","strategy","boundary","rootBoundary","elementContext","altBoundary","paddingObject","element","clippingClientRect","offsetParent","offsetScale","elementClientRect","MAX_RESET_COUNT","computePosition","config","middleware","platformWithDetectOverflow","__spreadProps","statefulPlacement","resetCount","middlewareData","i","currentMiddleware","name","fn","nextX","nextY","data","reset","flip","options","state","__async","_b","_c","_d","_e","_f","_g","placement","middlewareData","rects","initialPlacement","platform","elements","_a","evaluate","checkMainAxis","checkCrossAxis","specifiedFallbackPlacements","fallbackStrategy","fallbackAxisSideDirection","flipAlignment","detectOverflowOptions","__objRest","side","getSide","initialSideAxis","getSideAxis","isBasePlacement","rtl","fallbackPlacements","getOppositePlacement","getExpandedPlacements","hasFallbackAxisSideDirection","getOppositeAxisPlacements","placements","overflow","overflows","overflowsData","sides","getAlignmentSides","nextIndex","nextPlacement","d","resetPlacement","a","b","currentSideAxis","acc","originSides","convertValueToCoords","state","options","__async","_a","placement","platform","elements","rtl","side","getSide","alignment","getAlignment","isVertical","getSideAxis","mainAxisMulti","crossAxisMulti","rawValue","evaluate","mainAxis","crossAxis","alignmentAxis","offset","_b","x","y","middlewareData","diffCoords","__spreadProps","__spreadValues","shift","checkMainAxis","checkCrossAxis","limiter","detectOverflowOptions","__objRest","coords","overflow","getOppositeAxis","mainAxisCoord","crossAxisCoord","minSide","maxSide","min","max","clamp","limitedCoords","hasWindow","getNodeName","node","isNode","getWindow","_a","getDocumentElement","value","isElement","isHTMLElement","isShadowRoot","isOverflowElement","element","overflow","overflowX","overflowY","display","getComputedStyle","isTableElement","isTopLayer","_e","willChangeRe","containRe","isNotNone","isWebKitValue","isContainingBlock","elementOrCss","css","isWebKit","getContainingBlock","currentNode","getParentNode","isLastTraversableNode","getNodeScroll","result","getNearestOverflowAncestor","parentNode","getOverflowAncestors","list","traverseIframes","scrollableAncestor","isBody","win","frameElement","getFrameElement","getCssDimensions","width","height","hasOffset","offsetWidth","offsetHeight","shouldFallback","round","unwrapElement","getScale","domElement","createCoords","rect","$","x","y","noOffsets","getVisualOffsets","shouldAddVisualOffsets","isFixed","floatingOffsetParent","getBoundingClientRect","includeScale","isFixedStrategy","offsetParent","clientRect","scale","visualOffsets","offsetWin","currentWin","currentIFrame","iframeScale","iframeRect","left","top","rectToClientRect","getWindowScrollBarX","leftScroll","getHTMLOffset","documentElement","scroll","htmlRect","convertOffsetParentRelativeRectToViewportRelativeRect","elements","strategy","topLayer","offsets","isOffsetParentAnElement","offsetRect","htmlOffset","getClientRects","getDocumentRect","html","body","max","SCROLLBAR_MAX","getViewportRect","visualViewport","visualViewportBased","windowScrollbarX","doc","bodyStyles","bodyMarginInline","clippingStableScrollbarWidth","getInnerBoundingClientRect","getClientRectFromClippingAncestor","clippingAncestor","hasFixedPositionAncestor","stopNode","getClippingElementAncestors","cache","cachedResult","el","currentContainingBlockComputedStyle","elementIsFixed","computedStyle","currentNodeIsContaining","ancestor","getClippingRect","boundary","rootBoundary","clippingAncestors","firstRect","right","bottom","i","min","getDimensions","getRectRelativeToOffsetParent","setLeftRTLScrollbarOffset","isStaticPositioned","getTrueOffsetParent","polyfill","rawOffsetParent","getOffsetParent","svgOffsetParent","getElementRects","data","__async","getOffsetParentFn","getDimensionsFn","floatingDimensions","isRTL","platform","rectsAreEqual","a","b","observeMove","onMove","io","timeoutId","root","cleanup","refresh","skip","threshold","elementRectForRootMargin","insetTop","floor","insetRight","insetBottom","insetLeft","options","isFirstUpdate","handleObserve","entries","ratio","__spreadProps","__spreadValues","autoUpdate","reference","floating","update","ancestorScroll","ancestorResize","elementResize","layoutShift","animationFrame","referenceEl","ancestors","cleanupIo","reobserveFrame","resizeObserver","firstEntry","frameId","prevRefRect","frameLoop","nextRefRect","offset","shift","flip","computePosition","reference","floating","options","cache","mergedOptions","__spreadValues","platform","platformWithCache","__spreadProps","attachFloating","node","initialProps","_a","openState","placement","content","keepOpenOnContentHover","timer","cleanup","floating","floatingNode","mounted","reference","rootNode","floatingPartial","listener","event","hide","show","mountedNode","dataTheme","rNode","overlay","overlayEle","wireContent","target","w","ensureMounted","instantShow","Qt","nr","Je","Ze","Qe","x","y","resolved","instantHide","handleOutside","props","createFloating","kind","open","nt","behaviorKey","anchorPartial","__spreadValues","e","at","xSvg","tag","props","_a","removable","color","nt","node","removeBtn","e","ne","listener","ge","he","combobox","props","options","placement","color","open","multiple","state","nt","openState","show","hide","anchorPartial","createFloating","popoverPartial","_e","node","listener","ge","ne","ae","elevation","w","inputStyle","he","inputElement","inputPartial","wrap","val","vals","items","opt","tag","_node","cur","filter","v","partial","command","_node","element","w","nt","commandSearch","props","color","accentColor","node","ctx","input","onInput","listener","he","ne","ae","ge","commandItem","_a","_b","el","text","applyFilter","q","release","atMidnight","date","addDays","count","addMonths","sameDay","a","b","isoOf","startOfWeek","weekStart","localeWeekStart","locale","_a","_b","localeObject","info","e","datePicker","props","_c","_d","mode","time","min","max","disabledDate","format","onChange","accentColor","nt","placeState","selection","releaseOnChange","value","primaryDate","current","base","viewYear","viewMonth","focused","hovered","hour","minute","contentElement","dateFormatter","__spreadValues","monthFormatter","weekdayFormatter","fullDateFormatter","formatOne","formatDisplay","start","end","weekdayNames","_unused","index","isDisabled","withTime","result","selectDate","instantHideRef","reapplyTime","inSelectedRange","listener","tail","low","high","day","isSelectedEnd","goToDate","shiftMonth","delta","next","shiftYear","focusActiveCell","calendar","buildCalendar","show","hide","anchorPartial","createFloating","triggerPartial","_e","node","openAndFocus","event","key","isSelectedPrimary","w","navButton","label","ariaLabel","onClick","navButtonStyle","header","he","ne","weekdayHeader","name","ge","gridRowStyle","grid","buildWeeks","onGridKey","children","buildTimeRow","buildFooter","ae","elevation","first","month","weeks","week","cells","buildDayCell","disabled","selected","within","outside","isFocused","isToday","l","numberSelect","state","timeSelectStyle","action","today","keyboard","descriptionList","props","_a","color","nt","node","ne","listener","he","ge","details","props","_a","_b","duration","color","nt","accentColor","node","listener","he","ge","ne","ae","lockCount","lockScroll","unlockScroll","FOCUSABLE","dialog","props","color","open","state","nt","previousFocus","closing","scrollLocked","finalizeClose","dlg","unlockScroll","node","e","r","closeTimer","trapFocus","focusables","el","first","last","onCancel","update","val","lockScroll","focusable","release","listener","he","ge","ne","ae","elevation","divider","props","_a","color","nt","node","ne","listener","he","ge","translateOut","marginMap","isVertical","p","resolvePhysical","placement","isRTL","drawer","props","color","open","size","state","nt","isLogical","physicalFallback","defaultSize","ne","drawerSize","node","e","dlg","onCancel","physical","closing","scrollLocked","closeTimer","finishClose","unlockScroll","onTransitionEnd","update","val","lockScroll","release","listener","he","ge","ae","elevation","emphasis","props","_a","color","nt","node","listener","he","ge","empty","props","_a","color","nt","ne","listener","ge","errorBoundary","props","node","error","reset","_a","_b","fallbackEl","SIZE_MAP","fab","props","_a","_b","color","nt","dim","ne","node","listener","he","ge","elevation","focusRing","figure","props","_a","color","nt","node","ne","listener","ge","he","formGroup","props","_a","layout","color","nt","isVertical","node","listener","ne","ae","he","ge","HeadingShift","heading","props","_a","color","nt","node","listener","ge","ne","offset","he","horizontalRule","props","_a","color","nt","node","ne","listener","ge","icon","props","_a","color","nt","node","ne","listener","he","ge","image","props","_a","color","nt","node","ne","listener","ge","inputCheckbox","props","_a","_b","color","nt","accentColor","node","listener","he","ne","ge","inputColor","_props","node","element","listener","he","ne","ae","ge","inputDateTime","props","_a","_b","mode","color","nt","accentColor","node","element","listener","he","ge","ne","ae","focusRing","inputFile","props","_a","_b","color","nt","accentColor","node","element","listener","he","ge","ne","ae","focusRing","inputNumber","props","_a","_b","color","nt","accentColor","node","element","ne","listener","ae","he","ge","focusRing","EYE_SVG","EYE_OFF_SVG","inputPassword","props","_a","_b","colorState","nt","accentState","visibleState","node","field","l","toggle","ne","ae","ge","he","focusRing","inputOTP","ne","node","container","getInputs","onInput","e","inputs","target","idx","onKeydown","onPaste","_a","_b","_c","text","found","startIdx","char","i","lastFilled","inputRadio","props","_a","_b","color","nt","accentColor","node","listener","he","ne","ge","inputRange","props","_a","_b","color","nt","accentColor","node","ne","listener","ge","inputSearch","props","_a","_b","color","nt","accentColor","node","element","listener","he","ge","ne","ae","focusRing","inputSwitch","props","_a","accentColor","nt","node","listener","he","ne","ge","inputText","props","_a","_b","color","nt","accentColor","node","element","ne","listener","ae","he","ge","focusRing","keyboard","props","_a","color","nt","node","listener","he","ge","ne","label","props","_a","_b","color","nt","accentColor","node","ne","listener","he","ge","link","props","_a","_b","color","nt","accentColor","node","listener","he","ge","ne","linkButton","props","_a","color","nt","node","listener","he","ne","ae","ge","focusRing","list","_props","listItem","props","dense","listener","ne","ae","he","listItemButton","_a","_b","color","nt","accentColor","ge","mark","props","_a","accentColor","nt","node","listener","he","ge","ne","menu","props","_a","items","selectable","color","accentColor","activeKey","nt","node","element","id","buttons","item","index","key","__spreadProps","__spreadValues","l","e","k","keys","it","i","idx","next","ne","he","ae","ge","elevation","isState","value","toStyles","frame","out","transforms","key","motion","props","_a","_b","_c","_d","initial","animate","exit","transition","options","node","el","target","release","next","done","orderedList","props","_a","color","nt","node","listener","he","ge","ne","getPages","current","total","_","i","pages","start","end","pagination","props","_a","color","accentColor","state","nt","btnBase","listener","ne","ae","he","ge","focusRing","activeStyle","__spreadProps","__spreadValues","node","content","page","items","ellipsisIndex","p","isActive","panelSection","props","_a","padding","divider","color","nt","__spreadValues","listener","ne","ae","ge","paragraph","props","_a","color","nt","node","listener","he","ge","popover","props","_a","open","placement","openOn","popoverId","openState","nt","placeState","show","hide","anchorPartial","createFloating","popoverPartial","l","ge","ne","ae","elevation","node","id","w","listener","_e","e","related","root","floatingEl","popoverArrow","props","placement","color","sideOffset","ne","bordered","place","nt","flipMap","getFlipped","listener","_a","start","pos","end","he","ge","x","y","preformated","props","_a","color","nt","node","listener","he","ge","ne","ae","progress","props","_a","_b","color","nt","accentColor","node","ne","listener","ge","STAR_FILLED","STAR_EMPTY","rating","props","_a","_b","max","readOnly","onChange","color","valueState","nt","hoveredState","activeCount","listener","hovered","ne","ge","node","i","index","interactive","next","e","current","target","star","__spreadProps","__spreadValues","focusRing","ringProgress","props","_a","_b","_c","size","thickness","value","nt","color","trackColor","holePercent","mask","l","node","ne","ge","row","props","gap","align","justify","wrap","__spreadValues","listener","ne","ae","scrollArea","props","_a","color","nt","ne","l","ge","segmented","props","_a","_b","_c","items","color","accentColor","value","nt","node","element","buttons","item","index","key","l","he","ne","ge","focusRing","select","props","color","accentColor","node","listener","he","ge","ne","ae","l","svg","Te","focusRing","selectBox","props","options","placement","color","open","multiple","state","nt","openState","show","hide","anchorPartial","createFloating","popoverPartial","_e","node","listener","ge","ne","ae","elevation","w","wrap","val","vals","opt","tag","_node","cur","filter","v","partial","he","selectItem","props","accentColor","color","value","node","select","state","listener","val","v","he","ne","ae","ge","selectList","props","_a","color","multiple","state","nt","inputs","listener","val","v","node","ne","ae","he","ge","skeleton","props","_a","color","nt","keyframes","animationName","we","listener","he","ge","ne","small","props","_a","color","nt","node","listener","he","ge","keyframes","animationName","we","spinner","props","_a","color","nt","node","listener","he","ge","ne","splitter","props","direction","defaultSize","min","max","_node","element","w","nt","splitterPanel","node","ctx","el","prop","isFirst","apply","size","release","splitterHandle","handle","isHorizontal","releaseAriaValue","onKeydown","e","step","next","cancelDrag","onMousedown","container","onMousemove","rect","raw","onMouseup","listener","ge","ne","stack","props","gap","align","__spreadValues","listener","ne","ae","steps","props","_a","items","direction","color","accentColor","current","nt","node","element","stepEls","item","index","l","cur","ne","he","ge","strong","props","_a","color","nt","node","listener","he","ge","subscript","props","_a","color","nt","node","listener","he","ge","superscript","props","_a","color","nt","node","listener","he","ge","table","props","_a","color","nt","node","listener","he","ge","ne","ae","l","tabs","props","_a","_b","_c","items","accentColor","color","activeKey","nt","node","element","id","tablist","item","index","key","l","e","k","keys","it","i","idx","next","he","ne","ae","ge","focusRing","panels","textarea","props","_a","_b","color","nt","accentColor","autoResize","node","el","resize","listener","ne","ae","he","ge","focusRing","timeline","timelineItem","props","_a","_b","_c","last","color","accentColor","activeState","nt","__spreadValues","listener","ne","ae","ge","toast","props","position","color","state","nt","isTop","isCenter","isRight","overlayEle","ne","rootNode","overlay","listener","ae","he","ge","elevation","node","done","finished","timer","finish","onEnd","e","_a","toggleGroup","props","_a","items","multiple","color","accentColor","value","nt","node","element","buttons","item","index","key","l","val","arr","v","he","ne","ge","focusRing","toolbar","props","row","toolbarSpacer","tooltip","props","open","placement","content","placeState","nt","contentState","tooltipId","contentElement","listener","show","hide","anchorPartial","createFloating","tooltipPartial","ne","ae","ge","he","elevation","popoverArrow","w","_e","node","e","getItemId","node","index","transitionGroup","props","duration","delay","previousRects","cancelMap","pendingTimers","pendingFrames","cancel","timer","frame","item","g","dom","_a","key","prev","next","deltaX","deltaY","cancelled","finish","onEnd","event","unorderedList","props","_a","color","nt","node","listener","he","ge","ne"]}
|