fernwell 0.3.0 → 0.5.0
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/CHANGELOG.md +49 -0
- package/README.md +59 -13
- package/dist/_position.d.cts +73 -0
- package/dist/_position.d.ts +73 -0
- package/dist/_tokenData.d.cts +12 -0
- package/dist/_tokenData.d.ts +12 -0
- package/dist/combobox.d.cts +28 -0
- package/dist/css.d.cts +2 -0
- package/dist/css.d.ts +2 -0
- package/dist/fernwell.cjs +5 -3
- package/dist/fernwell.cjs.map +4 -4
- package/dist/fernwell.css +456 -6
- package/dist/fernwell.esm.js +5 -3
- package/dist/fernwell.esm.js.map +4 -4
- package/dist/fernwell.iife.js +5 -3
- package/dist/fernwell.iife.js.map +4 -4
- package/dist/fernwell.min.css +2 -2
- package/dist/fernwell.tokens.css +7 -1
- package/dist/icon.d.cts +16 -0
- package/dist/icon.d.ts +16 -0
- package/dist/iife.d.cts +2 -0
- package/dist/iife.d.ts +2 -2
- package/dist/index.d.cts +58 -0
- package/dist/index.d.ts +31 -15
- package/dist/loading.d.cts +5 -0
- package/dist/menu.d.cts +49 -0
- package/dist/modal.d.cts +13 -0
- package/dist/nav.d.cts +3 -0
- package/dist/popover.d.cts +48 -0
- package/dist/popover.d.ts +48 -0
- package/dist/table.d.cts +40 -0
- package/dist/tabs.d.cts +43 -0
- package/dist/tabs.d.ts +43 -0
- package/dist/theme.d.cts +12 -0
- package/dist/theme.d.ts +2 -42
- package/dist/toast.d.cts +14 -0
- package/dist/tokens.d.cts +105 -0
- package/dist/tokens.d.ts +105 -0
- package/dist/tokens.json +12 -0
- package/dist/tooltip.d.cts +51 -0
- package/dist/tooltip.d.ts +51 -0
- package/package.json +32 -10
package/dist/fernwell.min.css
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
/*! fernwell v0.
|
|
2
|
-
@layer fw-tokens{:root,[data-theme=light]{--fw-text: #1F2430;--fw-text-soft: #565D6E;--fw-bg: #F5F6F1;--fw-bg-dim: #EAEBE4;--fw-surface: #FFFFFF;--fw-primary: #FFC145;--fw-primary-hover: color-mix(in srgb, var(--fw-primary), var(--fw-text) 12%);--fw-primary-soft: color-mix(in srgb, var(--fw-primary), white 35%);--fw-secondary: #4C3A73;--fw-secondary-hover: color-mix(in srgb, var(--fw-secondary), var(--fw-text) 15%);--fw-secondary-bg: color-mix(in srgb, var(--fw-secondary) 10%, var(--fw-surface));--fw-success: #3FA672;--fw-success-bg: color-mix(in srgb, var(--fw-success) 12%, var(--fw-surface));--fw-warning: #E8A521;--fw-warning-bg: color-mix(in srgb, var(--fw-warning) 14%, var(--fw-surface));--fw-danger: #E85B4F;--fw-danger-bg: color-mix(in srgb, var(--fw-danger) 13%, var(--fw-surface));--fw-info: #3E8FD0;--fw-info-bg: color-mix(in srgb, var(--fw-info) 12%, var(--fw-surface));--fw-on-primary: #1F2430;--fw-on-secondary: #FFFFFF;--fw-on-secondary-soft: color-mix(in srgb, var(--fw-on-secondary) 72%, transparent);--fw-on-secondary-fill: color-mix(in srgb, var(--fw-on-secondary) 10%, transparent);--fw-on-secondary-line: color-mix(in srgb, var(--fw-on-secondary) 16%, transparent);--fw-overlay: rgba(31, 36, 48, .55);--fw-overlay-soft: rgba(31, 36, 48, .32);--fw-focus-ring: 0 0 0 4px color-mix(in srgb, var(--fw-primary) 25%, transparent);--fw-font-display: "Plus Jakarta Sans", system-ui, sans-serif;--fw-font-body: "Inter", system-ui, sans-serif;--fw-font-mono: "IBM Plex Mono", ui-monospace, SFMono-Regular, Menlo, monospace;--fw-sp-1: 4px;--fw-sp-2: 8px;--fw-sp-3: 12px;--fw-sp-4: 16px;--fw-sp-5: 24px;--fw-sp-6: 32px;--fw-sp-7: 48px;--fw-sp-8: 64px;--fw-sp-9: 96px;--fw-r-sm: 10px;--fw-r-md: 16px;--fw-r-lg: 24px;--fw-r-xl: 32px;--fw-r-full: 999px;--fw-shadow-sm: 0 1px 2px rgba(31, 36, 48, .06), 0 1px 1px rgba(31, 36, 48, .04);--fw-shadow-md: 0 4px 12px rgba(31, 36, 48, .08), 0 2px 4px rgba(31, 36, 48, .04);--fw-shadow-lg: 0 12px 32px rgba(31, 36, 48, .12), 0 4px 8px rgba(31, 36, 48, .06);--fw-shadow-primary: 0 6px 16px color-mix(in srgb, var(--fw-primary) 35%, transparent);--fw-shadow-success: 0 6px 16px color-mix(in srgb, var(--fw-success) 28%, transparent);--fw-border-w: 1.5px;--fw-motion-fast: .12s;--fw-motion-base: .18s;--fw-motion-ease: ease}[data-theme=dark]{--fw-text: #F2F1EA;--fw-text-soft: #9CA1B0;--fw-bg: #14161C;--fw-bg-dim: #2B2F3B;--fw-surface: #1D2029;--fw-primary: #FFC145;--fw-primary-hover: color-mix(in srgb, var(--fw-primary), var(--fw-text) 12%);--fw-primary-soft: color-mix(in srgb, var(--fw-primary), white 35%);--fw-secondary: #6B54A3;--fw-secondary-hover: color-mix(in srgb, var(--fw-secondary), var(--fw-text) 15%);--fw-secondary-bg: color-mix(in srgb, var(--fw-secondary) 16%, transparent);--fw-success: #55D194;--fw-success-bg: color-mix(in srgb, var(--fw-success) 14%, transparent);--fw-warning: #FFD166;--fw-warning-bg: color-mix(in srgb, var(--fw-warning) 16%, transparent);--fw-danger: #FF8478;--fw-danger-bg: color-mix(in srgb, var(--fw-danger) 14%, transparent);--fw-info: #6BB3E8;--fw-info-bg: color-mix(in srgb, var(--fw-info) 14%, transparent);--fw-on-primary: #1F2430;--fw-on-secondary: #FFFFFF;--fw-on-secondary-soft: color-mix(in srgb, var(--fw-on-secondary) 72%, transparent);--fw-on-secondary-fill: color-mix(in srgb, var(--fw-on-secondary) 10%, transparent);--fw-on-secondary-line: color-mix(in srgb, var(--fw-on-secondary) 16%, transparent);--fw-overlay: rgba(0, 0, 0, .6);--fw-overlay-soft: rgba(0, 0, 0, .4);--fw-focus-ring: 0 0 0 4px color-mix(in srgb, var(--fw-primary) 25%, transparent);--fw-shadow-sm: 0 1px 2px rgba(0, 0, 0, .3);--fw-shadow-md: 0 4px 12px rgba(0, 0, 0, .35);--fw-shadow-lg: 0 12px 32px rgba(0, 0, 0, .45);--fw-shadow-primary: 0 6px 16px color-mix(in srgb, var(--fw-primary) 22%, transparent);--fw-shadow-success: 0 6px 16px color-mix(in srgb, var(--fw-success) 22%, transparent)}}.fw-root{background:var(--fw-bg);color:var(--fw-text);font-family:var(--fw-font-body);line-height:1.5;-webkit-font-smoothing:antialiased;transition:background var(--fw-motion-base) var(--fw-motion-ease),color var(--fw-motion-base) var(--fw-motion-ease)}.fw-root,.fw-root *,.fw-root *:before,.fw-root *:after{box-sizing:border-box}.fw-root :where(h1,h2,h3,h4){font-family:var(--fw-font-display);color:var(--fw-text);margin:0}.fw-root :where(p){margin:0}.fw-root :where(a){color:inherit}.fw-root :where(code){font-family:var(--fw-font-mono)}[hidden]{display:none!important}.fw-sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;border:0}.fw-scroll-lock{overflow:hidden}@media(prefers-reduced-motion:reduce){.fw-root{scroll-behavior:auto}.fw-btn,.fw-btn:hover,.fw-list-row,.fw-list-row:hover{transform:none}}.fw-wrap{max-width:1100px;margin:0 auto;padding:0 var(--fw-sp-5)}.fw-row{display:flex;gap:var(--fw-sp-4);flex-wrap:wrap;align-items:center}.fw-grid-2{display:grid;grid-template-columns:1fr 1fr;gap:var(--fw-sp-5)}@media(max-width:640px){.fw-grid-2{grid-template-columns:1fr}}.fw-btn{font-family:var(--fw-font-body);font-weight:700;font-size:15px;line-height:1.2;border-radius:var(--fw-r-md);padding:12px 22px;border:none;cursor:pointer;display:inline-flex;align-items:center;gap:var(--fw-sp-2);text-decoration:none;transition:transform var(--fw-motion-fast) var(--fw-motion-ease),box-shadow var(--fw-motion-fast) var(--fw-motion-ease),background var(--fw-motion-fast) var(--fw-motion-ease),border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-btn:hover{transform:translateY(-1px)}.fw-btn:active{transform:translateY(0)}.fw-btn:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-btn-primary{background:var(--fw-primary);color:var(--fw-on-primary);box-shadow:var(--fw-shadow-primary)}.fw-btn-primary:hover{background:var(--fw-primary-hover)}.fw-btn-secondary{background:var(--fw-secondary);color:var(--fw-on-secondary)}.fw-btn-secondary:hover{background:var(--fw-secondary-hover)}.fw-btn-ghost{background:transparent;color:var(--fw-text);border:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-btn-ghost:hover{border-color:var(--fw-text-soft)}.fw-btn-danger{background:var(--fw-danger-bg);color:var(--fw-danger)}.fw-btn-lg{padding:14px 26px}.fw-btn:disabled,.fw-btn[aria-disabled=true]{opacity:.45;cursor:not-allowed;transform:none}.fw-btn-loading{cursor:progress}.fw-btn .fw-spinner{margin-right:2px}.fw-icon-btn{width:32px;height:32px;border-radius:var(--fw-r-sm);border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:inline-flex;align-items:center;justify-content:center;cursor:pointer;color:var(--fw-text-soft);flex-shrink:0;padding:0;text-decoration:none;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease),color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-icon-btn:hover{border-color:var(--fw-secondary);color:var(--fw-secondary)}.fw-icon-btn:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-icon-btn svg{width:15px;height:15px}.fw-card{background:var(--fw-surface);border-radius:var(--fw-r-lg);border:var(--fw-border-w) solid var(--fw-bg-dim);box-shadow:var(--fw-shadow-sm);padding:var(--fw-sp-5);color:var(--fw-text)}.fw-tag{display:inline-flex;align-items:center;gap:6px;font-family:var(--fw-font-mono);font-size:12px;font-weight:600;line-height:1.3;padding:5px 12px;border-radius:var(--fw-r-md);transform:rotate(-2deg);background:var(--fw-bg-dim);color:var(--fw-text-soft);white-space:nowrap}.fw-tag:nth-of-type(2n){transform:rotate(1.5deg)}.fw-tag:nth-of-type(3n){transform:rotate(-1deg)}.fw-tag-pill,.fw-tag-pill:nth-of-type(n){transform:none;font-size:11px;padding:4px 10px;border-radius:var(--fw-r-full)}.fw-tag-live{background:var(--fw-success-bg);color:var(--fw-success)}.fw-tag-live:before{content:"";width:6px;height:6px;border-radius:50%;background:var(--fw-success)}.fw-tag-pending{background:var(--fw-warning-bg);color:var(--fw-warning)}.fw-tag-error{background:var(--fw-danger-bg);color:var(--fw-danger)}.fw-tag-info{background:var(--fw-info-bg);color:var(--fw-info)}.fw-tag-secondary{background:var(--fw-secondary-bg);color:var(--fw-secondary)}@media(prefers-reduced-motion:no-preference){.fw-tag{transition:transform var(--fw-motion-fast) var(--fw-motion-ease)}}.fw-eyebrow{display:inline-flex;align-items:center;gap:var(--fw-sp-2);font-family:var(--fw-font-mono);font-size:12px;font-weight:600;letter-spacing:.08em;text-transform:uppercase;color:var(--fw-secondary);background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);padding:7px 16px;border-radius:var(--fw-r-full);box-shadow:var(--fw-shadow-sm)}.fw-eyebrow:before{content:"";width:6px;height:6px;border-radius:50%;background:var(--fw-primary)}[data-theme=dark] .fw-eyebrow{color:var(--fw-secondary-hover)}.fw-field{display:flex;flex-direction:column;gap:6px;max-width:320px}.fw-field-full{max-width:none}.fw-label,.fw-field>label{font-size:13px;font-weight:600;color:var(--fw-text)}.fw-hint{font-size:12px;color:var(--fw-text-soft)}.fw-error-msg{font-size:12px;color:var(--fw-danger);font-weight:600}.fw-required{color:var(--fw-danger);font-weight:700;margin-left:3px}.fw-input,.fw-field input:not([type=checkbox]):not([type=radio]),.fw-field select,.fw-field textarea{font-family:var(--fw-font-body);font-size:15px;line-height:1.4;padding:11px 14px;border-radius:var(--fw-r-sm);border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);color:var(--fw-text);outline:none;width:100%;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease),box-shadow var(--fw-motion-fast) var(--fw-motion-ease),background var(--fw-motion-base) var(--fw-motion-ease),color var(--fw-motion-base) var(--fw-motion-ease)}textarea.fw-input,.fw-field textarea{min-height:96px;resize:vertical}.fw-input::placeholder,.fw-field input::placeholder,.fw-field textarea::placeholder{color:var(--fw-text-soft);opacity:1}.fw-input:focus,.fw-field input:focus,.fw-field select:focus,.fw-field textarea:focus{border-color:var(--fw-primary-hover);box-shadow:var(--fw-focus-ring)}.fw-input.is-error,.fw-input[aria-invalid=true],.fw-field.is-error input,.fw-field.is-error select,.fw-field.is-error textarea,.fw-field input.is-error,.fw-field textarea.is-error{border-color:var(--fw-danger)}.fw-input:disabled,.fw-field input:disabled,.fw-field select:disabled,.fw-field textarea:disabled{background:var(--fw-bg-dim);color:var(--fw-text-soft);border-color:var(--fw-bg-dim);cursor:not-allowed}.fw-field.is-disabled .fw-label,.fw-field.is-disabled>label{color:var(--fw-text-soft)}.fw-checkbox,.fw-radio,.fw-toggle{position:relative;display:inline-flex;align-items:center;gap:10px;cursor:pointer;font-family:var(--fw-font-body);font-size:14px;font-weight:600;color:var(--fw-text)}.fw-checkbox input,.fw-radio input,.fw-toggle input{position:absolute;opacity:0;width:0;height:0;margin:0}.fw-checkbox:has(input:disabled),.fw-radio:has(input:disabled),.fw-toggle:has(input:disabled){cursor:not-allowed}.fw-checkbox input:disabled~span,.fw-radio input:disabled~span,.fw-toggle input:disabled~span{color:var(--fw-text-soft)}.fw-option-group{display:flex;flex-direction:column;gap:var(--fw-sp-3)}.fw-option-group-inline{flex-direction:row;flex-wrap:wrap;gap:var(--fw-sp-5)}.fw-checkbox .fw-box{width:20px;height:20px;border-radius:6px;border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:background var(--fw-motion-fast) var(--fw-motion-ease),border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-checkbox .fw-box:after{content:"";width:12px;height:12px;opacity:0;background-color:var(--fw-on-primary);-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3 8.5L6.2 11.5L13 4.5' stroke='%23000' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3 8.5L6.2 11.5L13 4.5' stroke='%23000' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;transition:opacity .1s var(--fw-motion-ease)}.fw-checkbox input:checked+.fw-box{background:var(--fw-primary);border-color:var(--fw-primary)}.fw-checkbox input:checked+.fw-box:after{opacity:1}.fw-checkbox input:indeterminate+.fw-box{background:var(--fw-primary);border-color:var(--fw-primary)}.fw-checkbox input:indeterminate+.fw-box:after{opacity:1;-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3.5 8h9' stroke='%23000' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3.5 8h9' stroke='%23000' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat}.fw-checkbox input:focus-visible+.fw-box{box-shadow:var(--fw-focus-ring)}.fw-checkbox input:disabled+.fw-box{background:var(--fw-bg-dim);border-color:var(--fw-bg-dim)}.fw-radio .fw-box{width:20px;height:20px;border-radius:50%;border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-radio .fw-box:after{content:"";width:10px;height:10px;border-radius:50%;background:transparent;transition:background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-radio input:checked+.fw-box{border-color:var(--fw-primary)}.fw-radio input:checked+.fw-box:after{background:var(--fw-primary)}.fw-radio input:focus-visible+.fw-box{box-shadow:var(--fw-focus-ring)}.fw-radio input:disabled+.fw-box{background:var(--fw-bg-dim);border-color:var(--fw-bg-dim)}.fw-toggle .fw-track{width:42px;height:24px;border-radius:var(--fw-r-full);background:var(--fw-bg-dim);position:relative;flex-shrink:0;transition:background .16s var(--fw-motion-ease)}.fw-toggle .fw-thumb{position:absolute;top:2px;left:2px;width:20px;height:20px;border-radius:50%;background:var(--fw-surface);box-shadow:var(--fw-shadow-sm);transition:transform .16s var(--fw-motion-ease)}.fw-toggle input:checked+.fw-track{background:var(--fw-primary)}.fw-toggle input:checked+.fw-track .fw-thumb{transform:translate(18px)}.fw-toggle input:focus-visible+.fw-track{box-shadow:var(--fw-focus-ring)}.fw-toggle input:disabled+.fw-track{opacity:.5}.fw-combobox{position:relative}.fw-combobox-list{position:absolute;top:calc(100% + 6px);left:0;right:0;z-index:30;background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-md);box-shadow:var(--fw-shadow-lg);max-height:220px;overflow-y:auto;padding:6px;margin:0;list-style:none;opacity:0;transform:translateY(-4px);pointer-events:none;transition:opacity .14s var(--fw-motion-ease),transform .14s var(--fw-motion-ease)}.fw-combobox-list.is-open{opacity:1;transform:translateY(0);pointer-events:auto}.fw-combobox-option{padding:10px 12px;border-radius:var(--fw-r-sm);font-family:var(--fw-font-body);font-size:14px;cursor:pointer;color:var(--fw-text)}.fw-combobox-option:hover,.fw-combobox-option.is-active{background:var(--fw-bg)}.fw-combobox-option b{color:var(--fw-primary-hover);font-weight:700}.fw-combobox-empty{padding:14px 12px;font-size:13px;color:var(--fw-text-soft);text-align:center}@media(prefers-reduced-motion:reduce){.fw-combobox-list{transform:none}}.fw-alert{display:flex;gap:var(--fw-sp-3);padding:var(--fw-sp-4);border-radius:var(--fw-r-md);align-items:flex-start;font-family:var(--fw-font-body);color:var(--fw-text);background:var(--fw-bg-dim)}.fw-alert-dot{width:20px;height:20px;border-radius:50%;flex-shrink:0;margin-top:2px;background:var(--fw-text-soft)}.fw-alert-title{font-weight:700;font-size:14px}.fw-alert-body{font-size:13px;color:var(--fw-text-soft);margin-top:2px}.fw-alert-success{background:var(--fw-success-bg)}.fw-alert-success .fw-alert-dot{background:var(--fw-success)}.fw-alert-error{background:var(--fw-danger-bg)}.fw-alert-error .fw-alert-dot{background:var(--fw-danger)}.fw-alert-pending{background:var(--fw-warning-bg)}.fw-alert-pending .fw-alert-dot{background:var(--fw-warning)}.fw-alert-info{background:var(--fw-info-bg)}.fw-alert-info .fw-alert-dot{background:var(--fw-info)}.fw-alert-with-action{align-items:center;justify-content:space-between;flex-wrap:wrap}.fw-alert-with-action .fw-alert-main{display:flex;align-items:center;gap:var(--fw-sp-3)}.fw-progress-label{display:flex;justify-content:space-between;align-items:baseline;margin-bottom:6px;font-family:var(--fw-font-body);font-size:13px}.fw-progress-name{font-weight:600;color:var(--fw-text)}.fw-progress-pct{font-family:var(--fw-font-mono);color:var(--fw-text-soft)}.fw-progress{position:relative;height:10px;border-radius:var(--fw-r-full);background:var(--fw-bg-dim);overflow:hidden}.fw-progress-sm{height:8px}.fw-progress-fill{height:100%;border-radius:var(--fw-r-full);background:var(--fw-primary);transition:width .4s var(--fw-motion-ease)}.fw-progress.is-success .fw-progress-fill,.fw-progress-fill.is-success{background:var(--fw-success)}.fw-progress.is-indeterminate .fw-progress-fill{position:absolute;width:40%;left:-40%;animation:fw-indeterminate-slide 1.4s ease-in-out infinite}@keyframes fw-indeterminate-slide{0%{left:-40%;width:40%}50%{width:60%}to{left:100%;width:40%}}@media(prefers-reduced-motion:reduce){.fw-progress.is-indeterminate .fw-progress-fill{position:static;width:100%;animation:fw-pulse-opacity 1.2s ease-in-out infinite}}.fw-spinner{display:inline-block;border-radius:50%;flex-shrink:0;width:24px;height:24px;border:3px solid var(--fw-bg-dim);border-top-color:currentColor;animation:fw-spin .8s linear infinite}.fw-spinner-sm{width:16px;height:16px;border-width:2px}.fw-spinner-md{width:24px;height:24px;border-width:3px}.fw-spinner-lg{width:40px;height:40px;border-width:4px}@keyframes fw-spin{to{transform:rotate(360deg)}}@keyframes fw-pulse-opacity{0%,to{opacity:1}50%{opacity:.35}}@media(prefers-reduced-motion:reduce){.fw-spinner{animation:fw-pulse-opacity 1.2s ease-in-out infinite;border-top-color:var(--fw-bg-dim)}}.fw-nav{position:relative;background:var(--fw-secondary);border-radius:var(--fw-r-lg);padding:var(--fw-sp-4) var(--fw-sp-5);display:flex;align-items:center;justify-content:space-between;gap:var(--fw-sp-4);box-shadow:var(--fw-shadow-md);font-family:var(--fw-font-body);color:var(--fw-on-secondary)}.fw-nav-sticky{position:sticky;top:var(--fw-sp-5);z-index:100}.fw-nav-brand{color:var(--fw-on-secondary);font-family:var(--fw-font-display);font-weight:800;font-size:18px;display:flex;align-items:center;gap:var(--fw-sp-2);text-decoration:none}.fw-nav-dot{width:10px;height:10px;border-radius:50%;background:var(--fw-primary)}.fw-nav-hex{width:16px;height:16px;background:var(--fw-primary);clip-path:polygon(25% 0,75% 0,100% 50%,75% 100%,25% 100%,0 50%)}.fw-nav-links{display:flex;gap:var(--fw-sp-5);align-items:center}.fw-nav-links a{color:var(--fw-on-secondary-soft);font-size:14px;font-weight:600;text-decoration:none;transition:color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-nav-links a:hover{color:var(--fw-on-secondary)}.fw-nav-links a.is-active{color:var(--fw-on-secondary);border-bottom:2px solid var(--fw-primary);padding-bottom:3px}.fw-nav-right{display:flex;align-items:center;gap:var(--fw-sp-4)}.fw-nav-avatar{width:34px;height:34px;border-radius:var(--fw-r-sm);background:var(--fw-primary);display:flex;align-items:center;justify-content:center;font-weight:800;font-size:13px;color:var(--fw-on-primary);font-family:var(--fw-font-display);border:none;padding:0;cursor:default}.fw-nav-btn,.fw-nav-toggle{width:38px;height:38px;border-radius:var(--fw-r-sm);background:var(--fw-on-secondary-fill);border:var(--fw-border-w) solid var(--fw-on-secondary-line);color:var(--fw-on-secondary);cursor:pointer;display:flex;align-items:center;justify-content:center;padding:0;font-size:15px;transition:background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-nav-btn:hover,.fw-nav-toggle:hover{background:var(--fw-on-secondary-line)}.fw-nav-btn:focus-visible,.fw-nav-toggle:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-nav-toggle{display:none;flex-direction:column;gap:4px}.fw-nav-toggle span{width:16px;height:2px;background:var(--fw-on-secondary);border-radius:2px;transition:transform var(--fw-motion-base) var(--fw-motion-ease),opacity var(--fw-motion-base) var(--fw-motion-ease)}.fw-nav-toggle[aria-expanded=true] span:nth-child(1){transform:translateY(6px) rotate(45deg)}.fw-nav-toggle[aria-expanded=true] span:nth-child(2){opacity:0}.fw-nav-toggle[aria-expanded=true] span:nth-child(3){transform:translateY(-6px) rotate(-45deg)}.fw-nav-dropdown{position:absolute;top:calc(100% + 8px);left:0;right:0;z-index:20;background:var(--fw-surface);border-radius:var(--fw-r-lg);border:var(--fw-border-w) solid var(--fw-bg-dim);box-shadow:var(--fw-shadow-lg);padding:var(--fw-sp-3);display:flex;flex-direction:column;gap:2px;opacity:0;transform:translateY(-6px) scale(.98);pointer-events:none;transition:opacity .16s var(--fw-motion-ease),transform .16s var(--fw-motion-ease)}.fw-nav-dropdown.is-open{opacity:1;transform:translateY(0) scale(1);pointer-events:auto}.fw-nav-dropdown-menu{left:auto;min-width:200px}.fw-nav-dropdown a,.fw-nav-dropdown button{color:var(--fw-text);font-family:var(--fw-font-body);font-size:15px;font-weight:600;text-decoration:none;text-align:left;padding:12px 14px;border-radius:var(--fw-r-sm);background:none;border:none;cursor:pointer;transition:background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-nav-dropdown a:hover,.fw-nav-dropdown button:hover{background:var(--fw-bg)}.fw-nav-dropdown a.is-active{background:var(--fw-primary);color:var(--fw-on-primary)}@media(max-width:600px){.fw-nav-links{display:none}.fw-nav-toggle{display:flex}}@media(prefers-reduced-motion:reduce){.fw-nav-dropdown{transform:none}}.fw-stat-label{font-family:var(--fw-font-body);font-size:13px;color:var(--fw-text-soft);font-weight:600}.fw-stat-value{font-family:var(--fw-font-display);font-size:32px;font-weight:800;line-height:1.1;color:var(--fw-text);margin-top:4px}.fw-stat-value .fw-stat-unit{font-size:18px;color:var(--fw-primary-hover)}.fw-stat-delta{font-family:var(--fw-font-mono);font-size:12px;font-weight:600;color:var(--fw-text-soft);margin-top:4px}.fw-stat-delta.is-up{color:var(--fw-success)}.fw-stat-delta.is-down{color:var(--fw-danger)}.fw-empty{text-align:center;padding:var(--fw-sp-7) var(--fw-sp-5);font-family:var(--fw-font-body)}.fw-empty-blob{width:72px;height:72px;margin:0 auto var(--fw-sp-4);border-radius:38% 62% 60% 40%/48% 42% 58% 52%;background:linear-gradient(135deg,var(--fw-primary),var(--fw-primary-soft));display:flex;align-items:center;justify-content:center;font-size:28px}.fw-empty-title{font-family:var(--fw-font-display);font-size:17px;font-weight:700;color:var(--fw-text);margin:0 0 6px}.fw-empty-body{font-size:14px;color:var(--fw-text-soft);max-width:36ch;margin:0 auto var(--fw-sp-4)}.fw-modal-overlay{position:fixed;inset:0;background:var(--fw-overlay);display:flex;align-items:center;justify-content:center;padding:var(--fw-sp-5);z-index:100;opacity:0;pointer-events:none;transition:opacity var(--fw-motion-base) var(--fw-motion-ease)}.fw-modal-overlay.is-open{opacity:1;pointer-events:auto}.fw-modal{background:var(--fw-surface);color:var(--fw-text);font-family:var(--fw-font-body);border-radius:var(--fw-r-xl);box-shadow:var(--fw-shadow-lg);width:100%;max-width:460px;max-height:88vh;overflow-y:auto;padding:var(--fw-sp-6);transform:translateY(8px) scale(.98);transition:transform var(--fw-motion-base) var(--fw-motion-ease)}.fw-modal-wide{max-width:600px}.fw-modal-overlay.is-open .fw-modal{transform:translateY(0) scale(1)}.fw-modal-head{display:flex;justify-content:space-between;align-items:flex-start;gap:var(--fw-sp-3);margin-bottom:var(--fw-sp-5)}.fw-modal-head h2,.fw-modal-title{font-family:var(--fw-font-display);font-size:19px;font-weight:800;color:var(--fw-text);margin:0}.fw-modal-sub{font-size:13px;color:var(--fw-text-soft);margin:2px 0 0}.fw-modal-foot{display:flex;justify-content:flex-end;gap:var(--fw-sp-3);align-items:center;margin-top:var(--fw-sp-2);padding-top:var(--fw-sp-5);border-top:var(--fw-border-w) solid var(--fw-bg-dim)}@media(prefers-reduced-motion:reduce){.fw-modal{transform:none}}.fw-drawer-overlay{position:fixed;inset:0;background:var(--fw-overlay-soft);opacity:0;pointer-events:none;transition:opacity var(--fw-motion-base) var(--fw-motion-ease);z-index:90}.fw-drawer-overlay.is-open{opacity:1;pointer-events:auto}.fw-drawer{position:fixed;top:0;right:0;height:100%;width:440px;max-width:92vw;background:var(--fw-bg);color:var(--fw-text);font-family:var(--fw-font-body);box-shadow:var(--fw-shadow-lg);border-left:var(--fw-border-w) solid var(--fw-bg-dim);transform:translate(100%);transition:transform .24s var(--fw-motion-ease);z-index:91;display:flex;flex-direction:column}.fw-drawer.is-open{transform:translate(0)}.fw-drawer-head{padding:var(--fw-sp-5);border-bottom:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:flex;align-items:flex-start;gap:var(--fw-sp-3);flex-shrink:0}.fw-drawer-head-text{flex:1;min-width:0}.fw-drawer-eyebrow{font-family:var(--fw-font-mono);font-size:11px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--fw-text-soft);margin-bottom:4px}.fw-drawer-title{font-family:var(--fw-font-display);font-size:19px;font-weight:800;color:var(--fw-text);margin:0}.fw-drawer-title-input{font-family:var(--fw-font-display);font-size:19px;font-weight:800;color:var(--fw-text);border:none;background:transparent;padding:2px 0;width:100%;outline:none;border-radius:6px}.fw-drawer-title-input:focus{background:var(--fw-bg);padding:2px 6px;margin:0 -6px}.fw-drawer>form{flex:1;min-height:0;display:flex;flex-direction:column}.fw-drawer-body{flex:1;min-height:0;overflow-y:auto;-webkit-overflow-scrolling:touch;padding:var(--fw-sp-5);display:flex;flex-direction:column;gap:var(--fw-sp-5)}.fw-drawer-foot{padding:var(--fw-sp-4) var(--fw-sp-5);display:flex;align-items:center;justify-content:space-between;gap:var(--fw-sp-3);flex-shrink:0;border-top:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface)}@media(max-width:560px){.fw-drawer{left:0;width:auto;max-width:none}}@media(prefers-reduced-motion:reduce){.fw-drawer{transition:opacity var(--fw-motion-base) var(--fw-motion-ease);transform:none;opacity:0;pointer-events:none}.fw-drawer.is-open{opacity:1;pointer-events:auto}}.fw-toast{position:fixed;bottom:var(--fw-sp-6);right:var(--fw-sp-6);z-index:200;display:flex;align-items:center;gap:var(--fw-sp-3);max-width:min(360px,calc(100vw - 2 * var(--fw-sp-5)));background:var(--fw-success-bg);color:var(--fw-text);font-family:var(--fw-font-body);border-radius:var(--fw-r-md);padding:var(--fw-sp-3) var(--fw-sp-4);box-shadow:var(--fw-shadow-lg);font-size:13px;font-weight:600;transform:translateY(12px);opacity:0;pointer-events:none;transition:transform var(--fw-motion-base) var(--fw-motion-ease),opacity var(--fw-motion-base) var(--fw-motion-ease)}.fw-toast.is-show{transform:translateY(0);opacity:1;pointer-events:auto}.fw-toast-dot{width:8px;height:8px;border-radius:50%;background:var(--fw-success);flex-shrink:0}.fw-toast-error{background:var(--fw-danger-bg)}.fw-toast-error .fw-toast-dot{background:var(--fw-danger)}.fw-toast-info{background:var(--fw-info-bg)}.fw-toast-info .fw-toast-dot{background:var(--fw-info)}.fw-toast-pending{background:var(--fw-warning-bg)}.fw-toast-pending .fw-toast-dot{background:var(--fw-warning)}@media(prefers-reduced-motion:reduce){.fw-toast{transform:none}}.fw-list-row{display:block;background:var(--fw-surface);border-radius:var(--fw-r-lg);border:var(--fw-border-w) solid var(--fw-bg-dim);box-shadow:var(--fw-shadow-sm);padding:var(--fw-sp-4) var(--fw-sp-5);color:inherit;font-family:var(--fw-font-body);text-decoration:none;transition:transform var(--fw-motion-fast) var(--fw-motion-ease),box-shadow var(--fw-motion-fast) var(--fw-motion-ease)}.fw-list-row:hover{transform:translateY(-1px);box-shadow:var(--fw-shadow-md);text-decoration:none}.fw-list-row:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-list-row.is-locked{opacity:.6}.fw-list-row.is-locked:hover{transform:none;box-shadow:var(--fw-shadow-sm)}.fw-list-row+.fw-list-row{margin-top:var(--fw-sp-3)}.fw-list-row-main{display:flex;flex-wrap:wrap;align-items:center;gap:var(--fw-sp-2) var(--fw-sp-4)}.fw-list-row-title{font-family:var(--fw-font-display);font-weight:700;font-size:16px;color:var(--fw-text)}.fw-list-row-meta{font-size:13px;color:var(--fw-text-soft)}.fw-sub-list{margin:var(--fw-sp-2) 0 0 var(--fw-sp-5);padding-left:var(--fw-sp-4);border-left:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-sub-list-row{display:flex;flex-wrap:wrap;align-items:center;gap:var(--fw-sp-2) var(--fw-sp-3);padding:var(--fw-sp-2) 0}.fw-sub-list-row+.fw-sub-list-row{border-top:1px solid var(--fw-bg-dim)}.fw-sub-list-title{font-size:13.5px;font-weight:600;color:var(--fw-text)}.fw-disclosure>summary{cursor:pointer;color:var(--fw-secondary);font-family:var(--fw-font-body);font-weight:600;font-size:13px;list-style:none;display:flex;align-items:center;gap:6px}.fw-disclosure>summary::-webkit-details-marker{display:none}.fw-disclosure>summary:hover{text-decoration:underline}.fw-disclosure>summary:focus-visible{outline:none;border-radius:4px;box-shadow:var(--fw-focus-ring)}.fw-disclosure-chevron{width:12px;height:12px;flex-shrink:0;transition:transform .15s var(--fw-motion-ease)}.fw-disclosure[open]>summary .fw-disclosure-chevron{transform:rotate(180deg)}.fw-disclosure-count{font-family:var(--fw-font-mono);font-size:10.5px;font-weight:700;color:var(--fw-secondary);background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-full);padding:1px 7px}.fw-disclosure-body{margin-top:var(--fw-sp-3);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-md);padding:var(--fw-sp-4);background:var(--fw-bg);display:flex;flex-direction:column;gap:var(--fw-sp-3)}.fw-menu{--fw-menu-indent: var(--fw-sp-4);--fw-menu-row-h: 36px;font-family:var(--fw-font-body);color:var(--fw-text)}.fw-menu-list{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:2px}.fw-menu-group>.fw-menu-list{margin:2px 0 0 var(--fw-menu-indent);padding-left:var(--fw-sp-3);border-left:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-menu-link,.fw-menu-summary{display:flex;align-items:center;gap:var(--fw-sp-2);min-height:var(--fw-menu-row-h);padding:0 var(--fw-sp-3);border-radius:var(--fw-r-sm);color:var(--fw-text);font-family:var(--fw-font-body);font-size:14px;font-weight:600;line-height:1.3;text-decoration:none;text-align:left;background:none;border:none;cursor:pointer;transition:background-color var(--fw-motion-fast) var(--fw-motion-ease),color var(--fw-motion-fast) var(--fw-motion-ease)}@media(hover:hover){.fw-menu-link:hover,.fw-menu-summary:hover{background:var(--fw-bg);text-decoration:none}}.fw-menu-link:focus-visible,.fw-menu-summary:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-menu-link[aria-current=page]{background:var(--fw-secondary-bg);color:var(--fw-secondary)}.fw-menu-summary.is-current{color:var(--fw-secondary)}.fw-menu-summary{list-style:none;user-select:none}.fw-menu-summary::-webkit-details-marker{display:none}.fw-menu-summary:after{content:"";flex-shrink:0;width:16px;height:16px;margin-left:auto;background-color:currentColor;opacity:.55;-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M6 4l4 4-4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M6 4l4 4-4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;transition:transform var(--fw-motion-fast) var(--fw-motion-ease),opacity var(--fw-motion-fast) var(--fw-motion-ease)}.fw-menu-summary:hover:after,.fw-menu-summary.is-current:after{opacity:1}.fw-menu-group[open]>.fw-menu-summary:after{transform:rotate(90deg)}.fw-menu-split{position:relative}.fw-menu-split>.fw-menu-link{padding-right:44px}.fw-menu-summary-icon{position:absolute;top:0;right:0;width:var(--fw-menu-row-h);height:var(--fw-menu-row-h);min-height:0;padding:0;justify-content:center}.fw-menu-summary-icon:after{margin-left:0}.fw-menu-panel{padding:var(--fw-sp-2) var(--fw-sp-3) var(--fw-sp-4);color:var(--fw-text-soft);font-size:14px;line-height:1.5}.fw-menu-panel>:first-child{margin-top:0}.fw-menu-panel>:last-child{margin-bottom:0}.fw-menu-accordion>.fw-menu-group+.fw-menu-group{border-top:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-menu-accordion>.fw-menu-group>.fw-menu-summary{min-height:44px;padding-inline:0;border-radius:0;font-family:var(--fw-font-display);font-size:15px;font-weight:700}.fw-menu-accordion>.fw-menu-group>.fw-menu-summary:after{-webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E")}.fw-menu-accordion>.fw-menu-group[open]>.fw-menu-summary:after{transform:rotate(180deg)}@media(hover:hover){.fw-menu-accordion>.fw-menu-group>.fw-menu-summary:hover{background:none;color:var(--fw-secondary)}}.fw-menu-accordion>.fw-menu-group>.fw-menu-summary:focus-visible{border-radius:4px}.fw-menu-accordion>.fw-menu-group>.fw-menu-panel{padding-inline:0}@media(prefers-reduced-motion:reduce){.fw-menu-summary:after{transition:none}}.fw-pagination{display:flex;align-items:center;justify-content:space-between;flex-wrap:wrap;gap:var(--fw-sp-3);font-family:var(--fw-font-body)}.fw-pag-info,.fw-pag-label{font-family:var(--fw-font-mono);font-size:12px;color:var(--fw-text-soft)}.fw-pag-controls{display:flex;align-items:center;gap:var(--fw-sp-3)}.fw-btn-page{display:inline-flex;align-items:center;height:34px;padding:0 14px;border-radius:var(--fw-r-sm);border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);color:var(--fw-text);font-family:var(--fw-font-body);font-size:13px;font-weight:600;text-decoration:none;cursor:pointer;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-btn-page:hover{border-color:var(--fw-text-soft);text-decoration:none}.fw-btn-page:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-btn-page.is-disabled,.fw-btn-page[aria-disabled=true],.fw-btn-page:disabled{opacity:.35;cursor:not-allowed;pointer-events:none}.fw-table-wrap{overflow-x:auto;background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-lg);box-shadow:var(--fw-shadow-sm);font-family:var(--fw-font-body);color:var(--fw-text)}.fw-table-wrap:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-table-wrap.fw-table-sticky{max-height:var(--fw-table-max-height, 460px);overflow:auto}.fw-table-sticky .fw-table thead th{position:sticky;top:0;z-index:1}.fw-table{width:100%;border-collapse:separate;border-spacing:0;font-family:var(--fw-font-body);font-size:14px;line-height:1.4;color:var(--fw-text);text-align:left}.fw-table caption{caption-side:top;text-align:left;font-family:var(--fw-font-display);font-weight:700;font-size:16px;color:var(--fw-text);padding:var(--fw-sp-4) var(--fw-sp-5) var(--fw-sp-2)}.fw-table th,.fw-table td{padding:var(--fw-sp-3) var(--fw-sp-4);vertical-align:middle}.fw-table th:first-child,.fw-table td:first-child{padding-left:var(--fw-sp-5)}.fw-table th:last-child,.fw-table td:last-child{padding-right:var(--fw-sp-5)}.fw-table thead th{font-size:12px;font-weight:700;letter-spacing:.02em;color:var(--fw-text-soft);background:var(--fw-surface);border-bottom:var(--fw-border-w) solid var(--fw-bg-dim);white-space:nowrap}.fw-table tbody tr+tr>td{border-top:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-table tbody td{transition:background-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-table-striped tbody tr:nth-child(2n)>td{background:var(--fw-bg)}@media(hover:hover){.fw-table tbody tr:hover>td{background:var(--fw-secondary-bg)}}.fw-table tbody tr.is-selected>td,.fw-table tbody tr[aria-selected=true]>td{background:var(--fw-secondary-bg)}.fw-table tbody tr.is-selected>td:first-child,.fw-table tbody tr[aria-selected=true]>td:first-child{box-shadow:inset 3px 0 0 var(--fw-secondary)}.fw-table-compact th,.fw-table-compact td{padding:var(--fw-sp-2) var(--fw-sp-3);font-size:13px}.fw-table-compact th:first-child,.fw-table-compact td:first-child{padding-left:var(--fw-sp-4)}.fw-table-compact th:last-child,.fw-table-compact td:last-child{padding-right:var(--fw-sp-4)}.fw-table-num{font-family:var(--fw-font-mono);text-align:right;font-variant-numeric:tabular-nums;white-space:nowrap}.fw-table-num .fw-table-sort{flex-direction:row-reverse}.fw-table-select{width:1%;padding-right:0;box-sizing:border-box}.fw-table-select .fw-checkbox{gap:0;vertical-align:middle}.fw-table-actions{width:1%;text-align:right;white-space:nowrap;box-sizing:border-box}.fw-table-actions .fw-icon-btn{vertical-align:middle}.fw-table-actions>*+*{margin-left:var(--fw-sp-1)}.fw-table-empty>td{text-align:center;padding:var(--fw-sp-7) var(--fw-sp-5);color:var(--fw-text-soft);font-family:var(--fw-font-display)}.fw-table-empty:hover>td{background:transparent}.fw-table-loading>td{text-align:center;padding:var(--fw-sp-6) var(--fw-sp-5)}.fw-table[aria-busy=true] tbody,.fw-table.is-loading tbody{opacity:.5;pointer-events:none;transition:opacity var(--fw-motion-fast) var(--fw-motion-ease)}th[data-fw-sort]{cursor:pointer}.fw-table-sort{display:inline-flex;align-items:center;gap:var(--fw-sp-1);padding:2px 4px;margin:-2px -4px;border:0;background:none;font:inherit;color:inherit;letter-spacing:inherit;cursor:pointer;border-radius:6px}th[data-fw-sort]:hover .fw-table-sort,th[aria-sort=ascending] .fw-table-sort,th[aria-sort=descending] .fw-table-sort{color:var(--fw-text)}.fw-table-sort:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-table-sort:after{content:"";width:12px;height:12px;flex-shrink:0;background-color:currentColor;opacity:.35;-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M5 6.5l3-3 3 3M5 9.5l3 3 3-3' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M5 6.5l3-3 3 3M5 9.5l3 3 3-3' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;transition:opacity var(--fw-motion-fast) var(--fw-motion-ease)}th[aria-sort=ascending] .fw-table-sort:after{opacity:1;-webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 10l4-4 4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 10l4-4 4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E")}th[aria-sort=descending] .fw-table-sort:after{opacity:1;-webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E")}@media(max-width:560px){.fw-table{table-layout:fixed}.fw-table-select{width:var(--fw-table-select-w, 44px)}.fw-table-actions{width:var(--fw-table-actions-w, 96px)}.fw-table td:not(.fw-table-select):not(.fw-table-actions):not(.fw-table-num){white-space:normal;overflow-wrap:anywhere}.fw-table-num,.fw-table th{overflow:hidden;text-overflow:ellipsis}}
|
|
1
|
+
/*! fernwell v0.5.0 | MIT | https://github.com/JacobKnaack/fernwell */
|
|
2
|
+
@layer fw-tokens{:root,[data-theme=light]{--fw-text: #1F2430;--fw-text-soft: #565D6E;--fw-bg: #F5F6F1;--fw-bg-dim: #EAEBE4;--fw-surface: #FFFFFF;--fw-primary: #FFC145;--fw-primary-hover: color-mix(in srgb, var(--fw-primary), var(--fw-text) 12%);--fw-primary-soft: color-mix(in srgb, var(--fw-primary), white 35%);--fw-secondary: #4C3A73;--fw-secondary-hover: color-mix(in srgb, var(--fw-secondary), var(--fw-text) 15%);--fw-secondary-bg: color-mix(in srgb, var(--fw-secondary) 10%, var(--fw-surface));--fw-success: #3FA672;--fw-success-bg: color-mix(in srgb, var(--fw-success) 12%, var(--fw-surface));--fw-warning: #E8A521;--fw-warning-bg: color-mix(in srgb, var(--fw-warning) 14%, var(--fw-surface));--fw-danger: #E85B4F;--fw-danger-bg: color-mix(in srgb, var(--fw-danger) 13%, var(--fw-surface));--fw-info: #3E8FD0;--fw-info-bg: color-mix(in srgb, var(--fw-info) 12%, var(--fw-surface));--fw-on-primary: #1F2430;--fw-on-secondary: #FFFFFF;--fw-on-secondary-soft: color-mix(in srgb, var(--fw-on-secondary) 72%, transparent);--fw-on-secondary-fill: color-mix(in srgb, var(--fw-on-secondary) 10%, transparent);--fw-on-secondary-line: color-mix(in srgb, var(--fw-on-secondary) 16%, transparent);--fw-overlay: rgba(31, 36, 48, .55);--fw-overlay-soft: rgba(31, 36, 48, .32);--fw-focus-ring: 0 0 0 4px color-mix(in srgb, var(--fw-primary) 25%, transparent);--fw-scrollbar-thumb: var(--fw-text-soft);--fw-scrollbar-thumb-hover: color-mix(in srgb, var(--fw-text-soft), var(--fw-text) 15%);--fw-scrollbar-track: transparent;--fw-font-display: "Plus Jakarta Sans", system-ui, sans-serif;--fw-font-body: "Inter", system-ui, sans-serif;--fw-font-mono: "IBM Plex Mono", ui-monospace, SFMono-Regular, Menlo, monospace;--fw-sp-1: 4px;--fw-sp-2: 8px;--fw-sp-3: 12px;--fw-sp-4: 16px;--fw-sp-5: 24px;--fw-sp-6: 32px;--fw-sp-7: 48px;--fw-sp-8: 64px;--fw-sp-9: 96px;--fw-r-sm: 10px;--fw-r-md: 16px;--fw-r-lg: 24px;--fw-r-xl: 32px;--fw-r-full: 999px;--fw-shadow-sm: 0 1px 2px rgba(31, 36, 48, .06), 0 1px 1px rgba(31, 36, 48, .04);--fw-shadow-md: 0 4px 12px rgba(31, 36, 48, .08), 0 2px 4px rgba(31, 36, 48, .04);--fw-shadow-lg: 0 12px 32px rgba(31, 36, 48, .12), 0 4px 8px rgba(31, 36, 48, .06);--fw-shadow-primary: 0 6px 16px color-mix(in srgb, var(--fw-primary) 35%, transparent);--fw-shadow-success: 0 6px 16px color-mix(in srgb, var(--fw-success) 28%, transparent);--fw-border-w: 1.5px;--fw-motion-fast: .12s;--fw-motion-base: .18s;--fw-motion-ease: ease}[data-theme=dark]{--fw-text: #F2F1EA;--fw-text-soft: #9CA1B0;--fw-bg: #14161C;--fw-bg-dim: #2B2F3B;--fw-surface: #1D2029;--fw-primary: #FFC145;--fw-primary-hover: color-mix(in srgb, var(--fw-primary), var(--fw-text) 12%);--fw-primary-soft: color-mix(in srgb, var(--fw-primary), white 35%);--fw-secondary: #6B54A3;--fw-secondary-hover: color-mix(in srgb, var(--fw-secondary), var(--fw-text) 15%);--fw-secondary-bg: color-mix(in srgb, var(--fw-secondary) 16%, transparent);--fw-success: #55D194;--fw-success-bg: color-mix(in srgb, var(--fw-success) 14%, transparent);--fw-warning: #FFD166;--fw-warning-bg: color-mix(in srgb, var(--fw-warning) 16%, transparent);--fw-danger: #FF8478;--fw-danger-bg: color-mix(in srgb, var(--fw-danger) 14%, transparent);--fw-info: #6BB3E8;--fw-info-bg: color-mix(in srgb, var(--fw-info) 14%, transparent);--fw-on-primary: #1F2430;--fw-on-secondary: #FFFFFF;--fw-on-secondary-soft: color-mix(in srgb, var(--fw-on-secondary) 72%, transparent);--fw-on-secondary-fill: color-mix(in srgb, var(--fw-on-secondary) 10%, transparent);--fw-on-secondary-line: color-mix(in srgb, var(--fw-on-secondary) 16%, transparent);--fw-overlay: rgba(0, 0, 0, .6);--fw-overlay-soft: rgba(0, 0, 0, .4);--fw-focus-ring: 0 0 0 4px color-mix(in srgb, var(--fw-primary) 25%, transparent);--fw-scrollbar-thumb: var(--fw-text-soft);--fw-scrollbar-thumb-hover: color-mix(in srgb, var(--fw-text-soft), var(--fw-text) 15%);--fw-scrollbar-track: transparent;--fw-shadow-sm: 0 1px 2px rgba(0, 0, 0, .3);--fw-shadow-md: 0 4px 12px rgba(0, 0, 0, .35);--fw-shadow-lg: 0 12px 32px rgba(0, 0, 0, .45);--fw-shadow-primary: 0 6px 16px color-mix(in srgb, var(--fw-primary) 22%, transparent);--fw-shadow-success: 0 6px 16px color-mix(in srgb, var(--fw-success) 22%, transparent)}}.fw-root{background:var(--fw-bg);color:var(--fw-text);font-family:var(--fw-font-body);line-height:1.5;-webkit-font-smoothing:antialiased;transition:background var(--fw-motion-base) var(--fw-motion-ease),color var(--fw-motion-base) var(--fw-motion-ease)}[data-fw-theme-init],[data-fw-theme-init] *{transition:none!important}.fw-root,.fw-root *,.fw-root *:before,.fw-root *:after{box-sizing:border-box}.fw-root :where(h1,h2,h3,h4){font-family:var(--fw-font-display);color:var(--fw-text);margin:0}.fw-root :where(p){margin:0}.fw-root :where(a){color:inherit}.fw-root :where(code){font-family:var(--fw-font-mono)}[hidden]{display:none!important}.fw-sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;border:0}html:has(body.fw-scroll-lock){scrollbar-gutter:stable}.fw-scroll-lock{overflow:hidden}@media(prefers-reduced-motion:reduce){.fw-root{scroll-behavior:auto}.fw-btn,.fw-btn:hover,.fw-list-row,.fw-list-row:hover{transform:none}}.fw-wrap{max-width:1100px;margin:0 auto;padding:0 var(--fw-sp-5)}.fw-row{display:flex;gap:var(--fw-sp-4);flex-wrap:wrap;align-items:center}.fw-grid-2{display:grid;grid-template-columns:1fr 1fr;gap:var(--fw-sp-5)}@media(max-width:640px){.fw-grid-2{grid-template-columns:1fr}}.fw-spacer{display:block;flex-shrink:0}.fw-spacer[data-fw-axis=horizontal]{display:inline-block;width:var(--fw-spacer-size, var(--fw-sp-4));height:1px}.fw-spacer:not([data-fw-axis=horizontal]):not([data-fw-axis=both]){width:100%;height:var(--fw-spacer-size, var(--fw-sp-4))}.fw-spacer[data-fw-axis=both]{width:var(--fw-spacer-size, var(--fw-sp-4));height:var(--fw-spacer-size, var(--fw-sp-4))}.fw-spacer[data-fw-size="1"]{--fw-spacer-size: var(--fw-sp-1)}.fw-spacer[data-fw-size="2"]{--fw-spacer-size: var(--fw-sp-2)}.fw-spacer[data-fw-size="3"]{--fw-spacer-size: var(--fw-sp-3)}.fw-spacer[data-fw-size="4"]{--fw-spacer-size: var(--fw-sp-4)}.fw-spacer[data-fw-size="5"]{--fw-spacer-size: var(--fw-sp-5)}.fw-spacer[data-fw-size="6"]{--fw-spacer-size: var(--fw-sp-6)}.fw-spacer[data-fw-size="7"]{--fw-spacer-size: var(--fw-sp-7)}.fw-spacer[data-fw-size="8"]{--fw-spacer-size: var(--fw-sp-8)}.fw-spacer[data-fw-size="9"]{--fw-spacer-size: var(--fw-sp-9)}.fw-spacer[data-fw-size=auto]{flex:1 1 auto;width:auto;height:auto}.fw-divider{border:none;margin:0;flex-shrink:0;background:var(--fw-bg-dim)}.fw-divider,.fw-divider[aria-orientation=horizontal]{width:100%;height:var(--fw-border-w)}.fw-divider[aria-orientation=vertical]{width:var(--fw-border-w);height:100%;align-self:stretch}.fw-divider-dashed,.fw-divider-dotted{background:none;height:0}.fw-divider-dashed{border-top:var(--fw-border-w) dashed var(--fw-bg-dim)}.fw-divider-dotted{border-top:var(--fw-border-w) dotted var(--fw-bg-dim)}.fw-divider[aria-orientation=vertical].fw-divider-dashed,.fw-divider[aria-orientation=vertical].fw-divider-dotted{width:0;border-top:none}.fw-divider[aria-orientation=vertical].fw-divider-dashed{border-left:var(--fw-border-w) dashed var(--fw-bg-dim)}.fw-divider[aria-orientation=vertical].fw-divider-dotted{border-left:var(--fw-border-w) dotted var(--fw-bg-dim)}.fw-divider-labeled{display:flex;align-items:center;gap:var(--fw-sp-3);width:100%;color:var(--fw-text-soft);font-size:13px;font-family:var(--fw-font-body)}.fw-divider-labeled:before,.fw-divider-labeled:after{content:"";flex:1;height:var(--fw-border-w);background:var(--fw-bg-dim)}.fw-divider-labeled-start:before{flex:0 0 var(--fw-sp-5)}.fw-divider-labeled-end:after{flex:0 0 var(--fw-sp-5)}.fw-aspect-ratio{position:relative;overflow:hidden;width:100%;aspect-ratio:var(--fw-aspect-ratio, 16 / 9)}.fw-aspect-ratio>img,.fw-aspect-ratio>video,.fw-aspect-ratio>iframe,.fw-aspect-ratio>.fw-aspect-ratio-media{display:block;width:100%;height:100%;object-fit:cover;object-position:var(--fw-aspect-position, 50% 50%)}.fw-aspect-ratio[data-fw-ratio="1:1"]{--fw-aspect-ratio: 1 / 1}.fw-aspect-ratio[data-fw-ratio="4:3"]{--fw-aspect-ratio: 4 / 3}.fw-aspect-ratio[data-fw-ratio="16:9"]{--fw-aspect-ratio: 16 / 9}.fw-aspect-ratio[data-fw-ratio="21:9"]{--fw-aspect-ratio: 21 / 9}.fw-aspect-ratio[data-fw-fit=contain]>img,.fw-aspect-ratio[data-fw-fit=contain]>video,.fw-aspect-ratio[data-fw-fit=contain]>iframe,.fw-aspect-ratio[data-fw-fit=contain]>.fw-aspect-ratio-media{object-fit:contain}.fw-btn{font-family:var(--fw-font-body);font-weight:700;font-size:15px;line-height:1.2;border-radius:var(--fw-r-md);padding:12px 22px;border:none;cursor:pointer;display:inline-flex;align-items:center;gap:var(--fw-sp-2);text-decoration:none;transition:transform var(--fw-motion-fast) var(--fw-motion-ease),box-shadow var(--fw-motion-fast) var(--fw-motion-ease),background var(--fw-motion-fast) var(--fw-motion-ease),border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-btn:hover{transform:translateY(-1px)}.fw-btn:active{transform:translateY(0)}.fw-btn:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-btn-primary{background:var(--fw-primary);color:var(--fw-on-primary);box-shadow:var(--fw-shadow-primary)}.fw-btn-primary:hover{background:var(--fw-primary-hover)}.fw-btn-secondary{background:var(--fw-secondary);color:var(--fw-on-secondary)}.fw-btn-secondary:hover{background:var(--fw-secondary-hover)}.fw-btn-ghost{background:transparent;color:var(--fw-text);border:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-btn-ghost:hover{border-color:var(--fw-text-soft)}.fw-btn-danger{background:var(--fw-danger-bg);color:var(--fw-danger)}.fw-btn-lg{padding:14px 26px}.fw-btn:disabled,.fw-btn[aria-disabled=true]{opacity:.45;cursor:not-allowed;transform:none}.fw-btn-loading{cursor:progress}.fw-btn .fw-spinner{margin-right:2px}.fw-icon-btn{width:32px;height:32px;border-radius:var(--fw-r-sm);border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:inline-flex;align-items:center;justify-content:center;cursor:pointer;color:var(--fw-text-soft);flex-shrink:0;padding:0;text-decoration:none;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease),color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-icon-btn:hover{border-color:var(--fw-secondary);color:var(--fw-secondary)}.fw-icon-btn:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-icon-btn svg{width:15px;height:15px}.fw-icon{display:inline-flex;width:1em;height:1em;color:inherit;vertical-align:-.125em}.fw-icon svg{width:100%;height:100%;display:block}.fw-card{background:var(--fw-surface);border-radius:var(--fw-r-lg);border:var(--fw-border-w) solid var(--fw-bg-dim);box-shadow:var(--fw-shadow-sm);padding:var(--fw-sp-5);color:var(--fw-text)}.fw-tag{display:inline-flex;align-items:center;gap:6px;font-family:var(--fw-font-mono);font-size:12px;font-weight:600;line-height:1.3;padding:5px 12px;border-radius:var(--fw-r-md);transform:rotate(-2deg);background:var(--fw-bg-dim);color:var(--fw-text-soft);white-space:nowrap}.fw-tag:nth-of-type(2n){transform:rotate(1.5deg)}.fw-tag:nth-of-type(3n){transform:rotate(-1deg)}.fw-tag-pill,.fw-tag-pill:nth-of-type(n){transform:none;font-size:11px;padding:4px 10px;border-radius:var(--fw-r-full)}.fw-tag-live{background:var(--fw-success-bg);color:var(--fw-success)}.fw-tag-live:before{content:"";width:6px;height:6px;border-radius:50%;background:var(--fw-success)}.fw-tag-pending{background:var(--fw-warning-bg);color:var(--fw-warning)}.fw-tag-error{background:var(--fw-danger-bg);color:var(--fw-danger)}.fw-tag-info{background:var(--fw-info-bg);color:var(--fw-info)}.fw-tag-secondary{background:var(--fw-secondary-bg);color:var(--fw-secondary)}@media(prefers-reduced-motion:no-preference){.fw-tag{transition:transform var(--fw-motion-fast) var(--fw-motion-ease)}}.fw-eyebrow{display:inline-flex;align-items:center;gap:var(--fw-sp-2);font-family:var(--fw-font-mono);font-size:12px;font-weight:600;letter-spacing:.08em;text-transform:uppercase;color:var(--fw-secondary);background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);padding:7px 16px;border-radius:var(--fw-r-full);box-shadow:var(--fw-shadow-sm)}.fw-eyebrow:before{content:"";width:6px;height:6px;border-radius:50%;background:var(--fw-primary)}[data-theme=dark] .fw-eyebrow{color:var(--fw-secondary-hover)}.fw-field{display:flex;flex-direction:column;gap:6px;max-width:320px}.fw-field-full{max-width:none}.fw-label,.fw-field>label{font-size:13px;font-weight:600;color:var(--fw-text)}.fw-hint{font-size:12px;color:var(--fw-text-soft)}.fw-error-msg{font-size:12px;color:var(--fw-danger);font-weight:600}.fw-required{color:var(--fw-danger);font-weight:700;margin-left:3px}.fw-input,.fw-field input:not([type=checkbox]):not([type=radio]),.fw-field select,.fw-field textarea{font-family:var(--fw-font-body);font-size:15px;line-height:1.4;padding:11px 14px;border-radius:var(--fw-r-sm);border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);color:var(--fw-text);outline:none;width:100%;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease),box-shadow var(--fw-motion-fast) var(--fw-motion-ease),background var(--fw-motion-base) var(--fw-motion-ease),color var(--fw-motion-base) var(--fw-motion-ease)}textarea.fw-input,.fw-field textarea{min-height:96px;resize:vertical}.fw-input::placeholder,.fw-field input::placeholder,.fw-field textarea::placeholder{color:var(--fw-text-soft);opacity:1}.fw-input:focus,.fw-field input:focus,.fw-field select:focus,.fw-field textarea:focus{border-color:var(--fw-primary-hover);box-shadow:var(--fw-focus-ring)}.fw-input.is-error,.fw-input[aria-invalid=true],.fw-field.is-error input,.fw-field.is-error select,.fw-field.is-error textarea,.fw-field input.is-error,.fw-field textarea.is-error{border-color:var(--fw-danger)}.fw-input:disabled,.fw-field input:disabled,.fw-field select:disabled,.fw-field textarea:disabled{background:var(--fw-bg-dim);color:var(--fw-text-soft);border-color:var(--fw-bg-dim);cursor:not-allowed}.fw-field.is-disabled .fw-label,.fw-field.is-disabled>label{color:var(--fw-text-soft)}.fw-checkbox,.fw-radio,.fw-toggle{position:relative;display:inline-flex;align-items:center;gap:10px;cursor:pointer;font-family:var(--fw-font-body);font-size:14px;font-weight:600;color:var(--fw-text)}.fw-checkbox input,.fw-radio input,.fw-toggle input{position:absolute;opacity:0;width:0;height:0;margin:0}.fw-checkbox:has(input:disabled),.fw-radio:has(input:disabled),.fw-toggle:has(input:disabled){cursor:not-allowed}.fw-checkbox input:disabled~span,.fw-radio input:disabled~span,.fw-toggle input:disabled~span{color:var(--fw-text-soft)}.fw-option-group{display:flex;flex-direction:column;gap:var(--fw-sp-3)}.fw-option-group-inline{flex-direction:row;flex-wrap:wrap;gap:var(--fw-sp-5)}.fw-checkbox .fw-box{width:20px;height:20px;border-radius:6px;border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:background var(--fw-motion-fast) var(--fw-motion-ease),border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-checkbox .fw-box:after{content:"";width:12px;height:12px;opacity:0;background-color:var(--fw-on-primary);-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3 8.5L6.2 11.5L13 4.5' stroke='%23000' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3 8.5L6.2 11.5L13 4.5' stroke='%23000' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;transition:opacity .1s var(--fw-motion-ease)}.fw-checkbox input:checked+.fw-box{background:var(--fw-primary);border-color:var(--fw-primary)}.fw-checkbox input:checked+.fw-box:after{opacity:1}.fw-checkbox input:indeterminate+.fw-box{background:var(--fw-primary);border-color:var(--fw-primary)}.fw-checkbox input:indeterminate+.fw-box:after{opacity:1;-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3.5 8h9' stroke='%23000' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M3.5 8h9' stroke='%23000' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat}.fw-checkbox input:focus-visible+.fw-box{box-shadow:var(--fw-focus-ring)}.fw-checkbox input:disabled+.fw-box{background:var(--fw-bg-dim);border-color:var(--fw-bg-dim)}.fw-radio .fw-box{width:20px;height:20px;border-radius:50%;border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-radio .fw-box:after{content:"";width:10px;height:10px;border-radius:50%;background:transparent;transition:background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-radio input:checked+.fw-box{border-color:var(--fw-primary)}.fw-radio input:checked+.fw-box:after{background:var(--fw-primary)}.fw-radio input:focus-visible+.fw-box{box-shadow:var(--fw-focus-ring)}.fw-radio input:disabled+.fw-box{background:var(--fw-bg-dim);border-color:var(--fw-bg-dim)}.fw-toggle .fw-track{width:42px;height:24px;border-radius:var(--fw-r-full);background:var(--fw-bg-dim);position:relative;flex-shrink:0;transition:background .16s var(--fw-motion-ease)}.fw-toggle .fw-thumb{position:absolute;top:2px;left:2px;width:20px;height:20px;border-radius:50%;background:var(--fw-surface);box-shadow:var(--fw-shadow-sm);transition:transform .16s var(--fw-motion-ease)}.fw-toggle input:checked+.fw-track{background:var(--fw-primary)}.fw-toggle input:checked+.fw-track .fw-thumb{transform:translate(18px)}.fw-toggle input:focus-visible+.fw-track{box-shadow:var(--fw-focus-ring)}.fw-toggle input:disabled+.fw-track{opacity:.5}.fw-combobox{position:relative}.fw-combobox-list{position:absolute;top:calc(100% + 6px);left:0;right:0;z-index:30;background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-md);box-shadow:var(--fw-shadow-lg);max-height:220px;overflow-y:auto;padding:6px;margin:0;list-style:none;opacity:0;transform:translateY(-4px);pointer-events:none;transition:opacity .14s var(--fw-motion-ease),transform .14s var(--fw-motion-ease)}.fw-combobox-list.is-open{opacity:1;transform:translateY(0);pointer-events:auto}.fw-combobox-option{padding:10px 12px;border-radius:var(--fw-r-sm);font-family:var(--fw-font-body);font-size:14px;cursor:pointer;color:var(--fw-text)}.fw-combobox-option:hover,.fw-combobox-option.is-active{background:var(--fw-bg)}.fw-combobox-option b{color:var(--fw-primary-hover);font-weight:700}.fw-combobox-empty{padding:14px 12px;font-size:13px;color:var(--fw-text-soft);text-align:center}@media(prefers-reduced-motion:reduce){.fw-combobox-list{transform:none}}.fw-alert{display:flex;gap:var(--fw-sp-3);padding:var(--fw-sp-4);border-radius:var(--fw-r-md);align-items:flex-start;font-family:var(--fw-font-body);color:var(--fw-text);background:var(--fw-bg-dim)}.fw-alert-dot{width:20px;height:20px;border-radius:50%;flex-shrink:0;margin-top:2px;background:var(--fw-text-soft)}.fw-alert-title{font-weight:700;font-size:14px}.fw-alert-body{font-size:13px;color:var(--fw-text-soft);margin-top:2px}.fw-alert-success{background:var(--fw-success-bg)}.fw-alert-success .fw-alert-dot{background:var(--fw-success)}.fw-alert-error{background:var(--fw-danger-bg)}.fw-alert-error .fw-alert-dot{background:var(--fw-danger)}.fw-alert-pending{background:var(--fw-warning-bg)}.fw-alert-pending .fw-alert-dot{background:var(--fw-warning)}.fw-alert-info{background:var(--fw-info-bg)}.fw-alert-info .fw-alert-dot{background:var(--fw-info)}.fw-alert-with-action{align-items:center;justify-content:space-between;flex-wrap:wrap}.fw-alert-with-action .fw-alert-main{display:flex;align-items:center;gap:var(--fw-sp-3)}.fw-progress-label{display:flex;justify-content:space-between;align-items:baseline;margin-bottom:6px;font-family:var(--fw-font-body);font-size:13px}.fw-progress-name{font-weight:600;color:var(--fw-text)}.fw-progress-pct{font-family:var(--fw-font-mono);color:var(--fw-text-soft)}.fw-progress{position:relative;height:10px;border-radius:var(--fw-r-full);background:var(--fw-bg-dim);overflow:hidden}.fw-progress-sm{height:8px}.fw-progress-fill{height:100%;border-radius:var(--fw-r-full);background:var(--fw-primary);transition:width .4s var(--fw-motion-ease)}.fw-progress.is-success .fw-progress-fill,.fw-progress-fill.is-success{background:var(--fw-success)}.fw-progress.is-indeterminate .fw-progress-fill{position:absolute;width:40%;left:-40%;animation:fw-indeterminate-slide 1.4s ease-in-out infinite}@keyframes fw-indeterminate-slide{0%{left:-40%;width:40%}50%{width:60%}to{left:100%;width:40%}}@media(prefers-reduced-motion:reduce){.fw-progress.is-indeterminate .fw-progress-fill{position:static;width:100%;animation:fw-pulse-opacity 1.2s ease-in-out infinite}}.fw-spinner{display:inline-block;border-radius:50%;flex-shrink:0;width:24px;height:24px;border:3px solid var(--fw-bg-dim);border-top-color:currentColor;animation:fw-spin .8s linear infinite}.fw-spinner-sm{width:16px;height:16px;border-width:2px}.fw-spinner-md{width:24px;height:24px;border-width:3px}.fw-spinner-lg{width:40px;height:40px;border-width:4px}@keyframes fw-spin{to{transform:rotate(360deg)}}@keyframes fw-pulse-opacity{0%,to{opacity:1}50%{opacity:.35}}@media(prefers-reduced-motion:reduce){.fw-spinner{animation:fw-pulse-opacity 1.2s ease-in-out infinite;border-top-color:var(--fw-bg-dim)}}.fw-nav{position:relative;background:var(--fw-secondary);border-radius:var(--fw-r-lg);padding:var(--fw-sp-4) var(--fw-sp-5);display:flex;align-items:center;justify-content:space-between;gap:var(--fw-sp-4);box-shadow:var(--fw-shadow-md);font-family:var(--fw-font-body);color:var(--fw-on-secondary)}.fw-nav-sticky{position:sticky;top:var(--fw-sp-5);z-index:100}.fw-nav-brand{color:var(--fw-on-secondary);font-family:var(--fw-font-display);font-weight:800;font-size:18px;display:flex;align-items:center;gap:var(--fw-sp-2);text-decoration:none}.fw-nav-dot{width:10px;height:10px;border-radius:50%;background:var(--fw-primary)}.fw-nav-hex{width:16px;height:16px;background:var(--fw-primary);clip-path:polygon(25% 0,75% 0,100% 50%,75% 100%,25% 100%,0 50%)}.fw-nav-links{display:flex;gap:var(--fw-sp-5);align-items:center}.fw-nav-links a{color:var(--fw-on-secondary-soft);font-size:14px;font-weight:600;text-decoration:none;transition:color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-nav-links a:hover{color:var(--fw-on-secondary)}.fw-nav-links a.is-active{color:var(--fw-on-secondary);border-bottom:2px solid var(--fw-primary);padding-bottom:3px}.fw-nav-right{display:flex;align-items:center;gap:var(--fw-sp-4)}.fw-nav-avatar{width:34px;height:34px;border-radius:var(--fw-r-sm);background:var(--fw-primary);display:flex;align-items:center;justify-content:center;font-weight:800;font-size:13px;color:var(--fw-on-primary);font-family:var(--fw-font-display);border:none;padding:0;cursor:default}.fw-nav-btn,.fw-nav-toggle{width:38px;height:38px;border-radius:var(--fw-r-sm);background:var(--fw-on-secondary-fill);border:var(--fw-border-w) solid var(--fw-on-secondary-line);color:var(--fw-on-secondary);cursor:pointer;display:flex;align-items:center;justify-content:center;padding:0;font-size:15px;transition:background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-nav-btn:hover,.fw-nav-toggle:hover{background:var(--fw-on-secondary-line)}.fw-nav-btn:focus-visible,.fw-nav-toggle:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-nav-toggle{display:none;flex-direction:column;gap:4px}.fw-nav-toggle span{width:16px;height:2px;background:var(--fw-on-secondary);border-radius:2px;transition:transform var(--fw-motion-base) var(--fw-motion-ease),opacity var(--fw-motion-base) var(--fw-motion-ease)}.fw-nav-toggle[aria-expanded=true] span:nth-child(1){transform:translateY(6px) rotate(45deg)}.fw-nav-toggle[aria-expanded=true] span:nth-child(2){opacity:0}.fw-nav-toggle[aria-expanded=true] span:nth-child(3){transform:translateY(-6px) rotate(-45deg)}.fw-nav-dropdown{position:absolute;top:calc(100% + 8px);left:0;right:0;z-index:20;background:var(--fw-surface);border-radius:var(--fw-r-lg);border:var(--fw-border-w) solid var(--fw-bg-dim);box-shadow:var(--fw-shadow-lg);padding:var(--fw-sp-3);display:flex;flex-direction:column;gap:2px;opacity:0;transform:translateY(-6px) scale(.98);pointer-events:none;transition:opacity .16s var(--fw-motion-ease),transform .16s var(--fw-motion-ease)}.fw-nav-dropdown.is-open{opacity:1;transform:translateY(0) scale(1);pointer-events:auto}.fw-nav-dropdown-menu{left:auto;min-width:200px}.fw-nav-dropdown a,.fw-nav-dropdown button{color:var(--fw-text);font-family:var(--fw-font-body);font-size:15px;font-weight:600;text-decoration:none;text-align:left;padding:12px 14px;border-radius:var(--fw-r-sm);background:none;border:none;cursor:pointer;transition:background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-nav-dropdown a:hover,.fw-nav-dropdown button:hover{background:var(--fw-bg)}.fw-nav-dropdown a.is-active{background:var(--fw-primary);color:var(--fw-on-primary)}@media(max-width:600px){.fw-nav-links{display:none}.fw-nav-toggle{display:flex}}@media(prefers-reduced-motion:reduce){.fw-nav-dropdown{transform:none}}.fw-stat-label{font-family:var(--fw-font-body);font-size:13px;color:var(--fw-text-soft);font-weight:600}.fw-stat-value{font-family:var(--fw-font-display);font-size:32px;font-weight:800;line-height:1.1;color:var(--fw-text);margin-top:4px}.fw-stat-value .fw-stat-unit{font-size:18px;color:var(--fw-primary-hover)}.fw-stat-delta{font-family:var(--fw-font-mono);font-size:12px;font-weight:600;color:var(--fw-text-soft);margin-top:4px}.fw-stat-delta.is-up{color:var(--fw-success)}.fw-stat-delta.is-down{color:var(--fw-danger)}.fw-empty{text-align:center;padding:var(--fw-sp-7) var(--fw-sp-5);font-family:var(--fw-font-body)}.fw-empty-blob{width:72px;height:72px;margin:0 auto var(--fw-sp-4);border-radius:38% 62% 60% 40%/48% 42% 58% 52%;background:linear-gradient(135deg,var(--fw-primary),var(--fw-primary-soft));color:var(--fw-on-primary);display:flex;align-items:center;justify-content:center;font-size:28px}.fw-empty-title{font-family:var(--fw-font-display);font-size:17px;font-weight:700;color:var(--fw-text);margin:0 0 6px}.fw-empty-body{font-size:14px;color:var(--fw-text-soft);max-width:36ch;margin:0 auto var(--fw-sp-4)}.fw-modal-overlay{position:fixed;inset:0;background:var(--fw-overlay);display:flex;align-items:center;justify-content:center;padding:var(--fw-sp-5);z-index:100;opacity:0;pointer-events:none;transition:opacity var(--fw-motion-base) var(--fw-motion-ease)}.fw-modal-overlay.is-open{opacity:1;pointer-events:auto}.fw-modal{background:var(--fw-surface);color:var(--fw-text);font-family:var(--fw-font-body);border-radius:var(--fw-r-xl);box-shadow:var(--fw-shadow-lg);overflow:hidden;width:100%;max-width:460px;transform:translateY(8px) scale(.98);transition:transform var(--fw-motion-base) var(--fw-motion-ease)}.fw-modal-scroll{max-height:88vh;overflow-y:auto;padding:var(--fw-sp-6)}.fw-modal-wide{max-width:600px}.fw-modal-overlay.is-open .fw-modal{transform:translateY(0) scale(1)}.fw-modal-head{display:flex;justify-content:space-between;align-items:flex-start;gap:var(--fw-sp-3);margin-bottom:var(--fw-sp-5)}.fw-modal-head h2,.fw-modal-title{font-family:var(--fw-font-display);font-size:19px;font-weight:800;color:var(--fw-text);margin:0}.fw-modal-sub{font-size:13px;color:var(--fw-text-soft);margin:2px 0 0}.fw-modal-foot{display:flex;justify-content:flex-end;gap:var(--fw-sp-3);align-items:center;margin-top:var(--fw-sp-2);padding-top:var(--fw-sp-5);border-top:var(--fw-border-w) solid var(--fw-bg-dim)}@media(prefers-reduced-motion:reduce){.fw-modal{transform:none}}.fw-drawer-overlay{position:fixed;inset:0;background:var(--fw-overlay-soft);opacity:0;pointer-events:none;transition:opacity var(--fw-motion-base) var(--fw-motion-ease);z-index:90}.fw-drawer-overlay.is-open{opacity:1;pointer-events:auto}.fw-drawer{position:fixed;top:0;right:0;height:100%;width:440px;max-width:92vw;background:var(--fw-bg);color:var(--fw-text);font-family:var(--fw-font-body);box-shadow:var(--fw-shadow-lg);border-left:var(--fw-border-w) solid var(--fw-bg-dim);transform:translate(100%);transition:transform .24s var(--fw-motion-ease);z-index:91;display:flex;flex-direction:column}.fw-drawer.is-open{transform:translate(0)}.fw-drawer-head{padding:var(--fw-sp-5);border-bottom:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);display:flex;align-items:flex-start;gap:var(--fw-sp-3);flex-shrink:0}.fw-drawer-head-text{flex:1;min-width:0}.fw-drawer-eyebrow{font-family:var(--fw-font-mono);font-size:11px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--fw-text-soft);margin-bottom:4px}.fw-drawer-title{font-family:var(--fw-font-display);font-size:19px;font-weight:800;color:var(--fw-text);margin:0}.fw-drawer-title-input{font-family:var(--fw-font-display);font-size:19px;font-weight:800;color:var(--fw-text);border:none;background:transparent;padding:2px 0;width:100%;outline:none;border-radius:6px}.fw-drawer-title-input:focus{background:var(--fw-bg);padding:2px 6px;margin:0 -6px}.fw-drawer>form{flex:1;min-height:0;display:flex;flex-direction:column}.fw-drawer-body{flex:1;min-height:0;overflow-y:auto;-webkit-overflow-scrolling:touch;padding:var(--fw-sp-5);display:flex;flex-direction:column;gap:var(--fw-sp-5)}.fw-drawer-foot{padding:var(--fw-sp-4) var(--fw-sp-5);display:flex;align-items:center;justify-content:space-between;gap:var(--fw-sp-3);flex-shrink:0;border-top:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface)}@media(max-width:560px){.fw-drawer{left:0;width:auto;max-width:none}}@media(prefers-reduced-motion:reduce){.fw-drawer{transition:opacity var(--fw-motion-base) var(--fw-motion-ease);transform:none;opacity:0;pointer-events:none}.fw-drawer.is-open{opacity:1;pointer-events:auto}}.fw-popover{position:fixed;top:0;left:0;z-index:40;width:max-content;max-width:min(320px,calc(100vw - 2 * var(--fw-sp-4)));background:var(--fw-surface);color:var(--fw-text);font-family:var(--fw-font-body);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-lg);box-shadow:var(--fw-shadow-lg);padding:var(--fw-sp-4);opacity:0;transform:scale(.98);pointer-events:none;transition:opacity var(--fw-motion-base) var(--fw-motion-ease),transform var(--fw-motion-base) var(--fw-motion-ease)}.fw-popover.is-open{opacity:1;transform:scale(1);pointer-events:auto}.fw-popover-head{display:flex;align-items:flex-start;justify-content:space-between;gap:var(--fw-sp-3);margin-bottom:var(--fw-sp-3)}.fw-popover-title{font-family:var(--fw-font-display);font-size:15px;font-weight:700;color:var(--fw-text);margin:0}.fw-popover-body{font-size:13px;color:var(--fw-text-soft)}@media(prefers-reduced-motion:reduce){.fw-popover{transform:none}}.fw-toast{position:fixed;bottom:var(--fw-sp-6);right:var(--fw-sp-6);z-index:200;display:flex;align-items:center;gap:var(--fw-sp-3);max-width:min(360px,calc(100vw - 2 * var(--fw-sp-5)));background:var(--fw-success-bg);color:var(--fw-text);font-family:var(--fw-font-body);border-radius:var(--fw-r-md);padding:var(--fw-sp-3) var(--fw-sp-4);box-shadow:var(--fw-shadow-lg);font-size:13px;font-weight:600;transform:translateY(12px);opacity:0;pointer-events:none;transition:transform var(--fw-motion-base) var(--fw-motion-ease),opacity var(--fw-motion-base) var(--fw-motion-ease)}.fw-toast.is-show{transform:translateY(0);opacity:1;pointer-events:auto}.fw-toast-dot{width:8px;height:8px;border-radius:50%;background:var(--fw-success);flex-shrink:0}.fw-toast-error{background:var(--fw-danger-bg)}.fw-toast-error .fw-toast-dot{background:var(--fw-danger)}.fw-toast-info{background:var(--fw-info-bg)}.fw-toast-info .fw-toast-dot{background:var(--fw-info)}.fw-toast-pending{background:var(--fw-warning-bg)}.fw-toast-pending .fw-toast-dot{background:var(--fw-warning)}@media(prefers-reduced-motion:reduce){.fw-toast{transform:none}}.fw-list-row{display:block;background:var(--fw-surface);border-radius:var(--fw-r-lg);border:var(--fw-border-w) solid var(--fw-bg-dim);box-shadow:var(--fw-shadow-sm);padding:var(--fw-sp-4) var(--fw-sp-5);color:inherit;font-family:var(--fw-font-body);text-decoration:none;transition:transform var(--fw-motion-fast) var(--fw-motion-ease),box-shadow var(--fw-motion-fast) var(--fw-motion-ease)}.fw-list-row:hover{transform:translateY(-1px);box-shadow:var(--fw-shadow-md);text-decoration:none}.fw-list-row:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-list-row.is-locked{opacity:.6}.fw-list-row.is-locked:hover{transform:none;box-shadow:var(--fw-shadow-sm)}.fw-list-row+.fw-list-row{margin-top:var(--fw-sp-3)}.fw-list-row-main{display:flex;flex-wrap:wrap;align-items:center;gap:var(--fw-sp-2) var(--fw-sp-4)}.fw-list-row-title{font-family:var(--fw-font-display);font-weight:700;font-size:16px;color:var(--fw-text)}.fw-list-row-meta{font-size:13px;color:var(--fw-text-soft)}.fw-sub-list{margin:var(--fw-sp-2) 0 0 var(--fw-sp-5);padding-left:var(--fw-sp-4);border-left:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-sub-list-row{display:flex;flex-wrap:wrap;align-items:center;gap:var(--fw-sp-2) var(--fw-sp-3);padding:var(--fw-sp-2) 0}.fw-sub-list-row+.fw-sub-list-row{border-top:1px solid var(--fw-bg-dim)}.fw-sub-list-title{font-size:13.5px;font-weight:600;color:var(--fw-text)}.fw-disclosure>summary{cursor:pointer;color:var(--fw-secondary);font-family:var(--fw-font-body);font-weight:600;font-size:13px;list-style:none;display:flex;align-items:center;gap:6px}.fw-disclosure>summary::-webkit-details-marker{display:none}.fw-disclosure>summary:hover{text-decoration:underline}.fw-disclosure>summary:focus-visible{outline:none;border-radius:4px;box-shadow:var(--fw-focus-ring)}.fw-disclosure-chevron{width:12px;height:12px;flex-shrink:0;transition:transform .15s var(--fw-motion-ease)}.fw-disclosure[open]>summary .fw-disclosure-chevron{transform:rotate(180deg)}.fw-disclosure-count{font-family:var(--fw-font-mono);font-size:10.5px;font-weight:700;color:var(--fw-secondary);background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-full);padding:1px 7px}.fw-disclosure-body{margin-top:var(--fw-sp-3);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-md);padding:var(--fw-sp-4);background:var(--fw-bg);display:flex;flex-direction:column;gap:var(--fw-sp-3)}.fw-menu{--fw-menu-indent: var(--fw-sp-4);--fw-menu-row-h: 36px;font-family:var(--fw-font-body);color:var(--fw-text)}.fw-menu-list{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:2px}.fw-menu-group>.fw-menu-list{margin:2px 0 0 var(--fw-menu-indent);padding-left:var(--fw-sp-3);border-left:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-menu-link,.fw-menu-summary{display:flex;align-items:center;gap:var(--fw-sp-2);min-height:var(--fw-menu-row-h);padding:0 var(--fw-sp-3);border-radius:var(--fw-r-sm);color:var(--fw-text);font-family:var(--fw-font-body);font-size:14px;font-weight:600;line-height:1.3;text-decoration:none;text-align:left;background:none;border:none;cursor:pointer;transition:background-color var(--fw-motion-fast) var(--fw-motion-ease),color var(--fw-motion-fast) var(--fw-motion-ease)}@media(hover:hover){.fw-menu-link:hover,.fw-menu-summary:hover{background:var(--fw-bg);text-decoration:none}}.fw-menu-link:focus-visible,.fw-menu-summary:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-menu-link[aria-current=page]{background:var(--fw-secondary-bg);color:var(--fw-secondary)}.fw-menu-summary.is-current{color:var(--fw-secondary)}.fw-menu-summary{list-style:none;user-select:none}.fw-menu-summary::-webkit-details-marker{display:none}.fw-menu-summary:after{content:"";flex-shrink:0;width:16px;height:16px;margin-left:auto;background-color:currentColor;opacity:.55;-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M6 4l4 4-4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M6 4l4 4-4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;transition:transform var(--fw-motion-fast) var(--fw-motion-ease),opacity var(--fw-motion-fast) var(--fw-motion-ease)}.fw-menu-summary:hover:after,.fw-menu-summary.is-current:after{opacity:1}.fw-menu-group[open]>.fw-menu-summary:after{transform:rotate(90deg)}.fw-menu-split{position:relative}.fw-menu-split>.fw-menu-link{padding-right:44px}.fw-menu-summary-icon{position:absolute;top:0;right:0;width:var(--fw-menu-row-h);height:var(--fw-menu-row-h);min-height:0;padding:0;justify-content:center}.fw-menu-summary-icon:after{margin-left:0}.fw-menu-panel{padding:var(--fw-sp-2) var(--fw-sp-3) var(--fw-sp-4);color:var(--fw-text-soft);font-size:14px;line-height:1.5}.fw-menu-panel>:first-child{margin-top:0}.fw-menu-panel>:last-child{margin-bottom:0}.fw-menu-accordion>.fw-menu-group+.fw-menu-group{border-top:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-menu-accordion>.fw-menu-group>.fw-menu-summary{min-height:44px;padding-inline:0;border-radius:0;font-family:var(--fw-font-display);font-size:15px;font-weight:700}.fw-menu-accordion>.fw-menu-group>.fw-menu-summary:after{-webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E")}.fw-menu-accordion>.fw-menu-group[open]>.fw-menu-summary:after{transform:rotate(180deg)}@media(hover:hover){.fw-menu-accordion>.fw-menu-group>.fw-menu-summary:hover{background:none;color:var(--fw-secondary)}}.fw-menu-accordion>.fw-menu-group>.fw-menu-summary:focus-visible{border-radius:4px}.fw-menu-accordion>.fw-menu-group>.fw-menu-panel{padding-inline:0}@media(prefers-reduced-motion:reduce){.fw-menu-summary:after{transition:none}}.fw-pagination{display:flex;align-items:center;justify-content:space-between;flex-wrap:wrap;gap:var(--fw-sp-3);font-family:var(--fw-font-body)}.fw-pag-info,.fw-pag-label{font-family:var(--fw-font-mono);font-size:12px;color:var(--fw-text-soft)}.fw-pag-controls{display:flex;align-items:center;gap:var(--fw-sp-3)}.fw-btn-page{display:inline-flex;align-items:center;height:34px;padding:0 14px;border-radius:var(--fw-r-sm);border:var(--fw-border-w) solid var(--fw-bg-dim);background:var(--fw-surface);color:var(--fw-text);font-family:var(--fw-font-body);font-size:13px;font-weight:600;text-decoration:none;cursor:pointer;transition:border-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-btn-page:hover{border-color:var(--fw-text-soft);text-decoration:none}.fw-btn-page:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-btn-page.is-disabled,.fw-btn-page[aria-disabled=true],.fw-btn-page:disabled{opacity:.35;cursor:not-allowed;pointer-events:none}.fw-table-wrap{overflow:hidden;background:var(--fw-surface);border:var(--fw-border-w) solid var(--fw-bg-dim);border-radius:var(--fw-r-lg);box-shadow:var(--fw-shadow-sm);font-family:var(--fw-font-body);color:var(--fw-text)}.fw-table-scroll{overflow-x:auto}.fw-table-scroll:focus-visible{outline:none}.fw-table-wrap:has(.fw-table-scroll:focus-visible){box-shadow:var(--fw-focus-ring)}.fw-table-wrap.fw-table-sticky .fw-table-scroll{max-height:var(--fw-table-max-height, 460px);overflow:auto}.fw-table-sticky .fw-table thead th{position:sticky;top:0;z-index:1}.fw-table{width:100%;border-collapse:separate;border-spacing:0;font-family:var(--fw-font-body);font-size:14px;line-height:1.4;color:var(--fw-text);text-align:left}.fw-table caption{caption-side:top;text-align:left;font-family:var(--fw-font-display);font-weight:700;font-size:16px;color:var(--fw-text);padding:var(--fw-sp-4) var(--fw-sp-5) var(--fw-sp-2)}.fw-table th,.fw-table td{padding:var(--fw-sp-3) var(--fw-sp-4);vertical-align:middle}.fw-table th:first-child,.fw-table td:first-child{padding-left:var(--fw-sp-5)}.fw-table th:last-child,.fw-table td:last-child{padding-right:var(--fw-sp-5)}.fw-table thead th{font-size:12px;font-weight:700;letter-spacing:.02em;color:var(--fw-text-soft);background:var(--fw-surface);border-bottom:var(--fw-border-w) solid var(--fw-bg-dim);white-space:nowrap}.fw-table tbody tr+tr>td{border-top:var(--fw-border-w) solid var(--fw-bg-dim)}.fw-table tbody td{transition:background-color var(--fw-motion-fast) var(--fw-motion-ease)}.fw-table-striped tbody tr:nth-child(2n)>td{background:var(--fw-bg)}@media(hover:hover){.fw-table tbody tr:hover>td{background:var(--fw-secondary-bg)}}.fw-table tbody tr.is-selected>td,.fw-table tbody tr[aria-selected=true]>td{background:var(--fw-secondary-bg)}.fw-table tbody tr.is-selected>td:first-child,.fw-table tbody tr[aria-selected=true]>td:first-child{box-shadow:inset 3px 0 0 var(--fw-secondary)}.fw-table-compact th,.fw-table-compact td{padding:var(--fw-sp-2) var(--fw-sp-3);font-size:13px}.fw-table-compact th:first-child,.fw-table-compact td:first-child{padding-left:var(--fw-sp-4)}.fw-table-compact th:last-child,.fw-table-compact td:last-child{padding-right:var(--fw-sp-4)}.fw-table-num{font-family:var(--fw-font-mono);text-align:right;font-variant-numeric:tabular-nums;white-space:nowrap}.fw-table-num .fw-table-sort{flex-direction:row-reverse}.fw-table-select{width:1%;padding-right:0;box-sizing:border-box}.fw-table-select .fw-checkbox{gap:0;vertical-align:middle}.fw-table-actions{width:1%;text-align:right;white-space:nowrap;box-sizing:border-box}.fw-table-actions .fw-icon-btn{vertical-align:middle}.fw-table-actions>*+*{margin-left:var(--fw-sp-1)}.fw-table-empty>td{text-align:center;padding:var(--fw-sp-7) var(--fw-sp-5);color:var(--fw-text-soft);font-family:var(--fw-font-display)}.fw-table-empty:hover>td{background:transparent}.fw-table-loading>td{text-align:center;padding:var(--fw-sp-6) var(--fw-sp-5)}.fw-table[aria-busy=true] tbody,.fw-table.is-loading tbody{opacity:.5;pointer-events:none;transition:opacity var(--fw-motion-fast) var(--fw-motion-ease)}th[data-fw-sort]{cursor:pointer}.fw-table-sort{display:inline-flex;align-items:center;gap:var(--fw-sp-1);padding:2px 4px;margin:-2px -4px;border:0;background:none;font:inherit;color:inherit;letter-spacing:inherit;cursor:pointer;border-radius:6px}th[data-fw-sort]:hover .fw-table-sort,th[aria-sort=ascending] .fw-table-sort,th[aria-sort=descending] .fw-table-sort{color:var(--fw-text)}.fw-table-sort:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-table-sort:after{content:"";width:12px;height:12px;flex-shrink:0;background-color:currentColor;opacity:.35;-webkit-mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M5 6.5l3-3 3 3M5 9.5l3 3 3-3' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;mask:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M5 6.5l3-3 3 3M5 9.5l3 3 3-3' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;transition:opacity var(--fw-motion-fast) var(--fw-motion-ease)}th[aria-sort=ascending] .fw-table-sort:after{opacity:1;-webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 10l4-4 4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 10l4-4 4 4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E")}th[aria-sort=descending] .fw-table-sort:after{opacity:1;-webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none'%3E%3Cpath d='M4 6l4 4 4-4' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E")}@media(max-width:560px){.fw-table{table-layout:fixed}.fw-table-select{width:var(--fw-table-select-w, 44px)}.fw-table-actions{width:var(--fw-table-actions-w, 96px)}.fw-table td:not(.fw-table-select):not(.fw-table-actions):not(.fw-table-num){white-space:normal;overflow-wrap:anywhere}.fw-table-num,.fw-table th{overflow:hidden;text-overflow:ellipsis}}.fw-tablist{display:flex;gap:var(--fw-sp-2);border-bottom:var(--fw-border-w) solid var(--fw-bg-dim);overflow-x:auto;scrollbar-width:none}.fw-tablist::-webkit-scrollbar{display:none}.fw-tablist[aria-orientation=vertical]{flex-direction:column;align-items:flex-start;border-bottom:none;border-right:var(--fw-border-w) solid var(--fw-bg-dim);overflow-x:visible;overflow-y:auto}.fw-tab{appearance:none;background:transparent;border:none;border-bottom:2px solid transparent;border-radius:var(--fw-r-sm) var(--fw-r-sm) 0 0;font-family:var(--fw-font-body);font-weight:600;font-size:13px;color:var(--fw-text-soft);padding:var(--fw-sp-3) var(--fw-sp-4);cursor:pointer;white-space:nowrap;flex-shrink:0;transition:color var(--fw-motion-fast) var(--fw-motion-ease),border-color var(--fw-motion-fast) var(--fw-motion-ease),background var(--fw-motion-fast) var(--fw-motion-ease)}.fw-tablist[aria-orientation=vertical] .fw-tab{border-bottom:none;border-right:2px solid transparent;border-radius:var(--fw-r-sm) 0 0 var(--fw-r-sm);text-align:left;width:100%}.fw-tab:hover:not([aria-selected=true]):not([aria-disabled=true]){color:var(--fw-text);background:var(--fw-bg-dim)}.fw-tab[aria-selected=true]{color:var(--fw-text);border-color:var(--fw-secondary)}.fw-tab:focus-visible{outline:none;box-shadow:var(--fw-focus-ring)}.fw-tab[aria-disabled=true]{opacity:.45;cursor:not-allowed}.fw-tabpanel{padding:var(--fw-sp-4) 0}.fw-tabpanel:focus-visible{outline:none;border-radius:var(--fw-r-sm);box-shadow:var(--fw-focus-ring)}@media(prefers-reduced-motion:reduce){.fw-tab{transition:none}}.fw-tooltip{position:fixed;top:0;left:0;z-index:50;max-width:220px;background:var(--fw-text);color:var(--fw-bg);font-family:var(--fw-font-body);font-size:12.5px;font-weight:600;line-height:1.4;border-radius:var(--fw-r-sm);padding:6px 10px;box-shadow:var(--fw-shadow-md);opacity:0;transform:scale(.96);pointer-events:none;transition:opacity var(--fw-motion-fast) var(--fw-motion-ease),transform var(--fw-motion-fast) var(--fw-motion-ease);--fw-tooltip-arrow: 5px}.fw-tooltip.is-open{opacity:1;transform:scale(1);pointer-events:auto}.fw-tooltip:after{content:"";position:absolute;width:0;height:0;border:var(--fw-tooltip-arrow) solid transparent}.fw-tooltip[data-placement^=top]:after{top:100%;left:var(--fw-tooltip-arrow-pos, 50%);transform:translate(-50%);border-top-color:var(--fw-text);border-bottom-width:0}.fw-tooltip[data-placement^=bottom]:after{bottom:100%;left:var(--fw-tooltip-arrow-pos, 50%);transform:translate(-50%);border-bottom-color:var(--fw-text);border-top-width:0}.fw-tooltip[data-placement=left]:after{left:100%;top:var(--fw-tooltip-arrow-pos, 50%);transform:translateY(-50%);border-left-color:var(--fw-text);border-right-width:0}.fw-tooltip[data-placement=right]:after{right:100%;top:var(--fw-tooltip-arrow-pos, 50%);transform:translateY(-50%);border-right-color:var(--fw-text);border-left-width:0}@media(prefers-reduced-motion:reduce){.fw-tooltip{transform:none}}.fw-root,.fw-modal-scroll,.fw-drawer-body,.fw-table-scroll{scrollbar-width:thin;scrollbar-color:var(--fw-scrollbar-thumb) var(--fw-scrollbar-track)}.fw-root::-webkit-scrollbar,.fw-modal-scroll::-webkit-scrollbar,.fw-drawer-body::-webkit-scrollbar,.fw-table-scroll::-webkit-scrollbar{width:var(--fw-sp-2);height:var(--fw-sp-2)}.fw-root::-webkit-scrollbar-track,.fw-modal-scroll::-webkit-scrollbar-track,.fw-drawer-body::-webkit-scrollbar-track{background:var(--fw-scrollbar-track)}.fw-root::-webkit-scrollbar-thumb,.fw-modal-scroll::-webkit-scrollbar-thumb,.fw-drawer-body::-webkit-scrollbar-thumb,.fw-table-scroll::-webkit-scrollbar-thumb{background-color:var(--fw-scrollbar-thumb);border-radius:var(--fw-r-full);border:2px solid var(--fw-surface)}.fw-root::-webkit-scrollbar-thumb:hover,.fw-modal-scroll::-webkit-scrollbar-thumb:hover,.fw-drawer-body::-webkit-scrollbar-thumb:hover,.fw-table-scroll::-webkit-scrollbar-thumb:hover{background-color:var(--fw-scrollbar-thumb-hover)}.fw-table-scroll{scrollbar-color:var(--fw-scrollbar-thumb) var(--fw-bg-dim)}.fw-table-scroll::-webkit-scrollbar-track{background:var(--fw-bg-dim)}.fw-tablist:not([aria-orientation=vertical]){mask-image:linear-gradient(to right,transparent,black 24px,black calc(100% - 24px),transparent);-webkit-mask-image:linear-gradient(to right,transparent,black 24px,black calc(100% - 24px),transparent)}.fw-tablist[aria-orientation=vertical]{mask-image:linear-gradient(to bottom,transparent,black 24px,black calc(100% - 24px),transparent);-webkit-mask-image:linear-gradient(to bottom,transparent,black 24px,black calc(100% - 24px),transparent)}
|
package/dist/fernwell.tokens.css
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/*! fernwell v0.
|
|
1
|
+
/*! fernwell v0.5.0 | MIT | https://github.com/JacobKnaack/fernwell */
|
|
2
2
|
/* src/css/tokens.css */
|
|
3
3
|
@layer fw-tokens {
|
|
4
4
|
:root,
|
|
@@ -30,6 +30,9 @@
|
|
|
30
30
|
--fw-overlay: rgba(31, 36, 48, 0.55);
|
|
31
31
|
--fw-overlay-soft: rgba(31, 36, 48, 0.32);
|
|
32
32
|
--fw-focus-ring: 0 0 0 4px color-mix(in srgb, var(--fw-primary) 25%, transparent);
|
|
33
|
+
--fw-scrollbar-thumb: var(--fw-text-soft);
|
|
34
|
+
--fw-scrollbar-thumb-hover: color-mix(in srgb, var(--fw-text-soft), var(--fw-text) 15%);
|
|
35
|
+
--fw-scrollbar-track: transparent;
|
|
33
36
|
--fw-font-display:
|
|
34
37
|
"Plus Jakarta Sans",
|
|
35
38
|
system-ui,
|
|
@@ -96,6 +99,9 @@
|
|
|
96
99
|
--fw-overlay: rgba(0, 0, 0, 0.6);
|
|
97
100
|
--fw-overlay-soft: rgba(0, 0, 0, 0.4);
|
|
98
101
|
--fw-focus-ring: 0 0 0 4px color-mix(in srgb, var(--fw-primary) 25%, transparent);
|
|
102
|
+
--fw-scrollbar-thumb: var(--fw-text-soft);
|
|
103
|
+
--fw-scrollbar-thumb-hover: color-mix(in srgb, var(--fw-text-soft), var(--fw-text) 15%);
|
|
104
|
+
--fw-scrollbar-track: transparent;
|
|
99
105
|
--fw-shadow-sm: 0 1px 2px rgba(0, 0, 0, 0.3);
|
|
100
106
|
--fw-shadow-md: 0 4px 12px rgba(0, 0, 0, 0.35);
|
|
101
107
|
--fw-shadow-lg: 0 12px 32px rgba(0, 0, 0, 0.45);
|
package/dist/icon.d.cts
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Icon — renders a named SVG icon into a `data-fw-icon` element.
|
|
3
|
+
*
|
|
4
|
+
* <span class="fw-icon" data-fw-icon="trash" aria-hidden="true"></span>
|
|
5
|
+
*
|
|
6
|
+
* Icons are decorative by default (the injected <svg> is `aria-hidden` and
|
|
7
|
+
* `focusable="false"`); give the accessible name to a wrapping interactive
|
|
8
|
+
* element instead (e.g. `aria-label` on a button), same as `.fw-icon-btn`.
|
|
9
|
+
* Color and size are not set here — `.fw-icon` inherits `color` and sizes
|
|
10
|
+
* itself in `em`, so an icon matches whatever text surrounds it.
|
|
11
|
+
*/
|
|
12
|
+
declare const icons: Record<string, string>;
|
|
13
|
+
export type IconName = keyof typeof icons;
|
|
14
|
+
export declare function render(name: string): string;
|
|
15
|
+
export declare function init(root?: ParentNode): void;
|
|
16
|
+
export {};
|
package/dist/icon.d.ts
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Icon — renders a named SVG icon into a `data-fw-icon` element.
|
|
3
|
+
*
|
|
4
|
+
* <span class="fw-icon" data-fw-icon="trash" aria-hidden="true"></span>
|
|
5
|
+
*
|
|
6
|
+
* Icons are decorative by default (the injected <svg> is `aria-hidden` and
|
|
7
|
+
* `focusable="false"`); give the accessible name to a wrapping interactive
|
|
8
|
+
* element instead (e.g. `aria-label` on a button), same as `.fw-icon-btn`.
|
|
9
|
+
* Color and size are not set here — `.fw-icon` inherits `color` and sizes
|
|
10
|
+
* itself in `em`, so an icon matches whatever text surrounds it.
|
|
11
|
+
*/
|
|
12
|
+
declare const icons: Record<string, string>;
|
|
13
|
+
export type IconName = keyof typeof icons;
|
|
14
|
+
export declare function render(name: string): string;
|
|
15
|
+
export declare function init(root?: ParentNode): void;
|
|
16
|
+
export {};
|
package/dist/iife.d.cts
ADDED
package/dist/iife.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export * from './index';
|
|
2
|
-
export { default } from './index';
|
|
1
|
+
export * from './index.js';
|
|
2
|
+
export { default } from './index.js';
|
package/dist/index.d.cts
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Fernwell — vanilla JS enhancers for the Fernwell design system.
|
|
3
|
+
*
|
|
4
|
+
* ESM / CJS: import { init, theme, toast } from 'fernwell'; init();
|
|
5
|
+
* <script>: <script src="https://unpkg.com/fernwell/dist/fernwell.iife.js"></script>
|
|
6
|
+
* → window.Fernwell, auto-initialised on DOMContentLoaded
|
|
7
|
+
* (add data-fw-no-init to the <script> tag to opt out).
|
|
8
|
+
*/
|
|
9
|
+
import * as theme from './theme.cjs';
|
|
10
|
+
import * as tokens from './tokens.cjs';
|
|
11
|
+
import * as combobox from './combobox.cjs';
|
|
12
|
+
import * as modal from './modal.cjs';
|
|
13
|
+
import * as nav from './nav.cjs';
|
|
14
|
+
import * as loading from './loading.cjs';
|
|
15
|
+
import * as toast from './toast.cjs';
|
|
16
|
+
import * as table from './table.cjs';
|
|
17
|
+
import * as menu from './menu.cjs';
|
|
18
|
+
import * as icon from './icon.cjs';
|
|
19
|
+
import * as popover from './popover.cjs';
|
|
20
|
+
import * as tooltip from './tooltip.cjs';
|
|
21
|
+
import * as tabs from './tabs.cjs';
|
|
22
|
+
export { theme, tokens, combobox, modal, nav, loading, toast, table, menu, icon, popover, tooltip, tabs };
|
|
23
|
+
export type { Theme } from './theme.cjs';
|
|
24
|
+
export type { TokenName } from './_tokenData.cjs';
|
|
25
|
+
export type { TokenKey, TokenOverrides, TokenThemeOverrides, SetTokensOptions, TokensChangeDetail, } from './tokens.cjs';
|
|
26
|
+
export type { ComboboxOptions, ComboboxInstance } from './combobox.cjs';
|
|
27
|
+
export type { ToastVariant, ToastOptions } from './toast.cjs';
|
|
28
|
+
export type { SortDirection, SortDetail, SelectDetail } from './table.cjs';
|
|
29
|
+
export type { ToggleDetail } from './menu.cjs';
|
|
30
|
+
export type { IconName } from './icon.cjs';
|
|
31
|
+
export type { PopoverOptions, PopoverInstance } from './popover.cjs';
|
|
32
|
+
export type { TooltipOptions, TooltipInstance } from './tooltip.cjs';
|
|
33
|
+
export type { TabsOptions, TabsInstance, TabsActivation, TabsChangeDetail } from './tabs.cjs';
|
|
34
|
+
export declare const version: string;
|
|
35
|
+
/**
|
|
36
|
+
* Wire every `data-fw-*` hook under `root`. Safe to call more than once —
|
|
37
|
+
* already-bound elements are skipped — so call it again after injecting
|
|
38
|
+
* markup (e.g. after an HTMX / Turbo swap).
|
|
39
|
+
*/
|
|
40
|
+
export declare function init(root?: ParentNode): void;
|
|
41
|
+
declare const Fernwell: {
|
|
42
|
+
version: string;
|
|
43
|
+
init: typeof init;
|
|
44
|
+
theme: typeof theme;
|
|
45
|
+
tokens: typeof tokens;
|
|
46
|
+
combobox: typeof combobox;
|
|
47
|
+
modal: typeof modal;
|
|
48
|
+
nav: typeof nav;
|
|
49
|
+
loading: typeof loading;
|
|
50
|
+
toast: typeof toast;
|
|
51
|
+
table: typeof table;
|
|
52
|
+
menu: typeof menu;
|
|
53
|
+
icon: typeof icon;
|
|
54
|
+
popover: typeof popover;
|
|
55
|
+
tooltip: typeof tooltip;
|
|
56
|
+
tabs: typeof tabs;
|
|
57
|
+
};
|
|
58
|
+
export default Fernwell;
|
package/dist/index.d.ts
CHANGED
|
@@ -6,21 +6,32 @@
|
|
|
6
6
|
* → window.Fernwell, auto-initialised on DOMContentLoaded
|
|
7
7
|
* (add data-fw-no-init to the <script> tag to opt out).
|
|
8
8
|
*/
|
|
9
|
-
import * as theme from './theme';
|
|
10
|
-
import * as
|
|
11
|
-
import * as
|
|
12
|
-
import * as
|
|
13
|
-
import * as
|
|
14
|
-
import * as
|
|
15
|
-
import * as
|
|
16
|
-
import * as
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
export
|
|
23
|
-
export
|
|
9
|
+
import * as theme from './theme.js';
|
|
10
|
+
import * as tokens from './tokens.js';
|
|
11
|
+
import * as combobox from './combobox.js';
|
|
12
|
+
import * as modal from './modal.js';
|
|
13
|
+
import * as nav from './nav.js';
|
|
14
|
+
import * as loading from './loading.js';
|
|
15
|
+
import * as toast from './toast.js';
|
|
16
|
+
import * as table from './table.js';
|
|
17
|
+
import * as menu from './menu.js';
|
|
18
|
+
import * as icon from './icon.js';
|
|
19
|
+
import * as popover from './popover.js';
|
|
20
|
+
import * as tooltip from './tooltip.js';
|
|
21
|
+
import * as tabs from './tabs.js';
|
|
22
|
+
export { theme, tokens, combobox, modal, nav, loading, toast, table, menu, icon, popover, tooltip, tabs };
|
|
23
|
+
export type { Theme } from './theme.js';
|
|
24
|
+
export type { TokenName } from './_tokenData.js';
|
|
25
|
+
export type { TokenKey, TokenOverrides, TokenThemeOverrides, SetTokensOptions, TokensChangeDetail, } from './tokens.js';
|
|
26
|
+
export type { ComboboxOptions, ComboboxInstance } from './combobox.js';
|
|
27
|
+
export type { ToastVariant, ToastOptions } from './toast.js';
|
|
28
|
+
export type { SortDirection, SortDetail, SelectDetail } from './table.js';
|
|
29
|
+
export type { ToggleDetail } from './menu.js';
|
|
30
|
+
export type { IconName } from './icon.js';
|
|
31
|
+
export type { PopoverOptions, PopoverInstance } from './popover.js';
|
|
32
|
+
export type { TooltipOptions, TooltipInstance } from './tooltip.js';
|
|
33
|
+
export type { TabsOptions, TabsInstance, TabsActivation, TabsChangeDetail } from './tabs.js';
|
|
34
|
+
export declare const version: string;
|
|
24
35
|
/**
|
|
25
36
|
* Wire every `data-fw-*` hook under `root`. Safe to call more than once —
|
|
26
37
|
* already-bound elements are skipped — so call it again after injecting
|
|
@@ -31,6 +42,7 @@ declare const Fernwell: {
|
|
|
31
42
|
version: string;
|
|
32
43
|
init: typeof init;
|
|
33
44
|
theme: typeof theme;
|
|
45
|
+
tokens: typeof tokens;
|
|
34
46
|
combobox: typeof combobox;
|
|
35
47
|
modal: typeof modal;
|
|
36
48
|
nav: typeof nav;
|
|
@@ -38,5 +50,9 @@ declare const Fernwell: {
|
|
|
38
50
|
toast: typeof toast;
|
|
39
51
|
table: typeof table;
|
|
40
52
|
menu: typeof menu;
|
|
53
|
+
icon: typeof icon;
|
|
54
|
+
popover: typeof popover;
|
|
55
|
+
tooltip: typeof tooltip;
|
|
56
|
+
tabs: typeof tabs;
|
|
41
57
|
};
|
|
42
58
|
export default Fernwell;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
export declare function setButtonLoading(btn: HTMLButtonElement | null, loadingText?: string): void;
|
|
2
|
+
export declare function resetButtonLoading(btn: HTMLButtonElement | null): void;
|
|
3
|
+
/** Reset every loading button — e.g. after a bfcache restore. */
|
|
4
|
+
export declare function resetAll(root?: ParentNode): void;
|
|
5
|
+
export declare function init(root?: ParentNode): void;
|
package/dist/menu.d.cts
ADDED
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Menu — a nestable collapsible menu (nav tree or accordion) built on
|
|
3
|
+
* native <details>/<summary>, enhanced for `.fw-menu[data-fw-menu]`.
|
|
4
|
+
*
|
|
5
|
+
* <nav class="fw-menu" aria-label="Docs" data-fw-menu>
|
|
6
|
+
* <ul class="fw-menu-list">
|
|
7
|
+
* <li class="fw-menu-item"><a class="fw-menu-link" href="/" aria-current="page">Overview</a></li>
|
|
8
|
+
* <li class="fw-menu-item">
|
|
9
|
+
* <details class="fw-menu-group">
|
|
10
|
+
* <summary class="fw-menu-summary">Billing</summary>
|
|
11
|
+
* <ul class="fw-menu-list">
|
|
12
|
+
* <li class="fw-menu-item fw-menu-split">
|
|
13
|
+
* <a class="fw-menu-link" href="/billing/plans">Plans</a>
|
|
14
|
+
* <details class="fw-menu-group">
|
|
15
|
+
* <summary class="fw-menu-summary fw-menu-summary-icon"><span class="fw-sr-only">Toggle Plans</span></summary>
|
|
16
|
+
* <ul class="fw-menu-list">…</ul>
|
|
17
|
+
* </details>
|
|
18
|
+
* </li>
|
|
19
|
+
* </ul>
|
|
20
|
+
* </details>
|
|
21
|
+
* </li>
|
|
22
|
+
* </ul>
|
|
23
|
+
* </nav>
|
|
24
|
+
*
|
|
25
|
+
* The `open` attribute on each `.fw-menu-group` is the state — server-rendered
|
|
26
|
+
* state is honoured, and the menu still expands/collapses without JS.
|
|
27
|
+
*
|
|
28
|
+
* The enhancer adds:
|
|
29
|
+
* - auto-reveal: every ancestor group of an `[aria-current]` link is opened on
|
|
30
|
+
* init, and a collapsed summary whose branch holds the current page gets `.is-current`
|
|
31
|
+
* - `data-fw-menu-exclusive`: opening a group closes its siblings (accordion)
|
|
32
|
+
* - keyboard: ArrowUp/ArrowDown move between visible rows, ArrowRight opens /
|
|
33
|
+
* enters a group, ArrowLeft closes / goes to the parent, Home/End jump.
|
|
34
|
+
* Tab order is untouched — every row stays natively tabbable.
|
|
35
|
+
*
|
|
36
|
+
* Events (bubbling, from the <details>): `fw:toggle` { group, open }.
|
|
37
|
+
*/
|
|
38
|
+
export interface ToggleDetail {
|
|
39
|
+
group: HTMLDetailsElement;
|
|
40
|
+
open: boolean;
|
|
41
|
+
}
|
|
42
|
+
export declare function open(group: HTMLDetailsElement): void;
|
|
43
|
+
export declare function close(group: HTMLDetailsElement): void;
|
|
44
|
+
export declare function toggle(group: HTMLDetailsElement, force?: boolean): void;
|
|
45
|
+
export declare function expandAll(root: ParentNode): void;
|
|
46
|
+
export declare function collapseAll(root: ParentNode): void;
|
|
47
|
+
/** Open every ancestor group of `el` so it is visible. */
|
|
48
|
+
export declare function reveal(el: Element): void;
|
|
49
|
+
export declare function init(root?: ParentNode): void;
|
package/dist/modal.d.cts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export declare function open(target: string | HTMLElement, opener?: HTMLElement | null): void;
|
|
2
|
+
export declare function close(target: string | HTMLElement): void;
|
|
3
|
+
export declare function toggle(target: string | HTMLElement): void;
|
|
4
|
+
/**
|
|
5
|
+
* Click-outside-to-close, guarded against a classic false positive: a
|
|
6
|
+
* browser's `click` fires on the nearest common ancestor of mousedown and
|
|
7
|
+
* mouseup. A drag that starts inside the panel and ends on the backdrop has
|
|
8
|
+
* the overlay as that ancestor, so a naive `e.target === overlay` check would
|
|
9
|
+
* close the modal mid-selection. Close only when BOTH landed on the backdrop.
|
|
10
|
+
*/
|
|
11
|
+
export declare function bindOutsideClickToClose(backdrop: HTMLElement, onClose: () => void): void;
|
|
12
|
+
/** Wire every trigger, overlay and close button under `root`. */
|
|
13
|
+
export declare function init(root?: ParentNode): void;
|
package/dist/nav.d.cts
ADDED
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Popover — a non-modal floating panel anchored to its trigger.
|
|
3
|
+
*
|
|
4
|
+
* <button type="button" data-fw-popover-trigger="settings-pop">Settings</button>
|
|
5
|
+
*
|
|
6
|
+
* <div class="fw-popover" id="settings-pop">
|
|
7
|
+
* <div class="fw-popover-head">
|
|
8
|
+
* <h3 class="fw-popover-title">Settings</h3>
|
|
9
|
+
* <button type="button" class="fw-icon-btn" data-fw-popover-close aria-label="Close">
|
|
10
|
+
* <span data-fw-icon="close" aria-hidden="true"></span>
|
|
11
|
+
* </button>
|
|
12
|
+
* </div>
|
|
13
|
+
* <div class="fw-popover-body">…</div>
|
|
14
|
+
* </div>
|
|
15
|
+
*
|
|
16
|
+
* Optional trigger attributes: `data-fw-popover-placement` ("top" | "bottom" |
|
|
17
|
+
* "left" | "right" — centered on the trigger's cross-axis midpoint — or a
|
|
18
|
+
* corner variant "top-left" | "top-right" | "bottom-left" | "bottom-right"
|
|
19
|
+
* that leans the panel toward that corner instead of centering it, e.g. to
|
|
20
|
+
* steer it clear of something else on the page; default "bottom"),
|
|
21
|
+
* `data-fw-popover-offset` (px, default 8).
|
|
22
|
+
*
|
|
23
|
+
* While open, the panel is moved to the end of <body> so its `position: fixed`
|
|
24
|
+
* containing block is always the viewport — not an ancestor with `transform`,
|
|
25
|
+
* `filter` or `contain` (e.g. a card, or another modal) that would otherwise
|
|
26
|
+
* break the positioning math — and moved back to its authored location on close.
|
|
27
|
+
*
|
|
28
|
+
* This is a non-modal dialog (`aria-modal="false"`), so per WAI-ARIA APG it
|
|
29
|
+
* does NOT trap Tab — focus is allowed to move naturally out of the panel.
|
|
30
|
+
* Closing on focus leaving the panel/trigger (`focusout`) does the equivalent
|
|
31
|
+
* job without fighting the surrounding page's tab order.
|
|
32
|
+
*
|
|
33
|
+
* Events (bubbling, from the panel): `fw:open`, `fw:close`.
|
|
34
|
+
*/
|
|
35
|
+
import { type Placement } from './_position.cjs';
|
|
36
|
+
export interface PopoverOptions {
|
|
37
|
+
placement?: Placement;
|
|
38
|
+
offset?: number;
|
|
39
|
+
}
|
|
40
|
+
export interface PopoverInstance {
|
|
41
|
+
open(): void;
|
|
42
|
+
close(): void;
|
|
43
|
+
toggle(): void;
|
|
44
|
+
destroy(): void;
|
|
45
|
+
}
|
|
46
|
+
export declare function popover(trigger: HTMLElement, panel: HTMLElement, opts?: PopoverOptions): PopoverInstance;
|
|
47
|
+
/** Wire every `[data-fw-popover-trigger]` under `root`. */
|
|
48
|
+
export declare function init(root?: ParentNode): void;
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Popover — a non-modal floating panel anchored to its trigger.
|
|
3
|
+
*
|
|
4
|
+
* <button type="button" data-fw-popover-trigger="settings-pop">Settings</button>
|
|
5
|
+
*
|
|
6
|
+
* <div class="fw-popover" id="settings-pop">
|
|
7
|
+
* <div class="fw-popover-head">
|
|
8
|
+
* <h3 class="fw-popover-title">Settings</h3>
|
|
9
|
+
* <button type="button" class="fw-icon-btn" data-fw-popover-close aria-label="Close">
|
|
10
|
+
* <span data-fw-icon="close" aria-hidden="true"></span>
|
|
11
|
+
* </button>
|
|
12
|
+
* </div>
|
|
13
|
+
* <div class="fw-popover-body">…</div>
|
|
14
|
+
* </div>
|
|
15
|
+
*
|
|
16
|
+
* Optional trigger attributes: `data-fw-popover-placement` ("top" | "bottom" |
|
|
17
|
+
* "left" | "right" — centered on the trigger's cross-axis midpoint — or a
|
|
18
|
+
* corner variant "top-left" | "top-right" | "bottom-left" | "bottom-right"
|
|
19
|
+
* that leans the panel toward that corner instead of centering it, e.g. to
|
|
20
|
+
* steer it clear of something else on the page; default "bottom"),
|
|
21
|
+
* `data-fw-popover-offset` (px, default 8).
|
|
22
|
+
*
|
|
23
|
+
* While open, the panel is moved to the end of <body> so its `position: fixed`
|
|
24
|
+
* containing block is always the viewport — not an ancestor with `transform`,
|
|
25
|
+
* `filter` or `contain` (e.g. a card, or another modal) that would otherwise
|
|
26
|
+
* break the positioning math — and moved back to its authored location on close.
|
|
27
|
+
*
|
|
28
|
+
* This is a non-modal dialog (`aria-modal="false"`), so per WAI-ARIA APG it
|
|
29
|
+
* does NOT trap Tab — focus is allowed to move naturally out of the panel.
|
|
30
|
+
* Closing on focus leaving the panel/trigger (`focusout`) does the equivalent
|
|
31
|
+
* job without fighting the surrounding page's tab order.
|
|
32
|
+
*
|
|
33
|
+
* Events (bubbling, from the panel): `fw:open`, `fw:close`.
|
|
34
|
+
*/
|
|
35
|
+
import { type Placement } from './_position.js';
|
|
36
|
+
export interface PopoverOptions {
|
|
37
|
+
placement?: Placement;
|
|
38
|
+
offset?: number;
|
|
39
|
+
}
|
|
40
|
+
export interface PopoverInstance {
|
|
41
|
+
open(): void;
|
|
42
|
+
close(): void;
|
|
43
|
+
toggle(): void;
|
|
44
|
+
destroy(): void;
|
|
45
|
+
}
|
|
46
|
+
export declare function popover(trigger: HTMLElement, panel: HTMLElement, opts?: PopoverOptions): PopoverInstance;
|
|
47
|
+
/** Wire every `[data-fw-popover-trigger]` under `root`. */
|
|
48
|
+
export declare function init(root?: ParentNode): void;
|