@ohhwells/bridge 0.1.139-next.376 → 0.1.140
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/index.cjs +120 -303
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1 -135
- package/dist/index.d.ts +1 -135
- package/dist/index.js +120 -301
- package/dist/index.js.map +1 -1
- package/dist/pages.cjs +1 -1
- package/dist/pages.cjs.map +1 -1
- package/dist/pages.js +1 -1
- package/dist/pages.js.map +1 -1
- package/dist/styles.css +0 -62
- package/package.json +3 -3
package/dist/index.cjs
CHANGED
|
@@ -72,7 +72,6 @@ __export(index_exports, {
|
|
|
72
72
|
dropIndicatorVariants: () => dropIndicatorVariants,
|
|
73
73
|
ensureFooterTree: () => ensureFooterTree,
|
|
74
74
|
filterAvailablePages: () => filterAvailablePages,
|
|
75
|
-
foldAlignIntoTrees: () => foldAlignIntoTrees,
|
|
76
75
|
getEditModeInitialState: () => getEditModeInitialState,
|
|
77
76
|
insertFooterHours: () => insertFooterHours,
|
|
78
77
|
isEditSessionActive: () => isEditSessionActive,
|
|
@@ -81,7 +80,6 @@ __export(index_exports, {
|
|
|
81
80
|
isValidUrl: () => isValidUrl,
|
|
82
81
|
nextViableSlide: () => nextViableSlide,
|
|
83
82
|
parseAiFooterState: () => parseAiFooterState,
|
|
84
|
-
parseAiSectionsState: () => parseAiSectionsState,
|
|
85
83
|
parseTarget: () => parseTarget,
|
|
86
84
|
removeFooterBlock: () => removeFooterBlock,
|
|
87
85
|
resolveFooterCopyright: () => resolveFooterCopyright,
|
|
@@ -5298,21 +5296,19 @@ function findIndexSegment(keys) {
|
|
|
5298
5296
|
if (len < 2 || tokenLists.some((t) => t.length !== len)) return null;
|
|
5299
5297
|
let position = -1;
|
|
5300
5298
|
for (let p = 0; p < len; p++) {
|
|
5301
|
-
const
|
|
5302
|
-
const allSame =
|
|
5299
|
+
const values = tokenLists.map((t) => t[p]);
|
|
5300
|
+
const allSame = values.every((v) => v === values[0]);
|
|
5303
5301
|
if (allSame) continue;
|
|
5304
|
-
|
|
5302
|
+
const allNumeric = values.every((v) => /^\d+$/.test(v));
|
|
5303
|
+
if (!allNumeric || position !== -1) return null;
|
|
5305
5304
|
position = p;
|
|
5306
5305
|
}
|
|
5307
5306
|
if (position === -1) return null;
|
|
5308
|
-
const values = tokenLists.map((t) => t[position]);
|
|
5309
|
-
const numericCount = values.filter((v) => /^\d+$/.test(v)).length;
|
|
5310
|
-
if (numericCount !== 0 && numericCount !== values.length) return null;
|
|
5311
|
-
if (numericCount === 0 && position === len - 1) return null;
|
|
5312
5307
|
const group = tokenLists[0].slice(0, position).join("-");
|
|
5313
5308
|
if (!group) return null;
|
|
5314
|
-
|
|
5315
|
-
|
|
5309
|
+
const indices = tokenLists.map((t) => parseInt(t[position], 10));
|
|
5310
|
+
if (new Set(indices).size !== indices.length) return null;
|
|
5311
|
+
return { position, group };
|
|
5316
5312
|
}
|
|
5317
5313
|
function singleIndexSegment(key) {
|
|
5318
5314
|
const tokens = baseKey(key).split("-");
|
|
@@ -5358,19 +5354,7 @@ function detectItemGroups(sectionEl) {
|
|
|
5358
5354
|
list.push(m);
|
|
5359
5355
|
byShape.set(shape, list);
|
|
5360
5356
|
}
|
|
5361
|
-
|
|
5362
|
-
clusters.push(...shaped.filter((c) => c.length >= 2));
|
|
5363
|
-
const singles = shaped.filter((c) => c.length === 1).map((c) => c[0]);
|
|
5364
|
-
const bySlugShape = /* @__PURE__ */ new Map();
|
|
5365
|
-
for (const m of singles) {
|
|
5366
|
-
const primary = primaryKey(keyedDescendants(m));
|
|
5367
|
-
const tokens = baseKey(primary ?? "").split("-");
|
|
5368
|
-
const slugShape = `${tokens.length}|${tokens[0]}|${tokens[tokens.length - 1]}`;
|
|
5369
|
-
const list = bySlugShape.get(slugShape) ?? [];
|
|
5370
|
-
list.push(m);
|
|
5371
|
-
bySlugShape.set(slugShape, list);
|
|
5372
|
-
}
|
|
5373
|
-
clusters.push(...Array.from(bySlugShape.values()));
|
|
5357
|
+
clusters.push(...Array.from(byShape.values()));
|
|
5374
5358
|
}
|
|
5375
5359
|
for (const members of clusters) {
|
|
5376
5360
|
const keyedPerMember = members.map((m) => keyedDescendants(m));
|
|
@@ -5381,28 +5365,11 @@ function detectItemGroups(sectionEl) {
|
|
|
5381
5365
|
const dedupeKey = `${segment.group}`;
|
|
5382
5366
|
if (seenParents.has(dedupeKey)) continue;
|
|
5383
5367
|
seenParents.add(dedupeKey);
|
|
5384
|
-
|
|
5385
|
-
|
|
5386
|
-
|
|
5387
|
-
|
|
5388
|
-
|
|
5389
|
-
const cloneMatch = t.match(/^x(\d+)$/);
|
|
5390
|
-
return cloneMatch ? parseInt(cloneMatch[1], 10) : nextOriginal++;
|
|
5391
|
-
});
|
|
5392
|
-
if (new Set(indices).size !== indices.length) continue;
|
|
5393
|
-
items = members.map((el, i) => ({
|
|
5394
|
-
el,
|
|
5395
|
-
index: indices[i],
|
|
5396
|
-
keyed: keyedPerMember[i],
|
|
5397
|
-
slugToken: tokens[i]
|
|
5398
|
-
}));
|
|
5399
|
-
} else {
|
|
5400
|
-
items = members.map((el, i) => ({
|
|
5401
|
-
el,
|
|
5402
|
-
index: indexFromKey(primaries[i], segment.position),
|
|
5403
|
-
keyed: keyedPerMember[i]
|
|
5404
|
-
}));
|
|
5405
|
-
}
|
|
5368
|
+
const items = members.map((el, i) => ({
|
|
5369
|
+
el,
|
|
5370
|
+
index: indexFromKey(primaries[i], segment.position),
|
|
5371
|
+
keyed: keyedPerMember[i]
|
|
5372
|
+
}));
|
|
5406
5373
|
groups.push({ group: segment.group, parent, nested: false, items });
|
|
5407
5374
|
}
|
|
5408
5375
|
}
|
|
@@ -5526,18 +5493,6 @@ function rekeyItemClone(clone, source, sibling, group, newIndex) {
|
|
|
5526
5493
|
const delta = newIndex - source.index;
|
|
5527
5494
|
const cloneKeyed = keyedDescendants(clone);
|
|
5528
5495
|
const pairs = [];
|
|
5529
|
-
if (source.slugToken) {
|
|
5530
|
-
source.keyed.forEach((src, i) => {
|
|
5531
|
-
const target = cloneKeyed[i];
|
|
5532
|
-
if (!target || target.attr !== src.attr) return;
|
|
5533
|
-
const tokens = baseKey(src.key).split("-");
|
|
5534
|
-
if (!tokens.includes(source.slugToken)) return;
|
|
5535
|
-
const next = tokens.map((t) => t === source.slugToken ? `x${newIndex}` : t).join("-") + keySuffix(src.key);
|
|
5536
|
-
target.el.setAttribute(src.attr, next);
|
|
5537
|
-
pairs.push({ from: src.key, to: next });
|
|
5538
|
-
});
|
|
5539
|
-
return pairs;
|
|
5540
|
-
}
|
|
5541
5496
|
source.keyed.forEach((src, i) => {
|
|
5542
5497
|
const target = cloneKeyed[i];
|
|
5543
5498
|
if (!target || target.attr !== src.attr) return;
|
|
@@ -5581,12 +5536,7 @@ function syncGroup(detected, state) {
|
|
|
5581
5536
|
clone.setAttribute(ITEM_ATTR, `${detected.group}:${entry.index}`);
|
|
5582
5537
|
rekeyItemClone(clone, source, sibling, detected.group, entry.index);
|
|
5583
5538
|
source.el.insertAdjacentElement("afterend", clone);
|
|
5584
|
-
byIndex.set(entry.index, {
|
|
5585
|
-
el: clone,
|
|
5586
|
-
index: entry.index,
|
|
5587
|
-
keyed: keyedDescendants(clone),
|
|
5588
|
-
...source.slugToken ? { slugToken: `x${entry.index}` } : {}
|
|
5589
|
-
});
|
|
5539
|
+
byIndex.set(entry.index, { el: clone, index: entry.index, keyed: keyedDescendants(clone) });
|
|
5590
5540
|
}
|
|
5591
5541
|
const listed = state.items.map((e) => byIndex.get(e.index)?.el).filter((el) => !!el);
|
|
5592
5542
|
let prev = null;
|
|
@@ -5688,16 +5638,9 @@ function applyItemOps(store, ops, currentContent) {
|
|
|
5688
5638
|
const nodes = [];
|
|
5689
5639
|
const added = [];
|
|
5690
5640
|
let elements = syncGroup(detected, state);
|
|
5691
|
-
const sluggy = detected.items.some((item) => item.slugToken);
|
|
5692
|
-
const slugTokenOf = (index) => detected.items.find((item) => item.index === index)?.slugToken ?? (sluggy ? `x${index}` : void 0);
|
|
5693
5641
|
for (const add of ops.add ?? []) {
|
|
5694
5642
|
const sourceEl = elements.get(add.cloneOf);
|
|
5695
|
-
const source = sourceEl ? {
|
|
5696
|
-
el: sourceEl,
|
|
5697
|
-
index: add.cloneOf,
|
|
5698
|
-
keyed: keyedDescendants(sourceEl),
|
|
5699
|
-
...slugTokenOf(add.cloneOf) ? { slugToken: slugTokenOf(add.cloneOf) } : {}
|
|
5700
|
-
} : void 0;
|
|
5643
|
+
const source = sourceEl ? { el: sourceEl, index: add.cloneOf, keyed: keyedDescendants(sourceEl) } : void 0;
|
|
5701
5644
|
if (!source) continue;
|
|
5702
5645
|
const newIndex = Math.max(...state.items.map((e) => e.index), ...detected.items.map((i) => i.index)) + 1;
|
|
5703
5646
|
const sibling = detected.items.find((item) => item.index !== add.cloneOf && !item.el.hasAttribute(ITEM_CLONE_ATTR)) ?? null;
|
|
@@ -5724,12 +5667,7 @@ function applyItemOps(store, ops, currentContent) {
|
|
|
5724
5667
|
if (anchor) anchor.insertAdjacentElement("afterend", clone);
|
|
5725
5668
|
else source.el.insertAdjacentElement("afterend", clone);
|
|
5726
5669
|
elements.set(newIndex, clone);
|
|
5727
|
-
detected.items.push({
|
|
5728
|
-
el: clone,
|
|
5729
|
-
index: newIndex,
|
|
5730
|
-
keyed: cloneKeyed,
|
|
5731
|
-
...sluggy ? { slugToken: `x${newIndex}` } : {}
|
|
5732
|
-
});
|
|
5670
|
+
detected.items.push({ el: clone, index: newIndex, keyed: cloneKeyed });
|
|
5733
5671
|
added.push(newIndex);
|
|
5734
5672
|
elements = syncGroup(detected, state);
|
|
5735
5673
|
}
|
|
@@ -6172,25 +6110,16 @@ function foldAlignIntoTrees(state, store) {
|
|
|
6172
6110
|
nextTrees.set(id, fresh);
|
|
6173
6111
|
return fresh;
|
|
6174
6112
|
};
|
|
6175
|
-
const stripChildAligns = (node) => node.children ? {
|
|
6176
|
-
...node,
|
|
6177
|
-
children: node.children.map((child) => {
|
|
6178
|
-
const { align: _dropped, ...rest } = child;
|
|
6179
|
-
return stripChildAligns(rest);
|
|
6180
|
-
})
|
|
6181
|
-
} : node;
|
|
6182
6113
|
const nodes = {};
|
|
6183
6114
|
for (const [key, override] of Object.entries(store.nodes)) {
|
|
6184
6115
|
const match = override.align !== void 0 && key.startsWith(AI_SLOT_KEY_PREFIX) ? key.match(/^ai\.(.+?)\.r(\d+)\.b(\d+)(?:\.|$)/) : null;
|
|
6185
6116
|
const tree = match ? treeFor(match[1]) : void 0;
|
|
6186
|
-
const
|
|
6187
|
-
|
|
6188
|
-
const block = row?.blocks[blockIdx];
|
|
6189
|
-
if (!row || !block) {
|
|
6117
|
+
const block = match && tree ? tree.rows[Number(match[2])]?.blocks[Number(match[3])] : void 0;
|
|
6118
|
+
if (!block) {
|
|
6190
6119
|
nodes[key] = override;
|
|
6191
6120
|
continue;
|
|
6192
6121
|
}
|
|
6193
|
-
|
|
6122
|
+
block.align = override.align;
|
|
6194
6123
|
const rest = { ...override };
|
|
6195
6124
|
delete rest.align;
|
|
6196
6125
|
if (Object.keys(rest).length > 0) nodes[key] = rest;
|
|
@@ -6203,7 +6132,7 @@ function foldAlignIntoTrees(state, store) {
|
|
|
6203
6132
|
continue;
|
|
6204
6133
|
}
|
|
6205
6134
|
for (const row of tree.rows) {
|
|
6206
|
-
|
|
6135
|
+
for (const block of row.blocks) block.align = override.align;
|
|
6207
6136
|
}
|
|
6208
6137
|
const rest = { ...override };
|
|
6209
6138
|
delete rest.align;
|
|
@@ -7364,7 +7293,6 @@ var blockAlignStyle = (blockAlign) => blockAlign ? {
|
|
|
7364
7293
|
alignItems: blockAlign === "left" ? "flex-start" : blockAlign === "right" ? "flex-end" : "center",
|
|
7365
7294
|
textAlign: blockAlign
|
|
7366
7295
|
} : {};
|
|
7367
|
-
var fullBleedBlock = (block) => block.type === "carousel" || block.type === "group" && str(block.slots?.layout) === "overlap";
|
|
7368
7296
|
var featureLines = (value) => value.split(/\n|<br\s*\/?>/i).map((line) => line.trim()).filter(Boolean);
|
|
7369
7297
|
var AI_MOBILE_CSS = [
|
|
7370
7298
|
// Unscoped (applies at every viewport, not just mobile): re-enables pointer-events for the
|
|
@@ -7409,7 +7337,7 @@ var AI_MOBILE_CSS = [
|
|
|
7409
7337
|
// page's first section. Top only (bottom needs no nav clearance); ~96px approximates the
|
|
7410
7338
|
// template nav's own height (measured ~94px) — there's no shared `--ohw-header-h` var to read
|
|
7411
7339
|
// an exact figure from (no live measurement exists), so this is a safe approximation, not a
|
|
7412
|
-
// pixel-exact fit. Horizontal spacing already comes from `data-ai-
|
|
7340
|
+
// pixel-exact fit. Horizontal spacing already comes from `data-ai-container`.
|
|
7413
7341
|
'[data-ai-overlay-clearance] [data-ai-overlap-layer="overlay"]{padding-top:96px}',
|
|
7414
7342
|
// A full-bleed carousel's height is pure arithmetic: it spans the whole window, so 16/9 turns
|
|
7415
7343
|
// window width straight into height. Measured at 16/9 it came out ~90% of the viewport at EVERY
|
|
@@ -7425,10 +7353,8 @@ var AI_MOBILE_CSS = [
|
|
|
7425
7353
|
"[data-ai-section]{overflow-x:hidden}",
|
|
7426
7354
|
// `:not([data-ai-full-bleed])`: this `!important` gutter beat the inline `padding: 0` that a
|
|
7427
7355
|
// full-bleed section's container sets, so a carousel/media hero that is edge-to-edge on desktop
|
|
7428
|
-
// still got a 20px band of section background down both sides on a phone.
|
|
7429
|
-
|
|
7430
|
-
"[data-ai-section-inner]:not([data-ai-full-bleed]){padding:0 20px !important}",
|
|
7431
|
-
"[data-ai-container]{padding:0 20px !important}",
|
|
7356
|
+
// still got a 20px band of section background down both sides on a phone.
|
|
7357
|
+
"[data-ai-container]:not([data-ai-full-bleed]){padding:0 20px !important}",
|
|
7432
7358
|
"[data-ai-row]{display:flex !important;flex-direction:column !important;align-items:stretch !important}",
|
|
7433
7359
|
"[data-ai-cell]{width:100%;min-width:0}",
|
|
7434
7360
|
// The rule above turns every row into a COLUMN flex container on phones, which silently breaks
|
|
@@ -7633,31 +7559,6 @@ function pricingCardEmphasis(featured, ctx, hasBg) {
|
|
|
7633
7559
|
function textAttrs(ctx, path) {
|
|
7634
7560
|
return ctx.keyFor ? { "data-ohw-key": ctx.keyFor(path), "data-ohw-editable": "text" } : {};
|
|
7635
7561
|
}
|
|
7636
|
-
var AI_RESPONSIVE_CSS = [
|
|
7637
|
-
"@media (max-width: 960px) {",
|
|
7638
|
-
" [data-ai-responsive] [data-ai-grid] { grid-template-columns: repeat(2, 1fr) !important; }",
|
|
7639
|
-
' [data-ai-responsive] [data-ai-grid="1"] { grid-template-columns: 1fr !important; }',
|
|
7640
|
-
"}",
|
|
7641
|
-
"@media (max-width: 640px) {",
|
|
7642
|
-
" [data-ai-responsive] [data-ai-grid] { grid-template-columns: 1fr !important; }",
|
|
7643
|
-
" [data-ai-responsive] [data-ai-columns] > * { grid-column: 1 / -1 !important; }",
|
|
7644
|
-
// Group containers flatten to a column on phones; span placements come along for free.
|
|
7645
|
-
// `:not([data-ai-group="overlap"])` for the same reason as the twin pair in AI_MOBILE_CSS — see
|
|
7646
|
-
// the comment there. This sheet's copy is the narrower selector, so without the exemption it
|
|
7647
|
-
// flattens an `overlap` hero below 640px even though the other rule stands down: measured a 390px
|
|
7648
|
-
// viewport with the heading/CTA in flow *under* the image, 219px of section background where the
|
|
7649
|
-
// layered text used to be.
|
|
7650
|
-
' [data-ai-responsive] [data-ai-group]:not([data-ai-group="overlap"]) { display: flex !important; flex-direction: column !important; }',
|
|
7651
|
-
' [data-ai-responsive] [data-ai-group]:not([data-ai-group="overlap"]) > * { grid-column: auto !important; }',
|
|
7652
|
-
// `:not([data-ai-full-bleed])` for the same reason as the twin rule in AI_MOBILE_CSS: this one
|
|
7653
|
-
// is narrower (0,2,0 vs 0,1,0) and also `!important`, so without the guard it wins outright and
|
|
7654
|
-
// a full-bleed hero gets its 20px side band back below 640px only — the one width where the
|
|
7655
|
-
// other rule had already been taught to stand down.
|
|
7656
|
-
" [data-ai-responsive] [data-ai-section-inner]:not([data-ai-full-bleed]) { padding-left: 20px !important; padding-right: 20px !important; }",
|
|
7657
|
-
" [data-ai-responsive] { overflow-x: hidden; }",
|
|
7658
|
-
" [data-ai-responsive] img { max-width: 100%; }",
|
|
7659
|
-
"}"
|
|
7660
|
-
].join("\n");
|
|
7661
7562
|
var TRANSPARENT_PX = "data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7";
|
|
7662
7563
|
function MediaBox({
|
|
7663
7564
|
refValue,
|
|
@@ -7678,9 +7579,9 @@ function MediaBox({
|
|
|
7678
7579
|
const url = refValue ? ctx.resolveMedia(refValue) : null;
|
|
7679
7580
|
const isIcon = /^(lucide|simple):/.test(refValue);
|
|
7680
7581
|
const aspectRatio = aspect && /^\d+:\d+$/.test(aspect) ? aspect.replace(":", " / ") : void 0;
|
|
7681
|
-
const editAttrs = ctx.keyFor && editPath ? {
|
|
7582
|
+
const editAttrs = ctx.keyFor && editPath && !isIcon ? {
|
|
7682
7583
|
"data-ohw-key": ctx.keyFor(editPath),
|
|
7683
|
-
...
|
|
7584
|
+
...genericImageEdit ? { "data-ohw-editable": "image" } : {}
|
|
7684
7585
|
} : {};
|
|
7685
7586
|
if (isIcon) {
|
|
7686
7587
|
const Icon = refValue.startsWith("lucide:") ? lucideByName(refValue.slice(7)) : null;
|
|
@@ -7688,7 +7589,6 @@ function MediaBox({
|
|
|
7688
7589
|
"span",
|
|
7689
7590
|
{
|
|
7690
7591
|
"data-ai-icon": refValue,
|
|
7691
|
-
...editAttrs,
|
|
7692
7592
|
style: {
|
|
7693
7593
|
display: "inline-flex",
|
|
7694
7594
|
width: 48,
|
|
@@ -9194,7 +9094,7 @@ function CollectionBlock({ node, ctx, path }) {
|
|
|
9194
9094
|
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
9195
9095
|
"div",
|
|
9196
9096
|
{
|
|
9197
|
-
"data-ai-grid":
|
|
9097
|
+
"data-ai-grid": "",
|
|
9198
9098
|
"data-ohw-pricing-collection": isPricing ? "" : void 0,
|
|
9199
9099
|
style: {
|
|
9200
9100
|
display: "grid",
|
|
@@ -9454,12 +9354,12 @@ function renderNode(node, ctx, path, ambientAlign) {
|
|
|
9454
9354
|
},
|
|
9455
9355
|
children: [
|
|
9456
9356
|
i > 0 && ctx.heroOverlapFullBleed ? (
|
|
9457
|
-
// The section's `data-ai-
|
|
9357
|
+
// The section's `data-ai-container` gave up its max-width/gutter so the base
|
|
9458
9358
|
// layer (this group's i===0 sibling) can span edge-to-edge — reintroduced here,
|
|
9459
9359
|
// scoped to just the overlay text, so a heading/copy/CTA stack doesn't stretch
|
|
9460
9360
|
// the full section width instead of reading at the usual content width.
|
|
9461
|
-
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { style: { maxWidth: AI_TREE_TOKENS.sectionMaxWidth, margin: "0 auto", padding: "0 40px", width: "100%", boxSizing: "border-box" }, children: renderNode(child, ctx, `${path}.c${i}`, child.align ??
|
|
9462
|
-
) : renderNode(child, ctx, `${path}.c${i}`, i > 0 ? child.align ??
|
|
9361
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { style: { maxWidth: AI_TREE_TOKENS.sectionMaxWidth, margin: "0 auto", padding: "0 40px", width: "100%", boxSizing: "border-box" }, children: renderNode(child, ctx, `${path}.c${i}`, child.align ?? "center") })
|
|
9362
|
+
) : renderNode(child, ctx, `${path}.c${i}`, i > 0 ? child.align ?? "center" : void 0),
|
|
9463
9363
|
i === 0 && needsBaseScrim && /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
9464
9364
|
"div",
|
|
9465
9365
|
{
|
|
@@ -9492,7 +9392,7 @@ function renderNode(node, ctx, path, ambientAlign) {
|
|
|
9492
9392
|
// child otherwise stretches full-width (unchanged pre-existing behaviour).
|
|
9493
9393
|
...blockAlignStyle(child.align ?? ambientAlign)
|
|
9494
9394
|
},
|
|
9495
|
-
children: renderNode(child, ctx, `${path}.c${i}`,
|
|
9395
|
+
children: renderNode(child, ctx, `${path}.c${i}`, ambientAlign)
|
|
9496
9396
|
},
|
|
9497
9397
|
i
|
|
9498
9398
|
));
|
|
@@ -9522,20 +9422,8 @@ function renderNode(node, ctx, path, ambientAlign) {
|
|
|
9522
9422
|
}
|
|
9523
9423
|
case "button":
|
|
9524
9424
|
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(ButtonEl, { slots, ctx, path });
|
|
9525
|
-
case "button-row":
|
|
9526
|
-
|
|
9527
|
-
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
9528
|
-
"div",
|
|
9529
|
-
{
|
|
9530
|
-
style: {
|
|
9531
|
-
display: "flex",
|
|
9532
|
-
gap: AI_TREE_TOKENS.spacing6,
|
|
9533
|
-
justifyContent: rowAlign === "left" ? "flex-start" : rowAlign === "right" ? "flex-end" : "center"
|
|
9534
|
-
},
|
|
9535
|
-
children: (node.children ?? []).map((child, i) => /* @__PURE__ */ (0, import_jsx_runtime.jsx)(ButtonEl, { slots: child.slots ?? {}, ctx, path: `${path}.c${i}` }, i))
|
|
9536
|
-
}
|
|
9537
|
-
);
|
|
9538
|
-
}
|
|
9425
|
+
case "button-row":
|
|
9426
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { style: { display: "flex", gap: AI_TREE_TOKENS.spacing6, justifyContent: "center" }, children: (node.children ?? []).map((child, i) => /* @__PURE__ */ (0, import_jsx_runtime.jsx)(ButtonEl, { slots: child.slots ?? {}, ctx, path: `${path}.c${i}` }, i)) });
|
|
9539
9427
|
case "media":
|
|
9540
9428
|
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
9541
9429
|
MediaBox,
|
|
@@ -9859,7 +9747,6 @@ function AiTreeRenderer({
|
|
|
9859
9747
|
...fillHeight ? { "data-ai-fill-height": "" } : {},
|
|
9860
9748
|
...needsOverlayClearance ? { "data-ai-overlay-clearance": "" } : {},
|
|
9861
9749
|
...bgAttrs,
|
|
9862
|
-
"data-ai-responsive": "",
|
|
9863
9750
|
style: {
|
|
9864
9751
|
position: "relative",
|
|
9865
9752
|
padding: `${padCss} 0`,
|
|
@@ -9873,13 +9760,12 @@ function AiTreeRenderer({
|
|
|
9873
9760
|
...fillHeight ? { display: "grid" } : {}
|
|
9874
9761
|
},
|
|
9875
9762
|
children: [
|
|
9876
|
-
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("style", { children: AI_RESPONSIVE_CSS }),
|
|
9877
|
-
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("style", { children: AI_MOBILE_CSS }),
|
|
9878
9763
|
isOverlay && backgroundUrl && /* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { style: { position: "absolute", inset: 0, background: `rgba(255,255,255,${overlayAlpha})` } }),
|
|
9764
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("style", { children: AI_MOBILE_CSS }),
|
|
9879
9765
|
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
9880
9766
|
"div",
|
|
9881
9767
|
{
|
|
9882
|
-
"data-ai-
|
|
9768
|
+
"data-ai-container": "",
|
|
9883
9769
|
...fullBleedMedia ? { "data-ai-full-bleed": "" } : {},
|
|
9884
9770
|
style: {
|
|
9885
9771
|
position: "relative",
|
|
@@ -9896,7 +9782,7 @@ function AiTreeRenderer({
|
|
|
9896
9782
|
children: tree.rows.map((row, r2) => /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
9897
9783
|
"div",
|
|
9898
9784
|
{
|
|
9899
|
-
"data-ai-
|
|
9785
|
+
"data-ai-row": "",
|
|
9900
9786
|
style: {
|
|
9901
9787
|
display: "grid",
|
|
9902
9788
|
gridTemplateColumns: "repeat(12, 1fr)",
|
|
@@ -9916,7 +9802,7 @@ function AiTreeRenderer({
|
|
|
9916
9802
|
// its own horizontal `align`, which takes priority for that block.
|
|
9917
9803
|
...fillHeight ? { display: "grid" } : {},
|
|
9918
9804
|
// Horizontal placement of the block's content within its column.
|
|
9919
|
-
...
|
|
9805
|
+
...cellAlignStyle(block.align),
|
|
9920
9806
|
// space-between: each column becomes a flex column whose content spreads over
|
|
9921
9807
|
// the full row height instead of clumping at the top.
|
|
9922
9808
|
...distributed === "space-between" ? { display: "flex", flexDirection: "column", justifyContent: "space-between" } : {}
|
|
@@ -10552,10 +10438,9 @@ function applyAiSectionsToDom(state, options) {
|
|
|
10552
10438
|
if (existing && existing.serialized === serialized && existing.container.isConnected) {
|
|
10553
10439
|
continue;
|
|
10554
10440
|
}
|
|
10441
|
+
const isNewMount = !existing || !existing.container.isConnected;
|
|
10555
10442
|
let container = existing?.container;
|
|
10556
|
-
let isNewMount = false;
|
|
10557
10443
|
if (!container || !container.isConnected) {
|
|
10558
|
-
isNewMount = true;
|
|
10559
10444
|
existing?.root.unmount();
|
|
10560
10445
|
container?.remove();
|
|
10561
10446
|
container = document.createElement("div");
|
|
@@ -16997,7 +16882,6 @@ function MediaOverlay({
|
|
|
16997
16882
|
(prev) => prev && prev.fullWidth === width && prev.height === height ? prev : { fullWidth: width, height }
|
|
16998
16883
|
);
|
|
16999
16884
|
}, [isVideo]);
|
|
17000
|
-
const replaceLabel = isVideo ? "Replace video" : hover.elementType === "bg-image" ? "Replace background" : "Replace image";
|
|
17001
16885
|
const replaceMode = buttonSize ? replaceButtonMode({ width: rect.width, height: rect.height }, buttonSize) : "none";
|
|
17002
16886
|
const box = {
|
|
17003
16887
|
position: "fixed",
|
|
@@ -17096,10 +16980,11 @@ function MediaOverlay({
|
|
|
17096
16980
|
className: "flex items-center justify-center cursor-pointer",
|
|
17097
16981
|
style: {
|
|
17098
16982
|
...box,
|
|
17099
|
-
//
|
|
17100
|
-
//
|
|
17101
|
-
//
|
|
17102
|
-
|
|
16983
|
+
// When text overlays this media, let clicks fall THROUGH to the text underneath. In the
|
|
16984
|
+
// parent this needed a whole `ow:click-at` round-trip to re-hit-test inside the iframe;
|
|
16985
|
+
// in-document, pointer-events does it natively. The button below opts back in, so
|
|
16986
|
+
// Replace still works.
|
|
16987
|
+
pointerEvents: hover.hasTextOverlap || cueOnly ? "none" : "auto",
|
|
17103
16988
|
// Selected: a firm component ring with no wash, so the image reads as chosen rather
|
|
17104
16989
|
// than hovered. Hover keeps the existing tinted preview.
|
|
17105
16990
|
boxShadow: selected ? "inset 0 0 0 2px var(--color-bridge-primary)" : "inset 0 0 0 1.5px var(--color-bridge-primary)",
|
|
@@ -17126,17 +17011,17 @@ function MediaOverlay({
|
|
|
17126
17011
|
},
|
|
17127
17012
|
children: [
|
|
17128
17013
|
isVideo ? /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(import_lucide_react5.Film, { size: 14 }) : /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(import_lucide_react5.ImageIcon, { size: 14 }),
|
|
17129
|
-
|
|
17014
|
+
isVideo ? "Replace video" : "Replace image"
|
|
17130
17015
|
]
|
|
17131
17016
|
}
|
|
17132
17017
|
),
|
|
17133
|
-
|
|
17018
|
+
replaceMode === "none" || cueOnly ? null : /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)(
|
|
17134
17019
|
Button,
|
|
17135
17020
|
{
|
|
17136
17021
|
"data-ohw-media-overlay": "",
|
|
17137
17022
|
variant: "outline",
|
|
17138
17023
|
size: "sm",
|
|
17139
|
-
"aria-label":
|
|
17024
|
+
"aria-label": isVideo ? "Replace video" : "Replace image",
|
|
17140
17025
|
className: "gap-1.5 cursor-pointer hover:bg-background",
|
|
17141
17026
|
style: {
|
|
17142
17027
|
...OVERLAY_BUTTON_STYLE,
|
|
@@ -17159,7 +17044,7 @@ function MediaOverlay({
|
|
|
17159
17044
|
},
|
|
17160
17045
|
children: [
|
|
17161
17046
|
isVideo ? /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(import_lucide_react5.Film, { size: 14 }) : /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(import_lucide_react5.ImageIcon, { size: 14 }),
|
|
17162
|
-
replaceMode === "full" ?
|
|
17047
|
+
replaceMode === "full" ? isVideo ? "Replace video" : hover.elementType === "bg-image" ? "Replace background" : "Replace image" : null
|
|
17163
17048
|
]
|
|
17164
17049
|
}
|
|
17165
17050
|
)
|
|
@@ -18551,23 +18436,10 @@ function setPricingCardStyle(tree, index, style) {
|
|
|
18551
18436
|
});
|
|
18552
18437
|
}
|
|
18553
18438
|
function setPricingCardFeaturedTag(tree, index, on) {
|
|
18554
|
-
return
|
|
18555
|
-
const children = collection.children;
|
|
18556
|
-
if (index < 0 || index >= children.length) return false;
|
|
18557
|
-
if (on) {
|
|
18558
|
-
children.forEach((card, i) => {
|
|
18559
|
-
if (i === index) return;
|
|
18560
|
-
const prev2 = featuredOf(card);
|
|
18561
|
-
if (prev2.enabled !== true || badgeOf(prev2).length === 0) return;
|
|
18562
|
-
card.slots = card.slots ?? {};
|
|
18563
|
-
card.slots.featured = composeFeatured(pricingCardStyleOf(prev2), false, badgeOf(prev2));
|
|
18564
|
-
});
|
|
18565
|
-
}
|
|
18566
|
-
const target = children[index];
|
|
18567
|
-
target.slots = target.slots ?? {};
|
|
18439
|
+
return withPricingCard(tree, index, (target) => {
|
|
18568
18440
|
const prev = featuredOf(target);
|
|
18569
|
-
|
|
18570
|
-
|
|
18441
|
+
const style = pricingCardStyleOf(prev);
|
|
18442
|
+
target.slots.featured = composeFeatured(style, on, badgeOf(prev));
|
|
18571
18443
|
});
|
|
18572
18444
|
}
|
|
18573
18445
|
function pricingCardStyleOf(featured) {
|
|
@@ -18817,40 +18689,25 @@ function ToolbarSeparator() {
|
|
|
18817
18689
|
}
|
|
18818
18690
|
function CardStyleMenu({
|
|
18819
18691
|
value,
|
|
18820
|
-
onChange
|
|
18821
|
-
disabled = false
|
|
18692
|
+
onChange
|
|
18822
18693
|
}) {
|
|
18823
18694
|
const current = PRICING_CARD_STYLES.find((s) => s.value === value) ?? PRICING_CARD_STYLES[0];
|
|
18824
|
-
const trigger = /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
18825
|
-
"button",
|
|
18826
|
-
{
|
|
18827
|
-
type: "button",
|
|
18828
|
-
"aria-label": "Card style",
|
|
18829
|
-
disabled,
|
|
18830
|
-
className: cn(
|
|
18831
|
-
"inline-flex h-8 min-w-[110px] items-center gap-[7px] rounded-[6px] bg-transparent px-2 text-[13px] font-medium text-foreground transition-colors hover:bg-muted data-[state=open]:bg-muted",
|
|
18832
|
-
disabled && "cursor-not-allowed opacity-40 hover:bg-transparent"
|
|
18833
|
-
),
|
|
18834
|
-
children: [
|
|
18835
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(StyleSwatch, { style: current.value }),
|
|
18836
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "flex-1 text-left", children: current.label }),
|
|
18837
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react9.ChevronDown, { size: 16, style: { pointerEvents: "none" } })
|
|
18838
|
-
]
|
|
18839
|
-
}
|
|
18840
|
-
);
|
|
18841
|
-
if (disabled) {
|
|
18842
|
-
return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex items-center gap-1.5 pl-1.5", children: [
|
|
18843
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "text-xs text-muted-foreground opacity-50", children: "Card style" }),
|
|
18844
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(Tooltip, { children: [
|
|
18845
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "inline-flex", children: trigger }) }),
|
|
18846
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TooltipContent, { side: "bottom", sideOffset: 8, children: "Mark as featured to edit card style" })
|
|
18847
|
-
] })
|
|
18848
|
-
] });
|
|
18849
|
-
}
|
|
18850
18695
|
return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex items-center gap-1.5 pl-1.5", children: [
|
|
18851
18696
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "text-xs text-muted-foreground", children: "Card style" }),
|
|
18852
18697
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(DropdownMenu, { modal: false, children: [
|
|
18853
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(DropdownMenuTrigger, { asChild: true, children:
|
|
18698
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
18699
|
+
"button",
|
|
18700
|
+
{
|
|
18701
|
+
type: "button",
|
|
18702
|
+
"aria-label": "Card style",
|
|
18703
|
+
className: "inline-flex h-8 min-w-[110px] items-center gap-[7px] rounded-[6px] bg-transparent px-2 text-[13px] font-medium text-foreground transition-colors hover:bg-muted data-[state=open]:bg-muted",
|
|
18704
|
+
children: [
|
|
18705
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(StyleSwatch, { style: current.value }),
|
|
18706
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "flex-1 text-left", children: current.label }),
|
|
18707
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react9.ChevronDown, { size: 16, style: { pointerEvents: "none" } })
|
|
18708
|
+
]
|
|
18709
|
+
}
|
|
18710
|
+
) }),
|
|
18854
18711
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(DropdownMenuContent, { align: "end", sideOffset: 8, className: "w-[152px] min-w-[152px] p-1", children: PRICING_CARD_STYLES.map((style) => {
|
|
18855
18712
|
const selected = style.value === value;
|
|
18856
18713
|
return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
@@ -18914,35 +18771,23 @@ function PricingCardToolbar({
|
|
|
18914
18771
|
mobile ? "flex-wrap justify-center" : "flex-nowrap"
|
|
18915
18772
|
),
|
|
18916
18773
|
children: [
|
|
18774
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(CardStyleMenu, { value: style, onChange: onSetStyle }),
|
|
18917
18775
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(Tooltip, { children: [
|
|
18918
18776
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
18919
18777
|
CustomToolbarButton,
|
|
18920
18778
|
{
|
|
18921
18779
|
type: "button",
|
|
18922
|
-
"aria-label": featuredTag ? "
|
|
18780
|
+
"aria-label": featuredTag ? "Remove featured tag" : "Add featured tag",
|
|
18923
18781
|
"aria-pressed": featuredTag,
|
|
18782
|
+
active: featuredTag,
|
|
18924
18783
|
onClick: () => onSetFeaturedTag(!featuredTag),
|
|
18925
|
-
className: "
|
|
18926
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
18927
|
-
import_lucide_react9.Star,
|
|
18928
|
-
{
|
|
18929
|
-
size: 16,
|
|
18930
|
-
fill: "currentColor",
|
|
18931
|
-
strokeWidth: 0,
|
|
18932
|
-
className: cn(
|
|
18933
|
-
"transition-colors",
|
|
18934
|
-
featuredTag ? "text-[#f59e0b] group-hover:text-[#d97706]" : "text-[#d6d3d1] group-hover:text-[#fbbf24]"
|
|
18935
|
-
),
|
|
18936
|
-
style: { pointerEvents: "none" }
|
|
18937
|
-
}
|
|
18938
|
-
)
|
|
18784
|
+
className: "size-8",
|
|
18785
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react9.Star, { size: 16, fill: featuredTag ? "currentColor" : "none", style: { pointerEvents: "none" } })
|
|
18939
18786
|
}
|
|
18940
18787
|
) }),
|
|
18941
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TooltipContent, { side: "bottom", sideOffset: 8, children: featuredTag ? "
|
|
18788
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TooltipContent, { side: "bottom", sideOffset: 8, children: featuredTag ? "Remove featured tag" : "Add featured tag" })
|
|
18942
18789
|
] }),
|
|
18943
18790
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(ToolbarSeparator, {}),
|
|
18944
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(CardStyleMenu, { value: style, onChange: onSetStyle, disabled: !featuredTag }),
|
|
18945
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(ToolbarSeparator, {}),
|
|
18946
18791
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(ToolbarAction, { label: "Add button", onClick: onAddButton, disabled: buttonCount >= 2, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(ButtonGlyph, {}) }),
|
|
18947
18792
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(ToolbarAction, { label: "Remove button", onClick: onRemoveButton, disabled: buttonCount === 0, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("span", { className: "relative inline-flex", children: [
|
|
18948
18793
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(ButtonGlyph, {}),
|
|
@@ -19085,12 +18930,7 @@ function AiPricingCardOverlay({
|
|
|
19085
18930
|
index: active.index,
|
|
19086
18931
|
pending,
|
|
19087
18932
|
error,
|
|
19088
|
-
onAddTier: () =>
|
|
19089
|
-
const newIndex = pricingCardCount(activeEntry.tree);
|
|
19090
|
-
void runMutation(active.sectionId, addPricingTier).then((applied) => {
|
|
19091
|
-
if (applied) setActive({ sectionId: active.sectionId, index: newIndex });
|
|
19092
|
-
});
|
|
19093
|
-
},
|
|
18933
|
+
onAddTier: () => runMutation(active.sectionId, addPricingTier),
|
|
19094
18934
|
onRemoveTier: () => {
|
|
19095
18935
|
void runMutation(active.sectionId, (tree) => removePricingTier(tree, active.index)).then(
|
|
19096
18936
|
(applied) => {
|
|
@@ -21639,7 +21479,6 @@ function shouldUseDevFixtures() {
|
|
|
21639
21479
|
function getLogoElement(el) {
|
|
21640
21480
|
const marked = el.closest('[data-ohw-role="logo"], [data-ohw-logo]');
|
|
21641
21481
|
if (marked) return marked;
|
|
21642
|
-
if (el.closest('[data-ohw-editable="icon"]')) return null;
|
|
21643
21482
|
const root = el.closest("nav, [data-ohw-nav-root], footer");
|
|
21644
21483
|
if (!root) return null;
|
|
21645
21484
|
const anchor = el.closest("a");
|
|
@@ -24203,7 +24042,7 @@ function getNavigationSelectionParent(el) {
|
|
|
24203
24042
|
if (!isFooterLinksContainer(el) && (el.hasAttribute("data-ohw-footer-col") || el.hasAttribute("data-ohw-footer-column") || isInferredFooterGroup2(el))) {
|
|
24204
24043
|
return resolveFooterLinksContainerFrom(el);
|
|
24205
24044
|
}
|
|
24206
|
-
if (el.hasAttribute("data-ohw-nav-container") || el.hasAttribute("data-ohw-nav-drawer") ||
|
|
24045
|
+
if (el.hasAttribute("data-ohw-nav-container") || el.hasAttribute("data-ohw-nav-drawer") || isFooterLinksContainer(el)) {
|
|
24207
24046
|
return getNavigationRoot(el);
|
|
24208
24047
|
}
|
|
24209
24048
|
return null;
|
|
@@ -24425,6 +24264,7 @@ var ICONS = {
|
|
|
24425
24264
|
insertUnorderedList: '<line x1="8" y1="6" x2="21" y2="6"/><line x1="8" y1="12" x2="21" y2="12"/><line x1="8" y1="18" x2="21" y2="18"/><line x1="3" y1="6" x2="3.01" y2="6"/><line x1="3" y1="12" x2="3.01" y2="12"/><line x1="3" y1="18" x2="3.01" y2="18"/>',
|
|
24426
24265
|
insertOrderedList: '<line x1="10" y1="6" x2="21" y2="6"/><line x1="10" y1="12" x2="21" y2="12"/><line x1="10" y1="18" x2="21" y2="18"/><path d="M4 6h1v4"/><path d="M4 10h2"/><path d="M6 18H4c0-1 2-2 2-3s-1-1.5-2-1"/>'
|
|
24427
24266
|
};
|
|
24267
|
+
var HEIGHT_SETTLE_DELAYS = [150, 400, 800];
|
|
24428
24268
|
var SELECTION_CHROME_GAP2 = 4;
|
|
24429
24269
|
var TOOLBAR_STROKE_GAP2 = 4;
|
|
24430
24270
|
var TOOLBAR_OFFSET_FROM_ELEMENT = SELECTION_CHROME_GAP2 + TOOLBAR_STROKE_GAP2;
|
|
@@ -25404,6 +25244,21 @@ function OhhwellsBridge() {
|
|
|
25404
25244
|
const [isItemDragging, setIsItemDragging] = (0, import_react21.useState)(false);
|
|
25405
25245
|
const [isFooterFrameSelection, setIsFooterFrameSelection] = (0, import_react21.useState)(false);
|
|
25406
25246
|
isFooterFrameSelectionRef.current = isFooterFrameSelection;
|
|
25247
|
+
const [floatingPanel, setFloatingPanel] = (0, import_react21.useState)(null);
|
|
25248
|
+
const floatingPanelOpenRef = (0, import_react21.useRef)(false);
|
|
25249
|
+
floatingPanelOpenRef.current = floatingPanel !== null;
|
|
25250
|
+
const floatingPanelRef = (0, import_react21.useRef)(null);
|
|
25251
|
+
floatingPanelRef.current = floatingPanel;
|
|
25252
|
+
const [floatingPanelPos, setFloatingPanelPos] = (0, import_react21.useState)(null);
|
|
25253
|
+
const buttonCollectionDragRef = (0, import_react21.useRef)(null);
|
|
25254
|
+
const buttonDropInsertIndexRef = (0, import_react21.useRef)(null);
|
|
25255
|
+
const [buttonDropSlots, setButtonDropSlots] = (0, import_react21.useState)([]);
|
|
25256
|
+
const [activeButtonDropIndex, setActiveButtonDropIndex] = (0, import_react21.useState)(null);
|
|
25257
|
+
const buttonPointerDragRef = (0, import_react21.useRef)(null);
|
|
25258
|
+
const [buttonStyleTick, setButtonStyleTick] = (0, import_react21.useState)(0);
|
|
25259
|
+
const [logoSizeDraft, setLogoSizeDraft] = (0, import_react21.useState)(null);
|
|
25260
|
+
const [editorViewport, setEditorViewport] = (0, import_react21.useState)("desktop");
|
|
25261
|
+
const [parentScrollSnap, setParentScrollSnap] = (0, import_react21.useState)(null);
|
|
25407
25262
|
const [navDropdownPreviewOpen, setNavDropdownPreviewOpen] = (0, import_react21.useState)(null);
|
|
25408
25263
|
const [footerHeadingVisible, setFooterHeadingVisible] = (0, import_react21.useState)(null);
|
|
25409
25264
|
const footerDragRef = (0, import_react21.useRef)(null);
|
|
@@ -25429,21 +25284,6 @@ function OhhwellsBridge() {
|
|
|
25429
25284
|
const stylesRef = (0, import_react21.useRef)("");
|
|
25430
25285
|
const appliedDrawerRef = (0, import_react21.useRef)(null);
|
|
25431
25286
|
const pendingDeleteUndoRef = (0, import_react21.useRef)(null);
|
|
25432
|
-
const [floatingPanel, setFloatingPanel] = (0, import_react21.useState)(null);
|
|
25433
|
-
const floatingPanelOpenRef = (0, import_react21.useRef)(false);
|
|
25434
|
-
const floatingPanelRef = (0, import_react21.useRef)(null);
|
|
25435
|
-
floatingPanelRef.current = floatingPanel;
|
|
25436
|
-
const setFloatingPanelRef = (0, import_react21.useRef)(setFloatingPanel);
|
|
25437
|
-
const [floatingPanelPos, setFloatingPanelPos] = (0, import_react21.useState)(null);
|
|
25438
|
-
const buttonCollectionDragRef = (0, import_react21.useRef)(null);
|
|
25439
|
-
const buttonDropInsertIndexRef = (0, import_react21.useRef)(null);
|
|
25440
|
-
const [buttonDropSlots, setButtonDropSlots] = (0, import_react21.useState)([]);
|
|
25441
|
-
const [activeButtonDropIndex, setActiveButtonDropIndex] = (0, import_react21.useState)(null);
|
|
25442
|
-
const buttonPointerDragRef = (0, import_react21.useRef)(null);
|
|
25443
|
-
const [buttonStyleTick, setButtonStyleTick] = (0, import_react21.useState)(0);
|
|
25444
|
-
const [logoSizeDraft, setLogoSizeDraft] = (0, import_react21.useState)(null);
|
|
25445
|
-
const [editorViewport, setEditorViewport] = (0, import_react21.useState)("desktop");
|
|
25446
|
-
const [parentScrollSnap, setParentScrollSnap] = (0, import_react21.useState)(null);
|
|
25447
25287
|
const [sitePages, setSitePages] = (0, import_react21.useState)([]);
|
|
25448
25288
|
const [sectionsByPath, setSectionsByPath] = (0, import_react21.useState)({});
|
|
25449
25289
|
const sectionsPrefetchGenRef = (0, import_react21.useRef)(0);
|
|
@@ -25452,18 +25292,7 @@ function OhhwellsBridge() {
|
|
|
25452
25292
|
const linkPopoverOpenRef = (0, import_react21.useRef)(false);
|
|
25453
25293
|
const linkPopoverGraceUntilRef = (0, import_react21.useRef)(0);
|
|
25454
25294
|
setLinkPopoverRef.current = setLinkPopover;
|
|
25455
|
-
setFloatingPanelRef.current = setFloatingPanel;
|
|
25456
25295
|
linkPopoverSessionRef.current = linkPopover;
|
|
25457
|
-
floatingPanelOpenRef.current = Boolean(floatingPanel);
|
|
25458
|
-
(0, import_react21.useEffect)(() => {
|
|
25459
|
-
const syncViewport = () => {
|
|
25460
|
-
const next = window.innerWidth <= 480 ? "mobile" : "desktop";
|
|
25461
|
-
setEditorViewport((prev) => prev === next ? prev : next);
|
|
25462
|
-
};
|
|
25463
|
-
syncViewport();
|
|
25464
|
-
window.addEventListener("resize", syncViewport);
|
|
25465
|
-
return () => window.removeEventListener("resize", syncViewport);
|
|
25466
|
-
}, []);
|
|
25467
25296
|
(0, import_react21.useEffect)(() => {
|
|
25468
25297
|
setSectionOrderPersistHandler((entries) => {
|
|
25469
25298
|
const currentPath = window.location.pathname;
|
|
@@ -27142,7 +26971,6 @@ function OhhwellsBridge() {
|
|
|
27142
26971
|
applyAiFooterFromContent(content);
|
|
27143
26972
|
if (typeof content[STYLE_STORE_KEY] === "string") {
|
|
27144
26973
|
stylesRef.current = content[STYLE_STORE_KEY];
|
|
27145
|
-
document.querySelectorAll('[data-ohw-editable="form"]').forEach((f) => markFormFields(f));
|
|
27146
26974
|
applyStylesToDom(parseStyleStore(content[STYLE_STORE_KEY]));
|
|
27147
26975
|
}
|
|
27148
26976
|
applyBrandChrome(content);
|
|
@@ -27153,12 +26981,12 @@ function OhhwellsBridge() {
|
|
|
27153
26981
|
if (key === "__ohw_sections") continue;
|
|
27154
26982
|
if (key === AI_SECTIONS_KEY) continue;
|
|
27155
26983
|
if (key === AI_FOOTER_KEY) continue;
|
|
27156
|
-
if (key === LOGO_PLACEHOLDER_KEY) continue;
|
|
27157
|
-
if (LOGO_IMAGE_KEYS.includes(key)) continue;
|
|
27158
26984
|
if (key === BRAND_KIT_KEY) continue;
|
|
27159
26985
|
if (key === STYLE_STORE_KEY) continue;
|
|
27160
26986
|
if (BRAND_CHROME_KEYS.has(key)) continue;
|
|
26987
|
+
if (key === LOGO_PLACEHOLDER_KEY) continue;
|
|
27161
26988
|
if (key === CUSTOM_CODE_AFTER_HEAD_KEY || key === CUSTOM_CODE_BEFORE_HEAD_KEY) continue;
|
|
26989
|
+
if (LOGO_IMAGE_KEYS.includes(key)) continue;
|
|
27162
26990
|
if (typeof content[AI_FOOTER_KEY] === "string" && content[AI_FOOTER_KEY] && isAiFooterOwnedContentKey(key)) {
|
|
27163
26991
|
continue;
|
|
27164
26992
|
}
|
|
@@ -27373,18 +27201,17 @@ function OhhwellsBridge() {
|
|
|
27373
27201
|
}
|
|
27374
27202
|
applyAiFooterFromContent(content);
|
|
27375
27203
|
if (typeof content[STYLE_STORE_KEY] === "string") {
|
|
27376
|
-
document.querySelectorAll('[data-ohw-editable="form"]').forEach((f) => markFormFields(f));
|
|
27377
27204
|
applyStylesToDom(parseStyleStore(content[STYLE_STORE_KEY]));
|
|
27378
27205
|
}
|
|
27379
27206
|
for (const [key, val] of Object.entries(content)) {
|
|
27380
27207
|
if (key === "__ohw_sections") continue;
|
|
27381
27208
|
if (key === AI_SECTIONS_KEY) continue;
|
|
27382
27209
|
if (key === AI_FOOTER_KEY) continue;
|
|
27383
|
-
if (key === LOGO_PLACEHOLDER_KEY) continue;
|
|
27384
|
-
if (LOGO_IMAGE_KEYS.includes(key)) continue;
|
|
27385
27210
|
if (key === BRAND_KIT_KEY) continue;
|
|
27386
27211
|
if (key === STYLE_STORE_KEY) continue;
|
|
27387
27212
|
if (BRAND_CHROME_KEYS.has(key)) continue;
|
|
27213
|
+
if (key === LOGO_PLACEHOLDER_KEY) continue;
|
|
27214
|
+
if (LOGO_IMAGE_KEYS.includes(key)) continue;
|
|
27388
27215
|
if (typeof content[AI_FOOTER_KEY] === "string" && content[AI_FOOTER_KEY] && isAiFooterOwnedContentKey(key)) {
|
|
27389
27216
|
continue;
|
|
27390
27217
|
}
|
|
@@ -27641,11 +27468,26 @@ function OhhwellsBridge() {
|
|
|
27641
27468
|
const t2 = setTimeout(measure, 500);
|
|
27642
27469
|
const ro = new ResizeObserver(schedule);
|
|
27643
27470
|
ro.observe(document.body);
|
|
27471
|
+
let lastWidth = window.innerWidth;
|
|
27472
|
+
let resizeTimers = [];
|
|
27473
|
+
const clearResizeTimers = () => {
|
|
27474
|
+
resizeTimers.forEach(clearTimeout);
|
|
27475
|
+
resizeTimers = [];
|
|
27476
|
+
};
|
|
27477
|
+
const handleResize = () => {
|
|
27478
|
+
if (window.innerWidth === lastWidth) return;
|
|
27479
|
+
lastWidth = window.innerWidth;
|
|
27480
|
+
clearResizeTimers();
|
|
27481
|
+
resizeTimers = HEIGHT_SETTLE_DELAYS.map((delay) => setTimeout(measure, delay));
|
|
27482
|
+
};
|
|
27483
|
+
window.addEventListener("resize", handleResize);
|
|
27644
27484
|
return () => {
|
|
27645
27485
|
clearTimeout(t1);
|
|
27646
27486
|
clearTimeout(t2);
|
|
27647
27487
|
if (raf != null) cancelAnimationFrame(raf);
|
|
27648
27488
|
ro.disconnect();
|
|
27489
|
+
clearResizeTimers();
|
|
27490
|
+
window.removeEventListener("resize", handleResize);
|
|
27649
27491
|
};
|
|
27650
27492
|
}, [pathname, isEditMode, postToParent2]);
|
|
27651
27493
|
(0, import_react21.useEffect)(() => {
|
|
@@ -27940,13 +27782,6 @@ function OhhwellsBridge() {
|
|
|
27940
27782
|
if (target.closest("[data-ohw-state-toggle]")) return;
|
|
27941
27783
|
if (target.closest("[data-ohw-max-badge]")) return;
|
|
27942
27784
|
if (isInsideLinkEditor(target)) return;
|
|
27943
|
-
if (isInsideFloatingPanel(target)) return;
|
|
27944
|
-
if (target.closest("[data-ohw-form-toolbar]")) return;
|
|
27945
|
-
if (target.closest(
|
|
27946
|
-
'[data-ohw-field-toolbar], [data-ohw-field-type-picker], [data-radix-popper-content-wrapper], [role="menu"], [data-slot="dropdown-menu-content"]'
|
|
27947
|
-
)) {
|
|
27948
|
-
return;
|
|
27949
|
-
}
|
|
27950
27785
|
if (selectedMediaElRef.current && !selectedMediaElRef.current.contains(target) && !target.closest("[data-ohw-media-overlay], [data-ohw-edit-chrome], [data-ohw-item-interaction]")) {
|
|
27951
27786
|
clearMediaSelectionRef.current();
|
|
27952
27787
|
}
|
|
@@ -27967,6 +27802,13 @@ function OhhwellsBridge() {
|
|
|
27967
27802
|
return;
|
|
27968
27803
|
}
|
|
27969
27804
|
}
|
|
27805
|
+
if (isInsideFloatingPanel(target)) return;
|
|
27806
|
+
if (target.closest("[data-ohw-form-toolbar]")) return;
|
|
27807
|
+
if (target.closest(
|
|
27808
|
+
'[data-ohw-field-toolbar], [data-ohw-field-type-picker], [data-radix-popper-content-wrapper], [role="menu"], [data-slot="dropdown-menu-content"]'
|
|
27809
|
+
)) {
|
|
27810
|
+
return;
|
|
27811
|
+
}
|
|
27970
27812
|
{
|
|
27971
27813
|
const formEl = getFormElement(target);
|
|
27972
27814
|
const onSuccessText = target.closest(`[${SUCCESS_TEXT_ATTR}]`);
|
|
@@ -28346,9 +28188,6 @@ function OhhwellsBridge() {
|
|
|
28346
28188
|
setHoveredItemRect(null);
|
|
28347
28189
|
hoveredNavContainerRef.current = null;
|
|
28348
28190
|
setHoveredNavContainerRect(null);
|
|
28349
|
-
siblingHintElRef.current = null;
|
|
28350
|
-
setSiblingHintRect(null);
|
|
28351
|
-
setSiblingHintRects([]);
|
|
28352
28191
|
return;
|
|
28353
28192
|
}
|
|
28354
28193
|
{
|
|
@@ -28469,6 +28308,7 @@ function OhhwellsBridge() {
|
|
|
28469
28308
|
hoveredNavContainerRef.current = null;
|
|
28470
28309
|
setHoveredNavContainerRect(null);
|
|
28471
28310
|
hoveredItemElRef.current = editable;
|
|
28311
|
+
setHoveredItemRect(isSelectedForHoverRef.current(editable) ? null : editable.getBoundingClientRect());
|
|
28472
28312
|
}
|
|
28473
28313
|
}
|
|
28474
28314
|
}
|
|
@@ -29178,11 +29018,7 @@ function OhhwellsBridge() {
|
|
|
29178
29018
|
};
|
|
29179
29019
|
const handleMouseMove = (e) => {
|
|
29180
29020
|
const { clientX, clientY } = e;
|
|
29181
|
-
if (pointOwnedByFloatingPanel(clientX, clientY))
|
|
29182
|
-
dismissImageHover();
|
|
29183
|
-
clearImageHover();
|
|
29184
|
-
return;
|
|
29185
|
-
}
|
|
29021
|
+
if (pointOwnedByFloatingPanel(clientX, clientY)) return;
|
|
29186
29022
|
if (isNavDrawerOpen() && isPointOutsideOpenDrawer(clientX, clientY)) {
|
|
29187
29023
|
document.querySelectorAll("[data-ohw-hovered]").forEach((el) => el.removeAttribute("data-ohw-hovered"));
|
|
29188
29024
|
formHoverElRef.current = null;
|
|
@@ -29211,12 +29047,7 @@ function OhhwellsBridge() {
|
|
|
29211
29047
|
setHoveredItemRect(null);
|
|
29212
29048
|
hoveredNavContainerRef.current = null;
|
|
29213
29049
|
setHoveredNavContainerRect(null);
|
|
29214
|
-
siblingHintElRef.current = null;
|
|
29215
|
-
setSiblingHintRect(null);
|
|
29216
|
-
setSiblingHintRects([]);
|
|
29217
29050
|
dismissImageHover();
|
|
29218
|
-
clearImageHover();
|
|
29219
|
-
setSectionGap(null);
|
|
29220
29051
|
return;
|
|
29221
29052
|
}
|
|
29222
29053
|
if (probeSocialsRowAt(clientX, clientY)) return;
|
|
@@ -29228,11 +29059,7 @@ function OhhwellsBridge() {
|
|
|
29228
29059
|
if (e.data?.type !== "ow:pointer-sync") return;
|
|
29229
29060
|
const { clientX, clientY } = e.data;
|
|
29230
29061
|
if (typeof clientX !== "number" || typeof clientY !== "number") return;
|
|
29231
|
-
if (pointOwnedByFloatingPanel(clientX, clientY))
|
|
29232
|
-
dismissImageHover();
|
|
29233
|
-
clearImageHover();
|
|
29234
|
-
return;
|
|
29235
|
-
}
|
|
29062
|
+
if (pointOwnedByFloatingPanel(clientX, clientY)) return;
|
|
29236
29063
|
if (isNavDrawerOpen() && isPointOutsideOpenDrawer(clientX, clientY)) return;
|
|
29237
29064
|
if (probeSocialsRowAt(clientX, clientY)) return;
|
|
29238
29065
|
probeSectionGapAt(clientX, clientY);
|
|
@@ -29584,7 +29411,6 @@ function OhhwellsBridge() {
|
|
|
29584
29411
|
applyAiFooterFromContent(content);
|
|
29585
29412
|
if (typeof content[STYLE_STORE_KEY] === "string") {
|
|
29586
29413
|
stylesRef.current = content[STYLE_STORE_KEY];
|
|
29587
|
-
document.querySelectorAll('[data-ohw-editable="form"]').forEach((f) => markFormFields(f));
|
|
29588
29414
|
applyStylesToDom(parseStyleStore(content[STYLE_STORE_KEY]));
|
|
29589
29415
|
}
|
|
29590
29416
|
applyBrandChrome(content);
|
|
@@ -29599,12 +29425,12 @@ function OhhwellsBridge() {
|
|
|
29599
29425
|
}
|
|
29600
29426
|
if (key === AI_SECTIONS_KEY) continue;
|
|
29601
29427
|
if (key === AI_FOOTER_KEY) continue;
|
|
29602
|
-
if (key === LOGO_PLACEHOLDER_KEY) continue;
|
|
29603
|
-
if (LOGO_IMAGE_KEYS.includes(key) && !String(val ?? "").trim()) continue;
|
|
29604
29428
|
if (key === BRAND_KIT_KEY) continue;
|
|
29605
29429
|
if (key === STYLE_STORE_KEY) continue;
|
|
29606
29430
|
if (BRAND_CHROME_KEYS.has(key)) continue;
|
|
29431
|
+
if (key === LOGO_PLACEHOLDER_KEY) continue;
|
|
29607
29432
|
if (key === CUSTOM_CODE_AFTER_HEAD_KEY || key === CUSTOM_CODE_BEFORE_HEAD_KEY) continue;
|
|
29433
|
+
if (LOGO_IMAGE_KEYS.includes(key) && !String(val ?? "").trim()) continue;
|
|
29608
29434
|
if (typeof content[AI_FOOTER_KEY] === "string" && content[AI_FOOTER_KEY] && isAiFooterOwnedContentKey(key)) {
|
|
29609
29435
|
continue;
|
|
29610
29436
|
}
|
|
@@ -30142,12 +29968,6 @@ function OhhwellsBridge() {
|
|
|
30142
29968
|
closeLinkPopoverRef.current();
|
|
30143
29969
|
return;
|
|
30144
29970
|
}
|
|
30145
|
-
if (floatingPanelOpenRef.current) {
|
|
30146
|
-
setFloatingPanelRef.current(null);
|
|
30147
|
-
deselectRef.current();
|
|
30148
|
-
deactivateRef.current();
|
|
30149
|
-
return;
|
|
30150
|
-
}
|
|
30151
29971
|
deselectRef.current();
|
|
30152
29972
|
deactivateRef.current();
|
|
30153
29973
|
clearMediaSelectionRef.current();
|
|
@@ -30517,10 +30337,9 @@ function OhhwellsBridge() {
|
|
|
30517
30337
|
if (e.data?.type !== "ow:collect-section") return;
|
|
30518
30338
|
const sectionId = e.data.sectionId;
|
|
30519
30339
|
if (typeof sectionId !== "string" || !sectionId) return;
|
|
30520
|
-
const
|
|
30340
|
+
const sectionEl = document.querySelector(
|
|
30521
30341
|
`[data-ohw-section="${CSS.escape(sectionId)}"]`
|
|
30522
30342
|
);
|
|
30523
|
-
const sectionEl = foundEl && !foundEl.hasAttribute("data-ohw-ai-template-hidden") && !foundEl.hasAttribute("data-ohw-ai-removed") && !foundEl.hasAttribute("data-ohw-ai-replaced-by") ? foundEl : null;
|
|
30524
30343
|
const nodes = sectionEl ? collectEditableNodes(void 0, sectionEl).filter(
|
|
30525
30344
|
(n) => n.key && !n.key.startsWith("__ohw_") && !["meta", "sections", "video-setting"].includes(n.type)
|
|
30526
30345
|
).map((n) => ({ ...n, text: n.text ?? "", type: normalizeAiNodeType(n.type) })) : [];
|
|
@@ -30962,10 +30781,10 @@ function OhhwellsBridge() {
|
|
|
30962
30781
|
window.removeEventListener("message", handleDeleteSection);
|
|
30963
30782
|
window.removeEventListener("message", handleDuplicateSection);
|
|
30964
30783
|
window.removeEventListener("message", handleDeactivate);
|
|
30784
|
+
document.documentElement.removeAttribute("data-ohw-panel-dragging");
|
|
30965
30785
|
window.removeEventListener("message", handleToastAction);
|
|
30966
30786
|
window.removeEventListener("message", handleFormCount);
|
|
30967
30787
|
window.removeEventListener("message", handleUiEscape);
|
|
30968
|
-
document.documentElement.removeAttribute("data-ohw-panel-dragging");
|
|
30969
30788
|
autoSaveTimers.current.forEach(clearTimeout);
|
|
30970
30789
|
autoSaveTimers.current.clear();
|
|
30971
30790
|
if (imageUnhoverTimerRef.current) clearTimeout(imageUnhoverTimerRef.current);
|
|
@@ -32475,7 +32294,6 @@ function EmptySection({ title, homeHref = "/", eyebrowKey, titleKey, subtitleKey
|
|
|
32475
32294
|
dropIndicatorVariants,
|
|
32476
32295
|
ensureFooterTree,
|
|
32477
32296
|
filterAvailablePages,
|
|
32478
|
-
foldAlignIntoTrees,
|
|
32479
32297
|
getEditModeInitialState,
|
|
32480
32298
|
insertFooterHours,
|
|
32481
32299
|
isEditSessionActive,
|
|
@@ -32484,7 +32302,6 @@ function EmptySection({ title, homeHref = "/", eyebrowKey, titleKey, subtitleKey
|
|
|
32484
32302
|
isValidUrl,
|
|
32485
32303
|
nextViableSlide,
|
|
32486
32304
|
parseAiFooterState,
|
|
32487
|
-
parseAiSectionsState,
|
|
32488
32305
|
parseTarget,
|
|
32489
32306
|
removeFooterBlock,
|
|
32490
32307
|
resolveFooterCopyright,
|