starlight-cannoli-plugins 2.10.2 → 2.10.4
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.
|
@@ -3,6 +3,57 @@ import { fileURLToPath } from "url";
|
|
|
3
3
|
var css = String.raw;
|
|
4
4
|
var js = String.raw;
|
|
5
5
|
var CONDITIONAL_CSS = {
|
|
6
|
+
offerTabbedContent: {
|
|
7
|
+
enabled: css`
|
|
8
|
+
/* Suppress the default crossfade for the named panel transition. */
|
|
9
|
+
::view-transition-old(tabbed-panel),
|
|
10
|
+
::view-transition-new(tabbed-panel) {
|
|
11
|
+
animation: none;
|
|
12
|
+
mix-blend-mode: normal;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
/* Slide animation — only when the user has no motion preference. */
|
|
16
|
+
@media (prefers-reduced-motion: no-preference) {
|
|
17
|
+
:root[data-tab-direction="next"]::view-transition-old(tabbed-panel) {
|
|
18
|
+
animation: tabbed-slide-out-to-left 250ms ease both;
|
|
19
|
+
}
|
|
20
|
+
:root[data-tab-direction="next"]::view-transition-new(tabbed-panel) {
|
|
21
|
+
animation: tabbed-slide-in-from-right 250ms ease both;
|
|
22
|
+
}
|
|
23
|
+
:root[data-tab-direction="prev"]::view-transition-old(tabbed-panel) {
|
|
24
|
+
animation: tabbed-slide-out-to-right 250ms ease both;
|
|
25
|
+
}
|
|
26
|
+
:root[data-tab-direction="prev"]::view-transition-new(tabbed-panel) {
|
|
27
|
+
animation: tabbed-slide-in-from-left 250ms ease both;
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
@keyframes tabbed-slide-out-to-left {
|
|
32
|
+
to {
|
|
33
|
+
transform: translateX(-30%);
|
|
34
|
+
opacity: 0;
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
@keyframes tabbed-slide-in-from-right {
|
|
38
|
+
from {
|
|
39
|
+
transform: translateX(30%);
|
|
40
|
+
opacity: 0;
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
@keyframes tabbed-slide-out-to-right {
|
|
44
|
+
to {
|
|
45
|
+
transform: translateX(30%);
|
|
46
|
+
opacity: 0;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
@keyframes tabbed-slide-in-from-left {
|
|
50
|
+
from {
|
|
51
|
+
transform: translateX(-30%);
|
|
52
|
+
opacity: 0;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
`
|
|
56
|
+
},
|
|
6
57
|
limitDetailsElementHeight: {
|
|
7
58
|
enabled: css`
|
|
8
59
|
.main-pane details[open] {
|
package/dist/index.js
CHANGED
|
@@ -146,16 +146,40 @@ function tabbedH2Content() {
|
|
|
146
146
|
contentContainer.appendChild(tabbedWrapper);
|
|
147
147
|
contentContainer.appendChild(paginationBar);
|
|
148
148
|
let activeTabIndex = 0;
|
|
149
|
-
function
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
149
|
+
function isTabNavVisible() {
|
|
150
|
+
const rect = tabNav.getBoundingClientRect();
|
|
151
|
+
return rect.top < window.innerHeight && rect.bottom > 0;
|
|
152
|
+
}
|
|
153
|
+
function activateTab(targetIndex, updateHash = true, scrollToNav = false) {
|
|
154
|
+
const applySwitch = () => {
|
|
155
|
+
tabPanels[activeTabIndex].style.viewTransitionName = "";
|
|
156
|
+
activeTabIndex = targetIndex;
|
|
157
|
+
tabButtons.forEach((tabButton, buttonIndex) => {
|
|
158
|
+
tabButton.dataset.active = String(buttonIndex === targetIndex);
|
|
159
|
+
});
|
|
160
|
+
tabPanels.forEach((tabPanel, panelIndex) => {
|
|
161
|
+
tabPanel.hidden = panelIndex !== targetIndex;
|
|
162
|
+
});
|
|
163
|
+
tabPanels[targetIndex].style.viewTransitionName = "tabbed-panel";
|
|
164
|
+
prevTabButton.disabled = targetIndex === 0;
|
|
165
|
+
nextTabButton.disabled = targetIndex === allSections.length - 1;
|
|
166
|
+
};
|
|
167
|
+
if (targetIndex !== activeTabIndex && "startViewTransition" in document) {
|
|
168
|
+
document.documentElement.dataset.tabDirection = targetIndex > activeTabIndex ? "next" : "prev";
|
|
169
|
+
tabPanels[activeTabIndex].style.viewTransitionName = "tabbed-panel";
|
|
170
|
+
document.startViewTransition(applySwitch);
|
|
171
|
+
} else {
|
|
172
|
+
applySwitch();
|
|
173
|
+
}
|
|
174
|
+
const scrollBehavior = getComputedStyle(document.documentElement).scrollBehavior;
|
|
175
|
+
tabButtons[targetIndex].scrollIntoView({
|
|
176
|
+
behavior: scrollBehavior,
|
|
177
|
+
block: "nearest",
|
|
178
|
+
inline: "nearest"
|
|
156
179
|
});
|
|
157
|
-
|
|
158
|
-
|
|
180
|
+
if (scrollToNav) {
|
|
181
|
+
tabNav.scrollIntoView({ behavior: scrollBehavior, block: "nearest" });
|
|
182
|
+
}
|
|
159
183
|
if (updateHash) {
|
|
160
184
|
const targetHeadingId = allSections[targetIndex].headingId;
|
|
161
185
|
if (targetHeadingId) {
|
|
@@ -169,12 +193,19 @@ function tabbedH2Content() {
|
|
|
169
193
|
}
|
|
170
194
|
}
|
|
171
195
|
}
|
|
196
|
+
function findPanelIndexForHash(urlHash) {
|
|
197
|
+
const targetHeadingId = urlHash.startsWith("#") ? urlHash.slice(1) : urlHash;
|
|
198
|
+
return tabPanels.findIndex(
|
|
199
|
+
(tabPanel) => tabPanel.querySelector(`#${CSS.escape(targetHeadingId)}`)
|
|
200
|
+
);
|
|
201
|
+
}
|
|
172
202
|
function setEnabled(enabled) {
|
|
173
203
|
tabbedWrapper.dataset.enabled = String(enabled);
|
|
174
204
|
tabNav.hidden = !enabled;
|
|
175
205
|
paginationBar.hidden = !enabled;
|
|
176
206
|
if (enabled) {
|
|
177
|
-
|
|
207
|
+
const hashPanelIndex = window.location.hash ? findPanelIndexForHash(window.location.hash) : -1;
|
|
208
|
+
activateTab(hashPanelIndex >= 0 ? hashPanelIndex : activeTabIndex, false);
|
|
178
209
|
} else {
|
|
179
210
|
tabPanels.forEach((tabPanel) => {
|
|
180
211
|
tabPanel.hidden = false;
|
|
@@ -183,19 +214,22 @@ function tabbedH2Content() {
|
|
|
183
214
|
}
|
|
184
215
|
function navigateToHash(urlHash) {
|
|
185
216
|
if (!urlHash || tabbedWrapper.dataset.enabled !== "true") return;
|
|
186
|
-
const
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
activateTab(panelIndex, false);
|
|
190
|
-
});
|
|
217
|
+
const targetPanelIndex = findPanelIndexForHash(urlHash);
|
|
218
|
+
if (targetPanelIndex >= 0 && targetPanelIndex !== activeTabIndex)
|
|
219
|
+
activateTab(targetPanelIndex, false);
|
|
191
220
|
}
|
|
192
221
|
function wireInteractions(viewToggleCheckbox2) {
|
|
193
222
|
prevTabButton.addEventListener("click", () => {
|
|
194
|
-
if (activeTabIndex > 0)
|
|
223
|
+
if (activeTabIndex > 0) {
|
|
224
|
+
const scrollToNav = !isTabNavVisible();
|
|
225
|
+
activateTab(activeTabIndex - 1, true, scrollToNav);
|
|
226
|
+
}
|
|
195
227
|
});
|
|
196
228
|
nextTabButton.addEventListener("click", () => {
|
|
197
|
-
if (activeTabIndex < allSections.length - 1)
|
|
198
|
-
|
|
229
|
+
if (activeTabIndex < allSections.length - 1) {
|
|
230
|
+
const scrollToNav = !isTabNavVisible();
|
|
231
|
+
activateTab(activeTabIndex + 1, true, scrollToNav);
|
|
232
|
+
}
|
|
199
233
|
});
|
|
200
234
|
tabButtons.forEach((tabButton, buttonIndex) => {
|
|
201
235
|
tabButton.addEventListener("click", () => {
|
package/package.json
CHANGED