@ohhwells/bridge 0.1.52-next.133 → 0.1.52-next.137

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 CHANGED
@@ -69,7 +69,7 @@ __export(index_exports, {
69
69
  module.exports = __toCommonJS(index_exports);
70
70
 
71
71
  // src/OhhwellsBridge.tsx
72
- var import_react13 = __toESM(require("react"), 1);
72
+ var import_react14 = __toESM(require("react"), 1);
73
73
  var import_client = require("react-dom/client");
74
74
  var import_react_dom2 = require("react-dom");
75
75
 
@@ -121,11 +121,43 @@ function useLinkHrefGuardian(...deps) {
121
121
  }, deps);
122
122
  }
123
123
 
124
+ // src/useSavedLinkNavigation.ts
125
+ var import_react2 = require("react");
126
+ var import_navigation = require("next/navigation");
127
+ function isRouterHref(href) {
128
+ return href.startsWith("/") || href.startsWith("#");
129
+ }
130
+ function shouldLetBrowserHandle(e, anchor) {
131
+ return e.defaultPrevented || e.button !== 0 || e.metaKey || e.ctrlKey || e.shiftKey || e.altKey || anchor.hasAttribute("download") || anchor.target !== "" && anchor.target !== "_self";
132
+ }
133
+ function useSavedLinkNavigation(isEditMode) {
134
+ const router = (0, import_navigation.useRouter)();
135
+ (0, import_react2.useEffect)(() => {
136
+ if (isEditMode) return;
137
+ const onClick = (e) => {
138
+ const anchor = e.target?.closest(
139
+ "a[data-ohw-href-key]"
140
+ );
141
+ if (!anchor || shouldLetBrowserHandle(e, anchor)) return;
142
+ const key = anchor.getAttribute("data-ohw-href-key");
143
+ if (!key || getStoredLinkHref(key) === void 0) return;
144
+ const href = anchor.getAttribute("href");
145
+ if (!href) return;
146
+ e.preventDefault();
147
+ e.stopPropagation();
148
+ if (isRouterHref(href)) router.push(href);
149
+ else window.location.assign(href);
150
+ };
151
+ document.addEventListener("click", onClick, true);
152
+ return () => document.removeEventListener("click", onClick, true);
153
+ }, [isEditMode, router]);
154
+ }
155
+
124
156
  // src/ui/SchedulingWidget.tsx
125
- var import_react3 = require("react");
157
+ var import_react4 = require("react");
126
158
 
127
159
  // src/ui/EmailCaptureModal.tsx
128
- var import_react2 = require("react");
160
+ var import_react3 = require("react");
129
161
  var import_radix_ui = require("radix-ui");
130
162
  var import_jsx_runtime = require("react/jsx-runtime");
131
163
  var isValidEmail = (value) => /^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(value);
@@ -155,11 +187,11 @@ function Spinner() {
155
187
  );
156
188
  }
157
189
  function EmailCaptureModal({ title, subtitle, onSubmit, onClose }) {
158
- const [email, setEmail] = (0, import_react2.useState)("");
159
- const [submittedEmail, setSubmittedEmail] = (0, import_react2.useState)("");
160
- const [loading, setLoading] = (0, import_react2.useState)(false);
161
- const [success, setSuccess] = (0, import_react2.useState)(false);
162
- const [error, setError] = (0, import_react2.useState)(null);
190
+ const [email, setEmail] = (0, import_react3.useState)("");
191
+ const [submittedEmail, setSubmittedEmail] = (0, import_react3.useState)("");
192
+ const [loading, setLoading] = (0, import_react3.useState)(false);
193
+ const [success, setSuccess] = (0, import_react3.useState)(false);
194
+ const [error, setError] = (0, import_react3.useState)(null);
163
195
  const isBook = title === "Confirm your spot";
164
196
  const handleSubmit = async () => {
165
197
  const trimmed = email.trim();
@@ -423,21 +455,21 @@ function LoadingSkeleton() {
423
455
  ] });
424
456
  }
