@chromvoid/uikit 0.1.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/LICENSE +8 -0
- package/README.md +96 -0
- package/dist/components/cv-accordion-item.d.ts +69 -0
- package/dist/components/cv-accordion-item.js +176 -0
- package/dist/components/cv-accordion.d.ts +79 -0
- package/dist/components/cv-accordion.js +310 -0
- package/dist/components/cv-alert-dialog.d.ts +86 -0
- package/dist/components/cv-alert-dialog.js +393 -0
- package/dist/components/cv-alert.d.ts +48 -0
- package/dist/components/cv-alert.js +156 -0
- package/dist/components/cv-badge.d.ts +56 -0
- package/dist/components/cv-badge.js +280 -0
- package/dist/components/cv-breadcrumb-item.d.ts +35 -0
- package/dist/components/cv-breadcrumb-item.js +64 -0
- package/dist/components/cv-breadcrumb.d.ts +39 -0
- package/dist/components/cv-breadcrumb.js +160 -0
- package/dist/components/cv-button.d.ts +83 -0
- package/dist/components/cv-button.js +541 -0
- package/dist/components/cv-callout.d.ts +32 -0
- package/dist/components/cv-callout.js +221 -0
- package/dist/components/cv-card.d.ts +48 -0
- package/dist/components/cv-card.js +269 -0
- package/dist/components/cv-carousel-slide.d.ts +25 -0
- package/dist/components/cv-carousel-slide.js +51 -0
- package/dist/components/cv-carousel.d.ts +96 -0
- package/dist/components/cv-carousel.js +457 -0
- package/dist/components/cv-checkbox.d.ts +84 -0
- package/dist/components/cv-checkbox.js +274 -0
- package/dist/components/cv-combobox-group.d.ts +15 -0
- package/dist/components/cv-combobox-group.js +34 -0
- package/dist/components/cv-combobox-option.d.ts +30 -0
- package/dist/components/cv-combobox-option.js +66 -0
- package/dist/components/cv-combobox.d.ts +135 -0
- package/dist/components/cv-combobox.js +834 -0
- package/dist/components/cv-command-item.d.ts +30 -0
- package/dist/components/cv-command-item.js +68 -0
- package/dist/components/cv-command-palette.d.ts +105 -0
- package/dist/components/cv-command-palette.js +578 -0
- package/dist/components/cv-context-menu.d.ts +98 -0
- package/dist/components/cv-context-menu.js +515 -0
- package/dist/components/cv-copy-button.d.ts +61 -0
- package/dist/components/cv-copy-button.js +318 -0
- package/dist/components/cv-date-picker.d.ts +161 -0
- package/dist/components/cv-date-picker.js +803 -0
- package/dist/components/cv-dialog.d.ts +89 -0
- package/dist/components/cv-dialog.js +459 -0
- package/dist/components/cv-disclosure.d.ts +57 -0
- package/dist/components/cv-disclosure.js +241 -0
- package/dist/components/cv-drawer.d.ts +102 -0
- package/dist/components/cv-drawer.js +595 -0
- package/dist/components/cv-feed-article.d.ts +26 -0
- package/dist/components/cv-feed-article.js +52 -0
- package/dist/components/cv-feed.d.ts +62 -0
- package/dist/components/cv-feed.js +310 -0
- package/dist/components/cv-grid-cell.d.ts +30 -0
- package/dist/components/cv-grid-cell.js +57 -0
- package/dist/components/cv-grid-column.d.ts +30 -0
- package/dist/components/cv-grid-column.js +43 -0
- package/dist/components/cv-grid-row.d.ts +30 -0
- package/dist/components/cv-grid-row.js +42 -0
- package/dist/components/cv-grid.d.ts +119 -0
- package/dist/components/cv-grid.js +567 -0
- package/dist/components/cv-icon.d.ts +57 -0
- package/dist/components/cv-icon.js +352 -0
- package/dist/components/cv-input.d.ts +127 -0
- package/dist/components/cv-input.js +482 -0
- package/dist/components/cv-landmark.d.ts +32 -0
- package/dist/components/cv-landmark.js +62 -0
- package/dist/components/cv-link.d.ts +22 -0
- package/dist/components/cv-link.js +99 -0
- package/dist/components/cv-listbox-group.d.ts +15 -0
- package/dist/components/cv-listbox-group.js +42 -0
- package/dist/components/cv-listbox.d.ts +81 -0
- package/dist/components/cv-listbox.js +388 -0
- package/dist/components/cv-menu-button.d.ts +118 -0
- package/dist/components/cv-menu-button.js +822 -0
- package/dist/components/cv-menu-group.d.ts +20 -0
- package/dist/components/cv-menu-group.js +48 -0
- package/dist/components/cv-menu-item.d.ts +52 -0
- package/dist/components/cv-menu-item.js +105 -0
- package/dist/components/cv-menu.d.ts +62 -0
- package/dist/components/cv-menu.js +414 -0
- package/dist/components/cv-meter.d.ts +66 -0
- package/dist/components/cv-meter.js +154 -0
- package/dist/components/cv-number.d.ts +139 -0
- package/dist/components/cv-number.js +553 -0
- package/dist/components/cv-option.d.ts +30 -0
- package/dist/components/cv-option.js +84 -0
- package/dist/components/cv-popover.d.ts +87 -0
- package/dist/components/cv-popover.js +373 -0
- package/dist/components/cv-progress-ring.d.ts +45 -0
- package/dist/components/cv-progress-ring.js +169 -0
- package/dist/components/cv-progress.d.ts +45 -0
- package/dist/components/cv-progress.js +148 -0
- package/dist/components/cv-radio-group.d.ts +79 -0
- package/dist/components/cv-radio-group.js +398 -0
- package/dist/components/cv-radio.d.ts +36 -0
- package/dist/components/cv-radio.js +123 -0
- package/dist/components/cv-select-group.d.ts +15 -0
- package/dist/components/cv-select-group.js +44 -0
- package/dist/components/cv-select-option.d.ts +30 -0
- package/dist/components/cv-select-option.js +66 -0
- package/dist/components/cv-select.d.ts +128 -0
- package/dist/components/cv-select.js +666 -0
- package/dist/components/cv-sidebar-item.d.ts +26 -0
- package/dist/components/cv-sidebar-item.js +142 -0
- package/dist/components/cv-sidebar.d.ts +171 -0
- package/dist/components/cv-sidebar.js +767 -0
- package/dist/components/cv-slider-multi-thumb.d.ts +73 -0
- package/dist/components/cv-slider-multi-thumb.js +374 -0
- package/dist/components/cv-slider.d.ts +84 -0
- package/dist/components/cv-slider.js +328 -0
- package/dist/components/cv-spinbutton.d.ts +121 -0
- package/dist/components/cv-spinbutton.js +486 -0
- package/dist/components/cv-spinner.d.ts +18 -0
- package/dist/components/cv-spinner.js +95 -0
- package/dist/components/cv-switch.d.ts +81 -0
- package/dist/components/cv-switch.js +285 -0
- package/dist/components/cv-tab-panel.d.ts +20 -0
- package/dist/components/cv-tab-panel.js +37 -0
- package/dist/components/cv-tab.d.ts +40 -0
- package/dist/components/cv-tab.js +132 -0
- package/dist/components/cv-table-cell.d.ts +31 -0
- package/dist/components/cv-table-cell.js +49 -0
- package/dist/components/cv-table-column.d.ts +37 -0
- package/dist/components/cv-table-column.js +63 -0
- package/dist/components/cv-table-row.d.ts +30 -0
- package/dist/components/cv-table-row.js +45 -0
- package/dist/components/cv-table.d.ts +147 -0
- package/dist/components/cv-table.js +607 -0
- package/dist/components/cv-tabs.d.ts +70 -0
- package/dist/components/cv-tabs.js +524 -0
- package/dist/components/cv-textarea.d.ts +108 -0
- package/dist/components/cv-textarea.js +328 -0
- package/dist/components/cv-toast-region.d.ts +39 -0
- package/dist/components/cv-toast-region.js +162 -0
- package/dist/components/cv-toast.d.ts +67 -0
- package/dist/components/cv-toast.js +315 -0
- package/dist/components/cv-toolbar-item.d.ts +25 -0
- package/dist/components/cv-toolbar-item.js +72 -0
- package/dist/components/cv-toolbar-separator.d.ts +25 -0
- package/dist/components/cv-toolbar-separator.js +45 -0
- package/dist/components/cv-toolbar.d.ts +63 -0
- package/dist/components/cv-toolbar.js +295 -0
- package/dist/components/cv-tooltip.d.ts +83 -0
- package/dist/components/cv-tooltip.js +455 -0
- package/dist/components/cv-treegrid-cell.d.ts +30 -0
- package/dist/components/cv-treegrid-cell.js +57 -0
- package/dist/components/cv-treegrid-column.d.ts +37 -0
- package/dist/components/cv-treegrid-column.js +53 -0
- package/dist/components/cv-treegrid-row.d.ts +55 -0
- package/dist/components/cv-treegrid-row.js +90 -0
- package/dist/components/cv-treegrid.d.ts +96 -0
- package/dist/components/cv-treegrid.js +632 -0
- package/dist/components/cv-treeitem.d.ts +58 -0
- package/dist/components/cv-treeitem.js +144 -0
- package/dist/components/cv-treeview.d.ts +70 -0
- package/dist/components/cv-treeview.js +396 -0
- package/dist/components/cv-window-splitter.d.ts +79 -0
- package/dist/components/cv-window-splitter.js +316 -0
- package/dist/components/index.d.ts +94 -0
- package/dist/components/index.js +79 -0
- package/dist/dialog/create-dialog-controller.d.ts +31 -0
- package/dist/dialog/create-dialog-controller.js +320 -0
- package/dist/dialog/index.d.ts +2 -0
- package/dist/dialog/index.js +1 -0
- package/dist/form-associated/FormAssociatedReatomElement.d.ts +25 -0
- package/dist/form-associated/FormAssociatedReatomElement.js +70 -0
- package/dist/form-associated/withFormAssociated.d.ts +5 -0
- package/dist/form-associated/withFormAssociated.js +1 -0
- package/dist/index.d.ts +10 -0
- package/dist/index.js +9 -0
- package/dist/reatom-lit/ReatomLitElement.d.ts +27 -0
- package/dist/reatom-lit/ReatomLitElement.js +118 -0
- package/dist/reatom-lit/html.d.ts +4 -0
- package/dist/reatom-lit/html.js +10 -0
- package/dist/reatom-lit/index.d.ts +4 -0
- package/dist/reatom-lit/index.js +4 -0
- package/dist/reatom-lit/watch.d.ts +15 -0
- package/dist/reatom-lit/watch.js +40 -0
- package/dist/reatom-lit/withReatomElement.d.ts +4 -0
- package/dist/reatom-lit/withReatomElement.js +57 -0
- package/dist/register.d.ts +1 -0
- package/dist/register.js +84 -0
- package/dist/styles/component-styles.d.ts +4 -0
- package/dist/styles/component-styles.js +78 -0
- package/dist/theme/cv-theme-provider.d.ts +32 -0
- package/dist/theme/cv-theme-provider.js +110 -0
- package/dist/theme/index.d.ts +4 -0
- package/dist/theme/index.js +2 -0
- package/dist/theme/theme-engine.d.ts +4 -0
- package/dist/theme/theme-engine.js +67 -0
- package/dist/theme/tokens.css +265 -0
- package/dist/theme/types.d.ts +7 -0
- package/dist/theme/types.js +1 -0
- package/dist/toast/create-toast-controller.d.ts +12 -0
- package/dist/toast/create-toast-controller.js +12 -0
- package/dist/toast/index.d.ts +2 -0
- package/dist/toast/index.js +1 -0
- package/package.json +146 -0
- package/specs/_template.md +110 -0
- package/specs/components/accordion.md +207 -0
- package/specs/components/alert.md +83 -0
- package/specs/components/badge.md +183 -0
- package/specs/components/breadcrumb.md +152 -0
- package/specs/components/button.md +227 -0
- package/specs/components/callout.md +153 -0
- package/specs/components/card.md +192 -0
- package/specs/components/carousel.md +232 -0
- package/specs/components/checkbox.md +141 -0
- package/specs/components/combobox.md +427 -0
- package/specs/components/context-menu.md +375 -0
- package/specs/components/copy-button.md +236 -0
- package/specs/components/date-picker.md +290 -0
- package/specs/components/dialog.md +184 -0
- package/specs/components/disclosure.md +151 -0
- package/specs/components/drawer.md +216 -0
- package/specs/components/feed.md +266 -0
- package/specs/components/grid.md +423 -0
- package/specs/components/input.md +237 -0
- package/specs/components/landmark.md +92 -0
- package/specs/components/link.md +117 -0
- package/specs/components/listbox.md +327 -0
- package/specs/components/menu.md +508 -0
- package/specs/components/meter.md +148 -0
- package/specs/components/number.md +268 -0
- package/specs/components/option.md +167 -0
- package/specs/components/popover.md +207 -0
- package/specs/components/progress-ring.md +134 -0
- package/specs/components/progress.md +110 -0
- package/specs/components/radio.md +208 -0
- package/specs/components/select.md +305 -0
- package/specs/components/sidebar.md +204 -0
- package/specs/components/spinbutton.md +157 -0
- package/specs/components/spinner.md +83 -0
- package/specs/components/switch.md +145 -0
- package/specs/components/table.md +372 -0
- package/specs/components/tabs.md +242 -0
- package/specs/components/textarea.md +166 -0
- package/specs/components/theme.md +364 -0
- package/specs/components/toast.md +198 -0
- package/specs/components/toolbar.md +258 -0
- package/specs/components/tooltip.md +152 -0
- package/specs/components/treegrid.md +363 -0
- package/specs/components/treeview.md +263 -0
- package/specs/components/window-splitter.md +225 -0
|
@@ -0,0 +1,237 @@
|
|
|
1
|
+
# cv-input
|
|
2
|
+
|
|
3
|
+
Single-line text input control supporting text-like types, clearable behavior, and password visibility toggling.
|
|
4
|
+
|
|
5
|
+
**Headless:** [`createInput`](https://github.com/chromvoid/headless-ui/blob/main/specs/components/input.md)
|
|
6
|
+
|
|
7
|
+
## Anatomy
|
|
8
|
+
|
|
9
|
+
```
|
|
10
|
+
<cv-input> (host)
|
|
11
|
+
├── <span part="form-control-label">
|
|
12
|
+
│ └── <slot name="label">
|
|
13
|
+
├── <div part="base">
|
|
14
|
+
│ ├── <span part="prefix">
|
|
15
|
+
│ │ └── <slot name="prefix">
|
|
16
|
+
│ ├── <input part="input" />
|
|
17
|
+
│ ├── <span part="clear-button">
|
|
18
|
+
│ │ └── <slot name="clear-icon">×</slot>
|
|
19
|
+
│ ├── <span part="password-toggle">
|
|
20
|
+
│ │ └── <slot name="show-password-icon|hide-password-icon">
|
|
21
|
+
│ └── <span part="suffix">
|
|
22
|
+
│ └── <slot name="suffix">
|
|
23
|
+
└── <span part="form-control-help-text">
|
|
24
|
+
└── <slot name="help-text">
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
## Attributes
|
|
28
|
+
|
|
29
|
+
| Attribute | Type | Default | Reflects | Description |
|
|
30
|
+
| ----------------- | ----------- | ------------ | -------- | -------------------------------------------------------------------------- |
|
|
31
|
+
| `value` | String | `""` | no | Current input value |
|
|
32
|
+
| `type` | `InputType` | `"text"` | no | Input type: `text` \| `password` \| `email` \| `url` \| `tel` \| `search` |
|
|
33
|
+
| `placeholder` | String | `""` | no | Placeholder text displayed when the input is empty |
|
|
34
|
+
| `disabled` | Boolean | `false` | yes | Prevents interaction and dims the component |
|
|
35
|
+
| `readonly` | Boolean | `false` | yes | Prevents editing while keeping the input focusable |
|
|
36
|
+
| `required` | Boolean | `false` | yes | Marks the input as required for form validation |
|
|
37
|
+
| `clearable` | Boolean | `false` | yes | Shows a clear button when the input has a value |
|
|
38
|
+
| `password-toggle` | Boolean | `false` | yes | Shows a password visibility toggle (only effective when `type="password"`) |
|
|
39
|
+
| `size` | String | `"medium"` | yes | Component size: `small` \| `medium` \| `large` |
|
|
40
|
+
| `variant` | String | `"outlined"` | yes | Visual variant: `outlined` \| `filled` |
|
|
41
|
+
| `name` | String | `""` | no | Name for form association |
|
|
42
|
+
|
|
43
|
+
## Variants
|
|
44
|
+
|
|
45
|
+
| Variant | Description |
|
|
46
|
+
| ---------- | ------------------------------------------------------------ |
|
|
47
|
+
| `outlined` | Default style with visible border and transparent background |
|
|
48
|
+
| `filled` | Subtle background fill with no visible border |
|
|
49
|
+
|
|
50
|
+
## Sizes
|
|
51
|
+
|
|
52
|
+
| Size | `--cv-input-height` | `--cv-input-padding-inline` | `--cv-input-font-size` |
|
|
53
|
+
| -------- | ------------------- | --------------------------- | -------------------------------- |
|
|
54
|
+
| `small` | `30px` | `var(--cv-space-2, 8px)` | `var(--cv-font-size-sm, 13px)` |
|
|
55
|
+
| `medium` | `36px` | `var(--cv-space-3, 12px)` | `var(--cv-font-size-base, 14px)` |
|
|
56
|
+
| `large` | `42px` | `var(--cv-space-4, 16px)` | `var(--cv-font-size-md, 16px)` |
|
|
57
|
+
|
|
58
|
+
## Slots
|
|
59
|
+
|
|
60
|
+
| Slot | Description |
|
|
61
|
+
| -------------------- | -------------------------------------------------- |
|
|
62
|
+
| `prefix` | Content rendered before the input (e.g., icon) |
|
|
63
|
+
| `suffix` | Content rendered after the input (e.g., icon) |
|
|
64
|
+
| `clear-icon` | Custom icon for the clear button (default: `×`) |
|
|
65
|
+
| `show-password-icon` | Custom icon for the "show password" state |
|
|
66
|
+
| `hide-password-icon` | Custom icon for the "hide password" state |
|
|
67
|
+
| `label` | Label text displayed above or beside the input |
|
|
68
|
+
| `help-text` | Help or description text displayed below the input |
|
|
69
|
+
|
|
70
|
+
> **Note:** The native `<input>` element is not slottable. There is no default slot.
|
|
71
|
+
|
|
72
|
+
## CSS Parts
|
|
73
|
+
|
|
74
|
+
| Part | Element | Description |
|
|
75
|
+
| ------------------------ | --------- | ----------------------------------- |
|
|
76
|
+
| `base` | `<div>` | Outermost wrapper element |
|
|
77
|
+
| `input` | `<input>` | The native input element |
|
|
78
|
+
| `prefix` | `<span>` | Wrapper around the `prefix` slot |
|
|
79
|
+
| `suffix` | `<span>` | Wrapper around the `suffix` slot |
|
|
80
|
+
| `clear-button` | `<span>` | The clear button wrapper |
|
|
81
|
+
| `password-toggle` | `<span>` | The password toggle button wrapper |
|
|
82
|
+
| `form-control-label` | `<span>` | Wrapper around the `label` slot |
|
|
83
|
+
| `form-control-help-text` | `<span>` | Wrapper around the `help-text` slot |
|
|
84
|
+
|
|
85
|
+
## CSS Custom Properties
|
|
86
|
+
|
|
87
|
+
| Property | Default | Description |
|
|
88
|
+
| -------------------------------- | -------------------------------------------- | --------------------------------------------------------------- |
|
|
89
|
+
| `--cv-input-height` | `36px` | Component block size |
|
|
90
|
+
| `--cv-input-padding-inline` | `var(--cv-space-3, 12px)` | Horizontal padding inside the input |
|
|
91
|
+
| `--cv-input-font-size` | `var(--cv-font-size-base, 14px)` | Font size of the input text |
|
|
92
|
+
| `--cv-input-border-radius` | `var(--cv-radius-sm, 6px)` | Border radius of the input container |
|
|
93
|
+
| `--cv-input-border-color` | `var(--cv-color-border, #2a3245)` | Border color in default state |
|
|
94
|
+
| `--cv-input-background` | `transparent` | Background color of the input container |
|
|
95
|
+
| `--cv-input-color` | `var(--cv-color-text, #e8ecf6)` | Text color of the input value |
|
|
96
|
+
| `--cv-input-placeholder-color` | `var(--cv-color-text-muted, #6b7a99)` | Placeholder text color |
|
|
97
|
+
| `--cv-input-focus-ring` | `0 0 0 2px var(--cv-color-primary, #65d7ff)` | Box-shadow applied on focus |
|
|
98
|
+
| `--cv-input-icon-size` | `1em` | Size of prefix/suffix/clear/toggle icons |
|
|
99
|
+
| `--cv-input-gap` | `var(--cv-space-2, 8px)` | Spacing between inner elements (prefix, input, suffix, buttons) |
|
|
100
|
+
| `--cv-input-transition-duration` | `var(--cv-duration-fast, 120ms)` | Transition duration for state changes |
|
|
101
|
+
|
|
102
|
+
Additionally, component styles depend on theme tokens through fallback values:
|
|
103
|
+
|
|
104
|
+
| Theme Property | Default | Description |
|
|
105
|
+
| ----------------------- | --------- | --------------------------------------------------- |
|
|
106
|
+
| `--cv-color-border` | `#2a3245` | Base border color |
|
|
107
|
+
| `--cv-color-surface` | `#141923` | Surface background color (used by `filled` variant) |
|
|
108
|
+
| `--cv-color-text` | `#e8ecf6` | Default text color |
|
|
109
|
+
| `--cv-color-text-muted` | `#6b7a99` | Muted text color for placeholder |
|
|
110
|
+
| `--cv-color-primary` | `#65d7ff` | Primary accent color for focus ring |
|
|
111
|
+
| `--cv-duration-fast` | `120ms` | Transition duration |
|
|
112
|
+
| `--cv-easing-standard` | `ease` | Transition timing function |
|
|
113
|
+
| `--cv-radius-sm` | `6px` | Base border radius fallback |
|
|
114
|
+
| `--cv-font-size-sm` | `13px` | Small font size |
|
|
115
|
+
| `--cv-font-size-base` | `14px` | Base font size |
|
|
116
|
+
| `--cv-font-size-md` | `16px` | Medium font size |
|
|
117
|
+
| `--cv-space-2` | `8px` | Spacing scale: small |
|
|
118
|
+
| `--cv-space-3` | `12px` | Spacing scale: medium |
|
|
119
|
+
| `--cv-space-4` | `16px` | Spacing scale: large |
|
|
120
|
+
|
|
121
|
+
## Visual States
|
|
122
|
+
|
|
123
|
+
| Host selector | Description |
|
|
124
|
+
| ----------------------------- | ---------------------------------------------------------------- |
|
|
125
|
+
| `:host([disabled])` | Reduced opacity (`0.55`), `cursor: not-allowed`, no interaction |
|
|
126
|
+
| `:host([readonly])` | Normal opacity, `cursor: default`, input text not editable |
|
|
127
|
+
| `:host([required])` | No visual change by default (can be styled via part selectors) |
|
|
128
|
+
| `:host([focused])` | Focus ring applied via `--cv-input-focus-ring` |
|
|
129
|
+
| `:host([filled])` | Indicates non-empty value (e.g., for floating label transitions) |
|
|
130
|
+
| `:host([clearable])` | Clear button space reserved in layout |
|
|
131
|
+
| `:host([password-toggle])` | Password toggle button space reserved in layout |
|
|
132
|
+
| `:host([size="small"])` | Small size overrides |
|
|
133
|
+
| `:host([size="large"])` | Large size overrides |
|
|
134
|
+
| `:host([variant="outlined"])` | Visible border, transparent background |
|
|
135
|
+
| `:host([variant="filled"])` | Subtle background (`--cv-color-surface`), no visible border |
|
|
136
|
+
|
|
137
|
+
## Reactive State Mapping
|
|
138
|
+
|
|
139
|
+
`cv-input` is a visual adapter over headless `createInput`.
|
|
140
|
+
|
|
141
|
+
### UIKit properties to headless actions
|
|
142
|
+
|
|
143
|
+
| UIKit Property | Direction | Headless Binding |
|
|
144
|
+
| ----------------- | ------------------- | ---------------------------------- |
|
|
145
|
+
| `value` | attr/prop -> action | `actions.setValue(value)` |
|
|
146
|
+
| `type` | attr -> action | `actions.setType(type)` |
|
|
147
|
+
| `disabled` | attr -> action | `actions.setDisabled(value)` |
|
|
148
|
+
| `readonly` | attr -> action | `actions.setReadonly(value)` |
|
|
149
|
+
| `required` | attr -> action | `actions.setRequired(value)` |
|
|
150
|
+
| `placeholder` | attr -> action | `actions.setPlaceholder(value)` |
|
|
151
|
+
| `clearable` | attr -> action | `actions.setClearable(value)` |
|
|
152
|
+
| `password-toggle` | attr -> action | `actions.setPasswordToggle(value)` |
|
|
153
|
+
|
|
154
|
+
### Headless state to DOM reflection
|
|
155
|
+
|
|
156
|
+
| Headless State | Direction | DOM Reflection |
|
|
157
|
+
| ---------------------------- | ------------- | ----------------------------------------------------------------- |
|
|
158
|
+
| `state.disabled()` | state -> attr | `[disabled]` host attribute |
|
|
159
|
+
| `state.readonly()` | state -> attr | `[readonly]` host attribute |
|
|
160
|
+
| `state.required()` | state -> attr | `[required]` host attribute |
|
|
161
|
+
| `state.focused()` | state -> attr | `[focused]` host attribute |
|
|
162
|
+
| `state.filled()` | state -> attr | `[filled]` host attribute |
|
|
163
|
+
| `state.passwordVisible()` | state -> DOM | toggles between `show-password-icon` / `hide-password-icon` slots |
|
|
164
|
+
| `state.showClearButton()` | state -> DOM | shows/hides the clear button element |
|
|
165
|
+
| `state.showPasswordToggle()` | state -> DOM | shows/hides the password toggle element |
|
|
166
|
+
| `state.resolvedType()` | state -> DOM | applied as `type` attribute on the native `<input>` |
|
|
167
|
+
|
|
168
|
+
### Contract props spreading
|
|
169
|
+
|
|
170
|
+
- `contracts.getInputProps()` is spread onto the `[part="input"]` native `<input>` element to apply `id`, `type`, `aria-disabled`, `aria-readonly`, `aria-required`, `placeholder`, `disabled`, `readonly`, `tabindex`, and `autocomplete`.
|
|
171
|
+
- `contracts.getClearButtonProps()` is spread onto the `[part="clear-button"]` element to apply `role`, `aria-label`, `tabindex`, `hidden`, and `aria-hidden`.
|
|
172
|
+
- `contracts.getPasswordToggleProps()` is spread onto the `[part="password-toggle"]` element to apply `role`, `aria-label`, `aria-pressed`, `tabindex`, `hidden`, and `aria-hidden`.
|
|
173
|
+
|
|
174
|
+
### Event wiring
|
|
175
|
+
|
|
176
|
+
- Native `<input>` `input` event -> `actions.handleInput(e.target.value)` -> dispatches `cv-input` CustomEvent
|
|
177
|
+
- Native `<input>` `keydown` event -> `actions.handleKeyDown(e)` -> may trigger `actions.clear()` -> dispatches `cv-clear` CustomEvent
|
|
178
|
+
- Native `<input>` `focus` event -> `actions.setFocused(true)` -> dispatches `cv-focus` CustomEvent
|
|
179
|
+
- Native `<input>` `blur` event -> `actions.setFocused(false)` -> dispatches `cv-blur` CustomEvent; if value changed since focus, dispatches `cv-change` CustomEvent
|
|
180
|
+
- Clear button `click` -> `actions.clear()` -> dispatches `cv-clear` CustomEvent
|
|
181
|
+
- Password toggle `click` -> `actions.togglePasswordVisibility()`
|
|
182
|
+
|
|
183
|
+
UIKit does not own value management, type resolution, clearable logic, or password toggle logic; headless state is the source of truth.
|
|
184
|
+
|
|
185
|
+
## Events
|
|
186
|
+
|
|
187
|
+
| Event | Detail | Description |
|
|
188
|
+
| ----------- | ------------------- | -------------------------------------------------------------------------------------------------- |
|
|
189
|
+
| `cv-input` | `{ value: string }` | Fires on value change from user interaction (native input event), not from programmatic `setValue` |
|
|
190
|
+
| `cv-change` | `{ value: string }` | Fires on value commit (blur after the value changed since focus) |
|
|
191
|
+
| `cv-clear` | `{ }` | Fires when the value is cleared via the clear button or `Escape` key |
|
|
192
|
+
| `cv-focus` | `{ }` | Fires when the input receives focus |
|
|
193
|
+
| `cv-blur` | `{ }` | Fires when the input loses focus |
|
|
194
|
+
|
|
195
|
+
## Usage
|
|
196
|
+
|
|
197
|
+
```html
|
|
198
|
+
<!-- Basic text input -->
|
|
199
|
+
<cv-input placeholder="Enter text"></cv-input>
|
|
200
|
+
|
|
201
|
+
<!-- With label and help text -->
|
|
202
|
+
<cv-input>
|
|
203
|
+
<span slot="label">Username</span>
|
|
204
|
+
<span slot="help-text">Enter your username</span>
|
|
205
|
+
</cv-input>
|
|
206
|
+
|
|
207
|
+
<!-- Clearable -->
|
|
208
|
+
<cv-input clearable value="Hello world"></cv-input>
|
|
209
|
+
|
|
210
|
+
<!-- Password with toggle -->
|
|
211
|
+
<cv-input type="password" password-toggle placeholder="Password"></cv-input>
|
|
212
|
+
|
|
213
|
+
<!-- Filled variant, small size -->
|
|
214
|
+
<cv-input variant="filled" size="small" placeholder="Search..."></cv-input>
|
|
215
|
+
|
|
216
|
+
<!-- With prefix and suffix icons -->
|
|
217
|
+
<cv-input>
|
|
218
|
+
<icon-search slot="prefix"></icon-search>
|
|
219
|
+
<icon-arrow slot="suffix"></icon-arrow>
|
|
220
|
+
</cv-input>
|
|
221
|
+
|
|
222
|
+
<!-- Disabled -->
|
|
223
|
+
<cv-input disabled value="Cannot edit"></cv-input>
|
|
224
|
+
|
|
225
|
+
<!-- Readonly -->
|
|
226
|
+
<cv-input readonly value="Read only value"></cv-input>
|
|
227
|
+
|
|
228
|
+
<!-- Email type, required -->
|
|
229
|
+
<cv-input type="email" required placeholder="Email address">
|
|
230
|
+
<span slot="label">Email</span>
|
|
231
|
+
</cv-input>
|
|
232
|
+
|
|
233
|
+
<!-- Large size, outlined variant with custom clear icon -->
|
|
234
|
+
<cv-input size="large" clearable>
|
|
235
|
+
<icon-x slot="clear-icon"></icon-x>
|
|
236
|
+
</cv-input>
|
|
237
|
+
```
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
# cv-landmark
|
|
2
|
+
|
|
3
|
+
Semantic wrapper that identifies a page region as an ARIA landmark for assistive technology navigation.
|
|
4
|
+
|
|
5
|
+
**Headless:** [`createLandmark`](https://github.com/chromvoid/headless-ui/blob/main/specs/components/landmarks.md)
|
|
6
|
+
|
|
7
|
+
## Anatomy
|
|
8
|
+
|
|
9
|
+
```
|
|
10
|
+
<cv-landmark> (host)
|
|
11
|
+
└── <section part="base" role="…">
|
|
12
|
+
└── <slot>
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
## Attributes
|
|
16
|
+
|
|
17
|
+
| Attribute | Type | Default | Description |
|
|
18
|
+
| ---------- | ------ | ---------- | ----------------------------------------------------------------------------------------------------------------------- |
|
|
19
|
+
| `type` | String | `"region"` | Landmark role: `banner` \| `main` \| `navigation` \| `complementary` \| `contentinfo` \| `search` \| `form` \| `region` |
|
|
20
|
+
| `label` | String | `""` | Accessible label applied via `aria-label` |
|
|
21
|
+
| `label-id` | String | `""` | ID of the external labelling element, applied via `aria-labelledby` (takes precedence over `label`) |
|
|
22
|
+
|
|
23
|
+
## Slots
|
|
24
|
+
|
|
25
|
+
| Slot | Description |
|
|
26
|
+
| ----------- | ---------------- |
|
|
27
|
+
| `(default)` | Landmark content |
|
|
28
|
+
|
|
29
|
+
## CSS Parts
|
|
30
|
+
|
|
31
|
+
| Part | Element | Description |
|
|
32
|
+
| ------ | ----------- | ------------------------------------ |
|
|
33
|
+
| `base` | `<section>` | Root landmark element with ARIA role |
|
|
34
|
+
|
|
35
|
+
## CSS Custom Properties
|
|
36
|
+
|
|
37
|
+
None. `cv-landmark` is a pure semantic wrapper with `display: block` only.
|
|
38
|
+
|
|
39
|
+
## Visual States
|
|
40
|
+
|
|
41
|
+
| Host selector | Description |
|
|
42
|
+
| ------------- | ---------------------------------------------- |
|
|
43
|
+
| `:host` | `display: block`; no additional visual styling |
|
|
44
|
+
|
|
45
|
+
## Events
|
|
46
|
+
|
|
47
|
+
None. Landmark has no user-driven interactions.
|
|
48
|
+
|
|
49
|
+
## Reactive State Mapping
|
|
50
|
+
|
|
51
|
+
`cv-landmark` is a visual adapter over headless `createLandmark`.
|
|
52
|
+
|
|
53
|
+
| UIKit Property | Direction | Headless Binding |
|
|
54
|
+
| -------------- | ------------- | ------------------------------------------------ |
|
|
55
|
+
| `type` | attr → option | passed as `type` in `createLandmark(options)` |
|
|
56
|
+
| `label` | attr → option | passed as `label` in `createLandmark(options)` |
|
|
57
|
+
| `label-id` | attr → option | passed as `labelId` in `createLandmark(options)` |
|
|
58
|
+
|
|
59
|
+
| Headless State | Direction | DOM Reflection |
|
|
60
|
+
| ----------------- | ------------ | --------------------------- |
|
|
61
|
+
| `state.type()` | state → attr | `[type]` host attribute |
|
|
62
|
+
| `state.label()` | state → attr | `[label]` host attribute |
|
|
63
|
+
| `state.labelId()` | state → attr | `[label-id]` host attribute |
|
|
64
|
+
|
|
65
|
+
- `contracts.getLandmarkProps()` is spread onto the inner `[part="base"]` element to apply `role`, `aria-label`, and `aria-labelledby`.
|
|
66
|
+
- When any of `type`, `label`, or `label-id` attributes change, the headless model is recreated with updated options.
|
|
67
|
+
- UIKit does not own labeling precedence logic; headless `getLandmarkProps()` determines whether `aria-label` or `aria-labelledby` is emitted.
|
|
68
|
+
|
|
69
|
+
## Usage
|
|
70
|
+
|
|
71
|
+
```html
|
|
72
|
+
<cv-landmark type="navigation" label="Main navigation">
|
|
73
|
+
<nav-links></nav-links>
|
|
74
|
+
</cv-landmark>
|
|
75
|
+
|
|
76
|
+
<cv-landmark type="main">
|
|
77
|
+
<page-content></page-content>
|
|
78
|
+
</cv-landmark>
|
|
79
|
+
|
|
80
|
+
<cv-landmark type="complementary" label="Related articles">
|
|
81
|
+
<aside-content></aside-content>
|
|
82
|
+
</cv-landmark>
|
|
83
|
+
|
|
84
|
+
<cv-landmark type="search" label="Site search">
|
|
85
|
+
<search-form></search-form>
|
|
86
|
+
</cv-landmark>
|
|
87
|
+
|
|
88
|
+
<cv-landmark type="region" label-id="section-heading">
|
|
89
|
+
<h2 id="section-heading">Latest News</h2>
|
|
90
|
+
<article-list></article-list>
|
|
91
|
+
</cv-landmark>
|
|
92
|
+
```
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
# cv-link
|
|
2
|
+
|
|
3
|
+
Inline navigational element that directs the user to another page or resource.
|
|
4
|
+
|
|
5
|
+
**Headless:** [`createLink`](https://github.com/chromvoid/headless-ui/blob/main/specs/components/link.md)
|
|
6
|
+
|
|
7
|
+
## Anatomy
|
|
8
|
+
|
|
9
|
+
```
|
|
10
|
+
<cv-link> (host)
|
|
11
|
+
└── <a part="base">
|
|
12
|
+
├── <span part="prefix">
|
|
13
|
+
│ └── <slot name="prefix">
|
|
14
|
+
├── <span part="label">
|
|
15
|
+
│ └── <slot>
|
|
16
|
+
└── <span part="suffix">
|
|
17
|
+
└── <slot name="suffix">
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## Attributes
|
|
21
|
+
|
|
22
|
+
| Attribute | Type | Default | Description |
|
|
23
|
+
| --------- | ------ | ------- | -------------------------------------------------- |
|
|
24
|
+
| `href` | String | `""` | Target URL; reflected to the inner anchor's `href` |
|
|
25
|
+
|
|
26
|
+
## Slots
|
|
27
|
+
|
|
28
|
+
| Slot | Description |
|
|
29
|
+
| ----------- | ---------------------------- |
|
|
30
|
+
| `(default)` | Link text |
|
|
31
|
+
| `prefix` | Icon or element before label |
|
|
32
|
+
| `suffix` | Icon or element after label |
|
|
33
|
+
|
|
34
|
+
## CSS Parts
|
|
35
|
+
|
|
36
|
+
| Part | Element | Description |
|
|
37
|
+
| -------- | -------- | -------------------------------- |
|
|
38
|
+
| `base` | `<a>` | The anchor element |
|
|
39
|
+
| `label` | `<span>` | Wrapper around the default slot |
|
|
40
|
+
| `prefix` | `<span>` | Wrapper around the `prefix` slot |
|
|
41
|
+
| `suffix` | `<span>` | Wrapper around the `suffix` slot |
|
|
42
|
+
|
|
43
|
+
## CSS Custom Properties
|
|
44
|
+
|
|
45
|
+
| Property | Default | Description |
|
|
46
|
+
| --------------------------------- | ------------------------------------------------------------------ | --------------------------------------- |
|
|
47
|
+
| `--cv-link-color` | `var(--cv-color-primary, #65d7ff)` | Default text and icon color |
|
|
48
|
+
| `--cv-link-color-hover` | `color-mix(in oklab, var(--cv-color-primary, #65d7ff) 78%, white)` | Text color on hover |
|
|
49
|
+
| `--cv-link-color-active` | `color-mix(in oklab, var(--cv-color-primary, #65d7ff) 60%, white)` | Text color on active press |
|
|
50
|
+
| `--cv-link-gap` | `var(--cv-space-1, 4px)` | Space between prefix, label, and suffix |
|
|
51
|
+
| `--cv-link-text-decoration` | `underline` | Text decoration style |
|
|
52
|
+
| `--cv-link-text-decoration-hover` | `none` | Text decoration on hover |
|
|
53
|
+
| `--cv-link-outline-color` | `var(--cv-color-primary, #65d7ff)` | Focus-visible outline color |
|
|
54
|
+
| `--cv-link-outline-offset` | `2px` | Focus-visible outline offset |
|
|
55
|
+
|
|
56
|
+
Additionally, component styles depend on theme tokens through fallback values:
|
|
57
|
+
|
|
58
|
+
| Theme Property | Default | Description |
|
|
59
|
+
| ---------------------- | --------- | ---------------------------- |
|
|
60
|
+
| `--cv-color-primary` | `#65d7ff` | Primary accent color |
|
|
61
|
+
| `--cv-duration-fast` | `120ms` | Transition duration |
|
|
62
|
+
| `--cv-easing-standard` | `ease` | Transition timing function |
|
|
63
|
+
| `--cv-space-1` | `4px` | Small spacing scale fallback |
|
|
64
|
+
|
|
65
|
+
## Visual States
|
|
66
|
+
|
|
67
|
+
| Host selector | Description |
|
|
68
|
+
| ----------------------- | ---------------------------------------------------------------------- |
|
|
69
|
+
| `:host(:hover)` | Applies `--cv-link-color-hover` to text color; updates text decoration |
|
|
70
|
+
| `:host(:focus-visible)` | Shows outline ring around the base element |
|
|
71
|
+
| `:host(:active)` | Applies `--cv-link-color-active` to text color |
|
|
72
|
+
|
|
73
|
+
## Reactive State Mapping
|
|
74
|
+
|
|
75
|
+
`cv-link` is a visual adapter over headless `createLink`.
|
|
76
|
+
|
|
77
|
+
| UIKit Property | Direction | Headless Binding |
|
|
78
|
+
| -------------- | -------------- | ----------------------------------------- |
|
|
79
|
+
| `href` | attr -> option | passed as `href` in `createLink(options)` |
|
|
80
|
+
|
|
81
|
+
| Headless State | Direction | DOM Reflection |
|
|
82
|
+
| -------------- | --------- | --------------------------------------- |
|
|
83
|
+
| _(none)_ | — | Link is stateless at the headless level |
|
|
84
|
+
|
|
85
|
+
- `contracts.getLinkProps()` is spread onto the inner `[part="base"]` element to apply `id`, `href`, and keyboard/click handlers.
|
|
86
|
+
- Because the inner element is a native `<a>`, `createLink` is called with `isSemanticHost: true`, so `role` and `tabindex` are omitted from the contract (the native element provides them).
|
|
87
|
+
- When `href` changes, the model is recreated with the new value (headless link options are immutable).
|
|
88
|
+
- UIKit dispatches a `press` event by providing an `onPress` callback to the headless `createLink` options.
|
|
89
|
+
- UIKit does not own activation logic; headless event handlers are the source of truth.
|
|
90
|
+
|
|
91
|
+
## Events
|
|
92
|
+
|
|
93
|
+
| Event | Detail | Description |
|
|
94
|
+
| ------- | ---------------- | ----------------------------------------------- |
|
|
95
|
+
| `press` | `{href: string}` | Fires on activation (click or `Enter` keypress) |
|
|
96
|
+
|
|
97
|
+
## Usage
|
|
98
|
+
|
|
99
|
+
```html
|
|
100
|
+
<cv-link href="/about">About us</cv-link>
|
|
101
|
+
|
|
102
|
+
<cv-link href="/docs">
|
|
103
|
+
<icon-book slot="prefix"></icon-book>
|
|
104
|
+
Documentation
|
|
105
|
+
</cv-link>
|
|
106
|
+
|
|
107
|
+
<cv-link href="/settings">
|
|
108
|
+
Settings
|
|
109
|
+
<icon-arrow-right slot="suffix"></icon-arrow-right>
|
|
110
|
+
</cv-link>
|
|
111
|
+
|
|
112
|
+
<cv-link href="/home">
|
|
113
|
+
<icon-home slot="prefix"></icon-home>
|
|
114
|
+
Home
|
|
115
|
+
<icon-external slot="suffix"></icon-external>
|
|
116
|
+
</cv-link>
|
|
117
|
+
```
|