@kerfjs/ui 5.0.0-beta.107 → 5.0.0-beta.109
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/ai/component-catalog.json +26 -13
- package/ai/component-composition-rules.json +2 -2
- package/ai/component-composition.json +10 -4
- package/ai/components/button.md +5 -5
- package/ai/components/chip.md +1 -0
- package/ai/components/foundation.md +1 -1
- package/ai/components/list.md +1 -1
- package/ai/components/segmented-control.md +1 -0
- package/ai/components/surface-scaffold.md +1 -0
- package/ai/components/tab-bar.md +5 -5
- package/ai/components/text-field.md +3 -1
- package/ai/components/toolbar-control-group.md +1 -0
- package/ai/components/toolbar.md +1 -1
- package/ai/public-api-signatures-v1.md +66 -15
- package/ai/skill.md +13 -7
- package/ai/webawesome-jsx-signatures-v1.md +1 -1
- package/dist/button.d.ts +3 -3
- package/dist/button.js +1 -1
- package/dist/catalog.js +4 -4
- package/dist/chip.d.ts +20 -2
- package/dist/chip.js +2 -1
- package/dist/{chunk-23PPPNH6.js → chunk-4OV272LF.js} +2 -2
- package/dist/{chunk-23PPPNH6.js.map → chunk-4OV272LF.js.map} +1 -1
- package/dist/{chunk-2PXZBFEC.js → chunk-5J6Z4BWY.js} +1 -1
- package/dist/{chunk-2PXZBFEC.js.map → chunk-5J6Z4BWY.js.map} +1 -1
- package/dist/{chunk-G4DRH4A5.js → chunk-6CDILXF4.js} +3 -1
- package/dist/chunk-6CDILXF4.js.map +1 -0
- package/dist/{chunk-RFLW4FPL.js → chunk-7AK5I7U7.js} +1 -1
- package/dist/chunk-7AK5I7U7.js.map +1 -0
- package/dist/{chunk-NLMEDZRM.js → chunk-CPSGUGAY.js} +5 -5
- package/dist/{chunk-NLMEDZRM.js.map → chunk-CPSGUGAY.js.map} +1 -1
- package/dist/{chunk-TXRKCGT3.js → chunk-KPINJHIC.js} +1 -1
- package/dist/chunk-KPINJHIC.js.map +1 -0
- package/dist/{chunk-N7MBGONH.js → chunk-LMHN2TJL.js} +22 -2
- package/dist/chunk-LMHN2TJL.js.map +1 -0
- package/dist/{chunk-NS2TBYM4.js → chunk-LZUUUHNH.js} +7 -3
- package/dist/chunk-LZUUUHNH.js.map +1 -0
- package/dist/{chunk-OY2MXIBB.js → chunk-NB6POCFH.js} +3 -1
- package/dist/chunk-NB6POCFH.js.map +1 -0
- package/dist/{chunk-AZ3WT77F.js → chunk-P7EJ4CAD.js} +2 -2
- package/dist/{chunk-AZ3WT77F.js.map → chunk-P7EJ4CAD.js.map} +1 -1
- package/dist/{chunk-Z4DS77U2.js → chunk-SOFPUW3O.js} +4 -4
- package/dist/{chunk-Z4DS77U2.js.map → chunk-SOFPUW3O.js.map} +1 -1
- package/dist/{chunk-QLA25V2K.js → chunk-WPNIKZMJ.js} +15 -1
- package/dist/chunk-WPNIKZMJ.js.map +1 -0
- package/dist/{chunk-DNWWF6UN.js → chunk-WSEJ2FDE.js} +4 -4
- package/dist/{chunk-DNWWF6UN.js.map → chunk-WSEJ2FDE.js.map} +1 -1
- package/dist/{chunk-WU57BYYM.js → chunk-YVZCKXR3.js} +8 -2
- package/dist/chunk-YVZCKXR3.js.map +1 -0
- package/dist/{chunk-CMLPFIC5.js → chunk-ZN7KUMPY.js} +3 -1
- package/dist/chunk-ZN7KUMPY.js.map +1 -0
- package/dist/collapsible-panel.js +2 -2
- package/dist/index.js +10 -10
- package/dist/list-detail-dialog.js +4 -4
- package/dist/list.d.ts +7 -1
- package/dist/list.js +1 -1
- package/dist/message-composer.js +1 -1
- package/dist/nav-stack.js +1 -1
- package/dist/segmented-control.d.ts +3 -1
- package/dist/segmented-control.js +1 -1
- package/dist/split-view.js +1 -1
- package/dist/styles/button.css +28 -2
- package/dist/styles/components/actions/button/button.css +28 -2
- package/dist/styles/components/actions/toolbar/toolbar.css +9 -0
- package/dist/styles/components/actions/toolbar-control-group/toolbar-control-group.css +29 -1
- package/dist/styles/components/collections/framed-list/framed-list.css +2 -0
- package/dist/styles/components/layout/pane/pane.css +15 -0
- package/dist/styles/components/navigation/nav-stack/nav-stack.css +13 -0
- package/dist/styles/components/navigation/tab-bar/tab-bar.css +6 -0
- package/dist/styles/components/navigation/tab-navigator/tab-navigator.css +16 -0
- package/dist/styles/components/surfaces/surface-scaffold/surface-scaffold.css +2 -0
- package/dist/styles/foundation.css +63 -19
- package/dist/styles/framed-list.css +2 -0
- package/dist/styles/nav-stack.css +13 -0
- package/dist/styles/pane.css +15 -0
- package/dist/styles/surface-scaffold.css +2 -0
- package/dist/styles/tab-bar.css +6 -0
- package/dist/styles/tab-navigator.css +16 -0
- package/dist/styles/toolbar-control-group.css +29 -1
- package/dist/styles/toolbar.css +9 -0
- package/dist/styles/webawesome.css +11 -3
- package/dist/surface-scaffold.d.ts +9 -1
- package/dist/surface-scaffold.js +1 -1
- package/dist/tab-bar.d.ts +2 -2
- package/dist/tab-bar.js +1 -1
- package/dist/text-field.d.ts +7 -1
- package/dist/text-field.js +1 -1
- package/dist/toolbar-control-group.d.ts +8 -2
- package/dist/toolbar-control-group.js +1 -1
- package/dist/toolbar.d.ts +6 -1
- package/dist/toolbar.js +1 -1
- package/dist/wire-catalog.js +1 -1
- package/dist/wire-workbench.js +1 -1
- package/dist/workbench-dialog.js +3 -3
- package/dist/workbench.js +1 -1
- package/docs/accessibility.md +29 -11
- package/docs/component-contract.md +19 -6
- package/docs/component-selection.md +38 -12
- package/docs/design/templates/button/tones-dark.svg +1 -1
- package/docs/design/templates/button/tones.svg +1 -1
- package/docs/design/templates/button-dark.svg +1 -1
- package/docs/design/templates/button.svg +1 -1
- package/docs/design/templates/split-button/states-dark.svg +1 -1
- package/docs/design/templates/split-button/states.svg +1 -1
- package/docs/design/templates/split-button-dark.svg +1 -1
- package/docs/design/templates/split-button.svg +1 -1
- package/docs/design/templates/text-field/number-dark.svg +1 -0
- package/docs/design/templates/text-field/number.svg +1 -0
- package/docs/design/templates/text-field-dark.svg +1 -1
- package/docs/design/templates/text-field.svg +1 -1
- package/docs/layout.md +16 -5
- package/docs/webawesome-migration.md +2 -0
- package/docs/webawesome-theme.md +8 -2
- package/docs/workbench.md +7 -1
- package/llms.txt +19 -7
- package/package.json +1 -1
- package/dist/chunk-CMLPFIC5.js.map +0 -1
- package/dist/chunk-G4DRH4A5.js.map +0 -1
- package/dist/chunk-N7MBGONH.js.map +0 -1
- package/dist/chunk-NS2TBYM4.js.map +0 -1
- package/dist/chunk-OY2MXIBB.js.map +0 -1
- package/dist/chunk-QLA25V2K.js.map +0 -1
- package/dist/chunk-RFLW4FPL.js.map +0 -1
- package/dist/chunk-TXRKCGT3.js.map +0 -1
- package/dist/chunk-WU57BYYM.js.map +0 -1
package/dist/styles/pane.css
CHANGED
|
@@ -76,11 +76,16 @@
|
|
|
76
76
|
surface instead. */
|
|
77
77
|
.kui-pane[data-background] {
|
|
78
78
|
background: var(--_kui-pane-background);
|
|
79
|
+
--kui-color-surface-current-region: var(--_kui-pane-background);
|
|
79
80
|
}
|
|
80
81
|
|
|
82
|
+
/* The transparent slots keep the root's surface context. */
|
|
81
83
|
.kui-pane[data-background][data-appearance="sunken"] > .kui-pane__content,
|
|
82
84
|
.kui-pane[data-background][data-appearance="sunken"][data-chrome-placement="auto"]
|
|
83
85
|
> :is(.kui-pane__header, .kui-pane__footer) {
|
|
86
|
+
--kui-color-surface-current: inherit;
|
|
87
|
+
--kui-color-surface-current-region: inherit;
|
|
88
|
+
--kui-color-surface-current-tint: inherit;
|
|
84
89
|
background: transparent;
|
|
85
90
|
}
|
|
86
91
|
|
|
@@ -266,6 +271,16 @@
|
|
|
266
271
|
background: var(--kui-chrome-material);
|
|
267
272
|
}
|
|
268
273
|
|
|
274
|
+
/* The material has no single color over scrolling content; the surface
|
|
275
|
+
context takes it at rest, as a tint over the region it covers. A clear
|
|
276
|
+
header paints nothing and keeps the inherited context. */
|
|
277
|
+
.kui-pane[data-header-presentation="overlay"]:not(
|
|
278
|
+
[data-header-material="clear"]
|
|
279
|
+
)
|
|
280
|
+
> .kui-pane__header {
|
|
281
|
+
--kui-color-surface-current-tint: var(--kui-chrome-material);
|
|
282
|
+
}
|
|
283
|
+
|
|
269
284
|
.kui-pane[data-header-presentation="overlay"][data-header-overlay="measured"]:not(
|
|
270
285
|
[data-chrome-placement="auto"]
|
|
271
286
|
)
|
|
@@ -337,6 +337,8 @@ h2.kui-dialog-surface__title {
|
|
|
337
337
|
-webkit-backdrop-filter: var(--kui-chrome-material-filter);
|
|
338
338
|
backdrop-filter: var(--kui-chrome-material-filter);
|
|
339
339
|
background: var(--kui-chrome-material-raised);
|
|
340
|
+
/* The material's surface context at rest, over the raised panel. */
|
|
341
|
+
--kui-color-surface-current-tint: var(--kui-chrome-material-raised);
|
|
340
342
|
/* The divider is scroll state: the register publishes it only while
|
|
341
343
|
content is scrolled beneath the header. An inset shadow, so showing it
|
|
342
344
|
never moves the header or the content. */
|
package/dist/styles/tab-bar.css
CHANGED
|
@@ -38,6 +38,12 @@
|
|
|
38
38
|
--kui-tab-bar-strip-background,
|
|
39
39
|
var(--kui-tab-bar-background)
|
|
40
40
|
);
|
|
41
|
+
/* The surface context (foundation.css): the strip's fill is a tint over
|
|
42
|
+
whatever the bar sits on. */
|
|
43
|
+
--kui-color-surface-current-tint: var(
|
|
44
|
+
--kui-tab-bar-strip-background,
|
|
45
|
+
var(--kui-tab-bar-background)
|
|
46
|
+
);
|
|
41
47
|
scrollbar-width: none;
|
|
42
48
|
align-items: center;
|
|
43
49
|
flex: var(--kui-tab-bar-strip-flex, 1 1 auto);
|
|
@@ -70,6 +70,13 @@
|
|
|
70
70
|
|
|
71
71
|
.kui-tab-scaffold__scene[data-background] {
|
|
72
72
|
background: var(--_kui-tab-scaffold-scene-background);
|
|
73
|
+
--kui-color-surface-current-region: var(--_kui-tab-scaffold-scene-background);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/* The navigator's color paints its root and a docked bar over whatever holds
|
|
77
|
+
the navigator: a region in the surface context. */
|
|
78
|
+
.kui-tab-scaffold[data-background] {
|
|
79
|
+
--kui-color-surface-current-region: var(--_kui-tab-scaffold-background);
|
|
73
80
|
}
|
|
74
81
|
|
|
75
82
|
@media (forced-colors: active) {
|
|
@@ -213,6 +220,15 @@
|
|
|
213
220
|
background: var(--kui-chrome-material);
|
|
214
221
|
}
|
|
215
222
|
|
|
223
|
+
/* The material's surface context at rest (see pane.css); a clear bar keeps
|
|
224
|
+
the inherited context. */
|
|
225
|
+
.kui-tab-scaffold[data-bar-presentation="overlay"]:not(
|
|
226
|
+
[data-bar-material="clear"]
|
|
227
|
+
)
|
|
228
|
+
> .kui-tab-scaffold__bar {
|
|
229
|
+
--kui-color-surface-current-tint: var(--kui-chrome-material);
|
|
230
|
+
}
|
|
231
|
+
|
|
216
232
|
.kui-tab-scaffold[data-bar-presentation="overlay"][data-bar-overlay="measured"] {
|
|
217
233
|
position: relative;
|
|
218
234
|
}
|
|
@@ -132,6 +132,31 @@
|
|
|
132
132
|
}
|
|
133
133
|
}
|
|
134
134
|
|
|
135
|
+
/* A sibling of an expanded trailing control yields to the trailing-priority
|
|
136
|
+
row the Toolbar moves that control onto: the same container queries and
|
|
137
|
+
responsiveAt keys as the Toolbar's own row (toolbar.css), so the group
|
|
138
|
+
hides exactly while the row is active and never wraps onto a third row at
|
|
139
|
+
a threshold restated with hideBelow. */
|
|
140
|
+
@container kui-toolbar (max-width: 52rem) {
|
|
141
|
+
.kui-toolbar[data-responsive="trailing-priority"][data-responsive-at="narrow"]
|
|
142
|
+
> .kui-toolbar__trailing:has(> [data-expanded="true"])
|
|
143
|
+
> .kui-toolbar-control-group[data-visibility="yield-to-priority-row"]:not(
|
|
144
|
+
[data-expanded="true"]
|
|
145
|
+
) {
|
|
146
|
+
display: none;
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
@container kui-toolbar (max-width: 44rem) {
|
|
151
|
+
.kui-toolbar[data-responsive="trailing-priority"][data-responsive-at="compact"]
|
|
152
|
+
> .kui-toolbar__trailing:has(> [data-expanded="true"])
|
|
153
|
+
> .kui-toolbar-control-group[data-visibility="yield-to-priority-row"]:not(
|
|
154
|
+
[data-expanded="true"]
|
|
155
|
+
) {
|
|
156
|
+
display: none;
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
|
|
135
160
|
/* `shape="rounded"` swaps the default pill radius for the design system's softer
|
|
136
161
|
rounded rectangle. The shared highlight contract derives every inner hover or
|
|
137
162
|
selected surface from this outer radius and the group's full inset. */
|
|
@@ -206,7 +231,10 @@
|
|
|
206
231
|
border-color 0.2s ease;
|
|
207
232
|
}
|
|
208
233
|
|
|
209
|
-
|
|
234
|
+
/* A fill search spans a content-sized group's line. A `sizing="grow"` group
|
|
235
|
+
keeps its own grow basis instead (below): taking the whole line would make
|
|
236
|
+
it the line's hypothetical size and wrap every sibling group. */
|
|
237
|
+
.kui-toolbar-control-group[data-content="search"]:not([data-sizing="grow"]):has(
|
|
210
238
|
> .kui-search-field[data-expanded="true"][data-fill="true"]
|
|
211
239
|
) {
|
|
212
240
|
width: 100%;
|
package/dist/styles/toolbar.css
CHANGED
|
@@ -16,6 +16,15 @@
|
|
|
16
16
|
font-family: var(--kui-font-sans);
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
+
/* In a List, a vertical stack, the toolbar is chrome and keeps its whole
|
|
20
|
+
natural height. Its explicit one-band min-height (below) replaces the flex
|
|
21
|
+
item's automatic content minimum, so a column shrinking toward a long
|
|
22
|
+
flex scroller beside it would otherwise squeeze a wrapped or stacked
|
|
23
|
+
toolbar onto its first row and clip the rest. */
|
|
24
|
+
.kui-list > .kui-toolbar {
|
|
25
|
+
flex-shrink: 0;
|
|
26
|
+
}
|
|
27
|
+
|
|
19
28
|
/* Safe areas: a toolbar compensates only for the inline edges its owner hands
|
|
20
29
|
it through `--kui-edge-inset-inline-*` (a Pane header or footer does), so its
|
|
21
30
|
box and dividers keep reaching the edge while its zones clear the unsafe
|
|
@@ -54,14 +54,19 @@
|
|
|
54
54
|
theme stylesheets build their shadows from this token, so an app that
|
|
55
55
|
layers one of them keeps kerf's scheme-aware shadow color. */
|
|
56
56
|
--wa-color-shadow: light-dark(rgb(0 0 0 / 0.14), rgb(0 0 0 / 0.5));
|
|
57
|
-
--
|
|
57
|
+
/* The brand tokens follow kerf's opt-in --kui-color-brand when the app
|
|
58
|
+
sets it (foundation.css derives the ramp); unset, the literals stand. */
|
|
59
|
+
--wa-color-focus: var(--_kui-brand-focus, light-dark(#007aff, #64d2ff));
|
|
58
60
|
/* Kerf-owned loud fills and on-loud text: every on-loud/fill-loud pair
|
|
59
61
|
clears WCAG AA (4.5:1) in both schemes. Light brand and danger keep
|
|
60
62
|
white text on a slightly deeper fill of the same hue (#0088ff ->
|
|
61
63
|
#0075db, #ff383c -> #eb0005); success keeps its bright green with dark
|
|
62
64
|
text, as warning already does; dark brand and danger keep their fills
|
|
63
65
|
with dark text. src/foundation.css mirrors these as fallbacks. */
|
|
64
|
-
--wa-color-brand-fill-loud:
|
|
66
|
+
--wa-color-brand-fill-loud: var(
|
|
67
|
+
--_kui-brand-fill-loud,
|
|
68
|
+
light-dark(#0075db, #64d2ff)
|
|
69
|
+
);
|
|
65
70
|
--wa-color-brand-fill-quiet: color-mix(
|
|
66
71
|
in srgb,
|
|
67
72
|
var(--wa-color-brand-fill-loud) 8%,
|
|
@@ -86,7 +91,10 @@
|
|
|
86
91
|
/* Kerf-owned light on-quiet values: darkened from Hot Sheet 2's hues so
|
|
87
92
|
they clear AA on the lowered page background (#f2f2f7) as well as on
|
|
88
93
|
the surface; src/foundation.css mirrors them as fallbacks. */
|
|
89
|
-
--wa-color-brand-on-quiet:
|
|
94
|
+
--wa-color-brand-on-quiet: var(
|
|
95
|
+
--_kui-brand-on-quiet,
|
|
96
|
+
light-dark(#0c62f3, #8acbff)
|
|
97
|
+
);
|
|
90
98
|
--wa-color-brand-on-normal: var(--wa-color-brand-on-quiet);
|
|
91
99
|
--wa-color-brand-on-loud: light-dark(#fff, #111113);
|
|
92
100
|
|
|
@@ -88,6 +88,14 @@ interface DialogSurfaceOptions {
|
|
|
88
88
|
* copy in the body; rendered as `aria-describedby` on the `<dialog>`.
|
|
89
89
|
*/
|
|
90
90
|
describedBy?: string;
|
|
91
|
+
/**
|
|
92
|
+
* An alert dialog: a confirmation that interrupts the person to report
|
|
93
|
+
* something urgent or ask before a destructive action ("Delete this
|
|
94
|
+
* topic?"). Renders `role="alertdialog"` on the `<dialog>`; set
|
|
95
|
+
* `describedBy` to the element holding the message, and leave
|
|
96
|
+
* `lightDismiss` off so the person answers it.
|
|
97
|
+
*/
|
|
98
|
+
alert?: boolean;
|
|
91
99
|
/** The body content. */
|
|
92
100
|
children: KerfUiContent;
|
|
93
101
|
/**
|
|
@@ -202,7 +210,7 @@ interface DialogSurfaceOptions {
|
|
|
202
210
|
* floating header and footer measurement, the bottom sheet's keyboard
|
|
203
211
|
* clearance and grabber, and re-render resilience while open.
|
|
204
212
|
*/
|
|
205
|
-
declare function DialogSurface({ id, label, labelledBy, describedBy, heading, headerActions, footer, withoutHeader, lightDismiss, closeLabel, children, size, presentation, preferredWidth, bodyInset, footerInset, viewportGutter, maxHeight, height, minHeight, resizable, enterMotion, exitMotion, bodyLayout, headerPresentation, footerPresentation, footerOffset, rootAttributes, className, slot, }: DialogSurfaceProps): kerfjs.SafeHtml;
|
|
213
|
+
declare function DialogSurface({ id, label, labelledBy, describedBy, alert, heading, headerActions, footer, withoutHeader, lightDismiss, closeLabel, children, size, presentation, preferredWidth, bodyInset, footerInset, viewportGutter, maxHeight, height, minHeight, resizable, enterMotion, exitMotion, bodyLayout, headerPresentation, footerPresentation, footerOffset, rootAttributes, className, slot, }: DialogSurfaceProps): kerfjs.SafeHtml;
|
|
206
214
|
/** Where a PopoverDialogSurface appears: the top layer, or in flow. */
|
|
207
215
|
type PopoverDialogSurfacePresentation = 'overlay' | 'embedded';
|
|
208
216
|
/** Application `data-*` metadata on the surface root. */
|
package/dist/surface-scaffold.js
CHANGED
package/dist/tab-bar.d.ts
CHANGED
|
@@ -12,12 +12,12 @@ interface TabBarProps {
|
|
|
12
12
|
label: string;
|
|
13
13
|
children: KerfUiContent;
|
|
14
14
|
leading?: KerfUiContent;
|
|
15
|
-
/** Tab-local action:
|
|
15
|
+
/** Tab-local action: one ToolbarControlGroup, Kerf Button, or Web Awesome button. */
|
|
16
16
|
trailing?: KerfUiContent;
|
|
17
17
|
/**
|
|
18
18
|
* Action pinned to the far edge of the bar. Combine with an adjacent `trailing`
|
|
19
19
|
* action when the tab-local and workspace-level actions must remain distinct.
|
|
20
|
-
* Accepts
|
|
20
|
+
* Accepts one ToolbarControlGroup, Kerf Button, or Web Awesome button.
|
|
21
21
|
*/
|
|
22
22
|
end?: KerfUiContent;
|
|
23
23
|
className?: string;
|
package/dist/tab-bar.js
CHANGED
package/dist/text-field.d.ts
CHANGED
|
@@ -50,6 +50,12 @@ interface TextFieldOptions {
|
|
|
50
50
|
showCount?: boolean;
|
|
51
51
|
/** Single-line value kind (default `text`). */
|
|
52
52
|
type?: TextFieldType;
|
|
53
|
+
/** Native lower bound for `type="number"` (number or numeric string). */
|
|
54
|
+
min?: number | string;
|
|
55
|
+
/** Native upper bound for `type="number"` (number or numeric string). */
|
|
56
|
+
max?: number | string;
|
|
57
|
+
/** Native number increment (number, numeric string, or `"any"`). */
|
|
58
|
+
step?: number | string;
|
|
53
59
|
/** A multi-line field: a `<textarea>`. */
|
|
54
60
|
multiline?: boolean;
|
|
55
61
|
/** A multi-line field's height in lines (default 3). */
|
|
@@ -78,6 +84,6 @@ interface TextFieldOptions {
|
|
|
78
84
|
* The whole field is one `<label>`, so clicking anywhere on it focuses the
|
|
79
85
|
* input; the input is named by `label` (or `ariaLabel`) directly.
|
|
80
86
|
*/
|
|
81
|
-
declare function TextField({ label, ariaLabel, value, name, placeholder, hint, error, size, icon, clearable, clearLabel, maxLength, showCount, type, multiline, rows, maxRows, disabled, readOnly, required, autocomplete, id, className, rootAttributes, slot, }: TextFieldProps): kerfjs.SafeHtml;
|
|
87
|
+
declare function TextField({ label, ariaLabel, value, name, placeholder, hint, error, size, icon, clearable, clearLabel, maxLength, showCount, type, min, max, step, multiline, rows, maxRows, disabled, readOnly, required, autocomplete, id, className, rootAttributes, slot, }: TextFieldProps): kerfjs.SafeHtml;
|
|
82
88
|
|
|
83
89
|
export { TextField, type TextFieldName, type TextFieldOptions, type TextFieldProps, type TextFieldRootAttributes, type TextFieldSize, type TextFieldType };
|
package/dist/text-field.js
CHANGED
|
@@ -19,7 +19,7 @@ type ToolbarControlGroupSelectedTone = 'brand' | 'neutral' | 'pop';
|
|
|
19
19
|
type ToolbarControlGroupOverflow = 'visible' | 'scroll' | 'wrap';
|
|
20
20
|
type ToolbarControlGroupExpandedOverflow = 'clip' | 'visible';
|
|
21
21
|
type ToolbarControlGroupMenuInset = 'standard' | 'compact' | 'list-zero';
|
|
22
|
-
type ToolbarControlGroupVisibility = 'always' | 'compact-only' | 'hide-collapsed-tiny' | 'yield-to-expanded-sibling';
|
|
22
|
+
type ToolbarControlGroupVisibility = 'always' | 'compact-only' | 'hide-collapsed-tiny' | 'yield-to-expanded-sibling' | 'yield-to-priority-row';
|
|
23
23
|
type ToolbarControlGroupSizing = 'content' | 'grow' | 'fill';
|
|
24
24
|
type ToolbarControlGroupPlacement = 'start' | 'end';
|
|
25
25
|
interface ToolbarActionLinkProps {
|
|
@@ -82,7 +82,13 @@ interface ToolbarControlGroupProps {
|
|
|
82
82
|
overflow?: ToolbarControlGroupOverflow;
|
|
83
83
|
/** Let app-owned anchored surfaces extend outside an expanded search group. Collapsed searches retain their clipping. */
|
|
84
84
|
expandedOverflow?: ToolbarControlGroupExpandedOverflow;
|
|
85
|
-
/**
|
|
85
|
+
/**
|
|
86
|
+
* Responsive visibility owned by the enclosing Toolbar container.
|
|
87
|
+
* `yield-to-priority-row` hides this trailing group exactly while its
|
|
88
|
+
* Toolbar's `responsive="trailing-priority"` row is active (an expanded
|
|
89
|
+
* trailing sibling at the Toolbar's `responsiveAt` width), so the app never
|
|
90
|
+
* restates that breakpoint with `hideBelow`.
|
|
91
|
+
*/
|
|
86
92
|
visibility?: ToolbarControlGroupVisibility;
|
|
87
93
|
/** Hide below this Toolbar content width; requires wireToolbarVisibility. */
|
|
88
94
|
hideBelow?: CssLength;
|
package/dist/toolbar.d.ts
CHANGED
|
@@ -9,6 +9,11 @@ type ToolbarPosition = 'header' | 'footer';
|
|
|
9
9
|
/** Control-band density: `default` (60px with 44px groups) or `compact`. */
|
|
10
10
|
type ToolbarDensity = 'default' | 'compact';
|
|
11
11
|
interface ToolbarProps {
|
|
12
|
+
/**
|
|
13
|
+
* The toolbar's id, so app code can address it: name it as a scrolling
|
|
14
|
+
* List's chrome in `wireScrollDividers({ targets })`, or find it in tests.
|
|
15
|
+
*/
|
|
16
|
+
id?: string;
|
|
12
17
|
leading?: KerfUiContent;
|
|
13
18
|
center?: KerfUiContent;
|
|
14
19
|
trailing?: KerfUiContent;
|
|
@@ -73,6 +78,6 @@ interface ToolbarProps {
|
|
|
73
78
|
* toolbar) forwards, so the app configures that toolbar instead of styling it.
|
|
74
79
|
*/
|
|
75
80
|
type ToolbarConfig = Pick<ToolbarProps, 'density' | 'dividerSides' | 'centerAlign' | 'responsive' | 'responsiveAt' | 'safeAreaEdges'>;
|
|
76
|
-
declare function Toolbar({ leading, center, trailing, label, position, density, dividerSides, centerAlign, responsive, responsiveAt, safeAreaEdges, className, slot, }: ToolbarProps): kerfjs.SafeHtml;
|
|
81
|
+
declare function Toolbar({ id, leading, center, trailing, label, position, density, dividerSides, centerAlign, responsive, responsiveAt, safeAreaEdges, className, slot, }: ToolbarProps): kerfjs.SafeHtml;
|
|
77
82
|
|
|
78
83
|
export { Sides, Toolbar, type ToolbarConfig, type ToolbarDensity, type ToolbarPosition, type ToolbarProps };
|
package/dist/toolbar.js
CHANGED
package/dist/wire-catalog.js
CHANGED
package/dist/wire-workbench.js
CHANGED
package/dist/workbench-dialog.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { DialogSurface } from './chunk-
|
|
1
|
+
import { DialogSurface } from './chunk-6CDILXF4.js';
|
|
2
2
|
export { closeDialog, openDialog } from './chunk-ATGAJVZ6.js';
|
|
3
3
|
|
|
4
|
-
import { Workbench } from './chunk-
|
|
4
|
+
import { Workbench } from './chunk-CPSGUGAY.js';
|
|
5
5
|
|
|
6
6
|
|
|
7
7
|
|
|
@@ -10,7 +10,7 @@ import { ToolbarText } from './chunk-EKHDLBRP.js';
|
|
|
10
10
|
|
|
11
11
|
|
|
12
12
|
|
|
13
|
-
import { ToolbarControlGroup } from './chunk-
|
|
13
|
+
import { ToolbarControlGroup } from './chunk-5J6Z4BWY.js';
|
|
14
14
|
|
|
15
15
|
|
|
16
16
|
|
package/dist/workbench.js
CHANGED
package/docs/accessibility.md
CHANGED
|
@@ -370,7 +370,10 @@ supporting line (or app-owned summary copy in the body) is the dialog's
|
|
|
370
370
|
accessible description; `WorkbenchDialog` wires its title `description`
|
|
371
371
|
automatically (`<id>-description`), and `ListDetailDialog` takes an explicit
|
|
372
372
|
`describedBy`, since its detail description describes the selection, not the
|
|
373
|
-
dialog.
|
|
373
|
+
dialog. A `DialogSurface` that asks before a destructive action ("Delete this
|
|
374
|
+
topic?") sets `alert`, which renders `role="alertdialog"` on the native
|
|
375
|
+
`<dialog>`; pair it with `describedBy` on the message so it is announced, and
|
|
376
|
+
leave `lightDismiss` off so the person answers it. For a **page or view**
|
|
374
377
|
title, pass `headingLevel` (usually `1`) to `ToolbarText`: it then exposes
|
|
375
378
|
`role="heading"` with a matching `aria-level`, giving the view a heading landmark
|
|
376
379
|
so screen-reader heading navigation and "main heading" semantics work — the same
|
|
@@ -418,8 +421,10 @@ workspace action in `end`; TabBar keeps the adjacent action immediately after
|
|
|
418
421
|
the shrinkable/scrolling tabs and pins `end` at the far edge. Leading,
|
|
419
422
|
trailing, and end actions remain visible and do not shrink. The component owns
|
|
420
423
|
that geometry; applications must not override its anatomy to create the split.
|
|
421
|
-
`trailing` and `end` each accept one `ToolbarControlGroup` for grouped controls
|
|
422
|
-
|
|
424
|
+
`trailing` and `end` each accept one `ToolbarControlGroup` for grouped controls,
|
|
425
|
+
one standalone Kerf `Button` for an action with its own chrome, or one standalone
|
|
426
|
+
Web Awesome `wa-button` for an exceptional ecosystem use. Do not add a wrapper
|
|
427
|
+
or flex margins to position the action.
|
|
423
428
|
`TabBarItem` provides compact 32px, segmented, truncating-label, and icon-only
|
|
424
429
|
presentations. Icon-only tabs keep the required `name` as the tab button's
|
|
425
430
|
accessible name while visually hiding the duplicate label. The default name
|
|
@@ -479,7 +484,9 @@ controls; Enter and Space use native button activation. The application handles
|
|
|
479
484
|
the supplied `data-action`, reads `data-segment-value`, updates `value`, and
|
|
480
485
|
re-renders. Keep labels unique and meaningful even when `content` shows only an
|
|
481
486
|
icon. The filled track uses the normal neutral text role for readable unselected
|
|
482
|
-
labels in light and dark themes.
|
|
487
|
+
labels in light and dark themes. A whole-control `disabled` disables every
|
|
488
|
+
native button and marks the group `aria-disabled` while `aria-pressed` still
|
|
489
|
+
reports the current choice. Use tabs—not a segmented control—when choices switch page regions that
|
|
483
490
|
need `tab`/`tabpanel` semantics.
|
|
484
491
|
|
|
485
492
|
## ChoiceChips
|
|
@@ -539,6 +546,12 @@ its label; the input itself reports `required`. The focus ring is drawn on the
|
|
|
539
546
|
box around the input (`:focus-within`), 3px with a 1px offset like every Kerf
|
|
540
547
|
control.
|
|
541
548
|
|
|
549
|
+
For `type="number"`, `min`, `max`, and `step` pass through to the native input.
|
|
550
|
+
Each accepts a number or string; `step="any"` allows arbitrary decimals.
|
|
551
|
+
They are omitted for other input types and `multiline` textareas. Native
|
|
552
|
+
constraint validation (`rangeUnderflow`, `rangeOverflow`, and `stepMismatch`)
|
|
553
|
+
then applies without custom field wiring.
|
|
554
|
+
|
|
542
555
|
`clearable` adds a native `<button>` named by `clearLabel` (default "Clear")
|
|
543
556
|
after the input. It is hidden while the field is empty, is a normal Tab stop,
|
|
544
557
|
and with `wireTextFields(root)` empties the field, dispatches bubbling `input`
|
|
@@ -567,12 +580,16 @@ a surface that changes the background behind its children publishes the
|
|
|
567
580
|
surface context (`--kui-color-surface-current`, `-region`, and `-tint`; see
|
|
568
581
|
`docs/component-contract.md`), and the line layers it the same way the page
|
|
569
582
|
does. On a sunken panel, a quiet `ContentItem`, a lowered `FramedList`, a
|
|
570
|
-
raised `List`, popup, or dialog,
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
the
|
|
574
|
-
|
|
575
|
-
|
|
583
|
+
raised `List`, popup, or dialog, a highlighted `FramedList` row, a sunken
|
|
584
|
+
Pane, Workbench area, or TabNavigator scene, or a Pane or TabNavigator app
|
|
585
|
+
`background`, the line matches the pixels outside the box, so it reads as a
|
|
586
|
+
cut through the fill instead of a light halo. On a doubly sunken surface the
|
|
587
|
+
brand ring still clears 3:1 against the line (about 3.2:1 in light, 6.9:1 in
|
|
588
|
+
dark). A sunken surface's grain is not part of the line. Translucent glass
|
|
589
|
+
chrome (an overlay header, bar, or bottom toolbar, a dialog's floating
|
|
590
|
+
header) has no single color over scrolling content, so the line paints the
|
|
591
|
+
material over the surface beneath it: exact at rest, an approximation while
|
|
592
|
+
content scrolls under the bar.
|
|
576
593
|
|
|
577
594
|
## Checkbox, RadioGroup, and Switch
|
|
578
595
|
|
|
@@ -786,7 +803,8 @@ the Tab order while collapsed or not inline. `wireWorkbench`, given a panel's
|
|
|
786
803
|
`collapsed` signal, returns focus stranded in a closing panel to the control that
|
|
787
804
|
opened it, else the restore control, else a control whose `aria-controls` names the
|
|
788
805
|
panel; an open overlay panel takes focus and keeps Tab inside it (the ARIA dialog
|
|
789
|
-
pattern)
|
|
806
|
+
pattern), whether its own toggle or a persistent toggle outside the Workbench
|
|
807
|
+
opened it, as soon as the panel can take focus. See [`workbench.md`](workbench.md).
|
|
790
808
|
|
|
791
809
|
## Chrome material
|
|
792
810
|
|
|
@@ -424,11 +424,17 @@ background behind its children publishes, on its own painted element, the
|
|
|
424
424
|
foundation tokens `--kui-color-surface-current` (the opaque surface beneath:
|
|
425
425
|
a raised `DialogSurface`, popover dialog, `AnchoredSurface`, or `List`
|
|
426
426
|
`surface`, and a sunken Pane's opaque auto chrome, set it and clear both
|
|
427
|
-
layers), `--kui-color-surface-current-region` (a layout region's
|
|
428
|
-
|
|
429
|
-
`--kui-color-surface-current-tint` (a
|
|
430
|
-
`SunkenPanel`, a sunken `Disclosure`, a lowered
|
|
431
|
-
hovered, pressed, or selected
|
|
427
|
+
layers), `--kui-color-surface-current-region` (a layout region's fill: a sunken
|
|
428
|
+
`Pane`, `Workbench` area, or `TabNavigator` scene, and a `Pane`'s or
|
|
429
|
+
`TabNavigator`'s app `background`), and `--kui-color-surface-current-tint` (a
|
|
430
|
+
content surface's fill: a `SunkenPanel`, a sunken `Disclosure`, a lowered
|
|
431
|
+
`FramedList` and its highlighted row, a quiet, hovered, pressed, or selected
|
|
432
|
+
`ContentItem`, a `TabBar` strip, and translucent glass chrome at rest — a
|
|
433
|
+
`Pane` overlay header, `NavStack` overlay chrome or bottom toolbar, a
|
|
434
|
+
`TabNavigator` overlay bar, and a dialog's floating header; clear chrome
|
|
435
|
+
paints nothing and keeps the inherited context). Interactive rows (`ListItem`,
|
|
436
|
+
`ListActionRow`, `SummaryRow`) are buttons or links themselves, so no control
|
|
437
|
+
nests on their hover or selection fill and they publish nothing. They are undeclared at `:root`
|
|
432
438
|
and a scoped `[data-kui-tint]` resets them. A control that must match what
|
|
433
439
|
lies behind it (the inset focus ring's inner line on `Button` and
|
|
434
440
|
`SplitButton`) layers tint over region over the opaque color, falling back to
|
|
@@ -635,7 +641,14 @@ preferences remove that entrance animation.
|
|
|
635
641
|
Use `visibility="yield-to-expanded-sibling"` on trailing groups that should
|
|
636
642
|
leave a 480px-or-narrower toolbar while a sibling trailing group is expanded.
|
|
637
643
|
They return when it collapses or the toolbar widens; leading and center zones
|
|
638
|
-
remain visible.
|
|
644
|
+
remain visible. In a `responsive="trailing-priority"` Toolbar, use
|
|
645
|
+
`visibility="yield-to-priority-row"` instead: the group leaves exactly while
|
|
646
|
+
the expanded trailing control has its own row, from the same container query
|
|
647
|
+
as the row at the Toolbar's `responsiveAt` (832px for `narrow`, 704px for
|
|
648
|
+
`compact`, both inclusive). Do not restate that width with `hideBelow`, which
|
|
649
|
+
hides strictly below its threshold: at exactly 704px the row is active while
|
|
650
|
+
`hideBelow={rem(44)}` still shows the group, which then wraps onto a third
|
|
651
|
+
row.
|
|
639
652
|
A group's controls are plain `<button>`s (a standalone `Button` belongs outside a group); a popup menu is a `PopupMenu`, which renders its own
|
|
640
653
|
trigger. By default a group stays on one row: each icon sits beside its label,
|
|
641
654
|
and the enclosing `Toolbar`'s responsive policy relocates whole groups. Set
|
|
@@ -108,6 +108,30 @@ useful subtree. Prefer a component prop or component-specific token when the
|
|
|
108
108
|
change belongs to one component or instance, and preserve the documented
|
|
109
109
|
foreground/background contrast relationships and visible focus ring.
|
|
110
110
|
|
|
111
|
+
### Brand color
|
|
112
|
+
|
|
113
|
+
Set the opt-in `--kui-color-brand` once on `:root` to give the application its
|
|
114
|
+
own brand. Any color works: Kerf derives the whole brand ramp from it — the
|
|
115
|
+
loud fill (and the quiet and normal fills and borders mixed from it), its
|
|
116
|
+
on-loud text, brand text and links, brand text on brand fills, and the focus
|
|
117
|
+
ring — clamping lightness in each color scheme so every pair keeps WCAG AA for
|
|
118
|
+
any hue. Unset, every brand token keeps its tuned default exactly. With the
|
|
119
|
+
Web Awesome integration the same derivation drives `--wa-color-brand-*` and
|
|
120
|
+
`--wa-color-focus`.
|
|
121
|
+
|
|
122
|
+
```css
|
|
123
|
+
:root {
|
|
124
|
+
--kui-color-brand: #1a7f37;
|
|
125
|
+
}
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
Do not change the brand by overriding `--kui-color-brand-fill-loud` alone:
|
|
129
|
+
brand text (`--kui-color-brand-on-quiet`, `--kui-color-brand-on-fill`) and the
|
|
130
|
+
focus ring are separate tuned values and would stay the default blue. Choose a
|
|
131
|
+
brand hue apart from the status tones it shares surfaces with: `info` follows
|
|
132
|
+
the brand, so a green brand makes an info banner read like `success`. For one
|
|
133
|
+
subtree with a different identity, use a scoped `tint` accent instead.
|
|
134
|
+
|
|
111
135
|
### Typed runtime dimensions
|
|
112
136
|
|
|
113
137
|
Use `Row`, `Grid`, or `List` spacing shorthands for repeated sibling spacing: `gap="xs"`,
|
|
@@ -643,15 +667,15 @@ the control's dimensions, shows `LoadingSpinner` in its place, sets
|
|
|
643
667
|
group hides only the glyph; a `content="text"` or `"mixed"` group hides the
|
|
644
668
|
whole control, label included, so the spinner never draws over text.
|
|
645
669
|
|
|
646
|
-
| Want | Put in the zone | Notes
|
|
647
|
-
| ------------------------------ | -------------------------------------------------------------------------------------- |
|
|
648
|
-
| Identity or title text | `<ToolbarText text="…" size="large" />` (or `xlarge` for a page/panel title that fits) | Wrap in a `single` borderless group only when it must align with adjacent control pills
|
|
649
|
-
| One or more icon/text buttons | `<ToolbarControlGroup>{buttons}</ToolbarControlGroup>` | Use `buttonAppearance="push"` for toggle buttons with `aria-pressed`; `single` for a lone control
|
|
650
|
-
| One primary application action | `trailing={<Button tone="brand">New Ticket…</Button>}` | The standalone button keeps its own chrome; use `tone="danger"` when the action is destructive
|
|
651
|
-
| An exclusive view switch | `<ToolbarControlGroup><SegmentedControl … /></ToolbarControlGroup>` | Not `TabBar`, which switches tabpanels
|
|
652
|
-
| A value list | `<ToolbarControlGroup><Select … /></ToolbarControlGroup>` | Register `@kerfjs/ui/select/register` once; use `focusRingOwner="group"` so focus follows the group's geometry
|
|
653
|
-
| A command menu | `<ToolbarControlGroup single nestedDropdown><PopupMenu … /></ToolbarControlGroup>` | Register `@kerfjs/ui/popup-menu/register` once; set `menuInset` on the group
|
|
654
|
-
| A collapsible search box | `<ToolbarControlGroup single><SearchField collapsible … /></ToolbarControlGroup>` | The group animates the iconic ↔ expanded states; `wireSearchFields` manages expand/collapse/focus by default
|
|
670
|
+
| Want | Put in the zone | Notes |
|
|
671
|
+
| ------------------------------ | -------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
672
|
+
| Identity or title text | `<ToolbarText text="…" size="large" />` (or `xlarge` for a page/panel title that fits) | Wrap in a `single` borderless group only when it must align with adjacent control pills |
|
|
673
|
+
| One or more icon/text buttons | `<ToolbarControlGroup>{buttons}</ToolbarControlGroup>` | Use `buttonAppearance="push"` for toggle buttons with `aria-pressed`; `single` for a lone control |
|
|
674
|
+
| One primary application action | `trailing={<Button tone="brand">New Ticket…</Button>}` | The standalone button keeps its own chrome; use `tone="success"` for a positive pricing check or `tone="danger"` when the action is destructive |
|
|
675
|
+
| An exclusive view switch | `<ToolbarControlGroup><SegmentedControl … /></ToolbarControlGroup>` | Not `TabBar`, which switches tabpanels |
|
|
676
|
+
| A value list | `<ToolbarControlGroup><Select … /></ToolbarControlGroup>` | Register `@kerfjs/ui/select/register` once; use `focusRingOwner="group"` so focus follows the group's geometry |
|
|
677
|
+
| A command menu | `<ToolbarControlGroup single nestedDropdown><PopupMenu … /></ToolbarControlGroup>` | Register `@kerfjs/ui/popup-menu/register` once; set `menuInset` on the group |
|
|
678
|
+
| A collapsible search box | `<ToolbarControlGroup single><SearchField collapsible … /></ToolbarControlGroup>` | The group animates the iconic ↔ expanded states; `wireSearchFields` manages expand/collapse/focus by default |
|
|
655
679
|
|
|
656
680
|
### Room for an expanded search
|
|
657
681
|
|
|
@@ -665,9 +689,11 @@ other controls; plan for it instead:
|
|
|
665
689
|
beside the siblings.
|
|
666
690
|
- If a useful search cannot fit beside the other controls, set those controls
|
|
667
691
|
aside while it is open. Mark them `visibility="yield-to-expanded-sibling"`
|
|
668
|
-
(they leave a 480px-or-narrower toolbar while a sibling is expanded), or
|
|
669
|
-
|
|
670
|
-
|
|
692
|
+
(they leave a 480px-or-narrower toolbar while a sibling is expanded), or, in
|
|
693
|
+
a `responsive="trailing-priority"` Toolbar,
|
|
694
|
+
`visibility="yield-to-priority-row"` (they leave exactly while the expanded
|
|
695
|
+
control has its own row), or gather them behind a "…" `PopupMenu` overflow
|
|
696
|
+
group. The application decides which controls yield.
|
|
671
697
|
|
|
672
698
|
### Application surfaces below search
|
|
673
699
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 520 84" width="520" height="84"><defs><clipPath id="ct0"><rect x="29" y="33" width="105.3" height="18"/></clipPath><clipPath id="ct1"><rect x="160.3" y="33" width="51" height="18"/></clipPath><clipPath id="ct2"><rect x="237.3" y="33" width="104.8" height="18"/></clipPath></defs><rect x="20" y="20" width="123.3" height="44" rx="12" fill="rgb(100,210,255)"/><rect x="20.5" y="20.5" width="122" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="29" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(17,17,19)">Save Changes</text><rect x="151.3" y="20" width="69" height="44" rx="12" fill="rgb(229,229,234)"/><rect x="151.5" y="20.5" width="68" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="160.28" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(28,28,30)">Cancel</text><rect x="228.3" y="20" width="122.8" height="44" rx="12" fill="rgb(255,56,60)"/><rect x="
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 520 84" width="520" height="84"><defs><clipPath id="ct0"><rect x="29" y="33" width="105.3" height="18"/></clipPath><clipPath id="ct1"><rect x="160.3" y="33" width="51" height="18"/></clipPath><clipPath id="ct2"><rect x="237.3" y="33" width="88.9" height="18"/></clipPath><clipPath id="ct3"><rect x="352.2" y="33" width="104.8" height="18"/></clipPath></defs><rect x="20" y="20" width="123.3" height="44" rx="12" fill="rgb(100,210,255)"/><rect x="20.5" y="20.5" width="122" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="29" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(17,17,19)">Save Changes</text><rect x="151.3" y="20" width="69" height="44" rx="12" fill="rgb(229,229,234)"/><rect x="151.5" y="20.5" width="68" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="160.28" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(28,28,30)">Cancel</text><rect x="228.3" y="20" width="106.9" height="44" rx="12" fill="rgb(52,199,89)"/><rect x="228.5" y="20.5" width="106" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="237.27" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(29,29,31)">Price Check</text><rect x="343.2" y="20" width="122.8" height="44" rx="12" fill="rgb(255,56,60)"/><rect x="343.5" y="20.5" width="122" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="352.16" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(17,17,19)">Delete Project</text></svg>
|
|
@@ -1 +1 @@
|
|
|
1
|
-
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 520 84" width="520" height="84"><defs><clipPath id="ct0"><rect x="29" y="33" width="105.3" height="18"/></clipPath><clipPath id="ct1"><rect x="160.3" y="33" width="51" height="18"/></clipPath><clipPath id="ct2"><rect x="237.3" y="33" width="104.8" height="18"/></clipPath></defs><rect x="20" y="20" width="123.3" height="44" rx="12" fill="rgb(0,117,219)"/><rect x="20.5" y="20.5" width="122" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="29" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(255,255,255)">Save Changes</text><rect x="151.3" y="20" width="69" height="44" rx="12" fill="rgb(72,72,74)"/><rect x="151.5" y="20.5" width="68" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="160.28" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(255,255,255)">Cancel</text><rect x="228.3" y="20" width="122.8" height="44" rx="12" fill="rgb(235,0,5)"/><rect x="
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 520 84" width="520" height="84"><defs><clipPath id="ct0"><rect x="29" y="33" width="105.3" height="18"/></clipPath><clipPath id="ct1"><rect x="160.3" y="33" width="51" height="18"/></clipPath><clipPath id="ct2"><rect x="237.3" y="33" width="88.9" height="18"/></clipPath><clipPath id="ct3"><rect x="352.2" y="33" width="104.8" height="18"/></clipPath></defs><rect x="20" y="20" width="123.3" height="44" rx="12" fill="rgb(0,117,219)"/><rect x="20.5" y="20.5" width="122" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="29" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(255,255,255)">Save Changes</text><rect x="151.3" y="20" width="69" height="44" rx="12" fill="rgb(72,72,74)"/><rect x="151.5" y="20.5" width="68" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="160.28" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(255,255,255)">Cancel</text><rect x="228.3" y="20" width="106.9" height="44" rx="12" fill="rgb(52,199,89)"/><rect x="228.5" y="20.5" width="106" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="237.27" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(29,29,31)">Price Check</text><rect x="343.2" y="20" width="122.8" height="44" rx="12" fill="rgb(235,0,5)"/><rect x="343.5" y="20.5" width="122" height="43" rx="11.5" fill="none" stroke="rgba(0,0,0,0)" stroke-width="1"/><text x="352.16" y="48" font-family="system-ui, "-apple-system", sans-serif" font-size="16" font-weight="500" fill="rgb(255,255,255)">Delete Project</text></svg>
|