@plexui/styles 0.0.0-stage → 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.
Files changed (83) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +28 -2
  3. package/dist/es/components/Accordion/Accordion.module.css +89 -0
  4. package/dist/es/components/Alert/Alert.module.css +210 -0
  5. package/dist/es/components/Avatar/Avatar.module.css +168 -0
  6. package/dist/es/components/Avatar/AvatarGroup.module.css +26 -0
  7. package/dist/es/components/Badge/Badge.module.css +196 -0
  8. package/dist/es/components/Breadcrumb/Breadcrumb.module.css +59 -0
  9. package/dist/es/components/Button/Button.module.css +863 -0
  10. package/dist/es/components/ButtonGroup/ButtonGroup.module.css +158 -0
  11. package/dist/es/components/Card/Card.module.css +125 -0
  12. package/dist/es/components/Checkbox/Checkbox.module.css +225 -0
  13. package/dist/es/components/CodeBlock/CodeBlock.module.css +139 -0
  14. package/dist/es/components/DataTable/DataTable.module.css +117 -0
  15. package/dist/es/components/DatePicker/Calendar.module.css +271 -0
  16. package/dist/es/components/DateRangePicker/Calendar.module.css +295 -0
  17. package/dist/es/components/DateRangePicker/Trigger.module.css +25 -0
  18. package/dist/es/components/Dialog/Dialog.module.css +240 -0
  19. package/dist/es/components/EmptyMessage/EmptyMessage.module.css +116 -0
  20. package/dist/es/components/Field/Field.module.css +152 -0
  21. package/dist/es/components/FieldError/FieldError.module.css +28 -0
  22. package/dist/es/components/FileUpload/FileUpload.module.css +133 -0
  23. package/dist/es/components/FloatingLabelInput/FloatingLabelInput.module.css +220 -0
  24. package/dist/es/components/FloatingLabelSelect/FloatingLabelSelect.module.css +152 -0
  25. package/dist/es/components/Image/Image.module.css +9 -0
  26. package/dist/es/components/Indicator/CircularProgress.module.css +28 -0
  27. package/dist/es/components/Indicator/LoadingDots.module.css +35 -0
  28. package/dist/es/components/Indicator/LoadingIndicator.module.css +41 -0
  29. package/dist/es/components/Input/Input.module.css +519 -0
  30. package/dist/es/components/InputGroup/InputGroup.module.css +309 -0
  31. package/dist/es/components/Kbd/Kbd.module.css +47 -0
  32. package/dist/es/components/Label/Label.module.css +16 -0
  33. package/dist/es/components/Markdown/Markdown.module.css +233 -0
  34. package/dist/es/components/MarkdownEditor/MarkdownEditor.module.css +297 -0
  35. package/dist/es/components/Menu/Menu.module.css +386 -0
  36. package/dist/es/components/OTPInput/OTPInput.module.css +70 -0
  37. package/dist/es/components/Popover/Popover.module.css +82 -0
  38. package/dist/es/components/Progress/Progress.module.css +34 -0
  39. package/dist/es/components/ProgressSteps/ProgressSteps.module.css +246 -0
  40. package/dist/es/components/RadioGroup/RadioGroup.module.css +159 -0
  41. package/dist/es/components/Select/Select.module.css +338 -0
  42. package/dist/es/components/SelectControl/SelectControl.module.css +558 -0
  43. package/dist/es/components/Separator/Separator.module.css +16 -0
  44. package/dist/es/components/ShimmerText/ShimmerText.module.css +43 -0
  45. package/dist/es/components/Sidebar/Sidebar.module.css +913 -0
  46. package/dist/es/components/Skeleton/Skeleton.module.css +17 -0
  47. package/dist/es/components/Slider/Slider.module.css +199 -0
  48. package/dist/es/components/StatCard/StatCard.module.css +234 -0
  49. package/dist/es/components/Switch/Switch.module.css +121 -0
  50. package/dist/es/components/Table/Table.module.css +56 -0
  51. package/dist/es/components/Tabs/Tabs.module.css +688 -0
  52. package/dist/es/components/TagInput/TagInput.module.css +320 -0
  53. package/dist/es/components/TextLink/TextLink.module.css +50 -0
  54. package/dist/es/components/Textarea/Textarea.module.css +272 -0
  55. package/dist/es/components/Toast/Toast.module.css +99 -0
  56. package/dist/es/components/Tooltip/Tooltip.module.css +91 -0
  57. package/dist/es/components/Transition/Animate.module.css +54 -0
  58. package/dist/es/components/Transition/AnimateLayout.module.css +101 -0
  59. package/dist/es/components/Transition/AnimateLayoutGroup.module.css +88 -0
  60. package/dist/es/components/Transition/TransitionGroup.module.css +4 -0
  61. package/dist/es/styles/base.css +102 -0
  62. package/dist/es/styles/globals.css +50 -0
  63. package/dist/es/styles/index.css +22 -0
  64. package/dist/es/styles/katex.min.css +1296 -0
  65. package/dist/es/styles/tailwind-utilities.css +1316 -0
  66. package/dist/es/styles/variables-components.css +626 -0
  67. package/dist/es/styles/variables-primitive.css +327 -0
  68. package/dist/es/styles/variables-semantic.css +629 -0
  69. package/dist/es/styles/variables-tailwind-theme.css +34 -0
  70. package/dist/es/styles/variables-tokens-root.css +40 -0
  71. package/dist/es/types.js +4 -0
  72. package/dist/es/types.js.map +1 -0
  73. package/dist/es/vite/index.js +54 -0
  74. package/dist/es/vite/index.js.map +1 -0
  75. package/dist/types/types.d.ts +15 -0
  76. package/dist/types/vite/index.d.ts +55 -0
  77. package/package.json +109 -4
  78. package/postcss/functions.mjs +23 -0
  79. package/postcss/injectBreakpoints.mjs +47 -0
  80. package/postcss/mixins.mjs +100 -0
  81. package/postcss/parseLightDark.mjs +174 -0
  82. package/postcss/wrapModulesInLayer.mjs +21 -0
  83. package/postcss.config.mjs +52 -0
