@wordpress/grid 0.1.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 +33 -0
- package/LICENSE.md +788 -0
- package/README.md +534 -0
- package/build/dashboard-grid/grid-item.cjs +308 -0
- package/build/dashboard-grid/grid-item.cjs.map +7 -0
- package/build/dashboard-grid/index.cjs +591 -0
- package/build/dashboard-grid/index.cjs.map +7 -0
- package/build/dashboard-grid/resolve-fill-widths.cjs +189 -0
- package/build/dashboard-grid/resolve-fill-widths.cjs.map +7 -0
- package/build/dashboard-grid/types.cjs +19 -0
- package/build/dashboard-grid/types.cjs.map +7 -0
- package/build/dashboard-lanes/index.cjs +558 -0
- package/build/dashboard-lanes/index.cjs.map +7 -0
- package/build/dashboard-lanes/lane-placement.cjs +110 -0
- package/build/dashboard-lanes/lane-placement.cjs.map +7 -0
- package/build/dashboard-lanes/lanes-item.cjs +295 -0
- package/build/dashboard-lanes/lanes-item.cjs.map +7 -0
- package/build/dashboard-lanes/types.cjs +19 -0
- package/build/dashboard-lanes/types.cjs.map +7 -0
- package/build/dashboard-lanes/use-lane-placement.cjs +206 -0
- package/build/dashboard-lanes/use-lane-placement.cjs.map +7 -0
- package/build/index.cjs +34 -0
- package/build/index.cjs.map +7 -0
- package/build/shared/drag-overlay-drop-animation.cjs +70 -0
- package/build/shared/drag-overlay-drop-animation.cjs.map +7 -0
- package/build/shared/grid-item-key.cjs +31 -0
- package/build/shared/grid-item-key.cjs.map +7 -0
- package/build/shared/grid-overlay.cjs +187 -0
- package/build/shared/grid-overlay.cjs.map +7 -0
- package/build/shared/item-exit-overlay.cjs +150 -0
- package/build/shared/item-exit-overlay.cjs.map +7 -0
- package/build/shared/resize-handle.cjs +224 -0
- package/build/shared/resize-handle.cjs.map +7 -0
- package/build/shared/resize-snap.cjs +47 -0
- package/build/shared/resize-snap.cjs.map +7 -0
- package/build/shared/types.cjs +19 -0
- package/build/shared/types.cjs.map +7 -0
- package/build/shared/use-item-exit-animation.cjs +148 -0
- package/build/shared/use-item-exit-animation.cjs.map +7 -0
- package/build/shared/use-layout-shift-animation.cjs +167 -0
- package/build/shared/use-layout-shift-animation.cjs.map +7 -0
- package/build-module/dashboard-grid/grid-item.mjs +273 -0
- package/build-module/dashboard-grid/grid-item.mjs.map +7 -0
- package/build-module/dashboard-grid/index.mjs +579 -0
- package/build-module/dashboard-grid/index.mjs.map +7 -0
- package/build-module/dashboard-grid/resolve-fill-widths.mjs +164 -0
- package/build-module/dashboard-grid/resolve-fill-widths.mjs.map +7 -0
- package/build-module/dashboard-grid/types.mjs +1 -0
- package/build-module/dashboard-grid/types.mjs.map +7 -0
- package/build-module/dashboard-lanes/index.mjs +547 -0
- package/build-module/dashboard-lanes/index.mjs.map +7 -0
- package/build-module/dashboard-lanes/lane-placement.mjs +85 -0
- package/build-module/dashboard-lanes/lane-placement.mjs.map +7 -0
- package/build-module/dashboard-lanes/lanes-item.mjs +260 -0
- package/build-module/dashboard-lanes/lanes-item.mjs.map +7 -0
- package/build-module/dashboard-lanes/types.mjs +1 -0
- package/build-module/dashboard-lanes/types.mjs.map +7 -0
- package/build-module/dashboard-lanes/use-lane-placement.mjs +181 -0
- package/build-module/dashboard-lanes/use-lane-placement.mjs.map +7 -0
- package/build-module/index.mjs +8 -0
- package/build-module/index.mjs.map +7 -0
- package/build-module/shared/drag-overlay-drop-animation.mjs +47 -0
- package/build-module/shared/drag-overlay-drop-animation.mjs.map +7 -0
- package/build-module/shared/grid-item-key.mjs +6 -0
- package/build-module/shared/grid-item-key.mjs.map +7 -0
- package/build-module/shared/grid-overlay.mjs +152 -0
- package/build-module/shared/grid-overlay.mjs.map +7 -0
- package/build-module/shared/item-exit-overlay.mjs +125 -0
- package/build-module/shared/item-exit-overlay.mjs.map +7 -0
- package/build-module/shared/resize-handle.mjs +193 -0
- package/build-module/shared/resize-handle.mjs.map +7 -0
- package/build-module/shared/resize-snap.mjs +21 -0
- package/build-module/shared/resize-snap.mjs.map +7 -0
- package/build-module/shared/types.mjs +1 -0
- package/build-module/shared/types.mjs.map +7 -0
- package/build-module/shared/use-item-exit-animation.mjs +128 -0
- package/build-module/shared/use-item-exit-animation.mjs.map +7 -0
- package/build-module/shared/use-layout-shift-animation.mjs +140 -0
- package/build-module/shared/use-layout-shift-animation.mjs.map +7 -0
- package/build-types/dashboard-grid/grid-item.d.ts +3 -0
- package/build-types/dashboard-grid/grid-item.d.ts.map +1 -0
- package/build-types/dashboard-grid/index.d.ts +35 -0
- package/build-types/dashboard-grid/index.d.ts.map +1 -0
- package/build-types/dashboard-grid/resolve-fill-widths.d.ts +26 -0
- package/build-types/dashboard-grid/resolve-fill-widths.d.ts.map +1 -0
- package/build-types/dashboard-grid/stories/index.story.d.ts +98 -0
- package/build-types/dashboard-grid/stories/index.story.d.ts.map +1 -0
- package/build-types/dashboard-grid/types.d.ts +232 -0
- package/build-types/dashboard-grid/types.d.ts.map +1 -0
- package/build-types/dashboard-lanes/index.d.ts +40 -0
- package/build-types/dashboard-lanes/index.d.ts.map +1 -0
- package/build-types/dashboard-lanes/lane-placement.d.ts +126 -0
- package/build-types/dashboard-lanes/lane-placement.d.ts.map +1 -0
- package/build-types/dashboard-lanes/lanes-item.d.ts +52 -0
- package/build-types/dashboard-lanes/lanes-item.d.ts.map +1 -0
- package/build-types/dashboard-lanes/stories/index.story.d.ts +64 -0
- package/build-types/dashboard-lanes/stories/index.story.d.ts.map +1 -0
- package/build-types/dashboard-lanes/types.d.ts +151 -0
- package/build-types/dashboard-lanes/types.d.ts.map +1 -0
- package/build-types/dashboard-lanes/use-lane-placement.d.ts +74 -0
- package/build-types/dashboard-lanes/use-lane-placement.d.ts.map +1 -0
- package/build-types/index.d.ts +6 -0
- package/build-types/index.d.ts.map +1 -0
- package/build-types/shared/drag-overlay-drop-animation.d.ts +13 -0
- package/build-types/shared/drag-overlay-drop-animation.d.ts.map +1 -0
- package/build-types/shared/grid-item-key.d.ts +6 -0
- package/build-types/shared/grid-item-key.d.ts.map +1 -0
- package/build-types/shared/grid-overlay.d.ts +19 -0
- package/build-types/shared/grid-overlay.d.ts.map +1 -0
- package/build-types/shared/item-exit-overlay.d.ts +20 -0
- package/build-types/shared/item-exit-overlay.d.ts.map +1 -0
- package/build-types/shared/resize-handle.d.ts +23 -0
- package/build-types/shared/resize-handle.d.ts.map +1 -0
- package/build-types/shared/resize-snap.d.ts +41 -0
- package/build-types/shared/resize-snap.d.ts.map +1 -0
- package/build-types/shared/types.d.ts +144 -0
- package/build-types/shared/types.d.ts.map +1 -0
- package/build-types/shared/use-item-exit-animation.d.ts +37 -0
- package/build-types/shared/use-item-exit-animation.d.ts.map +1 -0
- package/build-types/shared/use-layout-shift-animation.d.ts +77 -0
- package/build-types/shared/use-layout-shift-animation.d.ts.map +1 -0
- package/package.json +80 -0
- package/src/dashboard-grid/grid-item.module.css +94 -0
- package/src/dashboard-grid/grid-item.tsx +205 -0
- package/src/dashboard-grid/grid.module.css +134 -0
- package/src/dashboard-grid/index.tsx +713 -0
- package/src/dashboard-grid/resolve-fill-widths.ts +224 -0
- package/src/dashboard-grid/stories/index.story.tsx +930 -0
- package/src/dashboard-grid/test/keyboard-activation.test.tsx +76 -0
- package/src/dashboard-grid/test/resolve-fill-widths.test.ts +250 -0
- package/src/dashboard-grid/types.ts +271 -0
- package/src/dashboard-lanes/index.tsx +629 -0
- package/src/dashboard-lanes/lane-placement.ts +245 -0
- package/src/dashboard-lanes/lanes-item.module.css +93 -0
- package/src/dashboard-lanes/lanes-item.tsx +236 -0
- package/src/dashboard-lanes/lanes.module.css +152 -0
- package/src/dashboard-lanes/stories/index.story.tsx +518 -0
- package/src/dashboard-lanes/test/keyboard-activation.test.tsx +71 -0
- package/src/dashboard-lanes/test/lane-placement.test.ts +442 -0
- package/src/dashboard-lanes/test/use-lane-placement.test.tsx +358 -0
- package/src/dashboard-lanes/types.ts +176 -0
- package/src/dashboard-lanes/use-lane-placement.ts +313 -0
- package/src/index.ts +17 -0
- package/src/shared/actionable-area-slot.module.css +16 -0
- package/src/shared/drag-overlay-drop-animation.ts +66 -0
- package/src/shared/grid-item-key.ts +5 -0
- package/src/shared/grid-overlay.module.css +82 -0
- package/src/shared/grid-overlay.tsx +93 -0
- package/src/shared/item-exit-animation.module.css +49 -0
- package/src/shared/item-exit-overlay.tsx +57 -0
- package/src/shared/layout-shift-animation.module.css +16 -0
- package/src/shared/resize-handle.module.css +88 -0
- package/src/shared/resize-handle.tsx +163 -0
- package/src/shared/resize-snap.ts +63 -0
- package/src/shared/test/resize-snap.test.ts +35 -0
- package/src/shared/types.ts +164 -0
- package/src/shared/use-item-exit-animation.ts +199 -0
- package/src/shared/use-layout-shift-animation.ts +284 -0
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
// packages/grid/src/dashboard-lanes/lane-placement.ts
|
|
2
|
+
function clampSpan(span, lanes) {
|
|
3
|
+
if (!Number.isFinite(span)) {
|
|
4
|
+
return 1;
|
|
5
|
+
}
|
|
6
|
+
return Math.max(1, Math.min(Math.floor(span), lanes));
|
|
7
|
+
}
|
|
8
|
+
function clampLane(lane, span, lanes) {
|
|
9
|
+
if (!Number.isFinite(lane)) {
|
|
10
|
+
return 0;
|
|
11
|
+
}
|
|
12
|
+
return Math.max(0, Math.min(Math.floor(lane), lanes - span));
|
|
13
|
+
}
|
|
14
|
+
function maxBaselineAcross(laneBottoms, startLane, span) {
|
|
15
|
+
let maxBaseline = 0;
|
|
16
|
+
for (let i = startLane; i < startLane + span; i++) {
|
|
17
|
+
if (laneBottoms[i] > maxBaseline) {
|
|
18
|
+
maxBaseline = laneBottoms[i];
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
return maxBaseline;
|
|
22
|
+
}
|
|
23
|
+
function computeLanePlacements(input) {
|
|
24
|
+
const lanes = Math.max(1, Math.floor(input.lanes));
|
|
25
|
+
const gap = Math.max(0, input.gap);
|
|
26
|
+
const tolerance = Math.max(0, input.flowTolerance);
|
|
27
|
+
const laneBottoms = new Array(lanes).fill(0);
|
|
28
|
+
const placements = /* @__PURE__ */ new Map();
|
|
29
|
+
const explicitItems = [];
|
|
30
|
+
const autoItems = [];
|
|
31
|
+
for (const item of input.items) {
|
|
32
|
+
if (item.lane !== void 0) {
|
|
33
|
+
explicitItems.push(item);
|
|
34
|
+
} else {
|
|
35
|
+
autoItems.push(item);
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
for (const item of explicitItems) {
|
|
39
|
+
const span = clampSpan(item.span, lanes);
|
|
40
|
+
const lane = clampLane(item.lane, span, lanes);
|
|
41
|
+
const baseline = maxBaselineAcross(laneBottoms, lane, span);
|
|
42
|
+
const top = baseline === 0 ? 0 : baseline + gap;
|
|
43
|
+
const height = Math.max(0, item.height);
|
|
44
|
+
placements.set(item.key, { key: item.key, lane, top, span });
|
|
45
|
+
const newBottom = top + height;
|
|
46
|
+
for (let i = lane; i < lane + span; i++) {
|
|
47
|
+
laneBottoms[i] = newBottom;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
for (const item of autoItems) {
|
|
51
|
+
const span = clampSpan(item.span, lanes);
|
|
52
|
+
let bestLane = 0;
|
|
53
|
+
let bestBaseline = Infinity;
|
|
54
|
+
for (let candidate = 0; candidate <= lanes - span; candidate++) {
|
|
55
|
+
const baseline = maxBaselineAcross(laneBottoms, candidate, span);
|
|
56
|
+
if (bestBaseline - baseline > tolerance) {
|
|
57
|
+
bestBaseline = baseline;
|
|
58
|
+
bestLane = candidate;
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
const top = bestBaseline === 0 ? 0 : bestBaseline + gap;
|
|
62
|
+
const height = Math.max(0, item.height);
|
|
63
|
+
placements.set(item.key, {
|
|
64
|
+
key: item.key,
|
|
65
|
+
lane: bestLane,
|
|
66
|
+
top,
|
|
67
|
+
span
|
|
68
|
+
});
|
|
69
|
+
const newBottom = top + height;
|
|
70
|
+
for (let i = bestLane; i < bestLane + span; i++) {
|
|
71
|
+
laneBottoms[i] = newBottom;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
let totalHeight = 0;
|
|
75
|
+
for (const bottom of laneBottoms) {
|
|
76
|
+
if (bottom > totalHeight) {
|
|
77
|
+
totalHeight = bottom;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
return { placements, totalHeight };
|
|
81
|
+
}
|
|
82
|
+
export {
|
|
83
|
+
computeLanePlacements
|
|
84
|
+
};
|
|
85
|
+
//# sourceMappingURL=lane-placement.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../src/dashboard-lanes/lane-placement.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Lane placement algorithm for `display: grid-lanes` polyfill.\n *\n * Implements the source-ordered, shortest-lane placement described in\n * https://webkit.org/blog/17660/introducing-css-grid-lanes/.\n *\n * The skyline + tolerance core is adapted from the CSS Grid Lanes\n * Polyfill by Simon Willison (MIT,\n * https://tools.simonwillison.net/grid-lanes-polyfill.js). The rest\n * of this module is a pure function suitable for unit testing in\n * isolation from any DOM.\n *\n * Concepts:\n * - \"Lane\" is the cross-axis track: a column in waterfall mode, a row\n * in brick mode. The algorithm is axis-agnostic; the renderer maps\n * the chosen lane index plus offset to `grid-column-start` /\n * `grid-row-start` (or vice versa).\n * - Items are placed in source order. Explicit-lane items are placed\n * first so auto-placed items can flow around them.\n * - `flowTolerance` is a length: when two candidate lanes differ in\n * baseline by no more than this, the earlier lane wins (preserves\n * reading order).\n */\n\n/**\n * A single item to place. Heights are pre-measured by the caller.\n */\nexport type LanePlacementItem = {\n\t/**\n\t * Stable identity. Returned in the result map.\n\t */\n\tkey: string;\n\n\t/**\n\t * Number of contiguous lanes this item occupies. Clamped to\n\t * `[ 1, lanes ]` by the algorithm.\n\t */\n\tspan: number;\n\n\t/**\n\t * Measured cross-axis size (typically pixels). The algorithm only\n\t * adds and compares heights; the unit is whatever the caller uses,\n\t * as long as `gap` and `flowTolerance` use the same one.\n\t */\n\theight: number;\n\n\t/**\n\t * Explicit 0-indexed starting lane. When set, the item bypasses\n\t * the skyline lookup and is placed at this lane regardless of\n\t * source order. Out-of-range values are clamped.\n\t */\n\tlane?: number;\n};\n\n/**\n * Algorithm input.\n */\nexport type LanePlacementInput = {\n\t/**\n\t * Items in source order.\n\t */\n\titems: ReadonlyArray< LanePlacementItem >;\n\n\t/**\n\t * Total number of lanes. Clamped to `>= 1`.\n\t */\n\tlanes: number;\n\n\t/**\n\t * Gap between items in the same lane. Same unit as `height`.\n\t */\n\tgap: number;\n\n\t/**\n\t * Tolerance for source-order tiebreaking. When two candidate\n\t * lanes have baselines within this amount, the earlier lane wins.\n\t * Defaults to `0` if a negative value is passed.\n\t */\n\tflowTolerance: number;\n};\n\n/**\n * Resolved position for a single item.\n */\nexport type LanePlacement = {\n\t/**\n\t * Mirrors the input key.\n\t */\n\tkey: string;\n\n\t/**\n\t * 0-indexed starting lane. The renderer adds 1 for\n\t * `grid-column-start`.\n\t */\n\tlane: number;\n\n\t/**\n\t * Cross-axis offset from the container's start edge, in the same\n\t * unit as the input heights. Use as the item's start position\n\t * (e.g. `top`, or `grid-row-start` after dividing by a row unit).\n\t */\n\ttop: number;\n\n\t/**\n\t * Effective span after clamping. Useful for the renderer when the\n\t * input span exceeded the lane count.\n\t */\n\tspan: number;\n};\n\n/**\n * Algorithm output.\n */\nexport type LanePlacementResult = {\n\t/**\n\t * Per-key placement. Insertion-ordered: the first iteration yields\n\t * the explicit items in source order, then the auto items in\n\t * source order.\n\t */\n\tplacements: Map< string, LanePlacement >;\n\n\t/**\n\t * Sum of the tallest lane after all items are placed. The renderer\n\t * applies this as the container's intrinsic height.\n\t */\n\ttotalHeight: number;\n};\n\nfunction clampSpan( span: number, lanes: number ): number {\n\tif ( ! Number.isFinite( span ) ) {\n\t\treturn 1;\n\t}\n\treturn Math.max( 1, Math.min( Math.floor( span ), lanes ) );\n}\n\nfunction clampLane( lane: number, span: number, lanes: number ): number {\n\tif ( ! Number.isFinite( lane ) ) {\n\t\treturn 0;\n\t}\n\treturn Math.max( 0, Math.min( Math.floor( lane ), lanes - span ) );\n}\n\nfunction maxBaselineAcross(\n\tlaneBottoms: ReadonlyArray< number >,\n\tstartLane: number,\n\tspan: number\n): number {\n\tlet maxBaseline = 0;\n\tfor ( let i = startLane; i < startLane + span; i++ ) {\n\t\tif ( laneBottoms[ i ] > maxBaseline ) {\n\t\t\tmaxBaseline = laneBottoms[ i ];\n\t\t}\n\t}\n\treturn maxBaseline;\n}\n\n/**\n * Places all items into a fixed lane count using the grid-lanes\n * algorithm: explicit items first, then auto items chosen by the\n * shortest-lane skyline with a tolerance for source order.\n *\n * Pure: no DOM access, no mutation of inputs. Safe to call from a\n * worker or during SSR.\n *\n * @param input Items, lane count, gap, and tolerance.\n * @return Per-key placements plus the resulting total height.\n */\nexport function computeLanePlacements(\n\tinput: LanePlacementInput\n): LanePlacementResult {\n\tconst lanes = Math.max( 1, Math.floor( input.lanes ) );\n\tconst gap = Math.max( 0, input.gap );\n\tconst tolerance = Math.max( 0, input.flowTolerance );\n\n\tconst laneBottoms = new Array< number >( lanes ).fill( 0 );\n\tconst placements = new Map< string, LanePlacement >();\n\n\tconst explicitItems: LanePlacementItem[] = [];\n\tconst autoItems: LanePlacementItem[] = [];\n\tfor ( const item of input.items ) {\n\t\tif ( item.lane !== undefined ) {\n\t\t\texplicitItems.push( item );\n\t\t} else {\n\t\t\tautoItems.push( item );\n\t\t}\n\t}\n\n\tfor ( const item of explicitItems ) {\n\t\tconst span = clampSpan( item.span, lanes );\n\t\tconst lane = clampLane( item.lane as number, span, lanes );\n\t\tconst baseline = maxBaselineAcross( laneBottoms, lane, span );\n\t\tconst top = baseline === 0 ? 0 : baseline + gap;\n\t\tconst height = Math.max( 0, item.height );\n\n\t\tplacements.set( item.key, { key: item.key, lane, top, span } );\n\n\t\tconst newBottom = top + height;\n\t\tfor ( let i = lane; i < lane + span; i++ ) {\n\t\t\tlaneBottoms[ i ] = newBottom;\n\t\t}\n\t}\n\n\tfor ( const item of autoItems ) {\n\t\tconst span = clampSpan( item.span, lanes );\n\t\tlet bestLane = 0;\n\t\tlet bestBaseline = Infinity;\n\n\t\tfor ( let candidate = 0; candidate <= lanes - span; candidate++ ) {\n\t\t\tconst baseline = maxBaselineAcross( laneBottoms, candidate, span );\n\n\t\t\t// Only take a lane that is strictly shorter beyond\n\t\t\t// tolerance. Within-tolerance ties keep the earlier lane\n\t\t\t// because candidates iterate in lane order, so the first\n\t\t\t// acceptable baseline wins.\n\t\t\tif ( bestBaseline - baseline > tolerance ) {\n\t\t\t\tbestBaseline = baseline;\n\t\t\t\tbestLane = candidate;\n\t\t\t}\n\t\t}\n\n\t\tconst top = bestBaseline === 0 ? 0 : bestBaseline + gap;\n\t\tconst height = Math.max( 0, item.height );\n\n\t\tplacements.set( item.key, {\n\t\t\tkey: item.key,\n\t\t\tlane: bestLane,\n\t\t\ttop,\n\t\t\tspan,\n\t\t} );\n\n\t\tconst newBottom = top + height;\n\t\tfor ( let i = bestLane; i < bestLane + span; i++ ) {\n\t\t\tlaneBottoms[ i ] = newBottom;\n\t\t}\n\t}\n\n\tlet totalHeight = 0;\n\tfor ( const bottom of laneBottoms ) {\n\t\tif ( bottom > totalHeight ) {\n\t\t\ttotalHeight = bottom;\n\t\t}\n\t}\n\n\treturn { placements, totalHeight };\n}\n"],
|
|
5
|
+
"mappings": ";AAgIA,SAAS,UAAW,MAAc,OAAwB;AACzD,MAAK,CAAE,OAAO,SAAU,IAAK,GAAI;AAChC,WAAO;AAAA,EACR;AACA,SAAO,KAAK,IAAK,GAAG,KAAK,IAAK,KAAK,MAAO,IAAK,GAAG,KAAM,CAAE;AAC3D;AAEA,SAAS,UAAW,MAAc,MAAc,OAAwB;AACvE,MAAK,CAAE,OAAO,SAAU,IAAK,GAAI;AAChC,WAAO;AAAA,EACR;AACA,SAAO,KAAK,IAAK,GAAG,KAAK,IAAK,KAAK,MAAO,IAAK,GAAG,QAAQ,IAAK,CAAE;AAClE;AAEA,SAAS,kBACR,aACA,WACA,MACS;AACT,MAAI,cAAc;AAClB,WAAU,IAAI,WAAW,IAAI,YAAY,MAAM,KAAM;AACpD,QAAK,YAAa,CAAE,IAAI,aAAc;AACrC,oBAAc,YAAa,CAAE;AAAA,IAC9B;AAAA,EACD;AACA,SAAO;AACR;AAaO,SAAS,sBACf,OACsB;AACtB,QAAM,QAAQ,KAAK,IAAK,GAAG,KAAK,MAAO,MAAM,KAAM,CAAE;AACrD,QAAM,MAAM,KAAK,IAAK,GAAG,MAAM,GAAI;AACnC,QAAM,YAAY,KAAK,IAAK,GAAG,MAAM,aAAc;AAEnD,QAAM,cAAc,IAAI,MAAiB,KAAM,EAAE,KAAM,CAAE;AACzD,QAAM,aAAa,oBAAI,IAA6B;AAEpD,QAAM,gBAAqC,CAAC;AAC5C,QAAM,YAAiC,CAAC;AACxC,aAAY,QAAQ,MAAM,OAAQ;AACjC,QAAK,KAAK,SAAS,QAAY;AAC9B,oBAAc,KAAM,IAAK;AAAA,IAC1B,OAAO;AACN,gBAAU,KAAM,IAAK;AAAA,IACtB;AAAA,EACD;AAEA,aAAY,QAAQ,eAAgB;AACnC,UAAM,OAAO,UAAW,KAAK,MAAM,KAAM;AACzC,UAAM,OAAO,UAAW,KAAK,MAAgB,MAAM,KAAM;AACzD,UAAM,WAAW,kBAAmB,aAAa,MAAM,IAAK;AAC5D,UAAM,MAAM,aAAa,IAAI,IAAI,WAAW;AAC5C,UAAM,SAAS,KAAK,IAAK,GAAG,KAAK,MAAO;AAExC,eAAW,IAAK,KAAK,KAAK,EAAE,KAAK,KAAK,KAAK,MAAM,KAAK,KAAK,CAAE;AAE7D,UAAM,YAAY,MAAM;AACxB,aAAU,IAAI,MAAM,IAAI,OAAO,MAAM,KAAM;AAC1C,kBAAa,CAAE,IAAI;AAAA,IACpB;AAAA,EACD;AAEA,aAAY,QAAQ,WAAY;AAC/B,UAAM,OAAO,UAAW,KAAK,MAAM,KAAM;AACzC,QAAI,WAAW;AACf,QAAI,eAAe;AAEnB,aAAU,YAAY,GAAG,aAAa,QAAQ,MAAM,aAAc;AACjE,YAAM,WAAW,kBAAmB,aAAa,WAAW,IAAK;AAMjE,UAAK,eAAe,WAAW,WAAY;AAC1C,uBAAe;AACf,mBAAW;AAAA,MACZ;AAAA,IACD;AAEA,UAAM,MAAM,iBAAiB,IAAI,IAAI,eAAe;AACpD,UAAM,SAAS,KAAK,IAAK,GAAG,KAAK,MAAO;AAExC,eAAW,IAAK,KAAK,KAAK;AAAA,MACzB,KAAK,KAAK;AAAA,MACV,MAAM;AAAA,MACN;AAAA,MACA;AAAA,IACD,CAAE;AAEF,UAAM,YAAY,MAAM;AACxB,aAAU,IAAI,UAAU,IAAI,WAAW,MAAM,KAAM;AAClD,kBAAa,CAAE,IAAI;AAAA,IACpB;AAAA,EACD;AAEA,MAAI,cAAc;AAClB,aAAY,UAAU,aAAc;AACnC,QAAK,SAAS,aAAc;AAC3B,oBAAc;AAAA,IACf;AAAA,EACD;AAEA,SAAO,EAAE,YAAY,YAAY;AAClC;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,260 @@
|
|
|
1
|
+
// packages/grid/src/dashboard-lanes/lanes-item.tsx
|
|
2
|
+
import { useSortable } from "@dnd-kit/sortable";
|
|
3
|
+
import clsx from "clsx";
|
|
4
|
+
import { useState, useRef } from "@wordpress/element";
|
|
5
|
+
import { useMergeRefs } from "@wordpress/compose";
|
|
6
|
+
|
|
7
|
+
// packages/style-runtime/src/index.ts
|
|
8
|
+
var STYLE_HASH_ATTRIBUTE = "data-wp-hash";
|
|
9
|
+
function getRuntime() {
|
|
10
|
+
const globalScope = globalThis;
|
|
11
|
+
if (globalScope.__wpStyleRuntime) {
|
|
12
|
+
return globalScope.__wpStyleRuntime;
|
|
13
|
+
}
|
|
14
|
+
globalScope.__wpStyleRuntime = {
|
|
15
|
+
documents: /* @__PURE__ */ new Map(),
|
|
16
|
+
styles: /* @__PURE__ */ new Map(),
|
|
17
|
+
injectedStyles: /* @__PURE__ */ new WeakMap()
|
|
18
|
+
};
|
|
19
|
+
if (typeof document !== "undefined") {
|
|
20
|
+
registerDocument(document);
|
|
21
|
+
}
|
|
22
|
+
return globalScope.__wpStyleRuntime;
|
|
23
|
+
}
|
|
24
|
+
function documentContainsStyleHash(targetDocument, hash) {
|
|
25
|
+
if (!targetDocument.head) {
|
|
26
|
+
return false;
|
|
27
|
+
}
|
|
28
|
+
for (const style of targetDocument.head.querySelectorAll(
|
|
29
|
+
`style[${STYLE_HASH_ATTRIBUTE}]`
|
|
30
|
+
)) {
|
|
31
|
+
if (style.getAttribute(STYLE_HASH_ATTRIBUTE) === hash) {
|
|
32
|
+
return true;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
return false;
|
|
36
|
+
}
|
|
37
|
+
function injectStyle(targetDocument, hash, css) {
|
|
38
|
+
if (!targetDocument.head) {
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
const runtime = getRuntime();
|
|
42
|
+
let injectedStyles = runtime.injectedStyles.get(targetDocument);
|
|
43
|
+
if (!injectedStyles) {
|
|
44
|
+
injectedStyles = /* @__PURE__ */ new Set();
|
|
45
|
+
runtime.injectedStyles.set(targetDocument, injectedStyles);
|
|
46
|
+
}
|
|
47
|
+
if (injectedStyles.has(hash)) {
|
|
48
|
+
return;
|
|
49
|
+
}
|
|
50
|
+
if (documentContainsStyleHash(targetDocument, hash)) {
|
|
51
|
+
injectedStyles.add(hash);
|
|
52
|
+
return;
|
|
53
|
+
}
|
|
54
|
+
const style = targetDocument.createElement("style");
|
|
55
|
+
style.setAttribute(STYLE_HASH_ATTRIBUTE, hash);
|
|
56
|
+
style.appendChild(targetDocument.createTextNode(css));
|
|
57
|
+
targetDocument.head.appendChild(style);
|
|
58
|
+
injectedStyles.add(hash);
|
|
59
|
+
}
|
|
60
|
+
function registerDocument(targetDocument) {
|
|
61
|
+
const runtime = getRuntime();
|
|
62
|
+
runtime.documents.set(
|
|
63
|
+
targetDocument,
|
|
64
|
+
(runtime.documents.get(targetDocument) ?? 0) + 1
|
|
65
|
+
);
|
|
66
|
+
for (const [hash, css] of runtime.styles) {
|
|
67
|
+
injectStyle(targetDocument, hash, css);
|
|
68
|
+
}
|
|
69
|
+
return () => {
|
|
70
|
+
const count = runtime.documents.get(targetDocument);
|
|
71
|
+
if (count === void 0) {
|
|
72
|
+
return;
|
|
73
|
+
}
|
|
74
|
+
if (count <= 1) {
|
|
75
|
+
runtime.documents.delete(targetDocument);
|
|
76
|
+
return;
|
|
77
|
+
}
|
|
78
|
+
runtime.documents.set(targetDocument, count - 1);
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
function registerStyle(hash, css) {
|
|
82
|
+
const runtime = getRuntime();
|
|
83
|
+
runtime.styles.set(hash, css);
|
|
84
|
+
for (const targetDocument of runtime.documents.keys()) {
|
|
85
|
+
injectStyle(targetDocument, hash, css);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
// packages/grid/src/shared/actionable-area-slot.module.css
|
|
90
|
+
if (typeof process === "undefined" || process.env.NODE_ENV !== "test") {
|
|
91
|
+
registerStyle("ac1094954c", "._1c54fe8165d3023e__actionable-area-slot{opacity:1}@media (prefers-reduced-motion:no-preference){._1c54fe8165d3023e__actionable-area-slot{transition:opacity var(--wpds-motion-duration-md,.2s) var(--wpds-motion-easing-subtle,cubic-bezier(.15,0,.15,1))}}[data-wp-grid-resizing] ._1c54fe8165d3023e__actionable-area-slot{opacity:0;pointer-events:none}");
|
|
92
|
+
}
|
|
93
|
+
var actionable_area_slot_default = { "actionable-area-slot": "_1c54fe8165d3023e__actionable-area-slot" };
|
|
94
|
+
|
|
95
|
+
// packages/grid/src/dashboard-lanes/lanes-item.tsx
|
|
96
|
+
import ResizeHandle from "../shared/resize-handle.mjs";
|
|
97
|
+
import { clampResizeDelta } from "../shared/resize-snap.mjs";
|
|
98
|
+
import { GRID_ITEM_DATA_KEY } from "../shared/grid-item-key.mjs";
|
|
99
|
+
|
|
100
|
+
// packages/grid/src/dashboard-lanes/lanes-item.module.css
|
|
101
|
+
if (typeof process === "undefined" || process.env.NODE_ENV !== "test") {
|
|
102
|
+
registerStyle("97a2a51c0b", "._0a62d9f1dff8c7d8__item{position:relative}._20c43fcd930d828a__item-content{height:100%;position:relative}._11928ee35f1a9519__is-resizing{overflow:visible;z-index:1}._11928ee35f1a9519__is-resizing ._20c43fcd930d828a__item-content{overflow:visible;position:relative;z-index:2}.b7fc83c8b16e9ee5__is-dragging{pointer-events:none}[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{border-radius:var(--wp-grid-placeholder-radius,0)}@media not (prefers-reduced-motion:reduce){[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{animation:b026dda570d0eea0__wp-grid-item-placeholder-in 0ms linear var(--wpds-motion-duration-sm,.1s) forwards;opacity:1;outline-color:transparent;outline-style:var(--wp-grid-placeholder-outline-style,dashed);outline-width:0}@keyframes b026dda570d0eea0__wp-grid-item-placeholder-in{to{opacity:var(--wp-grid-placeholder-opacity,.4);outline-color:var(--wp-grid-placeholder-outline-color,var(--wpds-color-stroke-interactive-brand,var(--wp-admin-theme-color,#3858e9)));outline-width:var(--wpds-border-width-sm,2px)}}}@media (prefers-reduced-motion:reduce){[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{opacity:var(--wp-grid-placeholder-opacity,.4);outline:var(--wpds-border-width-sm,2px) var(--wp-grid-placeholder-outline-style,dashed) var(--wp-grid-placeholder-outline-color,var(--wpds-color-stroke-interactive-brand,var(--wp-admin-theme-color,#3858e9)))}}@media (forced-colors:active){[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{--wp-grid-placeholder-outline-color:Highlight}}.cd44faab32c27168__preview-overlay{background:transparent;border:var(--wpds-border-width-sm,2px) var(--wp-grid-resize-preview-outline-style,solid) var(--wp-grid-placeholder-outline-color,var(--wpds-color-stroke-interactive-brand,var(--wp-admin-theme-color,#3858e9)));box-sizing:border-box;inset-inline-start:0;pointer-events:none;position:absolute;top:0;z-index:0}@media (forced-colors:active){.cd44faab32c27168__preview-overlay{border-color:Highlight}}");
|
|
103
|
+
}
|
|
104
|
+
var lanes_item_default = { "item": "_0a62d9f1dff8c7d8__item", "item-content": "_20c43fcd930d828a__item-content", "is-resizing": "_11928ee35f1a9519__is-resizing", "is-dragging": "b7fc83c8b16e9ee5__is-dragging", "wp-grid-item-placeholder-in": "b026dda570d0eea0__wp-grid-item-placeholder-in", "preview-overlay": "cd44faab32c27168__preview-overlay" };
|
|
105
|
+
|
|
106
|
+
// packages/grid/src/dashboard-lanes/lanes-item.tsx
|
|
107
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
108
|
+
function getItemCursor(disabled, interacting) {
|
|
109
|
+
if (disabled) {
|
|
110
|
+
return "default";
|
|
111
|
+
}
|
|
112
|
+
if (interacting) {
|
|
113
|
+
return void 0;
|
|
114
|
+
}
|
|
115
|
+
return "grab";
|
|
116
|
+
}
|
|
117
|
+
function LanesItem({
|
|
118
|
+
itemKey,
|
|
119
|
+
placementStyle,
|
|
120
|
+
disabled = false,
|
|
121
|
+
interacting = false,
|
|
122
|
+
children,
|
|
123
|
+
actionableArea = null,
|
|
124
|
+
onResize,
|
|
125
|
+
onResizeEnd,
|
|
126
|
+
resizeSnapPreview = null,
|
|
127
|
+
minResizeWidthPx,
|
|
128
|
+
renderResizeHandle,
|
|
129
|
+
dragging = false
|
|
130
|
+
}) {
|
|
131
|
+
const [resizeDelta, setResizeDelta] = useState(
|
|
132
|
+
null
|
|
133
|
+
);
|
|
134
|
+
const [initialContentSize, setInitialContentSize] = useState(null);
|
|
135
|
+
const itemRef = useRef(null);
|
|
136
|
+
const contentRef = useRef(null);
|
|
137
|
+
const {
|
|
138
|
+
attributes,
|
|
139
|
+
listeners,
|
|
140
|
+
setNodeRef,
|
|
141
|
+
setActivatorNodeRef,
|
|
142
|
+
isDragging
|
|
143
|
+
} = useSortable({
|
|
144
|
+
id: itemKey,
|
|
145
|
+
disabled
|
|
146
|
+
});
|
|
147
|
+
const mergedRef = useMergeRefs([itemRef, setNodeRef]);
|
|
148
|
+
const contentMergedRef = useMergeRefs([contentRef]);
|
|
149
|
+
const style = {
|
|
150
|
+
...placementStyle,
|
|
151
|
+
alignSelf: "start"
|
|
152
|
+
};
|
|
153
|
+
const isResizing = resizeDelta !== null;
|
|
154
|
+
const itemClassName = clsx(
|
|
155
|
+
lanes_item_default.item,
|
|
156
|
+
isDragging && lanes_item_default["is-dragging"],
|
|
157
|
+
isResizing && lanes_item_default["is-resizing"]
|
|
158
|
+
);
|
|
159
|
+
const handleResize = (delta) => {
|
|
160
|
+
const contentNode = contentRef.current;
|
|
161
|
+
let baselineSize = initialContentSize;
|
|
162
|
+
if (contentNode && !baselineSize) {
|
|
163
|
+
const { width, height } = contentNode.getBoundingClientRect();
|
|
164
|
+
baselineSize = { width, height };
|
|
165
|
+
setInitialContentSize(baselineSize);
|
|
166
|
+
}
|
|
167
|
+
let clamped = { width: delta.width, height: 0 };
|
|
168
|
+
if (baselineSize) {
|
|
169
|
+
clamped = clampResizeDelta(clamped, baselineSize, {
|
|
170
|
+
width: minResizeWidthPx
|
|
171
|
+
});
|
|
172
|
+
}
|
|
173
|
+
setResizeDelta(clamped);
|
|
174
|
+
onResize(itemKey, clamped);
|
|
175
|
+
};
|
|
176
|
+
const handleResizeEnd = () => {
|
|
177
|
+
setResizeDelta(null);
|
|
178
|
+
setInitialContentSize(null);
|
|
179
|
+
onResizeEnd();
|
|
180
|
+
};
|
|
181
|
+
const continuousContentStyle = resizeDelta && initialContentSize ? {
|
|
182
|
+
width: initialContentSize.width + resizeDelta.width
|
|
183
|
+
} : void 0;
|
|
184
|
+
const previewOverlay = resizeSnapPreview ? /* @__PURE__ */ jsx(
|
|
185
|
+
"div",
|
|
186
|
+
{
|
|
187
|
+
className: lanes_item_default["preview-overlay"],
|
|
188
|
+
style: {
|
|
189
|
+
width: resizeSnapPreview.widthPx,
|
|
190
|
+
height: resizeSnapPreview.heightPx ?? "100%"
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
) : null;
|
|
194
|
+
return /* @__PURE__ */ jsxs(
|
|
195
|
+
"div",
|
|
196
|
+
{
|
|
197
|
+
ref: mergedRef,
|
|
198
|
+
className: itemClassName,
|
|
199
|
+
style,
|
|
200
|
+
...{ [GRID_ITEM_DATA_KEY]: itemKey },
|
|
201
|
+
"data-wp-grid-item-resizing": isResizing || void 0,
|
|
202
|
+
children: [
|
|
203
|
+
actionableArea ? /* @__PURE__ */ jsx(
|
|
204
|
+
"div",
|
|
205
|
+
{
|
|
206
|
+
className: actionable_area_slot_default["actionable-area-slot"],
|
|
207
|
+
children: /* @__PURE__ */ jsx(
|
|
208
|
+
"div",
|
|
209
|
+
{
|
|
210
|
+
style: { display: "contents" },
|
|
211
|
+
...dragging ? { inert: "" } : {},
|
|
212
|
+
children: actionableArea
|
|
213
|
+
}
|
|
214
|
+
)
|
|
215
|
+
}
|
|
216
|
+
) : null,
|
|
217
|
+
/* @__PURE__ */ jsxs(
|
|
218
|
+
"div",
|
|
219
|
+
{
|
|
220
|
+
ref: setActivatorNodeRef,
|
|
221
|
+
...attributes,
|
|
222
|
+
...listeners,
|
|
223
|
+
style: {
|
|
224
|
+
height: "100%",
|
|
225
|
+
cursor: getItemCursor(disabled, interacting)
|
|
226
|
+
},
|
|
227
|
+
children: [
|
|
228
|
+
/* @__PURE__ */ jsxs(
|
|
229
|
+
"div",
|
|
230
|
+
{
|
|
231
|
+
ref: contentMergedRef,
|
|
232
|
+
className: lanes_item_default["item-content"],
|
|
233
|
+
style: continuousContentStyle,
|
|
234
|
+
children: [
|
|
235
|
+
children,
|
|
236
|
+
!disabled && /* @__PURE__ */ jsx(
|
|
237
|
+
ResizeHandle,
|
|
238
|
+
{
|
|
239
|
+
itemId: itemKey,
|
|
240
|
+
verticalResizable: false,
|
|
241
|
+
onResize: handleResize,
|
|
242
|
+
onResizeEnd: handleResizeEnd,
|
|
243
|
+
renderResizeHandle
|
|
244
|
+
}
|
|
245
|
+
)
|
|
246
|
+
]
|
|
247
|
+
}
|
|
248
|
+
),
|
|
249
|
+
previewOverlay
|
|
250
|
+
]
|
|
251
|
+
}
|
|
252
|
+
)
|
|
253
|
+
]
|
|
254
|
+
}
|
|
255
|
+
);
|
|
256
|
+
}
|
|
257
|
+
export {
|
|
258
|
+
LanesItem
|
|
259
|
+
};
|
|
260
|
+
//# sourceMappingURL=lanes-item.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../src/dashboard-lanes/lanes-item.tsx", "../../../style-runtime/src/index.ts", "../../src/shared/actionable-area-slot.module.css", "../../src/dashboard-lanes/lanes-item.module.css"],
|
|
4
|
+
"sourcesContent": ["/**\n * External dependencies\n */\nimport { useSortable } from '@dnd-kit/sortable';\nimport clsx from 'clsx';\n\n/**\n * WordPress dependencies\n */\nimport { useState, useRef } from '@wordpress/element';\nimport { useMergeRefs } from '@wordpress/compose';\n\n/**\n * Internal dependencies\n */\nimport actionableAreaStyles from '../shared/actionable-area-slot.module.css';\nimport ResizeHandle from '../shared/resize-handle';\nimport { clampResizeDelta, type ResizeSnapSize } from '../shared/resize-snap';\nimport { GRID_ITEM_DATA_KEY } from '../shared/grid-item-key';\nimport type { ResizeDelta, ResizeHandleRenderProps } from '../shared/types';\nimport styles from './lanes-item.module.css';\n\nfunction getItemCursor(\n\tdisabled: boolean,\n\tinteracting: boolean\n): React.CSSProperties[ 'cursor' ] {\n\tif ( disabled ) {\n\t\treturn 'default';\n\t}\n\tif ( interacting ) {\n\t\treturn undefined;\n\t}\n\treturn 'grab';\n}\n\n/**\n * Props for the internal `<LanesItem />` wrapper.\n */\nexport type LanesItemProps = {\n\t/**\n\t * Item key. Forwarded to dnd-kit and emitted as the\n\t * `data-wp-grid-item-key` attribute the hook reads to map measured DOM\n\t * nodes back to logical items.\n\t */\n\titemKey: string;\n\n\t/**\n\t * Inline placement style produced by `useLanePlacement`. On native\n\t * (`display: grid-lanes`), only `gridColumn: span N`. While\n\t * polyfilling, also `gridColumnStart` / `gridRowStart` /\n\t * `gridRowEnd: span N`.\n\t */\n\tplacementStyle: React.CSSProperties;\n\n\t/**\n\t * Whether drag and resize interactions are disabled.\n\t */\n\tdisabled?: boolean;\n\n\t/**\n\t * Whether any tile in the surface is currently being dragged or\n\t * resized. Drives the drag activator cursor.\n\t */\n\tinteracting?: boolean;\n\n\t/**\n\t * Whether a tile drag is in progress. Mutes each tile's\n\t * `actionableArea` with `inert` so hovers on other tiles' controls\n\t * do not steal the gesture.\n\t *\n\t * @default false\n\t */\n\tdragging?: boolean;\n\n\tchildren: React.ReactNode;\n\n\tactionableArea?: React.ReactNode;\n\n\tonResize: ( id: string, delta: ResizeDelta ) => void;\n\n\t/**\n\t * Snapped column span in pixels for the resize-preview outline.\n\t */\n\tresizeSnapPreview?: ResizeSnapSize | null;\n\n\t/**\n\t * Minimum tile width while resizing, in pixels (one column track).\n\t */\n\tminResizeWidthPx: number;\n\n\tonResizeEnd: () => void;\n\n\trenderResizeHandle?: React.ComponentType< ResizeHandleRenderProps >;\n};\n\nexport function LanesItem( {\n\titemKey,\n\tplacementStyle,\n\tdisabled = false,\n\tinteracting = false,\n\tchildren,\n\tactionableArea = null,\n\tonResize,\n\tonResizeEnd,\n\tresizeSnapPreview = null,\n\tminResizeWidthPx,\n\trenderResizeHandle,\n\tdragging = false,\n}: LanesItemProps ) {\n\tconst [ resizeDelta, setResizeDelta ] = useState< ResizeDelta | null >(\n\t\tnull\n\t);\n\tconst [ initialContentSize, setInitialContentSize ] = useState< {\n\t\twidth: number;\n\t\theight: number;\n\t} | null >( null );\n\tconst itemRef = useRef< HTMLDivElement >( null );\n\tconst contentRef = useRef< HTMLDivElement >( null );\n\n\tconst {\n\t\tattributes,\n\t\tlisteners,\n\t\tsetNodeRef,\n\t\tsetActivatorNodeRef,\n\t\tisDragging,\n\t} = useSortable( {\n\t\tid: itemKey,\n\t\tdisabled,\n\t} );\n\tconst mergedRef = useMergeRefs( [ itemRef, setNodeRef ] );\n\tconst contentMergedRef = useMergeRefs( [ contentRef ] );\n\n\tconst style: React.CSSProperties = {\n\t\t...placementStyle,\n\t\talignSelf: 'start',\n\t};\n\n\tconst isResizing = resizeDelta !== null;\n\tconst itemClassName = clsx(\n\t\tstyles.item,\n\t\tisDragging && styles[ 'is-dragging' ],\n\t\tisResizing && styles[ 'is-resizing' ]\n\t);\n\n\tconst handleResize = ( delta: ResizeDelta ) => {\n\t\tconst contentNode = contentRef.current;\n\t\tlet baselineSize = initialContentSize;\n\t\tif ( contentNode && ! baselineSize ) {\n\t\t\tconst { width, height } = contentNode.getBoundingClientRect();\n\t\t\tbaselineSize = { width, height };\n\t\t\tsetInitialContentSize( baselineSize );\n\t\t}\n\t\tlet clamped: ResizeDelta = { width: delta.width, height: 0 };\n\t\tif ( baselineSize ) {\n\t\t\tclamped = clampResizeDelta( clamped, baselineSize, {\n\t\t\t\twidth: minResizeWidthPx,\n\t\t\t} );\n\t\t}\n\t\tsetResizeDelta( clamped );\n\t\tonResize( itemKey, clamped );\n\t};\n\n\tconst handleResizeEnd = () => {\n\t\tsetResizeDelta( null );\n\t\tsetInitialContentSize( null );\n\t\tonResizeEnd();\n\t};\n\n\tconst continuousContentStyle: React.CSSProperties | undefined =\n\t\tresizeDelta && initialContentSize\n\t\t\t? {\n\t\t\t\t\twidth: initialContentSize.width + resizeDelta.width,\n\t\t\t }\n\t\t\t: undefined;\n\n\tconst previewOverlay = resizeSnapPreview ? (\n\t\t<div\n\t\t\tclassName={ styles[ 'preview-overlay' ] }\n\t\t\tstyle={ {\n\t\t\t\twidth: resizeSnapPreview.widthPx,\n\t\t\t\theight: resizeSnapPreview.heightPx ?? '100%',\n\t\t\t} }\n\t\t/>\n\t) : null;\n\n\treturn (\n\t\t<div\n\t\t\tref={ mergedRef }\n\t\t\tclassName={ itemClassName }\n\t\t\tstyle={ style }\n\t\t\t{ ...{ [ GRID_ITEM_DATA_KEY ]: itemKey } }\n\t\t\tdata-wp-grid-item-resizing={ isResizing || undefined }\n\t\t>\n\t\t\t{ actionableArea ? (\n\t\t\t\t<div\n\t\t\t\t\tclassName={ actionableAreaStyles[ 'actionable-area-slot' ] }\n\t\t\t\t>\n\t\t\t\t\t<div\n\t\t\t\t\t\tstyle={ { display: 'contents' } }\n\t\t\t\t\t\t{ ...( dragging ? { inert: '' } : {} ) }\n\t\t\t\t\t>\n\t\t\t\t\t\t{ actionableArea }\n\t\t\t\t\t</div>\n\t\t\t\t</div>\n\t\t\t) : null }\n\n\t\t\t<div\n\t\t\t\tref={ setActivatorNodeRef }\n\t\t\t\t{ ...attributes }\n\t\t\t\t{ ...listeners }\n\t\t\t\tstyle={ {\n\t\t\t\t\theight: '100%',\n\t\t\t\t\tcursor: getItemCursor( disabled, interacting ),\n\t\t\t\t} }\n\t\t\t>\n\t\t\t\t<div\n\t\t\t\t\tref={ contentMergedRef }\n\t\t\t\t\tclassName={ styles[ 'item-content' ] }\n\t\t\t\t\tstyle={ continuousContentStyle }\n\t\t\t\t>\n\t\t\t\t\t{ children }\n\t\t\t\t\t{ ! disabled && (\n\t\t\t\t\t\t<ResizeHandle\n\t\t\t\t\t\t\titemId={ itemKey }\n\t\t\t\t\t\t\tverticalResizable={ false }\n\t\t\t\t\t\t\tonResize={ handleResize }\n\t\t\t\t\t\t\tonResizeEnd={ handleResizeEnd }\n\t\t\t\t\t\t\trenderResizeHandle={ renderResizeHandle }\n\t\t\t\t\t\t/>\n\t\t\t\t\t) }\n\t\t\t\t</div>\n\t\t\t\t{ previewOverlay }\n\t\t\t</div>\n\t\t</div>\n\t);\n}\n", "type GlobalScopeWithStyleRuntime = typeof globalThis & {\n\t// This global is shared by separately bundled copies of this package.\n\t// Keep its shape backward compatible after release.\n\t__wpStyleRuntime?: {\n\t\tdocuments: Map< Document, number >;\n\t\tstyles: Map< string, string >;\n\t\tinjectedStyles: WeakMap< Document, Set< string > >;\n\t};\n};\n\nconst STYLE_HASH_ATTRIBUTE = 'data-wp-hash';\n\n/**\n * Returns the shared style runtime registry.\n *\n * The registry is stored on `globalThis` so separately bundled copies of this\n * package can coordinate through the same document and style maps.\n *\n * @return The shared runtime registry.\n */\nfunction getRuntime() {\n\tconst globalScope = globalThis as GlobalScopeWithStyleRuntime;\n\n\tif ( globalScope.__wpStyleRuntime ) {\n\t\treturn globalScope.__wpStyleRuntime;\n\t}\n\n\tglobalScope.__wpStyleRuntime = {\n\t\tdocuments: new Map(),\n\t\tstyles: new Map(),\n\t\tinjectedStyles: new WeakMap(),\n\t};\n\n\tif ( typeof document !== 'undefined' ) {\n\t\tregisterDocument( document );\n\t}\n\n\treturn globalScope.__wpStyleRuntime;\n}\n\n/**\n * Checks whether a document already contains a style tag for a hash.\n *\n * @param targetDocument Document to inspect.\n * @param hash Stable hash for the transformed CSS.\n *\n * @return Whether the style hash already exists in the document.\n */\nfunction documentContainsStyleHash(\n\ttargetDocument: Document,\n\thash: string\n): boolean {\n\tif ( ! targetDocument.head ) {\n\t\treturn false;\n\t}\n\n\tfor ( const style of targetDocument.head.querySelectorAll(\n\t\t`style[${ STYLE_HASH_ATTRIBUTE }]`\n\t) ) {\n\t\tif ( style.getAttribute( STYLE_HASH_ATTRIBUTE ) === hash ) {\n\t\t\treturn true;\n\t\t}\n\t}\n\n\treturn false;\n}\n\n/**\n * Injects a registered style into a document, unless that document already\n * contains a style tag for the same hash.\n *\n * @param targetDocument Document to inject the style into.\n * @param hash Stable hash for the transformed CSS.\n * @param css CSS text to inject.\n */\nfunction injectStyle( targetDocument: Document, hash: string, css: string ) {\n\tif ( ! targetDocument.head ) {\n\t\treturn;\n\t}\n\n\tconst runtime = getRuntime();\n\tlet injectedStyles = runtime.injectedStyles.get( targetDocument );\n\n\tif ( ! injectedStyles ) {\n\t\tinjectedStyles = new Set();\n\t\truntime.injectedStyles.set( targetDocument, injectedStyles );\n\t}\n\n\tif ( injectedStyles.has( hash ) ) {\n\t\treturn;\n\t}\n\n\t// Older generated CSS module output can still inject matching style tags\n\t// after this document's cache is created, so keep the DOM as the fallback\n\t// source of truth on cache misses.\n\tif ( documentContainsStyleHash( targetDocument, hash ) ) {\n\t\tinjectedStyles.add( hash );\n\t\treturn;\n\t}\n\n\tconst style = targetDocument.createElement( 'style' );\n\tstyle.setAttribute( STYLE_HASH_ATTRIBUTE, hash );\n\tstyle.appendChild( targetDocument.createTextNode( css ) );\n\ttargetDocument.head.appendChild( style );\n\tinjectedStyles.add( hash );\n}\n\n/**\n * Registers a document as a style injection target.\n *\n * Existing registered styles are replayed into the document immediately.\n * Documents are reference-counted so multiple providers can safely register the\n * same document without one cleanup removing it while another registration is\n * still active.\n *\n * @param targetDocument Document to receive registered styles.\n * @return Cleanup function that unregisters this document registration.\n */\nexport function registerDocument( targetDocument: Document ) {\n\tconst runtime = getRuntime();\n\n\truntime.documents.set(\n\t\ttargetDocument,\n\t\t( runtime.documents.get( targetDocument ) ?? 0 ) + 1\n\t);\n\n\tfor ( const [ hash, css ] of runtime.styles ) {\n\t\tinjectStyle( targetDocument, hash, css );\n\t}\n\n\treturn () => {\n\t\tconst count = runtime.documents.get( targetDocument );\n\n\t\tif ( count === undefined ) {\n\t\t\treturn;\n\t\t}\n\n\t\tif ( count <= 1 ) {\n\t\t\truntime.documents.delete( targetDocument );\n\t\t\treturn;\n\t\t}\n\n\t\truntime.documents.set( targetDocument, count - 1 );\n\t};\n}\n\n/**\n * Registers a style and injects it into all registered documents.\n *\n * The hash is used as the deduplication key, so calling this repeatedly with\n * the same hash will not add duplicate style tags to a document.\n * Registered styles are retained for the lifetime of the page so they can be\n * replayed into documents that are registered later.\n *\n * @param hash Stable hash for the transformed CSS.\n * @param css CSS text to inject.\n */\nexport function registerStyle( hash: string, css: string ) {\n\tconst runtime = getRuntime();\n\n\truntime.styles.set( hash, css );\n\n\tfor ( const targetDocument of runtime.documents.keys() ) {\n\t\tinjectStyle( targetDocument, hash, css );\n\t}\n}\n", "import { registerStyle } from '@wordpress/style-runtime';\nif (typeof process === 'undefined' || process.env.NODE_ENV !== 'test') {\n\tregisterStyle(\"ac1094954c\", \"._1c54fe8165d3023e__actionable-area-slot{opacity:1}@media (prefers-reduced-motion:no-preference){._1c54fe8165d3023e__actionable-area-slot{transition:opacity var(--wpds-motion-duration-md,.2s) var(--wpds-motion-easing-subtle,cubic-bezier(.15,0,.15,1))}}[data-wp-grid-resizing] ._1c54fe8165d3023e__actionable-area-slot{opacity:0;pointer-events:none}\");\n}\nexport default {\"actionable-area-slot\":\"_1c54fe8165d3023e__actionable-area-slot\"};\n", "import { registerStyle } from '@wordpress/style-runtime';\nif (typeof process === 'undefined' || process.env.NODE_ENV !== 'test') {\n\tregisterStyle(\"97a2a51c0b\", \"._0a62d9f1dff8c7d8__item{position:relative}._20c43fcd930d828a__item-content{height:100%;position:relative}._11928ee35f1a9519__is-resizing{overflow:visible;z-index:1}._11928ee35f1a9519__is-resizing ._20c43fcd930d828a__item-content{overflow:visible;position:relative;z-index:2}.b7fc83c8b16e9ee5__is-dragging{pointer-events:none}[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{border-radius:var(--wp-grid-placeholder-radius,0)}@media not (prefers-reduced-motion:reduce){[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{animation:b026dda570d0eea0__wp-grid-item-placeholder-in 0ms linear var(--wpds-motion-duration-sm,.1s) forwards;opacity:1;outline-color:transparent;outline-style:var(--wp-grid-placeholder-outline-style,dashed);outline-width:0}@keyframes b026dda570d0eea0__wp-grid-item-placeholder-in{to{opacity:var(--wp-grid-placeholder-opacity,.4);outline-color:var(--wp-grid-placeholder-outline-color,var(--wpds-color-stroke-interactive-brand,var(--wp-admin-theme-color,#3858e9)));outline-width:var(--wpds-border-width-sm,2px)}}}@media (prefers-reduced-motion:reduce){[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{opacity:var(--wp-grid-placeholder-opacity,.4);outline:var(--wpds-border-width-sm,2px) var(--wp-grid-placeholder-outline-style,dashed) var(--wp-grid-placeholder-outline-color,var(--wpds-color-stroke-interactive-brand,var(--wp-admin-theme-color,#3858e9)))}}@media (forced-colors:active){[data-wp-grid-dragging] .b7fc83c8b16e9ee5__is-dragging{--wp-grid-placeholder-outline-color:Highlight}}.cd44faab32c27168__preview-overlay{background:transparent;border:var(--wpds-border-width-sm,2px) var(--wp-grid-resize-preview-outline-style,solid) var(--wp-grid-placeholder-outline-color,var(--wpds-color-stroke-interactive-brand,var(--wp-admin-theme-color,#3858e9)));box-sizing:border-box;inset-inline-start:0;pointer-events:none;position:absolute;top:0;z-index:0}@media (forced-colors:active){.cd44faab32c27168__preview-overlay{border-color:Highlight}}\");\n}\nexport default {\"item\":\"_0a62d9f1dff8c7d8__item\",\"item-content\":\"_20c43fcd930d828a__item-content\",\"is-resizing\":\"_11928ee35f1a9519__is-resizing\",\"is-dragging\":\"b7fc83c8b16e9ee5__is-dragging\",\"wp-grid-item-placeholder-in\":\"b026dda570d0eea0__wp-grid-item-placeholder-in\",\"preview-overlay\":\"cd44faab32c27168__preview-overlay\"};\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
//# sourceMappingURL=types.mjs.map
|
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
// packages/grid/src/dashboard-lanes/use-lane-placement.ts
|
|
2
|
+
import { useState, useLayoutEffect, useMemo } from "@wordpress/element";
|
|
3
|
+
import { computeLanePlacements } from "./lane-placement.mjs";
|
|
4
|
+
import { GRID_ITEM_DATA_KEY } from "../shared/grid-item-key.mjs";
|
|
5
|
+
var DEFAULT_ROW_UNIT = 4;
|
|
6
|
+
function supportsGridLanes() {
|
|
7
|
+
if (typeof CSS === "undefined" || !CSS.supports) {
|
|
8
|
+
return false;
|
|
9
|
+
}
|
|
10
|
+
return CSS.supports("display", "grid-lanes");
|
|
11
|
+
}
|
|
12
|
+
function clampSpan(span) {
|
|
13
|
+
if (typeof span !== "number" || !Number.isFinite(span)) {
|
|
14
|
+
return 1;
|
|
15
|
+
}
|
|
16
|
+
return Math.max(1, Math.floor(span));
|
|
17
|
+
}
|
|
18
|
+
function useLanePlacement(container, input) {
|
|
19
|
+
const [isPolyfilled] = useState(() => !supportsGridLanes());
|
|
20
|
+
const [itemStyles, setItemStyles] = useState(() => /* @__PURE__ */ new Map());
|
|
21
|
+
const nativeStyles = useMemo(() => {
|
|
22
|
+
const map = /* @__PURE__ */ new Map();
|
|
23
|
+
for (const item of input.items) {
|
|
24
|
+
map.set(item.key, {
|
|
25
|
+
gridColumn: `span ${clampSpan(item.span)}`
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
return map;
|
|
29
|
+
}, [input.items]);
|
|
30
|
+
const itemsSignature = useMemo(() => {
|
|
31
|
+
return input.items.map(
|
|
32
|
+
(item) => `${item.key}/${item.span ?? 1}/${item.lane ?? ""}`
|
|
33
|
+
).join("\0");
|
|
34
|
+
}, [input.items]);
|
|
35
|
+
const itemsForPlacement = useMemo(() => input.items, [itemsSignature]);
|
|
36
|
+
const { lanes, gap, flowTolerance, rowUnit } = input;
|
|
37
|
+
useLayoutEffect(() => {
|
|
38
|
+
if (!isPolyfilled || !container) {
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
if (typeof ResizeObserver === "undefined") {
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
const heights = /* @__PURE__ */ new Map();
|
|
45
|
+
const observed = /* @__PURE__ */ new Set();
|
|
46
|
+
let cancelled = false;
|
|
47
|
+
let rafId = null;
|
|
48
|
+
const recompute = () => {
|
|
49
|
+
if (rafId !== null || cancelled) {
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
rafId = requestAnimationFrame(() => {
|
|
53
|
+
rafId = null;
|
|
54
|
+
if (cancelled) {
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
const itemsWithHeight = itemsForPlacement.map((item) => ({
|
|
58
|
+
key: item.key,
|
|
59
|
+
span: clampSpan(item.span),
|
|
60
|
+
lane: item.lane,
|
|
61
|
+
height: heights.get(item.key) ?? 0
|
|
62
|
+
}));
|
|
63
|
+
const result = computeLanePlacements({
|
|
64
|
+
items: itemsWithHeight,
|
|
65
|
+
lanes,
|
|
66
|
+
gap,
|
|
67
|
+
flowTolerance
|
|
68
|
+
});
|
|
69
|
+
const effectiveRowUnit = Math.max(
|
|
70
|
+
1,
|
|
71
|
+
rowUnit ?? DEFAULT_ROW_UNIT
|
|
72
|
+
);
|
|
73
|
+
const next = /* @__PURE__ */ new Map();
|
|
74
|
+
for (const item of itemsForPlacement) {
|
|
75
|
+
const placement = result.placements.get(item.key);
|
|
76
|
+
if (!placement) {
|
|
77
|
+
continue;
|
|
78
|
+
}
|
|
79
|
+
const height = heights.get(item.key) ?? 0;
|
|
80
|
+
const rowStart = Math.floor(placement.top / effectiveRowUnit) + 1;
|
|
81
|
+
const rowSpan = Math.max(
|
|
82
|
+
1,
|
|
83
|
+
Math.ceil(height / effectiveRowUnit)
|
|
84
|
+
);
|
|
85
|
+
next.set(item.key, {
|
|
86
|
+
gridColumnStart: placement.lane + 1,
|
|
87
|
+
gridColumnEnd: `span ${placement.span}`,
|
|
88
|
+
gridRowStart: rowStart,
|
|
89
|
+
gridRowEnd: `span ${rowSpan}`
|
|
90
|
+
});
|
|
91
|
+
}
|
|
92
|
+
setItemStyles(next);
|
|
93
|
+
});
|
|
94
|
+
};
|
|
95
|
+
const resizeObserver = new ResizeObserver((entries) => {
|
|
96
|
+
let changed = false;
|
|
97
|
+
for (const entry of entries) {
|
|
98
|
+
const key = entry.target.getAttribute(
|
|
99
|
+
GRID_ITEM_DATA_KEY
|
|
100
|
+
);
|
|
101
|
+
if (!key) {
|
|
102
|
+
continue;
|
|
103
|
+
}
|
|
104
|
+
const newHeight = entry.contentRect.height;
|
|
105
|
+
if (heights.get(key) !== newHeight) {
|
|
106
|
+
heights.set(key, newHeight);
|
|
107
|
+
changed = true;
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
if (changed) {
|
|
111
|
+
recompute();
|
|
112
|
+
}
|
|
113
|
+
});
|
|
114
|
+
const refreshObserved = () => {
|
|
115
|
+
const current = container.querySelectorAll(
|
|
116
|
+
`[${GRID_ITEM_DATA_KEY}]`
|
|
117
|
+
);
|
|
118
|
+
for (const element of current) {
|
|
119
|
+
if (!observed.has(element)) {
|
|
120
|
+
observed.add(element);
|
|
121
|
+
resizeObserver.observe(element);
|
|
122
|
+
const key = element.getAttribute(GRID_ITEM_DATA_KEY);
|
|
123
|
+
if (key) {
|
|
124
|
+
const rect = element.getBoundingClientRect();
|
|
125
|
+
heights.set(key, rect.height);
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
for (const element of observed) {
|
|
130
|
+
if (!container.contains(element)) {
|
|
131
|
+
resizeObserver.unobserve(element);
|
|
132
|
+
observed.delete(element);
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
};
|
|
136
|
+
const mutationObserver = typeof MutationObserver !== "undefined" ? new MutationObserver(() => {
|
|
137
|
+
refreshObserved();
|
|
138
|
+
recompute();
|
|
139
|
+
}) : null;
|
|
140
|
+
if (mutationObserver) {
|
|
141
|
+
mutationObserver.observe(container, {
|
|
142
|
+
childList: true,
|
|
143
|
+
subtree: true,
|
|
144
|
+
attributes: true,
|
|
145
|
+
attributeFilter: [GRID_ITEM_DATA_KEY]
|
|
146
|
+
});
|
|
147
|
+
}
|
|
148
|
+
refreshObserved();
|
|
149
|
+
recompute();
|
|
150
|
+
return () => {
|
|
151
|
+
cancelled = true;
|
|
152
|
+
if (rafId !== null) {
|
|
153
|
+
cancelAnimationFrame(rafId);
|
|
154
|
+
}
|
|
155
|
+
resizeObserver.disconnect();
|
|
156
|
+
mutationObserver?.disconnect();
|
|
157
|
+
};
|
|
158
|
+
}, [
|
|
159
|
+
container,
|
|
160
|
+
isPolyfilled,
|
|
161
|
+
lanes,
|
|
162
|
+
gap,
|
|
163
|
+
flowTolerance,
|
|
164
|
+
rowUnit,
|
|
165
|
+
itemsForPlacement
|
|
166
|
+
]);
|
|
167
|
+
if (!isPolyfilled) {
|
|
168
|
+
return { itemStyles: nativeStyles, isPolyfilled: false };
|
|
169
|
+
}
|
|
170
|
+
if (itemStyles.size === 0) {
|
|
171
|
+
return {
|
|
172
|
+
itemStyles: nativeStyles,
|
|
173
|
+
isPolyfilled: true
|
|
174
|
+
};
|
|
175
|
+
}
|
|
176
|
+
return { itemStyles, isPolyfilled: true };
|
|
177
|
+
}
|
|
178
|
+
export {
|
|
179
|
+
useLanePlacement
|
|
180
|
+
};
|
|
181
|
+
//# sourceMappingURL=use-lane-placement.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../src/dashboard-lanes/use-lane-placement.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * WordPress dependencies\n */\nimport { useState, useLayoutEffect, useMemo } from '@wordpress/element';\n\n/**\n * Internal dependencies\n */\nimport { computeLanePlacements } from './lane-placement';\nimport { GRID_ITEM_DATA_KEY } from '../shared/grid-item-key';\n\nconst DEFAULT_ROW_UNIT = 4;\n\nfunction supportsGridLanes(): boolean {\n\tif ( typeof CSS === 'undefined' || ! CSS.supports ) {\n\t\treturn false;\n\t}\n\treturn CSS.supports( 'display', 'grid-lanes' );\n}\n\nfunction clampSpan( span: number | undefined ): number {\n\tif ( typeof span !== 'number' || ! Number.isFinite( span ) ) {\n\t\treturn 1;\n\t}\n\treturn Math.max( 1, Math.floor( span ) );\n}\n\n/**\n * Logical item passed to the hook. The renderer is responsible for\n * mounting a DOM node with `data-wp-grid-item-key={ item.key }` for each\n * entry; the hook will measure that node and produce inline styles.\n */\nexport type LaneItemInput = {\n\tkey: string;\n\tspan?: number;\n\tlane?: number;\n};\n\nexport type UseLanePlacementInput = {\n\titems: ReadonlyArray< LaneItemInput >;\n\tlanes: number;\n\tgap: number;\n\tflowTolerance: number;\n\t/**\n\t * Snap unit for `grid-row-start` / `grid-row-end: span N` math.\n\t * Smaller values produce sharper placement at the cost of more\n\t * implicit rows. Defaults to 4 (px).\n\t */\n\trowUnit?: number;\n};\n\nexport type UseLanePlacementResult = {\n\t/**\n\t * Inline styles to apply to each item, keyed by item key. On\n\t * native (`display: grid-lanes`), entries carry only\n\t * `gridColumn: span N`; the browser handles row placement. While\n\t * polyfilling, entries also carry explicit `grid-column-start` /\n\t * `grid-row-*` values.\n\t */\n\titemStyles: Map< string, React.CSSProperties >;\n\n\t/**\n\t * `false` when the host browser supports `display: grid-lanes`\n\t * natively. The hook avoids mounting any observers in that case.\n\t */\n\tisPolyfilled: boolean;\n};\n\n/**\n * Hook that measures item heights and resolves their placement when\n * `display: grid-lanes` is unavailable, falling through to a no-op\n * pass when the host browser supports the feature natively.\n *\n * Usage from the renderer:\n *\n * ```tsx\n * const [ container, setContainer ] = useState< HTMLDivElement | null >( null );\n * const { itemStyles } = useLanePlacement( container, {\n * items: layout,\n * lanes: columns,\n * gap: gapPx,\n * flowTolerance: 16,\n * } );\n *\n * return (\n * <div ref={ setContainer } style={ { display: 'grid-lanes', ... } }>\n * { items.map( ( item ) => (\n * <div\n * key={ item.key }\n * data-wp-grid-item-key={ item.key }\n * style={ itemStyles.get( item.key ) }\n * >\n * { ... }\n * </div>\n * ) ) }\n * </div>\n * );\n * ```\n *\n * @param container HTMLElement (or null pre-mount) hosting the items.\n * @param input Logical items, lane count, gap, and tuning.\n * @return Per-item styles plus the `isPolyfilled` flag.\n */\nexport function useLanePlacement(\n\tcontainer: HTMLElement | null,\n\tinput: UseLanePlacementInput\n): UseLanePlacementResult {\n\t// Detect once at mount. SSR returns `true` (CSS undefined); the\n\t// client-first render returns the real value. Either path produces\n\t// the same DOM until the polyfill effect runs (both emit\n\t// span-only styles), so there is no hydration mismatch.\n\tconst [ isPolyfilled ] = useState( () => ! supportsGridLanes() );\n\n\tconst [ itemStyles, setItemStyles ] = useState<\n\t\tMap< string, React.CSSProperties >\n\t>( () => new Map() );\n\n\t// Native pass-through: items only need their column span; the\n\t// browser handles row placement. Memoized so a stable items\n\t// array yields a stable Map identity.\n\tconst nativeStyles = useMemo( () => {\n\t\tconst map = new Map< string, React.CSSProperties >();\n\t\tfor ( const item of input.items ) {\n\t\t\tmap.set( item.key, {\n\t\t\t\tgridColumn: `span ${ clampSpan( item.span ) }`,\n\t\t\t} );\n\t\t}\n\t\treturn map;\n\t}, [ input.items ] );\n\n\t// Stable signature of items for deps. Keys, spans, and explicit\n\t// lanes are the only fields that influence observer wiring or\n\t// placement, so we hash exactly those.\n\tconst itemsSignature = useMemo( () => {\n\t\treturn input.items\n\t\t\t.map(\n\t\t\t\t( item ) =>\n\t\t\t\t\t`${ item.key }/${ item.span ?? 1 }/${ item.lane ?? '' }`\n\t\t\t)\n\t\t\t.join( '\\0' );\n\t}, [ input.items ] );\n\n\t// Stable array identity while placement-relevant fields match\n\t// `itemsSignature`, so the layout effect is not torn down on every\n\t// parent re-render that passes a fresh `items` reference.\n\t// eslint-disable-next-line react-hooks/exhaustive-deps -- `itemsSignature` encodes keys/spans/lanes; `input.items` reference often changes without placement changes.\n\tconst itemsForPlacement = useMemo( () => input.items, [ itemsSignature ] );\n\n\tconst { lanes, gap, flowTolerance, rowUnit } = input;\n\n\tuseLayoutEffect( () => {\n\t\tif ( ! isPolyfilled || ! container ) {\n\t\t\treturn;\n\t\t}\n\t\tif ( typeof ResizeObserver === 'undefined' ) {\n\t\t\treturn;\n\t\t}\n\n\t\tconst heights = new Map< string, number >();\n\t\tconst observed = new Set< Element >();\n\t\tlet cancelled = false;\n\t\tlet rafId: number | null = null;\n\n\t\tconst recompute = () => {\n\t\t\tif ( rafId !== null || cancelled ) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// One layout per frame even when ResizeObserver and\n\t\t\t// MutationObserver fire in the same tick.\n\t\t\trafId = requestAnimationFrame( () => {\n\t\t\t\trafId = null;\n\t\t\t\tif ( cancelled ) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tconst itemsWithHeight = itemsForPlacement.map( ( item ) => ( {\n\t\t\t\t\tkey: item.key,\n\t\t\t\t\tspan: clampSpan( item.span ),\n\t\t\t\t\tlane: item.lane,\n\t\t\t\t\theight: heights.get( item.key ) ?? 0,\n\t\t\t\t} ) );\n\t\t\t\tconst result = computeLanePlacements( {\n\t\t\t\t\titems: itemsWithHeight,\n\t\t\t\t\tlanes,\n\t\t\t\t\tgap,\n\t\t\t\t\tflowTolerance,\n\t\t\t\t} );\n\t\t\t\tconst effectiveRowUnit = Math.max(\n\t\t\t\t\t1,\n\t\t\t\t\trowUnit ?? DEFAULT_ROW_UNIT\n\t\t\t\t);\n\t\t\t\tconst next = new Map< string, React.CSSProperties >();\n\t\t\t\tfor ( const item of itemsForPlacement ) {\n\t\t\t\t\tconst placement = result.placements.get( item.key );\n\t\t\t\t\tif ( ! placement ) {\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tconst height = heights.get( item.key ) ?? 0;\n\t\t\t\t\tconst rowStart =\n\t\t\t\t\t\tMath.floor( placement.top / effectiveRowUnit ) + 1;\n\t\t\t\t\tconst rowSpan = Math.max(\n\t\t\t\t\t\t1,\n\t\t\t\t\t\tMath.ceil( height / effectiveRowUnit )\n\t\t\t\t\t);\n\t\t\t\t\tnext.set( item.key, {\n\t\t\t\t\t\tgridColumnStart: placement.lane + 1,\n\t\t\t\t\t\tgridColumnEnd: `span ${ placement.span }`,\n\t\t\t\t\t\tgridRowStart: rowStart,\n\t\t\t\t\t\tgridRowEnd: `span ${ rowSpan }`,\n\t\t\t\t\t} );\n\t\t\t\t}\n\t\t\t\tsetItemStyles( next );\n\t\t\t} );\n\t\t};\n\n\t\tconst resizeObserver = new ResizeObserver( ( entries ) => {\n\t\t\tlet changed = false;\n\t\t\tfor ( const entry of entries ) {\n\t\t\t\tconst key = ( entry.target as HTMLElement ).getAttribute(\n\t\t\t\t\tGRID_ITEM_DATA_KEY\n\t\t\t\t);\n\t\t\t\tif ( ! key ) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tconst newHeight = entry.contentRect.height;\n\t\t\t\tif ( heights.get( key ) !== newHeight ) {\n\t\t\t\t\theights.set( key, newHeight );\n\t\t\t\t\tchanged = true;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif ( changed ) {\n\t\t\t\trecompute();\n\t\t\t}\n\t\t} );\n\n\t\tconst refreshObserved = () => {\n\t\t\tconst current = container.querySelectorAll(\n\t\t\t\t`[${ GRID_ITEM_DATA_KEY }]`\n\t\t\t);\n\t\t\tfor ( const element of current ) {\n\t\t\t\tif ( ! observed.has( element ) ) {\n\t\t\t\t\tobserved.add( element );\n\t\t\t\t\tresizeObserver.observe( element );\n\t\t\t\t\tconst key = element.getAttribute( GRID_ITEM_DATA_KEY );\n\t\t\t\t\tif ( key ) {\n\t\t\t\t\t\tconst rect = (\n\t\t\t\t\t\t\telement as HTMLElement\n\t\t\t\t\t\t ).getBoundingClientRect();\n\t\t\t\t\t\theights.set( key, rect.height );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor ( const element of observed ) {\n\t\t\t\tif ( ! container.contains( element ) ) {\n\t\t\t\t\tresizeObserver.unobserve( element );\n\t\t\t\t\tobserved.delete( element );\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\n\t\t// Children may mount, unmount, or change `data-wp-grid-item-key`\n\t\t// after the container exists (drag reorders, additions). The\n\t\t// mutation observer keeps the observed set in sync.\n\t\tconst mutationObserver =\n\t\t\ttypeof MutationObserver !== 'undefined'\n\t\t\t\t? new MutationObserver( () => {\n\t\t\t\t\t\trefreshObserved();\n\t\t\t\t\t\trecompute();\n\t\t\t\t } )\n\t\t\t\t: null;\n\t\tif ( mutationObserver ) {\n\t\t\tmutationObserver.observe( container, {\n\t\t\t\tchildList: true,\n\t\t\t\tsubtree: true,\n\t\t\t\tattributes: true,\n\t\t\t\tattributeFilter: [ GRID_ITEM_DATA_KEY ],\n\t\t\t} );\n\t\t}\n\n\t\trefreshObserved();\n\t\trecompute();\n\n\t\treturn () => {\n\t\t\tcancelled = true;\n\t\t\tif ( rafId !== null ) {\n\t\t\t\tcancelAnimationFrame( rafId );\n\t\t\t}\n\t\t\tresizeObserver.disconnect();\n\t\t\tmutationObserver?.disconnect();\n\t\t};\n\t}, [\n\t\tcontainer,\n\t\tisPolyfilled,\n\t\tlanes,\n\t\tgap,\n\t\tflowTolerance,\n\t\trowUnit,\n\t\titemsForPlacement,\n\t] );\n\n\tif ( ! isPolyfilled ) {\n\t\treturn { itemStyles: nativeStyles, isPolyfilled: false };\n\t}\n\tif ( itemStyles.size === 0 ) {\n\t\t// Pre-measurement frame: emit native-shape styles so items\n\t\t// appear in their default span rather than collapsing to 1\n\t\t// column at the top-left.\n\t\treturn {\n\t\t\titemStyles: nativeStyles as Map< string, React.CSSProperties >,\n\t\t\tisPolyfilled: true,\n\t\t};\n\t}\n\treturn { itemStyles, isPolyfilled: true };\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|