@webority/theme 0.6.13 → 0.7.1

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.
@@ -1,3 +1,4 @@
1
+ // Component classes use the .wui-* prefix.
1
2
  // Modal, confirm dialog.
2
3
  //
3
4
  // Part of the wui-components layer — see _wui-components.scss for the whole
@@ -6,18 +7,18 @@
6
7
  // here may be overridden by a later partial. Never reorder the imports.
7
8
 
8
9
  // ── Modal ──
9
- // Chrome stays on `.lx-modal-*`. The shell is react-bootstrap <Modal>:
10
- // .modal.lx-modal-shell ← className (layout container)
11
- // .modal-backdrop.lx-modal-dim ← backdropClassName (dim only)
12
- // .modal-dialog.lx-rb-dialog ← dialogClassName
13
- // .modal-content.lx-modal ← contentClassName (the card)
10
+ // Chrome stays on `.wui-modal-*`. The shell is react-bootstrap <Modal>:
11
+ // .modal.wui-modal-shell ← className (layout container)
12
+ // .modal-backdrop.wui-modal-dim ← backdropClassName (dim only)
13
+ // .modal-dialog.wui-rb-dialog ← dialogClassName
14
+ // .modal-content.wui-modal ← contentClassName (the card)
14
15
  // Do NOT put layout on backdropClassName — that targets a sibling, not
15
16
  // .modal.