425
457
  function ScheduleView({ schedule, dates, selectedIdx, onSelectDate, onOpenModal }) {
426
- const todayMs = (0, import_react3.useMemo)(() => {
458
+ const todayMs = (0, import_react4.useMemo)(() => {
427
459
  const d = /* @__PURE__ */ new Date();
428
460
  d.setHours(0, 0, 0, 0);
429
461
  return d.getTime();
430
462
  }, []);
431
- const scrollRef = (0, import_react3.useRef)(null);
432
- const [canScrollLeft, setCanScrollLeft] = (0, import_react3.useState)(false);
433
- const [canScrollRight, setCanScrollRight] = (0, import_react3.useState)(false);
463
+ const scrollRef = (0, import_react4.useRef)(null);
464
+ const [canScrollLeft, setCanScrollLeft] = (0, import_react4.useState)(false);
465
+ const [canScrollRight, setCanScrollRight] = (0, import_react4.useState)(false);
434
466
  const updateScrollState = () => {
435
467
  const el = scrollRef.current;
436
468
  if (!el) return;
437
469
  setCanScrollLeft(el.scrollLeft > 0);
438
470
  setCanScrollRight(el.scrollLeft + el.clientWidth < el.scrollWidth - 1);
439
471
  };
440
- (0, import_react3.useEffect)(() => {
472
+ (0, import_react4.useEffect)(() => {
441
473
  const el = scrollRef.current;
442
474
  if (!el) return;
443
475
  updateScrollState();
@@ -452,9 +484,9 @@ function ScheduleView({ schedule, dates, selectedIdx, onSelectDate, onOpenModal
452
484
  const scroll = (dir) => {
453
485
  scrollRef.current?.scrollBy({ left: dir === "left" ? -216 : 216, behavior: "smooth" });
454
486
  };
455
- const isDragging = (0, import_react3.useRef)(false);
456
- const dragStartX = (0, import_react3.useRef)(0);
457
- const dragStartScrollLeft = (0, import_react3.useRef)(0);
487
+ const isDragging = (0, import_react4.useRef)(false);
488
+ const dragStartX = (0, import_react4.useRef)(0);
489
+ const dragStartScrollLeft = (0, import_react4.useRef)(0);
458
490
  const onDragStart = (e) => {
459
491
  if (!scrollRef.current) return;
460
492
  isDragging.current = true;
@@ -474,14 +506,14 @@ function ScheduleView({ schedule, dates, selectedIdx, onSelectDate, onOpenModal
474
506
  scrollRef.current.style.cursor = "grab";
475
507
  scrollRef.current.style.userSelect = "";
476
508
  };
477
- const datesWithClasses = (0, import_react3.useMemo)(
509
+ const datesWithClasses = (0, import_react4.useMemo)(
478
510
  () => new Set(dates.map(
479
511
  (d, i) => schedule.classes?.some((c) => classRunsOnDate(c, d, schedule.type)) ? i : -1
480
512
  ).filter((i) => i >= 0)),
481
513
  [dates, schedule]
482
514
  );
483
515
  const selectedDate = dates[selectedIdx];
484
- const selectedClasses = (0, import_react3.useMemo)(
516
+ const selectedClasses = (0, import_react4.useMemo)(
485
517
  () => (schedule.classes ?? []).filter((c) => selectedDate && classRunsOnDate(c, selectedDate, schedule.type)),
486
518
  [schedule, selectedDate]
487
519
  );
@@ -666,16 +698,16 @@ function CalendarFoldIcon() {
666
698
  );
667
699
  }
668
700
  function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAfter: insertAfterProp }) {
669
- const autoId = (0, import_react3.useId)();
701
+ const autoId = (0, import_react4.useId)();
670
702
  const insertAfter = insertAfterProp ?? autoId;
671
- const [schedule, setSchedule] = (0, import_react3.useState)(null);
672
- const [loading, setLoading] = (0, import_react3.useState)(true);
673
- const [inEditor, setInEditor] = (0, import_react3.useState)(false);
674
- const [isHovered, setIsHovered] = (0, import_react3.useState)(false);
675
- const [modalState, setModalState] = (0, import_react3.useState)(null);
676
- const switchScheduleIdRef = (0, import_react3.useRef)(null);
677
- const liveScheduleIdRef = (0, import_react3.useRef)(null);
678
- const refetchLiveSchedule = (0, import_react3.useCallback)(async () => {
703
+ const [schedule, setSchedule] = (0, import_react4.useState)(null);
704
+ const [loading, setLoading] = (0, import_react4.useState)(true);
705
+ const [inEditor, setInEditor] = (0, import_react4.useState)(false);
706
+ const [isHovered, setIsHovered] = (0, import_react4.useState)(false);
707
+ const [modalState, setModalState] = (0, import_react4.useState)(null);
708
+ const switchScheduleIdRef = (0, import_react4.useRef)(null);
709
+ const liveScheduleIdRef = (0, import_react4.useRef)(null);
710
+ const refetchLiveSchedule = (0, import_react4.useCallback)(async () => {
679
711
  const id = liveScheduleIdRef.current;
680
712
  if (!id) return;
681
713
  try {
@@ -685,7 +717,7 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
685
717
  } catch {
686
718
  }
687
719
  }, []);
688
- const dates = (0, import_react3.useMemo)(() => {
720
+ const dates = (0, import_react4.useMemo)(() => {
689
721
  const today = /* @__PURE__ */ new Date();
690
722
  today.setHours(0, 0, 0, 0);
691
723
  return Array.from({ length: 14 }, (_, i) => {
@@ -694,8 +726,8 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
694
726
  return d;
695
727
  });
696
728
  }, []);
697
- const [selectedIdx, setSelectedIdx] = (0, import_react3.useState)(0);
698
- (0, import_react3.useEffect)(() => {
729
+ const [selectedIdx, setSelectedIdx] = (0, import_react4.useState)(0);
730
+ (0, import_react4.useEffect)(() => {
699
731
  if (!schedule?.classes) return;
700
732
  for (let i = 0; i < dates.length; i++) {
701
733
  if (schedule.classes.some((c) => classRunsOnDate(c, dates[i], schedule.type))) {
@@ -704,7 +736,7 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
704
736
  }
705
737
  }
706
738
  }, [schedule, dates]);
707
- (0, import_react3.useEffect)(() => {
739
+ (0, import_react4.useEffect)(() => {
708
740
  if (typeof window === "undefined") return;
709
741
  const onVisible = () => {
710
742
  if (!document.hidden) void refetchLiveSchedule();
@@ -716,7 +748,7 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
716
748
  document.removeEventListener("visibilitychange", onVisible);
717
749
  };
718
750
  }, [refetchLiveSchedule]);
719
- (0, import_react3.useEffect)(() => {
751
+ (0, import_react4.useEffect)(() => {
720
752
  if (typeof window === "undefined") return;
721
753
  const isInEditor = window.self !== window.top;
722
754
  setInEditor(isInEditor);
@@ -4412,7 +4444,7 @@ var CustomToolbarButton = React4.forwardRef(
4412
4444
  CustomToolbarButton.displayName = "CustomToolbarButton";
4413
4445
 
4414
4446
  // src/ui/item-action-toolbar.tsx
4415
- var import_react4 = require("react");
4447
+ var import_react5 = require("react");
4416
4448
  var import_lucide_react2 = require("lucide-react");
4417
4449
 
4418
4450
  // src/ui/dropdown-menu.tsx
@@ -4596,7 +4628,7 @@ function ItemActionToolbar({
4596
4628
  headingVisible = null,
4597
4629
  onHeadingVisibleChange
4598
4630
  }) {
4599
- const [moreOpen, setMoreOpen] = (0, import_react4.useState)(false);
4631
+ const [moreOpen, setMoreOpen] = (0, import_react5.useState)(false);
4600
4632
  const showDropdownToggle = dropdownOpen !== null && dropdownOpen !== void 0;
4601
4633
  const showHeadingToggle = headingVisible !== null && headingVisible !== void 0;
4602
4634
  const headingTooltip = headingVisible ? "Hide heading" : "Show heading";
@@ -4772,7 +4804,7 @@ function ItemActionToolbar({
4772
4804
  }
4773
4805
 
4774
4806
  // src/ui/item-interaction-layer.tsx
4775
- var import_react5 = require("react");
4807
+ var import_react6 = require("react");
4776
4808
  var import_jsx_runtime10 = require("react/jsx-runtime");
4777
4809
  var PRIMARY = "var(--ohw-primary, #0885FE)";
4778
4810
  var FOCUS_RING = `0 0 0 4px color-mix(in srgb, ${PRIMARY} 12%, transparent)`;
@@ -4824,8 +4856,8 @@ function ClampedToolbarSlot({
4824
4856
  placement,
4825
4857
  children
4826
4858
  }) {
4827
- const slotRef = (0, import_react5.useRef)(null);
4828
- (0, import_react5.useLayoutEffect)(() => {
4859
+ const slotRef = (0, import_react6.useRef)(null);
4860
+ (0, import_react6.useLayoutEffect)(() => {
4829
4861
  const slot = slotRef.current;
4830
4862
  if (!slot) return;
4831
4863
  const clamp = () => {
@@ -4878,8 +4910,8 @@ function DetachedBelowToolbarSlot({
4878
4910
  belowRect,
4879
4911
  children
4880
4912
  }) {
4881
- const slotRef = (0, import_react5.useRef)(null);
4882
- (0, import_react5.useLayoutEffect)(() => {
4913
+ const slotRef = (0, import_react6.useRef)(null);
4914
+ (0, import_react6.useLayoutEffect)(() => {
4883
4915
  const slot = slotRef.current;
4884
4916
  if (!slot) return;
4885
4917
  const clamp = () => {
@@ -5310,7 +5342,7 @@ function CarouselOverlay({
5310
5342
  }
5311
5343
 
5312
5344
  // src/ui/ai-section/AiSectionOverlay.tsx
5313
- var import_react6 = require("react");
5345
+ var import_react7 = require("react");
5314
5346
  var import_lucide_react5 = require("lucide-react");
5315
5347
 
5316
5348
  // src/lib/sections.ts
@@ -5350,8 +5382,8 @@ function readRect(sectionId) {
5350
5382
  return { top: r2.top, left: r2.left, width: r2.width, height: r2.height };
5351
5383
  }
5352
5384
  function useLiveSectionRect(sectionId) {
5353
- const [rect, setRect] = (0, import_react6.useState)(null);
5354
- (0, import_react6.useEffect)(() => {
5385
+ const [rect, setRect] = (0, import_react7.useState)(null);
5386
+ (0, import_react7.useEffect)(() => {
5355
5387
  if (!sectionId) {
5356
5388
  setRect(null);
5357
5389
  return;
@@ -5396,7 +5428,7 @@ function ReviewButton({
5396
5428
  background,
5397
5429
  color
5398
5430
  }) {
5399
- const [hover, setHover] = (0, import_react6.useState)(false);
5431
+ const [hover, setHover] = (0, import_react7.useState)(false);
5400
5432
  return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { style: { position: "relative" }, children: [
5401
5433
  /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
5402
5434
  "button",
@@ -5450,13 +5482,13 @@ function AiSectionOverlay({
5450
5482
  postToParent: postToParent2,
5451
5483
  apiRef
5452
5484
  }) {
5453
- const [selectedId, setSelectedId] = (0, import_react6.useState)(null);
5454
- const [reviewId, setReviewId] = (0, import_react6.useState)(null);
5455
- const reviewIdRef = (0, import_react6.useRef)(null);
5485
+ const [selectedId, setSelectedId] = (0, import_react7.useState)(null);
5486
+ const [reviewId, setReviewId] = (0, import_react7.useState)(null);
5487
+ const reviewIdRef = (0, import_react7.useRef)(null);
5456
5488
  reviewIdRef.current = reviewId;
5457
- const selectedIdRef = (0, import_react6.useRef)(null);
5489
+ const selectedIdRef = (0, import_react7.useRef)(null);
5458
5490
  selectedIdRef.current = selectedId;
5459
- const report = (0, import_react6.useCallback)(
5491
+ const report = (0, import_react7.useCallback)(
5460
5492
  (el) => {
5461
5493
  postToParent2({
5462
5494
  type: "ow:section-selected",
@@ -5466,7 +5498,7 @@ function AiSectionOverlay({
5466
5498
  },
5467
5499
  [postToParent2]
5468
5500
  );
5469
- const selectFromElement = (0, import_react6.useCallback)(
5501
+ const selectFromElement = (0, import_react7.useCallback)(
5470
5502
  (el, options) => {
5471
5503
  const sectionEl = el?.closest("[data-ohw-section]") ?? null;
5472
5504
  const id = sectionEl?.dataset.ohwSection ?? null;
@@ -5476,7 +5508,7 @@ function AiSectionOverlay({
5476
5508
  },
5477
5509
  [report]
5478
5510
  );
5479
- (0, import_react6.useEffect)(() => {
5511
+ (0, import_react7.useEffect)(() => {
5480
5512
  apiRef.current = {
5481
5513
  selectFromElement,
5482
5514
  handleBackgroundClick: (target, clientX, clientY) => {
@@ -5496,7 +5528,7 @@ function AiSectionOverlay({
5496
5528
  apiRef.current = null;
5497
5529
  };
5498
5530
  }, [apiRef, selectFromElement]);
5499
- (0, import_react6.useEffect)(() => {
5531
+ (0, import_react7.useEffect)(() => {
5500
5532
  const onMessage = (e) => {
5501
5533
  if (e.data?.type === "ow:ai-select" && e.data.sectionId === null) {
5502
5534
  setSelectedId(null);
@@ -5519,8 +5551,8 @@ function AiSectionOverlay({
5519
5551
  window.addEventListener("message", onMessage);
5520
5552
  return () => window.removeEventListener("message", onMessage);
5521
5553
  }, [postToParent2]);
5522
- const [hoveredId, setHoveredId] = (0, import_react6.useState)(null);
5523
- (0, import_react6.useEffect)(() => {
5554
+ const [hoveredId, setHoveredId] = (0, import_react7.useState)(null);
5555
+ (0, import_react7.useEffect)(() => {
5524
5556
  const onMove = (e) => {
5525
5557
  const t = e.target;
5526
5558
  if (!(t instanceof HTMLElement)) return;
@@ -5541,7 +5573,7 @@ function AiSectionOverlay({
5541
5573
  document.documentElement.removeEventListener("mouseleave", onLeave);
5542
5574
  };
5543
5575
  }, []);
5544
- (0, import_react6.useEffect)(() => {
5576
+ (0, import_react7.useEffect)(() => {
5545
5577
  const onKeyDown = (e) => {
5546
5578
  if (e.key !== "Escape") return;
5547
5579
  if (reviewIdRef.current) return;
@@ -5554,7 +5586,7 @@ function AiSectionOverlay({
5554
5586
  document.addEventListener("keydown", onKeyDown);
5555
5587
  return () => document.removeEventListener("keydown", onKeyDown);
5556
5588
  }, [report]);
5557
- const decide = (0, import_react6.useCallback)(
5589
+ const decide = (0, import_react7.useCallback)(
5558
5590
  (decision) => {
5559
5591
  const sectionId = reviewIdRef.current;
5560
5592
  if (!sectionId) return;
@@ -5647,7 +5679,7 @@ function AiSectionOverlay({
5647
5679
 
5648
5680
  // src/OhhwellsBridge.tsx
5649
5681
  var import_react_dom3 = require("react-dom");
5650
- var import_navigation2 = require("next/navigation");
5682
+ var import_navigation3 = require("next/navigation");
5651
5683
 
5652
5684
  // src/lib/cta-button.ts
5653
5685
  function isCtaButton(el) {
@@ -5935,7 +5967,7 @@ function scrollToHashSectionWhenReady(behavior = "smooth") {
5935
5967
  }
5936
5968
 
5937
5969
  // src/ui/link-modal/LinkPopover.tsx
5938
- var import_react10 = require("react");
5970
+ var import_react11 = require("react");
5939
5971
 
5940
5972
  // src/ui/dialog.tsx
5941
5973
  var React7 = __toESM(require("react"), 1);
@@ -6135,7 +6167,7 @@ function SectionTreeItem({
6135
6167
  }
6136
6168
 
6137
6169
  // src/ui/link-modal/UrlOrPageInput.tsx
6138
- var import_react7 = require("react");
6170
+ var import_react8 = require("react");
6139
6171
 
6140
6172
  // src/ui/input.tsx
6141
6173
  var React8 = __toESM(require("react"), 1);
@@ -6203,11 +6235,11 @@ function UrlOrPageInput({
6203
6235
  readOnly = false,
6204
6236
  urlError
6205
6237
  }) {
6206
- const inputId = (0, import_react7.useId)();
6207
- const inputRef = (0, import_react7.useRef)(null);
6208
- const rootRef = (0, import_react7.useRef)(null);
6209
- const [isFocused, setIsFocused] = (0, import_react7.useState)(false);
6210
- (0, import_react7.useEffect)(() => {
6238
+ const inputId = (0, import_react8.useId)();
6239
+ const inputRef = (0, import_react8.useRef)(null);
6240
+ const rootRef = (0, import_react8.useRef)(null);
6241
+ const [isFocused, setIsFocused] = (0, import_react8.useState)(false);
6242
+ (0, import_react8.useEffect)(() => {
6211
6243
  if (!dropdownOpen) return;
6212
6244
  const isOutside = (e) => {
6213
6245
  const root = rootRef.current;
@@ -6415,10 +6447,10 @@ function LinkEditorPanel({ state, onClose }) {
6415
6447
  }
6416
6448
 
6417
6449
  // src/ui/link-modal/SectionPickerOverlay.tsx
6418
- var import_react8 = require("react");
6450
+ var import_react9 = require("react");
6419
6451
  var import_react_dom = require("react-dom");
6420
6452
  var import_lucide_react11 = require("lucide-react");
6421
- var import_navigation = require("next/navigation");
6453
+ var import_navigation2 = require("next/navigation");
6422
6454
  var import_jsx_runtime22 = require("react/jsx-runtime");
6423
6455
  var DIM_OVERLAY = "rgba(0, 0, 0, 0.45)";
6424
6456
  function rectsEqual(a, b) {
@@ -6452,12 +6484,12 @@ function hitTestSectionId(x, y, sectionIds, rects) {
6452
6484
  return null;
6453
6485
  }
6454
6486
  function useSectionRects(sectionIdsKey, enabled) {
6455
- const [rects, setRects] = (0, import_react8.useState)(/* @__PURE__ */ new Map());
6456
- const sectionIds = (0, import_react8.useMemo)(
6487
+ const [rects, setRects] = (0, import_react9.useState)(/* @__PURE__ */ new Map());
6488
+ const sectionIds = (0, import_react9.useMemo)(
6457
6489
  () => sectionIdsKey ? sectionIdsKey.split("\0") : [],
6458
6490
  [sectionIdsKey]
6459
6491
  );
6460
- (0, import_react8.useEffect)(() => {
6492
+ (0, import_react9.useEffect)(() => {
6461
6493
  if (!enabled || sectionIds.length === 0) {
6462
6494
  setRects((prev) => prev.size === 0 ? prev : /* @__PURE__ */ new Map());
6463
6495
  return;
@@ -6496,15 +6528,15 @@ function SectionPickerOverlay({
6496
6528
  onBack,
6497
6529
  onSelect
6498
6530
  }) {
6499
- const router = (0, import_navigation.useRouter)();
6500
- const pathname = (0, import_navigation.usePathname)();
6501
- const [selectedId, setSelectedId] = (0, import_react8.useState)(null);
6502
- const [hoveredId, setHoveredId] = (0, import_react8.useState)(null);
6503
- const pointerRef = (0, import_react8.useRef)(null);
6504
- const pointerScreenRef = (0, import_react8.useRef)(null);
6505
- const iframeOffsetTopRef = (0, import_react8.useRef)(null);
6506
- const sectionIdsRef = (0, import_react8.useRef)([]);
6507
- const [chromeClip, setChromeClip] = (0, import_react8.useState)(
6531
+ const router = (0, import_navigation2.useRouter)();
6532
+ const pathname = (0, import_navigation2.usePathname)();
6533
+ const [selectedId, setSelectedId] = (0, import_react9.useState)(null);
6534
+ const [hoveredId, setHoveredId] = (0, import_react9.useState)(null);
6535
+ const pointerRef = (0, import_react9.useRef)(null);
6536
+ const pointerScreenRef = (0, import_react9.useRef)(null);
6537
+ const iframeOffsetTopRef = (0, import_react9.useRef)(null);
6538
+ const sectionIdsRef = (0, import_react9.useRef)([]);
6539
+ const [chromeClip, setChromeClip] = (0, import_react9.useState)(
6508
6540
  () => ({
6509
6541
  top: 0,
6510
6542
  bottom: typeof window !== "undefined" ? window.innerHeight : 0
@@ -6512,12 +6544,12 @@ function SectionPickerOverlay({
6512
6544
  );
6513
6545
  const normalizedTarget = normalizePath(pagePath);
6514
6546
  const isOnTargetPage = normalizePath(pathname) === normalizedTarget;
6515
- (0, import_react8.useEffect)(() => {
6547
+ (0, import_react9.useEffect)(() => {
6516
6548
  if (isOnTargetPage) return;
6517
6549
  const search = readPreservedSearch();
6518
6550
  router.push(`${normalizedTarget}${search}`);
6519
6551
  }, [isOnTargetPage, normalizedTarget, router]);
6520
- (0, import_react8.useEffect)(() => {
6552
+ (0, import_react9.useEffect)(() => {
6521
6553
  document.documentElement.setAttribute("data-ohw-section-picking", "");
6522
6554
  document.querySelectorAll("[data-ohw-hovered]").forEach((el) => {
6523
6555
  el.removeAttribute("data-ohw-hovered");
@@ -6529,24 +6561,24 @@ function SectionPickerOverlay({
6529
6561
  document.documentElement.removeAttribute("data-ohw-section-picking");
6530
6562
  };
6531
6563
  }, []);
6532
- const liveSections = (0, import_react8.useMemo)(() => {
6564
+ const liveSections = (0, import_react9.useMemo)(() => {
6533
6565
  if (!isOnTargetPage) return sections;
6534
6566
  const live = collectSectionsFromDom();
6535
6567
  if (live.length === 0) return sections;
6536
6568
  const labels = new Map(sections.map((s) => [s.id, s.label]));
6537
6569
  return live.map((s) => ({ id: s.id, label: labels.get(s.id) ?? s.label }));
6538
6570
  }, [isOnTargetPage, sections, pathname]);
6539
- const sectionIdsKey = (0, import_react8.useMemo)(
6571
+ const sectionIdsKey = (0, import_react9.useMemo)(
6540
6572
  () => liveSections.map((s) => s.id).join("\0"),
6541
6573
  [liveSections]
6542
6574
  );
6543
- const sectionIds = (0, import_react8.useMemo)(
6575
+ const sectionIds = (0, import_react9.useMemo)(
6544
6576
  () => liveSections.map((s) => s.id),
6545
6577
  [liveSections]
6546
6578
  );
6547
6579
  sectionIdsRef.current = sectionIds;
6548
6580
  const rects = useSectionRects(sectionIdsKey, isOnTargetPage);
6549
- const applyHoverAt = (0, import_react8.useCallback)(
6581
+ const applyHoverAt = (0, import_react9.useCallback)(
6550
6582
  (x, y, liveRects) => {
6551
6583
  const ids = sectionIdsRef.current;
6552
6584
  const map = liveRects ?? readSectionRects(ids);
@@ -6555,7 +6587,7 @@ function SectionPickerOverlay({
6555
6587
  },
6556
6588
  []
6557
6589
  );
6558
- (0, import_react8.useEffect)(() => {
6590
+ (0, import_react9.useEffect)(() => {
6559
6591
  const applyClip = (iframeOffsetTop, visibleCanvasTop, canvasH) => {
6560
6592
  const top = Math.max(0, visibleCanvasTop - iframeOffsetTop);
6561
6593
  const bottom = Math.min(
@@ -6597,12 +6629,12 @@ function SectionPickerOverlay({
6597
6629
  window.removeEventListener("resize", onResize);
6598
6630
  };
6599
6631
  }, [applyHoverAt]);
6600
- (0, import_react8.useEffect)(() => {
6632
+ (0, import_react9.useEffect)(() => {
6601
6633
  const ptr = pointerRef.current;
6602
6634
  if (!ptr) return;
6603
6635
  applyHoverAt(ptr.x, ptr.y, rects);
6604
6636
  }, [rects, applyHoverAt]);
6605
- (0, import_react8.useEffect)(() => {
6637
+ (0, import_react9.useEffect)(() => {
6606
6638
  const rememberPointer = (clientX, clientY) => {
6607
6639
  pointerRef.current = { x: clientX, y: clientY };
6608
6640
  const top = iframeOffsetTopRef.current;
@@ -6626,7 +6658,7 @@ function SectionPickerOverlay({
6626
6658
  window.removeEventListener("message", onPointerSync);
6627
6659
  };
6628
6660
  }, [rects, applyHoverAt]);
6629
- const handleSelect = (0, import_react8.useCallback)(
6661
+ const handleSelect = (0, import_react9.useCallback)(
6630
6662
  (section) => {
6631
6663
  if (selectedId) return;
6632
6664
  setSelectedId(section.id);
@@ -6634,7 +6666,7 @@ function SectionPickerOverlay({
6634
6666
  },
6635
6667
  [selectedId, onSelect]
6636
6668
  );
6637
- (0, import_react8.useEffect)(() => {
6669
+ (0, import_react9.useEffect)(() => {
6638
6670
  const onKeyDown = (e) => {
6639
6671
  if (e.key === "Escape") {
6640
6672
  e.preventDefault();
@@ -6757,7 +6789,7 @@ function SectionPickerOverlay({
6757
6789
  }
6758
6790
 
6759
6791
  // src/ui/link-modal/useLinkModalState.ts
6760
- var import_react9 = require("react");
6792
+ var import_react10 = require("react");
6761
6793
  function useLinkModalState({
6762
6794
  open,
6763
6795
  mode,
@@ -6769,14 +6801,14 @@ function useLinkModalState({
6769
6801
  onClose,
6770
6802
  onSubmit
6771
6803
  }) {
6772
- const availablePages = (0, import_react9.useMemo)(() => pages, [pages]);
6773
- const [searchValue, setSearchValue] = (0, import_react9.useState)("");
6774
- const [selectedPage, setSelectedPage] = (0, import_react9.useState)(null);
6775
- const [selectedSection, setSelectedSection] = (0, import_react9.useState)(null);
6776
- const [step, setStep] = (0, import_react9.useState)("input");
6777
- const [dropdownOpen, setDropdownOpen] = (0, import_react9.useState)(false);
6778
- const [urlError, setUrlError] = (0, import_react9.useState)("");
6779
- const reset = (0, import_react9.useCallback)(() => {
6804
+ const availablePages = (0, import_react10.useMemo)(() => pages, [pages]);
6805
+ const [searchValue, setSearchValue] = (0, import_react10.useState)("");
6806
+ const [selectedPage, setSelectedPage] = (0, import_react10.useState)(null);
6807
+ const [selectedSection, setSelectedSection] = (0, import_react10.useState)(null);
6808
+ const [step, setStep] = (0, import_react10.useState)("input");
6809
+ const [dropdownOpen, setDropdownOpen] = (0, import_react10.useState)(false);
6810
+ const [urlError, setUrlError] = (0, import_react10.useState)("");
6811
+ const reset = (0, import_react10.useCallback)(() => {
6780
6812
  setSearchValue("");
6781
6813
  setSelectedPage(null);
6782
6814
  setSelectedSection(null);
@@ -6784,7 +6816,7 @@ function useLinkModalState({
6784
6816
  setDropdownOpen(false);
6785
6817
  setUrlError("");
6786
6818
  }, []);
6787
- (0, import_react9.useEffect)(() => {
6819
+ (0, import_react10.useEffect)(() => {
6788
6820
  if (!open) return;
6789
6821
  if (mode === "edit" && initialTarget) {
6790
6822
  const { pageRoute } = parseTarget(initialTarget);
@@ -6800,11 +6832,11 @@ function useLinkModalState({
6800
6832
  setDropdownOpen(false);
6801
6833
  setUrlError("");
6802
6834
  }, [open, mode, initialTarget, reset]);
6803
- const filteredPages = (0, import_react9.useMemo)(() => {
6835
+ const filteredPages = (0, import_react10.useMemo)(() => {
6804
6836
  if (!searchValue.trim()) return availablePages;
6805
6837
  return availablePages.filter((p) => p.title.toLowerCase().startsWith(searchValue.toLowerCase()));
6806
6838
  }, [availablePages, searchValue]);
6807
- const activeSections = (0, import_react9.useMemo)(() => {
6839
+ const activeSections = (0, import_react10.useMemo)(() => {
6808
6840
  if (!selectedPage) return [];
6809
6841
  return getSectionsForPath(sectionsByPath, selectedPage.path);
6810
6842
  }, [selectedPage, sectionsByPath]);
@@ -6853,7 +6885,7 @@ function useLinkModalState({
6853
6885
  reset();
6854
6886
  onClose();
6855
6887
  };
6856
- const isValid = (0, import_react9.useMemo)(() => {
6888
+ const isValid = (0, import_react10.useMemo)(() => {
6857
6889
  if (urlError) return false;
6858
6890
  if (showBreadcrumb) return true;
6859
6891
  if (selectedPage) return true;
@@ -6950,7 +6982,7 @@ function LinkPopover({
6950
6982
  onSubmit
6951
6983
  });
6952
6984
  const sectionPickerActive = state.showSectionPicker && Boolean(state.selectedPage);
6953
- (0, import_react10.useEffect)(() => {
6985
+ (0, import_react11.useEffect)(() => {
6954
6986
  if (!open) return;
6955
6987
  if (sectionPickerActive) {
6956
6988
  postToParent({ type: "ui:unlock" });
@@ -9015,12 +9047,29 @@ function deleteFooterColumn(column) {
9015
9047
  // src/lib/logo-identity.ts
9016
9048
  var LOGO_TEXT_KEYS = ["nav-logo-text", "footer-logo-text", "logo-text"];
9017
9049
  var LOGO_IMAGE_KEYS = ["nav-logo-image", "footer-logo", "footer-logo-image"];
9050
+ var LOGO_HREF_KEYS = ["nav-logo-href", "footer-logo-href", "logo-href"];
9018
9051
  var LOGO_PLACEHOLDER_KEY = "logo-is-placeholder";
9052
+ var LOGO_ALT_KEY = "logo-alt";
9053
+ var LOGO_IMAGE_URL_KEY = "nav-logo-image";
9019
9054
  var PLACEHOLDER_BUSINESS_NAME = "Business name";
9020
9055
  function resolveLogoDisplayText(text) {
9021
9056
  const trimmed = (text ?? "").trim();
9022
9057
  return trimmed || PLACEHOLDER_BUSINESS_NAME;
9023
9058
  }
9059
+ function isFooterLogoRoot(root) {
9060
+ return Boolean(root.closest("footer") || root.closest('[data-ohw-section="footer"]'));
9061
+ }
9062
+ function imageKeyForRoot(root) {
9063
+ return isFooterLogoRoot(root) ? "footer-logo" : "nav-logo-image";
9064
+ }
9065
+ function textKeyForRoot(root) {
9066
+ return isFooterLogoRoot(root) ? "footer-logo-text" : "nav-logo-text";
9067
+ }
9068
+ function ensureLogoHrefKey(root) {
9069
+ if (!(root instanceof HTMLAnchorElement)) return;
9070
+ if (root.hasAttribute("data-ohw-href-key")) return;
9071
+ root.setAttribute("data-ohw-href-key", isFooterLogoRoot(root) ? "footer-logo-href" : "nav-logo-href");
9072
+ }
9024
9073
  function applyLogoIdentity(text, isPlaceholder) {
9025
9074
  const display = resolveLogoDisplayText(text);
9026
9075
  const placeholder = isPlaceholder || !text.trim() || display === PLACEHOLDER_BUSINESS_NAME;
@@ -9041,26 +9090,101 @@ function applyLogoIdentity(text, isPlaceholder) {
9041
9090
  });
9042
9091
  return display;
9043
9092
  }
9093
+ function applyLogoImage(url, alt) {
9094
+ const displayAlt = resolveLogoDisplayText(alt);
9095
+ document.querySelectorAll('[data-ohw-role="logo"], [data-ohw-logo]').forEach((root) => {
9096
+ ensureLogoHrefKey(root);
9097
+ const imageKey = imageKeyForRoot(root);
9098
+ const textKey = textKeyForRoot(root);
9099
+ let img = root.querySelector(`img[data-ohw-key="${imageKey}"]`) ?? (root.querySelector(`[data-ohw-key="${imageKey}"]`) instanceof HTMLImageElement ? root.querySelector(`[data-ohw-key="${imageKey}"]`) : null) ?? root.querySelector("img");
9100
+ let textEl = root.querySelector(`[data-ohw-key="${textKey}"]`) ?? root.querySelector('[data-ohw-key="logo-text"]');
9101
+ if (url) {
9102
+ if (!img) {
9103
+ img = document.createElement("img");
9104
+ img.setAttribute("data-ohw-editable", "image");
9105
+ img.setAttribute("data-ohw-key", imageKey);
9106
+ img.alt = displayAlt;
9107
+ img.style.maxHeight = "40px";
9108
+ img.style.width = "auto";
9109
+ img.style.display = "block";
9110
+ img.style.objectFit = "contain";
9111
+ root.insertBefore(img, root.firstChild);
9112
+ } else {
9113
+ img.setAttribute("data-ohw-editable", "image");
9114
+ img.setAttribute("data-ohw-key", imageKey);
9115
+ }
9116
+ img.removeAttribute("srcset");
9117
+ img.removeAttribute("sizes");
9118
+ img.src = url;
9119
+ img.alt = displayAlt;
9120
+ img.style.display = "";
9121
+ if (textEl) textEl.style.display = "none";
9122
+ root.removeAttribute("data-ohw-placeholder");
9123
+ return;
9124
+ }
9125
+ if (img) {
9126
+ img.remove();
9127
+ }
9128
+ if (!textEl) {
9129
+ textEl = document.createElement("span");
9130
+ textEl.setAttribute("data-ohw-editable", "plain");
9131
+ textEl.setAttribute("data-ohw-key", textKey);
9132
+ root.appendChild(textEl);
9133
+ }
9134
+ textEl.style.display = "";
9135
+ if (textEl.textContent !== displayAlt) textEl.textContent = displayAlt;
9136
+ if (!displayAlt.trim() || displayAlt === PLACEHOLDER_BUSINESS_NAME) {
9137
+ root.setAttribute("data-ohw-placeholder", "");
9138
+ } else {
9139
+ root.removeAttribute("data-ohw-placeholder");
9140
+ }
9141
+ });
9142
+ }
9143
+ function applyLogoHref(href) {
9144
+ const target = href.trim() || "/";
9145
+ document.querySelectorAll('[data-ohw-role="logo"], [data-ohw-logo]').forEach((root) => {
9146
+ ensureLogoHrefKey(root);
9147
+ if (root instanceof HTMLAnchorElement) {
9148
+ root.setAttribute("href", target);
9149
+ }
9150
+ });
9151
+ }
9044
9152
  function readLogoIdentityFromDom() {
9153
+ let imageUrl = null;
9154
+ for (const key of LOGO_IMAGE_KEYS) {
9155
+ const el = document.querySelector(`[data-ohw-key="${key}"]`);
9156
+ const img = el instanceof HTMLImageElement ? el : el?.querySelector("img");
9157
+ if (img?.src && !img.src.startsWith("data:") && img.style.display !== "none") {
9158
+ imageUrl = img.currentSrc || img.src;
9159
+ break;
9160
+ }
9161
+ }
9162
+ let text = PLACEHOLDER_BUSINESS_NAME;
9163
+ let isPlaceholder = true;
9045
9164
  for (const key of LOGO_TEXT_KEYS) {
9046
9165
  const el = document.querySelector(`[data-ohw-key="${key}"]`);
9047
9166
  if (el?.textContent?.trim()) {
9048
- const text = el.textContent.trim();
9049
- const logoRoot = el.closest('[data-ohw-role="logo"], [data-ohw-logo]');
9050
- const isPlaceholder = logoRoot?.hasAttribute("data-ohw-placeholder") === true || text === PLACEHOLDER_BUSINESS_NAME;
9051
- return { text, isPlaceholder };
9167
+ text = el.textContent.trim();
9168
+ const logoRoot2 = el.closest('[data-ohw-role="logo"], [data-ohw-logo]');
9169
+ isPlaceholder = logoRoot2?.hasAttribute("data-ohw-placeholder") === true || text === PLACEHOLDER_BUSINESS_NAME;
9170
+ break;
9052
9171
  }
9053
9172
  }
9054
- const logoImg = document.querySelector(
9055
- '[data-ohw-key="nav-logo-image"], [data-ohw-key="footer-logo"]'
9056
- );
9057
- if (logoImg?.alt?.trim()) {
9058
- const text = logoImg.alt.trim();
9059
- const logoRoot = logoImg.closest('[data-ohw-role="logo"], [data-ohw-logo]');
9060
- const isPlaceholder = logoRoot?.hasAttribute("data-ohw-placeholder") === true || text === PLACEHOLDER_BUSINESS_NAME;
9061
- return { text, isPlaceholder };
9173
+ if (imageUrl) {
9174
+ const logoImg = document.querySelector(
9175
+ '[data-ohw-key="nav-logo-image"], [data-ohw-key="footer-logo"]'
9176
+ );
9177
+ const alt = logoImg?.alt?.trim() || text;
9178
+ isPlaceholder = false;
9179
+ const hrefEl = document.querySelector(
9180
+ 'a[data-ohw-role="logo"], a[data-ohw-logo], [data-ohw-role="logo"]'
9181
+ );
9182
+ const href2 = (hrefEl instanceof HTMLAnchorElement ? hrefEl.getAttribute("href") : null) || hrefEl?.closest("a")?.getAttribute("href") || "/";
9183
+ return { text, isPlaceholder, imageUrl, href: href2, alt };
9062
9184
  }
9063
- return { text: PLACEHOLDER_BUSINESS_NAME, isPlaceholder: true };
9185
+ const logoRoot = document.querySelector('[data-ohw-role="logo"], [data-ohw-logo]');
9186
+ const href = (logoRoot instanceof HTMLAnchorElement ? logoRoot.getAttribute("href") : null) || logoRoot?.closest("a")?.getAttribute("href") || "/";
9187
+ return { text, isPlaceholder, imageUrl: null, href, alt: text };
9064
9188
  }
9065
9189
 
9066
9190
  // src/lib/site-wide-scope.ts
@@ -9330,7 +9454,7 @@ function hitTestNavDropSlot(clientX, clientY, draggedHrefKey) {
9330
9454
  }
9331
9455
 
9332
9456
  // src/useNavItemDrag.ts
9333
- var import_react11 = require("react");
9457
+ var import_react12 = require("react");
9334
9458
  function useNavItemDrag({
9335
9459
  isEditMode,
9336
9460
  editContentRef,
@@ -9354,11 +9478,11 @@ function useNavItemDrag({
9354
9478
  getNavigationItemAnchor: getNavigationItemAnchor2,
9355
9479
  isDragHandleDisabled: isDragHandleDisabled2
9356
9480
  }) {
9357
- const navDragRef = (0, import_react11.useRef)(null);
9358
- const [navDropSlots, setNavDropSlots] = (0, import_react11.useState)([]);
9359
- const [activeNavDropIndex, setActiveNavDropIndex] = (0, import_react11.useState)(null);
9360
- const navPointerDragRef = (0, import_react11.useRef)(null);
9361
- const clearNavDragVisuals = (0, import_react11.useCallback)(() => {
9481
+ const navDragRef = (0, import_react12.useRef)(null);
9482
+ const [navDropSlots, setNavDropSlots] = (0, import_react12.useState)([]);
9483
+ const [activeNavDropIndex, setActiveNavDropIndex] = (0, import_react12.useState)(null);
9484
+ const navPointerDragRef = (0, import_react12.useRef)(null);
9485
+ const clearNavDragVisuals = (0, import_react12.useCallback)(() => {
9362
9486
  const session = navDragRef.current;
9363
9487
  const keepOpenEl = session?.draggedEl?.closest("[data-ohw-nav-children]") != null ? session.draggedEl : null;
9364
9488
  navDragRef.current = null;
@@ -9375,7 +9499,7 @@ function useNavItemDrag({
9375
9499
  document.documentElement.removeAttribute("data-ohw-nav-dragging-root");
9376
9500
  unlockItemDragInteraction();
9377
9501
  }, [setDraggedItemRect, setIsItemDragging, setSiblingHintRects]);
9378
- const refreshNavDragVisuals = (0, import_react11.useCallback)(
9502
+ const refreshNavDragVisuals = (0, import_react12.useCallback)(
9379
9503
  (session, activeSlot, clientX, clientY) => {
9380
9504
  setDraggedItemRect(session.draggedEl.getBoundingClientRect());
9381
9505
  if (typeof clientX === "number" && typeof clientY === "number") {
@@ -9393,13 +9517,13 @@ function useNavItemDrag({
9393
9517
  },
9394
9518
  [setDraggedItemRect, setSiblingHintRects]
9395
9519
  );
9396
- const refreshNavDragVisualsRef = (0, import_react11.useRef)(refreshNavDragVisuals);
9520
+ const refreshNavDragVisualsRef = (0, import_react12.useRef)(refreshNavDragVisuals);
9397
9521
  refreshNavDragVisualsRef.current = refreshNavDragVisuals;
9398
- const commitNavDragRef = (0, import_react11.useRef)(() => {
9522
+ const commitNavDragRef = (0, import_react12.useRef)(() => {
9399
9523
  });
9400
- const beginNavDragRef = (0, import_react11.useRef)(() => {
9524
+ const beginNavDragRef = (0, import_react12.useRef)(() => {
9401
9525
  });
9402
- const beginNavDrag = (0, import_react11.useCallback)(
9526
+ const beginNavDrag = (0, import_react12.useCallback)(
9403
9527
  (session) => {
9404
9528
  const rect = session.draggedEl.getBoundingClientRect();
9405
9529
  session.lastClientX = session.lastClientX || rect.left + rect.width / 2;
@@ -9433,7 +9557,7 @@ function useNavItemDrag({
9433
9557
  ]
9434
9558
  );
9435
9559
  beginNavDragRef.current = beginNavDrag;
9436
- const commitNavDrag = (0, import_react11.useCallback)(
9560
+ const commitNavDrag = (0, import_react12.useCallback)(
9437
9561
  (clientX, clientY) => {
9438
9562
  const session = navDragRef.current;
9439
9563
  if (!session) {
@@ -9494,7 +9618,7 @@ function useNavItemDrag({
9494
9618
  [clearNavDragVisuals, deselectRef, editContentRef, postToParentRef, selectRef]
9495
9619
  );
9496
9620
  commitNavDragRef.current = commitNavDrag;
9497
- const startNavLinkDrag = (0, import_react11.useCallback)(
9621
+ const startNavLinkDrag = (0, import_react12.useCallback)(
9498
9622
  (anchor, clientX, clientY, wasSelected) => {
9499
9623
  if (footerDragRef.current) return false;
9500
9624
  const hrefKey = anchor.getAttribute("data-ohw-href-key");
@@ -9512,7 +9636,7 @@ function useNavItemDrag({
9512
9636
  },
9513
9637
  [beginNavDrag, footerDragRef, isDragHandleDisabled2, isCtaButton]
9514
9638
  );
9515
- const onNavDragOver = (0, import_react11.useCallback)(
9639
+ const onNavDragOver = (0, import_react12.useCallback)(
9516
9640
  (e) => {
9517
9641
  const session = navDragRef.current;
9518
9642
  if (!session) return false;
@@ -9524,7 +9648,7 @@ function useNavItemDrag({
9524
9648
  },
9525
9649
  []
9526
9650
  );
9527
- (0, import_react11.useEffect)(() => {
9651
+ (0, import_react12.useEffect)(() => {
9528
9652
  if (!isEditMode) return;
9529
9653
  const THRESHOLD = 10;
9530
9654
  const resolveWasSelected = (el) => {
@@ -9649,7 +9773,7 @@ function useNavItemDrag({
9649
9773
  setLinkPopover,
9650
9774
  suppressNextClickRef
9651
9775
  ]);
9652
- const armNavPressFromChrome = (0, import_react11.useCallback)(
9776
+ const armNavPressFromChrome = (0, import_react12.useCallback)(
9653
9777
  (selected, clientX, clientY, pointerId) => {
9654
9778
  const hrefKey = selected.getAttribute("data-ohw-href-key");
9655
9779
  if (!hrefKey || !isNavbarHrefKey(hrefKey)) return false;
@@ -9731,7 +9855,7 @@ function FooterContainerChrome({
9731
9855
  }
9732
9856
 
9733
9857
  // src/lib/carousel.ts
9734
- var import_react12 = require("react");
9858
+ var import_react13 = require("react");
9735
9859
  var CAROUSEL_ATTR = "data-ohw-carousel";
9736
9860
  var CAROUSEL_VALUE_ATTR = "data-ohw-carousel-value";
9737
9861
  var CAROUSEL_SLIDE_ATTR = "data-ohw-carousel-slide";
@@ -9793,8 +9917,8 @@ function applyCarouselNode(key, val) {
9793
9917
  return true;
9794
9918
  }
9795
9919
  function useOhwCarousel(key, initial) {
9796
- const [images, setImages] = (0, import_react12.useState)(initial);
9797
- (0, import_react12.useEffect)(() => {
9920
+ const [images, setImages] = (0, import_react13.useState)(initial);
9921
+ (0, import_react13.useEffect)(() => {
9798
9922
  const el = document.querySelector(
9799
9923
  `[${CAROUSEL_ATTR}][data-ohw-key="${CSS.escape(key)}"]`
9800
9924
  );
@@ -11270,9 +11394,9 @@ function FloatingToolbar({
11270
11394
  showEditLink,
11271
11395
  onEditLink
11272
11396
  }) {
11273
- const localRef = import_react13.default.useRef(null);
11274
- const [measuredW, setMeasuredW] = import_react13.default.useState(330);
11275
- const setRefs = import_react13.default.useCallback(
11397
+ const localRef = import_react14.default.useRef(null);
11398
+ const [measuredW, setMeasuredW] = import_react14.default.useState(330);
11399
+ const setRefs = import_react14.default.useCallback(
11276
11400
  (node) => {
11277
11401
  localRef.current = node;
11278
11402
  if (typeof elRef === "function") elRef(node);
@@ -11284,7 +11408,7 @@ function FloatingToolbar({
11284
11408
  },
11285
11409
  [elRef]
11286
11410
  );
11287
- import_react13.default.useLayoutEffect(() => {
11411
+ import_react14.default.useLayoutEffect(() => {
11288
11412
  const node = localRef.current;
11289
11413
  if (!node) return;
11290
11414
  const update = () => {
@@ -11310,7 +11434,7 @@ function FloatingToolbar({
11310
11434
  pointerEvents: "auto"
11311
11435
  },
11312
11436
  children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(CustomToolbar, { children: [
11313
- TOOLBAR_GROUPS.map((btns, gi) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(import_react13.default.Fragment, { children: [
11437
+ TOOLBAR_GROUPS.map((btns, gi) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(import_react14.default.Fragment, { children: [
11314
11438
  gi > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(CustomToolbarDivider, {}),
11315
11439
  btns.map((btn) => {
11316
11440
  const isActive = activeCommands.has(btn.cmd);
@@ -11412,12 +11536,12 @@ function resolveSubdomain(subdomainFromQuery) {
11412
11536
  return "";
11413
11537
  }
11414
11538
  function OhhwellsBridge() {
11415
- const pathname = (0, import_navigation2.usePathname)();
11416
- const router = (0, import_navigation2.useRouter)();
11417
- const searchParams = (0, import_navigation2.useSearchParams)();
11539
+ const pathname = (0, import_navigation3.usePathname)();
11540
+ const router = (0, import_navigation3.useRouter)();
11541
+ const searchParams = (0, import_navigation3.useSearchParams)();
11418
11542
  const isEditMode = isEditSessionActive();
11419
- const [bridgeRoot, setBridgeRoot] = (0, import_react13.useState)(null);
11420
- (0, import_react13.useEffect)(() => {
11543
+ const [bridgeRoot, setBridgeRoot] = (0, import_react14.useState)(null);
11544
+ (0, import_react14.useEffect)(() => {
11421
11545
  const figtreeFontId = "ohw-figtree-font";
11422
11546
  if (!document.getElementById(figtreeFontId)) {
11423
11547
  const preconnect1 = Object.assign(document.createElement("link"), { rel: "preconnect", href: "https://fonts.googleapis.com" });
@@ -11445,107 +11569,108 @@ function OhhwellsBridge() {
11445
11569
  const subdomainFromQuery = searchParams.get("subdomain");
11446
11570
  const subdomain = resolveSubdomain(subdomainFromQuery);
11447
11571
  useLinkHrefGuardian(pathname, subdomain, isEditMode);
11448
- const postToParent2 = (0, import_react13.useCallback)((data) => {
11572
+ useSavedLinkNavigation(isEditMode);
11573
+ const postToParent2 = (0, import_react14.useCallback)((data) => {
11449
11574
  if (typeof window !== "undefined" && window.parent !== window) {
11450
11575
  window.parent.postMessage(data, "*");
11451
11576
  }
11452
11577
  }, []);
11453
- const [fetchState, setFetchState] = (0, import_react13.useState)("idle");
11454
- const autoSaveTimers = (0, import_react13.useRef)(/* @__PURE__ */ new Map());
11455
- const activeElRef = (0, import_react13.useRef)(null);
11456
- const pointerHeldRef = (0, import_react13.useRef)(false);
11457
- const selectedElRef = (0, import_react13.useRef)(null);
11458
- const selectedHrefKeyRef = (0, import_react13.useRef)(null);
11459
- const selectedFooterColAttrRef = (0, import_react13.useRef)(null);
11460
- const originalContentRef = (0, import_react13.useRef)(null);
11461
- const activeStateElRef = (0, import_react13.useRef)(null);
11462
- const parentScrollRef = (0, import_react13.useRef)(null);
11463
- const visibleViewportRef = (0, import_react13.useRef)(null);
11464
- const [dialogPortalContainer, setDialogPortalContainer] = (0, import_react13.useState)(null);
11465
- const attachVisibleViewport = (0, import_react13.useCallback)((node) => {
11578
+ const [fetchState, setFetchState] = (0, import_react14.useState)("idle");
11579
+ const autoSaveTimers = (0, import_react14.useRef)(/* @__PURE__ */ new Map());
11580
+ const activeElRef = (0, import_react14.useRef)(null);
11581
+ const pointerHeldRef = (0, import_react14.useRef)(false);
11582
+ const selectedElRef = (0, import_react14.useRef)(null);
11583
+ const selectedHrefKeyRef = (0, import_react14.useRef)(null);
11584
+ const selectedFooterColAttrRef = (0, import_react14.useRef)(null);
11585
+ const originalContentRef = (0, import_react14.useRef)(null);
11586
+ const activeStateElRef = (0, import_react14.useRef)(null);
11587
+ const parentScrollRef = (0, import_react14.useRef)(null);
11588
+ const visibleViewportRef = (0, import_react14.useRef)(null);
11589
+ const [dialogPortalContainer, setDialogPortalContainer] = (0, import_react14.useState)(null);
11590
+ const attachVisibleViewport = (0, import_react14.useCallback)((node) => {
11466
11591
  visibleViewportRef.current = node;
11467
11592
  setDialogPortalContainer(node);
11468
11593
  if (node) applyVisibleViewport(node, parentScrollRef.current);
11469
11594
  }, []);
11470
- const toolbarElRef = (0, import_react13.useRef)(null);
11471
- const glowElRef = (0, import_react13.useRef)(null);
11472
- const hoveredImageRef = (0, import_react13.useRef)(null);
11473
- const hoveredImageHasTextOverlapRef = (0, import_react13.useRef)(false);
11474
- const dragOverElRef = (0, import_react13.useRef)(null);
11475
- const [mediaHover, setMediaHover] = (0, import_react13.useState)(null);
11476
- const [carouselHover, setCarouselHover] = (0, import_react13.useState)(null);
11477
- const [uploadingRects, setUploadingRects] = (0, import_react13.useState)({});
11478
- const hoveredGapRef = (0, import_react13.useRef)(null);
11479
- const imageUnhoverTimerRef = (0, import_react13.useRef)(null);
11480
- const imageShowTimerRef = (0, import_react13.useRef)(null);
11481
- const editStylesRef = (0, import_react13.useRef)(null);
11482
- const activateRef = (0, import_react13.useRef)(() => {
11595
+ const toolbarElRef = (0, import_react14.useRef)(null);
11596
+ const glowElRef = (0, import_react14.useRef)(null);
11597
+ const hoveredImageRef = (0, import_react14.useRef)(null);
11598
+ const hoveredImageHasTextOverlapRef = (0, import_react14.useRef)(false);
11599
+ const dragOverElRef = (0, import_react14.useRef)(null);
11600
+ const [mediaHover, setMediaHover] = (0, import_react14.useState)(null);
11601
+ const [carouselHover, setCarouselHover] = (0, import_react14.useState)(null);
11602
+ const [uploadingRects, setUploadingRects] = (0, import_react14.useState)({});
11603
+ const hoveredGapRef = (0, import_react14.useRef)(null);
11604
+ const imageUnhoverTimerRef = (0, import_react14.useRef)(null);
11605
+ const imageShowTimerRef = (0, import_react14.useRef)(null);
11606
+ const editStylesRef = (0, import_react14.useRef)(null);
11607
+ const activateRef = (0, import_react14.useRef)(() => {
11483
11608
  });
11484
- const deactivateRef = (0, import_react13.useRef)(() => {
11609
+ const deactivateRef = (0, import_react14.useRef)(() => {
11485
11610
  });
11486
- const selectRef = (0, import_react13.useRef)(() => {
11611
+ const selectRef = (0, import_react14.useRef)(() => {
11487
11612
  });
11488
- const selectFrameRef = (0, import_react13.useRef)(() => {
11613
+ const selectFrameRef = (0, import_react14.useRef)(() => {
11489
11614
  });
11490
- const deselectRef = (0, import_react13.useRef)(() => {
11615
+ const deselectRef = (0, import_react14.useRef)(() => {
11491
11616
  });
11492
- const reselectNavigationItemRef = (0, import_react13.useRef)(() => {
11617
+ const reselectNavigationItemRef = (0, import_react14.useRef)(() => {
11493
11618
  });
11494
- const commitNavigationTextEditRef = (0, import_react13.useRef)(() => {
11619
+ const commitNavigationTextEditRef = (0, import_react14.useRef)(() => {
11495
11620
  });
11496
- const handleDeleteSelectedRef = (0, import_react13.useRef)(() => false);
11497
- const runPendingDeleteUndoRef = (0, import_react13.useRef)(() => false);
11498
- const isFooterFrameSelectionRef = (0, import_react13.useRef)(false);
11499
- const refreshActiveCommandsRef = (0, import_react13.useRef)(() => {
11621
+ const handleDeleteSelectedRef = (0, import_react14.useRef)(() => false);
11622
+ const runPendingDeleteUndoRef = (0, import_react14.useRef)(() => false);
11623
+ const isFooterFrameSelectionRef = (0, import_react14.useRef)(false);
11624
+ const refreshActiveCommandsRef = (0, import_react14.useRef)(() => {
11500
11625
  });
11501
- const postToParentRef = (0, import_react13.useRef)(postToParent2);
11626
+ const postToParentRef = (0, import_react14.useRef)(postToParent2);
11502
11627
  postToParentRef.current = postToParent2;
11503
- const aiSectionApiRef = (0, import_react13.useRef)(null);
11504
- const sectionsLoadedRef = (0, import_react13.useRef)(false);
11505
- const pendingScheduleConfigRequests = (0, import_react13.useRef)([]);
11506
- const [toolbarRect, setToolbarRect] = (0, import_react13.useState)(null);
11507
- const [toolbarVariant, setToolbarVariant] = (0, import_react13.useState)("none");
11508
- const toolbarVariantRef = (0, import_react13.useRef)("none");
11628
+ const aiSectionApiRef = (0, import_react14.useRef)(null);
11629
+ const sectionsLoadedRef = (0, import_react14.useRef)(false);
11630
+ const pendingScheduleConfigRequests = (0, import_react14.useRef)([]);
11631
+ const [toolbarRect, setToolbarRect] = (0, import_react14.useState)(null);
11632
+ const [toolbarVariant, setToolbarVariant] = (0, import_react14.useState)("none");
11633
+ const toolbarVariantRef = (0, import_react14.useRef)("none");
11509
11634
  toolbarVariantRef.current = toolbarVariant;
11510
- const [selectedIsCta, setSelectedIsCta] = (0, import_react13.useState)(false);
11511
- const [reorderHrefKey, setReorderHrefKey] = (0, import_react13.useState)(null);
11512
- const [reorderDragDisabled, setReorderDragDisabled] = (0, import_react13.useState)(false);
11513
- const [toggleState, setToggleState] = (0, import_react13.useState)(null);
11514
- const [maxBadge, setMaxBadge] = (0, import_react13.useState)(null);
11515
- const [activeCommands, setActiveCommands] = (0, import_react13.useState)(/* @__PURE__ */ new Set());
11516
- const [sectionGap, setSectionGap] = (0, import_react13.useState)(null);
11517
- const [toolbarShowEditLink, setToolbarShowEditLink] = (0, import_react13.useState)(false);
11518
- const hoveredNavContainerRef = (0, import_react13.useRef)(null);
11519
- const [hoveredNavContainerRect, setHoveredNavContainerRect] = (0, import_react13.useState)(null);
11520
- const hoveredItemElRef = (0, import_react13.useRef)(null);
11521
- const [hoveredItemRect, setHoveredItemRect] = (0, import_react13.useState)(null);
11522
- const siblingHintElRef = (0, import_react13.useRef)(null);
11523
- const [siblingHintRect, setSiblingHintRect] = (0, import_react13.useState)(null);
11524
- const [siblingHintRects, setSiblingHintRects] = (0, import_react13.useState)([]);
11525
- const [isItemDragging, setIsItemDragging] = (0, import_react13.useState)(false);
11526
- const [isFooterFrameSelection, setIsFooterFrameSelection] = (0, import_react13.useState)(false);
11635
+ const [selectedIsCta, setSelectedIsCta] = (0, import_react14.useState)(false);
11636
+ const [reorderHrefKey, setReorderHrefKey] = (0, import_react14.useState)(null);
11637
+ const [reorderDragDisabled, setReorderDragDisabled] = (0, import_react14.useState)(false);
11638
+ const [toggleState, setToggleState] = (0, import_react14.useState)(null);
11639
+ const [maxBadge, setMaxBadge] = (0, import_react14.useState)(null);
11640
+ const [activeCommands, setActiveCommands] = (0, import_react14.useState)(/* @__PURE__ */ new Set());
11641
+ const [sectionGap, setSectionGap] = (0, import_react14.useState)(null);
11642
+ const [toolbarShowEditLink, setToolbarShowEditLink] = (0, import_react14.useState)(false);
11643
+ const hoveredNavContainerRef = (0, import_react14.useRef)(null);
11644
+ const [hoveredNavContainerRect, setHoveredNavContainerRect] = (0, import_react14.useState)(null);
11645
+ const hoveredItemElRef = (0, import_react14.useRef)(null);
11646
+ const [hoveredItemRect, setHoveredItemRect] = (0, import_react14.useState)(null);
11647
+ const siblingHintElRef = (0, import_react14.useRef)(null);
11648
+ const [siblingHintRect, setSiblingHintRect] = (0, import_react14.useState)(null);
11649
+ const [siblingHintRects, setSiblingHintRects] = (0, import_react14.useState)([]);
11650
+ const [isItemDragging, setIsItemDragging] = (0, import_react14.useState)(false);
11651
+ const [isFooterFrameSelection, setIsFooterFrameSelection] = (0, import_react14.useState)(false);
11527
11652
  isFooterFrameSelectionRef.current = isFooterFrameSelection;
11528
- const [navDropdownPreviewOpen, setNavDropdownPreviewOpen] = (0, import_react13.useState)(null);
11529
- const [footerHeadingVisible, setFooterHeadingVisible] = (0, import_react13.useState)(null);
11530
- const footerDragRef = (0, import_react13.useRef)(null);
11531
- const [footerDropSlots, setFooterDropSlots] = (0, import_react13.useState)([]);
11532
- const [activeFooterDropIndex, setActiveFooterDropIndex] = (0, import_react13.useState)(null);
11533
- const [draggedItemRect, setDraggedItemRect] = (0, import_react13.useState)(null);
11534
- const footerPointerDragRef = (0, import_react13.useRef)(null);
11535
- const suppressNextClickRef = (0, import_react13.useRef)(false);
11536
- const suppressClickUntilRef = (0, import_react13.useRef)(0);
11537
- const [linkPopover, setLinkPopover] = (0, import_react13.useState)(null);
11538
- const linkPopoverSessionRef = (0, import_react13.useRef)(null);
11539
- const addNavAfterAnchorRef = (0, import_react13.useRef)(null);
11540
- const editContentRef = (0, import_react13.useRef)({});
11541
- const pendingDeleteUndoRef = (0, import_react13.useRef)(null);
11542
- const [sitePages, setSitePages] = (0, import_react13.useState)([]);
11543
- const [sectionsByPath, setSectionsByPath] = (0, import_react13.useState)({});
11544
- const sectionsPrefetchGenRef = (0, import_react13.useRef)(0);
11545
- const setLinkPopoverRef = (0, import_react13.useRef)(setLinkPopover);
11546
- const linkPopoverPanelRef = (0, import_react13.useRef)(null);
11547
- const linkPopoverOpenRef = (0, import_react13.useRef)(false);
11548
- const linkPopoverGraceUntilRef = (0, import_react13.useRef)(0);
11653
+ const [navDropdownPreviewOpen, setNavDropdownPreviewOpen] = (0, import_react14.useState)(null);
11654
+ const [footerHeadingVisible, setFooterHeadingVisible] = (0, import_react14.useState)(null);
11655
+ const footerDragRef = (0, import_react14.useRef)(null);
11656
+ const [footerDropSlots, setFooterDropSlots] = (0, import_react14.useState)([]);
11657
+ const [activeFooterDropIndex, setActiveFooterDropIndex] = (0, import_react14.useState)(null);
11658
+ const [draggedItemRect, setDraggedItemRect] = (0, import_react14.useState)(null);
11659
+ const footerPointerDragRef = (0, import_react14.useRef)(null);
11660
+ const suppressNextClickRef = (0, import_react14.useRef)(false);
11661
+ const suppressClickUntilRef = (0, import_react14.useRef)(0);
11662
+ const [linkPopover, setLinkPopover] = (0, import_react14.useState)(null);
11663
+ const linkPopoverSessionRef = (0, import_react14.useRef)(null);
11664
+ const addNavAfterAnchorRef = (0, import_react14.useRef)(null);
11665
+ const editContentRef = (0, import_react14.useRef)({});
11666
+ const pendingDeleteUndoRef = (0, import_react14.useRef)(null);
11667
+ const [sitePages, setSitePages] = (0, import_react14.useState)([]);
11668
+ const [sectionsByPath, setSectionsByPath] = (0, import_react14.useState)({});
11669
+ const sectionsPrefetchGenRef = (0, import_react14.useRef)(0);
11670
+ const setLinkPopoverRef = (0, import_react14.useRef)(setLinkPopover);
11671
+ const linkPopoverPanelRef = (0, import_react14.useRef)(null);
11672
+ const linkPopoverOpenRef = (0, import_react14.useRef)(false);
11673
+ const linkPopoverGraceUntilRef = (0, import_react14.useRef)(0);
11549
11674
  setLinkPopoverRef.current = setLinkPopover;
11550
11675
  linkPopoverSessionRef.current = linkPopover;
11551
11676
  const {
@@ -11583,7 +11708,7 @@ function OhhwellsBridge() {
11583
11708
  const bumpLinkPopoverGrace = () => {
11584
11709
  linkPopoverGraceUntilRef.current = Date.now() + 350;
11585
11710
  };
11586
- const runSectionsPrefetch = (0, import_react13.useCallback)((pages) => {
11711
+ const runSectionsPrefetch = (0, import_react14.useCallback)((pages) => {
11587
11712
  if (!isEditMode || shouldUseDevFixtures() || pages.length === 0) return;
11588
11713
  const gen = ++sectionsPrefetchGenRef.current;
11589
11714
  const paths = pages.map((p) => p.path);
@@ -11602,9 +11727,9 @@ function OhhwellsBridge() {
11602
11727
  );
11603
11728
  });
11604
11729
  }, [isEditMode, pathname]);
11605
- const runSectionsPrefetchRef = (0, import_react13.useRef)(runSectionsPrefetch);
11730
+ const runSectionsPrefetchRef = (0, import_react14.useRef)(runSectionsPrefetch);
11606
11731
  runSectionsPrefetchRef.current = runSectionsPrefetch;
11607
- (0, import_react13.useEffect)(() => {
11732
+ (0, import_react14.useEffect)(() => {
11608
11733
  if (!linkPopover) {
11609
11734
  document.documentElement.removeAttribute("data-ohw-link-popover-open");
11610
11735
  return;
@@ -11632,7 +11757,7 @@ function OhhwellsBridge() {
11632
11757
  document.documentElement.removeAttribute("data-ohw-link-popover-open");
11633
11758
  };
11634
11759
  }, [linkPopover, postToParent2]);
11635
- (0, import_react13.useEffect)(() => {
11760
+ (0, import_react14.useEffect)(() => {
11636
11761
  if (!isEditMode) return;
11637
11762
  const useFixtures = shouldUseDevFixtures();
11638
11763
  if (useFixtures) {
@@ -11656,14 +11781,14 @@ function OhhwellsBridge() {
11656
11781
  if (!useFixtures) postToParent2({ type: "ow:request-site-pages" });
11657
11782
  return () => window.removeEventListener("message", onSitePages);
11658
11783
  }, [isEditMode, postToParent2]);
11659
- (0, import_react13.useEffect)(() => {
11784
+ (0, import_react14.useEffect)(() => {
11660
11785
  if (!isEditMode || shouldUseDevFixtures()) return;
11661
11786
  void loadAllSectionsManifest().then((manifest) => {
11662
11787
  if (Object.keys(manifest).length === 0) return;
11663
11788
  setSectionsByPath((prev) => ({ ...manifest, ...prev }));
11664
11789
  });
11665
11790
  }, [isEditMode]);
11666
- (0, import_react13.useEffect)(() => {
11791
+ (0, import_react14.useEffect)(() => {
11667
11792
  const update = () => {
11668
11793
  const el = activeElRef.current ?? selectedElRef.current;
11669
11794
  if (el) setToolbarRect(getEditMeasureEl(el).getBoundingClientRect());
@@ -11687,10 +11812,10 @@ function OhhwellsBridge() {
11687
11812
  vvp.removeEventListener("resize", update);
11688
11813
  };
11689
11814
  }, []);
11690
- const refreshStateRules = (0, import_react13.useCallback)(() => {
11815
+ const refreshStateRules = (0, import_react14.useCallback)(() => {
11691
11816
  editStylesRef.current?.forceHover && (editStylesRef.current.forceHover.textContent = collectStateRules());
11692
11817
  }, []);
11693
- const processConfigRequest = (0, import_react13.useCallback)((insertAfterVal) => {
11818
+ const processConfigRequest = (0, import_react14.useCallback)((insertAfterVal) => {
11694
11819
  const tracker = getSectionsTracker();
11695
11820
  let entries = [];
11696
11821
  try {
@@ -11713,7 +11838,7 @@ function OhhwellsBridge() {
11713
11838
  }
11714
11839
  window.postMessage({ type: "ow:schedule-config", insertAfter: insertAfterVal, scheduleId: null }, "*");
11715
11840
  }, [isEditMode]);
11716
- const deactivate = (0, import_react13.useCallback)(() => {
11841
+ const deactivate = (0, import_react14.useCallback)(() => {
11717
11842
  const el = activeElRef.current;
11718
11843
  if (!el) return;
11719
11844
  const key = el.dataset.ohwKey;
@@ -11746,12 +11871,12 @@ function OhhwellsBridge() {
11746
11871
  setToolbarShowEditLink(false);
11747
11872
  postToParent2({ type: "ow:exit-edit" });
11748
11873
  }, [postToParent2]);
11749
- const clearSelectedAttr = (0, import_react13.useCallback)(() => {
11874
+ const clearSelectedAttr = (0, import_react14.useCallback)(() => {
11750
11875
  document.querySelectorAll("[data-ohw-selected]").forEach((el) => {
11751
11876
  el.removeAttribute("data-ohw-selected");
11752
11877
  });
11753
11878
  }, []);
11754
- const deselect = (0, import_react13.useCallback)(() => {
11879
+ const deselect = (0, import_react14.useCallback)(() => {
11755
11880
  clearSelectedAttr();
11756
11881
  selectedElRef.current = null;
11757
11882
  selectedHrefKeyRef.current = null;
@@ -11776,11 +11901,11 @@ function OhhwellsBridge() {
11776
11901
  setToolbarVariant("none");
11777
11902
  }
11778
11903
  }, [clearSelectedAttr]);
11779
- const markSelected = (0, import_react13.useCallback)((el) => {
11904
+ const markSelected = (0, import_react14.useCallback)((el) => {
11780
11905
  clearSelectedAttr();
11781
11906
  el.setAttribute("data-ohw-selected", "");
11782
11907
  }, [clearSelectedAttr]);
11783
- const resolveHrefKeyElement = (0, import_react13.useCallback)((hrefKey) => {
11908
+ const resolveHrefKeyElement = (0, import_react14.useCallback)((hrefKey) => {
11784
11909
  if (isFooterHrefKey(hrefKey)) {
11785
11910
  return document.querySelector(
11786
11911
  `footer [data-ohw-href-key="${CSS.escape(hrefKey)}"]`
@@ -11795,7 +11920,7 @@ function OhhwellsBridge() {
11795
11920
  `[data-ohw-href-key="${CSS.escape(hrefKey)}"]`
11796
11921
  );
11797
11922
  }, []);
11798
- const resyncSelectedNavigationItem = (0, import_react13.useCallback)(() => {
11923
+ const resyncSelectedNavigationItem = (0, import_react14.useCallback)(() => {
11799
11924
  const hrefKey = selectedHrefKeyRef.current;
11800
11925
  if (hrefKey) {
11801
11926
  const link = resolveHrefKeyElement(hrefKey);
@@ -11833,7 +11958,7 @@ function OhhwellsBridge() {
11833
11958
  );
11834
11959
  }
11835
11960
  }, [resolveHrefKeyElement]);
11836
- const reselectNavigationItem = (0, import_react13.useCallback)((navAnchor) => {
11961
+ const reselectNavigationItem = (0, import_react14.useCallback)((navAnchor) => {
11837
11962
  selectedElRef.current = navAnchor;
11838
11963
  selectedHrefKeyRef.current = navAnchor.getAttribute("data-ohw-href-key");
11839
11964
  selectedFooterColAttrRef.current = null;
@@ -11862,7 +11987,7 @@ function OhhwellsBridge() {
11862
11987
  setToolbarShowEditLink(false);
11863
11988
  setActiveCommands(/* @__PURE__ */ new Set());
11864
11989
  }, [markSelected]);
11865
- const commitNavigationTextEdit = (0, import_react13.useCallback)((navAnchor) => {
11990
+ const commitNavigationTextEdit = (0, import_react14.useCallback)((navAnchor) => {
11866
11991
  const el = activeElRef.current;
11867
11992
  if (!el) return;
11868
11993
  const key = el.dataset.ohwKey;
@@ -11889,7 +12014,7 @@ function OhhwellsBridge() {
11889
12014
  postToParent2({ type: "ow:exit-edit" });
11890
12015
  reselectNavigationItem(navAnchor);
11891
12016
  }, [postToParent2, reselectNavigationItem]);
11892
- const handleAddTopLevelNavItem = (0, import_react13.useCallback)(() => {
12017
+ const handleAddTopLevelNavItem = (0, import_react14.useCallback)(() => {
11893
12018
  const items = listNavbarRootItems();
11894
12019
  addNavAfterAnchorRef.current = items[items.length - 1] ?? null;
11895
12020
  deselectRef.current();
@@ -11901,7 +12026,7 @@ function OhhwellsBridge() {
11901
12026
  intent: "add-nav"
11902
12027
  });
11903
12028
  }, []);
11904
- const maybeWarnNavLinkDropdownConflict = (0, import_react13.useCallback)(
12029
+ const maybeWarnNavLinkDropdownConflict = (0, import_react14.useCallback)(
11905
12030
  (anchor) => {
11906
12031
  if (!isNavbarHrefKey(anchor.getAttribute("data-ohw-href-key"))) return;
11907
12032
  if (!navDropdownsOpenOnClick()) return;
@@ -11914,7 +12039,7 @@ function OhhwellsBridge() {
11914
12039
  },
11915
12040
  [postToParent2]
11916
12041
  );
11917
- const handleNavDropdownOpenChange = (0, import_react13.useCallback)((open) => {
12042
+ const handleNavDropdownOpenChange = (0, import_react14.useCallback)((open) => {
11918
12043
  const selected = selectedElRef.current;
11919
12044
  if (!selected || !isNavigationItem2(selected)) return;
11920
12045
  setNavGroupForceOpen(selected, open);
@@ -11926,7 +12051,7 @@ function OhhwellsBridge() {
11926
12051
  }
11927
12052
  });
11928
12053
  }, []);
11929
- const handleFooterHeadingVisibleChange = (0, import_react13.useCallback)(
12054
+ const handleFooterHeadingVisibleChange = (0, import_react14.useCallback)(
11930
12055
  (visible) => {
11931
12056
  const selected = selectedElRef.current;
11932
12057
  if (!selected || !isFooterFrameSelectionRef.current) return;
@@ -11950,7 +12075,7 @@ function OhhwellsBridge() {
11950
12075
  },
11951
12076
  [postToParent2]
11952
12077
  );
11953
- const enterEditOnNewItem = (0, import_react13.useCallback)((anchor) => {
12078
+ const enterEditOnNewItem = (0, import_react14.useCallback)((anchor) => {
11954
12079
  const label = anchor.querySelector('[data-ohw-editable="text"]');
11955
12080
  if (!label) {
11956
12081
  selectRef.current(anchor);
@@ -11959,7 +12084,7 @@ function OhhwellsBridge() {
11959
12084
  setNavGroupForceOpen(anchor, true);
11960
12085
  activateRef.current(label);
11961
12086
  }, []);
11962
- const handleAddChildItem = (0, import_react13.useCallback)(() => {
12087
+ const handleAddChildItem = (0, import_react14.useCallback)(() => {
11963
12088
  const selected = selectedElRef.current;
11964
12089
  if (!selected) return;
11965
12090
  if (toolbarVariantRef.current === "select-frame" && isFooterFrameSelection) {
@@ -12035,7 +12160,7 @@ function OhhwellsBridge() {
12035
12160
  enterEditOnNewItem(result.anchor);
12036
12161
  });
12037
12162
  }, [enterEditOnNewItem, isFooterFrameSelection, maybeWarnNavLinkDropdownConflict, postToParent2]);
12038
- const handleAddFooterColumn = (0, import_react13.useCallback)(() => {
12163
+ const handleAddFooterColumn = (0, import_react14.useCallback)(() => {
12039
12164
  if (!canAddFooterColumn()) {
12040
12165
  postToParent2({
12041
12166
  type: "ow:toast",
@@ -12056,7 +12181,7 @@ function OhhwellsBridge() {
12056
12181
  selectRef.current(result.firstLink);
12057
12182
  });
12058
12183
  }, [postToParent2]);
12059
- const clearFooterDragVisuals = (0, import_react13.useCallback)(() => {
12184
+ const clearFooterDragVisuals = (0, import_react14.useCallback)(() => {
12060
12185
  footerDragRef.current = null;
12061
12186
  setSiblingHintRects([]);
12062
12187
  setFooterDropSlots([]);
@@ -12065,7 +12190,7 @@ function OhhwellsBridge() {
12065
12190
  setIsItemDragging(false);
12066
12191
  unlockFooterDragInteraction();
12067
12192
  }, []);
12068
- const refreshFooterDragVisuals = (0, import_react13.useCallback)((session, activeSlot, clientX, clientY) => {
12193
+ const refreshFooterDragVisuals = (0, import_react14.useCallback)((session, activeSlot, clientX, clientY) => {
12069
12194
  const dragged = session.draggedEl;
12070
12195
  setDraggedItemRect(dragged.getBoundingClientRect());
12071
12196
  if (typeof clientX === "number" && typeof clientY === "number") {
@@ -12090,13 +12215,13 @@ function OhhwellsBridge() {
12090
12215
  const activeIdx = activeSlot ? slots.findIndex((s) => s.insertIndex === activeSlot.insertIndex) : -1;
12091
12216
  setActiveFooterDropIndex(activeIdx >= 0 ? activeIdx : null);
12092
12217
  }, []);
12093
- const refreshFooterDragVisualsRef = (0, import_react13.useRef)(refreshFooterDragVisuals);
12218
+ const refreshFooterDragVisualsRef = (0, import_react14.useRef)(refreshFooterDragVisuals);
12094
12219
  refreshFooterDragVisualsRef.current = refreshFooterDragVisuals;
12095
- const commitFooterDragRef = (0, import_react13.useRef)(() => {
12220
+ const commitFooterDragRef = (0, import_react14.useRef)(() => {
12096
12221
  });
12097
- const beginFooterDragRef = (0, import_react13.useRef)(() => {
12222
+ const beginFooterDragRef = (0, import_react14.useRef)(() => {
12098
12223
  });
12099
- const beginFooterDrag = (0, import_react13.useCallback)(
12224
+ const beginFooterDrag = (0, import_react14.useCallback)(
12100
12225
  (session) => {
12101
12226
  const rect = session.draggedEl.getBoundingClientRect();
12102
12227
  session.lastClientX = session.lastClientX || rect.left + rect.width / 2;
@@ -12116,7 +12241,7 @@ function OhhwellsBridge() {
12116
12241
  [refreshFooterDragVisuals]
12117
12242
  );
12118
12243
  beginFooterDragRef.current = beginFooterDrag;
12119
- const commitFooterDrag = (0, import_react13.useCallback)(
12244
+ const commitFooterDrag = (0, import_react14.useCallback)(
12120
12245
  (clientX, clientY) => {
12121
12246
  const session = footerDragRef.current;
12122
12247
  if (!session) {
@@ -12220,7 +12345,7 @@ function OhhwellsBridge() {
12220
12345
  [clearFooterDragVisuals, resolveHrefKeyElement, resyncSelectedNavigationItem]
12221
12346
  );
12222
12347
  commitFooterDragRef.current = commitFooterDrag;
12223
- const startFooterLinkDrag = (0, import_react13.useCallback)(
12348
+ const startFooterLinkDrag = (0, import_react14.useCallback)(
12224
12349
  (anchor, clientX, clientY, wasSelected) => {
12225
12350
  const hrefKey = anchor.getAttribute("data-ohw-href-key");
12226
12351
  if (!hrefKey || !isFooterHrefKey(hrefKey)) return false;
@@ -12241,7 +12366,7 @@ function OhhwellsBridge() {
12241
12366
  },
12242
12367
  [beginFooterDrag]
12243
12368
  );
12244
- const startFooterColumnDrag = (0, import_react13.useCallback)(
12369
+ const startFooterColumnDrag = (0, import_react14.useCallback)(
12245
12370
  (columnEl, clientX, clientY, wasSelected) => {
12246
12371
  const columns = listFooterColumns();
12247
12372
  const idx = columns.indexOf(columnEl);
@@ -12261,7 +12386,7 @@ function OhhwellsBridge() {
12261
12386
  },
12262
12387
  [beginFooterDrag]
12263
12388
  );
12264
- const handleItemDragStart = (0, import_react13.useCallback)(
12389
+ const handleItemDragStart = (0, import_react14.useCallback)(
12265
12390
  (e) => {
12266
12391
  const selected = selectedElRef.current;
12267
12392
  if (!selected) {
@@ -12281,7 +12406,7 @@ function OhhwellsBridge() {
12281
12406
  },
12282
12407
  [startFooterColumnDrag, startFooterLinkDrag, startNavLinkDrag]
12283
12408
  );
12284
- const handleItemDragEnd = (0, import_react13.useCallback)(
12409
+ const handleItemDragEnd = (0, import_react14.useCallback)(
12285
12410
  (e) => {
12286
12411
  if (footerDragRef.current) {
12287
12412
  const x = e?.clientX;
@@ -12307,7 +12432,7 @@ function OhhwellsBridge() {
12307
12432
  },
12308
12433
  [commitFooterDrag, commitNavDrag, navDragRef]
12309
12434
  );
12310
- const handleItemChromePointerDown = (0, import_react13.useCallback)((e) => {
12435
+ const handleItemChromePointerDown = (0, import_react14.useCallback)((e) => {
12311
12436
  if (e.button !== 0) return;
12312
12437
  const selected = selectedElRef.current;
12313
12438
  if (!selected) return;
@@ -12338,7 +12463,7 @@ function OhhwellsBridge() {
12338
12463
  }
12339
12464
  if (armNavPressFromChrome(selected, e.clientX, e.clientY, e.pointerId)) return;
12340
12465
  }, [armNavPressFromChrome]);
12341
- const handleItemChromeClick = (0, import_react13.useCallback)((clientX, clientY) => {
12466
+ const handleItemChromeClick = (0, import_react14.useCallback)((clientX, clientY) => {
12342
12467
  if (suppressNextClickRef.current || Date.now() < suppressClickUntilRef.current) {
12343
12468
  suppressNextClickRef.current = false;
12344
12469
  return;
@@ -12351,7 +12476,7 @@ function OhhwellsBridge() {
12351
12476
  }, []);
12352
12477
  reselectNavigationItemRef.current = reselectNavigationItem;
12353
12478
  commitNavigationTextEditRef.current = commitNavigationTextEdit;
12354
- const select = (0, import_react13.useCallback)((anchor) => {
12479
+ const select = (0, import_react14.useCallback)((anchor) => {
12355
12480
  if (!isNavigationItem2(anchor)) return;
12356
12481
  if (activeElRef.current) deactivate();
12357
12482
  aiSectionApiRef.current?.selectFromElement(anchor);
@@ -12390,7 +12515,7 @@ function OhhwellsBridge() {
12390
12515
  setToolbarShowEditLink(false);
12391
12516
  setActiveCommands(/* @__PURE__ */ new Set());
12392
12517
  }, [deactivate, markSelected]);
12393
- const selectFrame = (0, import_react13.useCallback)((el) => {
12518
+ const selectFrame = (0, import_react14.useCallback)((el) => {
12394
12519
  if (!isNavigationContainer(el)) return;
12395
12520
  if (activeElRef.current) deactivate();
12396
12521
  aiSectionApiRef.current?.selectFromElement(el);
@@ -12437,7 +12562,7 @@ function OhhwellsBridge() {
12437
12562
  setToolbarShowEditLink(false);
12438
12563
  setActiveCommands(/* @__PURE__ */ new Set());
12439
12564
  }, [deactivate, markSelected, postToParent2]);
12440
- const activate = (0, import_react13.useCallback)((el, options) => {
12565
+ const activate = (0, import_react14.useCallback)((el, options) => {
12441
12566
  if (activeElRef.current === el) return;
12442
12567
  clearSelectedAttr();
12443
12568
  selectedElRef.current = null;
@@ -12514,8 +12639,8 @@ function OhhwellsBridge() {
12514
12639
  selectRef.current = select;
12515
12640
  selectFrameRef.current = selectFrame;
12516
12641
  deselectRef.current = deselect;
12517
- const lastSiteWideScopeRef = (0, import_react13.useRef)(null);
12518
- (0, import_react13.useEffect)(() => {
12642
+ const lastSiteWideScopeRef = (0, import_react14.useRef)(null);
12643
+ (0, import_react14.useEffect)(() => {
12519
12644
  if (!isEditMode) {
12520
12645
  if (lastSiteWideScopeRef.current !== false) {
12521
12646
  lastSiteWideScopeRef.current = false;
@@ -12541,7 +12666,7 @@ function OhhwellsBridge() {
12541
12666
  isFooterFrameSelection,
12542
12667
  postToParent2
12543
12668
  ]);
12544
- (0, import_react13.useLayoutEffect)(() => {
12669
+ (0, import_react14.useLayoutEffect)(() => {
12545
12670
  if (!subdomain || isEditMode) {
12546
12671
  setFetchState("done");
12547
12672
  return;
@@ -12612,7 +12737,7 @@ function OhhwellsBridge() {
12612
12737
  cancelled = true;
12613
12738
  };
12614
12739
  }, [subdomain, isEditMode]);
12615
- (0, import_react13.useEffect)(() => {
12740
+ (0, import_react14.useEffect)(() => {
12616
12741
  if (!subdomain || isEditMode) return;
12617
12742
  let debounceTimer = null;
12618
12743
  let observer = null;
@@ -12663,16 +12788,16 @@ function OhhwellsBridge() {
12663
12788
  if (debounceTimer) clearTimeout(debounceTimer);
12664
12789
  };
12665
12790
  }, [subdomain, isEditMode, pathname]);
12666
- (0, import_react13.useLayoutEffect)(() => {
12791
+ (0, import_react14.useLayoutEffect)(() => {
12667
12792
  const el = document.getElementById("ohw-loader");
12668
12793
  if (!el) return;
12669
12794
  const visible = Boolean(subdomain) && fetchState !== "done";
12670
12795
  el.style.display = visible ? "flex" : "none";
12671
12796
  }, [subdomain, fetchState]);
12672
- (0, import_react13.useEffect)(() => {
12797
+ (0, import_react14.useEffect)(() => {
12673
12798
  postToParent2({ type: "ow:navigation", path: pathname });
12674
12799
  }, [pathname, postToParent2]);
12675
- (0, import_react13.useEffect)(() => {
12800
+ (0, import_react14.useEffect)(() => {
12676
12801
  if (!isEditMode) return;
12677
12802
  if (linkPopoverSessionRef.current?.intent === "add-nav") return;
12678
12803
  if (document.querySelector("[data-ohw-section-picker]")) return;
@@ -12680,7 +12805,7 @@ function OhhwellsBridge() {
12680
12805
  deselectRef.current();
12681
12806
  deactivateRef.current();
12682
12807
  }, [pathname, isEditMode]);
12683
- (0, import_react13.useEffect)(() => {
12808
+ (0, import_react14.useEffect)(() => {
12684
12809
  const contentForNav = () => {
12685
12810
  if (isEditMode) return editContentRef.current;
12686
12811
  if (!subdomain) return {};
@@ -12745,7 +12870,7 @@ function OhhwellsBridge() {
12745
12870
  observer?.disconnect();
12746
12871
  };
12747
12872
  }, [isEditMode, pathname, subdomain, fetchState, resyncSelectedNavigationItem]);
12748
- (0, import_react13.useEffect)(() => {
12873
+ (0, import_react14.useEffect)(() => {
12749
12874
  if (!isEditMode) return;
12750
12875
  const measure = () => {
12751
12876
  const h = document.body.scrollHeight;
@@ -12769,7 +12894,7 @@ function OhhwellsBridge() {
12769
12894
  window.removeEventListener("resize", handleResize);
12770
12895
  };
12771
12896
  }, [pathname, isEditMode, postToParent2]);
12772
- (0, import_react13.useEffect)(() => {
12897
+ (0, import_react14.useEffect)(() => {
12773
12898
  if (!subdomainFromQuery || isEditMode) return;
12774
12899
  const handleClick = (e) => {
12775
12900
  const anchor = e.target.closest("a");
@@ -12785,7 +12910,7 @@ function OhhwellsBridge() {
12785
12910
  document.addEventListener("click", handleClick, true);
12786
12911
  return () => document.removeEventListener("click", handleClick, true);
12787
12912
  }, [subdomainFromQuery, isEditMode, router]);
12788
- (0, import_react13.useEffect)(() => {
12913
+ (0, import_react14.useEffect)(() => {
12789
12914
  if (!isEditMode) {
12790
12915
  editStylesRef.current?.base.remove();
12791
12916
  editStylesRef.current?.forceHover.remove();
@@ -14042,6 +14167,7 @@ function OhhwellsBridge() {
14042
14167
  continue;
14043
14168
  }
14044
14169
  if (key === LOGO_PLACEHOLDER_KEY) continue;
14170
+ if (LOGO_IMAGE_KEYS.includes(key) && !String(val ?? "").trim()) continue;
14045
14171
  if (applyVideoSettingNode(key, val)) continue;
14046
14172
  if (applyCarouselNode(key, val)) continue;
14047
14173
  document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
@@ -14061,11 +14187,27 @@ function OhhwellsBridge() {
14061
14187
  });
14062
14188
  applyLinkByKey(key, val);
14063
14189
  }
14064
- const hasLogoIdentity = LOGO_PLACEHOLDER_KEY in content || LOGO_TEXT_KEYS.some((key) => key in content);
14190
+ const hasLogoIdentity = LOGO_PLACEHOLDER_KEY in content || LOGO_TEXT_KEYS.some((key) => key in content) || LOGO_IMAGE_KEYS.some((key) => key in content) || LOGO_ALT_KEY in content || LOGO_HREF_KEYS.some((key) => key in content);
14065
14191
  if (hasLogoIdentity) {
14066
14192
  const logoText = content[LOGO_TEXT_KEYS[0]] ?? content[LOGO_TEXT_KEYS[1]] ?? readLogoIdentityFromDom().text;
14067
- const logoIsPlaceholder = LOGO_PLACEHOLDER_KEY in content ? content[LOGO_PLACEHOLDER_KEY] !== "false" : !logoText.trim() || logoText === PLACEHOLDER_BUSINESS_NAME;
14068
- applyLogoIdentity(logoText, logoIsPlaceholder);
14193
+ const logoAlt = content[LOGO_ALT_KEY] ?? logoText;
14194
+ const rawLogoImage = content[LOGO_IMAGE_URL_KEY] ?? content["footer-logo"] ?? content["footer-logo-image"] ?? null;
14195
+ const logoImageUrl = typeof rawLogoImage === "string" && rawLogoImage.trim() ? rawLogoImage.trim() : null;
14196
+ const imageExplicitlyCleared = LOGO_IMAGE_KEYS.some((key) => key in content) && !logoImageUrl;
14197
+ const logoIsPlaceholder = LOGO_PLACEHOLDER_KEY in content ? content[LOGO_PLACEHOLDER_KEY] !== "false" : !logoImageUrl && (!logoText.trim() || logoText === PLACEHOLDER_BUSINESS_NAME);
14198
+ if (logoImageUrl) {
14199
+ applyLogoImage(logoImageUrl, logoAlt);
14200
+ } else {
14201
+ if (imageExplicitlyCleared) applyLogoImage(null, logoAlt);
14202
+ applyLogoIdentity(logoText, logoIsPlaceholder);
14203
+ }
14204
+ const logoHref = content["nav-logo-href"] ?? content["footer-logo-href"] ?? content["logo-href"];
14205
+ if (typeof logoHref === "string" && logoHref.trim()) {
14206
+ applyLogoHref(logoHref);
14207
+ applyLinkByKey("nav-logo-href", logoHref);
14208
+ applyLinkByKey("footer-logo-href", logoHref);
14209
+ applyLinkByKey("logo-href", logoHref);
14210
+ }
14069
14211
  }
14070
14212
  if (sectionsJson) {
14071
14213
  initSectionsFromContent({ __ohw_sections: sectionsJson }, true);
@@ -14082,12 +14224,48 @@ function OhhwellsBridge() {
14082
14224
  const handleUpdateLogoIdentity = (e) => {
14083
14225
  if (e.data?.type !== "ow:update-logo-identity") return;
14084
14226
  const rawText = typeof e.data.text === "string" ? e.data.text : "";
14085
- const isPlaceholder = e.data.isPlaceholder !== false;
14227
+ const alt = typeof e.data.alt === "string" ? e.data.alt : rawText;
14228
+ const href = typeof e.data.href === "string" ? e.data.href : void 0;
14229
+ const imageProvided = "image" in e.data;
14230
+ const imageUrl = imageProvided && typeof e.data.image === "string" && e.data.image.trim() ? e.data.image.trim() : imageProvided ? null : void 0;
14231
+ let isPlaceholder = e.data.isPlaceholder !== false;
14232
+ if (imageUrl) isPlaceholder = false;
14233
+ else if (imageProvided && imageUrl === null) {
14234
+ isPlaceholder = e.data.isPlaceholder === true || !rawText.trim() || resolveLogoDisplayText(rawText) === PLACEHOLDER_BUSINESS_NAME;
14235
+ }
14086
14236
  const display = applyLogoIdentity(rawText, isPlaceholder);
14237
+ const displayAlt = resolveLogoDisplayText(alt || display);
14238
+ if (imageUrl !== void 0) {
14239
+ applyLogoImage(imageUrl, displayAlt);
14240
+ } else {
14241
+ for (const key of LOGO_IMAGE_KEYS) {
14242
+ document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
14243
+ const img = el instanceof HTMLImageElement ? el : el.querySelector("img");
14244
+ if (img) img.alt = displayAlt;
14245
+ });
14246
+ }
14247
+ }
14248
+ if (href !== void 0) {
14249
+ applyLogoHref(href);
14250
+ applyLinkByKey("nav-logo-href", href);
14251
+ applyLinkByKey("footer-logo-href", href);
14252
+ applyLinkByKey("logo-href", href);
14253
+ }
14087
14254
  const nodes = [
14088
14255
  ...LOGO_TEXT_KEYS.map((key) => ({ key, text: display })),
14089
- { key: LOGO_PLACEHOLDER_KEY, text: isPlaceholder || !rawText.trim() ? "true" : "false" }
14256
+ { key: LOGO_PLACEHOLDER_KEY, text: isPlaceholder ? "true" : "false" },
14257
+ { key: LOGO_ALT_KEY, text: displayAlt }
14090
14258
  ];
14259
+ if (imageUrl !== void 0) {
14260
+ if (imageUrl) {
14261
+ for (const key of LOGO_IMAGE_KEYS) nodes.push({ key, text: imageUrl });
14262
+ } else {
14263
+ for (const key of LOGO_IMAGE_KEYS) nodes.push({ key, text: "" });
14264
+ }
14265
+ }
14266
+ if (href !== void 0) {
14267
+ for (const key of LOGO_HREF_KEYS) nodes.push({ key, text: href.trim() || "/" });
14268
+ }
14091
14269
  editContentRef.current = {
14092
14270
  ...editContentRef.current,
14093
14271
  ...Object.fromEntries(nodes.map(({ key, text }) => [key, text]))
@@ -14695,7 +14873,7 @@ function OhhwellsBridge() {
14695
14873
  if (imageShowTimerRef.current) clearTimeout(imageShowTimerRef.current);
14696
14874
  };
14697
14875
  }, [isEditMode, refreshStateRules]);
14698
- (0, import_react13.useEffect)(() => {
14876
+ (0, import_react14.useEffect)(() => {
14699
14877
  if (!isEditMode) return;
14700
14878
  const THRESHOLD = 10;
14701
14879
  const resolveWasSelected = (el) => {
@@ -14849,7 +15027,7 @@ function OhhwellsBridge() {
14849
15027
  unlockFooterDragInteraction();
14850
15028
  };
14851
15029
  }, [isEditMode]);
14852
- (0, import_react13.useEffect)(() => {
15030
+ (0, import_react14.useEffect)(() => {
14853
15031
  const handler = (e) => {
14854
15032
  if (e.data?.type !== "ow:request-schedule-config") return;
14855
15033
  const insertAfterVal = e.data.insertAfter;
@@ -14865,7 +15043,7 @@ function OhhwellsBridge() {
14865
15043
  window.addEventListener("message", handler);
14866
15044
  return () => window.removeEventListener("message", handler);
14867
15045
  }, [processConfigRequest]);
14868
- (0, import_react13.useEffect)(() => {
15046
+ (0, import_react14.useEffect)(() => {
14869
15047
  if (!isEditMode) return;
14870
15048
  document.querySelectorAll("[data-ohw-active-state]").forEach((el) => {
14871
15049
  el.removeAttribute("data-ohw-active-state");
@@ -14901,13 +15079,13 @@ function OhhwellsBridge() {
14901
15079
  clearTimeout(timer);
14902
15080
  };
14903
15081
  }, [pathname, isEditMode, refreshStateRules, postToParent2]);
14904
- (0, import_react13.useEffect)(() => {
15082
+ (0, import_react14.useEffect)(() => {
14905
15083
  scrollToHashSectionWhenReady();
14906
15084
  const onHashChange = () => scrollToHashSectionWhenReady();
14907
15085
  window.addEventListener("hashchange", onHashChange);
14908
15086
  return () => window.removeEventListener("hashchange", onHashChange);
14909
15087
  }, [pathname]);
14910
- const handleCommand = (0, import_react13.useCallback)((cmd) => {
15088
+ const handleCommand = (0, import_react14.useCallback)((cmd) => {
14911
15089
  const el = activeElRef.current;
14912
15090
  const selBefore = window.getSelection();
14913
15091
  let savedOffsets = null;
@@ -14943,7 +15121,7 @@ function OhhwellsBridge() {
14943
15121
  if (el) setToolbarRect(getEditMeasureEl(el).getBoundingClientRect());
14944
15122
  refreshActiveCommandsRef.current();
14945
15123
  }, []);
14946
- const handleStateChange = (0, import_react13.useCallback)((state) => {
15124
+ const handleStateChange = (0, import_react14.useCallback)((state) => {
14947
15125
  if (!activeStateElRef.current) return;
14948
15126
  const el = activeStateElRef.current;
14949
15127
  if (state === "Default") {
@@ -14956,7 +15134,7 @@ function OhhwellsBridge() {
14956
15134
  }
14957
15135
  setToggleState((prev) => prev ? { ...prev, activeState: state } : null);
14958
15136
  }, [deactivate]);
14959
- const reselectAfterLinkPopover = (0, import_react13.useCallback)(
15137
+ const reselectAfterLinkPopover = (0, import_react14.useCallback)(
14960
15138
  (hrefKey) => {
14961
15139
  requestAnimationFrame(() => {
14962
15140
  const el = resolveHrefKeyElement(hrefKey);
@@ -14965,7 +15143,7 @@ function OhhwellsBridge() {
14965
15143
  },
14966
15144
  [resolveHrefKeyElement]
14967
15145
  );
14968
- const closeLinkPopover = (0, import_react13.useCallback)(() => {
15146
+ const closeLinkPopover = (0, import_react14.useCallback)(() => {
14969
15147
  const session = linkPopoverSessionRef.current;
14970
15148
  addNavAfterAnchorRef.current = null;
14971
15149
  setLinkPopover(null);
@@ -14973,9 +15151,9 @@ function OhhwellsBridge() {
14973
15151
  reselectAfterLinkPopover(session.key);
14974
15152
  }
14975
15153
  }, [reselectAfterLinkPopover]);
14976
- const closeLinkPopoverRef = (0, import_react13.useRef)(closeLinkPopover);
15154
+ const closeLinkPopoverRef = (0, import_react14.useRef)(closeLinkPopover);
14977
15155
  closeLinkPopoverRef.current = closeLinkPopover;
14978
- const openLinkPopoverForActive = (0, import_react13.useCallback)(() => {
15156
+ const openLinkPopoverForActive = (0, import_react14.useCallback)(() => {
14979
15157
  const hrefCtx = getHrefKeyFromElement(activeElRef.current);
14980
15158
  if (!hrefCtx) return;
14981
15159
  bumpLinkPopoverGrace();
@@ -14986,7 +15164,7 @@ function OhhwellsBridge() {
14986
15164
  });
14987
15165
  deactivate();
14988
15166
  }, [deactivate]);
14989
- const openLinkPopoverForSelected = (0, import_react13.useCallback)(() => {
15167
+ const openLinkPopoverForSelected = (0, import_react14.useCallback)(() => {
14990
15168
  const anchor = selectedElRef.current;
14991
15169
  if (!anchor) return;
14992
15170
  const key = anchor.getAttribute("data-ohw-href-key");
@@ -14999,7 +15177,7 @@ function OhhwellsBridge() {
14999
15177
  });
15000
15178
  deselect();
15001
15179
  }, [deselect]);
15002
- const handleSelectParent = (0, import_react13.useCallback)(() => {
15180
+ const handleSelectParent = (0, import_react14.useCallback)(() => {
15003
15181
  const selected = selectedElRef.current;
15004
15182
  if (!selected) return;
15005
15183
  if (toolbarVariantRef.current === "select-frame") {
@@ -15026,7 +15204,7 @@ function OhhwellsBridge() {
15026
15204
  }
15027
15205
  deselectRef.current();
15028
15206
  }, []);
15029
- const handleDuplicateSelected = (0, import_react13.useCallback)(() => {
15207
+ const handleDuplicateSelected = (0, import_react14.useCallback)(() => {
15030
15208
  const selected = selectedElRef.current;
15031
15209
  if (!selected || !isNavigationItem2(selected)) return;
15032
15210
  const hrefKey = selected.getAttribute("data-ohw-href-key");
@@ -15116,7 +15294,7 @@ function OhhwellsBridge() {
15116
15294
  });
15117
15295
  }
15118
15296
  }, [postToParent2]);
15119
- const runPendingDeleteUndo = (0, import_react13.useCallback)(() => {
15297
+ const runPendingDeleteUndo = (0, import_react14.useCallback)(() => {
15120
15298
  const pending = pendingDeleteUndoRef.current;
15121
15299
  if (!pending) return false;
15122
15300
  pendingDeleteUndoRef.current = null;
@@ -15124,7 +15302,7 @@ function OhhwellsBridge() {
15124
15302
  enforceLinkHrefs();
15125
15303
  return true;
15126
15304
  }, []);
15127
- const handleDeleteSelected = (0, import_react13.useCallback)(() => {
15305
+ const handleDeleteSelected = (0, import_react14.useCallback)(() => {
15128
15306
  const selected = selectedElRef.current;
15129
15307
  if (!selected) return false;
15130
15308
  return deleteSelectedNavFooterItem({
@@ -15145,7 +15323,7 @@ function OhhwellsBridge() {
15145
15323
  }, [postToParent2]);
15146
15324
  handleDeleteSelectedRef.current = handleDeleteSelected;
15147
15325
  runPendingDeleteUndoRef.current = runPendingDeleteUndo;
15148
- const handleLinkPopoverSubmit = (0, import_react13.useCallback)(
15326
+ const handleLinkPopoverSubmit = (0, import_react14.useCallback)(
15149
15327
  (target) => {
15150
15328
  const session = linkPopoverSessionRef.current;
15151
15329
  if (!session) return;
@@ -15211,19 +15389,19 @@ function OhhwellsBridge() {
15211
15389
  const showEditLink = toolbarShowEditLink;
15212
15390
  const currentSections = sectionsByPath[pathname] ?? [];
15213
15391
  linkPopoverOpenRef.current = linkPopover !== null;
15214
- const handleMediaReplace = (0, import_react13.useCallback)(
15392
+ const handleMediaReplace = (0, import_react14.useCallback)(
15215
15393
  (key) => {
15216
15394
  postToParent2({ type: "ow:image-pick", key, elementType: mediaHover?.elementType ?? "image" });
15217
15395
  },
15218
15396
  [postToParent2, mediaHover?.elementType]
15219
15397
  );
15220
- const handleEditCarousel = (0, import_react13.useCallback)(
15398
+ const handleEditCarousel = (0, import_react14.useCallback)(
15221
15399
  (key) => {
15222
15400
  postToParent2({ type: "ow:carousel-open", key, images: readCarouselValue(key) });
15223
15401
  },
15224
15402
  [postToParent2]
15225
15403
  );
15226
- const handleMediaFadeOutComplete = (0, import_react13.useCallback)((key) => {
15404
+ const handleMediaFadeOutComplete = (0, import_react14.useCallback)((key) => {
15227
15405
  setUploadingRects((prev) => {
15228
15406
  if (!(key in prev)) return prev;
15229
15407
  const next = { ...prev };
@@ -15231,7 +15409,7 @@ function OhhwellsBridge() {
15231
15409
  return next;
15232
15410
  });
15233
15411
  }, []);
15234
- const handleVideoSettingsChange = (0, import_react13.useCallback)(
15412
+ const handleVideoSettingsChange = (0, import_react14.useCallback)(
15235
15413
  (key, settings) => {
15236
15414
  document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
15237
15415
  const video = getVideoEl2(el);