@@ -0,0 +1,240 @@
1
+ @layer components {.Transition {
2
+ position: relative;
3
+ }.Overlay {
4
+ position: fixed;
5
+ inset: 0;
6
+ z-index: 50;
7
+ background: rgb(0 0 0 / 0.5);
8
+ }
9
+
10
+ .Transition[data-entering] .Overlay {
11
+ opacity: 0;
12
+ }
13
+
14
+ .Transition[data-entering-active] .Overlay,
15
+ .Transition[data-entering][data-interrupted] .Overlay {
16
+ opacity: 1;
17
+ transition: opacity 0.2s var(--cubic-enter);
18
+ }
19
+
20
+ .Transition[data-exiting] .Overlay {
21
+ opacity: 1;
22
+ }
23
+
24
+ .Transition[data-exiting-active] .Overlay,
25
+ .Transition[data-exiting][data-interrupted] .Overlay {
26
+ opacity: 0;
27
+ transition: opacity 0.15s var(--cubic-exit);
28
+ }.Content {
29
+ /* Placement presets set these; the panel and this layer read them */
30
+ --dialog-content-align: center;
31
+ --dialog-content-justify: center;
32
+ --dialog-content-padding: 1rem;
33
+ --dialog-panel-width: var(--dialog-width, 480px);
34
+ --dialog-panel-height: auto;
35
+ --dialog-panel-max-height: calc(100dvh - 2rem);
36
+ --dialog-panel-radius: var(--radius-xl);
37
+ --dialog-panel-padding-bottom: 1.25rem;
38
+ --dialog-panel-hidden-transform: scale(0.95) translateY(8px);
39
+
40
+ position: fixed;
41
+ inset: 0;
42
+ z-index: 50;
43
+ display: flex;
44
+ align-items: var(--dialog-content-align);
45
+ justify-content: var(--dialog-content-justify);
46
+ padding: var(--dialog-content-padding);
47
+ /* The positioning layer covers the overlay: presses around the panel go
48
+ through to the overlay, outside the dialog, so they dismiss it.
49
+ !important beats the dismissable layer's inline pointer-events. */
50
+ pointer-events: none !important;
51
+ }
52
+
53
+ .Content:focus {
54
+ outline: none;
55
+ }.Panel {
56
+ position: relative;
57
+ display: flex;
58
+ flex-direction: column;
59
+ gap: 1rem;
60
+ width: var(--dialog-panel-width);
61
+ max-width: 100%;
62
+ height: var(--dialog-panel-height);
63
+ max-height: var(--dialog-panel-max-height);
64
+ overflow: auto;
65
+ border-radius: var(--dialog-panel-radius);
66
+ background: var(--color-surface-elevated);
67
+ box-shadow: var(--shadow-lg), var(--shadow-hairline);
68
+ padding: 1.25rem 1.25rem var(--dialog-panel-padding-bottom);
69
+ pointer-events: auto;
70
+ }
71
+
72
+ /* With a Body, only the body scrolls: the header and footer stay in view */
73
+ .Panel:has(> .Body) {
74
+ overflow: hidden;
75
+ }
76
+
77
+ .Transition[data-entering] .Panel {
78
+ opacity: 0;
79
+ transform: var(--dialog-panel-hidden-transform);
80
+ }
81
+
82
+ .Transition[data-entering-active] .Panel,
83
+ .Transition[data-entering][data-interrupted] .Panel {
84
+ opacity: 1;
85
+ transform: scale(1) translateY(0);
86
+ transition: opacity 0.25s var(--cubic-enter), transform 0.25s var(--cubic-enter);
87
+ }
88
+
89
+ .Transition[data-exiting] .Panel {
90
+ opacity: 1;
91
+ transform: scale(1) translateY(0);
92
+ }
93
+
94
+ .Transition[data-exiting-active] .Panel,
95
+ .Transition[data-exiting][data-interrupted] .Panel {
96
+ opacity: 0;
97
+ transform: var(--dialog-panel-hidden-transform);
98
+ transition: opacity 0.15s var(--cubic-exit), transform 0.15s var(--cubic-exit);
99
+ }/* =============================================
100
+ Placement: `placement` everywhere, `mobilePlacement` at 640px and below
101
+ ============================================= */.Content:where([data-placement="top"]) {
102
+ --dialog-content-align: flex-start;
103
+ --dialog-content-padding: min(12vh, 6rem) 1rem 1rem;
104
+ /* A tall panel ends 1rem above the bottom edge, like a centered one */
105
+ --dialog-panel-max-height: calc(100dvh - min(12vh, 6rem) - 1rem);
106
+ }.Content:where([data-placement="bottom"]) {
107
+ --dialog-content-align: flex-end;
108
+ --dialog-content-padding: 0;
109
+ --dialog-panel-width: 100%;
110
+ --dialog-panel-radius: var(--radius-xl) var(--radius-xl) 0 0;
111
+ --dialog-panel-padding-bottom: calc(1.25rem + env(safe-area-inset-bottom, 0px));
112
+ --dialog-panel-hidden-transform: translateY(100%);
113
+ }.Content:where([data-placement="start"], [data-placement="end"]) {
114
+ --dialog-content-align: stretch;
115
+ --dialog-content-padding: 0;
116
+ --dialog-panel-height: 100%;
117
+ --dialog-panel-max-height: none;
118
+ --dialog-panel-radius: 0;
119
+ --dialog-panel-padding-bottom: calc(1.25rem + env(safe-area-inset-bottom, 0px));
120
+ }.Content:where([data-placement="start"]) {
121
+ --dialog-content-justify: flex-start;
122
+ --dialog-panel-hidden-transform: translateX(-100%);
123
+ }.Content:where([data-placement="end"]) {
124
+ --dialog-content-justify: flex-end;
125
+ --dialog-panel-hidden-transform: translateX(100%);
126
+ }/* Right to left, start is the right edge: the panel slides in from there */.Content:where([data-placement="start"]:dir(rtl)) {
127
+ --dialog-panel-hidden-transform: translateX(100%);
128
+ }.Content:where([data-placement="end"]:dir(rtl)) {
129
+ --dialog-panel-hidden-transform: translateX(-100%);
130
+ }.Content:where([data-placement="fullscreen"]) {
131
+ --dialog-content-padding: 0;
132
+ --dialog-panel-width: 100%;
133
+ --dialog-panel-height: 100%;
134
+ --dialog-panel-max-height: none;
135
+ --dialog-panel-radius: 0;
136
+ --dialog-panel-padding-bottom: calc(1.25rem + env(safe-area-inset-bottom, 0px));
137
+ --dialog-panel-hidden-transform: translateY(8px);
138
+ }@media (width <= 640px) {
139
+ .Content:where([data-mobile-placement="center"]) {
140
+ --dialog-content-align: center;
141
+ --dialog-content-justify: center;
142
+ --dialog-content-padding: 1rem;
143
+ --dialog-panel-width: var(--dialog-width, 480px);
144
+ --dialog-panel-height: auto;
145
+ --dialog-panel-max-height: calc(100dvh - 2rem);
146
+ --dialog-panel-radius: var(--radius-xl);
147
+ --dialog-panel-padding-bottom: 1.25rem;
148
+ --dialog-panel-hidden-transform: scale(0.95) translateY(8px);
149
+ }
150
+
151
+ .Content:where([data-mobile-placement="bottom"]) {
152
+ --dialog-content-align: flex-end;
153
+ --dialog-content-justify: center;
154
+ --dialog-content-padding: 0;
155
+ --dialog-panel-width: 100%;
156
+ --dialog-panel-height: auto;
157
+ --dialog-panel-max-height: calc(100dvh - 2rem);
158
+ --dialog-panel-radius: var(--radius-xl) var(--radius-xl) 0 0;
159
+ --dialog-panel-padding-bottom: calc(1.25rem + env(safe-area-inset-bottom, 0px));
160
+ --dialog-panel-hidden-transform: translateY(100%);
161
+ }
162
+
163
+ .Content:where([data-mobile-placement="fullscreen"]) {
164
+ --dialog-content-align: center;
165
+ --dialog-content-justify: center;
166
+ --dialog-content-padding: 0;
167
+ --dialog-panel-width: 100%;
168
+ --dialog-panel-height: 100%;
169
+ --dialog-panel-max-height: none;
170
+ --dialog-panel-radius: 0;
171
+ --dialog-panel-padding-bottom: calc(1.25rem + env(safe-area-inset-bottom, 0px));
172
+ --dialog-panel-hidden-transform: translateY(8px);
173
+ }
174
+ }.CloseButton {
175
+ position: absolute;
176
+ top: 0.75rem;
177
+ right: 0.75rem;
178
+ display: inline-flex;
179
+ align-items: center;
180
+ justify-content: center;
181
+ width: 2rem;
182
+ height: 2rem;
183
+ border: 0;
184
+ border-radius: 0.5rem;
185
+ background: transparent;
186
+ color: var(--color-text-tertiary);
187
+ cursor: pointer;
188
+ transition: background-color 0.2s var(--cubic-enter), color 0.2s var(--cubic-enter);
189
+ }
190
+
191
+ .CloseButton:hover {
192
+ background: color-mix(in srgb, var(--color-text-tertiary) 12%, transparent);
193
+ color: var(--color-text);
194
+ }
195
+
196
+ .CloseButton:focus-visible {
197
+ outline: 2px solid var(--color-text);
198
+ outline-offset: 2px;
199
+ }.CloseIcon {
200
+ display: block;
201
+ }.Header {
202
+ display: flex;
203
+ flex-shrink: 0;
204
+ flex-direction: column;
205
+ gap: 0.25rem;
206
+ }/* The scrolling part between the header and the footer. It reaches the
207
+ panel's edges, so its scrollbar sits there and focus rings are not cut */.Body {
208
+ flex: 1 1 auto;
209
+ min-height: 0;
210
+ overflow-y: auto;
211
+ overscroll-behavior: contain;
212
+ margin-inline: -1.25rem;
213
+ padding: 2px 1.25rem;
214
+ }.Footer {
215
+ display: flex;
216
+ flex-shrink: 0;
217
+ justify-content: flex-end;
218
+ gap: 0.5rem;
219
+ }.Title {
220
+ margin: 0;
221
+ font-size: 1.125rem;
222
+ font-weight: 600;
223
+ line-height: 1.4;
224
+ color: var(--color-text);
225
+ }.Description {
226
+ margin: 0;
227
+ font-size: 0.875rem;
228
+ line-height: 1.5;
229
+ color: var(--color-text-secondary);
230
+ }@media (width <= 640px) {
231
+ .Footer {
232
+ flex-direction: column;
233
+ }
234
+
235
+ .Footer > * {
236
+ width: 100%;
237
+ --button-size: var(--control-size-lg);
238
+ }
239
+ }
240
+ }
@@ -0,0 +1,116 @@
1
+ @layer components {.EmptyMessage {
2
+ display: flex;
3
+ flex-direction: column;
4
+ align-items: center;
5
+ justify-content: center;
6
+ min-width: min(20rem, 100%);
7
+ }
8
+
9
+ .EmptyMessage[data-fill="static"] {
10
+ width: 100%;
11
+ height: 100%;
12
+ }
13
+
14
+ .EmptyMessage[data-fill="absolute"] {
15
+ position: absolute;
16
+ inset: 0;
17
+ }
18
+
19
+ /* Compact: a panel, a card section or an empty list */
20
+ .EmptyMessage[data-size="sm"] {
21
+ min-width: 0;
22
+ }
23
+
24
+ .EmptyMessage[data-size="sm"] .IconBadge {
25
+ --badge-size: 32px;
26
+ --icon-size: 20px;
27
+
28
+ margin-bottom: calc(var(--spacing) * 2);
29
+ }
30
+
31
+ .EmptyMessage[data-size="sm"] .Title {
32
+ margin-bottom: calc(var(--spacing) * 1);
33
+ font-size: var(--font-text-sm-size);
34
+ line-height: var(--font-text-sm-line-height);
35
+ letter-spacing: normal;
36
+ }
37
+
38
+ .EmptyMessage[data-size="sm"] .ActionRow {
39
+ margin-top: calc(var(--spacing) * 3);
40
+ }
41
+
42
+ /* Left-aligned, under a section heading */
43
+ .EmptyMessage[data-align="start"] {
44
+ align-items: flex-start;
45
+ min-width: 0;
46
+ }
47
+
48
+ .EmptyMessage[data-align="start"] .Title,
49
+ .EmptyMessage[data-align="start"] .Description {
50
+ text-align: start;
51
+ }.IconBadge {
52
+ --badge-size: 40px;
53
+ --icon-size: 24px;
54
+
55
+ display: flex;
56
+ align-items: center;
57
+ justify-content: center;
58
+ width: var(--badge-size);
59
+ height: var(--badge-size);
60
+ border-radius: var(--radius-md);
61
+ margin: 0 0 12px;
62
+ background: var(--badge-background-color);
63
+ color: var(--badge-text-color);
64
+ }
65
+
66
+ .IconBadge svg {
67
+ width: var(--icon-size);
68
+ height: var(--icon-size);
69
+ }
70
+
71
+ .IconBadge[data-size="sm"] {
72
+ --badge-size: 32px;
73
+ --icon-size: 20px;
74
+ }
75
+
76
+ .IconBadge[data-color="secondary"] {
77
+ --badge-background-color: var(--color-background-secondary-soft);
78
+ --badge-text-color: var(--color-text-secondary-soft);
79
+ }
80
+
81
+ .IconBadge[data-color="warning"] {
82
+ --badge-background-color: var(--color-background-warning-soft);
83
+ --badge-text-color: var(--color-text-warning-soft);
84
+ }
85
+
86
+ .IconBadge[data-color="danger"] {
87
+ --badge-background-color: var(--color-background-danger-soft);
88
+ --badge-text-color: var(--color-text-danger-soft);
89
+ }.Title {
90
+ margin: 0 0 calc(var(--spacing) * 2);
91
+ color: var(--color-text);
92
+ font-size: var(--font-heading-xs-size);
93
+ font-weight: var(--font-weight-semibold);
94
+ line-height: 1.25;
95
+ letter-spacing: var(--font-heading-xs-tracking);
96
+ text-align: center;
97
+ text-wrap: balance;
98
+ }
99
+
100
+ .Title:where([data-color="danger"]) {
101
+ color: var(--color-text-danger);
102
+ }
103
+
104
+ .Title:where([data-color="warning"]) {
105
+ color: var(--color-text-warning);
106
+ }.Description {
107
+ margin: 0;
108
+ color: var(--color-text-tertiary);
109
+ font-size: var(--font-text-sm-size);
110
+ line-height: var(--font-text-sm-line-height);
111
+ text-align: center;
112
+ text-wrap: pretty;
113
+ }.ActionRow {
114
+ margin-top: calc(var(--spacing) * 4);
115
+ }
116
+ }
@@ -0,0 +1,152 @@
1
+ @layer components {.Field {
2
+ display: flex;
3
+ flex-direction: column;
4
+ gap: var(--field-gap);
5
+
6
+ /* Override FieldError margins since Field controls spacing via gap */
7
+ --field-error-margin-top: 0;
8
+ --field-error-margin-bottom: 0;
9
+ --field-error-padding-inline: 0;
10
+ }/* =============================================
11
+ LabelGroup (label + description)
12
+ ============================================= */.LabelGroup {
13
+ display: flex;
14
+ flex-direction: column;
15
+ gap: var(--field-label-description-gap, 0px);
16
+ }/* =============================================
17
+ Content (control + error)
18
+ ============================================= */.Content {
19
+ display: flex;
20
+ flex-direction: column;
21
+ gap: var(--field-gap);
22
+ }/* =============================================
23
+ Horizontal orientation
24
+ ============================================= */.Field:where([data-orientation="horizontal"]) {
25
+ flex-direction: row;
26
+ align-items: flex-start;
27
+ }.Field:where([data-orientation="horizontal"]) .LabelGroup {
28
+ flex-shrink: 0;
29
+ width: var(--field-horizontal-label-width);
30
+ padding-top: var(--field-label-horizontal-offset);
31
+ }.Field:where([data-orientation="horizontal"]) .Content {
32
+ flex-shrink: 0;
33
+ width: var(--field-horizontal-control-width);
34
+ }/* =============================================
35
+ Sizes — shared properties (grouped)
36
+ ============================================= */.Field:where([data-size="3xs"]),
37
+ .Field:where([data-size="2xs"]) {
38
+ --field-gap: calc(var(--spacing) * 1);
39
+ --field-label-description-gap: 0px;
40
+ --field-label-font-size: var(--font-text-xs-size);
41
+ --field-label-line-height: var(--font-text-xs-line-height);
42
+ --field-description-font-size: var(--font-text-xs-size);
43
+ --field-description-line-height: var(--font-text-xs-line-height);
44
+
45
+ /* Scale error elements down for compact sizes */
46
+ --field-error-icon-size: 0.875rem; /* 14px */
47
+ --field-error-gap: calc(var(--spacing) * 1.5); /* 6px */
48
+ }.Field:where([data-size="xs"]),
49
+ .Field:where([data-size="sm"]) {
50
+ --field-gap: calc(var(--spacing) * 1.5);
51
+ --field-label-description-gap: 0px;
52
+ --field-label-font-size: var(--font-text-xs-size);
53
+ --field-label-line-height: var(--font-text-xs-line-height);
54
+ --field-description-font-size: var(--font-text-xs-size);
55
+ --field-description-line-height: var(--font-text-xs-line-height);
56
+
57
+ /* Scale error elements down for compact sizes */
58
+ --field-error-icon-size: 0.875rem; /* 14px */
59
+ --field-error-gap: calc(var(--spacing) * 1.5); /* 6px */
60
+ }.Field:where([data-size="md"]) {
61
+ --field-gap: calc(var(--spacing) * 1.5);
62
+ --field-label-description-gap: 0px;
63
+ --field-label-font-size: var(--font-text-sm-size);
64
+ --field-label-line-height: var(--font-text-sm-line-height);
65
+ --field-description-font-size: var(--font-text-xs-size);
66
+ --field-description-line-height: var(--font-text-xs-line-height);
67
+ }.Field:where([data-size="lg"]),
68
+ .Field:where([data-size="xl"]) {
69
+ --field-gap: calc(var(--spacing) * 1.5);
70
+ --field-label-description-gap: 0px;
71
+ --field-label-font-size: var(--font-text-sm-size);
72
+ --field-label-line-height: var(--font-text-sm-line-height);
73
+ --field-description-font-size: var(--font-text-xs-size);
74
+ --field-description-line-height: var(--font-text-xs-line-height);
75
+ }.Field:where([data-size="2xl"]),
76
+ .Field:where([data-size="3xl"]) {
77
+ --field-gap: calc(var(--spacing) * 1.5);
78
+ --field-label-description-gap: 0px;
79
+ --field-label-font-size: var(--font-text-md-size);
80
+ --field-label-line-height: var(--font-text-md-line-height);
81
+ --field-description-font-size: var(--font-text-sm-size);
82
+ --field-description-line-height: var(--font-text-sm-line-height);
83
+
84
+ /* Scale error elements up for spacious sizes */
85
+ --field-error-font-size: var(--font-text-sm-size); /* 14px */
86
+ --field-error-line-height: var(--font-text-sm-line-height); /* 20px */
87
+ --field-error-icon-size: 1.125rem; /* 18px */
88
+ }/* =============================================
89
+ Sizes — horizontal label offset (per-size)
90
+ Centers label text vertically with the input:
91
+ offset = (control-height − label-line-height) / 2
92
+ ============================================= */.Field:where([data-size="3xs"]) {
93
+ --field-label-horizontal-offset: calc((var(--control-size-3xs) - var(--font-text-xs-line-height)) / 2); /* 2px */
94
+ }.Field:where([data-size="2xs"]) {
95
+ --field-label-horizontal-offset: calc((var(--control-size-2xs) - var(--font-text-xs-line-height)) / 2); /* 3px */
96
+ }.Field:where([data-size="xs"]) {
97
+ --field-label-horizontal-offset: calc((var(--control-size-xs) - var(--font-text-xs-line-height)) / 2); /* 4px */
98
+ }.Field:where([data-size="sm"]) {
99
+ --field-label-horizontal-offset: calc((var(--control-size-sm) - var(--font-text-xs-line-height)) / 2); /* 5px */
100
+ }.Field:where([data-size="md"]) {
101
+ --field-label-horizontal-offset: calc((var(--control-size-md) - var(--font-text-sm-line-height)) / 2); /* 6px */
102
+ }.Field:where([data-size="lg"]) {
103
+ --field-label-horizontal-offset: calc((var(--control-size-lg) - var(--font-text-sm-line-height)) / 2); /* 8px */
104
+ }.Field:where([data-size="xl"]) {
105
+ --field-label-horizontal-offset: calc((var(--control-size-xl) - var(--font-text-sm-line-height)) / 2); /* 10px */
106
+ }.Field:where([data-size="2xl"]) {
107
+ --field-label-horizontal-offset: calc((var(--control-size-2xl) - var(--font-text-md-line-height)) / 2); /* 10px */
108
+ }.Field:where([data-size="3xl"]) {
109
+ --field-label-horizontal-offset: calc((var(--control-size-3xl) - var(--font-text-md-line-height)) / 2); /* 12px */
110
+ }/* =============================================
111
+ Label
112
+ ============================================= */.Label {
113
+ display: inline-flex;
114
+ align-items: baseline;
115
+ gap: calc(var(--spacing) * 0.5);
116
+ color: var(--color-text);
117
+ font-size: var(--field-label-font-size);
118
+ line-height: var(--field-label-line-height);
119
+ font-weight: var(--field-label-font-weight);
120
+ cursor: default;
121
+ }/* =============================================
122
+ Label row (label + labelAction)
123
+ ============================================= */.LabelRow {
124
+ display: flex;
125
+ align-items: baseline;
126
+ justify-content: space-between;
127
+ gap: calc(var(--spacing) * 2);
128
+ min-width: 0;
129
+ }.LabelAction {
130
+ display: inline-flex;
131
+ flex-shrink: 0;
132
+ align-items: baseline;
133
+ gap: calc(var(--spacing) * 2);
134
+ font-size: var(--field-label-font-size);
135
+ line-height: var(--field-label-line-height);
136
+ }/* =============================================
137
+ Required Indicator
138
+ ============================================= */.RequiredIndicator {
139
+ color: var(--field-error-color);
140
+ font-weight: var(--font-weight-normal);
141
+ }/* =============================================
142
+ Description
143
+ ============================================= */.Description {
144
+ color: var(--color-text-secondary);
145
+ font-size: var(--field-description-font-size);
146
+ line-height: var(--field-description-line-height);
147
+ }/* =============================================
148
+ Control
149
+ ============================================= */.Control {
150
+ /* Container for the child form control */
151
+ }
152
+ }
@@ -0,0 +1,28 @@
1
+ @layer components {.FieldError {
2
+ display: flex;
3
+ align-items: flex-start;
4
+ gap: var(--field-error-gap);
5
+ padding-inline-start: var(--field-error-padding-inline);
6
+ color: var(--field-error-color);
7
+ font-size: var(--field-error-font-size);
8
+ line-height: var(--field-error-line-height);
9
+ text-align: left;
10
+ }.FieldError:first-of-type {
11
+ margin-top: var(--field-error-margin-top);
12
+ }.FieldError:last-of-type {
13
+ margin-bottom: var(--field-error-margin-bottom);
14
+ }/* The icon keeps its size and sits on the first line; the text wraps, also
15
+ inside a long unbroken word, instead of pushing out of the field. */.FieldError > * {
16
+ flex-shrink: 0;
17
+ }.FieldError > span {
18
+ flex-shrink: 1;
19
+ min-width: 0;
20
+ overflow-wrap: anywhere;
21
+ }.Icon {
22
+ width: var(--field-error-icon-size);
23
+ height: var(--field-error-icon-size);
24
+ display: block;
25
+ align-self: flex-start;
26
+ margin-block-start: calc((var(--field-error-line-height) - var(--field-error-icon-size)) / 2);
27
+ }
28
+ }
@@ -0,0 +1,133 @@
1
+ @layer components {.Root {
2
+ position: relative;
3
+ --field-error-padding-inline: 0;
4
+ --field-error-margin-top: 0.25rem;
5
+ }.AreaTrigger {
6
+ display: flex;
7
+ flex-direction: column;
8
+ justify-content: center;
9
+ align-items: center;
10
+ width: 100%;
11
+ min-height: var(--file-upload-area-min-height);
12
+ padding: 2rem var(--file-upload-gutter);
13
+ gap: 0.5rem;
14
+ border: 1px solid var(--floating-input-border-color);
15
+ border-radius: var(--file-upload-area-border-radius);
16
+ background-color: var(--floating-input-background);
17
+ color: var(--color-text);
18
+ font-size: 1rem;
19
+ cursor: pointer;
20
+ transition: border-color var(--floating-input-transition-duration) ease-in-out;
21
+ }.AreaTrigger:hover:not(:disabled) {
22
+ border-color: var(--floating-input-border-color-hover);
23
+ }.AreaTrigger[data-invalid] {
24
+ border-color: var(--floating-input-border-color-invalid);
25
+ }.AreaTrigger:disabled {
26
+ opacity: 0.5;
27
+ cursor: not-allowed;
28
+ }.AreaIcon {
29
+ color: var(--color-text-tertiary);
30
+ font-size: 2rem;
31
+ }.AreaLabel {
32
+ font-weight: 500;
33
+ color: var(--color-text);
34
+ }.AreaDescription {
35
+ color: var(--color-text-tertiary);
36
+ font-size: 0.875rem;
37
+ }.FileList {
38
+ margin-top: var(--file-upload-list-gap);
39
+ list-style: none;
40
+ padding: 0;
41
+ overflow: hidden;
42
+ border: 1px solid var(--color-border-primary-outline);
43
+ border-radius: 26px;
44
+ }.FileCardGroup {
45
+ overflow: hidden;
46
+ border: 1px solid var(--color-border-primary-outline);
47
+ border-radius: 26px;
48
+ }.FileItem {
49
+ display: flex;
50
+ align-items: center;
51
+ gap: 10px;
52
+ padding: 12px 21px;
53
+ }.FileItem + .FileItem {
54
+ border-top: 1px solid var(--color-border-primary-outline);
55
+ }.FileList li + li > .FileItem {
56
+ border-top: 1px solid var(--color-border-primary-outline);
57
+ }.FileIcon {
58
+ display: flex;
59
+ flex-shrink: 0;
60
+ width: 16px;
61
+ height: 16px;
62
+ margin-left: -4px;
63
+ color: var(--input-text-color);
64
+ }.FileIcon svg {
65
+ width: 16px;
66
+ height: 16px;
67
+ }.FileInfo {
68
+ flex: 1;
69
+ min-width: 0;
70
+ display: flex;
71
+ flex-direction: column;
72
+ }.FileNameRow {
73
+ display: flex;
74
+ min-width: 0;
75
+ }.FileNameStem {
76
+ overflow: hidden;
77
+ text-overflow: ellipsis;
78
+ white-space: nowrap;
79
+ font-size: 14px;
80
+ line-height: 1.4285714286;
81
+ letter-spacing: -0.01em;
82
+ color: var(--color-text);
83
+ }.FileNameExt {
84
+ flex-shrink: 0;
85
+ font-size: 14px;
86
+ line-height: 1.4285714286;
87
+ letter-spacing: -0.01em;
88
+ color: var(--color-text);
89
+ }.FileSize {
90
+ font-size: 12px;
91
+ line-height: 1.5;
92
+ color: var(--color-text-tertiary);
93
+ }.FileRemove {
94
+ display: flex;
95
+ align-items: center;
96
+ justify-content: center;
97
+ width: 20px;
98
+ height: 20px;
99
+ padding: 0;
100
+ margin: 0 -7px 0 0;
101
+ border: none;
102
+ border-radius: var(--radius-full);
103
+ background-color: var(--color-background-secondary-soft-alpha);
104
+ cursor: pointer;
105
+ color: var(--color-text-secondary-soft);
106
+ flex-shrink: 0;
107
+ }.FileRemove svg {
108
+ width: 15px;
109
+ height: 15px;
110
+ }.FileRemove:hover {
111
+ background-color: var(--color-background-secondary-soft-alpha-hover);
112
+ }.FileRemove:active {
113
+ background-color: var(--color-background-secondary-soft-alpha-active);
114
+ }.FileRemove:disabled {
115
+ pointer-events: none;
116
+ }.HiddenInput {
117
+ position: absolute;
118
+ width: 1px;
119
+ height: 1px;
120
+ padding: 0;
121
+ margin: -1px;
122
+ overflow: hidden;
123
+ clip: rect(0, 0, 0, 0);
124
+ white-space: nowrap;
125
+ border-width: 0;
126
+ }.ErrorMessage {
127
+ margin-top: var(--field-error-margin-top);
128
+ }@media (prefers-reduced-motion: reduce) {
129
+ .AreaTrigger {
130
+ transition: none;
131
+ }
132
+ }
133
+ }