@jsenv/navi 0.29.413 → 0.29.414
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/dist/dev/jsenv_navi.js +379 -290
- package/dist/dev/jsenv_navi.js.map +10 -8
- package/dist/jsenv_navi.js +379 -290
- package/dist/jsenv_navi.js.map +10 -8
- package/docs/AI_INSTRUCTIONS.md +10 -5
- package/docs/route_transitions.md +90 -1
- package/docs/view_transitions.md +61 -0
- package/package.json +2 -2
package/dist/jsenv_navi.js
CHANGED
|
@@ -6,8 +6,8 @@ import { installImportMetaCssBuild, coarsePointerSignal, windowHeightSignal, win
|
|
|
6
6
|
import { createPubSub, elementIsFocusable, createIterableWeakSet, dispatchInternalCustomEvent, dispatchCustomEvent, findEvent, mergeOneStyle, findFocusable, getElementSignature, chainEvent, isTouchDrivenEvent, getKeyboardEventDefaultAction, isPressDrivenClick, getVisuallyVisibleInfo, getFirstVisuallyVisibleAncestor, createValueEffect, findFocusDelegateTarget, scrollIntoViewThroughScrollables, allowWheelThrough, dispatchPublicCustomEvent, resolveCSSColor, getScrollContainerSet, ELEMENT_SIZE_CHANGE, findSelfOrAncestorFixedPosition, visibleRectEffect, pickPositionRelativeTo, getBorderSizes, getPaddingSizes, applyNewPosition, measureLongestVisualLineWidth, keepTouchRefusable, waitForTap, waitForPressHeld, suppressClickAfterGesture, startDragToTravel, dragSourceThatStoodDown, markDragSource, refuseDragTo, startDragTo, installPanZoom, createInternalCustomEvent, activeElementSignal, normalizeStyle, getPositionedParent, normalizeStyles, createGroupTransitionController, getBorderRadius, preventIntermediateScrollbar, createOpacityTransition, getScrollContainer, watchWheelTravel, scrollRoomTowards, trapScrollInside, scrollIntoViewScoped, closestOpenableAncestor, isAncestorOpen, isDisplayedDespiteClosedAncestor, observeAncestorOpenState, getAncestorOpenType, findBefore, findAfter, resolveCSSSize, hasCSSSizeUnit, releaseWheelGesture, getScrollIntoViewScopedOffsets, wheelGestureIsTakenFrom, claimWheelGesture, initFocusGroup, stringifyStyle as stringifyStyle$1, isScrollable, resolveOklchLightness, contrastColor, parsePositionArea, snapToPixel, trapFocusInside, onAncestorReopen, isPressDisputedByDrag, canScroll, measureWidestChildRow, performTabNavigation, dragAfterIntent, stickyAsRelativeCoords, createDragToMoveGestureController, getDropTargetInfo, setStyles, useActiveElement, setVirtualKeyboardOverlaysContent, subscribeVirtualKeyboardGeometryChange, getVirtualKeyboardOverlayHeight } from "@jsenv/dom";
|
|
7
7
|
export { chainEvent, clickIsSuppressed, contrastColor, createDragGestureController, dragAfterIntent, findEvent, markDragSource, startDragTo } from "@jsenv/dom";
|
|
8
8
|
import { signal, computed, effect, untracked, batch, useComputed, useSignal } from "@preact/signals";
|
|
9
|
-
import { options, isValidElement, createContext, render, h, toChildArray, cloneElement, createElement, Fragment as Fragment$1 } from "preact";
|
|
10
|
-
import { useErrorBoundary, useLayoutEffect, useContext, useMemo, useRef, useEffect, useCallback, useState, useId } from "preact/hooks";
|
|
9
|
+
import { options, isValidElement, createContext, render, h, toChildArray, createRef, cloneElement, createElement, Fragment as Fragment$1 } from "preact";
|
|
10
|
+
import { useErrorBoundary, useLayoutEffect, useContext, useMemo, useRef, useEffect, useCallback, useState, useReducer, useId } from "preact/hooks";
|
|
11
11
|
import { humanizeI18n, setRuntimeLangSource, formatDuration, formatMonth, formatDay, resolveTimeRangePrecision, formatDatePlaceholder, toDate, getRelativeDay, formatDayRelative, formatMonthPlaceholder, formatWeekPlaceholder, formatDatetimePlaceholder, formatDatetime, toTimeOfDay, formatTimeOfDay, formatTime, formatMinuteDuration, formatSecondDuration, formatHourDuration, formatTimeRelative, formatNumber, interpolateText, installInterpolateJsx } from "@jsenv/humanize";
|
|
12
12
|
export { createI18n, formatDatetime, formatDay, formatDayRelative, formatDuration, formatHourDuration, formatMinuteDuration, formatMonth, formatNumber, formatSecondDuration, formatTime, formatTimeOfDay, formatTimeRange, formatTimeRelative, interpolateText } from "@jsenv/humanize";
|
|
13
13
|
import { jsxs, jsx, Fragment } from "preact/jsx-runtime";
|
|
@@ -79,7 +79,7 @@ installImportMetaCssBuild(import.meta);
|
|
|
79
79
|
* any of these, and a number is the last resort, not the first tool.
|
|
80
80
|
*/
|
|
81
81
|
|
|
82
|
-
const css$
|
|
82
|
+
const css$18 = /* css */ `@layer navi {
|
|
83
83
|
:root {
|
|
84
84
|
--navi-z-index-control-hovered: 1;
|
|
85
85
|
--navi-z-index-control-focused: 2;
|
|
@@ -92,7 +92,7 @@ const css$17 = /* css */ `@layer navi {
|
|
|
92
92
|
}
|
|
93
93
|
}
|
|
94
94
|
`;
|
|
95
|
-
import.meta.css = [css$
|
|
95
|
+
import.meta.css = [css$18, "@jsenv/navi/src/navi_z_indexes.js"];
|
|
96
96
|
|
|
97
97
|
/**
|
|
98
98
|
* A navigation is ABOUT to be applied — said before its very first write.
|
|
@@ -430,7 +430,7 @@ installImportMetaCssBuild(import.meta);
|
|
|
430
430
|
|
|
431
431
|
const URL_TARGET_ATTRIBUTE = "data-url-target";
|
|
432
432
|
|
|
433
|
-
const css$
|
|
433
|
+
const css$17 = /* css */ `@layer navi {
|
|
434
434
|
[data-url-target] {
|
|
435
435
|
animation: navi_url_target var(--navi-url-target-duration, 2s)
|
|
436
436
|
ease-out;
|
|
@@ -448,7 +448,7 @@ const css$16 = /* css */ `@layer navi {
|
|
|
448
448
|
}
|
|
449
449
|
}
|
|
450
450
|
`;
|
|
451
|
-
import.meta.css = [css$
|
|
451
|
+
import.meta.css = [css$17, "@jsenv/navi/src/nav/url_target/url_target.js"];
|
|
452
452
|
|
|
453
453
|
let urlTargetOptions = {
|
|
454
454
|
block: "start",
|
|
@@ -2048,7 +2048,7 @@ const useActionStatus = (action) => {
|
|
|
2048
2048
|
};
|
|
2049
2049
|
|
|
2050
2050
|
installImportMetaCssBuild(import.meta);
|
|
2051
|
-
const css$
|
|
2051
|
+
const css$16 = /* css */`.action_error {
|
|
2052
2052
|
background: #fdd;
|
|
2053
2053
|
border: 1px solid red;
|
|
2054
2054
|
margin-top: 0;
|
|
@@ -2072,7 +2072,7 @@ const ActionRenderer = ({
|
|
|
2072
2072
|
children,
|
|
2073
2073
|
disabled
|
|
2074
2074
|
}) => {
|
|
2075
|
-
import.meta.css = [css$
|
|
2075
|
+
import.meta.css = [css$16, "@jsenv/navi/src/action/action_renderer.jsx"];
|
|
2076
2076
|
if (action === undefined) {
|
|
2077
2077
|
throw new Error("ActionRenderer requires an action to render, but none was provided.");
|
|
2078
2078
|
}
|
|
@@ -15336,7 +15336,7 @@ installImportMetaCssBuild(import.meta);
|
|
|
15336
15336
|
* (see calloutTemplate in callout.js).
|
|
15337
15337
|
*/
|
|
15338
15338
|
|
|
15339
|
-
const css$
|
|
15339
|
+
const css$15 = /* css */`.navi_callout_status_icon {
|
|
15340
15340
|
--x-callout-status-icon-color: var(--navi-callout-neutral-color);
|
|
15341
15341
|
box-sizing: border-box;
|
|
15342
15342
|
aspect-ratio: 1;
|
|
@@ -15407,7 +15407,7 @@ const CalloutStatusIcon = ({
|
|
|
15407
15407
|
status = "info",
|
|
15408
15408
|
shape = "square"
|
|
15409
15409
|
}) => {
|
|
15410
|
-
import.meta.css = [css$
|
|
15410
|
+
import.meta.css = [css$15, "@jsenv/navi/src/control/rules/callout/callout_status_icon.jsx"];
|
|
15411
15411
|
return jsx("span", {
|
|
15412
15412
|
className: "navi_callout_status_icon",
|
|
15413
15413
|
"data-status": status === "none" ? undefined : status,
|
|
@@ -15434,7 +15434,7 @@ let calloutCount = 0;
|
|
|
15434
15434
|
// large enough to survive the pixel or two a trackpad rests on.
|
|
15435
15435
|
const CLOSE_BY_SCROLL_DISTANCE = 10;
|
|
15436
15436
|
|
|
15437
|
-
const css$
|
|
15437
|
+
const css$14 = /* css */ `
|
|
15438
15438
|
/* jsenv-css-opaque: same as dialog.jsx, cascade order. */
|
|
15439
15439
|
@layer navi {
|
|
15440
15440
|
.navi_callout {
|
|
@@ -15795,7 +15795,7 @@ const openCallout = (
|
|
|
15795
15795
|
debug = () => {},
|
|
15796
15796
|
} = {},
|
|
15797
15797
|
) => {
|
|
15798
|
-
import.meta.css = [css$
|
|
15798
|
+
import.meta.css = [css$14, "@jsenv/navi/src/control/rules/callout/callout.js"];
|
|
15799
15799
|
if (debug === true) {
|
|
15800
15800
|
debug = (e, ...args) => console.debug(`"${e.type}" -> `, ...args);
|
|
15801
15801
|
}
|
|
@@ -20787,7 +20787,9 @@ const swipeTypeOf = (axis, pulled) => {
|
|
|
20787
20787
|
* meantime, nothing is picked up. The carry is the element's own, outcomes and
|
|
20788
20788
|
* refusal included, without the wait for intent (the hold was the proof), and
|
|
20789
20789
|
* the copy is brought to the finger rather than following it from wherever the
|
|
20790
|
-
* element stands.
|
|
20790
|
+
* element stands. Let go of there before it has travelled — the hold only meant
|
|
20791
|
+
* to open the popup — it goes back and nothing is answered, whatever it was
|
|
20792
|
+
* brought over. A copy or nothing: `move` and `moving` carry the thing itself,
|
|
20791
20793
|
* which would leave its place just for being handed a press. When it starts is
|
|
20792
20794
|
* navi's — after a popup still being lifted (see `--navi-grab` in commands.js).
|
|
20793
20795
|
*
|
|
@@ -30886,6 +30888,12 @@ const useUrlSearchParam = (paramName, defaultValue) => {
|
|
|
30886
30888
|
return [value, setSearchParamValue];
|
|
30887
30889
|
};
|
|
30888
30890
|
|
|
30891
|
+
// The title belongs to the last Head to arrive, whatever order they leave in:
|
|
30892
|
+
// the page being left by a route transition is taken down AFTER the page
|
|
30893
|
+
// arriving is up (see keepLeavingPages in route.jsx), and putting back the
|
|
30894
|
+
// title it found would put its own page's title over the new one.
|
|
30895
|
+
const titleEntries = [];
|
|
30896
|
+
let titleWithoutHead = null;
|
|
30889
30897
|
const Head = ({
|
|
30890
30898
|
children
|
|
30891
30899
|
}) => {
|
|
@@ -30894,15 +30902,17 @@ const Head = ({
|
|
|
30894
30902
|
return undefined;
|
|
30895
30903
|
}
|
|
30896
30904
|
const childArray = Array.isArray(children) ? children : [children];
|
|
30897
|
-
const previousTitle = document.title;
|
|
30898
30905
|
const appendedElements = [];
|
|
30906
|
+
let titleEntry = null;
|
|
30899
30907
|
for (const child of childArray) {
|
|
30900
30908
|
if (!child) {
|
|
30901
30909
|
continue;
|
|
30902
30910
|
}
|
|
30903
30911
|
if (child.type === "title") {
|
|
30904
30912
|
const titleChildren = child.props.children;
|
|
30905
|
-
|
|
30913
|
+
titleEntry = {
|
|
30914
|
+
title: Array.isArray(titleChildren) ? titleChildren.join("") : titleChildren ?? ""
|
|
30915
|
+
};
|
|
30906
30916
|
continue;
|
|
30907
30917
|
}
|
|
30908
30918
|
const el = document.createElement(child.type);
|
|
@@ -30913,8 +30923,19 @@ const Head = ({
|
|
|
30913
30923
|
document.head.appendChild(el);
|
|
30914
30924
|
appendedElements.push(el);
|
|
30915
30925
|
}
|
|
30926
|
+
if (titleEntry) {
|
|
30927
|
+
if (titleEntries.length === 0) {
|
|
30928
|
+
titleWithoutHead = document.title;
|
|
30929
|
+
}
|
|
30930
|
+
titleEntries.push(titleEntry);
|
|
30931
|
+
document.title = titleEntry.title;
|
|
30932
|
+
}
|
|
30916
30933
|
return () => {
|
|
30917
|
-
|
|
30934
|
+
if (titleEntry) {
|
|
30935
|
+
titleEntries.splice(titleEntries.indexOf(titleEntry), 1);
|
|
30936
|
+
const lastEntry = titleEntries[titleEntries.length - 1];
|
|
30937
|
+
document.title = lastEntry ? lastEntry.title : titleWithoutHead;
|
|
30938
|
+
}
|
|
30918
30939
|
for (const el of appendedElements) {
|
|
30919
30940
|
el.remove();
|
|
30920
30941
|
}
|
|
@@ -31077,75 +31098,7 @@ const samePages = (pages, otherPages) => {
|
|
|
31077
31098
|
return true;
|
|
31078
31099
|
};
|
|
31079
31100
|
|
|
31080
|
-
|
|
31081
|
-
* Route is the single primitive for URL-based rendering.
|
|
31082
|
-
*
|
|
31083
|
-
* ## Layout pattern
|
|
31084
|
-
* Use this when multiple routes share a common layout but have no shared URL prefix,
|
|
31085
|
-
* making it impossible to set a guard route on the parent container.
|
|
31086
|
-
* For example, `/profile` and `/settings` both live inside `AuthLayout` but there
|
|
31087
|
-
* is no `/auth/` prefix to match on. A container Route wraps them: the active
|
|
31088
|
-
* child's element is injected as `children` into the layout element.
|
|
31089
|
-
* If a page needs state owned by the layout, the layout must expose it via context.
|
|
31090
|
-
*
|
|
31091
|
-
* ```jsx
|
|
31092
|
-
* const PROFILE_ROUTE = route("/profile");
|
|
31093
|
-
* const SETTINGS_ROUTE = route("/settings");
|
|
31094
|
-
*
|
|
31095
|
-
* <Route element={AuthLayout}>
|
|
31096
|
-
* <Route route={PROFILE_ROUTE} element={ProfilePage} />
|
|
31097
|
-
* <Route route={SETTINGS_ROUTE} element={SettingsPage} />
|
|
31098
|
-
* </Route>
|
|
31099
|
-
* ```
|
|
31100
|
-
*
|
|
31101
|
-
* Such a container holds no fallback, and cannot: what makes this one the right
|
|
31102
|
-
* layout is a child matching, and having no prefix is the very reason it was
|
|
31103
|
-
* reached for — so there is no address that belongs to it and to none of its
|
|
31104
|
-
* children. An address nothing claims is the router's to answer; write the
|
|
31105
|
-
* fallback there.
|
|
31106
|
-
*
|
|
31107
|
-
* ## Self-contained section pattern
|
|
31108
|
-
* Use this when routes share a common URL prefix (e.g. `/dashboard/`).
|
|
31109
|
-
* A single leaf Route in the top-level router matches the prefix; the component
|
|
31110
|
-
* it renders owns its sub-router and all related routes internally.
|
|
31111
|
-
* Everything about the section — routes, structure, sub-pages — is co-located.
|
|
31112
|
-
* The component is not a reusable layout; it is the section.
|
|
31113
|
-
*
|
|
31114
|
-
* Compared to the layout pattern, a dedicated section component is more powerful:
|
|
31115
|
-
* - Wrapper elements (chrome, nav, containers) are part of the component's render,
|
|
31116
|
-
* not injected via `children`, so a layout is not needed.
|
|
31117
|
-
* - Local state can be passed directly via `elementProps` to sub-pages. With the
|
|
31118
|
-
* layout pattern, sub-pages receive state only through `children` or context.
|
|
31119
|
-
*
|
|
31120
|
-
* The layout pattern remains necessary when a shared prefix does not exist
|
|
31121
|
-
* (see "Layout pattern" above).
|
|
31122
|
-
*
|
|
31123
|
-
* ```jsx
|
|
31124
|
-
* const DASHBOARD_SECTION_ROUTE = route("/dashboard/");
|
|
31125
|
-
* const DASHBOARD_HOME_ROUTE = route("/dashboard");
|
|
31126
|
-
* const DASHBOARD_POSTS_ROUTE = route("/dashboard/posts");
|
|
31127
|
-
*
|
|
31128
|
-
* // top-level router — only knows about the prefix
|
|
31129
|
-
* <Route route={DASHBOARD_SECTION_ROUTE} element={DashboardSection} />
|
|
31130
|
-
*
|
|
31131
|
-
* // Dashboard owns the rest
|
|
31132
|
-
* const DashboardSection = () => {
|
|
31133
|
-
* const [sidebarOpen, setSidebarOpen] = useState(false);
|
|
31134
|
-
*
|
|
31135
|
-
* return <div
|
|
31136
|
-
* style="background: lightblue; padding: 10px;"
|
|
31137
|
-
* onClick={() => setSidebarOpen(o => !o)}
|
|
31138
|
-
* >
|
|
31139
|
-
* <Route>
|
|
31140
|
-
* <Route route={DASHBOARD_HOME_ROUTE} element={DashboardHomePage} elementProps={{ sidebarOpen}} />
|
|
31141
|
-
* <Route route={DASHBOARD_POSTS_ROUTE} element={DashboardPostsPage} elementProps={{ sidebarOpen }} />
|
|
31142
|
-
* <Route fallback element={DashboardNotFound} />
|
|
31143
|
-
* </Route>
|
|
31144
|
-
* </div>;
|
|
31145
|
-
* }
|
|
31146
|
-
* ```
|
|
31147
|
-
*/
|
|
31148
|
-
|
|
31101
|
+
installImportMetaCssBuild(import.meta);
|
|
31149
31102
|
|
|
31150
31103
|
/**
|
|
31151
31104
|
* Keep every container showing the page it is showing, whatever the routes say.
|
|
@@ -31169,6 +31122,56 @@ const freezeRouteRender = () => {
|
|
|
31169
31122
|
routeRenderFrozenSignal.value++;
|
|
31170
31123
|
};
|
|
31171
31124
|
};
|
|
31125
|
+
|
|
31126
|
+
/**
|
|
31127
|
+
* Keep the page a container leaves, hidden, until its route transition is over.
|
|
31128
|
+
*
|
|
31129
|
+
* The browser photographs the page being left before the change, and the page
|
|
31130
|
+
* arriving inside the transition's update callback — where everything done
|
|
31131
|
+
* delays the movement. Taking the page being left down is most of that: every
|
|
31132
|
+
* hook of every component in it is cleaned up, and a page of thirty cards
|
|
31133
|
+
* takes longer to take down than the page arriving takes to build. Its picture
|
|
31134
|
+
* is already taken, so it only has to stay out of the second one: a container
|
|
31135
|
+
* that changes page while this is held keeps the page it was showing, hidden,
|
|
31136
|
+
* and drops it once the movement is over (see route_transition.jsx).
|
|
31137
|
+
*
|
|
31138
|
+
* Kept only where Preact would have unmounted it: a page rendered by the same
|
|
31139
|
+
* element on both sides is the same component instance carried over, exactly
|
|
31140
|
+
* as without a movement.
|
|
31141
|
+
*/
|
|
31142
|
+
let leavingPagesHold = null;
|
|
31143
|
+
const keepLeavingPages = () => {
|
|
31144
|
+
const hold = {
|
|
31145
|
+
released: false,
|
|
31146
|
+
containers: new Set()
|
|
31147
|
+
};
|
|
31148
|
+
leavingPagesHold = hold;
|
|
31149
|
+
return () => {
|
|
31150
|
+
if (hold.released) {
|
|
31151
|
+
return;
|
|
31152
|
+
}
|
|
31153
|
+
hold.released = true;
|
|
31154
|
+
if (leavingPagesHold === hold) {
|
|
31155
|
+
leavingPagesHold = null;
|
|
31156
|
+
}
|
|
31157
|
+
for (const rerender of hold.containers) {
|
|
31158
|
+
rerender();
|
|
31159
|
+
}
|
|
31160
|
+
hold.containers.clear();
|
|
31161
|
+
};
|
|
31162
|
+
};
|
|
31163
|
+
|
|
31164
|
+
// What a page can learn about its place from the container rendering it:
|
|
31165
|
+
// whether it is a page kept while leaving (see keepLeavingPages). Such a page
|
|
31166
|
+
// is still mounted, and whatever it fills OUTSIDE its own nodes — a slot in a
|
|
31167
|
+
// bar, say — would otherwise go on showing with the page arriving (see
|
|
31168
|
+
// layout/slot.jsx).
|
|
31169
|
+
const RoutePageContext = createContext(null);
|
|
31170
|
+
const LEAVING_ATTRIBUTE = "data-navi-route-leaving";
|
|
31171
|
+
const css$13 = /* css */`[data-navi-route-leaving] {
|
|
31172
|
+
display: none !important;
|
|
31173
|
+
}
|
|
31174
|
+
`;
|
|
31172
31175
|
const debug$1 = (...args) => {
|
|
31173
31176
|
{
|
|
31174
31177
|
return;
|
|
@@ -31288,6 +31291,7 @@ const RouteContainer = ({
|
|
|
31288
31291
|
shownBranchRef.current = activeBranch;
|
|
31289
31292
|
}
|
|
31290
31293
|
const branch = shownBranchRef.current || activeBranch;
|
|
31294
|
+
const content = useContentKeepingLeavingPages(branch);
|
|
31291
31295
|
|
|
31292
31296
|
// The two things this component knows that nobody outside can find out: the
|
|
31293
31297
|
// pages a named fallback is the absence of — the children it was written
|
|
@@ -31309,7 +31313,6 @@ const RouteContainer = ({
|
|
|
31309
31313
|
};
|
|
31310
31314
|
}, [fallbackPage]);
|
|
31311
31315
|
debug$1(`[container "${id}"] RENDER, active=${branch ? branch.type : "none"}`);
|
|
31312
|
-
const content = branch ? branch.node : null;
|
|
31313
31316
|
if (!content) {
|
|
31314
31317
|
return null;
|
|
31315
31318
|
}
|
|
@@ -31318,12 +31321,141 @@ const RouteContainer = ({
|
|
|
31318
31321
|
}
|
|
31319
31322
|
return content;
|
|
31320
31323
|
};
|
|
31324
|
+
// What a container renders: the page it shows and, while a route transition
|
|
31325
|
+
// keeps them (see keepLeavingPages), the pages it has left — each the very
|
|
31326
|
+
// vnode rendered last time, which Preact does not look into, between two
|
|
31327
|
+
// markers that say which nodes to hide. Always an array, even of one page: the
|
|
31328
|
+
// page being left must stay the child it was when a page is added beside it,
|
|
31329
|
+
// or Preact takes it down and builds it again.
|
|
31330
|
+
let leavingKeyCount = 0;
|
|
31331
|
+
const useContentKeepingLeavingPages = branch => {
|
|
31332
|
+
const [, rerender] = useReducer(countRenders, 0);
|
|
31333
|
+
const shownRef = useRef(null);
|
|
31334
|
+
const leavingRef = useRef([]);
|
|
31335
|
+
const shown = shownRef.current;
|
|
31336
|
+
const element = branchElement(branch);
|
|
31337
|
+
let key;
|
|
31338
|
+
let page = null;
|
|
31339
|
+
if (shown && branch && (shown.id === branch.id || shown.element === element)) {
|
|
31340
|
+
// The same page, or one Preact carries over from it: the key it was
|
|
31341
|
+
// mounted with, or it would be mounted again.
|
|
31342
|
+
key = shown.key;
|
|
31343
|
+
page = shown.page;
|
|
31344
|
+
} else if (shown && leavingPagesHold) {
|
|
31345
|
+
leavingRef.current.push({
|
|
31346
|
+
vnode: shown.vnode,
|
|
31347
|
+
page: shown.page,
|
|
31348
|
+
key: `navi-route-leaving-${++leavingKeyCount}`,
|
|
31349
|
+
hold: leavingPagesHold,
|
|
31350
|
+
startRef: createRef(),
|
|
31351
|
+
endRef: createRef(),
|
|
31352
|
+
hidden: false
|
|
31353
|
+
});
|
|
31354
|
+
leavingPagesHold.containers.add(rerender);
|
|
31355
|
+
// Keyed apart from the page it takes the place of, which is still there.
|
|
31356
|
+
key = `navi-route-${++leavingKeyCount}`;
|
|
31357
|
+
}
|
|
31358
|
+
let vnode = null;
|
|
31359
|
+
if (branch) {
|
|
31360
|
+
if (!page) {
|
|
31361
|
+
page = {
|
|
31362
|
+
leavingSignal: signal(false)
|
|
31363
|
+
};
|
|
31364
|
+
}
|
|
31365
|
+
vnode = h(RoutePageContext.Provider, {
|
|
31366
|
+
key,
|
|
31367
|
+
value: page
|
|
31368
|
+
}, branch.node);
|
|
31369
|
+
}
|
|
31370
|
+
shownRef.current = branch ? {
|
|
31371
|
+
id: branch.id,
|
|
31372
|
+
element,
|
|
31373
|
+
key,
|
|
31374
|
+
vnode,
|
|
31375
|
+
page
|
|
31376
|
+
} : null;
|
|
31377
|
+
const leaving = leavingRef.current.filter(entry => !entry.hold.released);
|
|
31378
|
+
leavingRef.current = leaving;
|
|
31379
|
+
|
|
31380
|
+
// Hidden as soon as it is in the DOM next to the page arriving: this runs in
|
|
31381
|
+
// the update callback's render, before the second picture is taken.
|
|
31382
|
+
useLayoutEffect(() => {
|
|
31383
|
+
for (const entry of leavingRef.current) {
|
|
31384
|
+
const start = entry.startRef.current;
|
|
31385
|
+
const end = entry.endRef.current;
|
|
31386
|
+
if (entry.hidden || !start || !end) {
|
|
31387
|
+
continue;
|
|
31388
|
+
}
|
|
31389
|
+
entry.hidden = true;
|
|
31390
|
+
entry.page.leavingSignal.value = true;
|
|
31391
|
+
let node = start.nextSibling;
|
|
31392
|
+
while (node && node !== end) {
|
|
31393
|
+
if (node.nodeType === Node.ELEMENT_NODE) {
|
|
31394
|
+
node.setAttribute(LEAVING_ATTRIBUTE, "");
|
|
31395
|
+
}
|
|
31396
|
+
node = node.nextSibling;
|
|
31397
|
+
}
|
|
31398
|
+
}
|
|
31399
|
+
});
|
|
31400
|
+
useLayoutEffect(() => {
|
|
31401
|
+
return () => {
|
|
31402
|
+
for (const entry of leavingRef.current) {
|
|
31403
|
+
entry.hold.containers.delete(rerender);
|
|
31404
|
+
}
|
|
31405
|
+
};
|
|
31406
|
+
}, []);
|
|
31407
|
+
if (leaving.length === 0) {
|
|
31408
|
+
return vnode ? [vnode] : null;
|
|
31409
|
+
}
|
|
31410
|
+
import.meta.css = [css$13, "@jsenv/navi/src/nav/route.jsx"];
|
|
31411
|
+
const children = vnode ? [vnode] : [];
|
|
31412
|
+
for (const entry of leaving) {
|
|
31413
|
+
children.push(h("template", {
|
|
31414
|
+
key: `${entry.key}-start`,
|
|
31415
|
+
ref: entry.startRef
|
|
31416
|
+
}), entry.vnode, h("template", {
|
|
31417
|
+
key: `${entry.key}-end`,
|
|
31418
|
+
ref: entry.endRef
|
|
31419
|
+
}));
|
|
31420
|
+
}
|
|
31421
|
+
return children;
|
|
31422
|
+
};
|
|
31423
|
+
const countRenders = count => count + 1;
|
|
31424
|
+
// What Preact compares when a container changes page, below the <Route> it
|
|
31425
|
+
// renders either way: the element the page is rendered with — a layout, for a
|
|
31426
|
+
// container branch.
|
|
31427
|
+
const branchElement = branch => {
|
|
31428
|
+
if (!branch) {
|
|
31429
|
+
return null;
|
|
31430
|
+
}
|
|
31431
|
+
let node = branch.node;
|
|
31432
|
+
while (node && node.type !== Route) {
|
|
31433
|
+
// A wrapper around the branch (see wrapBranch).
|
|
31434
|
+
node = node.props.children;
|
|
31435
|
+
}
|
|
31436
|
+
if (!node) {
|
|
31437
|
+
return null;
|
|
31438
|
+
}
|
|
31439
|
+
const {
|
|
31440
|
+
element
|
|
31441
|
+
} = node.props;
|
|
31442
|
+
if (element === undefined || typeof element === "function") {
|
|
31443
|
+
return element;
|
|
31444
|
+
}
|
|
31445
|
+
return element.type;
|
|
31446
|
+
};
|
|
31447
|
+
|
|
31321
31448
|
// Walk JSX children vnodes (without rendering) to build a branch list and
|
|
31322
31449
|
// find the active one in the same pass. Anything that is not a <Route> is read
|
|
31323
31450
|
// through and kept around the branch it holds (see below).
|
|
31324
31451
|
// Returns { matchingBranch, fallbackBranch, activeBranch, pages }.
|
|
31325
|
-
|
|
31452
|
+
//
|
|
31453
|
+
// Each branch is given an id from where it is written among the children,
|
|
31454
|
+
// which is what tells a container it changed page: the vnodes themselves are
|
|
31455
|
+
// new at every render of the parent.
|
|
31456
|
+
const collectBranches = (children, path = "") => {
|
|
31326
31457
|
let matchingBranch = null;
|
|
31458
|
+
let childIndex = 0;
|
|
31327
31459
|
let fallbackBranch = null;
|
|
31328
31460
|
// Every page a branch can be on, at any depth: what a named fallback is the
|
|
31329
31461
|
// ABSENCE of (see route_fallback.js). A container with a guard route counts
|
|
@@ -31341,6 +31473,7 @@ const collectBranches = children => {
|
|
|
31341
31473
|
}
|
|
31342
31474
|
return;
|
|
31343
31475
|
}
|
|
31476
|
+
const id = `${path}${childIndex++}`;
|
|
31344
31477
|
if (child.type !== Route) {
|
|
31345
31478
|
// Anything else is a wrapper around branches, and the two that matter are
|
|
31346
31479
|
// navi's own: a page says what it renders and delegates what it cannot —
|
|
@@ -31360,7 +31493,7 @@ const collectBranches = children => {
|
|
|
31360
31493
|
matchingBranch: matchingInside,
|
|
31361
31494
|
fallbackBranch: fallbackInside,
|
|
31362
31495
|
pages: pagesInside
|
|
31363
|
-
} = collectBranches(wrapperChildren);
|
|
31496
|
+
} = collectBranches(wrapperChildren, `${id}.`);
|
|
31364
31497
|
for (const pageInside of pagesInside) {
|
|
31365
31498
|
pages.push(pageInside);
|
|
31366
31499
|
}
|
|
@@ -31383,7 +31516,7 @@ const collectBranches = children => {
|
|
|
31383
31516
|
matchingBranch: matchingChild,
|
|
31384
31517
|
fallbackBranch: fallbackChild,
|
|
31385
31518
|
pages: pagesChild
|
|
31386
|
-
} = collectBranches(nodeChildren);
|
|
31519
|
+
} = collectBranches(nodeChildren, `${id}.`);
|
|
31387
31520
|
if (fallbackChild && !route) {
|
|
31388
31521
|
// A fallback is the branch taken for an address none of its siblings
|
|
31389
31522
|
// claim — so something has to make that address BELONG to this
|
|
@@ -31407,6 +31540,7 @@ const collectBranches = children => {
|
|
|
31407
31540
|
}
|
|
31408
31541
|
const branch = {
|
|
31409
31542
|
type: "container",
|
|
31543
|
+
id,
|
|
31410
31544
|
node: child
|
|
31411
31545
|
};
|
|
31412
31546
|
const guardMatching = route ? route.matchingSignal.value : false;
|
|
@@ -31424,6 +31558,7 @@ const collectBranches = children => {
|
|
|
31424
31558
|
if (!fallbackBranch) {
|
|
31425
31559
|
fallbackBranch = {
|
|
31426
31560
|
type: "fallback",
|
|
31561
|
+
id,
|
|
31427
31562
|
node: child,
|
|
31428
31563
|
page: fallback.isRouteFallback ? fallback : null
|
|
31429
31564
|
};
|
|
@@ -31431,6 +31566,7 @@ const collectBranches = children => {
|
|
|
31431
31566
|
} else {
|
|
31432
31567
|
const branch = {
|
|
31433
31568
|
type: "leaf",
|
|
31569
|
+
id,
|
|
31434
31570
|
node: child
|
|
31435
31571
|
};
|
|
31436
31572
|
pages.push({
|
|
@@ -31878,7 +32014,7 @@ const holdTransitionFurniture = (owner, areaElement) => {
|
|
|
31878
32014
|
}
|
|
31879
32015
|
const namesLeaving = [];
|
|
31880
32016
|
for (const element of namedElements) {
|
|
31881
|
-
if (!element
|
|
32017
|
+
if (!isRendered(element)) {
|
|
31882
32018
|
namesLeaving.push(nameByElement.get(element));
|
|
31883
32019
|
} else if (element.matches(FIXED_BAR_SELECTOR$1)) {
|
|
31884
32020
|
element.setAttribute(FURNITURE_ATTRIBUTE, "shared");
|
|
@@ -31997,11 +32133,16 @@ const travelRule = (side, names, movementProperty) => {
|
|
|
31997
32133
|
* The pictures are up and about to move: what no picture covers heads to the
|
|
31998
32134
|
* state arriving, on the same clock.
|
|
31999
32135
|
*/
|
|
32000
|
-
const startTransitionFurniture = (owner) => {
|
|
32136
|
+
const startTransitionFurniture = (owner, { duration } = {}) => {
|
|
32001
32137
|
if (owner !== furnitureOwner) {
|
|
32002
32138
|
return;
|
|
32003
32139
|
}
|
|
32004
32140
|
for (const restWall of restWallElements) {
|
|
32141
|
+
// A duration of the movement's own is written for its pictures alone (see
|
|
32142
|
+
// transition_values.js); the stand-in is an element, and is told.
|
|
32143
|
+
if (duration !== undefined) {
|
|
32144
|
+
restWall.style.setProperty("--navi-route-transition-duration", duration);
|
|
32145
|
+
}
|
|
32005
32146
|
restWall.style.opacity = restWallOpacity;
|
|
32006
32147
|
}
|
|
32007
32148
|
};
|
|
@@ -32032,7 +32173,9 @@ const releaseTransitionFurniture = (owner) => {
|
|
|
32032
32173
|
// area's stand-in answers for it.
|
|
32033
32174
|
const paintTransitionWalls = (areaElement) => {
|
|
32034
32175
|
removeTransitionWalls();
|
|
32035
|
-
const sources =
|
|
32176
|
+
const sources = Array.from(
|
|
32177
|
+
document.querySelectorAll(TOP_LAYER_WALL_SELECTOR),
|
|
32178
|
+
).filter(isRendered);
|
|
32036
32179
|
if (sources.length === 0) {
|
|
32037
32180
|
return sources;
|
|
32038
32181
|
}
|
|
@@ -32234,6 +32377,14 @@ const subtractRect = (rect, hole) => {
|
|
|
32234
32377
|
return pieces;
|
|
32235
32378
|
};
|
|
32236
32379
|
|
|
32380
|
+
// Out of the state arriving: taken out of the document, or in a page kept
|
|
32381
|
+
// hidden until its movement is over (see keepLeavingPages in route.jsx) —
|
|
32382
|
+
// where a dialog is still :modal and a popover still :popover-open, and
|
|
32383
|
+
// neither is painted or photographed.
|
|
32384
|
+
const isRendered = (element) => {
|
|
32385
|
+
return element.isConnected && element.checkVisibility();
|
|
32386
|
+
};
|
|
32387
|
+
|
|
32237
32388
|
const removeRestWalls = () => {
|
|
32238
32389
|
for (const restWall of restWallElements) {
|
|
32239
32390
|
restWall.remove();
|
|
@@ -32243,6 +32394,52 @@ const removeRestWalls = () => {
|
|
|
32243
32394
|
leavingRects = new Map();
|
|
32244
32395
|
};
|
|
32245
32396
|
|
|
32397
|
+
/**
|
|
32398
|
+
* The values a movement hands to its pictures, written where only the pictures
|
|
32399
|
+
* read them: on ::view-transition, the root of the pseudo-element tree, rather
|
|
32400
|
+
* than on the document's root.
|
|
32401
|
+
*
|
|
32402
|
+
* A custom property written on :root is inherited by every element of the
|
|
32403
|
+
* document, and writing one restyles all of them. A movement writes its
|
|
32404
|
+
* numbers as its pages are held, again whenever a scroll moves the window, and
|
|
32405
|
+
* takes them off as it ends — each time a whole-document restyle of a page that
|
|
32406
|
+
* can be thousands of elements long. On ::view-transition they reach every
|
|
32407
|
+
* picture by plain inheritance, and no element at all.
|
|
32408
|
+
*
|
|
32409
|
+
* An inline style cannot target a pseudo-element, so they are declarations of
|
|
32410
|
+
* one rule, in a sheet of their own. Written only: what a pseudo-element that
|
|
32411
|
+
* is not on screen computes is not reliably readable, so nothing reads them
|
|
32412
|
+
* back from there.
|
|
32413
|
+
*/
|
|
32414
|
+
|
|
32415
|
+
let valuesStyle = null;
|
|
32416
|
+
const getValuesStyle = () => {
|
|
32417
|
+
if (valuesStyle) {
|
|
32418
|
+
return valuesStyle;
|
|
32419
|
+
}
|
|
32420
|
+
const sheet = new CSSStyleSheet();
|
|
32421
|
+
sheet.replaceSync(":root::view-transition {}");
|
|
32422
|
+
const [rule] = sheet.cssRules;
|
|
32423
|
+
if (rule) {
|
|
32424
|
+
document.adoptedStyleSheets.push(sheet);
|
|
32425
|
+
valuesStyle = rule.style;
|
|
32426
|
+
} else {
|
|
32427
|
+
// A browser without view transitions drops the rule: the movement runs its
|
|
32428
|
+
// steps all the same (see start_view_transition_polyfill.js), with no
|
|
32429
|
+
// pictures to hand anything to.
|
|
32430
|
+
valuesStyle = document.createElement("div").style;
|
|
32431
|
+
}
|
|
32432
|
+
return valuesStyle;
|
|
32433
|
+
};
|
|
32434
|
+
|
|
32435
|
+
const setTransitionValue = (name, value) => {
|
|
32436
|
+
getValuesStyle().setProperty(name, value);
|
|
32437
|
+
};
|
|
32438
|
+
|
|
32439
|
+
const removeTransitionValue = (name) => {
|
|
32440
|
+
getValuesStyle().removeProperty(name);
|
|
32441
|
+
};
|
|
32442
|
+
|
|
32246
32443
|
installImportMetaCssBuild(import.meta);
|
|
32247
32444
|
|
|
32248
32445
|
const TRANSITION_WINDOW_CSS = /* css */ `@property --navi-transition-cover-top {
|
|
@@ -32277,96 +32474,6 @@ const TRANSITION_WINDOW_CSS = /* css */ `@property --navi-transition-cover-top {
|
|
|
32277
32474
|
--navi-transition-cover-left: 0px;
|
|
32278
32475
|
}
|
|
32279
32476
|
}
|
|
32280
|
-
|
|
32281
|
-
@property --navi-transition-window-top {
|
|
32282
|
-
syntax: "*";
|
|
32283
|
-
inherits: false
|
|
32284
|
-
}
|
|
32285
|
-
|
|
32286
|
-
@property --navi-transition-window-left {
|
|
32287
|
-
syntax: "*";
|
|
32288
|
-
inherits: false
|
|
32289
|
-
}
|
|
32290
|
-
|
|
32291
|
-
@property --navi-transition-window-width {
|
|
32292
|
-
syntax: "*";
|
|
32293
|
-
inherits: false
|
|
32294
|
-
}
|
|
32295
|
-
|
|
32296
|
-
@property --navi-transition-window-height {
|
|
32297
|
-
syntax: "*";
|
|
32298
|
-
inherits: false
|
|
32299
|
-
}
|
|
32300
|
-
|
|
32301
|
-
@property --navi-transition-window-old-top {
|
|
32302
|
-
syntax: "*";
|
|
32303
|
-
inherits: false
|
|
32304
|
-
}
|
|
32305
|
-
|
|
32306
|
-
@property --navi-transition-window-old-left {
|
|
32307
|
-
syntax: "*";
|
|
32308
|
-
inherits: false
|
|
32309
|
-
}
|
|
32310
|
-
|
|
32311
|
-
@property --navi-transition-window-new-top {
|
|
32312
|
-
syntax: "*";
|
|
32313
|
-
inherits: false
|
|
32314
|
-
}
|
|
32315
|
-
|
|
32316
|
-
@property --navi-transition-window-new-left {
|
|
32317
|
-
syntax: "*";
|
|
32318
|
-
inherits: false
|
|
32319
|
-
}
|
|
32320
|
-
|
|
32321
|
-
@property --navi-transition-old-band-top {
|
|
32322
|
-
syntax: "*";
|
|
32323
|
-
inherits: false
|
|
32324
|
-
}
|
|
32325
|
-
|
|
32326
|
-
@property --navi-transition-old-band-right {
|
|
32327
|
-
syntax: "*";
|
|
32328
|
-
inherits: false
|
|
32329
|
-
}
|
|
32330
|
-
|
|
32331
|
-
@property --navi-transition-old-band-bottom {
|
|
32332
|
-
syntax: "*";
|
|
32333
|
-
inherits: false
|
|
32334
|
-
}
|
|
32335
|
-
|
|
32336
|
-
@property --navi-transition-old-band-left {
|
|
32337
|
-
syntax: "*";
|
|
32338
|
-
inherits: false
|
|
32339
|
-
}
|
|
32340
|
-
|
|
32341
|
-
:root::view-transition, :root::view-transition-group(*), :root::view-transition-image-pair(*), :root::view-transition-old(*), :root::view-transition-new(*) {
|
|
32342
|
-
--navi-transition-window-top: inherit;
|
|
32343
|
-
--navi-transition-window-left: inherit;
|
|
32344
|
-
--navi-transition-window-width: inherit;
|
|
32345
|
-
--navi-transition-window-height: inherit;
|
|
32346
|
-
--navi-transition-window-old-top: inherit;
|
|
32347
|
-
--navi-transition-window-old-left: inherit;
|
|
32348
|
-
--navi-transition-window-new-top: inherit;
|
|
32349
|
-
--navi-transition-window-new-left: inherit;
|
|
32350
|
-
--navi-transition-old-band-top: inherit;
|
|
32351
|
-
--navi-transition-old-band-right: inherit;
|
|
32352
|
-
--navi-transition-old-band-bottom: inherit;
|
|
32353
|
-
--navi-transition-old-band-left: inherit;
|
|
32354
|
-
}
|
|
32355
|
-
|
|
32356
|
-
:root::view-transition-group-children(*) {
|
|
32357
|
-
--navi-transition-window-top: inherit;
|
|
32358
|
-
--navi-transition-window-left: inherit;
|
|
32359
|
-
--navi-transition-window-width: inherit;
|
|
32360
|
-
--navi-transition-window-height: inherit;
|
|
32361
|
-
--navi-transition-window-old-top: inherit;
|
|
32362
|
-
--navi-transition-window-old-left: inherit;
|
|
32363
|
-
--navi-transition-window-new-top: inherit;
|
|
32364
|
-
--navi-transition-window-new-left: inherit;
|
|
32365
|
-
--navi-transition-old-band-top: inherit;
|
|
32366
|
-
--navi-transition-old-band-right: inherit;
|
|
32367
|
-
--navi-transition-old-band-bottom: inherit;
|
|
32368
|
-
--navi-transition-old-band-left: inherit;
|
|
32369
|
-
}
|
|
32370
32477
|
`;
|
|
32371
32478
|
|
|
32372
32479
|
// Called by whatever needs the window — a render, a movement declared or
|
|
@@ -32464,22 +32571,21 @@ const holdTransitionWindow = (
|
|
|
32464
32571
|
const right =
|
|
32465
32572
|
rectBefore.right > rectAfter.right ? rectBefore.right : rectAfter.right;
|
|
32466
32573
|
windowOwner = owner;
|
|
32467
|
-
|
|
32468
|
-
|
|
32469
|
-
|
|
32470
|
-
|
|
32471
|
-
|
|
32472
|
-
|
|
32473
|
-
|
|
32474
|
-
|
|
32475
|
-
style.setProperty(WINDOW_NEW_LEFT_PROPERTY, `${rectAfter.left}px`);
|
|
32574
|
+
setTransitionValue(WINDOW_TOP_PROPERTY, `${top}px`);
|
|
32575
|
+
setTransitionValue(WINDOW_LEFT_PROPERTY, `${left}px`);
|
|
32576
|
+
setTransitionValue(WINDOW_WIDTH_PROPERTY, `${right - left}px`);
|
|
32577
|
+
setTransitionValue(WINDOW_HEIGHT_PROPERTY, `${bottom - top}px`);
|
|
32578
|
+
setTransitionValue(WINDOW_OLD_TOP_PROPERTY, `${rectBefore.top}px`);
|
|
32579
|
+
setTransitionValue(WINDOW_OLD_LEFT_PROPERTY, `${rectBefore.left}px`);
|
|
32580
|
+
setTransitionValue(WINDOW_NEW_TOP_PROPERTY, `${rectAfter.top}px`);
|
|
32581
|
+
setTransitionValue(WINDOW_NEW_LEFT_PROPERTY, `${rectAfter.left}px`);
|
|
32476
32582
|
const oldBand = furnitureLive
|
|
32477
32583
|
? bandTheCutMayBeRelaxedTo(bandBefore, bandAfter, rectAfter)
|
|
32478
32584
|
: bandBefore;
|
|
32479
|
-
|
|
32480
|
-
|
|
32481
|
-
|
|
32482
|
-
|
|
32585
|
+
setTransitionValue(OLD_BAND_TOP_PROPERTY, `${oldBand.top}px`);
|
|
32586
|
+
setTransitionValue(OLD_BAND_RIGHT_PROPERTY, `${oldBand.right}px`);
|
|
32587
|
+
setTransitionValue(OLD_BAND_BOTTOM_PROPERTY, `${oldBand.bottom}px`);
|
|
32588
|
+
setTransitionValue(OLD_BAND_LEFT_PROPERTY, `${oldBand.left}px`);
|
|
32483
32589
|
followArrivingState(element, rectAfter, {
|
|
32484
32590
|
outerScroll,
|
|
32485
32591
|
windowTop: top,
|
|
@@ -32501,9 +32607,8 @@ const releaseTransitionWindow = (owner) => {
|
|
|
32501
32607
|
if (unfollowArrivingState) {
|
|
32502
32608
|
unfollowArrivingState();
|
|
32503
32609
|
}
|
|
32504
|
-
const { style } = document.documentElement;
|
|
32505
32610
|
for (const property of WINDOW_PROPERTIES) {
|
|
32506
|
-
|
|
32611
|
+
removeTransitionValue(property);
|
|
32507
32612
|
}
|
|
32508
32613
|
};
|
|
32509
32614
|
|
|
@@ -32512,12 +32617,11 @@ const releaseTransitionWindow = (owner) => {
|
|
|
32512
32617
|
// file) — and with it the offset outside the box, which carries the window
|
|
32513
32618
|
// and the corner of the state being left along. Requested, never awaited: the
|
|
32514
32619
|
// first call runs inside the update callback, where a frame cannot come.
|
|
32515
|
-
// Written only when it moved: every write restyles the
|
|
32620
|
+
// Written only when it moved: every write restyles the pictures.
|
|
32516
32621
|
const followArrivingState = (element, rectAtHold, heldAt) => {
|
|
32517
32622
|
if (unfollowArrivingState) {
|
|
32518
32623
|
unfollowArrivingState();
|
|
32519
32624
|
}
|
|
32520
|
-
const { style } = document.documentElement;
|
|
32521
32625
|
let top = rectAtHold.top;
|
|
32522
32626
|
let left = rectAtHold.left;
|
|
32523
32627
|
let outerTop = heldAt.outerScroll.top;
|
|
@@ -32526,24 +32630,27 @@ const followArrivingState = (element, rectAtHold, heldAt) => {
|
|
|
32526
32630
|
const rect = element.getBoundingClientRect();
|
|
32527
32631
|
if (rect.top !== top) {
|
|
32528
32632
|
top = rect.top;
|
|
32529
|
-
|
|
32633
|
+
setTransitionValue(WINDOW_NEW_TOP_PROPERTY, `${top}px`);
|
|
32530
32634
|
}
|
|
32531
32635
|
if (rect.left !== left) {
|
|
32532
32636
|
left = rect.left;
|
|
32533
|
-
|
|
32637
|
+
setTransitionValue(WINDOW_NEW_LEFT_PROPERTY, `${left}px`);
|
|
32534
32638
|
}
|
|
32535
32639
|
const outerScroll = readOuterScroll(element);
|
|
32536
32640
|
if (outerScroll.top !== outerTop) {
|
|
32537
32641
|
outerTop = outerScroll.top;
|
|
32538
32642
|
const shift = heldAt.outerScroll.top - outerTop;
|
|
32539
|
-
|
|
32540
|
-
|
|
32643
|
+
setTransitionValue(WINDOW_TOP_PROPERTY, `${heldAt.windowTop + shift}px`);
|
|
32644
|
+
setTransitionValue(WINDOW_OLD_TOP_PROPERTY, `${heldAt.oldTop + shift}px`);
|
|
32541
32645
|
}
|
|
32542
32646
|
if (outerScroll.left !== outerLeft) {
|
|
32543
32647
|
outerLeft = outerScroll.left;
|
|
32544
32648
|
const shift = heldAt.outerScroll.left - outerLeft;
|
|
32545
|
-
|
|
32546
|
-
|
|
32649
|
+
setTransitionValue(
|
|
32650
|
+
WINDOW_LEFT_PROPERTY,
|
|
32651
|
+
`${heldAt.windowLeft + shift}px`,
|
|
32652
|
+
);
|
|
32653
|
+
setTransitionValue(
|
|
32547
32654
|
WINDOW_OLD_LEFT_PROPERTY,
|
|
32548
32655
|
`${heldAt.oldLeft + shift}px`,
|
|
32549
32656
|
);
|
|
@@ -32906,58 +33013,9 @@ const css$12 = /* css */`@property --navi-route-transition-leave {
|
|
|
32906
33013
|
inherits: false
|
|
32907
33014
|
}
|
|
32908
33015
|
|
|
32909
|
-
@property --navi-route-transition-clip-top {
|
|
32910
|
-
syntax: "*";
|
|
32911
|
-
inherits: false
|
|
32912
|
-
}
|
|
32913
|
-
|
|
32914
|
-
@property --navi-route-transition-clip-right {
|
|
32915
|
-
syntax: "*";
|
|
32916
|
-
inherits: false
|
|
32917
|
-
}
|
|
32918
|
-
|
|
32919
|
-
@property --navi-route-transition-clip-bottom {
|
|
32920
|
-
syntax: "*";
|
|
32921
|
-
inherits: false
|
|
32922
|
-
}
|
|
32923
|
-
|
|
32924
|
-
@property --navi-route-transition-clip-left {
|
|
32925
|
-
syntax: "*";
|
|
32926
|
-
inherits: false
|
|
32927
|
-
}
|
|
32928
|
-
|
|
32929
|
-
@property --navi-route-transition-travel-x {
|
|
32930
|
-
syntax: "*";
|
|
32931
|
-
inherits: false
|
|
32932
|
-
}
|
|
32933
|
-
|
|
32934
|
-
@property --navi-route-transition-travel-y {
|
|
32935
|
-
syntax: "*";
|
|
32936
|
-
inherits: false
|
|
32937
|
-
}
|
|
32938
|
-
|
|
32939
33016
|
:root::view-transition, :root::view-transition-group(*), :root::view-transition-image-pair(*), :root::view-transition-old(*), :root::view-transition-new(*) {
|
|
32940
33017
|
--navi-route-transition-leave: inherit;
|
|
32941
33018
|
--navi-route-transition-enter: inherit;
|
|
32942
|
-
--navi-route-transition-covered: inherit;
|
|
32943
|
-
--navi-route-transition-clip-top: inherit;
|
|
32944
|
-
--navi-route-transition-clip-right: inherit;
|
|
32945
|
-
--navi-route-transition-clip-bottom: inherit;
|
|
32946
|
-
--navi-route-transition-clip-left: inherit;
|
|
32947
|
-
--navi-route-transition-travel-x: inherit;
|
|
32948
|
-
--navi-route-transition-travel-y: inherit;
|
|
32949
|
-
}
|
|
32950
|
-
|
|
32951
|
-
:root::view-transition-group-children(*) {
|
|
32952
|
-
--navi-route-transition-leave: inherit;
|
|
32953
|
-
--navi-route-transition-enter: inherit;
|
|
32954
|
-
--navi-route-transition-covered: inherit;
|
|
32955
|
-
--navi-route-transition-clip-top: inherit;
|
|
32956
|
-
--navi-route-transition-clip-right: inherit;
|
|
32957
|
-
--navi-route-transition-clip-bottom: inherit;
|
|
32958
|
-
--navi-route-transition-clip-left: inherit;
|
|
32959
|
-
--navi-route-transition-travel-x: inherit;
|
|
32960
|
-
--navi-route-transition-travel-y: inherit;
|
|
32961
33019
|
}
|
|
32962
33020
|
|
|
32963
33021
|
:root[data-navi-route-transition] [data-navi-route-transition-area] {
|
|
@@ -32978,28 +33036,32 @@ const css$12 = /* css */`@property --navi-route-transition-leave {
|
|
|
32978
33036
|
|
|
32979
33037
|
&[data-navi-route-transition-target="area"] {
|
|
32980
33038
|
view-transition-name: none;
|
|
32981
|
-
|
|
32982
|
-
|
|
32983
|
-
|
|
32984
|
-
|
|
32985
|
-
|
|
32986
|
-
|
|
32987
|
-
|
|
32988
|
-
|
|
32989
|
-
|
|
32990
|
-
|
|
32991
|
-
|
|
32992
|
-
var(--navi-transition-
|
|
32993
|
-
|
|
32994
|
-
|
|
32995
|
-
|
|
32996
|
-
|
|
32997
|
-
|
|
32998
|
-
|
|
32999
|
-
var(--navi-transition-
|
|
33000
|
-
|
|
33001
|
-
|
|
33002
|
-
|
|
33039
|
+
|
|
33040
|
+
&::view-transition {
|
|
33041
|
+
--navi-route-transition-clip-top: max(0px,
|
|
33042
|
+
min(var(--navi-safe-area-inset-top) + var(--navi-transition-cover-top),
|
|
33043
|
+
var(--navi-transition-old-band-top)) - var(--navi-transition-window-top));
|
|
33044
|
+
--navi-route-transition-clip-left: max(0px,
|
|
33045
|
+
min(var(--navi-safe-area-inset-left) +
|
|
33046
|
+
var(--navi-transition-cover-left),
|
|
33047
|
+
var(--navi-transition-old-band-left)) - var(--navi-transition-window-left));
|
|
33048
|
+
--navi-route-transition-clip-bottom: max(0px,
|
|
33049
|
+
var(--navi-transition-window-top) +
|
|
33050
|
+
var(--navi-transition-window-height) +
|
|
33051
|
+
min(var(--navi-safe-area-inset-bottom) +
|
|
33052
|
+
var(--navi-transition-cover-bottom),
|
|
33053
|
+
var(--navi-transition-old-band-bottom)) -
|
|
33054
|
+
100dvh);
|
|
33055
|
+
--navi-route-transition-clip-right: max(0px,
|
|
33056
|
+
var(--navi-transition-window-left) +
|
|
33057
|
+
var(--navi-transition-window-width) +
|
|
33058
|
+
min(var(--navi-safe-area-inset-right) +
|
|
33059
|
+
var(--navi-transition-cover-right),
|
|
33060
|
+
var(--navi-transition-old-band-right)) -
|
|
33061
|
+
100dvw);
|
|
33062
|
+
--navi-route-transition-travel-x: calc(var(--navi-transition-window-width) - var(--navi-route-transition-clip-left) - var(--navi-route-transition-clip-right));
|
|
33063
|
+
--navi-route-transition-travel-y: calc(var(--navi-transition-window-height) - var(--navi-route-transition-clip-top) - var(--navi-route-transition-clip-bottom));
|
|
33064
|
+
}
|
|
33003
33065
|
|
|
33004
33066
|
&::view-transition-group(*) {
|
|
33005
33067
|
z-index: 0;
|
|
@@ -34027,7 +34089,9 @@ const beginTransition = ({
|
|
|
34027
34089
|
decision: navigationDecision,
|
|
34028
34090
|
walkHome: null,
|
|
34029
34091
|
releaseReverting: null,
|
|
34030
|
-
|
|
34092
|
+
duration: undefined,
|
|
34093
|
+
restoreDuration: null,
|
|
34094
|
+
releaseLeavingPages: null
|
|
34031
34095
|
};
|
|
34032
34096
|
// The document wears one transition at a time, and the one this interrupts
|
|
34033
34097
|
// ends only after this one has begun — too late to take off what it wears
|
|
@@ -34080,18 +34144,13 @@ const beginTransition = ({
|
|
|
34080
34144
|
if (areaElement) {
|
|
34081
34145
|
documentElement.setAttribute(TRANSITION_TARGET_ATTRIBUTE, "area");
|
|
34082
34146
|
}
|
|
34083
|
-
// A duration of this relation's own, worn
|
|
34084
|
-
//
|
|
34085
|
-
// erased.
|
|
34147
|
+
// A duration of this relation's own, worn by the pictures for the length of
|
|
34148
|
+
// the transition, over whatever the application says on the root.
|
|
34086
34149
|
if (duration !== undefined) {
|
|
34087
|
-
|
|
34088
|
-
|
|
34150
|
+
transition.duration = typeof duration === "number" ? `${duration}ms` : duration;
|
|
34151
|
+
setTransitionValue(TRANSITION_DURATION_PROPERTY, transition.duration);
|
|
34089
34152
|
transition.restoreDuration = () => {
|
|
34090
|
-
|
|
34091
|
-
documentElement.style.setProperty(TRANSITION_DURATION_PROPERTY, durationBefore);
|
|
34092
|
-
} else {
|
|
34093
|
-
documentElement.style.removeProperty(TRANSITION_DURATION_PROPERTY);
|
|
34094
|
-
}
|
|
34153
|
+
removeTransitionValue(TRANSITION_DURATION_PROPERTY);
|
|
34095
34154
|
};
|
|
34096
34155
|
}
|
|
34097
34156
|
const releaseRendering = takeoverRoutingRenderingHold();
|
|
@@ -34104,7 +34163,9 @@ const beginTransition = ({
|
|
|
34104
34163
|
// the only place the silent misconfigurations show. They are all about the
|
|
34105
34164
|
// same thing — a movement playing on pictures that are not the pages.
|
|
34106
34165
|
const viewTransitionReady = () => {
|
|
34107
|
-
startTransitionFurniture(transition
|
|
34166
|
+
startTransitionFurniture(transition, {
|
|
34167
|
+
duration: transition.duration
|
|
34168
|
+
});
|
|
34108
34169
|
const capturedNames = capturedViewTransitionNames();
|
|
34109
34170
|
if (areaElements.length > 0) {
|
|
34110
34171
|
if (!capturedNames.has(AREA_NAME)) {
|
|
@@ -34130,6 +34191,10 @@ const beginTransition = ({
|
|
|
34130
34191
|
// is awaited here must be able to resolve without a frame: the document
|
|
34131
34192
|
// is frozen for the whole of this callback.
|
|
34132
34193
|
try {
|
|
34194
|
+
// The page being left is photographed already: it only has to stay out
|
|
34195
|
+
// of the second picture, not be taken down before it (see
|
|
34196
|
+
// keepLeavingPages in route.jsx).
|
|
34197
|
+
transition.releaseLeavingPages = keepLeavingPages();
|
|
34133
34198
|
// Releasing flushes the held render synchronously, so a route that
|
|
34134
34199
|
// rendered has already resolved the wait by the next line.
|
|
34135
34200
|
releaseRendering();
|
|
@@ -34182,6 +34247,11 @@ const beginTransition = ({
|
|
|
34182
34247
|
// must not strip what that one is wearing.
|
|
34183
34248
|
renderWait.stop();
|
|
34184
34249
|
releaseRendering();
|
|
34250
|
+
// Taken down once nobody sees it any more.
|
|
34251
|
+
if (transition.releaseLeavingPages) {
|
|
34252
|
+
transition.releaseLeavingPages();
|
|
34253
|
+
transition.releaseLeavingPages = null;
|
|
34254
|
+
}
|
|
34185
34255
|
// The hold a way back took, when it is still standing: the pictures were
|
|
34186
34256
|
// turned round a second time and played out, or something else took the
|
|
34187
34257
|
// document over mid-walk. A hold nobody gives back freezes the page.
|
|
@@ -89869,8 +89939,7 @@ const createSlot = (SlotRenderer = Box) => {
|
|
|
89869
89939
|
};
|
|
89870
89940
|
const SlotFill = props => {
|
|
89871
89941
|
const fillerRef = useRef();
|
|
89872
|
-
|
|
89873
|
-
slotPropsSignal.value = props;
|
|
89942
|
+
const routePage = useContext(RoutePageContext);
|
|
89874
89943
|
useLayoutEffect(() => {
|
|
89875
89944
|
return () => {
|
|
89876
89945
|
// Within one diff preact mounts the newcomer before unmounting the
|
|
@@ -89883,6 +89952,26 @@ const createSlot = (SlotRenderer = Box) => {
|
|
|
89883
89952
|
slotPropsSignal.value = null;
|
|
89884
89953
|
};
|
|
89885
89954
|
}, []);
|
|
89955
|
+
// In a page kept while leaving: out of the slot as if unmounted, since
|
|
89956
|
+
// the page arriving is what the slot must show — or nothing, when it
|
|
89957
|
+
// fills none.
|
|
89958
|
+
if (routePage && routePage.leavingSignal.value) {
|
|
89959
|
+
if (filler === fillerRef) {
|
|
89960
|
+
filler = null;
|
|
89961
|
+
slotPropsSignal.value = null;
|
|
89962
|
+
}
|
|
89963
|
+
return null;
|
|
89964
|
+
}
|
|
89965
|
+
if (!fillerRef.current) {
|
|
89966
|
+
fillerRef.current = true;
|
|
89967
|
+
filler = fillerRef;
|
|
89968
|
+
}
|
|
89969
|
+
if (filler === null) {
|
|
89970
|
+
filler = fillerRef;
|
|
89971
|
+
}
|
|
89972
|
+
if (filler === fillerRef) {
|
|
89973
|
+
slotPropsSignal.value = props;
|
|
89974
|
+
}
|
|
89886
89975
|
return null;
|
|
89887
89976
|
};
|
|
89888
89977
|
return [Slot, SlotFill];
|