@astronox/core 0.4.13 → 0.4.15
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/package.json +1 -1
- package/src/components/actions/ScrollToTop/scrollToTopController.ts +6 -6
- package/src/components/content/CardHeader/CardHeader.css +1 -1
- package/src/composition/Grid/Grid.css +20 -0
- package/src/composition/GridItem/GridItem.css +4 -3
- package/src/composition/SurfaceGroup/SurfaceGroup.css +1 -1
- package/src/composition/SurfaceGroup/stickySurfaceGroupController.ts +4 -0
- package/src/patterns/Combobox/comboboxController.ts +2 -3
- package/src/patterns/Modal/Modal.css +2 -0
- package/src/patterns/Table/Table.css +3 -2
- package/src/patterns/Table/TablePagination.css +8 -2
- package/src/patterns/Table/tableViewport.ts +38 -10
- package/src/styles/base.css +15 -19
- package/src/styles/tokens.css +3 -0
package/package.json
CHANGED
|
@@ -4,27 +4,27 @@ const noop = (): void => undefined;
|
|
|
4
4
|
export function initScrollToTop(control: HTMLButtonElement): () => void {
|
|
5
5
|
if (control.getAttribute(initializedAttribute) === 'true') return noop;
|
|
6
6
|
|
|
7
|
-
const
|
|
8
|
-
if (!
|
|
7
|
+
const scrollRoot = document.scrollingElement;
|
|
8
|
+
if (!scrollRoot) return noop;
|
|
9
9
|
|
|
10
10
|
control.setAttribute(initializedAttribute, 'true');
|
|
11
11
|
|
|
12
12
|
const sync = (): void => {
|
|
13
13
|
control.hidden =
|
|
14
|
-
|
|
14
|
+
scrollRoot.scrollTop <= 0 || document.fullscreenElement !== null;
|
|
15
15
|
};
|
|
16
16
|
|
|
17
17
|
const scrollToTop = (): void => {
|
|
18
|
-
|
|
18
|
+
window.scrollTo({ top: 0, behavior: 'auto' });
|
|
19
19
|
};
|
|
20
20
|
|
|
21
|
-
|
|
21
|
+
window.addEventListener('scroll', sync, { passive: true });
|
|
22
22
|
document.addEventListener('fullscreenchange', sync);
|
|
23
23
|
control.addEventListener('click', scrollToTop);
|
|
24
24
|
sync();
|
|
25
25
|
|
|
26
26
|
return () => {
|
|
27
|
-
|
|
27
|
+
window.removeEventListener('scroll', sync);
|
|
28
28
|
document.removeEventListener('fullscreenchange', sync);
|
|
29
29
|
control.removeEventListener('click', scrollToTop);
|
|
30
30
|
control.removeAttribute(initializedAttribute);
|
|
@@ -103,6 +103,18 @@
|
|
|
103
103
|
grid-template-columns: minmax(0, 7fr) minmax(0, 3fr);
|
|
104
104
|
}
|
|
105
105
|
|
|
106
|
+
.grid[data-layout='content-sidebar']:has(
|
|
107
|
+
> [data-composition='grid-item'][data-position='sticky']
|
|
108
|
+
) {
|
|
109
|
+
--table-progressive-runway-block-size: calc(
|
|
110
|
+
100vh - var(--nox-site-header-responsive-height) - var(--nox-layout-gap) * 2
|
|
111
|
+
);
|
|
112
|
+
--table-progressive-runway-block-size: calc(
|
|
113
|
+
100dvh - var(--nox-site-header-responsive-height) - var(--nox-layout-gap) *
|
|
114
|
+
2
|
|
115
|
+
);
|
|
116
|
+
}
|
|
117
|
+
|
|
106
118
|
.grid[data-rows] {
|
|
107
119
|
grid-template-rows: repeat(var(--grid-rows), minmax(0, 1fr));
|
|
108
120
|
}
|
|
@@ -112,6 +124,8 @@
|
|
|
112
124
|
[data-layout='fixed'],
|
|
113
125
|
[data-layout='content-sidebar']
|
|
114
126
|
)[data-collapse-at='sm'] {
|
|
127
|
+
--table-progressive-runway-block-size: 0px;
|
|
128
|
+
|
|
115
129
|
grid-template-columns: 1fr;
|
|
116
130
|
}
|
|
117
131
|
|
|
@@ -164,6 +178,8 @@
|
|
|
164
178
|
[data-layout='fixed'],
|
|
165
179
|
[data-layout='content-sidebar']
|
|
166
180
|
)[data-collapse-at='md'] {
|
|
181
|
+
--table-progressive-runway-block-size: 0px;
|
|
182
|
+
|
|
167
183
|
grid-template-columns: 1fr;
|
|
168
184
|
}
|
|
169
185
|
|
|
@@ -216,6 +232,8 @@
|
|
|
216
232
|
[data-layout='fixed'],
|
|
217
233
|
[data-layout='content-sidebar']
|
|
218
234
|
)[data-collapse-at='lg'] {
|
|
235
|
+
--table-progressive-runway-block-size: 0px;
|
|
236
|
+
|
|
219
237
|
grid-template-columns: 1fr;
|
|
220
238
|
}
|
|
221
239
|
|
|
@@ -268,6 +286,8 @@
|
|
|
268
286
|
[data-layout='fixed'],
|
|
269
287
|
[data-layout='content-sidebar']
|
|
270
288
|
)[data-collapse-at='xl'] {
|
|
289
|
+
--table-progressive-runway-block-size: 0px;
|
|
290
|
+
|
|
271
291
|
grid-template-columns: 1fr;
|
|
272
292
|
}
|
|
273
293
|
|
|
@@ -44,13 +44,14 @@
|
|
|
44
44
|
.grid-item[data-position='sticky'] {
|
|
45
45
|
position: sticky;
|
|
46
46
|
z-index: 1;
|
|
47
|
-
top: var(--nox-layout-gap);
|
|
47
|
+
top: calc(var(--nox-sticky-viewport-offset) + var(--nox-layout-gap));
|
|
48
48
|
padding-block-end: var(--nox-border-width);
|
|
49
49
|
max-block-size: calc(
|
|
50
|
-
100vh - var(--nox-site-header-height) - var(--nox-layout-gap) * 2
|
|
50
|
+
100vh - var(--nox-site-header-responsive-height) - var(--nox-layout-gap) * 2
|
|
51
51
|
);
|
|
52
52
|
max-block-size: calc(
|
|
53
|
-
100dvh - var(--nox-site-header-height) - var(--nox-layout-gap) *
|
|
53
|
+
100dvh - var(--nox-site-header-responsive-height) - var(--nox-layout-gap) *
|
|
54
|
+
2
|
|
54
55
|
);
|
|
55
56
|
align-self: start;
|
|
56
57
|
overflow-x: hidden;
|
|
@@ -6,6 +6,10 @@ const getScrollParent = (element: HTMLElement): HTMLElement | Window => {
|
|
|
6
6
|
let parent = element.parentElement;
|
|
7
7
|
|
|
8
8
|
while (parent) {
|
|
9
|
+
if (parent === document.body || parent === document.documentElement) {
|
|
10
|
+
return window;
|
|
11
|
+
}
|
|
12
|
+
|
|
9
13
|
const styles = window.getComputedStyle(parent);
|
|
10
14
|
|
|
11
15
|
if (/(auto|scroll|overlay)/.test(styles.overflowY)) {
|
|
@@ -506,9 +506,8 @@ export function initCombobox(root: HTMLElement): () => void {
|
|
|
506
506
|
const siteViewport = document.querySelector<HTMLElement>(
|
|
507
507
|
'[data-site-viewport]',
|
|
508
508
|
);
|
|
509
|
-
const isSiteScroll =
|
|
510
|
-
|
|
511
|
-
: target === document || target === window;
|
|
509
|
+
const isSiteScroll =
|
|
510
|
+
target === siteViewport || target === document || target === window;
|
|
512
511
|
if (isSiteScroll && window.matchMedia(compactViewportQuery).matches) {
|
|
513
512
|
close();
|
|
514
513
|
blurFocusedDescendant();
|
|
@@ -44,13 +44,14 @@
|
|
|
44
44
|
.table[data-table-sticky-header] [data-table-header] {
|
|
45
45
|
position: sticky;
|
|
46
46
|
z-index: 40;
|
|
47
|
-
top:
|
|
47
|
+
top: var(--nox-sticky-viewport-offset);
|
|
48
48
|
}
|
|
49
49
|
|
|
50
50
|
.table[data-table-sticky-header]:has([data-sticky-surface])
|
|
51
51
|
[data-table-header] {
|
|
52
52
|
top: calc(
|
|
53
|
-
var(--nox-
|
|
53
|
+
var(--nox-sticky-viewport-offset) + var(--nox-layout-gap) +
|
|
54
|
+
var(--surface-group-sticky-surface-block-size)
|
|
54
55
|
);
|
|
55
56
|
}
|
|
56
57
|
|
|
@@ -49,13 +49,19 @@
|
|
|
49
49
|
position: relative;
|
|
50
50
|
display: block;
|
|
51
51
|
overflow: visible;
|
|
52
|
-
block-size:
|
|
53
|
-
min-block-size:
|
|
52
|
+
block-size: var(--table-progressive-runway-block-size, 0px);
|
|
53
|
+
min-block-size: var(--table-progressive-runway-block-size, 0px);
|
|
54
54
|
border: 0;
|
|
55
55
|
border-radius: 0;
|
|
56
56
|
background: transparent;
|
|
57
57
|
}
|
|
58
58
|
|
|
59
|
+
.table-pagination[data-table-progressive-enhanced='true']
|
|
60
|
+
.table-pagination__sentinel {
|
|
61
|
+
inset-block-start: 0;
|
|
62
|
+
inset-block-end: auto;
|
|
63
|
+
}
|
|
64
|
+
|
|
59
65
|
.table-pagination[data-table-progressive-enhanced='true']
|
|
60
66
|
.table-pagination__content {
|
|
61
67
|
block-size: 0;
|
|
@@ -18,29 +18,57 @@ export function resolveTableStartScrollTop({
|
|
|
18
18
|
}
|
|
19
19
|
|
|
20
20
|
export function resolveTableScrollRoot(root: HTMLElement): HTMLElement | null {
|
|
21
|
-
|
|
21
|
+
let candidate = root.parentElement;
|
|
22
|
+
|
|
23
|
+
while (candidate) {
|
|
24
|
+
if (candidate === document.body || candidate === document.documentElement) {
|
|
25
|
+
return null;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
if (
|
|
29
|
+
/(auto|scroll|overlay)/u.test(
|
|
30
|
+
window.getComputedStyle(candidate).overflowY,
|
|
31
|
+
)
|
|
32
|
+
) {
|
|
33
|
+
return candidate;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
candidate = candidate.parentElement;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
return null;
|
|
22
40
|
}
|
|
23
41
|
|
|
24
42
|
function resolveTableStickyOffset(root: HTMLElement): number {
|
|
25
|
-
const
|
|
26
|
-
'[data-sticky-surface]'
|
|
27
|
-
|
|
28
|
-
if (!
|
|
43
|
+
const stickyElement =
|
|
44
|
+
root.querySelector<HTMLElement>('[data-sticky-surface]') ??
|
|
45
|
+
root.querySelector<HTMLElement>('[data-table-header]');
|
|
46
|
+
if (!stickyElement) return 0;
|
|
29
47
|
|
|
30
|
-
return Number.parseFloat(window.getComputedStyle(
|
|
48
|
+
return Number.parseFloat(window.getComputedStyle(stickyElement).top) || 0;
|
|
31
49
|
}
|
|
32
50
|
|
|
33
51
|
export function revealTableStart(root: HTMLElement): void {
|
|
34
52
|
const scrollRoot = resolveTableScrollRoot(root);
|
|
35
|
-
|
|
53
|
+
const documentScrollRoot = document.scrollingElement;
|
|
54
|
+
if (!scrollRoot && !documentScrollRoot) return;
|
|
55
|
+
|
|
56
|
+
const currentScrollTop = scrollRoot
|
|
57
|
+
? scrollRoot.scrollTop
|
|
58
|
+
: documentScrollRoot!.scrollTop;
|
|
36
59
|
|
|
37
60
|
const nextScrollTop = resolveTableStartScrollTop({
|
|
38
|
-
currentScrollTop
|
|
61
|
+
currentScrollTop,
|
|
39
62
|
stickyOffset: resolveTableStickyOffset(root),
|
|
40
63
|
tableTop: root.getBoundingClientRect().top,
|
|
41
|
-
viewportTop: scrollRoot
|
|
64
|
+
viewportTop: scrollRoot?.getBoundingClientRect().top ?? 0,
|
|
42
65
|
});
|
|
43
|
-
|
|
66
|
+
|
|
67
|
+
if (nextScrollTop === currentScrollTop) return;
|
|
68
|
+
|
|
69
|
+
if (scrollRoot) {
|
|
44
70
|
scrollRoot.scrollTop = nextScrollTop;
|
|
71
|
+
} else {
|
|
72
|
+
window.scrollTo({ top: nextScrollTop, behavior: 'auto' });
|
|
45
73
|
}
|
|
46
74
|
}
|
package/src/styles/base.css
CHANGED
|
@@ -44,46 +44,42 @@
|
|
|
44
44
|
|
|
45
45
|
html {
|
|
46
46
|
min-width: 320px;
|
|
47
|
-
height: 100%;
|
|
48
47
|
min-height: 100%;
|
|
49
|
-
|
|
48
|
+
scroll-padding-block-start: var(--nox-site-header-responsive-height);
|
|
49
|
+
scrollbar-gutter: stable;
|
|
50
50
|
background: var(--nox-page-background);
|
|
51
51
|
color: var(--nox-text);
|
|
52
52
|
font-family: var(--nox-font-body);
|
|
53
53
|
}
|
|
54
54
|
|
|
55
55
|
body {
|
|
56
|
-
height: 100%;
|
|
57
56
|
min-height: 100%;
|
|
58
57
|
margin: 0;
|
|
59
|
-
overflow: hidden;
|
|
60
58
|
background: var(--nox-page-background);
|
|
61
59
|
}
|
|
62
60
|
|
|
61
|
+
@media (hover: hover) and (pointer: fine) {
|
|
62
|
+
body {
|
|
63
|
+
border-inline-end: var(--nox-border-width) solid var(--nox-border);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
|
|
63
67
|
.site-shell {
|
|
64
68
|
display: grid;
|
|
65
|
-
width:
|
|
66
|
-
height: 100vh;
|
|
69
|
+
width: 100%;
|
|
67
70
|
min-height: 100vh;
|
|
68
71
|
grid-template-rows: auto minmax(0, 1fr);
|
|
69
|
-
overflow:
|
|
72
|
+
overflow-x: clip;
|
|
73
|
+
overflow-y: visible;
|
|
70
74
|
background: var(--nox-page-background);
|
|
71
75
|
}
|
|
72
76
|
|
|
73
|
-
@supports (height: 100svh) {
|
|
77
|
+
@supports (min-height: 100svh) {
|
|
74
78
|
.site-shell {
|
|
75
|
-
height: 100svh;
|
|
76
79
|
min-height: 100svh;
|
|
77
80
|
}
|
|
78
81
|
}
|
|
79
82
|
|
|
80
|
-
@media (width >= 48rem) {
|
|
81
|
-
.site-shell {
|
|
82
|
-
height: 100vh;
|
|
83
|
-
min-height: 100vh;
|
|
84
|
-
}
|
|
85
|
-
}
|
|
86
|
-
|
|
87
83
|
a {
|
|
88
84
|
color: var(--nox-content-link-color);
|
|
89
85
|
font-weight: var(--nox-content-link-font-weight);
|
|
@@ -133,13 +129,13 @@ p {
|
|
|
133
129
|
|
|
134
130
|
.site-viewport {
|
|
135
131
|
--site-content-gap: var(--nox-space-5);
|
|
132
|
+
--nox-sticky-viewport-offset: var(--nox-site-header-responsive-height);
|
|
136
133
|
|
|
137
134
|
min-width: 0;
|
|
138
135
|
min-height: 0;
|
|
139
|
-
overflow
|
|
140
|
-
overflow-y: auto;
|
|
136
|
+
overflow: visible;
|
|
141
137
|
background: var(--nox-page-background);
|
|
142
|
-
overscroll-behavior-y:
|
|
138
|
+
overscroll-behavior-y: auto;
|
|
143
139
|
}
|
|
144
140
|
|
|
145
141
|
.site-main {
|
package/src/styles/tokens.css
CHANGED
|
@@ -215,6 +215,8 @@
|
|
|
215
215
|
--nox-navigation-compact-block-size: 3rem;
|
|
216
216
|
--nox-site-header-height: 4.75rem;
|
|
217
217
|
--nox-site-header-compact-height: 4rem;
|
|
218
|
+
--nox-site-header-responsive-height: var(--nox-site-header-height);
|
|
219
|
+
--nox-sticky-viewport-offset: 0px;
|
|
218
220
|
|
|
219
221
|
/* Spacing scale. */
|
|
220
222
|
--nox-space: 0.25rem;
|
|
@@ -289,5 +291,6 @@
|
|
|
289
291
|
:root {
|
|
290
292
|
--nox-section-responsive-block-size: var(--nox-section-compact-block-size);
|
|
291
293
|
--nox-compact-media-responsive-size: 2.125rem;
|
|
294
|
+
--nox-site-header-responsive-height: var(--nox-site-header-compact-height);
|
|
292
295
|
}
|
|
293
296
|
}
|