@greypan/web-ui 3.0.0 → 4.0.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/README.CN.md +297 -34
- package/README.md +304 -39
- package/dist/_virtual/{_@oxc-project_runtime@0.140.0 → _@oxc-project_runtime@0.146.0}/helpers/esm/decorate.js +1 -1
- package/dist/assets/glass.js +1 -1
- package/dist/assets/glass.js.map +1 -1
- package/dist/assets/menu-portal.js +1 -1
- package/dist/assets/menu-portal.js.map +1 -1
- package/dist/assets/overlay-motion.js +1 -1
- package/dist/assets/overlay-motion.js.map +1 -1
- package/dist/assets/toast-containers.js +1 -1
- package/dist/assets/toast-containers.js.map +1 -1
- package/dist/components/autocomplete/index.d.ts +4 -12
- package/dist/components/autocomplete/index.js +95 -102
- package/dist/components/autocomplete/index.js.map +1 -1
- package/dist/components/autocomplete/style.js +1 -1
- package/dist/components/autocomplete/style.js.map +1 -1
- package/dist/components/avatar/index.d.ts +0 -1
- package/dist/components/avatar/index.js +8 -13
- package/dist/components/avatar/index.js.map +1 -1
- package/dist/components/back-top/index.js +1 -1
- package/dist/components/back-top/style.js +1 -1
- package/dist/components/back-top/style.js.map +1 -1
- package/dist/components/badge/index.d.ts +1 -0
- package/dist/components/badge/index.js +12 -14
- package/dist/components/badge/index.js.map +1 -1
- package/dist/components/button/index.d.ts +2 -0
- package/dist/components/button/index.js +51 -38
- package/dist/components/button/index.js.map +1 -1
- package/dist/components/button/style.js +1 -1
- package/dist/components/button/style.js.map +1 -1
- package/dist/components/button-group/index.d.ts +1 -2
- package/dist/components/button-group/index.js +19 -23
- package/dist/components/button-group/index.js.map +1 -1
- package/dist/components/checkbox/index.d.ts +4 -7
- package/dist/components/checkbox/index.js +48 -37
- package/dist/components/checkbox/index.js.map +1 -1
- package/dist/components/checkbox/style.js +1 -1
- package/dist/components/checkbox/style.js.map +1 -1
- package/dist/components/checkbox-group/index.d.ts +4 -10
- package/dist/components/checkbox-group/index.js +74 -60
- package/dist/components/checkbox-group/index.js.map +1 -1
- package/dist/components/context-menu/index.js +7 -8
- package/dist/components/context-menu/index.js.map +1 -1
- package/dist/components/dialog/index.d.ts +1 -0
- package/dist/components/dialog/index.js +13 -9
- package/dist/components/dialog/index.js.map +1 -1
- package/dist/components/dialog/style.js +1 -1
- package/dist/components/dialog/style.js.map +1 -1
- package/dist/components/drawer/index.d.ts +15 -0
- package/dist/components/drawer/index.js +58 -34
- package/dist/components/drawer/index.js.map +1 -1
- package/dist/components/drawer/style.js +1 -1
- package/dist/components/drawer/style.js.map +1 -1
- package/dist/components/dropdown/index.js +1 -1
- package/dist/components/dropdown-divider/index.js +1 -1
- package/dist/components/dropdown-header/index.js +1 -1
- package/dist/components/dropdown-header/style.js +1 -1
- package/dist/components/dropdown-header/style.js.map +1 -1
- package/dist/components/dropdown-item/index.js +3 -2
- package/dist/components/dropdown-item/index.js.map +1 -1
- package/dist/components/empty/index.js +1 -1
- package/dist/components/empty/style.js +1 -1
- package/dist/components/empty/style.js.map +1 -1
- package/dist/components/icon/index.js +1 -1
- package/dist/components/index.d.ts +1 -1
- package/dist/components/index.js +9 -9
- package/dist/components/input/index.d.ts +2 -3
- package/dist/components/input/index.js +62 -52
- package/dist/components/input/index.js.map +1 -1
- package/dist/components/input/style.js +1 -1
- package/dist/components/input/style.js.map +1 -1
- package/dist/components/input-number/index.d.ts +2 -3
- package/dist/components/input-number/index.js +58 -38
- package/dist/components/input-number/index.js.map +1 -1
- package/dist/components/input-number/style.js +1 -1
- package/dist/components/input-number/style.js.map +1 -1
- package/dist/components/layout/index.d.ts +53 -3
- package/dist/components/layout/index.js +146 -39
- package/dist/components/layout/index.js.map +1 -1
- package/dist/components/layout/style.js +1 -1
- package/dist/components/layout/style.js.map +1 -1
- package/dist/components/option/index.js +1 -1
- package/dist/components/option/style.js +1 -1
- package/dist/components/option/style.js.map +1 -1
- package/dist/components/popover/index.js +7 -5
- package/dist/components/popover/index.js.map +1 -1
- package/dist/components/popover/style.js +1 -1
- package/dist/components/popover/style.js.map +1 -1
- package/dist/components/radio/index.d.ts +4 -7
- package/dist/components/radio/index.js +48 -37
- package/dist/components/radio/index.js.map +1 -1
- package/dist/components/radio/style.js +1 -1
- package/dist/components/radio/style.js.map +1 -1
- package/dist/components/radio-group/index.d.ts +4 -10
- package/dist/components/radio-group/index.js +70 -52
- package/dist/components/radio-group/index.js.map +1 -1
- package/dist/components/segmented/index.d.ts +6 -11
- package/dist/components/segmented/index.js +67 -55
- package/dist/components/segmented/index.js.map +1 -1
- package/dist/components/segmented/style.js +1 -1
- package/dist/components/segmented/style.js.map +1 -1
- package/dist/components/segmented-trigger/index.d.ts +1 -2
- package/dist/components/segmented-trigger/index.js +18 -19
- package/dist/components/segmented-trigger/index.js.map +1 -1
- package/dist/components/segmented-trigger/style.js +1 -1
- package/dist/components/segmented-trigger/style.js.map +1 -1
- package/dist/components/select/index.d.ts +13 -8
- package/dist/components/select/index.js +110 -75
- package/dist/components/select/index.js.map +1 -1
- package/dist/components/select/style.js +1 -1
- package/dist/components/select/style.js.map +1 -1
- package/dist/components/slider/index.d.ts +3 -5
- package/dist/components/slider/index.js +59 -42
- package/dist/components/slider/index.js.map +1 -1
- package/dist/components/slider/style.js +1 -1
- package/dist/components/slider/style.js.map +1 -1
- package/dist/components/spinner/index.d.ts +0 -2
- package/dist/components/spinner/index.js +14 -13
- package/dist/components/spinner/index.js.map +1 -1
- package/dist/components/spinner/style.js +1 -1
- package/dist/components/spinner/style.js.map +1 -1
- package/dist/components/svg-draw-lines/index.js +1 -1
- package/dist/components/switch/index.d.ts +5 -6
- package/dist/components/switch/index.js +51 -37
- package/dist/components/switch/index.js.map +1 -1
- package/dist/components/switch/style.js +1 -1
- package/dist/components/switch/style.js.map +1 -1
- package/dist/components/textarea/index.d.ts +5 -6
- package/dist/components/textarea/index.js +73 -63
- package/dist/components/textarea/index.js.map +1 -1
- package/dist/components/textarea/style.js +1 -1
- package/dist/components/textarea/style.js.map +1 -1
- package/dist/components/theme/index.js +1 -1
- package/dist/components/theme/style.js +1 -1
- package/dist/components/theme/style.js.map +1 -1
- package/dist/components/toast/style.js +1 -1
- package/dist/components/toast/style.js.map +1 -1
- package/dist/components/toast/toast.js +12 -12
- package/dist/components/toast/toast.js.map +1 -1
- package/dist/components/tooltip/index.js +1 -1
- package/dist/components/tooltip/style.js +1 -1
- package/dist/components/tooltip/style.js.map +1 -1
- package/dist/icons/generated/lucide-clapperboard.d.ts +6 -0
- package/dist/icons/generated/lucide-clapperboard.js +10 -0
- package/dist/icons/generated/lucide-clapperboard.js.map +1 -0
- package/dist/icons/generated/lucide-external-link.d.ts +6 -0
- package/dist/icons/generated/lucide-external-link.js +10 -0
- package/dist/icons/generated/lucide-external-link.js.map +1 -0
- package/dist/icons/generated/lucide-eye.d.ts +6 -0
- package/dist/icons/generated/lucide-eye.js +10 -0
- package/dist/icons/generated/lucide-eye.js.map +1 -0
- package/dist/icons/generated/lucide-file-text.d.ts +6 -0
- package/dist/icons/generated/lucide-file-text.js +10 -0
- package/dist/icons/generated/lucide-file-text.js.map +1 -0
- package/dist/icons/generated/lucide-film.d.ts +6 -0
- package/dist/icons/generated/lucide-film.js +10 -0
- package/dist/icons/generated/lucide-film.js.map +1 -0
- package/dist/icons/generated/lucide-folder-open.d.ts +6 -0
- package/dist/icons/generated/lucide-folder-open.js +10 -0
- package/dist/icons/generated/lucide-folder-open.js.map +1 -0
- package/dist/icons/generated/lucide-headphones.d.ts +6 -0
- package/dist/icons/generated/lucide-headphones.js +10 -0
- package/dist/icons/generated/lucide-headphones.js.map +1 -0
- package/dist/icons/generated/lucide-layout-grid.d.ts +6 -0
- package/dist/icons/generated/lucide-layout-grid.js +10 -0
- package/dist/icons/generated/lucide-layout-grid.js.map +1 -0
- package/dist/icons/generated/lucide-link.d.ts +6 -0
- package/dist/icons/generated/lucide-link.js +10 -0
- package/dist/icons/generated/lucide-link.js.map +1 -0
- package/dist/icons/generated/lucide-music.d.ts +6 -0
- package/dist/icons/generated/lucide-music.js +10 -0
- package/dist/icons/generated/lucide-music.js.map +1 -0
- package/dist/icons/generated/lucide-package.d.ts +6 -0
- package/dist/icons/generated/lucide-package.js +10 -0
- package/dist/icons/generated/lucide-package.js.map +1 -0
- package/dist/icons/generated/lucide-pen-line.d.ts +6 -0
- package/dist/icons/generated/lucide-pen-line.js +10 -0
- package/dist/icons/generated/lucide-pen-line.js.map +1 -0
- package/dist/icons/generated/lucide-pencil.d.ts +6 -0
- package/dist/icons/generated/lucide-pencil.js +10 -0
- package/dist/icons/generated/lucide-pencil.js.map +1 -0
- package/dist/icons/generated/lucide-play.d.ts +6 -0
- package/dist/icons/generated/lucide-play.js +10 -0
- package/dist/icons/generated/lucide-play.js.map +1 -0
- package/dist/icons/generated/lucide-refresh-cw.d.ts +6 -0
- package/dist/icons/generated/lucide-refresh-cw.js +10 -0
- package/dist/icons/generated/lucide-refresh-cw.js.map +1 -0
- package/dist/icons/generated/lucide-sliders-horizontal.d.ts +6 -0
- package/dist/icons/generated/lucide-sliders-horizontal.js +10 -0
- package/dist/icons/generated/lucide-sliders-horizontal.js.map +1 -0
- package/dist/icons/generated/lucide-tags.d.ts +6 -0
- package/dist/icons/generated/lucide-tags.js +10 -0
- package/dist/icons/generated/lucide-tags.js.map +1 -0
- package/dist/icons/generated/lucide-wrench.d.ts +6 -0
- package/dist/icons/generated/lucide-wrench.js +10 -0
- package/dist/icons/generated/lucide-wrench.js.map +1 -0
- package/dist/icons/index.d.ts +18 -0
- package/dist/icons/index.js +19 -1
- package/dist/node_modules/.pnpm/@floating-ui_core@1.8.0/node_modules/@floating-ui/core/dist/floating-ui.core.js +1 -3
- package/dist/node_modules/.pnpm/@floating-ui_core@1.8.0/node_modules/@floating-ui/core/dist/floating-ui.core.js.map +1 -1
- package/dist/node_modules/.pnpm/@floating-ui_utils@0.2.12/node_modules/@floating-ui/utils/dist/floating-ui.utils.dom.js +2 -1
- package/dist/node_modules/.pnpm/@floating-ui_utils@0.2.12/node_modules/@floating-ui/utils/dist/floating-ui.utils.dom.js.map +1 -1
- package/dist/shared/events/user-change.js.map +1 -1
- package/dist/shared/form-association/index.js +41 -0
- package/dist/shared/form-association/index.js.map +1 -0
- package/dist/shared/group-management/index.js +109 -0
- package/dist/shared/group-management/index.js.map +1 -0
- package/dist/shared/menu-portal/menu-tree.js +20 -7
- package/dist/shared/menu-portal/menu-tree.js.map +1 -1
- package/dist/shared/option-portal/index.js +65 -0
- package/dist/shared/option-portal/index.js.map +1 -0
- package/dist/shared/overlay/overlay.js +1 -1
- package/dist/shared/overlay/overlay.js.map +1 -1
- package/dist/shared/overlay/portal.js +9 -6
- package/dist/shared/overlay/portal.js.map +1 -1
- package/dist/shared/overlay/presence.js.map +1 -1
- package/dist/shared/visible-area/index.js +69 -0
- package/dist/shared/visible-area/index.js.map +1 -0
- package/dist/types/utils.d.ts +6 -1
- package/package.json +7 -5
package/README.md
CHANGED
|
@@ -31,6 +31,30 @@ import '@greypan/web-ui'
|
|
|
31
31
|
|
|
32
32
|
## Framework Setup
|
|
33
33
|
|
|
34
|
+
### Cross-framework API conventions
|
|
35
|
+
|
|
36
|
+
`web-ui-*` elements expose three surfaces. The **DOM / JavaScript API is the source of truth**: Properties use
|
|
37
|
+
camelCase, Attributes use kebab-case, Events use kebab-case.
|
|
38
|
+
|
|
39
|
+
| Surface | Naming | Examples |
|
|
40
|
+
| --------- | ---------- | --------------------------------------------- |
|
|
41
|
+
| Property | camelCase | `open`, `sidebarCollapsed`, `noScrollLock` |
|
|
42
|
+
| Attribute | kebab-case | `open`, `sidebar-collapsed`, `no-scroll-lock` |
|
|
43
|
+
| Event | kebab-case | `open-change`, `sidebar-collapsed-change` |
|
|
44
|
+
|
|
45
|
+
- **Boolean attributes** follow native HTML presence semantics: absent → `false`, presence → `true`. A framework
|
|
46
|
+
binding that writes `disabled="false"` produces the string `"false"`, which is truthy — **bind dynamic booleans as
|
|
47
|
+
properties** (camelCase), not attributes, so `false` is written as a real property.
|
|
48
|
+
- **Vue**: dynamic binding must go to **Properties** with camelCase names (`:sidebarCollapsed="x"`, `:open="x"`).
|
|
49
|
+
A kebab-case binding like `:sidebar-collapsed="x"` is written as a string attribute and cannot express `false`;
|
|
50
|
+
use the camelCase property. The `.prop` modifier is only valid with the camelCase name
|
|
51
|
+
(`:sidebarCollapsed.prop="x"`). String/number values may stay on kebab-case attributes (`:max-height="120"`).
|
|
52
|
+
`v-model` is supported on value-bearing controls (`web-ui-input`, `web-ui-select`, `web-ui-autocomplete`, …) and
|
|
53
|
+
compiles to the element `value` property + `input` event.
|
|
54
|
+
- **React**: React 19 writes DOM properties for custom-element props, so use camelCase props (`open={open}`,
|
|
55
|
+
`noScrollLock`, `value={value}`). Never pass complex data (objects, arrays) through attribute strings — bind
|
|
56
|
+
them as properties. Kebab-case JSX props on a custom element are written as attributes.
|
|
57
|
+
|
|
34
58
|
### React
|
|
35
59
|
|
|
36
60
|
Requires `@types/react >= 19` as optional peer dependency.
|
|
@@ -129,11 +153,27 @@ import '@greypan/web-ui/types/vue'
|
|
|
129
153
|
</template>
|
|
130
154
|
```
|
|
131
155
|
|
|
156
|
+
Boolean properties must be bound with the **camelCase property name**, not the kebab-case attribute. Vue writes
|
|
157
|
+
attribute bindings as strings, and boolean attributes follow presence semantics — so `:sidebar-collapsed="false"`
|
|
158
|
+
produces the string `"false"`, which is truthy. Binding the camelCase name (`:sidebarCollapsed="false"`, or the
|
|
159
|
+
`.prop` modifier) makes Vue write the DOM property directly:
|
|
160
|
+
|
|
161
|
+
```vue
|
|
162
|
+
<web-ui-layout
|
|
163
|
+
header-glow
|
|
164
|
+
:sidebarCollapsed="sidebarCollapsed"
|
|
165
|
+
:sidebarOpen="sidebarOpen"
|
|
166
|
+
@sidebar-collapsed-change="sidebarCollapsed = $event.detail.collapsed"
|
|
167
|
+
@sidebar-open-change="sidebarOpen = $event.detail.open"
|
|
168
|
+
/>
|
|
169
|
+
```
|
|
170
|
+
|
|
132
171
|
Vue events are typed cast-free: `@input`/`@change` on value-bearing components resolve to the component emit, so
|
|
133
172
|
`$event.target` is the component instance and `value`/`checked` are read directly. `$event.detail` keeps the
|
|
134
173
|
`CustomEvent` payload type for kebab-case events like `open-change`. Named handlers annotate with
|
|
135
|
-
`WebUiEvent<WebUiXxx, 'change'
|
|
136
|
-
|
|
174
|
+
`WebUiEvent<WebUiXxx, 'change'>`; use `WebUiEventName<WebUiXxx>` when a value or generic represents an
|
|
175
|
+
event name, because it accepts only the component's string `$events` keys. `@click`/`@focus` and other native
|
|
176
|
+
events not declared as emits remain bindable on any `web-ui-*` element.
|
|
137
177
|
|
|
138
178
|
### Attribute and event boundaries
|
|
139
179
|
|
|
@@ -147,6 +187,10 @@ Components own their role and interaction state. Browser-native composed events
|
|
|
147
187
|
remain the primary interaction API. Kebab-case custom events such as `open-change` describe user-originated component
|
|
148
188
|
state changes; assigning a property programmatically does not emit them.
|
|
149
189
|
|
|
190
|
+
### Form-associated controls
|
|
191
|
+
|
|
192
|
+
All form controls participate in native `FormData`, constraint validation, `form.reset()` and browser form-state restoration. The control captures its reset default once, after declarative attributes have been applied on its first connection. Later runtime property updates do not redefine that default. A disabled ancestor `fieldset` disables validation and interaction without mutating the control's public `disabled` property. For checkbox/radio groups, the group is the single submission, reset and restoration owner; managed child controls do not submit or restore an independent state.
|
|
193
|
+
|
|
150
194
|
## All Components
|
|
151
195
|
|
|
152
196
|
| Category | Component |
|
|
@@ -215,6 +259,12 @@ Text input with clearable, prefix/suffix slots.
|
|
|
215
259
|
|
|
216
260
|
**Slots:** `prefix`, `default`, `suffix`
|
|
217
261
|
|
|
262
|
+
**CSS Custom Properties:**
|
|
263
|
+
|
|
264
|
+
| Property | Default | Description |
|
|
265
|
+
| ------------------------- | -------------------------------- | ------------------ |
|
|
266
|
+
| `--wui-input-clear-color` | `var(--wui-color-text-tertiary)` | Clear button color |
|
|
267
|
+
|
|
218
268
|
#### `<web-ui-textarea>`
|
|
219
269
|
|
|
220
270
|
Multi-line text input with auto-resize.
|
|
@@ -244,6 +294,13 @@ Multi-line text input with auto-resize.
|
|
|
244
294
|
|
|
245
295
|
**Slots:** `prefix`, `suffix`
|
|
246
296
|
|
|
297
|
+
**CSS Custom Properties:**
|
|
298
|
+
|
|
299
|
+
| Property | Default | Description |
|
|
300
|
+
| ---------------------------- | -------------------------------- | ------------------ |
|
|
301
|
+
| `--wui-textarea-width` | `200px` | Textarea width |
|
|
302
|
+
| `--wui-textarea-clear-color` | `var(--wui-color-text-tertiary)` | Clear button color |
|
|
303
|
+
|
|
247
304
|
#### `<web-ui-input-number>`
|
|
248
305
|
|
|
249
306
|
Numeric input with step buttons and keyboard control.
|
|
@@ -288,6 +345,13 @@ Select dropdown with option items, keyboard navigation, and portal support.
|
|
|
288
345
|
|
|
289
346
|
Child `<web-ui-option>` elements register via `option-register` / `option-unregister` events. Supports ArrowDown/ArrowUp/Enter/Escape keyboard navigation.
|
|
290
347
|
|
|
348
|
+
**CSS Custom Properties:**
|
|
349
|
+
|
|
350
|
+
| Property | Default | Description |
|
|
351
|
+
| ------------------------- | ------- | ------------------ |
|
|
352
|
+
| `--wui-select-max-width` | `500px` | Dropdown max width |
|
|
353
|
+
| `--wui-overlay-min-width` | `200px` | Dropdown min width |
|
|
354
|
+
|
|
291
355
|
#### `<web-ui-autocomplete>`
|
|
292
356
|
|
|
293
357
|
Editable combobox with input filtering and single option selection.
|
|
@@ -314,6 +378,13 @@ Editable combobox with input filtering and single option selection.
|
|
|
314
378
|
|
|
315
379
|
Typing filters the option list by label (`contains` or `prefix`, or `none` to disable filtering). Selecting an option fills the input with its label and exposes the option's value via `selected-value`; `change` fires on selection commit. Supports ArrowDown/ArrowUp/Enter/Escape keyboard navigation.
|
|
316
380
|
|
|
381
|
+
**CSS Custom Properties:**
|
|
382
|
+
|
|
383
|
+
| Property | Default | Description |
|
|
384
|
+
| ------------------------------ | ------- | ---------------------- |
|
|
385
|
+
| `--wui-autocomplete-max-width` | `500px` | Dropdown max width |
|
|
386
|
+
| `--wui-overlay-min-width` | `200px` | Dropdown minimum width |
|
|
387
|
+
|
|
317
388
|
#### `<web-ui-slider>`
|
|
318
389
|
|
|
319
390
|
Range slider with marks and vertical orientation.
|
|
@@ -336,6 +407,18 @@ Range slider with marks and vertical orientation.
|
|
|
336
407
|
|
|
337
408
|
Supports ArrowLeft/Right/Up/Down, Home/End, PageUp/PageDown keyboard navigation. Uses pointer capture for drag interaction across mouse, touch, and pen.
|
|
338
409
|
|
|
410
|
+
**CSS Custom Properties:**
|
|
411
|
+
|
|
412
|
+
| Property | Default | Description |
|
|
413
|
+
| ------------------------------ | ----------------------------------- | ---------------------- |
|
|
414
|
+
| `--wui-slider-width` | `200px` | Slider width |
|
|
415
|
+
| `--wui-slider-vertical-height` | `200px` | Vertical slider height |
|
|
416
|
+
| `--wui-slider-height` | `var(--wui-slider-track-size, 6px)` | Track thickness |
|
|
417
|
+
| `--wui-slider-track-size` | `6px` | Track size |
|
|
418
|
+
| `--wui-slider-thumb-width` | `24px` | Thumb short axis |
|
|
419
|
+
| `--wui-slider-thumb-height` | `32px` | Thumb long axis |
|
|
420
|
+
| `--wui-slider-marks-inset` | `0` | Marks inset from edges |
|
|
421
|
+
|
|
339
422
|
#### `<web-ui-checkbox>`
|
|
340
423
|
|
|
341
424
|
Individual checkbox.
|
|
@@ -450,16 +533,16 @@ Radio group managing single selection.
|
|
|
450
533
|
|
|
451
534
|
Styled button with variants and loading state.
|
|
452
535
|
|
|
453
|
-
| Attribute | Type | Default | Description
|
|
454
|
-
| ------------ | ------------------------------------------------------------ | ---------- |
|
|
455
|
-
| `variant` | `'primary' \| 'secondary' \| 'ghost' \| 'danger' \| 'glass'` | `'glass'` | Button variant
|
|
456
|
-
| `type` | `'button' \| 'submit' \| 'reset'` | `'button'` | Inner-button type; invalid values become `button`
|
|
457
|
-
| `disabled` | `boolean` | `false` | Disabled state
|
|
458
|
-
| `loading` | `boolean` | `false` | Loading spinner
|
|
459
|
-
| `full` | `boolean` | `false` | Full width
|
|
460
|
-
| `icon` | `boolean` | `false` | Icon-only mode
|
|
461
|
-
| `size` | `string` | `''` |
|
|
462
|
-
| `aria-label` | `string` | — | Accessible label (delegated to inner button)
|
|
536
|
+
| Attribute | Type | Default | Description |
|
|
537
|
+
| ------------ | ------------------------------------------------------------ | ---------- | ----------------------------------------------------------------------- |
|
|
538
|
+
| `variant` | `'primary' \| 'secondary' \| 'ghost' \| 'danger' \| 'glass'` | `'glass'` | Button variant |
|
|
539
|
+
| `type` | `'button' \| 'submit' \| 'reset'` | `'button'` | Inner-button type; invalid values become `button` |
|
|
540
|
+
| `disabled` | `boolean` | `false` | Disabled state |
|
|
541
|
+
| `loading` | `boolean` | `false` | Loading spinner |
|
|
542
|
+
| `full` | `boolean` | `false` | Full width |
|
|
543
|
+
| `icon` | `boolean` | `false` | Icon-only mode |
|
|
544
|
+
| `size` | `string` | `''` | Button height in px (icon mode: also sets min-width for square default) |
|
|
545
|
+
| `aria-label` | `string` | — | Accessible label (delegated to inner button) |
|
|
463
546
|
|
|
464
547
|
**Events:** standard `click`
|
|
465
548
|
|
|
@@ -470,6 +553,18 @@ form-associated control when external form submission behavior is required.
|
|
|
470
553
|
|
|
471
554
|
Disabled and loading states prevent `click` events.
|
|
472
555
|
|
|
556
|
+
**CSS Custom Properties:**
|
|
557
|
+
|
|
558
|
+
| Property | Default | Description |
|
|
559
|
+
| ------------------------ | ------------- | --------------------------------------- |
|
|
560
|
+
| `--wui-button-width` | `max-content` | Button width |
|
|
561
|
+
| `--wui-button-px` | `12px` | Horizontal padding |
|
|
562
|
+
| `--wui-button-gap` | `8px` | Gap between prefix/default/suffix slots |
|
|
563
|
+
| `--wui-button-color` | variant-based | Button text color |
|
|
564
|
+
| `--wui-button-bg` | variant-based | Button background color |
|
|
565
|
+
| `--wui-button-bg-hover` | variant-based | Button hover background |
|
|
566
|
+
| `--wui-button-bg-active` | variant-based | Button active background |
|
|
567
|
+
|
|
473
568
|
#### `<web-ui-button-group>`
|
|
474
569
|
|
|
475
570
|
Button group that manages child button layout and direction.
|
|
@@ -480,7 +575,7 @@ Button group that manages child button layout and direction.
|
|
|
480
575
|
|
|
481
576
|
**Slots:** `default` (project `<web-ui-button>` elements)
|
|
482
577
|
|
|
483
|
-
|
|
578
|
+
Applies the direction to the grouped button layout without changing child button attributes.
|
|
484
579
|
|
|
485
580
|
---
|
|
486
581
|
|
|
@@ -490,11 +585,12 @@ Propagates `direction` attribute to child buttons.
|
|
|
490
585
|
|
|
491
586
|
Modal dialog using native `<dialog>` with `showModal()`.
|
|
492
587
|
|
|
493
|
-
| Attribute | Type | Default | Description
|
|
494
|
-
| ------------------- | --------- | ------- |
|
|
495
|
-
| `open` | `boolean` | `false` | Dialog visibility
|
|
496
|
-
| `no-scroll-lock` | `boolean` | `false` | Do not lock body scroll when open
|
|
497
|
-
| `no-backdrop-close` | `boolean` | `false` | Do not close on backdrop click
|
|
588
|
+
| Attribute | Type | Default | Description |
|
|
589
|
+
| ------------------- | --------- | ------- | ----------------------------------- |
|
|
590
|
+
| `open` | `boolean` | `false` | Dialog visibility |
|
|
591
|
+
| `no-scroll-lock` | `boolean` | `false` | Do not lock body scroll when open |
|
|
592
|
+
| `no-backdrop-close` | `boolean` | `false` | Do not close on backdrop click |
|
|
593
|
+
| `no-escape-close` | `boolean` | `false` | Do not close when Escape is pressed |
|
|
498
594
|
|
|
499
595
|
**Events:** `open-change` (`CustomEvent<{ open: boolean }>`)
|
|
500
596
|
|
|
@@ -502,28 +598,49 @@ Modal dialog using native `<dialog>` with `showModal()`.
|
|
|
502
598
|
|
|
503
599
|
**Methods:** `showModal()`, `close()`
|
|
504
600
|
|
|
505
|
-
Uses native `<dialog>` with `@cancel` prevention
|
|
601
|
+
Uses native `<dialog>` with `@cancel` prevention. Escape calls `close()` unless `no-escape-close` is present. Click on backdrop closes dialog unless `no-backdrop-close` is present.
|
|
602
|
+
|
|
603
|
+
**CSS Custom Properties:**
|
|
604
|
+
|
|
605
|
+
| Property | Default | Description |
|
|
606
|
+
| ------------------------- | --------------------------- | ------------------- |
|
|
607
|
+
| `--wui-dialog-max-width` | `360px` | Dialog max width |
|
|
608
|
+
| `--wui-dialog-overlay-bg` | `var(--wui-color-backdrop)` | Backdrop background |
|
|
506
609
|
|
|
507
610
|
#### `<web-ui-drawer>`
|
|
508
611
|
|
|
509
612
|
Side drawer using native `<dialog>` with closing animation.
|
|
510
613
|
|
|
511
|
-
| Attribute | Type | Default | Description
|
|
512
|
-
| ------------------- | ---------------------------------------- | --------- |
|
|
513
|
-
| `open` | `boolean` | `false` | Drawer visibility
|
|
514
|
-
| `placement` | `'right' \| 'left' \| 'top' \| 'bottom'` | `'right'` | Slide-in direction
|
|
515
|
-
| `heading` | `string` | `''` | Title text (fallback when no header slot)
|
|
516
|
-
| `closable` | `boolean` | `false` | Show close button
|
|
517
|
-
| `no-scroll-lock` | `boolean` | `false` | Do not lock body scroll when open
|
|
518
|
-
| `no-backdrop-close` | `boolean` | `false` | Do not close on backdrop click
|
|
614
|
+
| Attribute | Type | Default | Description |
|
|
615
|
+
| ------------------- | ---------------------------------------- | --------- | --------------------------------------------------------------------------------- |
|
|
616
|
+
| `open` | `boolean` | `false` | Drawer visibility |
|
|
617
|
+
| `placement` | `'right' \| 'left' \| 'top' \| 'bottom'` | `'right'` | Slide-in direction |
|
|
618
|
+
| `heading` | `string` | `''` | Title text (fallback when no header slot) |
|
|
619
|
+
| `closable` | `boolean` | `false` | Show close button |
|
|
620
|
+
| `no-scroll-lock` | `boolean` | `false` | Do not lock body scroll when open |
|
|
621
|
+
| `no-backdrop-close` | `boolean` | `false` | Do not close on backdrop click |
|
|
622
|
+
| `request-only` | `boolean` | `false` | User close actions only request `open=false`; the consumer must update `open` |
|
|
623
|
+
| `headless` | `boolean` | `false` | Keep only overlay behavior and render the default slot without built-in drawer UI |
|
|
624
|
+
| `dialog-label` | `string` | `''` | Accessible name for the internal native dialog; required in headless mode |
|
|
519
625
|
|
|
520
|
-
**Events:** `open-change` (`CustomEvent<{ open: boolean }>`)
|
|
626
|
+
**Events:** `open-change` (`CustomEvent<{ open: boolean }>`). With `request-only`, Escape, backdrop and the built-in close button only request `open=false`; the drawer remains open until the consumer writes `open=false`. If native dialog closure occurs while that request is rejected, the drawer restores its open top-layer state and emits the same request.
|
|
521
627
|
|
|
522
|
-
**Slots:** `header`, `default`, `footer`
|
|
628
|
+
**Slots:** `header`, `default`, `footer` — with `headless`, only the `default` slot is rendered.
|
|
523
629
|
|
|
524
630
|
**Methods:** `show()`, `close()`
|
|
525
631
|
|
|
526
|
-
|
|
632
|
+
`headless` keeps the native dialog, backdrop, placement animation, Escape/backdrop close behavior, and scroll locking. It does not render the built-in glass body, header, close button, or footer; style the default-slot content completely in the consumer.
|
|
633
|
+
|
|
634
|
+
Closing keeps the native dialog in the top layer until the `--wui-duration-drawer-exit` transition completes (240ms by default), then calls `dialog.close()`. Escape always follows this close path; `no-backdrop-close` controls backdrop clicks only.
|
|
635
|
+
|
|
636
|
+
**CSS Custom Properties:**
|
|
637
|
+
|
|
638
|
+
| Property | Default | Description |
|
|
639
|
+
| ------------------------- | ---------------------------------- | -------------------------- |
|
|
640
|
+
| `--wui-drawer-width` | `320px` | Drawer width |
|
|
641
|
+
| `--wui-drawer-height` | `300px` | Drawer height (top/bottom) |
|
|
642
|
+
| `--wui-drawer-bg` | `var(--wui-color-surface-overlay)` | Drawer body background |
|
|
643
|
+
| `--wui-drawer-overlay-bg` | `rgb(0 0 0 / 0.12)` | Backdrop background |
|
|
527
644
|
|
|
528
645
|
---
|
|
529
646
|
|
|
@@ -573,6 +690,13 @@ Tooltip overlay using pointer/focus triggers.
|
|
|
573
690
|
|
|
574
691
|
`open` is a controlled visibility property. Pointer/focus triggers update it, and direct updates synchronize the local or portal panel. Adjacent tooltips open immediately after the first tooltip is visible; pointer/focus triggers otherwise use delay timers.
|
|
575
692
|
|
|
693
|
+
**CSS Custom Properties:**
|
|
694
|
+
|
|
695
|
+
| Property | Default | Description |
|
|
696
|
+
| ------------------------- | ------- | ----------------- |
|
|
697
|
+
| `--wui-tooltip-max-width` | `240px` | Tooltip max width |
|
|
698
|
+
| `--wui-tooltip-font-size` | `13px` | Tooltip font size |
|
|
699
|
+
|
|
576
700
|
#### `<web-ui-context-menu>`
|
|
577
701
|
|
|
578
702
|
Right-click context menu.
|
|
@@ -685,6 +809,17 @@ Empty state placeholder.
|
|
|
685
809
|
|
|
686
810
|
**Slots:** `default` (title, overrides `title` prop), `icon`, `description`, `action`
|
|
687
811
|
|
|
812
|
+
**CSS Custom Properties:**
|
|
813
|
+
|
|
814
|
+
| Property | Default | Description |
|
|
815
|
+
| ----------------------------------- | ----------- | ------------------------------ |
|
|
816
|
+
| `--wui-empty-min-height` | `240px` | Min height (medium) |
|
|
817
|
+
| `--wui-empty-padding` | `32px 24px` | Padding (medium) |
|
|
818
|
+
| `--wui-empty-icon-size` | `56px` | Icon container size (medium) |
|
|
819
|
+
| `--wui-empty-content-width` | `480px` | Max width of title/description |
|
|
820
|
+
| `--wui-empty-title-font-size` | `16px` | Title font size (medium) |
|
|
821
|
+
| `--wui-empty-description-font-size` | `14px` | Description font size (medium) |
|
|
822
|
+
|
|
688
823
|
#### `<web-ui-icon>`
|
|
689
824
|
|
|
690
825
|
Icon renderer using Iconify data objects.
|
|
@@ -703,6 +838,12 @@ import { lucideLoaderCircle } from '@greypan/web-ui/icons'
|
|
|
703
838
|
html`<web-ui-icon .icon=${lucideLoaderCircle} spin />`
|
|
704
839
|
```
|
|
705
840
|
|
|
841
|
+
**CSS Custom Properties:**
|
|
842
|
+
|
|
843
|
+
| Property | Default | Description |
|
|
844
|
+
| ------------------ | --------- | ----------- |
|
|
845
|
+
| `--wui-icon-color` | `inherit` | Icon color |
|
|
846
|
+
|
|
706
847
|
#### `<web-ui-spinner>`
|
|
707
848
|
|
|
708
849
|
Loading spinner.
|
|
@@ -735,14 +876,37 @@ WebUiSpinner.hide() // hide
|
|
|
735
876
|
|
|
736
877
|
#### `<web-ui-layout>`
|
|
737
878
|
|
|
738
|
-
|
|
879
|
+
Responsive page layout with an optional full-width banner, a collapsible desktop sidebar, and a headless-drawer mobile sidebar. The page itself scrolls; the desktop sidebar and header stick to the viewport after the banner scrolls away.
|
|
880
|
+
|
|
881
|
+
| Attribute | Type | Default | Description |
|
|
882
|
+
| ------------------- | --------- | --------- | ----------------------------------------------------- |
|
|
883
|
+
| `sidebar-collapsed` | `boolean` | `false` | Controlled desktop sidebar collapsed state |
|
|
884
|
+
| `sidebar-open` | `boolean` | `false` | Controlled mobile sidebar drawer open state |
|
|
885
|
+
| `header-glow` | `boolean` | `false` | Decorative Header background glow behind slot content |
|
|
886
|
+
| `sidebar-width` | `string` | `'240px'` | Expanded desktop and mobile sidebar width |
|
|
887
|
+
| `collapsed-width` | `string` | `'72px'` | Collapsed desktop sidebar width |
|
|
888
|
+
|
|
889
|
+
**Events:** `sidebar-collapsed-change` (`CustomEvent<{ collapsed: boolean }>`) requests a desktop collapse-state update. `sidebar-open-change` (`CustomEvent<{ open: boolean }>`) requests a mobile drawer open-state update. Consumers must write the requested value back to the corresponding controlled property.
|
|
890
|
+
|
|
891
|
+
| Slot | Description |
|
|
892
|
+
| --------- | ----------------------------------------------------------------------------------------- |
|
|
893
|
+
| `banner` | Optional full-width banner above the layout body |
|
|
894
|
+
| `header` | Sticky content-area header |
|
|
895
|
+
| `sidebar` | Sidebar-card content. The consumer owns its internal fixed regions and scroll containers. |
|
|
896
|
+
| `default` | Main content |
|
|
897
|
+
| `tabbar` | Bottom tab bar |
|
|
898
|
+
|
|
899
|
+
`web-ui-layout` constrains the sidebar card and owns the desktop toggle area, but does not create a sidebar scrollport. To make only part of the sidebar scroll, make the `sidebar` slot root a `height: 100%; min-height: 0` flex column and apply `overflow-y: auto` to the intended child. This keeps consumer-defined headers and footers fixed without adding extra public slots.
|
|
739
900
|
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
|
|
901
|
+
At `640px` and below, the sidebar becomes a headless `web-ui-drawer`. The consumer content is rendered in the same rounded sidebar card; the mobile toggle appears in the header row.
|
|
902
|
+
|
|
903
|
+
`header-glow` adds a pointer-transparent decorative glow behind header-slot content and the mobile toggle. It is a Header background rather than a foreground layer, so slotted content remains above it. Override its color with `--wui-layout-header-glow-color` (default: `--wui-color-page`). The glow concentration and spread are controlled by the internal variable `--wui-layout-header-glow-height` (default: `150%`); increase for stronger coverage, decrease for a subtler effect. Layout layers are ordered as Header (`10`) < Auxiliary (`20`) < Banner (`30`) < Tabbar (`40`) < Sidebar (`50`).
|
|
904
|
+
|
|
905
|
+
**CSS Custom Properties:**
|
|
906
|
+
|
|
907
|
+
| Property | Default | Description |
|
|
908
|
+
| ----------------------------- | ------- | ------------------------------------------------ |
|
|
909
|
+
| `--wui-layout-sidebar-radius` | `28px` | Border radius of sidebar card (desktop & mobile) |
|
|
746
910
|
|
|
747
911
|
#### `<web-ui-back-top>`
|
|
748
912
|
|
|
@@ -759,10 +923,21 @@ Scroll-to-top button.
|
|
|
759
923
|
|
|
760
924
|
**Methods:** `toTop()`
|
|
761
925
|
|
|
762
|
-
**Positioning:** With `scrollTarget` as `window`, the button is fixed to the viewport corner. With `scrollTarget` as an `HTMLElement`, place the element inside that container and the button floats at the container's bottom corner via `position: sticky`. Offsets follow the `--
|
|
926
|
+
**Positioning:** With `scrollTarget` as `window`, the button is fixed to the viewport corner. With `scrollTarget` as an `HTMLElement`, place the element inside that container and the button floats at the container's bottom corner via `position: sticky`. Offsets follow the `--wui-back-top-top/right/bottom/left` CSS variables.
|
|
763
927
|
|
|
764
928
|
Role: `button`, keyboard Enter scrolls to top.
|
|
765
929
|
|
|
930
|
+
**CSS Custom Properties:**
|
|
931
|
+
|
|
932
|
+
| Property | Default | Description |
|
|
933
|
+
| ------------------------- | -------------------------------- | ------------- |
|
|
934
|
+
| `--wui-back-top-position` | `fixed` | CSS position |
|
|
935
|
+
| `--wui-back-top-z-index` | `var(--wui-layer-auxiliary, 20)` | Z-index |
|
|
936
|
+
| `--wui-back-top-top` | `auto` | Top offset |
|
|
937
|
+
| `--wui-back-top-right` | `20px` | Right offset |
|
|
938
|
+
| `--wui-back-top-bottom` | `20px` | Bottom offset |
|
|
939
|
+
| `--wui-back-top-left` | `auto` | Left offset |
|
|
940
|
+
|
|
766
941
|
#### `<web-ui-svg-draw-lines>`
|
|
767
942
|
|
|
768
943
|
SVG line drawing animation using `stroke-dashoffset`. Animates geometry in-place — no cloning, no DOM manipulation.
|
|
@@ -791,7 +966,76 @@ Theme provider defining CSS custom property tokens.
|
|
|
791
966
|
|
|
792
967
|
**Methods:** `getOverlayRoot()` — returns the portal overlay container
|
|
793
968
|
|
|
794
|
-
Defines
|
|
969
|
+
Defines foundation, color, layer, shadow, and motion tokens for its subtree. `motion="system"` follows `prefers-reduced-motion`; use `motion="reduced"` to reduce animation in a scope or `motion="full"` in a nested theme to restore normal token values. System appearance follows `prefers-color-scheme`.
|
|
970
|
+
|
|
971
|
+
**Foundation tokens:**
|
|
972
|
+
|
|
973
|
+
| Property | Default | Description |
|
|
974
|
+
| ------------------------- | ------- | ------------------------------------------------ |
|
|
975
|
+
| `--wui-font-size` | `14px` | Base font size for controls |
|
|
976
|
+
| `--wui-input-width` | `200px` | Default width for compact form controls |
|
|
977
|
+
| `--wui-control-size` | `40px` | Default height and square min-width for controls |
|
|
978
|
+
| `--wui-overlay-min-width` | `200px` | Minimum anchored overlay width |
|
|
979
|
+
| `--wui-focus-ring-width` | `3px` | Focus indicator width |
|
|
980
|
+
|
|
981
|
+
**Layer tokens:**
|
|
982
|
+
|
|
983
|
+
| Property | Default | Description |
|
|
984
|
+
| ---------------------------- | ------- | ---------------------------- |
|
|
985
|
+
| `--wui-layer-base` | `0` | Base content |
|
|
986
|
+
| `--wui-layer-inline-overlay` | `1` | Overlay local to a component |
|
|
987
|
+
| `--wui-layer-header` | `10` | Page header |
|
|
988
|
+
| `--wui-layer-auxiliary` | `20` | Floating utility controls |
|
|
989
|
+
| `--wui-layer-banner` | `30` | Banners |
|
|
990
|
+
| `--wui-layer-tabbar` | `40` | Tab bars |
|
|
991
|
+
| `--wui-layer-sidebar` | `50` | Sidebars |
|
|
992
|
+
| `--wui-layer-menu` | `100` | Menus and floating panels |
|
|
993
|
+
| `--wui-layer-menu-nested` | `110` | Nested menus |
|
|
994
|
+
| `--wui-layer-toast` | `200` | Toasts |
|
|
995
|
+
| `--wui-layer-loading` | `300` | Blocking loading surfaces |
|
|
996
|
+
|
|
997
|
+
**Motion tokens:** duration defaults are `--wui-duration-press: 80ms`, `--wui-duration-feedback: 100ms`, `--wui-duration-trigger: 160ms`, `--wui-duration-focus: 200ms`, `--wui-duration-menu-enter: 140ms`, `--wui-duration-menu-exit: 100ms`, `--wui-duration-overlay-enter: 180ms`, `--wui-duration-overlay-exit: 140ms`, `--wui-duration-drawer-enter: 280ms`, `--wui-duration-drawer-exit: 240ms`, `--wui-duration-layout: 200ms`. Easing tokens are `--wui-ease-enter` and `--wui-ease-slide`; enter scale is `--wui-scale-enter: 0.97`.
|
|
998
|
+
|
|
999
|
+
**Color tokens:**
|
|
1000
|
+
|
|
1001
|
+
| Property | Light default | Dark default | Description |
|
|
1002
|
+
| ---------------------------------- | ------------------------------------------------------------ | ------------------------------------------------------------ | ------------------------------- |
|
|
1003
|
+
| `--wui-color-page` | `#fff` | `#18181a` | Page background |
|
|
1004
|
+
| `--wui-color-surface` | `#fff` | `#2c2c2e` | Plain surface |
|
|
1005
|
+
| `--wui-color-surface-raised` | `#f2f2f7` | `#2c2c2e` | Raised surface |
|
|
1006
|
+
| `--wui-color-surface-control` | `#dfdfdf` | `#3a3a3c` | Neutral control surface |
|
|
1007
|
+
| `--wui-color-surface-track` | `#e5e5ea` | `#444446` | Slider and switch track surface |
|
|
1008
|
+
| `--wui-color-surface-glass` | `rgb(250 250 250 / 0.34)` | `rgb(44 44 46 / 0.42)` | Liquid glass surface |
|
|
1009
|
+
| `--wui-color-surface-glass-hover` | `color-mix(... text 6%, surface-glass)` | `color-mix(... text 6%, surface-glass)` | Full glass hover background |
|
|
1010
|
+
| `--wui-color-surface-glass-active` | `color-mix(... text 15%, surface-glass)` | `color-mix(... text 15%, surface-glass)` | Full glass pressed background |
|
|
1011
|
+
| `--wui-color-surface-overlay` | `rgb(246 246 246 / 0.82)` | `rgb(44 44 46 / 0.82)` | Translucent overlay surface |
|
|
1012
|
+
| `--wui-color-text` | `#1b1b1b` | `#f5f5f7` | Primary text |
|
|
1013
|
+
| `--wui-color-text-secondary` | `#6a6a6a` | `#a1a1a6` | Secondary text |
|
|
1014
|
+
| `--wui-color-text-tertiary` | `color-mix(in srgb, var(--wui-color-text) 35%, transparent)` | `color-mix(in srgb, var(--wui-color-text) 42%, transparent)` | Tertiary text and quiet icons |
|
|
1015
|
+
| `--wui-color-text-disabled` | `color-mix(in srgb, var(--wui-color-text) 32%, transparent)` | `color-mix(in srgb, var(--wui-color-text) 38%, transparent)` | Disabled foreground text |
|
|
1016
|
+
| `--wui-color-state-layer-hover` | `color-mix(in srgb, var(--wui-color-text) 6%, transparent)` | `color-mix(in srgb, var(--wui-color-text) 6%, transparent)` | Transparent hover overlay |
|
|
1017
|
+
| `--wui-color-state-layer-active` | `color-mix(in srgb, var(--wui-color-text) 15%, transparent)` | `color-mix(in srgb, var(--wui-color-text) 15%, transparent)` | Transparent pressed overlay |
|
|
1018
|
+
| `--wui-color-border` | `rgb(0 0 0 / 0.1)` | `rgb(255 255 255 / 0.14)` | Normal border and divider |
|
|
1019
|
+
| `--wui-color-glass-border` | `rgb(51 51 51 / 0.12)` | `rgb(255 255 255 / 0.16)` | Glass border tint |
|
|
1020
|
+
| `--wui-color-glass-highlight` | `rgb(255 255 255 / 0.9)` | `rgb(255 255 255 / 0.22)` | Glass edge highlight |
|
|
1021
|
+
| `--wui-color-accent` | `#08f` | `#0a84ff` | Accent and focused input border |
|
|
1022
|
+
| `--wui-color-on-accent` | `#fff` | `#fff` | Foreground on accent |
|
|
1023
|
+
| `--wui-color-success` | `#16a34a` | `#30d158` | Success |
|
|
1024
|
+
| `--wui-color-warning` | `#d97706` | `#ff9f0a` | Warning |
|
|
1025
|
+
| `--wui-color-danger` | `#dc2626` | `#ff453a` | Danger |
|
|
1026
|
+
| `--wui-color-info` | `#2563eb` | `#64d2ff` | Info |
|
|
1027
|
+
| `--wui-color-backdrop` | `rgb(0 0 0 / 0.12)` | `rgb(0 0 0 / 0.48)` | Modal backdrop |
|
|
1028
|
+
| `--wui-color-focus-ring` | `rgb(0 136 255 / 0.4)` | `rgb(10 132 255 / 0.62)` | Focus indicator color |
|
|
1029
|
+
|
|
1030
|
+
**Shadow tokens:**
|
|
1031
|
+
|
|
1032
|
+
| Property | Light default | Dark default | Description |
|
|
1033
|
+
| ---------------------- | -------------------------------- | ------------------------------- | --------------------------- |
|
|
1034
|
+
| `--wui-shadow-overlay` | `2px 16px 40px rgb(0 0 0 / 0.4)` | `0 18px 48px rgb(0 0 0 / 0.54)` | Modal and drawer shadow |
|
|
1035
|
+
| `--wui-shadow-panel` | `0 3px 9px rgb(0 0 0 / 0.27)` | `0 4px 16px rgb(0 0 0 / 0.35)` | Small floating panel shadow |
|
|
1036
|
+
| `--wui-shadow-glass` | four-layer diffuse shadow | `0 12px 32px rgb(0 0 0 / 0.38)` | Base liquid glass shadow |
|
|
1037
|
+
|
|
1038
|
+
**Internal tokens:** variables prefixed `--wui-internal-*` are private wiring between shadow DOM parts; they are not part of the public token API and must not be overridden by consumers.
|
|
795
1039
|
|
|
796
1040
|
---
|
|
797
1041
|
|
|
@@ -845,6 +1089,13 @@ toast.updateMessage(id, { message: 'Upload 60% complete', heading: 'Uploading' }
|
|
|
845
1089
|
|
|
846
1090
|
Hover pauses auto-close timer (uses `pointerenter`/`pointerleave`). Batch-mounts toasts created in the same microtask.
|
|
847
1091
|
|
|
1092
|
+
**CSS Custom Properties:**
|
|
1093
|
+
|
|
1094
|
+
| Property | Default | Description |
|
|
1095
|
+
| ------------------------------- | ------- | -------------------------------------------------- |
|
|
1096
|
+
| `--wui-toast-viewport-gap` | `16px` | Visible distance between toasts and viewport edges |
|
|
1097
|
+
| `--wui-toast-container-padding` | `40px` | Container padding reserved for diffuse shadows |
|
|
1098
|
+
|
|
848
1099
|
---
|
|
849
1100
|
|
|
850
1101
|
### Sub-items
|
|
@@ -864,6 +1115,12 @@ Selection option for `<web-ui-select>`.
|
|
|
864
1115
|
|
|
865
1116
|
Not form-associated (child of select, not independent submit).
|
|
866
1117
|
|
|
1118
|
+
**CSS Custom Properties:**
|
|
1119
|
+
|
|
1120
|
+
| Property | Default | Description |
|
|
1121
|
+
| ---------------------------- | ------- | --------------------------------------------- |
|
|
1122
|
+
| `--wui-option-check-display` | `block` | Display mode of the selection check indicator |
|
|
1123
|
+
|
|
867
1124
|
#### `<web-ui-segmented-trigger>`
|
|
868
1125
|
|
|
869
1126
|
Segment trigger for `<web-ui-segmented>`.
|
|
@@ -877,3 +1134,11 @@ Segment trigger for `<web-ui-segmented>`.
|
|
|
877
1134
|
**Events:** `change`
|
|
878
1135
|
|
|
879
1136
|
Not form-associated (child of segmented, not independent submit).
|
|
1137
|
+
|
|
1138
|
+
**CSS Custom Properties:**
|
|
1139
|
+
|
|
1140
|
+
| Property | Default | Description |
|
|
1141
|
+
| ----------------------------------- | -------------------------------- | ------------------------- |
|
|
1142
|
+
| `--wui-segmented-trigger-px` | `12px` | Horizontal padding |
|
|
1143
|
+
| `--wui-segmented-trigger-bg-hover` | `--wui-color-state-layer-hover` | Trigger hover background |
|
|
1144
|
+
| `--wui-segmented-trigger-bg-active` | `--wui-color-state-layer-active` | Trigger active background |
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
//#region \0@oxc-project+runtime@0.
|
|
1
|
+
//#region \0@oxc-project+runtime@0.146.0/helpers/esm/decorate.js
|
|
2
2
|
function e(e, t, n, r) {
|
|
3
3
|
var i = arguments.length, a = i < 3 ? t : r === null ? r = Object.getOwnPropertyDescriptor(t, n) : r, o;
|
|
4
4
|
if (typeof Reflect == "object" && typeof Reflect.decorate == "function") a = Reflect.decorate(e, t, n, r);
|
package/dist/assets/glass.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
//#region src/assets/glass.css?inline
|
|
2
|
-
var e = ".wui-glass{
|
|
2
|
+
var e = ".wui-glass{background-color:var(--wui-color-surface-glass,#fafafa57);background-image:linear-gradient(to bottom, color-mix(in srgb, var(--wui-color-glass-highlight,#ffffffe6) 20%, transparent), color-mix(in srgb, var(--wui-color-glass-highlight,#ffffffe6) 4%, transparent) 48%, transparent);-webkit-backdrop-filter:blur(4px)saturate(160%)brightness(1.06);backdrop-filter:blur(4px)saturate(160%)brightness(1.06);box-shadow:inset 0 0 0 .5px color-mix(in srgb, var(--wui-color-glass-highlight,#ffffffe6) 38%, transparent), inset 0 1px .5px color-mix(in srgb, var(--wui-color-glass-highlight,#ffffffe6) 52%, transparent), inset 0 -.5px 1px #00000008, var(--wui-internal-glass-focus-ring,0 0 0 0 transparent), var(--wui-internal-glass-shadow,var(--wui-shadow-glass,0 0 1px #0000000d, 0 0 8px #00000008, 0 2px 16px #00000006, 0 8px 32px #00000004));background-clip:padding-box;position:relative}";
|
|
3
3
|
//#endregion
|
|
4
4
|
export { e as default };
|
|
5
5
|
|
package/dist/assets/glass.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"glass.js","names":[],"sources":["../../src/assets/glass.css?inline"],"sourcesContent":["/*\n * 玻璃公共样式\n */\n\n.wui-glass {\n position: relative;\n\n
|
|
1
|
+
{"version":3,"file":"glass.js","names":[],"sources":["../../src/assets/glass.css?inline"],"sourcesContent":["/*\n * 玻璃公共样式\n */\n\n.wui-glass {\n position: relative;\n\n background-color: var(--wui-color-surface-glass, rgb(250 250 250 / 0.34));\n background-image: linear-gradient(\n to bottom,\n color-mix(in srgb, var(--wui-color-glass-highlight, rgb(255 255 255 / 0.9)) 20%, transparent),\n color-mix(in srgb, var(--wui-color-glass-highlight, rgb(255 255 255 / 0.9)) 4%, transparent) 48%,\n transparent\n );\n background-clip: padding-box;\n\n /* Safari 16.4 只支持带 -webkit- 前缀的 backdrop-filter(无前缀 18 才支持),\n lightningcss 对 ?inline 导入不做自动前缀,需手动写前缀版本 */\n /* stylelint-disable-next-line property-no-vendor-prefix */\n -webkit-backdrop-filter: blur(4px) saturate(160%) brightness(1.06);\n backdrop-filter: blur(4px) saturate(160%) brightness(1.06);\n box-shadow:\n inset 0 0 0 0.5px color-mix(in srgb, var(--wui-color-glass-highlight, rgb(255 255 255 / 0.9)) 38%, transparent),\n inset 0 1px 0.5px color-mix(in srgb, var(--wui-color-glass-highlight, rgb(255 255 255 / 0.9)) 52%, transparent),\n inset 0 -0.5px 1px rgb(0 0 0 / 0.03),\n var(--wui-internal-glass-focus-ring, 0 0 0 0 transparent),\n var(\n --wui-internal-glass-shadow,\n var(\n --wui-shadow-glass,\n 0 0 1px rgb(0 0 0 / 0.05),\n 0 0 8px rgb(0 0 0 / 0.03),\n 0 2px 16px rgb(0 0 0 / 0.025),\n 0 8px 32px rgb(0 0 0 / 0.015)\n )\n );\n}\n"],"mappings":""}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
//#region src/assets/menu-portal.css?inline
|
|
2
|
-
var e = ".wui-menu-portal-overlay{--wui-glass-shadow:var(--wui-shadow-
|
|
2
|
+
var e = ".wui-menu-portal-overlay{--wui-internal-glass-shadow:var(--wui-shadow-panel,0 3px 9px #00000045);--wui-internal-duration-overlay-enter:var(--wui-duration-menu-enter,.14s);--wui-internal-duration-overlay-exit:var(--wui-duration-menu-exit,.1s);-webkit-user-select:none;user-select:none;z-index:var(--wui-layer-menu,100);box-sizing:border-box;min-width:var(--wui-overlay-min-width,200px);max-width:90vw;max-height:80vh;color:var(--wui-color-text,#1b1b1b);background-color:var(--wui-color-surface-overlay,#f6f6f6d1);border-radius:20px;position:fixed;overflow:hidden}.wui-menu-portal-overlay .wui-menu-scroll{max-height:80vh;overflow-y:auto}.wui-menu-portal-overlay .wui-menu-content{padding:4px}.wui-menu-portal-overlay.dropdown-overlay .wui-menu-scroll{max-height:320px}.wui-menu-portal-overlay.dropdown-overlay[data-level]:not([data-level=\"0\"]),.wui-menu-portal-overlay.context-submenu{z-index:var(--wui-layer-menu-nested,110)}";
|
|
3
3
|
//#endregion
|
|
4
4
|
export { e as default };
|
|
5
5
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"menu-portal.js","names":[],"sources":["../../src/assets/menu-portal.css?inline"],"sourcesContent":[".wui-menu-portal-overlay {\n --wui-glass-shadow: var(--wui-shadow-
|
|
1
|
+
{"version":3,"file":"menu-portal.js","names":[],"sources":["../../src/assets/menu-portal.css?inline"],"sourcesContent":[".wui-menu-portal-overlay {\n --wui-internal-glass-shadow: var(--wui-shadow-panel, 0 3px 9px rgb(0 0 0 / 0.27));\n --wui-internal-duration-overlay-enter: var(--wui-duration-menu-enter, 140ms);\n --wui-internal-duration-overlay-exit: var(--wui-duration-menu-exit, 100ms);\n user-select: none;\n\n position: fixed;\n z-index: var(--wui-layer-menu, 100);\n\n overflow: hidden;\n\n box-sizing: border-box;\n min-width: var(--wui-overlay-min-width, 200px);\n max-width: 90vw;\n max-height: 80vh;\n border-radius: 20px;\n\n color: var(--wui-color-text, #1b1b1b);\n\n background-color: var(--wui-color-surface-overlay, rgb(246 246 246 / 0.82));\n\n & .wui-menu-scroll {\n overflow-y: auto;\n max-height: 80vh;\n }\n\n & .wui-menu-content {\n padding: 4px;\n }\n\n &.dropdown-overlay {\n & .wui-menu-scroll {\n max-height: 320px;\n }\n\n &[data-level]:not([data-level='0']) {\n z-index: var(--wui-layer-menu-nested, 110);\n }\n }\n\n &.context-submenu {\n z-index: var(--wui-layer-menu-nested, 110);\n }\n}\n"],"mappings":""}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
//#region src/assets/overlay-motion.css?inline
|
|
2
|
-
var e = ".wui-floating-panel{transform-origin:var(--wui-overlay-transform-origin,center);opacity:1;transition:opacity var(--wui-duration-overlay-enter,.18s) var(--wui-ease-
|
|
2
|
+
var e = ".wui-floating-panel{transform-origin:var(--wui-internal-overlay-transform-origin,center);opacity:1;transition:opacity var(--wui-internal-duration-overlay-enter,var(--wui-duration-overlay-enter,.18s)) var(--wui-ease-enter,cubic-bezier(.23, 1, .32, 1)), transform var(--wui-internal-duration-overlay-enter,var(--wui-duration-overlay-enter,.18s)) var(--wui-ease-enter,cubic-bezier(.23, 1, .32, 1));transform:scale(1)}.wui-floating-panel[data-wui-presence=entering],.wui-floating-panel[data-wui-presence=closing]{transform:scale(var(--wui-scale-enter,.97));opacity:0}.wui-floating-panel[data-wui-presence=closing]{pointer-events:none;transition-duration:var(--wui-internal-duration-overlay-exit,var(--wui-duration-overlay-exit,.14s))}@media (prefers-reduced-motion:reduce){.wui-floating-panel,.wui-floating-panel[data-wui-presence=entering],.wui-floating-panel[data-wui-presence=closing]{transition-duration:.12s;transform:none}}";
|
|
3
3
|
//#endregion
|
|
4
4
|
export { e as default };
|
|
5
5
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"overlay-motion.js","names":[],"sources":["../../src/assets/overlay-motion.css?inline"],"sourcesContent":[".wui-floating-panel {\n transform-origin: var(--wui-overlay-transform-origin, center);\n transform: scale(1);\n opacity: 1;\n transition:\n opacity var(--wui-duration-overlay-enter, 180ms)
|
|
1
|
+
{"version":3,"file":"overlay-motion.js","names":[],"sources":["../../src/assets/overlay-motion.css?inline"],"sourcesContent":[".wui-floating-panel {\n transform-origin: var(--wui-internal-overlay-transform-origin, center);\n transform: scale(1);\n opacity: 1;\n transition:\n opacity var(--wui-internal-duration-overlay-enter, var(--wui-duration-overlay-enter, 180ms))\n var(--wui-ease-enter, cubic-bezier(0.23, 1, 0.32, 1)),\n transform var(--wui-internal-duration-overlay-enter, var(--wui-duration-overlay-enter, 180ms))\n var(--wui-ease-enter, cubic-bezier(0.23, 1, 0.32, 1));\n}\n\n.wui-floating-panel[data-wui-presence='entering'],\n.wui-floating-panel[data-wui-presence='closing'] {\n transform: scale(var(--wui-scale-enter, 0.97));\n opacity: 0;\n}\n\n.wui-floating-panel[data-wui-presence='closing'] {\n pointer-events: none;\n transition-duration: var(--wui-internal-duration-overlay-exit, var(--wui-duration-overlay-exit, 140ms));\n}\n\n@media (prefers-reduced-motion: reduce) {\n .wui-floating-panel,\n .wui-floating-panel[data-wui-presence='entering'],\n .wui-floating-panel[data-wui-presence='closing'] {\n transform: none;\n transition-duration: 120ms;\n }\n}\n"],"mappings":""}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
//#region src/assets/toast-containers.css?inline
|
|
2
|
-
var e = ".wui-toast-container{pointer-events:none;z-index:var(--wui-layer-toast,200);overscroll-behavior:contain;flex-direction:column;gap:8px;
|
|
2
|
+
var e = ".wui-toast-container{--wui-toast-viewport-gap:16px;--wui-toast-container-padding:40px;pointer-events:none;z-index:var(--wui-layer-toast,200);overscroll-behavior:contain;max-height:calc(100vh + 2 * (var(--wui-toast-container-padding) - var(--wui-toast-viewport-gap)));padding:var(--wui-toast-container-padding);flex-direction:column;gap:8px;display:flex;position:fixed;overflow-y:auto}.wui-toast-container>*{pointer-events:auto}.wui-toast-top-left{top:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));left:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));align-items:flex-start}.wui-toast-top-center{top:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));align-items:center;left:50%;transform:translate(-50%)}.wui-toast-top-right{top:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));right:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));align-items:flex-end}.wui-toast-bottom-left{bottom:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));left:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));flex-direction:column-reverse;align-items:flex-start}.wui-toast-bottom-center{bottom:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));flex-direction:column-reverse;align-items:center;left:50%;transform:translate(-50%)}.wui-toast-bottom-right{right:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));bottom:calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));flex-direction:column-reverse;align-items:flex-end}";
|
|
3
3
|
//#endregion
|
|
4
4
|
export { e as default };
|
|
5
5
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"toast-containers.js","names":[],"sources":["../../src/assets/toast-containers.css?inline"],"sourcesContent":["/* Toast 容器定位 — 由 toast 命令式 API 动态注入到 body */\n\n.wui-toast-container {\n pointer-events: none;\n\n position: fixed;\n z-index: var(--wui-layer-toast, 200);\n\n overflow-y: auto;\n overscroll-behavior: contain;\n display: flex;\n flex-direction: column;\n gap: 8px;\n\n max-height: 100vh;\n\n /* padding 需要 >=
|
|
1
|
+
{"version":3,"file":"toast-containers.js","names":[],"sources":["../../src/assets/toast-containers.css?inline"],"sourcesContent":["/* Toast 容器定位 — 由 toast 命令式 API 动态注入到 body */\n\n.wui-toast-container {\n --wui-toast-viewport-gap: 16px;\n --wui-toast-container-padding: 40px;\n pointer-events: none;\n\n position: fixed;\n z-index: var(--wui-layer-toast, 200);\n\n overflow-y: auto;\n overscroll-behavior: contain;\n display: flex;\n flex-direction: column;\n gap: 8px;\n\n /* 负向定位只露出可见 gap;剩余 padding 继续作为阴影裁剪缓冲区 */\n max-height: calc(100vh + 2 * (var(--wui-toast-container-padding) - var(--wui-toast-viewport-gap)));\n\n /* padding 需要 >= 阴影偏移 + 模糊半径,否则 overflow 会裁剪子元素 box-shadow */\n padding: var(--wui-toast-container-padding);\n}\n\n.wui-toast-container > * {\n pointer-events: auto;\n}\n\n/* ===== 顶部位置 ===== */\n\n.wui-toast-top-left {\n top: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n left: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n align-items: flex-start;\n}\n\n.wui-toast-top-center {\n top: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n left: 50%;\n transform: translateX(-50%);\n align-items: center;\n}\n\n.wui-toast-top-right {\n top: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n right: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n align-items: flex-end;\n}\n\n/* ===== 底部位置 ===== */\n\n.wui-toast-bottom-left {\n bottom: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n left: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n flex-direction: column-reverse;\n align-items: flex-start;\n}\n\n.wui-toast-bottom-center {\n bottom: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n left: 50%;\n transform: translateX(-50%);\n\n flex-direction: column-reverse;\n align-items: center;\n}\n\n.wui-toast-bottom-right {\n right: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n bottom: calc(var(--wui-toast-viewport-gap) - var(--wui-toast-container-padding));\n flex-direction: column-reverse;\n align-items: flex-end;\n}\n"],"mappings":""}
|