@zeyos/zx 2.2.1 → 3.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.
Files changed (117) hide show
  1. package/CHANGELOG.md +197 -0
  2. package/DESIGN-SYSTEM.md +136 -0
  3. package/MIGRATION.md +155 -4
  4. package/README.md +51 -14
  5. package/dist/types/compat/map/data.d.ts +3 -2
  6. package/dist/types/components/account-menu/account-menu.d.ts +144 -0
  7. package/dist/types/components/app-rail/app-rail.d.ts +250 -0
  8. package/dist/types/components/app-sidebar/app-sidebar.d.ts +169 -0
  9. package/dist/types/components/avatar/avatar.d.ts +100 -0
  10. package/dist/types/components/chart/chart.d.ts +321 -0
  11. package/dist/types/components/date-picker/month-picker.d.ts +6 -0
  12. package/dist/types/components/dialog/dialog.d.ts +9 -0
  13. package/dist/types/components/dock/dock.d.ts +495 -0
  14. package/dist/types/components/dropdown/dropdown.d.ts +2 -2
  15. package/dist/types/components/field/field.d.ts +14 -0
  16. package/dist/types/components/field-upload/field-upload.d.ts +37 -4
  17. package/dist/types/components/form/form.d.ts +25 -3
  18. package/dist/types/components/grid/grid.d.ts +172 -0
  19. package/dist/types/components/launcher/launcher.d.ts +300 -0
  20. package/dist/types/components/layout/layout.d.ts +4 -4
  21. package/dist/types/components/menu-button/menu-button.d.ts +10 -2
  22. package/dist/types/components/modal/modal.d.ts +25 -0
  23. package/dist/types/components/multi-value-editor/multi-value-editor.d.ts +74 -9
  24. package/dist/types/components/questionnaire/items.d.ts +327 -0
  25. package/dist/types/components/questionnaire/questionnaire.d.ts +449 -0
  26. package/dist/types/components/select/select.d.ts +36 -1
  27. package/dist/types/components/sheet/sheet-stack.d.ts +167 -0
  28. package/dist/types/components/sheet/sheet.d.ts +294 -0
  29. package/dist/types/components/split-view/split-view.d.ts +2 -21
  30. package/dist/types/components/tabbox/tabbox.d.ts +12 -3
  31. package/dist/types/components/table/table.d.ts +219 -12
  32. package/dist/types/components/tooltip/tooltip.d.ts +2 -2
  33. package/dist/types/components/value-list/value-list.d.ts +24 -3
  34. package/dist/types/core/dom.d.ts +114 -0
  35. package/dist/types/core/drag-axis.d.ts +111 -0
  36. package/dist/types/core/position.d.ts +4 -2
  37. package/dist/types/index.d.ts +12 -2
  38. package/dist/zx-compat.esm.js +943 -311
  39. package/dist/zx-compat.esm.min.js +1 -1
  40. package/dist/zx-compat.global.js +7893 -2252
  41. package/dist/zx-compat.global.min.js +3 -3
  42. package/dist/zx-zeyos.esm.js +826 -114
  43. package/dist/zx-zeyos.esm.min.js +1 -1
  44. package/dist/zx.css +1720 -243
  45. package/dist/zx.esm.js +8227 -2599
  46. package/dist/zx.esm.min.js +3 -3
  47. package/dist/zx.global.js +8227 -2599
  48. package/dist/zx.global.min.js +3 -3
  49. package/dist/zx.min.css +1 -1
  50. package/docs/api.json +2597 -255
  51. package/docs/llms.md +475 -37
  52. package/docs/llms.txt +21 -9
  53. package/package.json +4 -2
  54. package/src/compat/globals.js +3 -1
  55. package/src/compat/map/data.js +31 -9
  56. package/src/components/account-menu/account-menu.css +70 -0
  57. package/src/components/account-menu/account-menu.js +208 -0
  58. package/src/components/app-rail/app-rail.css +107 -0
  59. package/src/components/app-rail/app-rail.js +668 -0
  60. package/src/components/app-sidebar/app-sidebar.css +68 -0
  61. package/src/components/app-sidebar/app-sidebar.js +388 -0
  62. package/src/components/avatar/avatar.css +61 -0
  63. package/src/components/avatar/avatar.js +222 -0
  64. package/src/components/button/button.css +0 -1
  65. package/src/components/chart/chart.css +61 -0
  66. package/src/components/chart/chart.js +518 -0
  67. package/src/components/date-picker/date-range-picker.css +7 -0
  68. package/src/components/date-picker/month-picker.js +9 -0
  69. package/src/components/dialog/dialog.js +11 -4
  70. package/src/components/dock/dock.css +228 -0
  71. package/src/components/dock/dock.js +977 -0
  72. package/src/components/dropdown/dropdown.js +1 -1
  73. package/src/components/field/field.js +2 -0
  74. package/src/components/field-upload/field-upload.js +9 -4
  75. package/src/components/fieldset/fieldset.css +7 -0
  76. package/src/components/form/form.css +7 -0
  77. package/src/components/form/form.js +6 -3
  78. package/src/components/grid/grid.css +6 -0
  79. package/src/components/grid/grid.js +213 -0
  80. package/src/components/launcher/launcher.css +100 -0
  81. package/src/components/launcher/launcher.js +557 -0
  82. package/src/components/layout/layout.js +2 -2
  83. package/src/components/menu-button/menu-button.js +27 -2
  84. package/src/components/modal/modal.css +5 -1
  85. package/src/components/modal/modal.js +37 -2
  86. package/src/components/multi-value-editor/multi-value-editor.css +99 -15
  87. package/src/components/multi-value-editor/multi-value-editor.js +237 -19
  88. package/src/components/navigation-bar/navigation-bar.css +7 -0
  89. package/src/components/questionnaire/items.js +370 -0
  90. package/src/components/questionnaire/questionnaire.css +387 -0
  91. package/src/components/questionnaire/questionnaire.js +1033 -0
  92. package/src/components/search/search.css +10 -2
  93. package/src/components/select/select.css +6 -1
  94. package/src/components/select/select.js +99 -11
  95. package/src/components/sheet/sheet-stack.js +304 -0
  96. package/src/components/sheet/sheet.css +351 -0
  97. package/src/components/sheet/sheet.js +551 -0
  98. package/src/components/split-view/split-view.js +76 -161
  99. package/src/components/stepper/stepper.css +12 -2
  100. package/src/components/tabbox/tabbox.css +13 -3
  101. package/src/components/tabbox/tabbox.js +34 -10
  102. package/src/components/table/table.css +43 -0
  103. package/src/components/table/table.js +523 -45
  104. package/src/components/tooltip/tooltip.js +5 -2
  105. package/src/components/value-list/value-list.js +6 -3
  106. package/src/core/dom.js +302 -0
  107. package/src/core/drag-axis.js +203 -0
  108. package/src/core/position.js +68 -22
  109. package/src/index.js +19 -2
  110. package/styles/tokens/dark.css +15 -13
  111. package/styles/tokens/global.css +17 -5
  112. package/styles/tokens/semantic.css +14 -8
  113. package/styles/tokens/themes.css +72 -0
  114. package/styles/zx.css +11 -1
  115. package/dist/types/components/permission/permission.d.ts +0 -93
  116. package/src/components/permission/permission.css +0 -47
  117. package/src/components/permission/permission.js +0 -198