16
- .modal-backdrop.lx-modal-dim {
17
+ .modal-backdrop.wui-modal-dim {
17
18
  background: rgba(15, 23, 42, 0.45);
18
19
  z-index: 1500;
19
20
  }
20
- .modal.lx-modal-shell {
21
+ .modal.wui-modal-shell {
21
22
  --bs-modal-bg: transparent;
22
23
  align-items: center;
23
24
  justify-content: center;
@@ -36,11 +37,11 @@
36
37
  // react-bootstrap alike), which is what this keys on — it covers the whole opening
37
38
  // transition, not just the settled `.show` state. Specificity (0,3,0) beats `.modal`,
38
39
  // so no !important is needed.
39
- .modal.lx-modal-shell[style*="display: block"] {
40
+ .modal.wui-modal-shell[style*="display: block"] {
40
41
  display: flex;
41
42
  }
42
- // RB dialog shell: no Bootstrap max-width/margin so `.lx-modal` owns sizing.
43
- .modal.lx-modal-shell .modal-dialog.lx-rb-dialog {
43
+ // RB dialog shell: no Bootstrap max-width/margin so `.wui-modal` owns sizing.
44
+ .modal.wui-modal-shell .modal-dialog.wui-rb-dialog {
44
45
  margin: 0;
45
46
  max-width: none;
46
47
  width: auto;
@@ -49,7 +50,7 @@
49
50
  align-items: center;
50
51
  justify-content: center;
51
52
  }
52
- .modal.lx-modal-shell .modal-dialog.lx-rb-dialog .modal-content {
53
+ .modal.wui-modal-shell .modal-dialog.wui-rb-dialog .modal-content {
53
54
  pointer-events: auto;
54
55
  border: none;
55
56
  // Lift off the dim backdrop: a hairline ring defines the edge (carries
@@ -60,44 +61,44 @@
60
61
  var(--shadow-overlay-lg);
61
62
  background: var(--color-surface);
62
63
  }
63
- // `--lx-modal-max-width` is how a caller sets an explicit width. It is set on the
64
+ // `--wui-modal-max-width` is how a caller sets an explicit width. It is set on the
64
65
  // `.modal` shell by BOTH surfaces and inherits down to the card, because the card is
65
66
  // the element the width has to land on: `.modal-dialog` here is `width: auto`, so a
66
- // max-width there does nothing while `.lx-modal`'s own 440px still clamps the card.
67
+ // max-width there does nothing while `.wui-modal`'s own 440px still clamps the card.
67
68
  // React used to write the value straight onto `.modal-content` from JS and Razor put
68
69
  // it on `.modal-dialog`, so the same `maxWidth="800"` produced two different dialogs.
69
- .lx-modal {
70
+ .wui-modal {
70
71
  background: var(--color-surface);
71
72
  border-radius: var(--radius-xl);
72
73
  corner-shape: squircle;
73
74
  border: none;
74
75
  width: 100%;
75
- max-width: var(--lx-modal-max-width, 440px);
76
+ max-width: var(--wui-modal-max-width, 440px);
76
77
  max-height: calc(100vh - 40px);
77
78
  display: flex;
78
79
  flex-direction: column;
79
80
  overflow: hidden;
80
81
  }
81
- .lx-modal-wide {
82
- max-width: var(--lx-modal-max-width, 1240px);
82
+ .wui-modal-wide {
83
+ max-width: var(--wui-modal-max-width, 1240px);
83
84
  }
84
85
 
85
86
  // Side drawer — the dialog docks to the right edge at 30% of the viewport
86
87
  // and slides in, instead of sitting centred. Same chrome, different
87
88
  // geometry.
88
- .modal.lx-modal-shell.is-side {
89
+ .modal.wui-modal-shell.is-side {
89
90
  align-items: stretch;
90
91
  justify-content: flex-end;
91
92
  padding: 0;
92
93
  }
93
- .modal.lx-modal-shell.is-side .modal-dialog.lx-rb-dialog {
94
+ .modal.wui-modal-shell.is-side .modal-dialog.wui-rb-dialog {
94
95
  height: 100%;
95
96
  width: auto;
96
97
  max-width: none;
97
98
  align-items: stretch;
98
99
  justify-content: flex-end;
99
100
  }
100
- .lx-modal-side {
101
+ .wui-modal-side {
101
102
  width: 30vw;
102
103
  min-width: 420px;
103
104
  max-width: none;
@@ -105,19 +106,19 @@
105
106
  height: 100vh;
106
107
  border-radius: 0;
107
108
  corner-shape: normal;
108
- animation: lx-drawer-in 0.32s cubic-bezier(0.22, 1, 0.36, 1);
109
+ animation: wui-drawer-in 0.32s cubic-bezier(0.22, 1, 0.36, 1);
109
110
  }
110
111
  @media (max-width: 991.98px) {
111
- .lx-modal-side {
112
+ .wui-modal-side {
112
113
  width: 70vw;
113
114
  }
114
115
  }
115
116
  @media (max-width: 575.98px) {
116
- .lx-modal-side {
117
+ .wui-modal-side {
117
118
  width: 100vw;
118
119
  }
119
120
  }
120
- @keyframes lx-drawer-in {
121
+ @keyframes wui-drawer-in {
121
122
  from {
122
123
  transform: translateX(100%);
123
124
  }
@@ -126,11 +127,11 @@
126
127
  }
127
128
  }
128
129
  @media (prefers-reduced-motion: reduce) {
129
- .lx-modal-side {
130
+ .wui-modal-side {
130
131
  animation: none;
131
132
  }
132
133
  }
133
- .lx-modal-header {
134
+ .wui-modal-header {
134
135
  flex: 0 0 auto;
135
136
  display: flex;
136
137
  align-items: center;
@@ -139,7 +140,7 @@
139
140
  padding: 16px 20px;
140
141
  border-bottom: 1px solid var(--color-border);
141
142
  }
142
- .lx-modal-body {
143
+ .wui-modal-body {
143
144
  flex: 1 1 auto;
144
145
  min-height: 0;
145
146
  overflow-y: auto;
@@ -150,38 +151,38 @@
150
151
  scrollbar-color: var(--color-border-strong) transparent;
151
152
  padding: 20px 22px 24px;
152
153
  }
153
- .lx-modal-body::-webkit-scrollbar {
154
+ .wui-modal-body::-webkit-scrollbar {
154
155
  width: 8px;
155
156
  }
156
- .lx-modal-body::-webkit-scrollbar-track {
157
+ .wui-modal-body::-webkit-scrollbar-track {
157
158
  background: transparent;
158
159
  }
159
- .lx-modal-body::-webkit-scrollbar-thumb {
160
+ .wui-modal-body::-webkit-scrollbar-thumb {
160
161
  background: transparent;
161
162
  border-radius: 999px;
162
163
  border: 2px solid transparent;
163
164
  background-clip: padding-box;
164
165
  }
165
- .lx-modal-body:hover::-webkit-scrollbar-thumb {
166
+ .wui-modal-body:hover::-webkit-scrollbar-thumb {
166
167
  background: var(--color-border-strong);
167
168
  background-clip: padding-box;
168
169
  }
169
170
  @media (prefers-reduced-motion: reduce) {
170
- .lx-modal-body {
171
+ .wui-modal-body {
171
172
  scroll-behavior: auto;
172
173
  }
173
174
  }
174
175
  // Modal heading group: optional contextual (Bulk) icon tile + title/subtitle.
175
- .lx-modal-heading {
176
+ .wui-modal-heading {
176
177
  display: flex;
177
178
  align-items: center;
178
179
  gap: 10px;
179
180
  min-width: 0;
180
181
  }
181
- .lx-modal-headtext {
182
+ .wui-modal-headtext {
182
183
  min-width: 0;
183
184
  }
184
- .lx-modal-headicon {
185
+ .wui-modal-headicon {
185
186
  display: inline-flex;
186
187
  align-items: center;
187
188
  justify-content: center;
@@ -196,46 +197,46 @@
196
197
 
197
198
  // Break long unbroken names so they wrap within the heading instead of
198
199
  // running under the close button.
199
- .lx-modal-title {
200
+ .wui-modal-title {
200
201
  font-size: 20px;
201
202
  font-weight: 600;
202
203
  color: var(--color-text);
203
204
  overflow-wrap: anywhere;
204
205
  }
205
- .lx-modal-subtitle {
206
+ .wui-modal-subtitle {
206
207
  margin-top: 1px;
207
208
  font-size: 12px;
208
209
  font-weight: 400;
209
210
  color: var(--color-text-muted);
210
211
  overflow-wrap: anywhere;
211
212
  }
212
- .lx-form-section {
213
+ .wui-form-section {
213
214
  margin-top: 24px;
214
215
  }
215
- .lx-form-section:first-child {
216
+ .wui-form-section:first-child {
216
217
  margin-top: 0;
217
218
  }
218
219
  // Stretch controls to fill the column even though .field aligns to
219
220
  // flex-start.
220
- .lx-modal-body .field > .input,
221
- .lx-modal-body .field > .search-select,
222
- .lx-modal-body .field > .input-date-wrap,
223
- .lx-modal-body .field > .datepicker,
224
- .lx-modal-body .field > .phone-input-wrap,
225
- .lx-modal-body .field > .field-error {
221
+ .wui-modal-body .field > .input,
222
+ .wui-modal-body .field > .search-select,
223
+ .wui-modal-body .field > .input-date-wrap,
224
+ .wui-modal-body .field > .datepicker,
225
+ .wui-modal-body .field > .phone-input-wrap,
226
+ .wui-modal-body .field > .field-error {
226
227
  align-self: stretch;
227
228
  }
228
- .lx-form-section-head {
229
+ .wui-form-section-head {
229
230
  margin-bottom: 16px;
230
231
  }
231
- .lx-form-section-title {
232
+ .wui-form-section-title {
232
233
  font-size: 16px;
233
234
  font-weight: 600;
234
235
  text-transform: uppercase;
235
236
  letter-spacing: 0.04em;
236
237
  color: var(--color-text-subtle);
237
238
  }
238
- .lx-modal-footer {
239
+ .wui-modal-footer {
239
240
  flex: 0 0 auto;
240
241
  display: flex;
241
242
  align-items: center;
@@ -245,10 +246,11 @@
245
246
  border-top: 1px solid var(--color-border);
246
247
  }
247
248
 
248
- // Modal close — a squircle at rest that morphs into a circle on hover while
249
- // taking a danger tint, so dismissing reads as the destructive-ish gesture
250
- // it is. Slower on the way in than the way out.
251
- .lx-modal-close {
249
+ // Modal close — a steady rounded-square (squircle) that takes a danger tint on
250
+ // hover, so dismissing reads as the destructive-ish gesture it is. The corner is
251
+ // fixed across states: only the tint animates, so the button never morphs into a
252
+ // circle. Slower on the way in than the way out.
253
+ .wui-modal-close {
252
254
  margin-left: auto;
253
255
  display: grid;
254
256
  place-items: center;
@@ -261,32 +263,26 @@
261
263
  line-height: 1;
262
264
  background: var(--color-bg-subtle);
263
265
  color: var(--color-text-muted);
264
- border-radius: 999px;
266
+ border-radius: var(--radius-lg);
265
267
  corner-shape: squircle;
266
268
  transition:
267
269
  background 180ms cubic-bezier(0.4, 0, 0.2, 1),
268
- color 180ms cubic-bezier(0.4, 0, 0.2, 1),
269
- corner-shape 180ms cubic-bezier(0.4, 0, 0.2, 1);
270
+ color 180ms cubic-bezier(0.4, 0, 0.2, 1);
270
271
  }
271
- .lx-modal-close:hover {
272
+ .wui-modal-close:hover {
272
273
  background: var(--color-danger-soft);
273
274
  color: var(--color-danger-text);
274
- corner-shape: round;
275
275
  transition:
276
276
  background 280ms cubic-bezier(0.16, 1, 0.3, 1),
277
- color 280ms cubic-bezier(0.16, 1, 0.3, 1),
278
- corner-shape 280ms cubic-bezier(0.16, 1, 0.3, 1);
277
+ color 280ms cubic-bezier(0.16, 1, 0.3, 1);
279
278
  }
280
- .lx-modal-close:focus-visible {
279
+ .wui-modal-close:focus-visible {
281
280
  outline: 2px solid var(--color-primary);
282
281
  outline-offset: 2px;
283
282
  }
284
- // The shape morph is decorative; hold the colour cue for reduced-motion
285
- // users.
286
283
  @media (prefers-reduced-motion: reduce) {
287
- .lx-modal-close,
288
- .lx-modal-close:hover {
289
- corner-shape: squircle;
284
+ .wui-modal-close,
285
+ .wui-modal-close:hover {
290
286
  transition:
291
287
  background 1ms linear,
292
288
  color 1ms linear;
@@ -300,44 +296,44 @@
300
296
  // The confirm card's width belongs to the theme, not to every caller passing
301
297
  // maxWidth={440}. Both surfaces used to declare it and Razor's landed on the wrong
302
298
  // element, so the dialogs were different widths.
303
- .lx-confirm {
304
- max-width: var(--lx-modal-max-width, 440px);
299
+ .wui-confirm {
300
+ max-width: var(--wui-modal-max-width, 440px);
305
301
  }
306
- .lx-confirm-content {
302
+ .wui-confirm-content {
307
303
  display: flex;
308
304
  flex-direction: column;
309
305
  align-items: center;
310
306
  text-align: center;
311
307
  padding: 16px 12px 6px;
312
308
  }
313
- .lx-confirm-icon {
309
+ .wui-confirm-icon {
314
310
  line-height: 0;
315
311
  margin-bottom: 22px;
316
312
  }
317
- .lx-confirm-title {
313
+ .wui-confirm-title {
318
314
  margin: 0 0 10px;
319
315
  font-size: 22px;
320
316
  font-weight: 700;
321
317
  letter-spacing: -0.01em;
322
318
  color: var(--color-text);
323
319
  }
324
- .lx-confirm-msg {
320
+ .wui-confirm-msg {
325
321
  margin: 0;
326
322
  font-size: 15px;
327
323
  line-height: 1.55;
328
324
  color: var(--color-text-muted);
329
325
  max-width: 40ch;
330
326
  }
331
- .lx-confirm-actions {
327
+ .wui-confirm-actions {
332
328
  display: flex;
333
329
  gap: 12px;
334
330
  width: 100%;
335
331
  }
336
- .lx-modal-footer:has(.lx-confirm-actions) {
332
+ .wui-modal-footer:has(.wui-confirm-actions) {
337
333
  border-top: none;
338
334
  padding-top: 0;
339
335
  }
340
- .lx-confirm-actions .btn {
336
+ .wui-confirm-actions .btn {
341
337
  flex: 1;
342
338
  min-height: var(--wui-control-height);
343
339
  height: var(--wui-control-height);
@@ -1,3 +1,4 @@
1
+ // Component classes use the .wui-* prefix.
1
2
  // Text-scale utilities.
2
3
  //
3
4
  // Part of the wui-components layer — see _wui-components.scss for the whole
@@ -5,36 +6,36 @@
5
6
  // partials are a split of one stylesheet, not independent modules, so a rule
6
7
  // here may be overridden by a later partial. Never reorder the imports.
7
8
 
8
- // ── Text-scale utilities (lx-text-*) ──
9
- .lx-text-xs {
9
+ // ── Text-scale utilities (wui-text-*) ──
10
+ .wui-text-xs {
10
11
  font-size: 12px;
11
12
  line-height: 1.4;
12
13
  }
13
- .lx-text-sm {
14
+ .wui-text-sm {
14
15
  font-size: 13.5px;
15
16
  line-height: 1.5;
16
17
  }
17
- .lx-text-base {
18
+ .wui-text-base {
18
19
  font-size: 15px;
19
20
  line-height: 1.5;
20
21
  }
21
- .lx-text-lg {
22
+ .wui-text-lg {
22
23
  font-size: 17px;
23
24
  line-height: 1.4;
24
25
  }
25
- .lx-text-xl {
26
+ .wui-text-xl {
26
27
  font-size: 20px;
27
28
  line-height: 1.4;
28
29
  }
29
- .lx-text-2xl {
30
+ .wui-text-2xl {
30
31
  font-size: 24px;
31
32
  line-height: 1.3;
32
33
  }
33
- .lx-text-3xl {
34
+ .wui-text-3xl {
34
35
  font-size: 30px;
35
36
  line-height: 1.2;
36
37
  }
37
- .lx-text-4xl {
38
+ .wui-text-4xl {
38
39
  font-size: 36px;
39
40
  line-height: 1.15;
40
41
  }
@@ -1,3 +1,4 @@
1
+ // Component classes use the .wui-* prefix.
1
2
  // Grid utils, info tip, page header, row actions, spinner.
2
3
  //
3
4
  // Part of the wui-components layer — see _wui-components.scss for the whole
@@ -7,48 +8,48 @@
7
8
 
8
9
  // ── Grid / layout utils ──
9
10
  // Responsive card grids (Bootstrap has no grid-template utility).
10
- .lx-grid {
11
+ .wui-grid {
11
12
  display: grid;
12
13
  grid-template-columns: 1fr;
13
14
  }
14
- .lx-cols-2 {
15
+ .wui-cols-2 {
15
16
  grid-template-columns: repeat(2, minmax(0, 1fr));
16
17
  }
17
- .lx-cols-3 {
18
+ .wui-cols-3 {
18
19
  grid-template-columns: repeat(3, minmax(0, 1fr));
19
20
  }
20
- .lx-cols-4 {
21
+ .wui-cols-4 {
21
22
  grid-template-columns: repeat(4, minmax(0, 1fr));
22
23
  }
23
24
  @media (min-width: 768px) {
24
- .lx-grid-md-2 {
25
+ .wui-grid-md-2 {
25
26
  grid-template-columns: repeat(2, minmax(0, 1fr));
26
27
  }
27
- .lx-grid-md-3 {
28
+ .wui-grid-md-3 {
28
29
  grid-template-columns: repeat(3, minmax(0, 1fr));
29
30
  }
30
- .lx-grid-md-4 {
31
+ .wui-grid-md-4 {
31
32
  grid-template-columns: repeat(4, minmax(0, 1fr));
32
33
  }
33
34
  }
34
35
  @media (min-width: 992px) {
35
- .lx-grid-lg-2 {
36
+ .wui-grid-lg-2 {
36
37
  grid-template-columns: repeat(2, minmax(0, 1fr));
37
38
  }
38
- .lx-grid-lg-3 {
39
+ .wui-grid-lg-3 {
39
40
  grid-template-columns: repeat(3, minmax(0, 1fr));
40
41
  }
41
- .lx-grid-lg-4 {
42
+ .wui-grid-lg-4 {
42
43
  grid-template-columns: repeat(4, minmax(0, 1fr));
43
44
  }
44
45
  }
45
- .lx-col-span-2 {
46
+ .wui-col-span-2 {
46
47
  grid-column: span 2 / span 2;
47
48
  }
48
- .lx-col-span-3 {
49
+ .wui-col-span-3 {
49
50
  grid-column: span 3 / span 3;
50
51
  }
51
- .lx-col-span-full {
52
+ .wui-col-span-full {
52
53
  grid-column: 1 / -1;
53
54
  }
54
55
 
@@ -235,30 +236,30 @@
235
236
  }
236
237
 
237
238
  // ── Spinner / shimmer ──
238
- .lx-spinner {
239
+ .wui-spinner {
239
240
  width: 18px;
240
241
  height: 18px;
241
242
  border: 2.5px solid var(--color-border);
242
243
  border-top-color: var(--color-primary);
243
244
  border-radius: 999px;
244
- animation: lx-spin 0.7s linear infinite;
245
+ animation: wui-spin 0.7s linear infinite;
245
246
  display: inline-block;
246
247
  flex-shrink: 0;
247
248
  }
248
- @keyframes lx-spin {
249
+ @keyframes wui-spin {
249
250
  to {
250
251
  transform: rotate(360deg);
251
252
  }
252
253
  }
253
254
  // Small (14px) spinner variant.
254
- .lx-spinner-sm {
255
+ .wui-spinner-sm {
255
256
  width: 14px;
256
257
  height: 14px;
257
258
  border-width: 2px;
258
259
  }
259
260
  // Spinner for the Button loading state.
260
- .lx-spin {
261
- animation: lx-spin 0.8s linear infinite;
261
+ .wui-spin {
262
+ animation: wui-spin 0.8s linear infinite;
262
263
  }
263
264
 
264
265
  // Skeleton shimmer — used ONLY while loading the first data (loading &&