@ohhwells/bridge 0.1.136 → 0.1.138

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.js CHANGED
@@ -1,7 +1,7 @@
1
1
  "use client";
2
2
 
3
3
  // src/OhhwellsBridge.tsx
4
- import React12, { useCallback as useCallback12, useEffect as useEffect17, useLayoutEffect as useLayoutEffect5, useRef as useRef14, useState as useState18 } from "react";
4
+ import React12, { useCallback as useCallback12, useEffect as useEffect17, useLayoutEffect as useLayoutEffect6, useRef as useRef14, useState as useState18 } from "react";
5
5
  import { createRoot as createRoot3 } from "react-dom/client";
6
6
  import { flushSync as flushSync3 } from "react-dom";
7
7
 
@@ -5832,6 +5832,7 @@ function applyStylesToDom(store) {
5832
5832
  section.setAttribute("data-ohw-style-bgcolor", "");
5833
5833
  }
5834
5834
  if (override.cardBackgroundColor !== void 0 && !isDrawerMarker) {
5835
+ detectItemGroups(section);
5835
5836
  section.style.setProperty("--ohw-card-bg", override.cardBackgroundColor);
5836
5837
  section.setAttribute("data-ohw-style-cardbg", "");
5837
5838
  }
@@ -7829,6 +7830,21 @@ function PricingCard({ node, ctx, path }) {
7829
7830
  const fg = emphasis.fg;
7830
7831
  const features = pricingFeatureItems(slots.features);
7831
7832
  const buttons = (node.children ?? []).map((child, i) => ({ child, i })).filter((entry) => entry.child.type === "button");
7833
+ const badge = featured.enabled && str(featured.badge) ? /* @__PURE__ */ jsx(
7834
+ "div",
7835
+ {
7836
+ ...ctx.keyFor ? { "data-ohw-key": ctx.keyFor(`${path}.featured.badge`), "data-ohw-editable": "plain" } : {},
7837
+ style: {
7838
+ alignSelf: "flex-start",
7839
+ padding: `${AI_TREE_TOKENS.spacing2 / 2}px ${AI_TREE_TOKENS.spacing3}px`,
7840
+ borderRadius: 999,
7841
+ background: ctx.brand.palette.primary,
7842
+ color: primaryButtonLabel(ctx.brand),
7843
+ ...typeStyle(AI_TREE_TOKENS.type.eyebrow, ctx.brand.fonts.body)
7844
+ },
7845
+ children: str(featured.badge)
7846
+ }
7847
+ ) : null;
7832
7848
  const headingBlock = /* @__PURE__ */ jsxs("div", { style: { display: "flex", flexDirection: "column", gap: AI_TREE_TOKENS.spacing2 }, children: [
7833
7849
  str(slots.heading) && /* @__PURE__ */ jsx(
7834
7850
  "div",
@@ -7878,32 +7894,31 @@ function PricingCard({ node, ctx, path }) {
7878
7894
  position: "relative"
7879
7895
  },
7880
7896
  children: [
7881
- featured.enabled && str(featured.badge) && /* @__PURE__ */ jsx(
7882
- "div",
7883
- {
7884
- style: {
7885
- alignSelf: "flex-start",
7886
- padding: `${AI_TREE_TOKENS.spacing2 / 2}px ${AI_TREE_TOKENS.spacing3}px`,
7887
- borderRadius: 999,
7888
- background: ctx.brand.palette.primary,
7889
- color: primaryButtonLabel(ctx.brand),
7890
- ...typeStyle(AI_TREE_TOKENS.type.eyebrow, ctx.brand.fonts.body)
7891
- },
7892
- children: str(featured.badge)
7893
- }
7894
- ),
7895
- emphasis.headerBg ? /* @__PURE__ */ jsx(
7896
- "div",
7897
- {
7898
- style: {
7899
- background: emphasis.headerBg,
7900
- margin: `-${AI_TREE_TOKENS.paddingBlock}px -${AI_TREE_TOKENS.paddingBlock}px 0`,
7901
- padding: AI_TREE_TOKENS.paddingBlock,
7902
- borderRadius: `${cardRadius(slots)}px ${cardRadius(slots)}px 0 0`
7903
- },
7904
- children: headingBlock
7905
- }
7906
- ) : headingBlock,
7897
+ emphasis.headerBg ? (
7898
+ // The badge rides inside the band so the tint runs from the card's top edge down
7899
+ // through the price block, instead of starting underneath the badge.
7900
+ /* @__PURE__ */ jsxs(
7901
+ "div",
7902
+ {
7903
+ style: {
7904
+ background: emphasis.headerBg,
7905
+ margin: `-${AI_TREE_TOKENS.paddingBlock}px -${AI_TREE_TOKENS.paddingBlock}px 0`,
7906
+ padding: AI_TREE_TOKENS.paddingBlock,
7907
+ borderRadius: `${cardRadius(slots)}px ${cardRadius(slots)}px 0 0`,
7908
+ display: "flex",
7909
+ flexDirection: "column",
7910
+ gap: AI_TREE_TOKENS.spacing8
7911
+ },
7912
+ children: [
7913
+ badge,
7914
+ headingBlock
7915
+ ]
7916
+ }
7917
+ )
7918
+ ) : /* @__PURE__ */ jsxs(Fragment, { children: [
7919
+ badge,
7920
+ headingBlock
7921
+ ] }),
7907
7922
  features.length > 0 && /* @__PURE__ */ jsxs(Fragment, { children: [
7908
7923
  /* @__PURE__ */ jsx("hr", { style: { border: "none", borderTop: `1px solid ${fg}`, opacity: 0.2, margin: 0, width: "100%" } }),
7909
7924
  /* @__PURE__ */ jsxs("div", { style: { display: "flex", flexDirection: "column", gap: AI_TREE_TOKENS.spacing4 }, children: [
@@ -18147,8 +18162,8 @@ function AiMediaStripOverlay({
18147
18162
  }
18148
18163
 
18149
18164
  // src/ui/ai-section/AiPricingCardOverlay.tsx
18150
- import { useCallback as useCallback4, useEffect as useEffect7, useRef as useRef6, useState as useState9 } from "react";
18151
- import { Star as Star2 } from "lucide-react";
18165
+ import { useCallback as useCallback4, useEffect as useEffect7, useLayoutEffect as useLayoutEffect4, useRef as useRef6, useState as useState9 } from "react";
18166
+ import { Check as Check2, ChevronDown as ChevronDown3, Minus, Plus as Plus2, Star as Star2 } from "lucide-react";
18152
18167
 
18153
18168
  // src/lib/ai-pricing-tree.ts
18154
18169
  var PRICING_MIN_CARDS = 1;
@@ -18208,16 +18223,65 @@ function removePricingTier(tree, index) {
18208
18223
  return true;
18209
18224
  });
18210
18225
  }
18211
- function setPricingCardFeatured(tree, index, patch) {
18226
+ var PRICING_CARD_STYLES = [
18227
+ { value: "outline", label: "Outline", treatment: null },
18228
+ { value: "lift", label: "Lift", treatment: "lifted" },
18229
+ { value: "invert", label: "Invert", treatment: "inverted" },
18230
+ { value: "header", label: "Header", treatment: "accent-header" }
18231
+ ];
18232
+ var DEFAULT_FEATURED_BADGE = "Most popular";
18233
+ function featuredOf(target) {
18234
+ const raw = target?.slots?.featured;
18235
+ if (raw === true) return { enabled: true, treatment: "outlined" };
18236
+ return typeof raw === "object" && raw !== null ? raw : {};
18237
+ }
18238
+ function badgeOf(featured) {
18239
+ return typeof featured.badge === "string" ? featured.badge.trim() : "";
18240
+ }
18241
+ function pricingCardStyle(tree, index) {
18242
+ const featured = featuredOf(findPricingCollection(tree)?.children?.[index]);
18243
+ if (featured.enabled !== true) return "outline";
18244
+ return PRICING_CARD_STYLES.find((s) => s.treatment === featured.treatment)?.value ?? "outline";
18245
+ }
18246
+ function pricingCardFeaturedTag(tree, index) {
18247
+ const featured = featuredOf(findPricingCollection(tree)?.children?.[index]);
18248
+ return featured.enabled === true && badgeOf(featured).length > 0;
18249
+ }
18250
+ function composeFeatured(style, tagOn, badgeText) {
18251
+ const treatment = PRICING_CARD_STYLES.find((s) => s.value === style)?.treatment ?? null;
18252
+ if (tagOn) return { enabled: true, badge: badgeText || DEFAULT_FEATURED_BADGE, treatment: treatment ?? "outlined" };
18253
+ if (treatment) return { enabled: true, treatment };
18254
+ return badgeText.length > 0 ? { enabled: false, badge: badgeText } : { enabled: false };
18255
+ }
18256
+ function withPricingCard(tree, index, mutate) {
18212
18257
  return withPricingCollection(tree, (collection) => {
18213
18258
  const children = collection.children;
18214
18259
  if (index < 0 || index >= children.length) return false;
18215
18260
  const target = children[index];
18216
18261
  target.slots = target.slots ?? {};
18217
- target.slots.featured = { ...patch };
18262
+ mutate(target);
18218
18263
  return true;
18219
18264
  });
18220
18265
  }
18266
+ function setPricingCardStyle(tree, index, style) {
18267
+ if (!PRICING_CARD_STYLES.some((s) => s.value === style)) return null;
18268
+ return withPricingCard(tree, index, (target) => {
18269
+ const prev = featuredOf(target);
18270
+ const tagOn = prev.enabled === true && badgeOf(prev).length > 0;
18271
+ target.slots.featured = composeFeatured(style, tagOn, badgeOf(prev));
18272
+ });
18273
+ }
18274
+ function setPricingCardFeaturedTag(tree, index, on) {
18275
+ return withPricingCard(tree, index, (target) => {
18276
+ const prev = featuredOf(target);
18277
+ const style = pricingCardStyleOf(prev);
18278
+ target.slots.featured = composeFeatured(style, on, badgeOf(prev));
18279
+ });
18280
+ }
18281
+ function pricingCardStyleOf(featured) {
18282
+ if (featured.enabled !== true) return "outline";
18283
+ return PRICING_CARD_STYLES.find((s) => s.treatment === featured.treatment)?.value ?? "outline";
18284
+ }
18221
18285
  function addPricingCardButton(tree, index, label) {
18222
18286
  return withPricingCollection(tree, (collection) => {
18223
18287
  const children = collection.children;
@@ -18292,15 +18356,8 @@ function removePricingCardFeature(tree, index) {
18292
18356
 
18293
18357
  // src/ui/ai-section/AiPricingCardOverlay.tsx
18294
18358
  import { Fragment as Fragment7, jsx as jsx20, jsxs as jsxs11 } from "react/jsx-runtime";
18295
- var EMPHASIS_TREATMENTS = [
18296
- { value: "outlined", label: "Outline" },
18297
- { value: "lifted", label: "Lift" },
18298
- { value: "inverted", label: "Invert" },
18299
- { value: "accent-header", label: "Header" }
18300
- ];
18301
- var PRIMARY4 = "#0885FE";
18302
- var OHW_BLUE2 = `var(--ohw-primary, ${PRIMARY4})`;
18303
- var OHW_BLUE_DARK2 = `color-mix(in srgb, var(--ohw-primary, ${PRIMARY4}) 60%, #000000)`;
18359
+ var PRIMARY4 = "var(--ohw-primary, #0885FE)";
18360
+ var CHROME_SELECTOR = "[data-ohw-toolbar], [data-ohw-edit-chrome], [data-ohw-item-interaction], [data-ohw-link-modal-root], [data-ohw-section-picker], [data-ohw-ai-review], [data-ohw-more-menu]";
18304
18361
  function findPricingCardElement(sectionId, index) {
18305
18362
  const sectionEl = findByInstanceId(sectionId);
18306
18363
  if (!sectionEl) return null;
@@ -18310,14 +18367,35 @@ function findPricingCardElement(sectionId, index) {
18310
18367
  }
18311
18368
  return null;
18312
18369
  }
18313
- function readRect3(ref) {
18314
- const el = ref && findPricingCardElement(ref.sectionId, ref.index);
18370
+ function cardRefFromTarget(target) {
18371
+ if (!(target instanceof Element)) return null;
18372
+ if (target.closest(CHROME_SELECTOR)) return null;
18373
+ const cardEl = target.closest("[data-ohw-pricing-card]");
18374
+ if (!cardEl) return null;
18375
+ const sectionEl = cardEl.closest("[data-ohw-section]");
18376
+ const unit = sectionEl ? movableUnit(sectionEl) : null;
18377
+ const sectionId = unit ? instanceIdOf(unit) || null : null;
18378
+ const index = Number(cardEl.dataset.ohwPricingIndex);
18379
+ if (!sectionId || Number.isNaN(index)) return null;
18380
+ return { sectionId, index };
18381
+ }
18382
+ function sameRef(a, b) {
18383
+ return a?.sectionId === b?.sectionId && a?.index === b?.index;
18384
+ }
18385
+ function rectOf(el) {
18315
18386
  if (!el) return null;
18316
18387
  const r2 = el.getBoundingClientRect();
18317
18388
  if (r2.width <= 0 || r2.height <= 0) return null;
18318
18389
  return { top: r2.top, left: r2.left, width: r2.width, height: r2.height };
18319
18390
  }
18320
- function useLiveCardRect(ref) {
18391
+ function readRect3(ref) {
18392
+ return rectOf(ref && findPricingCardElement(ref.sectionId, ref.index));
18393
+ }
18394
+ function readGridRect(ref) {
18395
+ const card = ref && findPricingCardElement(ref.sectionId, ref.index);
18396
+ return rectOf(card?.closest("[data-ohw-pricing-collection]") ?? card);
18397
+ }
18398
+ function useLiveCardRect(ref, grid = false) {
18321
18399
  const [rect, setRect] = useState9(null);
18322
18400
  useEffect7(() => {
18323
18401
  if (!ref) {
@@ -18325,7 +18403,7 @@ function useLiveCardRect(ref) {
18325
18403
  return;
18326
18404
  }
18327
18405
  const update = () => {
18328
- const next = readRect3(ref);
18406
+ const next = grid ? readGridRect(ref) : readRect3(ref);
18329
18407
  setRect(
18330
18408
  (prev) => prev && next && prev.top === next.top && prev.left === next.left && prev.width === next.width && prev.height === next.height ? prev : next
18331
18409
  );
@@ -18340,9 +18418,49 @@ function useLiveCardRect(ref) {
18340
18418
  window.removeEventListener("resize", update);
18341
18419
  clearInterval(interval);
18342
18420
  };
18343
- }, [ref?.sectionId, ref?.index]);
18421
+ }, [ref?.sectionId, ref?.index, grid]);
18344
18422
  return rect;
18345
18423
  }
18424
+ var TOOLBAR_GRID_GAP = 52;
18425
+ var TOOLBAR_GRID_GAP_MOBILE = 42;
18426
+ var TOOLBAR_EDGE_MARGIN2 = 4;
18427
+ function GridToolbarSlot({ gridRect, children }) {
18428
+ const slotRef = useRef6(null);
18429
+ const [shift, setShift] = useState9(0);
18430
+ const centerX = gridRect.left + gridRect.width / 2;
18431
+ useLayoutEffect4(() => {
18432
+ const slot = slotRef.current;
18433
+ if (!slot) return;
18434
+ const clamp = () => {
18435
+ const w = slot.offsetWidth;
18436
+ if (w <= 0) return;
18437
+ const half = w / 2;
18438
+ const clamped = Math.max(TOOLBAR_EDGE_MARGIN2 + half, Math.min(centerX, window.innerWidth - TOOLBAR_EDGE_MARGIN2 - half));
18439
+ setShift((prev) => Math.abs(prev - (clamped - centerX)) < 0.5 ? prev : clamped - centerX);
18440
+ };
18441
+ clamp();
18442
+ const ro = new ResizeObserver(clamp);
18443
+ ro.observe(slot);
18444
+ return () => ro.disconnect();
18445
+ }, [centerX, children]);
18446
+ const mobile = window.innerWidth <= 480;
18447
+ return /* @__PURE__ */ jsx20(
18448
+ "div",
18449
+ {
18450
+ ref: slotRef,
18451
+ "data-ohw-bridge": "",
18452
+ "data-ohw-item-interaction": "",
18453
+ className: "pointer-events-auto fixed",
18454
+ style: {
18455
+ top: gridRect.top - (mobile ? TOOLBAR_GRID_GAP_MOBILE : TOOLBAR_GRID_GAP),
18456
+ left: centerX + shift,
18457
+ transform: "translate(-50%, -100%)",
18458
+ zIndex: 2147483645
18459
+ },
18460
+ children
18461
+ }
18462
+ );
18463
+ }
18346
18464
  function requestValidateTree2(postToParent2, tree) {
18347
18465
  return new Promise((resolve) => {
18348
18466
  const id = `ai-validate-${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
@@ -18360,40 +18478,93 @@ function requestValidateTree2(postToParent2, tree) {
18360
18478
  postToParent2({ type: "ow:ai-validate-tree-request", id, tree });
18361
18479
  });
18362
18480
  }
18363
- function Pill2({
18364
- label,
18365
- onClick,
18366
- disabled,
18367
- active
18368
- }) {
18481
+ function StyleSwatch({ style }) {
18369
18482
  return /* @__PURE__ */ jsx20(
18370
- "button",
18483
+ "span",
18371
18484
  {
18372
- type: "button",
18373
- onClick,
18374
- disabled,
18375
- style: {
18376
- height: 28,
18377
- padding: "0 10px",
18378
- display: "inline-flex",
18379
- alignItems: "center",
18380
- gap: 4,
18381
- borderRadius: 999,
18382
- border: "none",
18383
- cursor: disabled ? "default" : "pointer",
18384
- background: active ? OHW_BLUE_DARK2 : "#ffffff",
18385
- color: active ? "#ffffff" : OHW_BLUE_DARK2,
18386
- opacity: disabled ? 0.4 : 1,
18387
- fontSize: 12,
18388
- lineHeight: "16px",
18389
- fontFamily: "Figtree, ui-sans-serif, system-ui, sans-serif",
18390
- whiteSpace: "nowrap",
18391
- flex: "0 0 auto"
18392
- },
18393
- children: label
18485
+ "aria-hidden": true,
18486
+ className: cn(
18487
+ "inline-block h-4 w-[18px] shrink-0 rounded-[3px] border border-border bg-background",
18488
+ style === "lift" && "border-transparent shadow-[0_3px_5px_rgba(0,0,0,0.22)]",
18489
+ style === "invert" && "border-foreground bg-foreground",
18490
+ style === "header" && "bg-[linear-gradient(var(--ohw-foreground,#0c0a09)_48%,var(--ohw-background,#ffffff)_48%)]"
18491
+ )
18394
18492
  }
18395
18493
  );
18396
18494
  }
18495
+ function ButtonGlyph() {
18496
+ return /* @__PURE__ */ jsxs11("svg", { width: "18", height: "12", viewBox: "0 0 18 12", fill: "none", "aria-hidden": true, style: { pointerEvents: "none" }, children: [
18497
+ /* @__PURE__ */ jsx20("rect", { x: "0.75", y: "0.75", width: "16.5", height: "10.5", rx: "3", stroke: "currentColor", strokeWidth: "1.5" }),
18498
+ /* @__PURE__ */ jsx20("path", { d: "M5.5 6H12.5", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round" })
18499
+ ] });
18500
+ }
18501
+ function FeatureGlyph({ mode }) {
18502
+ return /* @__PURE__ */ jsxs11("svg", { width: "18", height: "18", viewBox: "0 0 18 18", fill: "none", "aria-hidden": true, style: { pointerEvents: "none" }, children: [
18503
+ /* @__PURE__ */ jsx20("circle", { cx: "8", cy: "8", r: "7.25", stroke: "currentColor", strokeWidth: "1.5" }),
18504
+ /* @__PURE__ */ jsx20("path", { d: "M5 8.2L7.2 10.3L11 6", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" }),
18505
+ /* @__PURE__ */ jsx20("circle", { cx: "13.5", cy: "13.5", r: "4.25", fill: "var(--ohw-background, #ffffff)", stroke: "var(--ohw-background, #ffffff)", strokeWidth: "1" }),
18506
+ /* @__PURE__ */ jsx20("circle", { cx: "13.5", cy: "13.5", r: "3.75", fill: "var(--ohw-background, #ffffff)", stroke: PRIMARY4, strokeWidth: "1" }),
18507
+ /* @__PURE__ */ jsx20("path", { d: "M11.5 13.5H15.5", stroke: PRIMARY4, strokeWidth: "1.5", strokeLinecap: "round" }),
18508
+ mode === "add" && /* @__PURE__ */ jsx20("path", { d: "M13.5 11.5V15.5", stroke: PRIMARY4, strokeWidth: "1.5", strokeLinecap: "round" })
18509
+ ] });
18510
+ }
18511
+ function ToolbarAction({
18512
+ label,
18513
+ onClick,
18514
+ disabled = false,
18515
+ children
18516
+ }) {
18517
+ const button = /* @__PURE__ */ jsx20(CustomToolbarButton, { type: "button", "aria-label": label, disabled, onClick, className: "size-8", children });
18518
+ return /* @__PURE__ */ jsxs11(Tooltip, { children: [
18519
+ /* @__PURE__ */ jsx20(TooltipTrigger, { asChild: true, children: disabled ? /* @__PURE__ */ jsx20("span", { className: "inline-flex", children: button }) : button }),
18520
+ /* @__PURE__ */ jsx20(TooltipContent, { side: "bottom", sideOffset: 8, children: label })
18521
+ ] });
18522
+ }
18523
+ function ToolbarSeparator() {
18524
+ return /* @__PURE__ */ jsx20("span", { "aria-hidden": true, className: "mx-0.5 block h-6 w-px shrink-0 bg-border" });
18525
+ }
18526
+ function CardStyleMenu({
18527
+ value,
18528
+ onChange
18529
+ }) {
18530
+ const current = PRICING_CARD_STYLES.find((s) => s.value === value) ?? PRICING_CARD_STYLES[0];
18531
+ return /* @__PURE__ */ jsxs11("div", { className: "flex items-center gap-1.5 pl-1.5", children: [
18532
+ /* @__PURE__ */ jsx20("span", { className: "text-xs text-muted-foreground", children: "Card style" }),
18533
+ /* @__PURE__ */ jsxs11(DropdownMenu, { modal: false, children: [
18534
+ /* @__PURE__ */ jsx20(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs11(
18535
+ "button",
18536
+ {
18537
+ type: "button",
18538
+ "aria-label": "Card style",
18539
+ 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",
18540
+ children: [
18541
+ /* @__PURE__ */ jsx20(StyleSwatch, { style: current.value }),
18542
+ /* @__PURE__ */ jsx20("span", { className: "flex-1 text-left", children: current.label }),
18543
+ /* @__PURE__ */ jsx20(ChevronDown3, { size: 16, style: { pointerEvents: "none" } })
18544
+ ]
18545
+ }
18546
+ ) }),
18547
+ /* @__PURE__ */ jsx20(DropdownMenuContent, { align: "end", sideOffset: 8, className: "w-[152px] min-w-[152px] p-1", children: PRICING_CARD_STYLES.map((style) => {
18548
+ const selected = style.value === value;
18549
+ return /* @__PURE__ */ jsxs11(
18550
+ DropdownMenuItem,
18551
+ {
18552
+ role: "menuitemradio",
18553
+ "aria-checked": selected,
18554
+ onSelect: () => onChange(style.value),
18555
+ className: cn("grid grid-cols-[18px_1fr_16px] gap-2 py-2 pl-2 pr-2 text-[13px]", selected && "bg-muted"),
18556
+ children: [
18557
+ /* @__PURE__ */ jsx20(StyleSwatch, { style: style.value }),
18558
+ /* @__PURE__ */ jsx20("span", { children: style.label }),
18559
+ selected && /* @__PURE__ */ jsx20(Check2, { size: 16, className: "text-bridge-primary" })
18560
+ ]
18561
+ },
18562
+ style.value
18563
+ );
18564
+ }) })
18565
+ ] })
18566
+ ] });
18567
+ }
18397
18568
  function PricingCardToolbar({
18398
18569
  entry,
18399
18570
  index,
@@ -18401,8 +18572,8 @@ function PricingCardToolbar({
18401
18572
  error,
18402
18573
  onAddTier,
18403
18574
  onRemoveTier,
18404
- onToggleFeatured,
18405
- onSetTreatment,
18575
+ onSetStyle,
18576
+ onSetFeaturedTag,
18406
18577
  onAddButton,
18407
18578
  onRemoveButton,
18408
18579
  onAddFeature,
@@ -18410,55 +18581,66 @@ function PricingCardToolbar({
18410
18581
  }) {
18411
18582
  const collectionCount = pricingCardCount(entry.tree);
18412
18583
  const card = findPricingCardNode(entry.tree, index);
18413
- const featured = card?.slots?.featured;
18414
- const isFeatured = featured?.enabled === true;
18415
18584
  const buttonCount = (card?.children ?? []).filter((c) => c.type === "button").length;
18416
18585
  const featureCount = pricingCardFeatureCount(entry.tree, index);
18417
- const pillWrap = window.innerWidth <= 480 ? "wrap" : "nowrap";
18418
- return /* @__PURE__ */ jsxs11(
18586
+ const style = pricingCardStyle(entry.tree, index);
18587
+ const featuredTag = pricingCardFeaturedTag(entry.tree, index);
18588
+ const mobile = window.innerWidth <= 480;
18589
+ return /* @__PURE__ */ jsx20(TooltipProvider, { delayDuration: 0, children: /* @__PURE__ */ jsxs11(
18419
18590
  "div",
18420
18591
  {
18421
18592
  "data-ohw-bridge": "",
18422
18593
  "data-ohw-toolbar": "",
18423
18594
  onMouseDown: (e) => e.stopPropagation(),
18424
- style: {
18425
- display: "flex",
18426
- flexDirection: "column",
18427
- gap: 6,
18428
- alignItems: "center",
18429
- background: OHW_BLUE2,
18430
- padding: 8,
18431
- borderRadius: 12,
18432
- boxShadow: "0 8px 24px rgba(0,0,0,0.25)",
18433
- pointerEvents: pending ? "none" : "auto",
18434
- opacity: pending ? 0.6 : 1,
18435
- // Only cap width on mobile, where the pill rows wrap — on desktop the row stays on one
18436
- // line and should size to fit it, not get clipped/overflow against a fixed cap.
18437
- maxWidth: pillWrap === "wrap" ? "calc(100vw - 24px)" : "none"
18438
- },
18595
+ className: cn(
18596
+ "flex flex-col items-center gap-1.5 font-sans",
18597
+ pending && "pointer-events-none opacity-60"
18598
+ ),
18599
+ style: { maxWidth: mobile ? "calc(100vw - 24px)" : void 0 },
18439
18600
  children: [
18440
- /* @__PURE__ */ jsxs11("div", { style: { display: "flex", gap: 6, flexWrap: pillWrap, justifyContent: "center" }, children: [
18441
- /* @__PURE__ */ jsx20(Pill2, { label: "+ Tier", onClick: onAddTier, disabled: collectionCount >= 4 }),
18442
- /* @__PURE__ */ jsx20(Pill2, { label: "- Tier", onClick: onRemoveTier, disabled: collectionCount <= 1 }),
18443
- /* @__PURE__ */ jsx20(Pill2, { label: "Featured", active: isFeatured, onClick: () => onToggleFeatured(!isFeatured) }),
18444
- /* @__PURE__ */ jsx20(Pill2, { label: "+ Button", onClick: onAddButton, disabled: buttonCount >= 2 }),
18445
- /* @__PURE__ */ jsx20(Pill2, { label: "- Button", onClick: onRemoveButton, disabled: buttonCount === 0 }),
18446
- /* @__PURE__ */ jsx20(Pill2, { label: "+ Feature", onClick: onAddFeature, disabled: featureCount >= 10 }),
18447
- /* @__PURE__ */ jsx20(Pill2, { label: "- Feature", onClick: onRemoveFeature, disabled: featureCount <= 1 })
18448
- ] }),
18449
- isFeatured && /* @__PURE__ */ jsx20("div", { style: { display: "flex", gap: 6, flexWrap: pillWrap, justifyContent: "center" }, children: EMPHASIS_TREATMENTS.map((t) => /* @__PURE__ */ jsx20(
18450
- Pill2,
18601
+ /* @__PURE__ */ jsxs11(
18602
+ "div",
18451
18603
  {
18452
- label: t.label,
18453
- active: (featured?.treatment ?? "outlined") === t.value,
18454
- onClick: () => onSetTreatment(t.value)
18455
- },
18456
- t.value
18457
- )) }),
18458
- error && /* @__PURE__ */ jsx20("div", { style: { color: "#FCA5A5", fontSize: 11, maxWidth: 220, textAlign: "center" }, children: error })
18604
+ className: cn(
18605
+ "flex items-center gap-1 rounded-[10px] border border-border bg-background p-1 whitespace-nowrap",
18606
+ "shadow-[0px_10px_15px_-3px_rgba(0,0,0,0.1),0px_4px_6px_-4px_rgba(0,0,0,0.1)]",
18607
+ mobile ? "flex-wrap justify-center" : "flex-nowrap"
18608
+ ),
18609
+ children: [
18610
+ /* @__PURE__ */ jsx20(CardStyleMenu, { value: style, onChange: onSetStyle }),
18611
+ /* @__PURE__ */ jsxs11(Tooltip, { children: [
18612
+ /* @__PURE__ */ jsx20(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ jsx20(
18613
+ CustomToolbarButton,
18614
+ {
18615
+ type: "button",
18616
+ "aria-label": featuredTag ? "Remove featured tag" : "Add featured tag",
18617
+ "aria-pressed": featuredTag,
18618
+ active: featuredTag,
18619
+ onClick: () => onSetFeaturedTag(!featuredTag),
18620
+ className: "size-8",
18621
+ children: /* @__PURE__ */ jsx20(Star2, { size: 16, fill: featuredTag ? "currentColor" : "none", style: { pointerEvents: "none" } })
18622
+ }
18623
+ ) }),
18624
+ /* @__PURE__ */ jsx20(TooltipContent, { side: "bottom", sideOffset: 8, children: featuredTag ? "Remove featured tag" : "Add featured tag" })
18625
+ ] }),
18626
+ /* @__PURE__ */ jsx20(ToolbarSeparator, {}),
18627
+ /* @__PURE__ */ jsx20(ToolbarAction, { label: "Add button", onClick: onAddButton, disabled: buttonCount >= 2, children: /* @__PURE__ */ jsx20(ButtonGlyph, {}) }),
18628
+ /* @__PURE__ */ jsx20(ToolbarAction, { label: "Remove button", onClick: onRemoveButton, disabled: buttonCount === 0, children: /* @__PURE__ */ jsxs11("span", { className: "relative inline-flex", children: [
18629
+ /* @__PURE__ */ jsx20(ButtonGlyph, {}),
18630
+ /* @__PURE__ */ jsx20(Minus, { size: 10, strokeWidth: 2.5, className: "absolute -right-1.5 -top-1.5 rounded-full bg-background text-bridge-primary" })
18631
+ ] }) }),
18632
+ /* @__PURE__ */ jsx20(ToolbarAction, { label: "Add feature", onClick: onAddFeature, disabled: featureCount >= 10, children: /* @__PURE__ */ jsx20(FeatureGlyph, { mode: "add" }) }),
18633
+ /* @__PURE__ */ jsx20(ToolbarAction, { label: "Remove feature", onClick: onRemoveFeature, disabled: featureCount <= 1, children: /* @__PURE__ */ jsx20(FeatureGlyph, { mode: "remove" }) }),
18634
+ /* @__PURE__ */ jsx20(ToolbarSeparator, {}),
18635
+ /* @__PURE__ */ jsx20(ToolbarAction, { label: "Add tier", onClick: onAddTier, disabled: collectionCount >= 4, children: /* @__PURE__ */ jsx20(Plus2, { size: 16, style: { pointerEvents: "none" } }) }),
18636
+ /* @__PURE__ */ jsx20(ToolbarAction, { label: "Remove tier", onClick: onRemoveTier, disabled: collectionCount <= 1, children: /* @__PURE__ */ jsx20(Minus, { size: 16, style: { pointerEvents: "none" } }) })
18637
+ ]
18638
+ }
18639
+ ),
18640
+ error && /* @__PURE__ */ jsx20("div", { className: "max-w-[260px] rounded-md bg-background px-2 py-1 text-center text-[11px] text-destructive shadow-sm", children: error })
18459
18641
  ]
18460
18642
  }
18461
- );
18643
+ ) });
18462
18644
  }
18463
18645
  function findPricingCardNode(tree, index) {
18464
18646
  const stack = tree.rows.flatMap((row) => row.blocks);
@@ -18484,25 +18666,13 @@ function AiPricingCardOverlay({
18484
18666
  activeRef.current = active;
18485
18667
  useEffect7(() => {
18486
18668
  const onMove = (e) => {
18669
+ const ref = cardRefFromTarget(e.target);
18487
18670
  const t = e.target;
18488
- if (!(t instanceof HTMLElement)) return;
18489
- if (t.closest("[data-ohw-toolbar], [data-ohw-edit-chrome], [data-ohw-item-interaction], [data-ohw-link-modal-root], [data-ohw-section-picker], [data-ohw-ai-review]")) {
18490
- return;
18491
- }
18492
- const cardEl = t.closest("[data-ohw-pricing-card]");
18493
- if (!cardEl) {
18494
- setHover(null);
18495
- return;
18496
- }
18497
- const sectionEl = cardEl.closest("[data-ohw-section]");
18498
- const unit = sectionEl ? movableUnit(sectionEl) : null;
18499
- const sectionId = unit ? instanceIdOf(unit) || null : null;
18500
- const index = Number(cardEl.dataset.ohwPricingIndex);
18501
- if (!sectionId || Number.isNaN(index)) {
18502
- setHover(null);
18503
- return;
18504
- }
18505
- setHover({ sectionId, index });
18671
+ const overEditable = Boolean(t?.closest?.("[data-ohw-editable], [data-ohw-role], a, button"));
18672
+ setHover((prev) => {
18673
+ const next = ref && !overEditable ? ref : null;
18674
+ return sameRef(prev, next) ? prev : next;
18675
+ });
18506
18676
  };
18507
18677
  const onLeave = () => setHover(null);
18508
18678
  document.addEventListener("mousemove", onMove, { passive: true });
@@ -18514,15 +18684,12 @@ function AiPricingCardOverlay({
18514
18684
  }, []);
18515
18685
  useEffect7(() => {
18516
18686
  const onClick = (e) => {
18517
- const current = activeRef.current;
18518
- if (!current) return;
18519
18687
  const t = e.target;
18520
- if (!(t instanceof HTMLElement)) return;
18521
- if (t.closest("[data-ohw-item-interaction]")) return;
18522
- const cardEl = findPricingCardElement(current.sectionId, current.index);
18523
- if (cardEl && cardEl.contains(t)) return;
18524
- setActive(null);
18525
- setError(null);
18688
+ if (!(t instanceof Element)) return;
18689
+ if (t.closest(CHROME_SELECTOR)) return;
18690
+ const ref = cardRefFromTarget(t);
18691
+ setActive((prev) => sameRef(prev, ref) ? prev : ref);
18692
+ if (!ref || !sameRef(activeRef.current, ref)) setError(null);
18526
18693
  };
18527
18694
  document.addEventListener("click", onClick, true);
18528
18695
  return () => document.removeEventListener("click", onClick, true);
@@ -18540,6 +18707,7 @@ function AiPricingCardOverlay({
18540
18707
  const onKeyDown = (e) => {
18541
18708
  if (e.key !== "Escape") return;
18542
18709
  if (!activeRef.current) return;
18710
+ if (document.querySelector('[data-ohw-more-menu][data-state="open"]')) return;
18543
18711
  setActive(null);
18544
18712
  setError(null);
18545
18713
  };
@@ -18585,72 +18753,52 @@ function AiPricingCardOverlay({
18585
18753
  );
18586
18754
  const activeEntry = active ? findEntry(active.sectionId) : null;
18587
18755
  const activeCardRect = useLiveCardRect(active);
18588
- const hoverHandleRect = useLiveCardRect(!active && hover ? hover : null);
18756
+ const activeGridRect = useLiveCardRect(active, true);
18757
+ const hoverRect = useLiveCardRect(hover && !sameRef(hover, active) ? hover : null);
18589
18758
  return /* @__PURE__ */ jsxs11(Fragment7, { children: [
18590
- hoverHandleRect && hover && /* @__PURE__ */ jsx20(
18591
- "button",
18592
- {
18593
- type: "button",
18594
- "data-ohw-toolbar": "",
18595
- onClick: () => setActive(hover),
18596
- "aria-label": "Configure pricing tier",
18597
- style: {
18598
- position: "fixed",
18599
- top: hoverHandleRect.top + 8,
18600
- left: hoverHandleRect.left + hoverHandleRect.width - 36,
18601
- width: 28,
18602
- height: 28,
18603
- borderRadius: 8,
18604
- border: `1.5px dashed ${PRIMARY4}`,
18605
- background: "#ffffff",
18606
- color: PRIMARY4,
18607
- display: "flex",
18608
- alignItems: "center",
18609
- justifyContent: "center",
18610
- cursor: "pointer",
18611
- zIndex: 2147483643,
18612
- fontSize: 14,
18613
- fontWeight: 700
18614
- },
18615
- children: /* @__PURE__ */ jsx20(Star2, { size: 14, style: { pointerEvents: "none" } })
18616
- }
18617
- ),
18618
- activeCardRect && active && activeEntry && /* @__PURE__ */ jsx20(
18619
- ItemInteractionLayer,
18620
- {
18621
- rect: activeCardRect,
18622
- state: "active-top",
18623
- toolbar: /* @__PURE__ */ jsx20(
18624
- PricingCardToolbar,
18625
- {
18626
- entry: activeEntry,
18627
- index: active.index,
18628
- pending,
18629
- error,
18630
- onAddTier: () => runMutation(active.sectionId, addPricingTier),
18631
- onRemoveTier: () => {
18632
- void runMutation(active.sectionId, (tree) => removePricingTier(tree, active.index)).then(
18633
- (applied) => {
18634
- if (applied) setActive(null);
18635
- }
18636
- );
18637
- },
18638
- onToggleFeatured: (enabled) => runMutation(
18639
- active.sectionId,
18640
- (tree) => setPricingCardFeatured(tree, active.index, { enabled })
18641
- ),
18642
- onSetTreatment: (treatment) => runMutation(
18643
- active.sectionId,
18644
- (tree) => setPricingCardFeatured(tree, active.index, { enabled: true, treatment })
18645
- ),
18646
- onAddButton: () => runMutation(active.sectionId, (tree) => addPricingCardButton(tree, active.index, "Learn more")),
18647
- onRemoveButton: () => runMutation(active.sectionId, (tree) => removePricingCardButton(tree, active.index)),
18648
- onAddFeature: () => runMutation(active.sectionId, (tree) => addPricingCardFeature(tree, active.index, "New feature")),
18649
- onRemoveFeature: () => runMutation(active.sectionId, (tree) => removePricingCardFeature(tree, active.index))
18650
- }
18651
- )
18652
- }
18653
- )
18759
+ hoverRect && /* @__PURE__ */ jsx20(ItemInteractionLayer, { rect: hoverRect, state: "hover" }),
18760
+ activeCardRect && activeGridRect && active && activeEntry && /* @__PURE__ */ jsxs11(Fragment7, { children: [
18761
+ /* @__PURE__ */ jsx20(ItemInteractionLayer, { rect: activeCardRect, state: "active-top" }),
18762
+ /* @__PURE__ */ jsx20(GridToolbarSlot, { gridRect: activeGridRect, children: /* @__PURE__ */ jsx20(
18763
+ PricingCardToolbar,
18764
+ {
18765
+ entry: activeEntry,
18766
+ index: active.index,
18767
+ pending,
18768
+ error,
18769
+ onAddTier: () => runMutation(active.sectionId, addPricingTier),
18770
+ onRemoveTier: () => {
18771
+ void runMutation(active.sectionId, (tree) => removePricingTier(tree, active.index)).then(
18772
+ (applied) => {
18773
+ if (applied) setActive(null);
18774
+ }
18775
+ );
18776
+ },
18777
+ onSetFeaturedTag: (on) => runMutation(active.sectionId, (tree) => setPricingCardFeaturedTag(tree, active.index, on)),
18778
+ onSetStyle: (style) => runMutation(active.sectionId, (tree) => setPricingCardStyle(tree, active.index, style)),
18779
+ onAddButton: () => runMutation(active.sectionId, (tree) => addPricingCardButton(tree, active.index, "Learn more")),
18780
+ onRemoveButton: () => runMutation(active.sectionId, (tree) => removePricingCardButton(tree, active.index)),
18781
+ onAddFeature: () => runMutation(active.sectionId, (tree) => addPricingCardFeature(tree, active.index, "New feature")),
18782
+ onRemoveFeature: () => runMutation(active.sectionId, (tree) => removePricingCardFeature(tree, active.index))
18783
+ }
18784
+ ) }),
18785
+ /* @__PURE__ */ jsx20(
18786
+ "div",
18787
+ {
18788
+ "data-ohw-bridge": "",
18789
+ "data-ohw-item-interaction": "",
18790
+ "aria-hidden": true,
18791
+ className: "pointer-events-none fixed rounded-[4px] px-[7px] py-[3px] font-sans text-[11px] font-medium leading-none text-primary-foreground whitespace-nowrap",
18792
+ style: {
18793
+ top: activeCardRect.top + activeCardRect.height + 10,
18794
+ left: activeCardRect.left - 5,
18795
+ background: PRIMARY4,
18796
+ zIndex: 2147483644
18797
+ },
18798
+ children: "Pricing card"
18799
+ }
18800
+ )
18801
+ ] })
18654
18802
  ] });
18655
18803
  }
18656
18804
 
@@ -18729,8 +18877,8 @@ function extractYouTubeId(input) {
18729
18877
  // src/ui/ai-section/AiVideoOverlay.tsx
18730
18878
  import { Fragment as Fragment8, jsx as jsx21, jsxs as jsxs12 } from "react/jsx-runtime";
18731
18879
  var PRIMARY5 = "#0885FE";
18732
- var OHW_BLUE3 = `var(--ohw-primary, ${PRIMARY5})`;
18733
- var OHW_BLUE_DARK3 = `color-mix(in srgb, var(--ohw-primary, ${PRIMARY5}) 60%, #000000)`;
18880
+ var OHW_BLUE2 = `var(--ohw-primary, ${PRIMARY5})`;
18881
+ var OHW_BLUE_DARK2 = `color-mix(in srgb, var(--ohw-primary, ${PRIMARY5}) 60%, #000000)`;
18734
18882
  function findVideoBlockElement(sectionId, path) {
18735
18883
  const sectionEl = findByInstanceId(sectionId);
18736
18884
  if (!sectionEl) return null;
@@ -18790,7 +18938,7 @@ function requestValidateTree3(postToParent2, tree) {
18790
18938
  postToParent2({ type: "ow:ai-validate-tree-request", id, tree });
18791
18939
  });
18792
18940
  }
18793
- function Pill3({
18941
+ function Pill2({
18794
18942
  label,
18795
18943
  onClick,
18796
18944
  disabled
@@ -18811,7 +18959,7 @@ function Pill3({
18811
18959
  border: "none",
18812
18960
  cursor: disabled ? "default" : "pointer",
18813
18961
  background: "#ffffff",
18814
- color: OHW_BLUE_DARK3,
18962
+ color: OHW_BLUE_DARK2,
18815
18963
  opacity: disabled ? 0.4 : 1,
18816
18964
  fontSize: 12,
18817
18965
  lineHeight: "16px",
@@ -18876,7 +19024,7 @@ function VideoUrlInput({ value, onCommit }) {
18876
19024
  {
18877
19025
  style: {
18878
19026
  flex: "0 0 auto",
18879
- color: OHW_BLUE_DARK3,
19027
+ color: OHW_BLUE_DARK2,
18880
19028
  fontSize: 10,
18881
19029
  lineHeight: "16px",
18882
19030
  fontWeight: 700,
@@ -18945,7 +19093,7 @@ function VideoToolbar({
18945
19093
  gap: 6,
18946
19094
  alignItems: "center",
18947
19095
  width: 280,
18948
- background: OHW_BLUE3,
19096
+ background: OHW_BLUE2,
18949
19097
  padding: 8,
18950
19098
  borderRadius: 12,
18951
19099
  boxShadow: "0 8px 24px rgba(0,0,0,0.25)",
@@ -18954,7 +19102,7 @@ function VideoToolbar({
18954
19102
  },
18955
19103
  children: [
18956
19104
  /* @__PURE__ */ jsx21(VideoUrlInput, { value: videoId, onCommit: onSetVideoId }),
18957
- /* @__PURE__ */ jsx21(Pill3, { label: "Remove video", onClick: onRemove, disabled: !videoId }),
19105
+ /* @__PURE__ */ jsx21(Pill2, { label: "Remove video", onClick: onRemove, disabled: !videoId }),
18958
19106
  error && /* @__PURE__ */ jsx21("div", { style: { color: "#FCA5A5", fontSize: 11, maxWidth: 220, textAlign: "center" }, children: error })
18959
19107
  ]
18960
19108
  }
@@ -19189,8 +19337,8 @@ function setCarouselAutoplay(tree, on) {
19189
19337
  // src/ui/ai-section/AiFadeCarouselOverlay.tsx
19190
19338
  import { Fragment as Fragment9, jsx as jsx22, jsxs as jsxs13 } from "react/jsx-runtime";
19191
19339
  var PRIMARY6 = "#0885FE";
19192
- var OHW_BLUE4 = `var(--ohw-primary, ${PRIMARY6})`;
19193
- var OHW_BLUE_DARK4 = `color-mix(in srgb, var(--ohw-primary, ${PRIMARY6}) 60%, #000000)`;
19340
+ var OHW_BLUE3 = `var(--ohw-primary, ${PRIMARY6})`;
19341
+ var OHW_BLUE_DARK3 = `color-mix(in srgb, var(--ohw-primary, ${PRIMARY6}) 60%, #000000)`;
19194
19342
  function findCarouselItemElement(sectionId, index) {
19195
19343
  const sectionEl = findByInstanceId(sectionId);
19196
19344
  if (!sectionEl) return null;
@@ -19269,7 +19417,7 @@ function requestAssetPick2(postToParent2) {
19269
19417
  postToParent2({ type: "ow:asset-pick", id });
19270
19418
  });
19271
19419
  }
19272
- function Pill4({ label, onClick, disabled }) {
19420
+ function Pill3({ label, onClick, disabled }) {
19273
19421
  return /* @__PURE__ */ jsx22(
19274
19422
  "button",
19275
19423
  {
@@ -19286,7 +19434,7 @@ function Pill4({ label, onClick, disabled }) {
19286
19434
  border: "none",
19287
19435
  cursor: disabled ? "default" : "pointer",
19288
19436
  background: "#ffffff",
19289
- color: OHW_BLUE_DARK4,
19437
+ color: OHW_BLUE_DARK3,
19290
19438
  opacity: disabled ? 0.4 : 1,
19291
19439
  fontSize: 12,
19292
19440
  lineHeight: "16px",
@@ -19323,7 +19471,7 @@ function TogglePill({
19323
19471
  border: "none",
19324
19472
  cursor: disabled ? "default" : "pointer",
19325
19473
  background: "#ffffff",
19326
- color: OHW_BLUE_DARK4,
19474
+ color: OHW_BLUE_DARK3,
19327
19475
  opacity: disabled ? 0.4 : 1,
19328
19476
  fontSize: 12,
19329
19477
  lineHeight: "16px",
@@ -19346,7 +19494,7 @@ function TogglePill({
19346
19494
  // Off is a grey track, not a washed-out blue: the pill's own white background already
19347
19495
  // carries the brand colour in the text, and a pale blue track next to it read as
19348
19496
  // "disabled control" rather than "switch that is off".
19349
- background: on ? OHW_BLUE_DARK4 : "#CBD5E1",
19497
+ background: on ? OHW_BLUE_DARK3 : "#CBD5E1",
19350
19498
  transition: "background 120ms ease"
19351
19499
  },
19352
19500
  children: /* @__PURE__ */ jsx22(
@@ -19389,7 +19537,7 @@ function CarouselSlideToolbar({
19389
19537
  flexDirection: "column",
19390
19538
  gap: 6,
19391
19539
  alignItems: "center",
19392
- background: OHW_BLUE4,
19540
+ background: OHW_BLUE3,
19393
19541
  padding: 8,
19394
19542
  borderRadius: 12,
19395
19543
  boxShadow: "0 8px 24px rgba(0,0,0,0.25)",
@@ -19402,7 +19550,7 @@ function CarouselSlideToolbar({
19402
19550
  },
19403
19551
  children: [
19404
19552
  /* @__PURE__ */ jsxs13("div", { style: { display: "flex", gap: 6, alignItems: "center" }, children: [
19405
- /* @__PURE__ */ jsx22(Pill4, { label: "Change Image", onClick: onChangeImage }),
19553
+ /* @__PURE__ */ jsx22(Pill3, { label: "Change Image", onClick: onChangeImage }),
19406
19554
  /* @__PURE__ */ jsx22(TogglePill, { label: "Autoplay", on: autoplay, onToggle: onToggleAutoplay })
19407
19555
  ] }),
19408
19556
  error && /* @__PURE__ */ jsx22("div", { style: { color: "#FCA5A5", fontSize: 11, maxWidth: 220, textAlign: "center" }, children: error })
@@ -20194,7 +20342,7 @@ function Label({ className, ...props }) {
20194
20342
  }
20195
20343
 
20196
20344
  // src/ui/link-modal/UrlOrPageInput.tsx
20197
- import { ChevronDown as ChevronDown3, File as File2, X as X3 } from "lucide-react";
20345
+ import { ChevronDown as ChevronDown4, File as File2, X as X3 } from "lucide-react";
20198
20346
  import { jsx as jsx28, jsxs as jsxs17 } from "react/jsx-runtime";
20199
20347
  function FieldChevron({
20200
20348
  onClick
@@ -20207,7 +20355,7 @@ function FieldChevron({
20207
20355
  onClick,
20208
20356
  "aria-label": "Open page list",
20209
20357
  tabIndex: -1,
20210
- children: /* @__PURE__ */ jsx28(ChevronDown3, { size: 16 })
20358
+ children: /* @__PURE__ */ jsx28(ChevronDown4, { size: 16 })
20211
20359
  }
20212
20360
  );
20213
20361
  }
@@ -20437,7 +20585,7 @@ function LinkEditorPanel({ state, onClose }) {
20437
20585
  // src/ui/link-modal/SectionPickerOverlay.tsx
20438
20586
  import { useCallback as useCallback7, useEffect as useEffect11, useMemo as useMemo2, useRef as useRef10, useState as useState13 } from "react";
20439
20587
  import { createPortal as createPortal2 } from "react-dom";
20440
- import { ArrowLeft as ArrowLeft2, Check as Check2 } from "lucide-react";
20588
+ import { ArrowLeft as ArrowLeft2, Check as Check3 } from "lucide-react";
20441
20589
  import { usePathname, useRouter as useRouter2 } from "next/navigation";
20442
20590
 
20443
20591
  // src/lib/parent-scroll.ts
@@ -20783,7 +20931,7 @@ function SectionPickerOverlay({
20783
20931
  className: "absolute right-3 top-3 flex size-8 items-center justify-center rounded-full text-white",
20784
20932
  style: { backgroundColor: "var(--ohw-primary, #0885fe)" },
20785
20933
  "aria-hidden": true,
20786
- children: /* @__PURE__ */ jsx30(Check2, { className: "size-5" })
20934
+ children: /* @__PURE__ */ jsx30(Check3, { className: "size-5" })
20787
20935
  }
20788
20936
  ) : null
20789
20937
  ]
@@ -21236,7 +21384,7 @@ function addFooterColumnWithPersist({
21236
21384
  import {
21237
21385
  useCallback as useCallback9,
21238
21386
  useEffect as useEffect14,
21239
- useLayoutEffect as useLayoutEffect4,
21387
+ useLayoutEffect as useLayoutEffect5,
21240
21388
  useRef as useRef11,
21241
21389
  useState as useState15
21242
21390
  } from "react";
@@ -21333,7 +21481,7 @@ function FloatingPanel({
21333
21481
  return () => window.removeEventListener("message", onParentScroll);
21334
21482
  }, [open]);
21335
21483
  const positionRef = useRef11(position);
21336
- useLayoutEffect4(() => {
21484
+ useLayoutEffect5(() => {
21337
21485
  if (!open) {
21338
21486
  positionRef.current = position;
21339
21487
  return;
@@ -21343,7 +21491,7 @@ function FloatingPanel({
21343
21491
  }
21344
21492
  positionRef.current = position;
21345
21493
  }, [open, position, liveScroll, parentScroll]);
21346
- useLayoutEffect4(() => {
21494
+ useLayoutEffect5(() => {
21347
21495
  if (!open || !panelRef.current) return;
21348
21496
  const el = panelRef.current;
21349
21497
  const header = el.querySelector("[data-ohw-floating-panel-header]");
@@ -21552,7 +21700,7 @@ function SocialsDisplayPanel({ display, onChange, className }) {
21552
21700
  }
21553
21701
 
21554
21702
  // src/ui/button-style-panel.tsx
21555
- import { Check as Check3 } from "lucide-react";
21703
+ import { Check as Check4 } from "lucide-react";
21556
21704
  import { jsx as jsx34, jsxs as jsxs23 } from "react/jsx-runtime";
21557
21705
  var SIZE_LABEL = { s: "S", m: "M", l: "L" };
21558
21706
  function ButtonStylePanel({
@@ -21623,7 +21771,7 @@ function ButtonStylePanel({
21623
21771
  {
21624
21772
  className: "absolute right-0.5 top-0.5 flex size-5 items-center justify-center rounded-full bg-primary text-primary-foreground",
21625
21773
  "aria-hidden": true,
21626
- children: /* @__PURE__ */ jsx34(Check3, { className: "size-3", strokeWidth: 3 })
21774
+ children: /* @__PURE__ */ jsx34(Check4, { className: "size-3", strokeWidth: 3 })
21627
21775
  }
21628
21776
  ) : null
21629
21777
  ]
@@ -22648,7 +22796,7 @@ function useSectionDrag({
22648
22796
  }
22649
22797
 
22650
22798
  // src/ui/footer-container-chrome.tsx
22651
- import { Plus as Plus2 } from "lucide-react";
22799
+ import { Plus as Plus3 } from "lucide-react";
22652
22800
  import { jsx as jsx35, jsxs as jsxs24 } from "react/jsx-runtime";
22653
22801
  function FooterContainerChrome({
22654
22802
  rect,
@@ -22689,7 +22837,7 @@ function FooterContainerChrome({
22689
22837
  if (addDisabled) return;
22690
22838
  onAdd();
22691
22839
  },
22692
- children: /* @__PURE__ */ jsx35(Plus2, { className: "size-4 shrink-0 text-foreground", "aria-hidden": true })
22840
+ children: /* @__PURE__ */ jsx35(Plus3, { className: "size-4 shrink-0 text-foreground", "aria-hidden": true })
22693
22841
  }
22694
22842
  ) }),
22695
22843
  /* @__PURE__ */ jsx35(TooltipContent, { side: "bottom", sideOffset: 9, children: addDisabled ? "Maximum columns reached" : "Add item" })
@@ -22868,7 +23016,7 @@ function deleteSelectedNavFooterItem(deps) {
22868
23016
  }
22869
23017
 
22870
23018
  // src/ui/navbar-container-chrome.tsx
22871
- import { Plus as Plus3 } from "lucide-react";
23019
+ import { Plus as Plus4 } from "lucide-react";
22872
23020
  import { jsx as jsx36 } from "react/jsx-runtime";
22873
23021
  function NavbarContainerChrome({
22874
23022
  rect,
@@ -22904,7 +23052,7 @@ function NavbarContainerChrome({
22904
23052
  e.stopPropagation();
22905
23053
  onAdd();
22906
23054
  },
22907
- children: /* @__PURE__ */ jsx36(Plus3, { className: "size-4 shrink-0 text-foreground", "aria-hidden": true })
23055
+ children: /* @__PURE__ */ jsx36(Plus4, { className: "size-4 shrink-0 text-foreground", "aria-hidden": true })
22908
23056
  }
22909
23057
  )
22910
23058
  }
@@ -22976,7 +23124,7 @@ function Badge({ className, variant, ...props }) {
22976
23124
  }
22977
23125
 
22978
23126
  // src/OhhwellsBridge.tsx
22979
- import { Brush as Brush2, Link as Link2, Plus as Plus4, Settings } from "lucide-react";
23127
+ import { Brush as Brush2, Link as Link2, Plus as Plus5, Settings } from "lucide-react";
22980
23128
  import { Fragment as Fragment12, jsx as jsx39, jsxs as jsxs25 } from "react/jsx-runtime";
22981
23129
  var PRIMARY7 = "#0885FE";
22982
23130
  var IMAGE_FADE_MS = 300;
@@ -24056,7 +24204,7 @@ function applyVisibleViewport(el, parentScroll) {
24056
24204
  el.style.top = `${top}px`;
24057
24205
  el.style.height = `${height}px`;
24058
24206
  }
24059
- var TOOLBAR_EDGE_MARGIN2 = 4;
24207
+ var TOOLBAR_EDGE_MARGIN3 = 4;
24060
24208
  function clampToolbarToClip(top, transform, rect, clip, approxH, gap) {
24061
24209
  const isAbove = transform.includes("translateY(-100%)");
24062
24210
  let visualTop = isAbove ? top - approxH : top;
@@ -24083,8 +24231,8 @@ function clampToolbarToClip(top, transform, rect, clip, approxH, gap) {
24083
24231
  function clampToolbarLeft(centerX, toolbarWidth) {
24084
24232
  const half = toolbarWidth / 2;
24085
24233
  return Math.max(
24086
- TOOLBAR_EDGE_MARGIN2 + half,
24087
- Math.min(centerX, window.innerWidth - TOOLBAR_EDGE_MARGIN2 - half)
24234
+ TOOLBAR_EDGE_MARGIN3 + half,
24235
+ Math.min(centerX, window.innerWidth - TOOLBAR_EDGE_MARGIN3 - half)
24088
24236
  );
24089
24237
  }
24090
24238
  function calcToolbarPos(rect, parentScroll, toolbarW = 306) {
@@ -24523,7 +24671,7 @@ function OhhwellsBridge() {
24523
24671
  }, []);
24524
24672
  const subdomainFromQuery = searchParams.get("subdomain");
24525
24673
  const [subdomain, setSubdomain] = useState18(() => resolveSubdomain(subdomainFromQuery));
24526
- useLayoutEffect5(() => {
24674
+ useLayoutEffect6(() => {
24527
24675
  const next = resolveSubdomain(subdomainFromQuery);
24528
24676
  if (next !== subdomain) setSubdomain(next);
24529
24677
  if (next) return;
@@ -26638,7 +26786,7 @@ function OhhwellsBridge() {
26638
26786
  isFooterFrameSelection,
26639
26787
  postToParent2
26640
26788
  ]);
26641
- useLayoutEffect5(() => {
26789
+ useLayoutEffect6(() => {
26642
26790
  if (!subdomain || isEditMode) {
26643
26791
  setFetchState("done");
26644
26792
  return;
@@ -26978,7 +27126,7 @@ function OhhwellsBridge() {
26978
27126
  if (debounceTimer) clearTimeout(debounceTimer);
26979
27127
  };
26980
27128
  }, [subdomain, isEditMode, pathname]);
26981
- useLayoutEffect5(() => {
27129
+ useLayoutEffect6(() => {
26982
27130
  const el = document.getElementById("ohw-loader");
26983
27131
  if (!el) return;
26984
27132
  const visible = Boolean(subdomain) && fetchState !== "done";
@@ -30771,7 +30919,7 @@ function OhhwellsBridge() {
30771
30919
  postToParent2({
30772
30920
  type: "ow:ready",
30773
30921
  version: "1",
30774
- bridgeVersion: "0.1.135",
30922
+ bridgeVersion: "0.1.137",
30775
30923
  path: pathname,
30776
30924
  nodes: collectEditableNodes(editContentRef.current),
30777
30925
  sections
@@ -31507,7 +31655,7 @@ function OhhwellsBridge() {
31507
31655
  className: "flex h-7 w-7 items-center justify-center rounded-md text-foreground transition-colors hover:bg-muted/80",
31508
31656
  onClick: () => setFieldTypePickerOpen((open) => !open),
31509
31657
  "data-ohw-add-field": "",
31510
- children: /* @__PURE__ */ jsx39(Plus4, { size: 15, "aria-hidden": true })
31658
+ children: /* @__PURE__ */ jsx39(Plus5, { size: 15, "aria-hidden": true })
31511
31659
  }
31512
31660
  ),
31513
31661
  /* @__PURE__ */ jsx39("div", { className: "mx-0.5 h-5 w-px bg-border" }),