nexus-shared 3.1.0 → 3.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/CHANGELOG.md +704 -446
- package/LICENSE +21 -21
- package/README.md +44 -5
- package/dist/Client.Index.d.ts +3 -0
- package/dist/Client.Index.js +3 -0
- package/dist/Components/Forms/Crud.js +322 -161
- package/dist/Components/Forms/CrudHistory.d.ts +66 -0
- package/dist/Components/Forms/CrudHistory.js +140 -0
- package/dist/Components/Forms/CrudParts.js +2 -1
- package/dist/Components/Forms/Form.js +4 -1
- package/dist/Components/Inputs/CodeBox.d.ts +69 -0
- package/dist/Components/Inputs/CodeBox.js +316 -0
- package/dist/Components/Inputs/DatePicker.js +4 -1
- package/dist/Components/Inputs/DateRangePicker.js +4 -1
- package/dist/Components/Inputs/DateTimePicker.js +4 -1
- package/dist/Components/Inputs/Dropdown.js +4 -1
- package/dist/Components/Inputs/InputRenderer.js +3 -0
- package/dist/Components/Inputs/NumberBox.js +4 -2
- package/dist/Components/Inputs/TextArea.js +4 -1
- package/dist/Components/Inputs/TextBox.js +4 -1
- package/dist/Components/Inputs/TimePicker.js +4 -1
- package/dist/Components/Inputs/TreeView.d.ts +55 -5
- package/dist/Components/Inputs/TreeView.js +372 -23
- package/dist/Components/Layouts/ThemePicker.d.ts +3 -2
- package/dist/Components/Layouts/ThemePicker.js +16 -4
- package/dist/Components/Viewers/DataTable.js +63 -21
- package/dist/Components/Viewers/DataTableParts.d.ts +26 -8
- package/dist/Components/Viewers/DataTableParts.js +39 -10
- package/dist/Helpers/ApiModules.d.ts +3 -34
- package/dist/Helpers/ApiModules.js +3 -3
- package/dist/Helpers/ApiRoutes.d.ts +68 -26
- package/dist/Helpers/ApiRoutes.js +31 -27
- package/dist/Helpers/ArrayHelpers.d.ts +0 -0
- package/dist/Helpers/ArrayHelpers.js +2 -0
- package/dist/Helpers/CodeHelpers.d.ts +97 -0
- package/dist/Helpers/CodeHelpers.js +332 -0
- package/dist/Helpers/CrudBackend.d.ts +94 -4
- package/dist/Helpers/CrudBackend.js +168 -9
- package/dist/Helpers/CrudColumns.d.ts +51 -0
- package/dist/Helpers/CrudColumns.js +69 -0
- package/dist/Helpers/CrudHelpers.d.ts +50 -5
- package/dist/Helpers/CrudHelpers.js +109 -12
- package/dist/Helpers/InputParamsHelpers.js +8 -0
- package/dist/Helpers/MessageBuilder.js +2 -0
- package/dist/Helpers/NexusHelpers.d.ts +0 -0
- package/dist/Helpers/NexusHelpers.js +1 -0
- package/dist/Helpers/RequestCache.d.ts +35 -0
- package/dist/Helpers/RequestCache.js +113 -0
- package/dist/Helpers/TableExport.js +12 -12
- package/dist/Helpers/TableHelpers.d.ts +1 -1
- package/dist/Helpers/TableHelpers.js +7 -2
- package/dist/Helpers/TableJoins.d.ts +70 -0
- package/dist/Helpers/TableJoins.js +250 -0
- package/dist/Helpers/TableStore.d.ts +5 -0
- package/dist/Helpers/TableStore.js +9 -0
- package/dist/Helpers/TreeStore.d.ts +225 -11
- package/dist/Helpers/TreeStore.js +683 -90
- package/dist/Helpers/UserPreferences.d.ts +8 -0
- package/dist/Helpers/UserPreferences.js +17 -0
- package/dist/Interfaces/CrudInterfaces.d.ts +47 -9
- package/dist/Interfaces/FormInterfaces.d.ts +4 -1
- package/dist/Interfaces/InputInterfaces.d.ts +24 -0
- package/dist/Interfaces/MessageInterfaces.d.ts +1 -1
- package/dist/Interfaces/PreferenceInterfaces.d.ts +8 -0
- package/dist/Interfaces/PreferenceInterfaces.js +2 -5
- package/dist/Interfaces/TableInterfaces.d.ts +86 -4
- package/dist/Services/ApiProxy.d.ts +36 -1
- package/dist/Services/ApiProxy.js +182 -52
- package/dist/Services/ApiProxyRules.d.ts +203 -0
- package/dist/Services/ApiProxyRules.js +426 -0
- package/dist/Services/JoinSources.d.ts +48 -0
- package/dist/Services/JoinSources.js +74 -0
- package/dist/Services/ServerApi.d.ts +13 -2
- package/dist/Services/ServerApi.js +8 -3
- package/dist/Shared.Index.d.ts +4 -0
- package/dist/Shared.Index.js +4 -0
- package/package.json +87 -85
- package/src/Styles/Nexus.Avatar.css +79 -79
- package/src/Styles/Nexus.Base.css +117 -117
- package/src/Styles/Nexus.Button.css +180 -180
- package/src/Styles/Nexus.Calendar.css +273 -273
- package/src/Styles/Nexus.Chat.css +1443 -1443
- package/src/Styles/Nexus.Choice.css +343 -343
- package/src/Styles/Nexus.Crud.css +168 -168
- package/src/Styles/Nexus.DateTime.css +81 -81
- package/src/Styles/Nexus.Dropdown.css +725 -725
- package/src/Styles/Nexus.Editor.css +295 -295
- package/src/Styles/Nexus.Excel.css +389 -389
- package/src/Styles/Nexus.Form.css +279 -279
- package/src/Styles/Nexus.Index.css +37 -37
- package/src/Styles/Nexus.Input.css +196 -4
- package/src/Styles/Nexus.Markdown.css +237 -237
- package/src/Styles/Nexus.Menu.css +237 -237
- package/src/Styles/Nexus.Popup.css +724 -724
- package/src/Styles/Nexus.Rows.css +637 -637
- package/src/Styles/Nexus.Slider.css +276 -276
- package/src/Styles/Nexus.Tab.Buttons.css +432 -432
- package/src/Styles/Nexus.Table.css +31 -30
- package/src/Styles/Nexus.Theme.Picker.css +59 -3
- package/src/Styles/Nexus.Themes.css +194 -194
- package/src/Styles/Nexus.Time.css +144 -144
- package/src/Styles/Nexus.Toast.css +263 -263
- package/src/Styles/Nexus.Tokens.css +89 -89
- package/src/Styles/Nexus.Tree.css +500 -431
|
@@ -1,724 +1,724 @@
|
|
|
1
|
-
@layer nexus.components {
|
|
2
|
-
/*
|
|
3
|
-
* Popup: a native <dialog> shown modally. The panel is the dialog itself, so a click on the backdrop reaches the
|
|
4
|
-
* dialog element and nothing else. The header and footer stay while the body scrolls.
|
|
5
|
-
*/
|
|
6
|
-
.nx-popup {
|
|
7
|
-
--nx-popup-width: 560px;
|
|
8
|
-
|
|
9
|
-
/* Percentages, not vw: the viewport width here leaves out the scrollbar. */
|
|
10
|
-
width: min(var(--nx-popup-width), calc(100% - 32px));
|
|
11
|
-
max-width: none;
|
|
12
|
-
max-height: min(calc(100vh - 48px), calc(100dvh - 48px));
|
|
13
|
-
margin: auto;
|
|
14
|
-
padding: 0;
|
|
15
|
-
overflow: hidden;
|
|
16
|
-
border: 1px solid var(--nx-border);
|
|
17
|
-
border-radius: var(--nx-radius-lg);
|
|
18
|
-
background: var(--nx-surface);
|
|
19
|
-
color: var(--nx-text);
|
|
20
|
-
box-shadow: var(--nx-shadow);
|
|
21
|
-
outline: none;
|
|
22
|
-
/* Where the title bar moved it, from the center (set by the Popup while dragging). */
|
|
23
|
-
translate: var(--nx-popup-x, 0px) var(--nx-popup-y, 0px);
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
/*
|
|
27
|
-
* Opening and closing are a plain fade, the popup and its backdrop together: it appears where it stays, at the size
|
|
28
|
-
* it keeps, so nothing in it moves while it fades. Closing waits for its fade (`afterAnimation`), and takes no clicks
|
|
29
|
-
* meanwhile, so a double-click on Save does not submit twice; with animations off there is no fade to wait for.
|
|
30
|
-
*/
|
|
31
|
-
.nx-popup[open] {
|
|
32
|
-
display: flex;
|
|
33
|
-
flex-direction: column;
|
|
34
|
-
animation: nx-popup-in 160ms ease-out;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
.nx-popup::backdrop {
|
|
38
|
-
background: rgb(0 0 0 / 0.5);
|
|
39
|
-
animation: nx-popup-in 160ms ease-out;
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
.nx-popup--closing[open] {
|
|
43
|
-
animation: nx-popup-out 120ms ease-in forwards;
|
|
44
|
-
pointer-events: none;
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
.nx-popup--closing::backdrop {
|
|
48
|
-
animation: nx-popup-out 120ms ease-in forwards;
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
@keyframes nx-popup-in {
|
|
52
|
-
from {
|
|
53
|
-
opacity: 0;
|
|
54
|
-
}
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
@keyframes nx-popup-out {
|
|
58
|
-
to {
|
|
59
|
-
opacity: 0;
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
/* The page behind a modal popup stops scrolling; the Popup sets --nx-scrollbar-gap to the scrollbar's width, so nothing shifts. */
|
|
64
|
-
:root:has(.nx-popup:modal) {
|
|
65
|
-
overflow: hidden;
|
|
66
|
-
padding-right: var(--nx-scrollbar-gap, 0px);
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
/* Sizes */
|
|
70
|
-
.nx-popup--xs {
|
|
71
|
-
--nx-popup-width: 360px;
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
.nx-popup--sm {
|
|
75
|
-
--nx-popup-width: 440px;
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
.nx-popup--lg {
|
|
79
|
-
--nx-popup-width: 720px;
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
.nx-popup--xl {
|
|
83
|
-
--nx-popup-width: 960px;
|
|
84
|
-
}
|
|
85
|
-
|
|
86
|
-
.nx-popup--full {
|
|
87
|
-
--nx-popup-width: calc(100% - 32px);
|
|
88
|
-
|
|
89
|
-
height: calc(100vh - 32px);
|
|
90
|
-
max-height: none;
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
/* Maximized: the whole window, edge to edge, wherever it was moved. Two classes, to win over the sizes and phones. */
|
|
94
|
-
.nx-popup.nx-popup--maximized {
|
|
95
|
-
width: 100%;
|
|
96
|
-
height: 100%;
|
|
97
|
-
max-height: none;
|
|
98
|
-
border-width: 0;
|
|
99
|
-
border-radius: 0;
|
|
100
|
-
translate: none;
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
/* Minimizing: the page comes back while the popup flies to the dock. */
|
|
104
|
-
.nx-popup[data-nx-minimizing] {
|
|
105
|
-
pointer-events: none;
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
.nx-popup[data-nx-minimizing]::backdrop {
|
|
109
|
-
animation: nx-popup-out 200ms ease-in forwards;
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
/* Header, either design: the title bar moves the popup, so it selects no text and a touch drags instead of scrolling. */
|
|
113
|
-
.nx-popup__head {
|
|
114
|
-
display: flex;
|
|
115
|
-
flex-shrink: 0;
|
|
116
|
-
}
|
|
117
|
-
|
|
118
|
-
.nx-popup--movable .nx-popup__head {
|
|
119
|
-
cursor: move;
|
|
120
|
-
touch-action: none;
|
|
121
|
-
user-select: none;
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
.nx-popup__title,
|
|
125
|
-
.nx-popup__description {
|
|
126
|
-
margin: 0;
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
.nx-popup__controls {
|
|
130
|
-
display: flex;
|
|
131
|
-
flex-shrink: 0;
|
|
132
|
-
margin-left: auto;
|
|
133
|
-
}
|
|
134
|
-
|
|
135
|
-
.nx-popup__control {
|
|
136
|
-
display: grid;
|
|
137
|
-
place-items: center;
|
|
138
|
-
padding: 0;
|
|
139
|
-
border: 0;
|
|
140
|
-
background: none;
|
|
141
|
-
color: var(--nx-text-muted);
|
|
142
|
-
cursor: pointer;
|
|
143
|
-
transition:
|
|
144
|
-
background-color var(--nx-duration),
|
|
145
|
-
color var(--nx-duration);
|
|
146
|
-
}
|
|
147
|
-
|
|
148
|
-
.nx-popup__control .nx-icon {
|
|
149
|
-
vertical-align: 0;
|
|
150
|
-
}
|
|
151
|
-
|
|
152
|
-
/* Close turns red on hover, the one button that throws away what the popup holds. */
|
|
153
|
-
.nx-popup__close:hover {
|
|
154
|
-
background: var(--nx-danger-solid);
|
|
155
|
-
color: var(--nx-danger-text);
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
/*
|
|
159
|
-
* Window (the default): one low title bar, as on a desktop window. The icon and the title on the left, the
|
|
160
|
-
* description after the title in muted text, and the window buttons filling the top right corner.
|
|
161
|
-
*/
|
|
162
|
-
.nx-popup--window {
|
|
163
|
-
--nx-popup-bar: 32px;
|
|
164
|
-
}
|
|
165
|
-
|
|
166
|
-
.nx-popup--window .nx-popup__head {
|
|
167
|
-
box-sizing: content-box;
|
|
168
|
-
align-items: center;
|
|
169
|
-
gap: var(--nx-space-2);
|
|
170
|
-
height: var(--nx-popup-bar);
|
|
171
|
-
padding-left: var(--nx-space-3);
|
|
172
|
-
border-bottom: 1px solid var(--nx-border);
|
|
173
|
-
background: color-mix(in oklab, var(--nx-surface), var(--nx-text) 4%);
|
|
174
|
-
}
|
|
175
|
-
|
|
176
|
-
.nx-popup--window .nx-popup__icon {
|
|
177
|
-
display: grid;
|
|
178
|
-
flex-shrink: 0;
|
|
179
|
-
place-items: center;
|
|
180
|
-
color: var(--nx-primary);
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
.nx-popup--window .nx-popup__icon .nx-icon {
|
|
184
|
-
width: 16px;
|
|
185
|
-
height: 16px;
|
|
186
|
-
vertical-align: 0;
|
|
187
|
-
}
|
|
188
|
-
|
|
189
|
-
/* One line: the title keeps its room, the description takes what is left, and both end in … when cut. */
|
|
190
|
-
.nx-popup--window .nx-popup__heading {
|
|
191
|
-
display: flex;
|
|
192
|
-
flex: 1 1 auto;
|
|
193
|
-
align-items: baseline;
|
|
194
|
-
gap: var(--nx-space-2);
|
|
195
|
-
min-width: 0;
|
|
196
|
-
white-space: nowrap;
|
|
197
|
-
}
|
|
198
|
-
|
|
199
|
-
.nx-popup--window .nx-popup__title {
|
|
200
|
-
flex: 0 1 auto;
|
|
201
|
-
min-width: 0;
|
|
202
|
-
overflow: hidden;
|
|
203
|
-
font-size: var(--nx-text-sm);
|
|
204
|
-
font-weight: 600;
|
|
205
|
-
line-height: var(--nx-popup-bar);
|
|
206
|
-
text-overflow: ellipsis;
|
|
207
|
-
}
|
|
208
|
-
|
|
209
|
-
.nx-popup--window .nx-popup__description {
|
|
210
|
-
flex: 1 1 0;
|
|
211
|
-
min-width: 0;
|
|
212
|
-
overflow: hidden;
|
|
213
|
-
color: var(--nx-text-muted);
|
|
214
|
-
font-size: var(--nx-text-xs);
|
|
215
|
-
text-overflow: ellipsis;
|
|
216
|
-
}
|
|
217
|
-
|
|
218
|
-
.nx-popup--window .nx-popup__controls {
|
|
219
|
-
align-self: stretch;
|
|
220
|
-
}
|
|
221
|
-
|
|
222
|
-
.nx-popup--window .nx-popup__control {
|
|
223
|
-
width: 46px;
|
|
224
|
-
height: 100%;
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
.nx-popup--window .nx-popup__control:hover {
|
|
228
|
-
background: color-mix(in oklab, var(--nx-text) 9%, transparent);
|
|
229
|
-
color: var(--nx-text);
|
|
230
|
-
}
|
|
231
|
-
|
|
232
|
-
.nx-popup--window .nx-popup__control:active {
|
|
233
|
-
background: color-mix(in oklab, var(--nx-text) 15%, transparent);
|
|
234
|
-
}
|
|
235
|
-
|
|
236
|
-
.nx-popup--window .nx-popup__close:hover {
|
|
237
|
-
background: var(--nx-danger-solid);
|
|
238
|
-
color: var(--nx-danger-text);
|
|
239
|
-
}
|
|
240
|
-
|
|
241
|
-
.nx-popup--window .nx-popup__close:active {
|
|
242
|
-
background: var(--nx-danger-hover);
|
|
243
|
-
}
|
|
244
|
-
|
|
245
|
-
/* The buttons touch the popup's edges, where an outer ring would be cut off, so the ring is drawn inside. */
|
|
246
|
-
.nx-popup--window .nx-popup__control:focus-visible {
|
|
247
|
-
outline: none;
|
|
248
|
-
box-shadow: inset 0 0 0 2px var(--nx-primary);
|
|
249
|
-
}
|
|
250
|
-
|
|
251
|
-
/* Thin lines, as desktop window buttons have; the square glyphs fill more of their box, so they are drawn smaller. */
|
|
252
|
-
.nx-popup--window .nx-popup__control .nx-icon {
|
|
253
|
-
width: 16px;
|
|
254
|
-
height: 16px;
|
|
255
|
-
stroke-width: 1.5;
|
|
256
|
-
}
|
|
257
|
-
|
|
258
|
-
.nx-popup--window .nx-popup__maximize .nx-icon {
|
|
259
|
-
width: 13px;
|
|
260
|
-
height: 13px;
|
|
261
|
-
stroke-width: 1.75;
|
|
262
|
-
}
|
|
263
|
-
|
|
264
|
-
/* Touch screens get taller buttons. */
|
|
265
|
-
@media (pointer: coarse) {
|
|
266
|
-
.nx-popup--window {
|
|
267
|
-
--nx-popup-bar: 40px;
|
|
268
|
-
}
|
|
269
|
-
|
|
270
|
-
.nx-popup--window .nx-popup__control {
|
|
271
|
-
width: 48px;
|
|
272
|
-
}
|
|
273
|
-
}
|
|
274
|
-
|
|
275
|
-
/*
|
|
276
|
-
* Dialog (message boxes): a larger heading, the icon in a circle that carries the tone, the description under the
|
|
277
|
-
* title, and a small close button.
|
|
278
|
-
*/
|
|
279
|
-
.nx-popup--dialog .nx-popup__head {
|
|
280
|
-
align-items: flex-start;
|
|
281
|
-
gap: var(--nx-space-3);
|
|
282
|
-
padding: var(--nx-space-5) var(--nx-space-5) 0;
|
|
283
|
-
}
|
|
284
|
-
|
|
285
|
-
.nx-popup--dialog .nx-popup__icon {
|
|
286
|
-
display: grid;
|
|
287
|
-
flex-shrink: 0;
|
|
288
|
-
place-items: center;
|
|
289
|
-
width: 40px;
|
|
290
|
-
height: 40px;
|
|
291
|
-
border-radius: 50%;
|
|
292
|
-
background: var(--nx-primary-soft);
|
|
293
|
-
color: var(--nx-primary);
|
|
294
|
-
}
|
|
295
|
-
|
|
296
|
-
.nx-popup--dialog .nx-popup__icon .nx-icon {
|
|
297
|
-
width: 22px;
|
|
298
|
-
height: 22px;
|
|
299
|
-
vertical-align: 0;
|
|
300
|
-
}
|
|
301
|
-
|
|
302
|
-
.nx-popup--dialog .nx-popup__heading {
|
|
303
|
-
flex: 1 1 auto;
|
|
304
|
-
min-width: 0;
|
|
305
|
-
padding-top: 2px;
|
|
306
|
-
}
|
|
307
|
-
|
|
308
|
-
.nx-popup--dialog .nx-popup__title {
|
|
309
|
-
font-size: var(--nx-text-lg);
|
|
310
|
-
font-weight: 600;
|
|
311
|
-
line-height: 1.35;
|
|
312
|
-
overflow-wrap: anywhere;
|
|
313
|
-
}
|
|
314
|
-
|
|
315
|
-
.nx-popup--dialog .nx-popup__description {
|
|
316
|
-
margin-top: 4px;
|
|
317
|
-
color: var(--nx-text-muted);
|
|
318
|
-
font-size: var(--nx-text-sm);
|
|
319
|
-
line-height: 1.45;
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
.nx-popup--dialog .nx-popup__controls {
|
|
323
|
-
gap: 2px;
|
|
324
|
-
margin: -6px -8px 0 auto;
|
|
325
|
-
}
|
|
326
|
-
|
|
327
|
-
.nx-popup--dialog .nx-popup__control {
|
|
328
|
-
width: 30px;
|
|
329
|
-
height: 30px;
|
|
330
|
-
border-radius: var(--nx-radius);
|
|
331
|
-
}
|
|
332
|
-
|
|
333
|
-
.nx-popup--dialog .nx-popup__control:not(.nx-popup__close):hover {
|
|
334
|
-
background: var(--nx-surface-hover);
|
|
335
|
-
color: var(--nx-text);
|
|
336
|
-
}
|
|
337
|
-
|
|
338
|
-
.nx-popup--dialog .nx-popup__control:focus-visible {
|
|
339
|
-
outline: none;
|
|
340
|
-
box-shadow: var(--nx-focus-ring);
|
|
341
|
-
}
|
|
342
|
-
|
|
343
|
-
.nx-popup--dialog .nx-popup__control .nx-icon {
|
|
344
|
-
width: 18px;
|
|
345
|
-
height: 18px;
|
|
346
|
-
}
|
|
347
|
-
|
|
348
|
-
.nx-popup--dialog .nx-popup__maximize .nx-icon {
|
|
349
|
-
width: 15px;
|
|
350
|
-
height: 15px;
|
|
351
|
-
}
|
|
352
|
-
|
|
353
|
-
/* Body: scrolls when the content is taller than the window allows. */
|
|
354
|
-
.nx-popup__body {
|
|
355
|
-
flex: 1 1 auto;
|
|
356
|
-
min-height: 0;
|
|
357
|
-
padding: var(--nx-space-4) var(--nx-space-5) var(--nx-space-5);
|
|
358
|
-
overflow: auto;
|
|
359
|
-
overscroll-behavior: contain;
|
|
360
|
-
}
|
|
361
|
-
|
|
362
|
-
.nx-popup__head + .nx-popup__body:empty {
|
|
363
|
-
padding-top: var(--nx-space-2);
|
|
364
|
-
}
|
|
365
|
-
|
|
366
|
-
.nx-popup__body:only-child,
|
|
367
|
-
.nx-popup--window .nx-popup__body {
|
|
368
|
-
padding-top: var(--nx-space-5);
|
|
369
|
-
}
|
|
370
|
-
|
|
371
|
-
.nx-popup--flush .nx-popup__body {
|
|
372
|
-
padding: 0;
|
|
373
|
-
}
|
|
374
|
-
|
|
375
|
-
/* Footer: buttons at the end. */
|
|
376
|
-
.nx-popup__foot {
|
|
377
|
-
display: flex;
|
|
378
|
-
flex-shrink: 0;
|
|
379
|
-
flex-wrap: wrap;
|
|
380
|
-
align-items: center;
|
|
381
|
-
justify-content: flex-end;
|
|
382
|
-
gap: var(--nx-space-2);
|
|
383
|
-
padding: var(--nx-space-3) var(--nx-space-5);
|
|
384
|
-
border-top: 1px solid var(--nx-border);
|
|
385
|
-
}
|
|
386
|
-
|
|
387
|
-
/* A form's bar fills the foot, so its status line sits beside the buttons instead of on a row of its own. */
|
|
388
|
-
.nx-popup__foot > .nx-form-buttons {
|
|
389
|
-
flex: 1 1 auto;
|
|
390
|
-
}
|
|
391
|
-
|
|
392
|
-
/* Message boxes: a small popup whose icon carries the tone. */
|
|
393
|
-
.nx-popup--message .nx-popup__body {
|
|
394
|
-
padding-top: var(--nx-space-2);
|
|
395
|
-
}
|
|
396
|
-
|
|
397
|
-
.nx-popup--message .nx-popup__body:empty {
|
|
398
|
-
padding: var(--nx-space-3) 0 0;
|
|
399
|
-
}
|
|
400
|
-
|
|
401
|
-
.nx-message__text {
|
|
402
|
-
color: var(--nx-text-muted);
|
|
403
|
-
line-height: 1.5;
|
|
404
|
-
}
|
|
405
|
-
|
|
406
|
-
.nx-message__form {
|
|
407
|
-
display: grid;
|
|
408
|
-
gap: var(--nx-space-4);
|
|
409
|
-
}
|
|
410
|
-
|
|
411
|
-
.nx-popup--tone-info .nx-popup__icon {
|
|
412
|
-
background: var(--nx-info-soft);
|
|
413
|
-
color: var(--nx-info);
|
|
414
|
-
}
|
|
415
|
-
|
|
416
|
-
.nx-popup--tone-success .nx-popup__icon {
|
|
417
|
-
background: var(--nx-success-soft);
|
|
418
|
-
color: var(--nx-success);
|
|
419
|
-
}
|
|
420
|
-
|
|
421
|
-
.nx-popup--tone-warning .nx-popup__icon {
|
|
422
|
-
background: var(--nx-warning-soft);
|
|
423
|
-
color: var(--nx-warning);
|
|
424
|
-
}
|
|
425
|
-
|
|
426
|
-
.nx-popup--tone-danger .nx-popup__icon {
|
|
427
|
-
background: var(--nx-danger-soft);
|
|
428
|
-
color: var(--nx-danger);
|
|
429
|
-
}
|
|
430
|
-
|
|
431
|
-
/*
|
|
432
|
-
* The dock: minimized popups as bars at the bottom right. Several stack behind the newest, with cards peeking out
|
|
433
|
-
* above it and a count that opens the whole list. It sits on the page, so an open popup's backdrop covers it.
|
|
434
|
-
*/
|
|
435
|
-
.nx-dock {
|
|
436
|
-
--nx-dock-edge: 16px;
|
|
437
|
-
|
|
438
|
-
position: fixed;
|
|
439
|
-
right: calc(var(--nx-dock-edge) + env(safe-area-inset-right, 0px));
|
|
440
|
-
bottom: calc(var(--nx-dock-edge) + env(safe-area-inset-bottom, 0px));
|
|
441
|
-
z-index: 1000;
|
|
442
|
-
display: flex;
|
|
443
|
-
flex-direction: column;
|
|
444
|
-
align-items: flex-end;
|
|
445
|
-
gap: var(--nx-space-2);
|
|
446
|
-
width: min(300px, calc(100% - 2 * var(--nx-dock-edge)));
|
|
447
|
-
max-height: calc(100dvh - 2 * var(--nx-dock-edge));
|
|
448
|
-
/* Only the bars and the count take clicks, not the space between them. */
|
|
449
|
-
pointer-events: none;
|
|
450
|
-
}
|
|
451
|
-
|
|
452
|
-
.nx-dock > * {
|
|
453
|
-
pointer-events: auto;
|
|
454
|
-
}
|
|
455
|
-
|
|
456
|
-
/* While a popup locks the page, its scrollbar's space is padding; the dock keeps its place beside it. */
|
|
457
|
-
:root:has(.nx-popup:modal) .nx-dock {
|
|
458
|
-
right: calc(var(--nx-dock-edge) + var(--nx-scrollbar-gap, 0px) + env(safe-area-inset-right, 0px));
|
|
459
|
-
}
|
|
460
|
-
|
|
461
|
-
.nx-dock__toggle {
|
|
462
|
-
display: inline-flex;
|
|
463
|
-
flex-shrink: 0;
|
|
464
|
-
align-items: center;
|
|
465
|
-
gap: 6px;
|
|
466
|
-
height: 28px;
|
|
467
|
-
padding: 0 10px 0 4px;
|
|
468
|
-
border: 1px solid var(--nx-border);
|
|
469
|
-
border-radius: var(--nx-radius-full);
|
|
470
|
-
background: light-dark(var(--nx-surface), var(--nx-surface-2));
|
|
471
|
-
color: var(--nx-text);
|
|
472
|
-
box-shadow: var(--nx-shadow-sm);
|
|
473
|
-
font: inherit;
|
|
474
|
-
font-size: var(--nx-text-sm);
|
|
475
|
-
font-weight: 600;
|
|
476
|
-
cursor: pointer;
|
|
477
|
-
transition: background-color var(--nx-duration);
|
|
478
|
-
}
|
|
479
|
-
|
|
480
|
-
.nx-dock__toggle:hover {
|
|
481
|
-
background: var(--nx-surface-hover);
|
|
482
|
-
}
|
|
483
|
-
|
|
484
|
-
.nx-dock__toggle:focus-visible {
|
|
485
|
-
outline: none;
|
|
486
|
-
box-shadow: var(--nx-focus-ring);
|
|
487
|
-
}
|
|
488
|
-
|
|
489
|
-
.nx-dock__toggle .nx-icon {
|
|
490
|
-
width: 16px;
|
|
491
|
-
height: 16px;
|
|
492
|
-
color: var(--nx-text-muted);
|
|
493
|
-
}
|
|
494
|
-
|
|
495
|
-
.nx-dock__count {
|
|
496
|
-
display: grid;
|
|
497
|
-
place-items: center;
|
|
498
|
-
min-width: 20px;
|
|
499
|
-
height: 20px;
|
|
500
|
-
padding: 0 6px;
|
|
501
|
-
border-radius: var(--nx-radius-full);
|
|
502
|
-
background: var(--nx-primary-solid);
|
|
503
|
-
color: var(--nx-primary-text);
|
|
504
|
-
font-size: var(--nx-text-xs);
|
|
505
|
-
font-variant-numeric: tabular-nums;
|
|
506
|
-
line-height: 1;
|
|
507
|
-
}
|
|
508
|
-
|
|
509
|
-
.nx-dock__list {
|
|
510
|
-
position: relative;
|
|
511
|
-
isolation: isolate;
|
|
512
|
-
display: flex;
|
|
513
|
-
flex-direction: column;
|
|
514
|
-
gap: 6px;
|
|
515
|
-
width: 100%;
|
|
516
|
-
min-height: 0;
|
|
517
|
-
margin: 0;
|
|
518
|
-
padding: 0;
|
|
519
|
-
list-style: none;
|
|
520
|
-
}
|
|
521
|
-
|
|
522
|
-
/* Open: the whole list, oldest at the top; it scrolls when taller than the window, with room for the shadows. */
|
|
523
|
-
.nx-dock--open .nx-dock__list {
|
|
524
|
-
margin: -8px;
|
|
525
|
-
padding: 8px;
|
|
526
|
-
width: calc(100% + 16px);
|
|
527
|
-
overflow-y: auto;
|
|
528
|
-
overscroll-behavior: contain;
|
|
529
|
-
}
|
|
530
|
-
|
|
531
|
-
/* Stacked: one or two cards peek out above the newest bar; a click on them opens the list. */
|
|
532
|
-
.nx-dock__list[data-depth] {
|
|
533
|
-
margin-top: calc(var(--nx-dock-depth) * 5px);
|
|
534
|
-
cursor: pointer;
|
|
535
|
-
}
|
|
536
|
-
|
|
537
|
-
.nx-dock__list[data-depth="1"] {
|
|
538
|
-
--nx-dock-depth: 1;
|
|
539
|
-
}
|
|
540
|
-
|
|
541
|
-
.nx-dock__list[data-depth="2"] {
|
|
542
|
-
--nx-dock-depth: 2;
|
|
543
|
-
}
|
|
544
|
-
|
|
545
|
-
.nx-dock__list[data-depth]::before,
|
|
546
|
-
.nx-dock__list[data-depth="2"]::after {
|
|
547
|
-
content: "";
|
|
548
|
-
position: absolute;
|
|
549
|
-
top: -5px;
|
|
550
|
-
right: 8px;
|
|
551
|
-
left: 8px;
|
|
552
|
-
z-index: -1;
|
|
553
|
-
height: 24px;
|
|
554
|
-
border: 1px solid var(--nx-border);
|
|
555
|
-
border-radius: var(--nx-radius-lg);
|
|
556
|
-
background: light-dark(var(--nx-surface), var(--nx-surface-2));
|
|
557
|
-
box-shadow: var(--nx-shadow-sm);
|
|
558
|
-
}
|
|
559
|
-
|
|
560
|
-
.nx-dock__list[data-depth="2"]::after {
|
|
561
|
-
top: -10px;
|
|
562
|
-
right: 16px;
|
|
563
|
-
left: 16px;
|
|
564
|
-
z-index: -2;
|
|
565
|
-
}
|
|
566
|
-
|
|
567
|
-
.nx-dock__item {
|
|
568
|
-
display: flex;
|
|
569
|
-
flex-shrink: 0;
|
|
570
|
-
align-items: center;
|
|
571
|
-
gap: 2px;
|
|
572
|
-
height: 44px;
|
|
573
|
-
padding-right: 6px;
|
|
574
|
-
border: 1px solid var(--nx-border);
|
|
575
|
-
border-radius: var(--nx-radius-lg);
|
|
576
|
-
background: light-dark(var(--nx-surface), var(--nx-surface-2));
|
|
577
|
-
color: var(--nx-text);
|
|
578
|
-
box-shadow: var(--nx-shadow);
|
|
579
|
-
cursor: default;
|
|
580
|
-
transition: background-color var(--nx-duration);
|
|
581
|
-
animation: nx-dock-in 180ms cubic-bezier(0.2, 0, 0, 1);
|
|
582
|
-
}
|
|
583
|
-
|
|
584
|
-
.nx-dock__item:has(.nx-dock__window:hover) {
|
|
585
|
-
background: var(--nx-surface-hover);
|
|
586
|
-
}
|
|
587
|
-
|
|
588
|
-
.nx-dock__item:has(.nx-dock__window:focus-visible) {
|
|
589
|
-
box-shadow: var(--nx-focus-ring), var(--nx-shadow);
|
|
590
|
-
}
|
|
591
|
-
|
|
592
|
-
/* The bar's title part brings the popup back. */
|
|
593
|
-
.nx-dock__window {
|
|
594
|
-
display: flex;
|
|
595
|
-
flex: 1 1 auto;
|
|
596
|
-
align-items: center;
|
|
597
|
-
gap: 10px;
|
|
598
|
-
min-width: 0;
|
|
599
|
-
height: 100%;
|
|
600
|
-
padding: 0 6px 0 7px;
|
|
601
|
-
border: 0;
|
|
602
|
-
border-radius: inherit;
|
|
603
|
-
background: none;
|
|
604
|
-
color: inherit;
|
|
605
|
-
font: inherit;
|
|
606
|
-
text-align: start;
|
|
607
|
-
cursor: pointer;
|
|
608
|
-
}
|
|
609
|
-
|
|
610
|
-
.nx-dock__window:focus-visible {
|
|
611
|
-
outline: none;
|
|
612
|
-
}
|
|
613
|
-
|
|
614
|
-
.nx-dock__icon {
|
|
615
|
-
display: grid;
|
|
616
|
-
flex-shrink: 0;
|
|
617
|
-
place-items: center;
|
|
618
|
-
width: 28px;
|
|
619
|
-
height: 28px;
|
|
620
|
-
border-radius: var(--nx-radius);
|
|
621
|
-
background: var(--nx-primary-soft);
|
|
622
|
-
color: var(--nx-primary);
|
|
623
|
-
}
|
|
624
|
-
|
|
625
|
-
.nx-dock__icon .nx-icon {
|
|
626
|
-
width: 16px;
|
|
627
|
-
height: 16px;
|
|
628
|
-
vertical-align: 0;
|
|
629
|
-
}
|
|
630
|
-
|
|
631
|
-
.nx-dock__title {
|
|
632
|
-
flex: 1 1 auto;
|
|
633
|
-
min-width: 0;
|
|
634
|
-
overflow: hidden;
|
|
635
|
-
font-size: var(--nx-text-md);
|
|
636
|
-
font-weight: 600;
|
|
637
|
-
line-height: 1.3;
|
|
638
|
-
text-overflow: ellipsis;
|
|
639
|
-
white-space: nowrap;
|
|
640
|
-
}
|
|
641
|
-
|
|
642
|
-
.nx-dock__restore {
|
|
643
|
-
flex-shrink: 0;
|
|
644
|
-
width: 18px;
|
|
645
|
-
height: 18px;
|
|
646
|
-
color: var(--nx-text-muted);
|
|
647
|
-
}
|
|
648
|
-
|
|
649
|
-
.nx-dock__window:hover .nx-dock__restore {
|
|
650
|
-
color: var(--nx-text);
|
|
651
|
-
}
|
|
652
|
-
|
|
653
|
-
.nx-dock__close {
|
|
654
|
-
display: grid;
|
|
655
|
-
flex-shrink: 0;
|
|
656
|
-
place-items: center;
|
|
657
|
-
width: 30px;
|
|
658
|
-
height: 30px;
|
|
659
|
-
padding: 0;
|
|
660
|
-
border: 0;
|
|
661
|
-
border-radius: var(--nx-radius);
|
|
662
|
-
background: none;
|
|
663
|
-
color: var(--nx-text-muted);
|
|
664
|
-
cursor: pointer;
|
|
665
|
-
transition:
|
|
666
|
-
background-color var(--nx-duration),
|
|
667
|
-
color var(--nx-duration);
|
|
668
|
-
}
|
|
669
|
-
|
|
670
|
-
.nx-dock__close:hover {
|
|
671
|
-
background: var(--nx-danger-solid);
|
|
672
|
-
color: var(--nx-danger-text);
|
|
673
|
-
}
|
|
674
|
-
|
|
675
|
-
.nx-dock__close:focus-visible {
|
|
676
|
-
outline: none;
|
|
677
|
-
box-shadow: var(--nx-focus-ring);
|
|
678
|
-
}
|
|
679
|
-
|
|
680
|
-
.nx-dock__close .nx-icon {
|
|
681
|
-
width: 16px;
|
|
682
|
-
height: 16px;
|
|
683
|
-
vertical-align: 0;
|
|
684
|
-
}
|
|
685
|
-
|
|
686
|
-
@keyframes nx-dock-in {
|
|
687
|
-
from {
|
|
688
|
-
opacity: 0;
|
|
689
|
-
transform: translateY(8px);
|
|
690
|
-
}
|
|
691
|
-
}
|
|
692
|
-
|
|
693
|
-
@media (max-width: 600px) {
|
|
694
|
-
.nx-popup {
|
|
695
|
-
width: calc(100% - 16px);
|
|
696
|
-
max-height: min(calc(100vh - 16px), calc(100dvh - 16px));
|
|
697
|
-
}
|
|
698
|
-
|
|
699
|
-
.nx-popup--dialog .nx-popup__head {
|
|
700
|
-
padding: var(--nx-space-4) var(--nx-space-4) 0;
|
|
701
|
-
}
|
|
702
|
-
|
|
703
|
-
.nx-popup__body {
|
|
704
|
-
padding: var(--nx-space-3) var(--nx-space-4) var(--nx-space-4);
|
|
705
|
-
}
|
|
706
|
-
|
|
707
|
-
.nx-popup--window:not(.nx-popup--flush) .nx-popup__body {
|
|
708
|
-
padding-top: var(--nx-space-4);
|
|
709
|
-
}
|
|
710
|
-
|
|
711
|
-
.nx-popup__foot {
|
|
712
|
-
padding: var(--nx-space-3) var(--nx-space-4);
|
|
713
|
-
}
|
|
714
|
-
}
|
|
715
|
-
|
|
716
|
-
[data-nx-motion="reduce"] .nx-popup[open],
|
|
717
|
-
[data-nx-motion="reduce"] .nx-popup--closing[open],
|
|
718
|
-
[data-nx-motion="reduce"] .nx-popup::backdrop,
|
|
719
|
-
[data-nx-motion="reduce"] .nx-popup--closing::backdrop,
|
|
720
|
-
[data-nx-motion="reduce"] .nx-popup[data-nx-minimizing]::backdrop,
|
|
721
|
-
[data-nx-motion="reduce"] .nx-dock__item {
|
|
722
|
-
animation: none;
|
|
723
|
-
}
|
|
724
|
-
}
|
|
1
|
+
@layer nexus.components {
|
|
2
|
+
/*
|
|
3
|
+
* Popup: a native <dialog> shown modally. The panel is the dialog itself, so a click on the backdrop reaches the
|
|
4
|
+
* dialog element and nothing else. The header and footer stay while the body scrolls.
|
|
5
|
+
*/
|
|
6
|
+
.nx-popup {
|
|
7
|
+
--nx-popup-width: 560px;
|
|
8
|
+
|
|
9
|
+
/* Percentages, not vw: the viewport width here leaves out the scrollbar. */
|
|
10
|
+
width: min(var(--nx-popup-width), calc(100% - 32px));
|
|
11
|
+
max-width: none;
|
|
12
|
+
max-height: min(calc(100vh - 48px), calc(100dvh - 48px));
|
|
13
|
+
margin: auto;
|
|
14
|
+
padding: 0;
|
|
15
|
+
overflow: hidden;
|
|
16
|
+
border: 1px solid var(--nx-border);
|
|
17
|
+
border-radius: var(--nx-radius-lg);
|
|
18
|
+
background: var(--nx-surface);
|
|
19
|
+
color: var(--nx-text);
|
|
20
|
+
box-shadow: var(--nx-shadow);
|
|
21
|
+
outline: none;
|
|
22
|
+
/* Where the title bar moved it, from the center (set by the Popup while dragging). */
|
|
23
|
+
translate: var(--nx-popup-x, 0px) var(--nx-popup-y, 0px);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/*
|
|
27
|
+
* Opening and closing are a plain fade, the popup and its backdrop together: it appears where it stays, at the size
|
|
28
|
+
* it keeps, so nothing in it moves while it fades. Closing waits for its fade (`afterAnimation`), and takes no clicks
|
|
29
|
+
* meanwhile, so a double-click on Save does not submit twice; with animations off there is no fade to wait for.
|
|
30
|
+
*/
|
|
31
|
+
.nx-popup[open] {
|
|
32
|
+
display: flex;
|
|
33
|
+
flex-direction: column;
|
|
34
|
+
animation: nx-popup-in 160ms ease-out;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
.nx-popup::backdrop {
|
|
38
|
+
background: rgb(0 0 0 / 0.5);
|
|
39
|
+
animation: nx-popup-in 160ms ease-out;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
.nx-popup--closing[open] {
|
|
43
|
+
animation: nx-popup-out 120ms ease-in forwards;
|
|
44
|
+
pointer-events: none;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
.nx-popup--closing::backdrop {
|
|
48
|
+
animation: nx-popup-out 120ms ease-in forwards;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
@keyframes nx-popup-in {
|
|
52
|
+
from {
|
|
53
|
+
opacity: 0;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
@keyframes nx-popup-out {
|
|
58
|
+
to {
|
|
59
|
+
opacity: 0;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
/* The page behind a modal popup stops scrolling; the Popup sets --nx-scrollbar-gap to the scrollbar's width, so nothing shifts. */
|
|
64
|
+
:root:has(.nx-popup:modal) {
|
|
65
|
+
overflow: hidden;
|
|
66
|
+
padding-right: var(--nx-scrollbar-gap, 0px);
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
/* Sizes */
|
|
70
|
+
.nx-popup--xs {
|
|
71
|
+
--nx-popup-width: 360px;
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
.nx-popup--sm {
|
|
75
|
+
--nx-popup-width: 440px;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
.nx-popup--lg {
|
|
79
|
+
--nx-popup-width: 720px;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
.nx-popup--xl {
|
|
83
|
+
--nx-popup-width: 960px;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
.nx-popup--full {
|
|
87
|
+
--nx-popup-width: calc(100% - 32px);
|
|
88
|
+
|
|
89
|
+
height: calc(100vh - 32px);
|
|
90
|
+
max-height: none;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
/* Maximized: the whole window, edge to edge, wherever it was moved. Two classes, to win over the sizes and phones. */
|
|
94
|
+
.nx-popup.nx-popup--maximized {
|
|
95
|
+
width: 100%;
|
|
96
|
+
height: 100%;
|
|
97
|
+
max-height: none;
|
|
98
|
+
border-width: 0;
|
|
99
|
+
border-radius: 0;
|
|
100
|
+
translate: none;
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
/* Minimizing: the page comes back while the popup flies to the dock. */
|
|
104
|
+
.nx-popup[data-nx-minimizing] {
|
|
105
|
+
pointer-events: none;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
.nx-popup[data-nx-minimizing]::backdrop {
|
|
109
|
+
animation: nx-popup-out 200ms ease-in forwards;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
/* Header, either design: the title bar moves the popup, so it selects no text and a touch drags instead of scrolling. */
|
|
113
|
+
.nx-popup__head {
|
|
114
|
+
display: flex;
|
|
115
|
+
flex-shrink: 0;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
.nx-popup--movable .nx-popup__head {
|
|
119
|
+
cursor: move;
|
|
120
|
+
touch-action: none;
|
|
121
|
+
user-select: none;
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
.nx-popup__title,
|
|
125
|
+
.nx-popup__description {
|
|
126
|
+
margin: 0;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
.nx-popup__controls {
|
|
130
|
+
display: flex;
|
|
131
|
+
flex-shrink: 0;
|
|
132
|
+
margin-left: auto;
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
.nx-popup__control {
|
|
136
|
+
display: grid;
|
|
137
|
+
place-items: center;
|
|
138
|
+
padding: 0;
|
|
139
|
+
border: 0;
|
|
140
|
+
background: none;
|
|
141
|
+
color: var(--nx-text-muted);
|
|
142
|
+
cursor: pointer;
|
|
143
|
+
transition:
|
|
144
|
+
background-color var(--nx-duration),
|
|
145
|
+
color var(--nx-duration);
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
.nx-popup__control .nx-icon {
|
|
149
|
+
vertical-align: 0;
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
/* Close turns red on hover, the one button that throws away what the popup holds. */
|
|
153
|
+
.nx-popup__close:hover {
|
|
154
|
+
background: var(--nx-danger-solid);
|
|
155
|
+
color: var(--nx-danger-text);
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
/*
|
|
159
|
+
* Window (the default): one low title bar, as on a desktop window. The icon and the title on the left, the
|
|
160
|
+
* description after the title in muted text, and the window buttons filling the top right corner.
|
|
161
|
+
*/
|
|
162
|
+
.nx-popup--window {
|
|
163
|
+
--nx-popup-bar: 32px;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
.nx-popup--window .nx-popup__head {
|
|
167
|
+
box-sizing: content-box;
|
|
168
|
+
align-items: center;
|
|
169
|
+
gap: var(--nx-space-2);
|
|
170
|
+
height: var(--nx-popup-bar);
|
|
171
|
+
padding-left: var(--nx-space-3);
|
|
172
|
+
border-bottom: 1px solid var(--nx-border);
|
|
173
|
+
background: color-mix(in oklab, var(--nx-surface), var(--nx-text) 4%);
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
.nx-popup--window .nx-popup__icon {
|
|
177
|
+
display: grid;
|
|
178
|
+
flex-shrink: 0;
|
|
179
|
+
place-items: center;
|
|
180
|
+
color: var(--nx-primary);
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
.nx-popup--window .nx-popup__icon .nx-icon {
|
|
184
|
+
width: 16px;
|
|
185
|
+
height: 16px;
|
|
186
|
+
vertical-align: 0;
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
/* One line: the title keeps its room, the description takes what is left, and both end in … when cut. */
|
|
190
|
+
.nx-popup--window .nx-popup__heading {
|
|
191
|
+
display: flex;
|
|
192
|
+
flex: 1 1 auto;
|
|
193
|
+
align-items: baseline;
|
|
194
|
+
gap: var(--nx-space-2);
|
|
195
|
+
min-width: 0;
|
|
196
|
+
white-space: nowrap;
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
.nx-popup--window .nx-popup__title {
|
|
200
|
+
flex: 0 1 auto;
|
|
201
|
+
min-width: 0;
|
|
202
|
+
overflow: hidden;
|
|
203
|
+
font-size: var(--nx-text-sm);
|
|
204
|
+
font-weight: 600;
|
|
205
|
+
line-height: var(--nx-popup-bar);
|
|
206
|
+
text-overflow: ellipsis;
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
.nx-popup--window .nx-popup__description {
|
|
210
|
+
flex: 1 1 0;
|
|
211
|
+
min-width: 0;
|
|
212
|
+
overflow: hidden;
|
|
213
|
+
color: var(--nx-text-muted);
|
|
214
|
+
font-size: var(--nx-text-xs);
|
|
215
|
+
text-overflow: ellipsis;
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
.nx-popup--window .nx-popup__controls {
|
|
219
|
+
align-self: stretch;
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
.nx-popup--window .nx-popup__control {
|
|
223
|
+
width: 46px;
|
|
224
|
+
height: 100%;
|
|
225
|
+
}
|
|
226
|
+
|
|
227
|
+
.nx-popup--window .nx-popup__control:hover {
|
|
228
|
+
background: color-mix(in oklab, var(--nx-text) 9%, transparent);
|
|
229
|
+
color: var(--nx-text);
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
.nx-popup--window .nx-popup__control:active {
|
|
233
|
+
background: color-mix(in oklab, var(--nx-text) 15%, transparent);
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
.nx-popup--window .nx-popup__close:hover {
|
|
237
|
+
background: var(--nx-danger-solid);
|
|
238
|
+
color: var(--nx-danger-text);
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
.nx-popup--window .nx-popup__close:active {
|
|
242
|
+
background: var(--nx-danger-hover);
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
/* The buttons touch the popup's edges, where an outer ring would be cut off, so the ring is drawn inside. */
|
|
246
|
+
.nx-popup--window .nx-popup__control:focus-visible {
|
|
247
|
+
outline: none;
|
|
248
|
+
box-shadow: inset 0 0 0 2px var(--nx-primary);
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
/* Thin lines, as desktop window buttons have; the square glyphs fill more of their box, so they are drawn smaller. */
|
|
252
|
+
.nx-popup--window .nx-popup__control .nx-icon {
|
|
253
|
+
width: 16px;
|
|
254
|
+
height: 16px;
|
|
255
|
+
stroke-width: 1.5;
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
.nx-popup--window .nx-popup__maximize .nx-icon {
|
|
259
|
+
width: 13px;
|
|
260
|
+
height: 13px;
|
|
261
|
+
stroke-width: 1.75;
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
/* Touch screens get taller buttons. */
|
|
265
|
+
@media (pointer: coarse) {
|
|
266
|
+
.nx-popup--window {
|
|
267
|
+
--nx-popup-bar: 40px;
|
|
268
|
+
}
|
|
269
|
+
|
|
270
|
+
.nx-popup--window .nx-popup__control {
|
|
271
|
+
width: 48px;
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
/*
|
|
276
|
+
* Dialog (message boxes): a larger heading, the icon in a circle that carries the tone, the description under the
|
|
277
|
+
* title, and a small close button.
|
|
278
|
+
*/
|
|
279
|
+
.nx-popup--dialog .nx-popup__head {
|
|
280
|
+
align-items: flex-start;
|
|
281
|
+
gap: var(--nx-space-3);
|
|
282
|
+
padding: var(--nx-space-5) var(--nx-space-5) 0;
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
.nx-popup--dialog .nx-popup__icon {
|
|
286
|
+
display: grid;
|
|
287
|
+
flex-shrink: 0;
|
|
288
|
+
place-items: center;
|
|
289
|
+
width: 40px;
|
|
290
|
+
height: 40px;
|
|
291
|
+
border-radius: 50%;
|
|
292
|
+
background: var(--nx-primary-soft);
|
|
293
|
+
color: var(--nx-primary);
|
|
294
|
+
}
|
|
295
|
+
|
|
296
|
+
.nx-popup--dialog .nx-popup__icon .nx-icon {
|
|
297
|
+
width: 22px;
|
|
298
|
+
height: 22px;
|
|
299
|
+
vertical-align: 0;
|
|
300
|
+
}
|
|
301
|
+
|
|
302
|
+
.nx-popup--dialog .nx-popup__heading {
|
|
303
|
+
flex: 1 1 auto;
|
|
304
|
+
min-width: 0;
|
|
305
|
+
padding-top: 2px;
|
|
306
|
+
}
|
|
307
|
+
|
|
308
|
+
.nx-popup--dialog .nx-popup__title {
|
|
309
|
+
font-size: var(--nx-text-lg);
|
|
310
|
+
font-weight: 600;
|
|
311
|
+
line-height: 1.35;
|
|
312
|
+
overflow-wrap: anywhere;
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
.nx-popup--dialog .nx-popup__description {
|
|
316
|
+
margin-top: 4px;
|
|
317
|
+
color: var(--nx-text-muted);
|
|
318
|
+
font-size: var(--nx-text-sm);
|
|
319
|
+
line-height: 1.45;
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
.nx-popup--dialog .nx-popup__controls {
|
|
323
|
+
gap: 2px;
|
|
324
|
+
margin: -6px -8px 0 auto;
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
.nx-popup--dialog .nx-popup__control {
|
|
328
|
+
width: 30px;
|
|
329
|
+
height: 30px;
|
|
330
|
+
border-radius: var(--nx-radius);
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
.nx-popup--dialog .nx-popup__control:not(.nx-popup__close):hover {
|
|
334
|
+
background: var(--nx-surface-hover);
|
|
335
|
+
color: var(--nx-text);
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
.nx-popup--dialog .nx-popup__control:focus-visible {
|
|
339
|
+
outline: none;
|
|
340
|
+
box-shadow: var(--nx-focus-ring);
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
.nx-popup--dialog .nx-popup__control .nx-icon {
|
|
344
|
+
width: 18px;
|
|
345
|
+
height: 18px;
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
.nx-popup--dialog .nx-popup__maximize .nx-icon {
|
|
349
|
+
width: 15px;
|
|
350
|
+
height: 15px;
|
|
351
|
+
}
|
|
352
|
+
|
|
353
|
+
/* Body: scrolls when the content is taller than the window allows. */
|
|
354
|
+
.nx-popup__body {
|
|
355
|
+
flex: 1 1 auto;
|
|
356
|
+
min-height: 0;
|
|
357
|
+
padding: var(--nx-space-4) var(--nx-space-5) var(--nx-space-5);
|
|
358
|
+
overflow: auto;
|
|
359
|
+
overscroll-behavior: contain;
|
|
360
|
+
}
|
|
361
|
+
|
|
362
|
+
.nx-popup__head + .nx-popup__body:empty {
|
|
363
|
+
padding-top: var(--nx-space-2);
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
.nx-popup__body:only-child,
|
|
367
|
+
.nx-popup--window .nx-popup__body {
|
|
368
|
+
padding-top: var(--nx-space-5);
|
|
369
|
+
}
|
|
370
|
+
|
|
371
|
+
.nx-popup--flush .nx-popup__body {
|
|
372
|
+
padding: 0;
|
|
373
|
+
}
|
|
374
|
+
|
|
375
|
+
/* Footer: buttons at the end. */
|
|
376
|
+
.nx-popup__foot {
|
|
377
|
+
display: flex;
|
|
378
|
+
flex-shrink: 0;
|
|
379
|
+
flex-wrap: wrap;
|
|
380
|
+
align-items: center;
|
|
381
|
+
justify-content: flex-end;
|
|
382
|
+
gap: var(--nx-space-2);
|
|
383
|
+
padding: var(--nx-space-3) var(--nx-space-5);
|
|
384
|
+
border-top: 1px solid var(--nx-border);
|
|
385
|
+
}
|
|
386
|
+
|
|
387
|
+
/* A form's bar fills the foot, so its status line sits beside the buttons instead of on a row of its own. */
|
|
388
|
+
.nx-popup__foot > .nx-form-buttons {
|
|
389
|
+
flex: 1 1 auto;
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
/* Message boxes: a small popup whose icon carries the tone. */
|
|
393
|
+
.nx-popup--message .nx-popup__body {
|
|
394
|
+
padding-top: var(--nx-space-2);
|
|
395
|
+
}
|
|
396
|
+
|
|
397
|
+
.nx-popup--message .nx-popup__body:empty {
|
|
398
|
+
padding: var(--nx-space-3) 0 0;
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
.nx-message__text {
|
|
402
|
+
color: var(--nx-text-muted);
|
|
403
|
+
line-height: 1.5;
|
|
404
|
+
}
|
|
405
|
+
|
|
406
|
+
.nx-message__form {
|
|
407
|
+
display: grid;
|
|
408
|
+
gap: var(--nx-space-4);
|
|
409
|
+
}
|
|
410
|
+
|
|
411
|
+
.nx-popup--tone-info .nx-popup__icon {
|
|
412
|
+
background: var(--nx-info-soft);
|
|
413
|
+
color: var(--nx-info);
|
|
414
|
+
}
|
|
415
|
+
|
|
416
|
+
.nx-popup--tone-success .nx-popup__icon {
|
|
417
|
+
background: var(--nx-success-soft);
|
|
418
|
+
color: var(--nx-success);
|
|
419
|
+
}
|
|
420
|
+
|
|
421
|
+
.nx-popup--tone-warning .nx-popup__icon {
|
|
422
|
+
background: var(--nx-warning-soft);
|
|
423
|
+
color: var(--nx-warning);
|
|
424
|
+
}
|
|
425
|
+
|
|
426
|
+
.nx-popup--tone-danger .nx-popup__icon {
|
|
427
|
+
background: var(--nx-danger-soft);
|
|
428
|
+
color: var(--nx-danger);
|
|
429
|
+
}
|
|
430
|
+
|
|
431
|
+
/*
|
|
432
|
+
* The dock: minimized popups as bars at the bottom right. Several stack behind the newest, with cards peeking out
|
|
433
|
+
* above it and a count that opens the whole list. It sits on the page, so an open popup's backdrop covers it.
|
|
434
|
+
*/
|
|
435
|
+
.nx-dock {
|
|
436
|
+
--nx-dock-edge: 16px;
|
|
437
|
+
|
|
438
|
+
position: fixed;
|
|
439
|
+
right: calc(var(--nx-dock-edge) + env(safe-area-inset-right, 0px));
|
|
440
|
+
bottom: calc(var(--nx-dock-edge) + env(safe-area-inset-bottom, 0px));
|
|
441
|
+
z-index: 1000;
|
|
442
|
+
display: flex;
|
|
443
|
+
flex-direction: column;
|
|
444
|
+
align-items: flex-end;
|
|
445
|
+
gap: var(--nx-space-2);
|
|
446
|
+
width: min(300px, calc(100% - 2 * var(--nx-dock-edge)));
|
|
447
|
+
max-height: calc(100dvh - 2 * var(--nx-dock-edge));
|
|
448
|
+
/* Only the bars and the count take clicks, not the space between them. */
|
|
449
|
+
pointer-events: none;
|
|
450
|
+
}
|
|
451
|
+
|
|
452
|
+
.nx-dock > * {
|
|
453
|
+
pointer-events: auto;
|
|
454
|
+
}
|
|
455
|
+
|
|
456
|
+
/* While a popup locks the page, its scrollbar's space is padding; the dock keeps its place beside it. */
|
|
457
|
+
:root:has(.nx-popup:modal) .nx-dock {
|
|
458
|
+
right: calc(var(--nx-dock-edge) + var(--nx-scrollbar-gap, 0px) + env(safe-area-inset-right, 0px));
|
|
459
|
+
}
|
|
460
|
+
|
|
461
|
+
.nx-dock__toggle {
|
|
462
|
+
display: inline-flex;
|
|
463
|
+
flex-shrink: 0;
|
|
464
|
+
align-items: center;
|
|
465
|
+
gap: 6px;
|
|
466
|
+
height: 28px;
|
|
467
|
+
padding: 0 10px 0 4px;
|
|
468
|
+
border: 1px solid var(--nx-border);
|
|
469
|
+
border-radius: var(--nx-radius-full);
|
|
470
|
+
background: light-dark(var(--nx-surface), var(--nx-surface-2));
|
|
471
|
+
color: var(--nx-text);
|
|
472
|
+
box-shadow: var(--nx-shadow-sm);
|
|
473
|
+
font: inherit;
|
|
474
|
+
font-size: var(--nx-text-sm);
|
|
475
|
+
font-weight: 600;
|
|
476
|
+
cursor: pointer;
|
|
477
|
+
transition: background-color var(--nx-duration);
|
|
478
|
+
}
|
|
479
|
+
|
|
480
|
+
.nx-dock__toggle:hover {
|
|
481
|
+
background: var(--nx-surface-hover);
|
|
482
|
+
}
|
|
483
|
+
|
|
484
|
+
.nx-dock__toggle:focus-visible {
|
|
485
|
+
outline: none;
|
|
486
|
+
box-shadow: var(--nx-focus-ring);
|
|
487
|
+
}
|
|
488
|
+
|
|
489
|
+
.nx-dock__toggle .nx-icon {
|
|
490
|
+
width: 16px;
|
|
491
|
+
height: 16px;
|
|
492
|
+
color: var(--nx-text-muted);
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
.nx-dock__count {
|
|
496
|
+
display: grid;
|
|
497
|
+
place-items: center;
|
|
498
|
+
min-width: 20px;
|
|
499
|
+
height: 20px;
|
|
500
|
+
padding: 0 6px;
|
|
501
|
+
border-radius: var(--nx-radius-full);
|
|
502
|
+
background: var(--nx-primary-solid);
|
|
503
|
+
color: var(--nx-primary-text);
|
|
504
|
+
font-size: var(--nx-text-xs);
|
|
505
|
+
font-variant-numeric: tabular-nums;
|
|
506
|
+
line-height: 1;
|
|
507
|
+
}
|
|
508
|
+
|
|
509
|
+
.nx-dock__list {
|
|
510
|
+
position: relative;
|
|
511
|
+
isolation: isolate;
|
|
512
|
+
display: flex;
|
|
513
|
+
flex-direction: column;
|
|
514
|
+
gap: 6px;
|
|
515
|
+
width: 100%;
|
|
516
|
+
min-height: 0;
|
|
517
|
+
margin: 0;
|
|
518
|
+
padding: 0;
|
|
519
|
+
list-style: none;
|
|
520
|
+
}
|
|
521
|
+
|
|
522
|
+
/* Open: the whole list, oldest at the top; it scrolls when taller than the window, with room for the shadows. */
|
|
523
|
+
.nx-dock--open .nx-dock__list {
|
|
524
|
+
margin: -8px;
|
|
525
|
+
padding: 8px;
|
|
526
|
+
width: calc(100% + 16px);
|
|
527
|
+
overflow-y: auto;
|
|
528
|
+
overscroll-behavior: contain;
|
|
529
|
+
}
|
|
530
|
+
|
|
531
|
+
/* Stacked: one or two cards peek out above the newest bar; a click on them opens the list. */
|
|
532
|
+
.nx-dock__list[data-depth] {
|
|
533
|
+
margin-top: calc(var(--nx-dock-depth) * 5px);
|
|
534
|
+
cursor: pointer;
|
|
535
|
+
}
|
|
536
|
+
|
|
537
|
+
.nx-dock__list[data-depth="1"] {
|
|
538
|
+
--nx-dock-depth: 1;
|
|
539
|
+
}
|
|
540
|
+
|
|
541
|
+
.nx-dock__list[data-depth="2"] {
|
|
542
|
+
--nx-dock-depth: 2;
|
|
543
|
+
}
|
|
544
|
+
|
|
545
|
+
.nx-dock__list[data-depth]::before,
|
|
546
|
+
.nx-dock__list[data-depth="2"]::after {
|
|
547
|
+
content: "";
|
|
548
|
+
position: absolute;
|
|
549
|
+
top: -5px;
|
|
550
|
+
right: 8px;
|
|
551
|
+
left: 8px;
|
|
552
|
+
z-index: -1;
|
|
553
|
+
height: 24px;
|
|
554
|
+
border: 1px solid var(--nx-border);
|
|
555
|
+
border-radius: var(--nx-radius-lg);
|
|
556
|
+
background: light-dark(var(--nx-surface), var(--nx-surface-2));
|
|
557
|
+
box-shadow: var(--nx-shadow-sm);
|
|
558
|
+
}
|
|
559
|
+
|
|
560
|
+
.nx-dock__list[data-depth="2"]::after {
|
|
561
|
+
top: -10px;
|
|
562
|
+
right: 16px;
|
|
563
|
+
left: 16px;
|
|
564
|
+
z-index: -2;
|
|
565
|
+
}
|
|
566
|
+
|
|
567
|
+
.nx-dock__item {
|
|
568
|
+
display: flex;
|
|
569
|
+
flex-shrink: 0;
|
|
570
|
+
align-items: center;
|
|
571
|
+
gap: 2px;
|
|
572
|
+
height: 44px;
|
|
573
|
+
padding-right: 6px;
|
|
574
|
+
border: 1px solid var(--nx-border);
|
|
575
|
+
border-radius: var(--nx-radius-lg);
|
|
576
|
+
background: light-dark(var(--nx-surface), var(--nx-surface-2));
|
|
577
|
+
color: var(--nx-text);
|
|
578
|
+
box-shadow: var(--nx-shadow);
|
|
579
|
+
cursor: default;
|
|
580
|
+
transition: background-color var(--nx-duration);
|
|
581
|
+
animation: nx-dock-in 180ms cubic-bezier(0.2, 0, 0, 1);
|
|
582
|
+
}
|
|
583
|
+
|
|
584
|
+
.nx-dock__item:has(.nx-dock__window:hover) {
|
|
585
|
+
background: var(--nx-surface-hover);
|
|
586
|
+
}
|
|
587
|
+
|
|
588
|
+
.nx-dock__item:has(.nx-dock__window:focus-visible) {
|
|
589
|
+
box-shadow: var(--nx-focus-ring), var(--nx-shadow);
|
|
590
|
+
}
|
|
591
|
+
|
|
592
|
+
/* The bar's title part brings the popup back. */
|
|
593
|
+
.nx-dock__window {
|
|
594
|
+
display: flex;
|
|
595
|
+
flex: 1 1 auto;
|
|
596
|
+
align-items: center;
|
|
597
|
+
gap: 10px;
|
|
598
|
+
min-width: 0;
|
|
599
|
+
height: 100%;
|
|
600
|
+
padding: 0 6px 0 7px;
|
|
601
|
+
border: 0;
|
|
602
|
+
border-radius: inherit;
|
|
603
|
+
background: none;
|
|
604
|
+
color: inherit;
|
|
605
|
+
font: inherit;
|
|
606
|
+
text-align: start;
|
|
607
|
+
cursor: pointer;
|
|
608
|
+
}
|
|
609
|
+
|
|
610
|
+
.nx-dock__window:focus-visible {
|
|
611
|
+
outline: none;
|
|
612
|
+
}
|
|
613
|
+
|
|
614
|
+
.nx-dock__icon {
|
|
615
|
+
display: grid;
|
|
616
|
+
flex-shrink: 0;
|
|
617
|
+
place-items: center;
|
|
618
|
+
width: 28px;
|
|
619
|
+
height: 28px;
|
|
620
|
+
border-radius: var(--nx-radius);
|
|
621
|
+
background: var(--nx-primary-soft);
|
|
622
|
+
color: var(--nx-primary);
|
|
623
|
+
}
|
|
624
|
+
|
|
625
|
+
.nx-dock__icon .nx-icon {
|
|
626
|
+
width: 16px;
|
|
627
|
+
height: 16px;
|
|
628
|
+
vertical-align: 0;
|
|
629
|
+
}
|
|
630
|
+
|
|
631
|
+
.nx-dock__title {
|
|
632
|
+
flex: 1 1 auto;
|
|
633
|
+
min-width: 0;
|
|
634
|
+
overflow: hidden;
|
|
635
|
+
font-size: var(--nx-text-md);
|
|
636
|
+
font-weight: 600;
|
|
637
|
+
line-height: 1.3;
|
|
638
|
+
text-overflow: ellipsis;
|
|
639
|
+
white-space: nowrap;
|
|
640
|
+
}
|
|
641
|
+
|
|
642
|
+
.nx-dock__restore {
|
|
643
|
+
flex-shrink: 0;
|
|
644
|
+
width: 18px;
|
|
645
|
+
height: 18px;
|
|
646
|
+
color: var(--nx-text-muted);
|
|
647
|
+
}
|
|
648
|
+
|
|
649
|
+
.nx-dock__window:hover .nx-dock__restore {
|
|
650
|
+
color: var(--nx-text);
|
|
651
|
+
}
|
|
652
|
+
|
|
653
|
+
.nx-dock__close {
|
|
654
|
+
display: grid;
|
|
655
|
+
flex-shrink: 0;
|
|
656
|
+
place-items: center;
|
|
657
|
+
width: 30px;
|
|
658
|
+
height: 30px;
|
|
659
|
+
padding: 0;
|
|
660
|
+
border: 0;
|
|
661
|
+
border-radius: var(--nx-radius);
|
|
662
|
+
background: none;
|
|
663
|
+
color: var(--nx-text-muted);
|
|
664
|
+
cursor: pointer;
|
|
665
|
+
transition:
|
|
666
|
+
background-color var(--nx-duration),
|
|
667
|
+
color var(--nx-duration);
|
|
668
|
+
}
|
|
669
|
+
|
|
670
|
+
.nx-dock__close:hover {
|
|
671
|
+
background: var(--nx-danger-solid);
|
|
672
|
+
color: var(--nx-danger-text);
|
|
673
|
+
}
|
|
674
|
+
|
|
675
|
+
.nx-dock__close:focus-visible {
|
|
676
|
+
outline: none;
|
|
677
|
+
box-shadow: var(--nx-focus-ring);
|
|
678
|
+
}
|
|
679
|
+
|
|
680
|
+
.nx-dock__close .nx-icon {
|
|
681
|
+
width: 16px;
|
|
682
|
+
height: 16px;
|
|
683
|
+
vertical-align: 0;
|
|
684
|
+
}
|
|
685
|
+
|
|
686
|
+
@keyframes nx-dock-in {
|
|
687
|
+
from {
|
|
688
|
+
opacity: 0;
|
|
689
|
+
transform: translateY(8px);
|
|
690
|
+
}
|
|
691
|
+
}
|
|
692
|
+
|
|
693
|
+
@media (max-width: 600px) {
|
|
694
|
+
.nx-popup {
|
|
695
|
+
width: calc(100% - 16px);
|
|
696
|
+
max-height: min(calc(100vh - 16px), calc(100dvh - 16px));
|
|
697
|
+
}
|
|
698
|
+
|
|
699
|
+
.nx-popup--dialog .nx-popup__head {
|
|
700
|
+
padding: var(--nx-space-4) var(--nx-space-4) 0;
|
|
701
|
+
}
|
|
702
|
+
|
|
703
|
+
.nx-popup__body {
|
|
704
|
+
padding: var(--nx-space-3) var(--nx-space-4) var(--nx-space-4);
|
|
705
|
+
}
|
|
706
|
+
|
|
707
|
+
.nx-popup--window:not(.nx-popup--flush) .nx-popup__body {
|
|
708
|
+
padding-top: var(--nx-space-4);
|
|
709
|
+
}
|
|
710
|
+
|
|
711
|
+
.nx-popup__foot {
|
|
712
|
+
padding: var(--nx-space-3) var(--nx-space-4);
|
|
713
|
+
}
|
|
714
|
+
}
|
|
715
|
+
|
|
716
|
+
[data-nx-motion="reduce"] .nx-popup[open],
|
|
717
|
+
[data-nx-motion="reduce"] .nx-popup--closing[open],
|
|
718
|
+
[data-nx-motion="reduce"] .nx-popup::backdrop,
|
|
719
|
+
[data-nx-motion="reduce"] .nx-popup--closing::backdrop,
|
|
720
|
+
[data-nx-motion="reduce"] .nx-popup[data-nx-minimizing]::backdrop,
|
|
721
|
+
[data-nx-motion="reduce"] .nx-dock__item {
|
|
722
|
+
animation: none;
|
|
723
|
+
}
|
|
724
|
+
}
|