@crewlethq/ui 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +68 -0
- package/dist/Accordion-NIMJQIOI.css +88 -0
- package/dist/AppShell-ZW3NSFBP.css +51 -0
- package/dist/Avatar-V6NG6Q45.css +67 -0
- package/dist/Button-XGCTXXYP.css +174 -0
- package/dist/Callout-LEGDIMAM.css +52 -0
- package/dist/Card-BOZGBML7.css +86 -0
- package/dist/Checkbox-OCUICIIZ.css +58 -0
- package/dist/CodeBlock-IEMBNIQC.css +90 -0
- package/dist/Container-LTKBA2FW.css +21 -0
- package/dist/Copyable-IB57OTHZ.css +123 -0
- package/dist/DataTable-3GALZUW2.css +1593 -0
- package/dist/DateTimePicker-NMSSGVPK.css +312 -0
- package/dist/Eyebrow-AVBORAS2.css +30 -0
- package/dist/IconButton-GB4PJDG2.css +82 -0
- package/dist/ImageUpload-3HQDF2KC.css +158 -0
- package/dist/Input-ZHUTN7CU.css +210 -0
- package/dist/Kbd-Q77CDZY7.css +23 -0
- package/dist/Modal-FJVG66S4.css +138 -0
- package/dist/Popover-FUFULUE2.css +123 -0
- package/dist/PricingCard-NKYV3JHA.css +238 -0
- package/dist/Section-665ZIPG6.css +20 -0
- package/dist/Select-GPRF7PRB.css +294 -0
- package/dist/Skeleton-3WEFLRDN.css +378 -0
- package/dist/StatCard-RTJIVTRB.css +50 -0
- package/dist/Table-AR3TRY2E.css +89 -0
- package/dist/Tabs-XZ4JIH3E.css +153 -0
- package/dist/Tag-R5QDJLYJ.css +163 -0
- package/dist/TimeWindowPicker-L3G5Q7UT.css +629 -0
- package/dist/Toaster-2O65VOR4.css +264 -0
- package/dist/index.d.ts +1217 -0
- package/dist/index.js +4518 -0
- package/dist/styles.css +5842 -0
- package/package.json +58 -0
|
@@ -0,0 +1,312 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* DateTimePicker, a themed replacement for <input type="datetime-local">.
|
|
3
|
+
* Trigger borrows the Select trigger's geometry so a DateTimePicker
|
|
4
|
+
* and a Select line up in the same toolbar; the popover paints its
|
|
5
|
+
* own calendar grid + (optional) hour / minute inputs.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
/* The accent variables are declared on the trigger AND on the calendar
|
|
9
|
+
popover. The popover is portaled to <body>, so it inherits nothing
|
|
10
|
+
from the trigger; declaring them on the trigger alone leaves the
|
|
11
|
+
selected day, the focused time input and the primary footer button
|
|
12
|
+
resolving an undefined variable and painting transparent. Both read
|
|
13
|
+
the brand accent tokens, so an app retints the picker by rebinding
|
|
14
|
+
--color-brand-accent and --color-brand-accent-rgb on <body>. */
|
|
15
|
+
.crewlet-datetime,
|
|
16
|
+
.crewlet-datetime__popover {
|
|
17
|
+
--crewlet-datetime-accent: var(--color-brand-accent, #5469d4);
|
|
18
|
+
--crewlet-datetime-accent-rgb: var(--color-brand-accent-rgb, 84, 105, 212);
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
.crewlet-datetime {
|
|
22
|
+
width: 100%;
|
|
23
|
+
display: inline-flex;
|
|
24
|
+
align-items: center;
|
|
25
|
+
gap: 8px;
|
|
26
|
+
padding: 8px 10px 8px 12px;
|
|
27
|
+
background: var(--color-surface-elevated, #1f2128);
|
|
28
|
+
border: 1px solid var(--color-border-default, rgba(255, 255, 255, 0.1));
|
|
29
|
+
border-radius: 8px;
|
|
30
|
+
color: var(--color-text-primary, #f5f5f7);
|
|
31
|
+
font-family: inherit;
|
|
32
|
+
font-size: 13px;
|
|
33
|
+
text-align: left;
|
|
34
|
+
cursor: pointer;
|
|
35
|
+
transition: border-color 0.15s ease, box-shadow 0.15s ease;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
.crewlet-datetime--sm {
|
|
39
|
+
padding: 6px 8px 6px 10px;
|
|
40
|
+
font-size: 12px;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
.crewlet-datetime:hover:not(:disabled) {
|
|
44
|
+
border-color: var(--color-border-strong, rgba(255, 255, 255, 0.18));
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
.crewlet-datetime:focus,
|
|
48
|
+
.crewlet-datetime.is-open {
|
|
49
|
+
outline: none;
|
|
50
|
+
border-color: var(--crewlet-datetime-accent);
|
|
51
|
+
box-shadow: 0 0 0 3px rgba(var(--crewlet-datetime-accent-rgb), 0.15);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
.crewlet-datetime.is-disabled,
|
|
55
|
+
.crewlet-datetime:disabled {
|
|
56
|
+
opacity: 0.55;
|
|
57
|
+
cursor: not-allowed;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
.crewlet-datetime__icon {
|
|
61
|
+
font-size: 16px;
|
|
62
|
+
color: var(--color-text-secondary, #c9ced8);
|
|
63
|
+
flex-shrink: 0;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
.crewlet-datetime__label {
|
|
67
|
+
flex: 1;
|
|
68
|
+
min-width: 0;
|
|
69
|
+
overflow: hidden;
|
|
70
|
+
text-overflow: ellipsis;
|
|
71
|
+
white-space: nowrap;
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
.crewlet-datetime__label.is-placeholder {
|
|
75
|
+
color: var(--color-text-tertiary, #8c99ad);
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
.crewlet-datetime__chevron {
|
|
79
|
+
font-size: 18px;
|
|
80
|
+
color: var(--color-text-tertiary, #8c99ad);
|
|
81
|
+
flex-shrink: 0;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
/* ─── Popover panel ─────────────────────────────────────────── */
|
|
85
|
+
/*
|
|
86
|
+
* The base .crewlet-popover rule caps height at min(360px, 60vh) and
|
|
87
|
+
* scrolls overflow. The picker's content (quick-pick row + nav +
|
|
88
|
+
* weekday strip + 6-row grid + time inputs + footer) is taller than
|
|
89
|
+
* that, which made the time row sit below the scroll fold. Override
|
|
90
|
+
* max-height/max-width to none and disable inner scroll so every
|
|
91
|
+
* section is visible without scrolling.
|
|
92
|
+
*/
|
|
93
|
+
/*
|
|
94
|
+
* Popover matches the trigger width via Popover width="match" so the
|
|
95
|
+
* calendar lines up edge-for-edge with the input that opened it. The
|
|
96
|
+
* min-width floor keeps the calendar grid usable when the trigger
|
|
97
|
+
* sits inside a narrow cell (e.g. a form row); the explicit overrides
|
|
98
|
+
* lift the base Popover's max-height / max-width / overflow so the
|
|
99
|
+
* calendar, time row, and footer render in full.
|
|
100
|
+
*/
|
|
101
|
+
.crewlet-datetime__popover {
|
|
102
|
+
padding: 0;
|
|
103
|
+
background: var(--color-surface-subtle, var(--color-surface-elevated, #1c1e24));
|
|
104
|
+
border: 1px solid var(--color-border-default, rgba(255, 255, 255, 0.1));
|
|
105
|
+
border-radius: 10px;
|
|
106
|
+
box-shadow: var(--shadow-lg, 0 12px 28px rgba(0, 0, 0, 0.45));
|
|
107
|
+
overflow: visible;
|
|
108
|
+
min-width: 320px;
|
|
109
|
+
max-width: none;
|
|
110
|
+
max-height: none;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
.crewlet-datetime__panel {
|
|
114
|
+
display: flex;
|
|
115
|
+
flex-direction: column;
|
|
116
|
+
padding: 12px;
|
|
117
|
+
gap: 8px;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
|
|
121
|
+
/* ─── Month nav header ──────────────────────────────────────── */
|
|
122
|
+
.crewlet-datetime__nav {
|
|
123
|
+
display: flex;
|
|
124
|
+
align-items: center;
|
|
125
|
+
gap: 4px;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
.crewlet-datetime__nav-btn {
|
|
129
|
+
background: transparent;
|
|
130
|
+
border: 0;
|
|
131
|
+
color: var(--color-text-secondary, #c9ced8);
|
|
132
|
+
width: 28px;
|
|
133
|
+
height: 28px;
|
|
134
|
+
border-radius: 6px;
|
|
135
|
+
display: inline-flex;
|
|
136
|
+
align-items: center;
|
|
137
|
+
justify-content: center;
|
|
138
|
+
cursor: pointer;
|
|
139
|
+
transition: background 0.12s ease, color 0.12s ease;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
.crewlet-datetime__nav-btn:hover {
|
|
143
|
+
background: var(--color-surface-elevated, rgba(255, 255, 255, 0.08));
|
|
144
|
+
color: var(--color-text-primary, #fafafa);
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
.crewlet-datetime__nav-btn .material-symbols-outlined {
|
|
148
|
+
font-size: 18px;
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
.crewlet-datetime__title {
|
|
152
|
+
flex: 1;
|
|
153
|
+
text-align: center;
|
|
154
|
+
font-size: 13px;
|
|
155
|
+
font-weight: 600;
|
|
156
|
+
color: var(--color-text-primary, #fafafa);
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
/* ─── Weekday header strip ──────────────────────────────────── */
|
|
160
|
+
.crewlet-datetime__weekdays {
|
|
161
|
+
display: grid;
|
|
162
|
+
grid-template-columns: repeat(7, 1fr);
|
|
163
|
+
gap: 2px;
|
|
164
|
+
padding: 0 2px;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
.crewlet-datetime__weekday {
|
|
168
|
+
text-align: center;
|
|
169
|
+
font-size: 11px;
|
|
170
|
+
font-weight: 600;
|
|
171
|
+
color: var(--color-text-tertiary, #8c99ad);
|
|
172
|
+
text-transform: uppercase;
|
|
173
|
+
letter-spacing: 0.04em;
|
|
174
|
+
padding: 4px 0;
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
/* ─── Calendar grid ─────────────────────────────────────────── */
|
|
178
|
+
.crewlet-datetime__grid {
|
|
179
|
+
display: grid;
|
|
180
|
+
grid-template-columns: repeat(7, 1fr);
|
|
181
|
+
gap: 2px;
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
.crewlet-datetime__cell {
|
|
185
|
+
height: 32px;
|
|
186
|
+
background: transparent;
|
|
187
|
+
border: 0;
|
|
188
|
+
border-radius: 6px;
|
|
189
|
+
color: var(--color-text-primary, #fafafa);
|
|
190
|
+
font: inherit;
|
|
191
|
+
font-size: 12px;
|
|
192
|
+
cursor: pointer;
|
|
193
|
+
transition: background 0.1s ease, color 0.1s ease, border-color 0.1s ease;
|
|
194
|
+
display: inline-flex;
|
|
195
|
+
align-items: center;
|
|
196
|
+
justify-content: center;
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
.crewlet-datetime__cell:hover:not(:disabled):not(.is-selected) {
|
|
200
|
+
background: var(--color-surface-elevated, rgba(255, 255, 255, 0.08));
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
.crewlet-datetime__cell.is-outside {
|
|
204
|
+
color: var(--color-text-tertiary, #8c99ad);
|
|
205
|
+
opacity: 0.55;
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
.crewlet-datetime__cell.is-today:not(.is-selected) {
|
|
209
|
+
/* Subtle outline so today's cell is always findable even when no
|
|
210
|
+
date is picked. The accent inset keeps it visible on every surface. */
|
|
211
|
+
box-shadow: inset 0 0 0 1px rgba(var(--crewlet-datetime-accent-rgb), 0.55);
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
.crewlet-datetime__cell.is-selected {
|
|
215
|
+
background: var(--crewlet-datetime-accent);
|
|
216
|
+
color: #ffffff;
|
|
217
|
+
font-weight: 600;
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
.crewlet-datetime__cell.is-disabled,
|
|
221
|
+
.crewlet-datetime__cell:disabled {
|
|
222
|
+
opacity: 0.3;
|
|
223
|
+
cursor: not-allowed;
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
/* ─── Time row ──────────────────────────────────────────────── */
|
|
227
|
+
.crewlet-datetime__time {
|
|
228
|
+
display: flex;
|
|
229
|
+
align-items: center;
|
|
230
|
+
gap: 6px;
|
|
231
|
+
padding: 8px 4px 0;
|
|
232
|
+
border-top: 1px solid var(--color-border-default, rgba(255, 255, 255, 0.06));
|
|
233
|
+
margin-top: 4px;
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
.crewlet-datetime__time-label {
|
|
237
|
+
font-size: 11px;
|
|
238
|
+
font-weight: 600;
|
|
239
|
+
text-transform: uppercase;
|
|
240
|
+
letter-spacing: 0.04em;
|
|
241
|
+
color: var(--color-text-tertiary, #8c99ad);
|
|
242
|
+
margin-right: auto;
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
/*
|
|
246
|
+
* Hour / minute / second inputs render as type="text" so leading
|
|
247
|
+
* zeros stay visible ("00 : 00 : 00" instead of "0 : 0 : 0"). The
|
|
248
|
+
* inputMode + pattern attrs keep mobile keyboards numeric.
|
|
249
|
+
*/
|
|
250
|
+
.crewlet-datetime__time-input {
|
|
251
|
+
width: 36px;
|
|
252
|
+
background: var(--color-surface-elevated, #1f2128);
|
|
253
|
+
border: 1px solid var(--color-border-default, rgba(255, 255, 255, 0.1));
|
|
254
|
+
border-radius: 6px;
|
|
255
|
+
padding: 4px 6px;
|
|
256
|
+
font: inherit;
|
|
257
|
+
font-size: 13px;
|
|
258
|
+
font-variant-numeric: tabular-nums;
|
|
259
|
+
color: var(--color-text-primary, #fafafa);
|
|
260
|
+
text-align: center;
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
.crewlet-datetime__time-input:focus {
|
|
264
|
+
outline: none;
|
|
265
|
+
border-color: var(--crewlet-datetime-accent);
|
|
266
|
+
box-shadow: 0 0 0 2px rgba(var(--crewlet-datetime-accent-rgb), 0.18);
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
.crewlet-datetime__time-sep {
|
|
270
|
+
color: var(--color-text-tertiary, #8c99ad);
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
/* ─── Footer ────────────────────────────────────────────────── */
|
|
274
|
+
.crewlet-datetime__footer {
|
|
275
|
+
display: flex;
|
|
276
|
+
align-items: center;
|
|
277
|
+
gap: 4px;
|
|
278
|
+
padding-top: 8px;
|
|
279
|
+
border-top: 1px solid var(--color-border-default, rgba(255, 255, 255, 0.06));
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
.crewlet-datetime__footer-spacer {
|
|
283
|
+
flex: 1;
|
|
284
|
+
}
|
|
285
|
+
|
|
286
|
+
.crewlet-datetime__footer-btn {
|
|
287
|
+
background: transparent;
|
|
288
|
+
border: 0;
|
|
289
|
+
font: inherit;
|
|
290
|
+
font-size: 12px;
|
|
291
|
+
color: var(--color-text-secondary, #c9ced8);
|
|
292
|
+
cursor: pointer;
|
|
293
|
+
padding: 6px 10px;
|
|
294
|
+
border-radius: 6px;
|
|
295
|
+
transition: background 0.12s ease, color 0.12s ease;
|
|
296
|
+
}
|
|
297
|
+
|
|
298
|
+
.crewlet-datetime__footer-btn:hover {
|
|
299
|
+
background: var(--color-surface-elevated, rgba(255, 255, 255, 0.08));
|
|
300
|
+
color: var(--color-text-primary, #fafafa);
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
.crewlet-datetime__footer-btn.is-primary {
|
|
304
|
+
background: var(--crewlet-datetime-accent);
|
|
305
|
+
color: #ffffff;
|
|
306
|
+
font-weight: 600;
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
.crewlet-datetime__footer-btn.is-primary:hover {
|
|
310
|
+
background: var(--crewlet-datetime-accent);
|
|
311
|
+
filter: brightness(1.08);
|
|
312
|
+
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Eyebrow (kicker), the uppercase section label. Monospace, tracked-out,
|
|
3
|
+
* and quiet so it names a section without competing with its title.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
.crewlet-eyebrow {
|
|
7
|
+
display: inline-block;
|
|
8
|
+
font-family: var(--font-family-mono);
|
|
9
|
+
font-size: var(--font-size-xs);
|
|
10
|
+
font-weight: var(--font-weight-semibold);
|
|
11
|
+
letter-spacing: 0.14em;
|
|
12
|
+
text-transform: uppercase;
|
|
13
|
+
line-height: var(--font-line-height-tight);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
.crewlet-eyebrow--muted {
|
|
17
|
+
color: var(--color-text-tertiary);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
.crewlet-eyebrow--accent {
|
|
21
|
+
color: var(--color-brand-accent);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
.crewlet-eyebrow--gradient {
|
|
25
|
+
background: var(--color-brand-gradient);
|
|
26
|
+
-webkit-background-clip: text;
|
|
27
|
+
background-clip: text;
|
|
28
|
+
-webkit-text-fill-color: transparent;
|
|
29
|
+
color: transparent;
|
|
30
|
+
}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* IconButton, square icon-only affordance.
|
|
3
|
+
*
|
|
4
|
+
* Two square sizes: 22x22 fits inline beside a form label, and 28x28
|
|
5
|
+
* matches the min-height of a small Button. Variant accents use the brand accent (lavender) and the
|
|
6
|
+
* feedback-danger (rose) tokens.
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
.crewlet-icon-btn {
|
|
10
|
+
display: inline-flex;
|
|
11
|
+
align-items: center;
|
|
12
|
+
justify-content: center;
|
|
13
|
+
padding: 0;
|
|
14
|
+
background: transparent;
|
|
15
|
+
border: 1px solid transparent;
|
|
16
|
+
border-radius: 6px;
|
|
17
|
+
cursor: pointer;
|
|
18
|
+
line-height: 1;
|
|
19
|
+
flex-shrink: 0;
|
|
20
|
+
transition: background 0.15s ease, border-color 0.15s ease, color 0.15s ease;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
.crewlet-icon-btn:focus-visible {
|
|
24
|
+
outline: none;
|
|
25
|
+
box-shadow: var(--shadow-focus, 0 0 0 3px rgba(var(--color-brand-accent-rgb, 84, 105, 212), 0.32));
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
.crewlet-icon-btn:disabled {
|
|
29
|
+
opacity: 0.35;
|
|
30
|
+
cursor: not-allowed;
|
|
31
|
+
pointer-events: none;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
/* ── Sizes ──────────────────────────────────────────────────────── */
|
|
35
|
+
.crewlet-icon-btn--sm { width: 22px; height: 22px; }
|
|
36
|
+
.crewlet-icon-btn--md { width: 28px; height: 28px; }
|
|
37
|
+
|
|
38
|
+
/* The icon glyph inside scales with the button size. */
|
|
39
|
+
.crewlet-icon-btn--sm .material-symbols-outlined { font-size: 14px; }
|
|
40
|
+
.crewlet-icon-btn--md .material-symbols-outlined { font-size: 18px; }
|
|
41
|
+
|
|
42
|
+
/* ── ghost: transparent surface, neutral text, mild tint on hover ── */
|
|
43
|
+
.crewlet-icon-btn--ghost {
|
|
44
|
+
color: var(--color-text-secondary);
|
|
45
|
+
}
|
|
46
|
+
.crewlet-icon-btn--ghost:hover:not(:disabled) {
|
|
47
|
+
background: var(--color-surface-elevated, var(--color-surface-subtle));
|
|
48
|
+
color: var(--color-text-primary);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/* ── ghost-brand: transparent → lavender-soft on hover ─────────── */
|
|
52
|
+
.crewlet-icon-btn--ghost-brand {
|
|
53
|
+
color: var(--color-text-tertiary);
|
|
54
|
+
}
|
|
55
|
+
.crewlet-icon-btn--ghost-brand:hover:not(:disabled) {
|
|
56
|
+
background: var(--color-brand-accent-soft, rgba(84, 105, 212, 0.10));
|
|
57
|
+
border-color: var(--color-brand-accent-soft-strong, rgba(84, 105, 212, 0.32));
|
|
58
|
+
color: var(--color-brand-accent, #5469d4);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/* ── ghost-danger: transparent → rose-soft on hover ─────────────── */
|
|
62
|
+
.crewlet-icon-btn--ghost-danger {
|
|
63
|
+
color: var(--color-text-tertiary);
|
|
64
|
+
}
|
|
65
|
+
.crewlet-icon-btn--ghost-danger:hover:not(:disabled) {
|
|
66
|
+
background: rgba(244, 63, 94, 0.10);
|
|
67
|
+
color: var(--color-feedback-danger, #f43f5e);
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
/*
|
|
71
|
+
* ── soft-brand: lavender-tinted square with matching outline. The
|
|
72
|
+
* add affordance beside a form label (for example "Add a policy").
|
|
73
|
+
*/
|
|
74
|
+
.crewlet-icon-btn--soft-brand {
|
|
75
|
+
background: rgba(var(--color-brand-accent-rgb, 84, 105, 212), 0.12);
|
|
76
|
+
border-color: rgba(var(--color-brand-accent-rgb, 84, 105, 212), 0.3);
|
|
77
|
+
color: var(--color-brand-accent, #5469d4);
|
|
78
|
+
}
|
|
79
|
+
.crewlet-icon-btn--soft-brand:hover:not(:disabled) {
|
|
80
|
+
background: rgba(var(--color-brand-accent-rgb, 84, 105, 212), 0.22);
|
|
81
|
+
border-color: var(--color-brand-accent, #5469d4);
|
|
82
|
+
}
|
|
@@ -0,0 +1,158 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* ImageUpload, click-to-upload affordance built on Avatar.
|
|
3
|
+
*
|
|
4
|
+
* Colour properties go through the @crewlethq/tokens variables, with literal
|
|
5
|
+
* fallbacks so the control still renders when the token stylesheet has not
|
|
6
|
+
* loaded.
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
.crewlet-image-upload {
|
|
10
|
+
position: relative;
|
|
11
|
+
display: inline-flex;
|
|
12
|
+
flex-shrink: 0;
|
|
13
|
+
width: var(--crewlet-image-upload-size, 64px);
|
|
14
|
+
height: var(--crewlet-image-upload-size, 64px);
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
.crewlet-image-upload__trigger {
|
|
18
|
+
position: relative;
|
|
19
|
+
display: inline-flex;
|
|
20
|
+
width: 100%;
|
|
21
|
+
height: 100%;
|
|
22
|
+
padding: 0;
|
|
23
|
+
margin: 0;
|
|
24
|
+
border: none;
|
|
25
|
+
background: transparent;
|
|
26
|
+
cursor: pointer;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/* Shape modifiers keep the trigger, overlay, and Avatar corners in sync. */
|
|
30
|
+
.crewlet-image-upload--circle .crewlet-image-upload__trigger,
|
|
31
|
+
.crewlet-image-upload--circle .crewlet-image-upload__overlay {
|
|
32
|
+
border-radius: var(--radius-circle, 50%);
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
.crewlet-image-upload--square .crewlet-image-upload__trigger,
|
|
36
|
+
.crewlet-image-upload--square .crewlet-image-upload__overlay {
|
|
37
|
+
border-radius: var(--radius-lg, 12px);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
.crewlet-image-upload__trigger:disabled {
|
|
41
|
+
cursor: default;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
.crewlet-image-upload.is-uploading .crewlet-image-upload__trigger {
|
|
45
|
+
cursor: progress;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
.crewlet-image-upload__trigger:focus-visible {
|
|
49
|
+
outline: none;
|
|
50
|
+
box-shadow: var(--shadow-focus, 0 0 0 3px rgba(84, 105, 212, 0.32));
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
.crewlet-image-upload__overlay {
|
|
54
|
+
position: absolute;
|
|
55
|
+
inset: 0;
|
|
56
|
+
display: flex;
|
|
57
|
+
flex-direction: column;
|
|
58
|
+
align-items: center;
|
|
59
|
+
justify-content: center;
|
|
60
|
+
gap: 2px;
|
|
61
|
+
background: rgba(0, 0, 0, 0.5);
|
|
62
|
+
color: #ffffff;
|
|
63
|
+
opacity: 0;
|
|
64
|
+
transition: opacity 0.2s ease, background 0.15s ease;
|
|
65
|
+
pointer-events: none;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
.crewlet-image-upload__trigger:hover .crewlet-image-upload__overlay,
|
|
69
|
+
.crewlet-image-upload__trigger:focus-visible .crewlet-image-upload__overlay {
|
|
70
|
+
opacity: 1;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
.crewlet-image-upload.is-uploading .crewlet-image-upload__overlay,
|
|
74
|
+
.crewlet-image-upload.is-empty .crewlet-image-upload__overlay {
|
|
75
|
+
opacity: 1;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
.crewlet-image-upload__overlay .material-symbols-outlined {
|
|
79
|
+
font-size: calc(var(--crewlet-image-upload-size, 64px) * 0.28);
|
|
80
|
+
color: #ffffff;
|
|
81
|
+
transition: color 0.15s ease;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
.crewlet-image-upload__overlay-text {
|
|
85
|
+
font-size: 10px;
|
|
86
|
+
font-weight: 500;
|
|
87
|
+
color: rgba(255, 255, 255, 0.85);
|
|
88
|
+
transition: color 0.15s ease;
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
/* Hovering an editable control brightens the overlay: a deeper scrim with the
|
|
92
|
+
label and icon at full white, so a control whose overlay is already showing
|
|
93
|
+
(nothing uploaded yet) still answers the pointer. */
|
|
94
|
+
.crewlet-image-upload__trigger:hover:not(:disabled) .crewlet-image-upload__overlay {
|
|
95
|
+
background: rgba(0, 0, 0, 0.66);
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
.crewlet-image-upload__trigger:hover:not(:disabled) .crewlet-image-upload__overlay .material-symbols-outlined,
|
|
99
|
+
.crewlet-image-upload__trigger:hover:not(:disabled) .crewlet-image-upload__overlay-text {
|
|
100
|
+
color: #ffffff;
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
.crewlet-image-upload__spinner {
|
|
104
|
+
width: calc(var(--crewlet-image-upload-size, 64px) * 0.3);
|
|
105
|
+
height: calc(var(--crewlet-image-upload-size, 64px) * 0.3);
|
|
106
|
+
border-radius: 50%;
|
|
107
|
+
border: 2px solid rgba(255, 255, 255, 0.35);
|
|
108
|
+
border-top-color: #ffffff;
|
|
109
|
+
animation: crewlet-image-upload-spin 0.7s linear infinite;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
@keyframes crewlet-image-upload-spin {
|
|
113
|
+
to {
|
|
114
|
+
transform: rotate(360deg);
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
.crewlet-image-upload__remove {
|
|
119
|
+
position: absolute;
|
|
120
|
+
top: -6px;
|
|
121
|
+
right: -6px;
|
|
122
|
+
z-index: 2;
|
|
123
|
+
width: 20px;
|
|
124
|
+
height: 20px;
|
|
125
|
+
padding: 0;
|
|
126
|
+
display: flex;
|
|
127
|
+
align-items: center;
|
|
128
|
+
justify-content: center;
|
|
129
|
+
border-radius: 50%;
|
|
130
|
+
background: var(--color-feedback-danger, #f43f5e);
|
|
131
|
+
border: 2px solid var(--color-surface-background, #15171c);
|
|
132
|
+
color: #ffffff;
|
|
133
|
+
cursor: pointer;
|
|
134
|
+
opacity: 0;
|
|
135
|
+
transition: opacity 0.15s ease;
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
.crewlet-image-upload:hover .crewlet-image-upload__remove,
|
|
139
|
+
.crewlet-image-upload__remove:focus-visible {
|
|
140
|
+
opacity: 1;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
.crewlet-image-upload__remove:disabled {
|
|
144
|
+
cursor: default;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
.crewlet-image-upload__remove:focus-visible {
|
|
148
|
+
outline: none;
|
|
149
|
+
box-shadow: var(--shadow-focus, 0 0 0 3px rgba(84, 105, 212, 0.32));
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
.crewlet-image-upload__remove .material-symbols-outlined {
|
|
153
|
+
font-size: 12px;
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
.crewlet-image-upload__input {
|
|
157
|
+
display: none;
|
|
158
|
+
}
|