@@ -0,0 +1,351 @@
1
+ /*
2
+ * Sheet builds on `.zx-modal` and `.zx-dialog`, so this file must be imported after both: the
3
+ * overrides below share their specificity and win on source order alone.
4
+ */
5
+ .zx-sheet {
6
+ position: fixed;
7
+ margin: 0;
8
+ padding: 0;
9
+ max-inline-size: 100vw;
10
+ max-block-size: 100dvh;
11
+ border: 0;
12
+ border-radius: 0;
13
+ /* The header and footer stay put; `.zx-dialog__body` is what scrolls. */
14
+ overflow: hidden;
15
+ box-shadow: var(--zx-overlay-shadow);
16
+ }
17
+
18
+ /* Horizontal sheets: full height, sized across the inline axis. */
19
+ .zx-sheet[data-side="start"],
20
+ .zx-sheet[data-side="end"] {
21
+ inset-block: 0;
22
+ block-size: 100dvh;
23
+ inline-size: var(--zx-sheet-size, min(24rem, 100vw));
24
+ }
25
+
26
+ .zx-sheet[data-side="start"] {
27
+ inset-inline-start: 0;
28
+ inset-inline-end: auto;
29
+ border-inline-end: 1px solid var(--zx-color-border);
30
+ --zx-sheet-enter: -100% 0;
31
+ }
32
+
33
+ .zx-sheet[data-side="end"] {
34
+ inset-inline-start: auto;
35
+ inset-inline-end: 0;
36
+ border-inline-start: 1px solid var(--zx-color-border);
37
+ --zx-sheet-enter: 100% 0;
38
+ }
39
+
40
+ /*
41
+ * `translate` is physical, so the logical sides need the one direction-aware rule in the library.
42
+ * Attribute rather than `:dir()` because the latter only reached Chrome in December 2023, at the
43
+ * very edge of the supported baseline, and this is the sole place it would buy anything.
44
+ */
45
+ [dir="rtl"] .zx-sheet[data-side="start"] { --zx-sheet-enter: 100% 0; }
46
+ [dir="rtl"] .zx-sheet[data-side="end"] { --zx-sheet-enter: -100% 0; }
47
+
48
+ /* Vertical sheets: full width, sized down the block axis, inner corners rounded like a drawer. */
49
+ .zx-sheet[data-side="top"],
50
+ .zx-sheet[data-side="bottom"] {
51
+ inset-inline: 0;
52
+ inline-size: 100vw;
53
+ block-size: var(--zx-sheet-size, min(60dvh, 100dvh));
54
+ }
55
+
56
+ .zx-sheet[data-side="top"] {
57
+ inset-block-start: 0;
58
+ inset-block-end: auto;
59
+ border-block-end: 1px solid var(--zx-color-border);
60
+ border-end-start-radius: var(--zx-sheet-radius, var(--zx-radius-xl));
61
+ border-end-end-radius: var(--zx-sheet-radius, var(--zx-radius-xl));
62
+ --zx-sheet-enter: 0 -100%;
63
+ }
64
+
65
+ .zx-sheet[data-side="bottom"] {
66
+ inset-block-start: auto;
67
+ inset-block-end: 0;
68
+ border-block-start: 1px solid var(--zx-color-border);
69
+ border-start-start-radius: var(--zx-sheet-radius, var(--zx-radius-xl));
70
+ border-start-end-radius: var(--zx-sheet-radius, var(--zx-radius-xl));
71
+ --zx-sheet-enter: 0 100%;
72
+ }
73
+
74
+ /*
75
+ * Backdrop treatments. Only a modal sheet has a `::backdrop` at all, which is why `backdrop` is
76
+ * documented as meaningful only alongside `modal: true`.
77
+ */
78
+ .zx-sheet[data-backdrop="none"]::backdrop {
79
+ background: transparent;
80
+ }
81
+
82
+ .zx-sheet[data-backdrop="blur"]::backdrop {
83
+ backdrop-filter: blur(var(--zx-overlay-blur));
84
+ }
85
+
86
+ /*
87
+ * Entry and exit both animate. A `<dialog>` normally cannot animate out — `close()` applies
88
+ * `display: none` immediately — so `display` and `overlay` transition with `allow-discrete`, which
89
+ * defers the discrete jump until the rest of the transition has finished. `@starting-style` gives
90
+ * the entry its from-state. Where either is unsupported the sheet simply appears and disappears.
91
+ */
92
+ @media (prefers-reduced-motion: no-preference) {
93
+ .zx-sheet {
94
+ transition:
95
+ translate var(--zx-dur-base) var(--zx-ease),
96
+ opacity var(--zx-dur-base) var(--zx-ease),
97
+ display var(--zx-dur-base) allow-discrete,
98
+ overlay var(--zx-dur-base) allow-discrete;
99
+ }
100
+
101
+ /* Modal's entry keyframes animate the centre-screen case and would fight the slide. */
102
+ .zx-sheet[data-state="open"] {
103
+ animation: none;
104
+ }
105
+
106
+ .zx-sheet:not([open]) {
107
+ translate: var(--zx-sheet-enter, 0 0);
108
+ opacity: 0;
109
+ }
110
+
111
+ @starting-style {
112
+ .zx-sheet[open] {
113
+ translate: var(--zx-sheet-enter, 0 0);
114
+ opacity: 0;
115
+ }
116
+ }
117
+
118
+ .zx-sheet::backdrop {
119
+ transition:
120
+ opacity var(--zx-dur-base) var(--zx-ease),
121
+ display var(--zx-dur-base) allow-discrete,
122
+ overlay var(--zx-dur-base) allow-discrete;
123
+ }
124
+
125
+ .zx-sheet[data-state="open"]::backdrop {
126
+ animation: none;
127
+ }
128
+
129
+ .zx-sheet:not([open])::backdrop {
130
+ opacity: 0;
131
+ }
132
+
133
+ @starting-style {
134
+ .zx-sheet[open]::backdrop {
135
+ opacity: 0;
136
+ }
137
+ }
138
+ }
139
+
140
+ /*
141
+ * A docked sheet is a track in its dock's flow, not an overlay: it drops out of fixed positioning
142
+ * and takes its size from the dock's own custom property, the same one the dock's panes use. It is
143
+ * always non-modal while docked, so there is no backdrop to consider.
144
+ *
145
+ * Closing animates the track to zero rather than sliding the sheet away — in the flow there is
146
+ * nowhere to slide to, and collapsing the space is what the surrounding layout should see.
147
+ */
148
+ .zx-sheet[data-docked] {
149
+ position: relative;
150
+ inset: auto;
151
+ flex: 0 0 var(--zx-pane-size, var(--zx-sheet-size, min(24rem, 100%)));
152
+ inline-size: auto;
153
+ block-size: auto;
154
+ max-inline-size: none;
155
+ max-block-size: none;
156
+ min-inline-size: 0;
157
+ min-block-size: 0;
158
+ border-radius: 0;
159
+ box-shadow: none;
160
+ }
161
+
162
+ .zx-dock[data-orientation="vertical"] > .zx-sheet[data-docked] {
163
+ border-inline: 0;
164
+ border-block: 1px solid var(--zx-color-border);
165
+ }
166
+
167
+ .zx-dock[data-orientation="horizontal"] > .zx-sheet[data-docked] {
168
+ border-block: 0;
169
+ border-inline: 1px solid var(--zx-color-border);
170
+ }
171
+
172
+ @media (prefers-reduced-motion: no-preference) {
173
+ .zx-sheet[data-docked] {
174
+ transition:
175
+ flex-basis var(--zx-dur-base) var(--zx-ease),
176
+ opacity var(--zx-dur-base) var(--zx-ease),
177
+ display var(--zx-dur-base) allow-discrete,
178
+ overlay var(--zx-dur-base) allow-discrete;
179
+ /* The slide belongs to the overlay life; in the flow the track itself is what moves. */
180
+ translate: none;
181
+ }
182
+
183
+ .zx-sheet[data-docked]:not([open]) {
184
+ flex-basis: 0;
185
+ translate: none;
186
+ opacity: 0;
187
+ }
188
+
189
+ @starting-style {
190
+ .zx-sheet[data-docked][open] {
191
+ flex-basis: 0;
192
+ translate: none;
193
+ opacity: 0;
194
+ }
195
+ }
196
+ }
197
+
198
+ /*
199
+ * The grab handle sits just inside the sheet's inner edge — the one facing the page. It is a
200
+ * `separator` with live values, so it is draggable, focusable, and steppable with the arrow keys.
201
+ * The hit area is deliberately wider than the pill it draws.
202
+ */
203
+ .zx-sheet__handle {
204
+ position: absolute;
205
+ z-index: 1;
206
+ display: flex;
207
+ align-items: center;
208
+ justify-content: center;
209
+ touch-action: none;
210
+ user-select: none;
211
+ }
212
+
213
+ .zx-sheet__handle::after {
214
+ content: "";
215
+ border-radius: var(--zx-radius-full);
216
+ background: var(--zx-color-border-strong);
217
+ opacity: 0;
218
+ transition: opacity var(--zx-dur-fast) var(--zx-ease);
219
+ }
220
+
221
+ .zx-sheet__handle:hover::after,
222
+ .zx-sheet__handle:focus-visible::after,
223
+ .zx-sheet[data-dragging] .zx-sheet__handle::after {
224
+ opacity: 1;
225
+ }
226
+
227
+ .zx-sheet__handle:focus-visible {
228
+ outline: none;
229
+ box-shadow: var(--zx-focus-ring);
230
+ }
231
+
232
+ /* Inner edge for each side, and the pill drawn across it. */
233
+ .zx-sheet[data-side="start"] > .zx-sheet__handle,
234
+ .zx-sheet[data-side="end"] > .zx-sheet__handle {
235
+ inset-block: 0;
236
+ inline-size: var(--zx-space-3);
237
+ cursor: col-resize;
238
+ }
239
+
240
+ .zx-sheet[data-side="start"] > .zx-sheet__handle { inset-inline-end: 0; }
241
+ .zx-sheet[data-side="end"] > .zx-sheet__handle { inset-inline-start: 0; }
242
+
243
+ .zx-sheet[data-side="start"] > .zx-sheet__handle::after,
244
+ .zx-sheet[data-side="end"] > .zx-sheet__handle::after {
245
+ inline-size: 3px;
246
+ block-size: var(--zx-space-8);
247
+ }
248
+
249
+ .zx-sheet[data-side="top"] > .zx-sheet__handle,
250
+ .zx-sheet[data-side="bottom"] > .zx-sheet__handle {
251
+ inset-inline: 0;
252
+ block-size: var(--zx-space-4);
253
+ cursor: row-resize;
254
+ }
255
+
256
+ .zx-sheet[data-side="top"] > .zx-sheet__handle { inset-block-end: 0; }
257
+ .zx-sheet[data-side="bottom"] > .zx-sheet__handle { inset-block-start: 0; }
258
+
259
+ .zx-sheet[data-side="top"] > .zx-sheet__handle::after,
260
+ .zx-sheet[data-side="bottom"] > .zx-sheet__handle::after {
261
+ inline-size: var(--zx-space-8);
262
+ block-size: 4px;
263
+ }
264
+
265
+ /* A drawer's handle is a standing invitation, so it does not wait to be hovered. */
266
+ .zx-sheet[data-side="top"] > .zx-sheet__handle::after,
267
+ .zx-sheet[data-side="bottom"] > .zx-sheet__handle::after {
268
+ opacity: 1;
269
+ }
270
+
271
+ /* A docked sheet is resized by the dock's divider, so its own handle stands down. */
272
+ .zx-sheet[data-docked] > .zx-sheet__handle {
273
+ display: none;
274
+ }
275
+
276
+ /* Nothing may animate while the pointer is driving the size, or the sheet lags behind it. */
277
+ .zx-sheet[data-dragging] {
278
+ transition: none;
279
+ }
280
+
281
+ /*
282
+ * Stacking. Depth is written by `SheetStack` as `--zx-sheet-depth`; the direction it moves in is
283
+ * a per-side unit vector pointing at the sheet's own edge, so one rule covers all four sides.
284
+ *
285
+ * `transform` rather than `translate`, because the enter and exit animation already owns
286
+ * `translate` — the two are independent properties and compose, so a sheet can slide in and sit at
287
+ * a depth at the same time.
288
+ */
289
+ .zx-sheet[data-side="start"] { --zx-sheet-dx: -1; --zx-sheet-dy: 0; }
290
+ .zx-sheet[data-side="end"] { --zx-sheet-dx: 1; --zx-sheet-dy: 0; }
291
+ .zx-sheet[data-side="top"] { --zx-sheet-dx: 0; --zx-sheet-dy: -1; }
292
+ .zx-sheet[data-side="bottom"] { --zx-sheet-dx: 0; --zx-sheet-dy: 1; }
293
+
294
+ /* Scaling a covered sheet shrinks it toward its own edge, so it never unglues from it. */
295
+ .zx-sheet[data-side="start"] { transform-origin: left center; }
296
+ .zx-sheet[data-side="end"] { transform-origin: right center; }
297
+ .zx-sheet[data-side="top"] { transform-origin: center top; }
298
+ .zx-sheet[data-side="bottom"] { transform-origin: center bottom; }
299
+
300
+ .zx-sheet[data-stack="stack"] {
301
+ transform:
302
+ translate(
303
+ calc(var(--zx-sheet-dx, 0) * var(--zx-sheet-depth, 0) * var(--zx-sheet-stack-offset, 24px)),
304
+ calc(var(--zx-sheet-dy, 0) * var(--zx-sheet-depth, 0) * var(--zx-sheet-stack-offset, 24px))
305
+ )
306
+ scale(calc(1 - var(--zx-sheet-depth, 0) * var(--zx-sheet-stack-scale, 0.04)));
307
+ }
308
+
309
+ /* A cascade moves each covered sheet clear of everything in front of it, so all stay readable. */
310
+ .zx-sheet[data-stack="cascade"] {
311
+ transform: translate(
312
+ calc(var(--zx-sheet-dx, 0) * var(--zx-sheet-depth-offset, 0px) * -1),
313
+ calc(var(--zx-sheet-dy, 0) * var(--zx-sheet-depth-offset, 0px) * -1)
314
+ );
315
+ }
316
+
317
+ /* Past `max` a sheet stays open and in the stack, but stops being drawn. */
318
+ .zx-sheet[data-stack-hidden] {
319
+ opacity: 0;
320
+ pointer-events: none;
321
+ }
322
+
323
+ /*
324
+ * Only the topmost backdrop shades the page — one per depth would compound into black.
325
+ */
326
+ .zx-sheet[data-depth]:not([data-depth="0"])::backdrop {
327
+ background: transparent;
328
+ backdrop-filter: none;
329
+ }
330
+
331
+ /*
332
+ * A cascade shades nothing at all. Its whole point is that the covered sheets stay readable and
333
+ * usable beside the top one, and a backdrop is painted directly beneath its own dialog in the top
334
+ * layer — so the topmost sheet's backdrop would dim exactly the sheets the layout exists to keep
335
+ * available. Pair a cascade with `modal: false` when the page behind should stay live too.
336
+ */
337
+ .zx-sheet[data-stack="cascade"]::backdrop {
338
+ background: transparent;
339
+ backdrop-filter: none;
340
+ }
341
+
342
+ @media (prefers-reduced-motion: no-preference) {
343
+ .zx-sheet[data-stack] {
344
+ transition:
345
+ transform var(--zx-dur-base) var(--zx-ease),
346
+ translate var(--zx-dur-base) var(--zx-ease),
347
+ opacity var(--zx-dur-base) var(--zx-ease),
348
+ display var(--zx-dur-base) allow-discrete,
349
+ overlay var(--zx-dur-base) allow-discrete;
350
+ }
351
+ }