@ohhwells/bridge 0.1.46 → 0.1.48-next.113
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/README.md +12 -0
- package/dist/index.cjs +1162 -385
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +22 -1
- package/dist/index.d.ts +22 -1
- package/dist/index.js +1109 -333
- package/dist/index.js.map +1 -1
- package/dist/styles.css +24 -18
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -57,12 +57,13 @@ __export(index_exports, {
|
|
|
57
57
|
isValidUrl: () => isValidUrl,
|
|
58
58
|
parseTarget: () => parseTarget,
|
|
59
59
|
toggleVariants: () => toggleVariants,
|
|
60
|
+
useOhwCarousel: () => useOhwCarousel,
|
|
60
61
|
validateUrlInput: () => validateUrlInput
|
|
61
62
|
});
|
|
62
63
|
module.exports = __toCommonJS(index_exports);
|
|
63
64
|
|
|
64
65
|
// src/OhhwellsBridge.tsx
|
|
65
|
-
var
|
|
66
|
+
var import_react10 = __toESM(require("react"), 1);
|
|
66
67
|
var import_client = require("react-dom/client");
|
|
67
68
|
var import_react_dom2 = require("react-dom");
|
|
68
69
|
|
|
@@ -115,6 +116,7 @@ var import_react3 = require("react");
|
|
|
115
116
|
var import_react2 = require("react");
|
|
116
117
|
var import_radix_ui = require("radix-ui");
|
|
117
118
|
var import_jsx_runtime = require("react/jsx-runtime");
|
|
119
|
+
var isValidEmail = (value) => /^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(value);
|
|
118
120
|
function Spinner() {
|
|
119
121
|
return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
|
|
120
122
|
"svg",
|
|
@@ -148,12 +150,17 @@ function EmailCaptureModal({ title, subtitle, onSubmit, onClose }) {
|
|
|
148
150
|
const [error, setError] = (0, import_react2.useState)(null);
|
|
149
151
|
const isBook = title === "Confirm your spot";
|
|
150
152
|
const handleSubmit = async () => {
|
|
151
|
-
|
|
153
|
+
const trimmed = email.trim();
|
|
154
|
+
if (!trimmed) return;
|
|
155
|
+
if (!isValidEmail(trimmed)) {
|
|
156
|
+
setError("Please enter a valid email address.");
|
|
157
|
+
return;
|
|
158
|
+
}
|
|
152
159
|
setLoading(true);
|
|
153
160
|
setError(null);
|
|
154
161
|
try {
|
|
155
|
-
await onSubmit(
|
|
156
|
-
setSubmittedEmail(
|
|
162
|
+
await onSubmit(trimmed);
|
|
163
|
+
setSubmittedEmail(trimmed);
|
|
157
164
|
setSuccess(true);
|
|
158
165
|
} catch (e) {
|
|
159
166
|
setError(e instanceof Error ? e.message : "Something went wrong. Please try again.");
|
|
@@ -228,7 +235,10 @@ function EmailCaptureModal({ title, subtitle, onSubmit, onClose }) {
|
|
|
228
235
|
{
|
|
229
236
|
type: "email",
|
|
230
237
|
value: email,
|
|
231
|
-
onChange: (e) =>
|
|
238
|
+
onChange: (e) => {
|
|
239
|
+
setEmail(e.target.value);
|
|
240
|
+
if (error) setError(null);
|
|
241
|
+
},
|
|
232
242
|
onKeyDown: handleKeyDown,
|
|
233
243
|
placeholder: "hello@gmail.com",
|
|
234
244
|
autoFocus: true,
|
|
@@ -285,12 +295,20 @@ function formatClassTime(cls) {
|
|
|
285
295
|
const em = endTotal % 60;
|
|
286
296
|
return `${h}:${cls.startTime.minutes}-${eh}:${String(em).padStart(2, "0")}`;
|
|
287
297
|
}
|
|
298
|
+
function formatBookingLabel(cls) {
|
|
299
|
+
const price = cls.price;
|
|
300
|
+
const isFree = price === null || price === void 0 || `${price}` === "" || `${price}` === "0";
|
|
301
|
+
return isFree ? "Book for free" : `Book for ${cls.currency ?? ""} ${price}`.trim();
|
|
302
|
+
}
|
|
288
303
|
function getBookingsOnDate(cls, date) {
|
|
289
304
|
if (!cls.bookings?.length) return 0;
|
|
290
|
-
const
|
|
305
|
+
const target = new Date(date);
|
|
306
|
+
target.setHours(0, 0, 0, 0);
|
|
291
307
|
return cls.bookings.filter((b) => {
|
|
292
308
|
try {
|
|
293
|
-
|
|
309
|
+
const bookingDate = new Date(b.classDate);
|
|
310
|
+
bookingDate.setHours(0, 0, 0, 0);
|
|
311
|
+
return bookingDate.getTime() === target.getTime();
|
|
294
312
|
} catch {
|
|
295
313
|
return false;
|
|
296
314
|
}
|
|
@@ -555,7 +573,7 @@ function ScheduleView({ schedule, dates, selectedIdx, onSelectDate, onOpenModal
|
|
|
555
573
|
}
|
|
556
574
|
)
|
|
557
575
|
] }),
|
|
558
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("div", { className: "sm:hidden flex flex-col gap-px", children: isFull ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-sm text-(--color-dark,#200C02) opacity-80", children: "Full" }) : /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(import_jsx_runtime2.Fragment, { children: [
|
|
576
|
+
cls.showAvailability !== false && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("div", { className: "sm:hidden flex flex-col gap-px", children: isFull ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-sm text-(--color-dark,#200C02) opacity-80", children: "Full" }) : /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(import_jsx_runtime2.Fragment, { children: [
|
|
559
577
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("span", { className: "font-body text-sm text-(--color-dark,#200C02) opacity-80", children: [
|
|
560
578
|
available,
|
|
561
579
|
"/",
|
|
@@ -567,9 +585,17 @@ function ScheduleView({ schedule, dates, selectedIdx, onSelectDate, onOpenModal
|
|
|
567
585
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { className: "flex flex-1 flex-col gap-2 min-w-0 sm:contents", children: [
|
|
568
586
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { className: "flex-1 flex flex-col gap-2 min-w-0", children: [
|
|
569
587
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-base font-bold text-(--color-dark,#200C02) block truncate", children: cls.name }),
|
|
570
|
-
cls.hostName && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-base font-normal text-(--color-dark,#200C02) opacity-80 block truncate", children: cls.hostName })
|
|
588
|
+
cls.hostName && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-base font-normal text-(--color-dark,#200C02) opacity-80 block truncate", children: cls.hostName }),
|
|
589
|
+
cls.description && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
|
|
590
|
+
"span",
|
|
591
|
+
{
|
|
592
|
+
className: "font-body text-base font-normal text-(--color-dark,#200C02) opacity-80 block",
|
|
593
|
+
style: { wordBreak: "break-word" },
|
|
594
|
+
children: cls.description
|
|
595
|
+
}
|
|
596
|
+
)
|
|
571
597
|
] }),
|
|
572
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("div", { className: "hidden sm:flex w-14 shrink-0 flex-col gap-px", children: isFull ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-sm text-(--color-dark,#200C02) opacity-80", children: "Full" }) : /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(import_jsx_runtime2.Fragment, { children: [
|
|
598
|
+
cls.showAvailability !== false && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("div", { className: "hidden sm:flex w-14 shrink-0 flex-col gap-px", children: isFull ? /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "font-body text-sm text-(--color-dark,#200C02) opacity-80", children: "Full" }) : /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(import_jsx_runtime2.Fragment, { children: [
|
|
573
599
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("span", { className: "font-body text-sm text-(--color-dark,#200C02) opacity-80", children: [
|
|
574
600
|
available,
|
|
575
601
|
"/",
|
|
@@ -594,7 +620,7 @@ function ScheduleView({ schedule, dates, selectedIdx, onSelectDate, onOpenModal
|
|
|
594
620
|
if (!cls.id) return;
|
|
595
621
|
onOpenModal?.(isFull ? "waitlist" : "book", cls.id, selectedDate);
|
|
596
622
|
},
|
|
597
|
-
children: isFull ? "Join Waitlist" :
|
|
623
|
+
children: isFull ? "Join Waitlist" : formatBookingLabel(cls)
|
|
598
624
|
}
|
|
599
625
|
)
|
|
600
626
|
] })
|
|
@@ -636,6 +662,17 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
|
|
|
636
662
|
const [isHovered, setIsHovered] = (0, import_react3.useState)(false);
|
|
637
663
|
const [modalState, setModalState] = (0, import_react3.useState)(null);
|
|
638
664
|
const switchScheduleIdRef = (0, import_react3.useRef)(null);
|
|
665
|
+
const liveScheduleIdRef = (0, import_react3.useRef)(null);
|
|
666
|
+
const refetchLiveSchedule = (0, import_react3.useCallback)(async () => {
|
|
667
|
+
const id = liveScheduleIdRef.current;
|
|
668
|
+
if (!id) return;
|
|
669
|
+
try {
|
|
670
|
+
const res = await fetch(`${API_URL}/api/schedule/id/${id}`);
|
|
671
|
+
const data = await res.json();
|
|
672
|
+
if (data?.id) setSchedule(data);
|
|
673
|
+
} catch {
|
|
674
|
+
}
|
|
675
|
+
}, []);
|
|
639
676
|
const dates = (0, import_react3.useMemo)(() => {
|
|
640
677
|
const today = /* @__PURE__ */ new Date();
|
|
641
678
|
today.setHours(0, 0, 0, 0);
|
|
@@ -655,6 +692,18 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
|
|
|
655
692
|
}
|
|
656
693
|
}
|
|
657
694
|
}, [schedule, dates]);
|
|
695
|
+
(0, import_react3.useEffect)(() => {
|
|
696
|
+
if (typeof window === "undefined") return;
|
|
697
|
+
const onVisible = () => {
|
|
698
|
+
if (!document.hidden) void refetchLiveSchedule();
|
|
699
|
+
};
|
|
700
|
+
window.addEventListener("focus", refetchLiveSchedule);
|
|
701
|
+
document.addEventListener("visibilitychange", onVisible);
|
|
702
|
+
return () => {
|
|
703
|
+
window.removeEventListener("focus", refetchLiveSchedule);
|
|
704
|
+
document.removeEventListener("visibilitychange", onVisible);
|
|
705
|
+
};
|
|
706
|
+
}, [refetchLiveSchedule]);
|
|
658
707
|
(0, import_react3.useEffect)(() => {
|
|
659
708
|
if (typeof window === "undefined") return;
|
|
660
709
|
const isInEditor = window.self !== window.top;
|
|
@@ -716,7 +765,7 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
|
|
|
716
765
|
setLoading(false);
|
|
717
766
|
return;
|
|
718
767
|
}
|
|
719
|
-
;
|
|
768
|
+
liveScheduleIdRef.current = effectiveId;
|
|
720
769
|
(async () => {
|
|
721
770
|
try {
|
|
722
771
|
const res = await fetch(`${API_URL}/api/schedule/id/${effectiveId}`);
|
|
@@ -773,18 +822,14 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
|
|
|
773
822
|
const data = await res.json().catch(() => ({}));
|
|
774
823
|
throw new Error(data?.message ?? "Something went wrong. Please try again.");
|
|
775
824
|
}
|
|
825
|
+
await refetchLiveSchedule();
|
|
776
826
|
};
|
|
777
827
|
const handleReplaceSchedule = () => {
|
|
778
828
|
setIsHovered(false);
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
insertAfter
|
|
784
|
-
}, "*");
|
|
785
|
-
} else {
|
|
786
|
-
window.parent.postMessage({ type: "ow:scheduling-not-connected", insertAfter }, "*");
|
|
787
|
-
}
|
|
829
|
+
window.parent.postMessage(
|
|
830
|
+
{ type: "ow:scheduling-not-connected", insertAfter, currentScheduleId: schedule?.id },
|
|
831
|
+
"*"
|
|
832
|
+
);
|
|
788
833
|
};
|
|
789
834
|
if (!inEditor && !loading && !schedule) return null;
|
|
790
835
|
const sectionId = `scheduling-${insertAfter}`;
|
|
@@ -827,7 +872,19 @@ function SchedulingWidget({ notifyOnConnect = false, initialScheduleId, insertAf
|
|
|
827
872
|
),
|
|
828
873
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { className: "max-w-[1280px] mx-auto flex flex-col items-center gap-16", children: [
|
|
829
874
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { className: "flex flex-col items-center gap-4", children: [
|
|
830
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
|
|
875
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
|
|
876
|
+
"h2",
|
|
877
|
+
{
|
|
878
|
+
className: "font-display text-center m-0 text-(--color-dark,#200C02)",
|
|
879
|
+
style: {
|
|
880
|
+
fontSize: "var(--fs-section-h2, clamp(40px, 4.4vw, 64px))",
|
|
881
|
+
fontWeight: "var(--font-weight-heading, 400)",
|
|
882
|
+
lineHeight: 1.05,
|
|
883
|
+
letterSpacing: "-0.02em"
|
|
884
|
+
},
|
|
885
|
+
children: schedule?.name ?? "Book an appointment"
|
|
886
|
+
}
|
|
887
|
+
),
|
|
831
888
|
schedule?.description && /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("p", { className: "font-body text-body text-center m-0 text-(--color-accent,#A89B83)", children: schedule.description })
|
|
832
889
|
] }),
|
|
833
890
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { className: "w-full flex flex-col items-end gap-3", children: [
|
|
@@ -4887,7 +4944,11 @@ function MediaOverlay({
|
|
|
4887
4944
|
variant: "outline",
|
|
4888
4945
|
size: "sm",
|
|
4889
4946
|
className: "gap-1.5 cursor-pointer hover:bg-background",
|
|
4890
|
-
style:
|
|
4947
|
+
style: {
|
|
4948
|
+
...OVERLAY_BUTTON_STYLE,
|
|
4949
|
+
// Don't let Replace steal clicks when text (e.g. nav) sits on top of this media.
|
|
4950
|
+
pointerEvents: hover.hasTextOverlap ? "none" : "auto"
|
|
4951
|
+
},
|
|
4891
4952
|
onMouseDown: (e) => e.preventDefault(),
|
|
4892
4953
|
onClick: (e) => {
|
|
4893
4954
|
e.stopPropagation();
|
|
@@ -4904,6 +4965,61 @@ function MediaOverlay({
|
|
|
4904
4965
|
] });
|
|
4905
4966
|
}
|
|
4906
4967
|
|
|
4968
|
+
// src/ui/CarouselOverlay.tsx
|
|
4969
|
+
var import_lucide_react4 = require("lucide-react");
|
|
4970
|
+
var import_jsx_runtime12 = require("react/jsx-runtime");
|
|
4971
|
+
var OVERLAY_BUTTON_STYLE2 = {
|
|
4972
|
+
pointerEvents: "auto",
|
|
4973
|
+
fontFamily: "Inter, sans-serif",
|
|
4974
|
+
fontSize: 12,
|
|
4975
|
+
color: "#000"
|
|
4976
|
+
};
|
|
4977
|
+
function CarouselOverlay({
|
|
4978
|
+
hover,
|
|
4979
|
+
onEdit
|
|
4980
|
+
}) {
|
|
4981
|
+
const { rect } = hover;
|
|
4982
|
+
return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
|
|
4983
|
+
"div",
|
|
4984
|
+
{
|
|
4985
|
+
"data-ohw-bridge": "",
|
|
4986
|
+
"data-ohw-carousel-overlay": "",
|
|
4987
|
+
className: "flex cursor-pointer items-center justify-center",
|
|
4988
|
+
style: {
|
|
4989
|
+
position: "fixed",
|
|
4990
|
+
top: rect.top,
|
|
4991
|
+
left: rect.left,
|
|
4992
|
+
width: rect.width,
|
|
4993
|
+
height: rect.height,
|
|
4994
|
+
zIndex: 2147483646,
|
|
4995
|
+
pointerEvents: "auto",
|
|
4996
|
+
boxShadow: "inset 0 0 0 1.5px var(--color-primary)",
|
|
4997
|
+
background: "color-mix(in srgb, var(--color-primary) 20%, transparent)"
|
|
4998
|
+
},
|
|
4999
|
+
onClick: () => onEdit(hover.key),
|
|
5000
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)(
|
|
5001
|
+
Button,
|
|
5002
|
+
{
|
|
5003
|
+
"data-ohw-carousel-overlay": "",
|
|
5004
|
+
variant: "outline",
|
|
5005
|
+
size: "sm",
|
|
5006
|
+
className: "cursor-pointer gap-1.5 hover:bg-background",
|
|
5007
|
+
style: OVERLAY_BUTTON_STYLE2,
|
|
5008
|
+
onMouseDown: (e) => e.preventDefault(),
|
|
5009
|
+
onClick: (e) => {
|
|
5010
|
+
e.stopPropagation();
|
|
5011
|
+
onEdit(hover.key);
|
|
5012
|
+
},
|
|
5013
|
+
children: [
|
|
5014
|
+
/* @__PURE__ */ (0, import_jsx_runtime12.jsx)(import_lucide_react4.GalleryHorizontal, { size: 14 }),
|
|
5015
|
+
"Edit gallery"
|
|
5016
|
+
]
|
|
5017
|
+
}
|
|
5018
|
+
)
|
|
5019
|
+
}
|
|
5020
|
+
);
|
|
5021
|
+
}
|
|
5022
|
+
|
|
4907
5023
|
// src/OhhwellsBridge.tsx
|
|
4908
5024
|
var import_react_dom3 = require("react-dom");
|
|
4909
5025
|
var import_navigation2 = require("next/navigation");
|
|
@@ -5189,23 +5305,23 @@ var import_react7 = require("react");
|
|
|
5189
5305
|
// src/ui/dialog.tsx
|
|
5190
5306
|
var React8 = __toESM(require("react"), 1);
|
|
5191
5307
|
var import_radix_ui5 = require("radix-ui");
|
|
5192
|
-
var
|
|
5193
|
-
var
|
|
5308
|
+
var import_lucide_react5 = require("lucide-react");
|
|
5309
|
+
var import_jsx_runtime13 = require("react/jsx-runtime");
|
|
5194
5310
|
function Dialog2({
|
|
5195
5311
|
...props
|
|
5196
5312
|
}) {
|
|
5197
|
-
return /* @__PURE__ */ (0,
|
|
5313
|
+
return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_radix_ui5.Dialog.Root, { "data-slot": "dialog", ...props });
|
|
5198
5314
|
}
|
|
5199
5315
|
function DialogPortal({
|
|
5200
5316
|
...props
|
|
5201
5317
|
}) {
|
|
5202
|
-
return /* @__PURE__ */ (0,
|
|
5318
|
+
return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_radix_ui5.Dialog.Portal, { ...props });
|
|
5203
5319
|
}
|
|
5204
5320
|
function DialogOverlay({
|
|
5205
5321
|
className,
|
|
5206
5322
|
...props
|
|
5207
5323
|
}) {
|
|
5208
|
-
return /* @__PURE__ */ (0,
|
|
5324
|
+
return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
|
|
5209
5325
|
import_radix_ui5.Dialog.Overlay,
|
|
5210
5326
|
{
|
|
5211
5327
|
"data-slot": "dialog-overlay",
|
|
@@ -5218,9 +5334,9 @@ function DialogOverlay({
|
|
|
5218
5334
|
var DialogContent = React8.forwardRef(
|
|
5219
5335
|
({ className, children, showCloseButton = true, container, ...props }, ref) => {
|
|
5220
5336
|
const positionMode = container ? "absolute" : "fixed";
|
|
5221
|
-
return /* @__PURE__ */ (0,
|
|
5222
|
-
/* @__PURE__ */ (0,
|
|
5223
|
-
/* @__PURE__ */ (0,
|
|
5337
|
+
return /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(DialogPortal, { container: container ?? void 0, children: [
|
|
5338
|
+
/* @__PURE__ */ (0, import_jsx_runtime13.jsx)(DialogOverlay, { className: cn(positionMode, "inset-0") }),
|
|
5339
|
+
/* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
|
|
5224
5340
|
import_radix_ui5.Dialog.Content,
|
|
5225
5341
|
{
|
|
5226
5342
|
ref,
|
|
@@ -5236,13 +5352,13 @@ var DialogContent = React8.forwardRef(
|
|
|
5236
5352
|
...props,
|
|
5237
5353
|
children: [
|
|
5238
5354
|
children,
|
|
5239
|
-
showCloseButton ? /* @__PURE__ */ (0,
|
|
5355
|
+
showCloseButton ? /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
|
|
5240
5356
|
import_radix_ui5.Dialog.Close,
|
|
5241
5357
|
{
|
|
5242
5358
|
type: "button",
|
|
5243
5359
|
className: "absolute right-[9px] top-[9px] rounded-sm p-1.5 text-foreground hover:bg-muted/50",
|
|
5244
5360
|
"aria-label": "Close",
|
|
5245
|
-
children: /* @__PURE__ */ (0,
|
|
5361
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_lucide_react5.X, { size: 16, "aria-hidden": true })
|
|
5246
5362
|
}
|
|
5247
5363
|
) : null
|
|
5248
5364
|
]
|
|
@@ -5256,13 +5372,13 @@ function DialogHeader({
|
|
|
5256
5372
|
className,
|
|
5257
5373
|
...props
|
|
5258
5374
|
}) {
|
|
5259
|
-
return /* @__PURE__ */ (0,
|
|
5375
|
+
return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: cn("flex flex-col gap-1.5", className), ...props });
|
|
5260
5376
|
}
|
|
5261
5377
|
function DialogFooter({
|
|
5262
5378
|
className,
|
|
5263
5379
|
...props
|
|
5264
5380
|
}) {
|
|
5265
|
-
return /* @__PURE__ */ (0,
|
|
5381
|
+
return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
|
|
5266
5382
|
"div",
|
|
5267
5383
|
{
|
|
5268
5384
|
className: cn("flex items-center justify-end gap-2", className),
|
|
@@ -5270,7 +5386,7 @@ function DialogFooter({
|
|
|
5270
5386
|
}
|
|
5271
5387
|
);
|
|
5272
5388
|
}
|
|
5273
|
-
var DialogTitle = React8.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0,
|
|
5389
|
+
var DialogTitle = React8.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
|
|
5274
5390
|
import_radix_ui5.Dialog.Title,
|
|
5275
5391
|
{
|
|
5276
5392
|
ref,
|
|
@@ -5282,7 +5398,7 @@ var DialogTitle = React8.forwardRef(({ className, ...props }, ref) => /* @__PURE
|
|
|
5282
5398
|
}
|
|
5283
5399
|
));
|
|
5284
5400
|
DialogTitle.displayName = import_radix_ui5.Dialog.Title.displayName;
|
|
5285
|
-
var DialogDescription = React8.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0,
|
|
5401
|
+
var DialogDescription = React8.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
|
|
5286
5402
|
import_radix_ui5.Dialog.Description,
|
|
5287
5403
|
{
|
|
5288
5404
|
ref,
|
|
@@ -5294,63 +5410,63 @@ DialogDescription.displayName = import_radix_ui5.Dialog.Description.displayName;
|
|
|
5294
5410
|
var DialogClose = import_radix_ui5.Dialog.Close;
|
|
5295
5411
|
|
|
5296
5412
|
// src/ui/link-modal/LinkEditorPanel.tsx
|
|
5297
|
-
var
|
|
5413
|
+
var import_lucide_react9 = require("lucide-react");
|
|
5298
5414
|
|
|
5299
5415
|
// src/ui/link-modal/DestinationBreadcrumb.tsx
|
|
5300
|
-
var
|
|
5301
|
-
var
|
|
5416
|
+
var import_lucide_react6 = require("lucide-react");
|
|
5417
|
+
var import_jsx_runtime14 = require("react/jsx-runtime");
|
|
5302
5418
|
function DestinationBreadcrumb({
|
|
5303
5419
|
pageTitle,
|
|
5304
5420
|
sectionLabel
|
|
5305
5421
|
}) {
|
|
5306
|
-
return /* @__PURE__ */ (0,
|
|
5307
|
-
/* @__PURE__ */ (0,
|
|
5308
|
-
/* @__PURE__ */ (0,
|
|
5309
|
-
/* @__PURE__ */ (0,
|
|
5310
|
-
/* @__PURE__ */ (0,
|
|
5311
|
-
/* @__PURE__ */ (0,
|
|
5422
|
+
return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "flex w-full flex-col gap-2", children: [
|
|
5423
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsx)("p", { className: "text-sm font-medium! text-foreground m-0", children: "Destination" }),
|
|
5424
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "flex items-center gap-3", children: [
|
|
5425
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "flex items-center gap-2", children: [
|
|
5426
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react6.File, { size: 16, className: "shrink-0 text-foreground", "aria-hidden": true }),
|
|
5427
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "text-sm font-medium leading-none text-foreground!", children: pageTitle })
|
|
5312
5428
|
] }),
|
|
5313
|
-
/* @__PURE__ */ (0,
|
|
5314
|
-
|
|
5429
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
|
|
5430
|
+
import_lucide_react6.ArrowRight,
|
|
5315
5431
|
{
|
|
5316
5432
|
size: 16,
|
|
5317
5433
|
className: "shrink-0 text-muted-foreground",
|
|
5318
5434
|
"aria-hidden": true
|
|
5319
5435
|
}
|
|
5320
5436
|
),
|
|
5321
|
-
/* @__PURE__ */ (0,
|
|
5322
|
-
/* @__PURE__ */ (0,
|
|
5323
|
-
|
|
5437
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "flex min-w-0 flex-1 items-center gap-2", children: [
|
|
5438
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
|
|
5439
|
+
import_lucide_react6.GalleryVertical,
|
|
5324
5440
|
{
|
|
5325
5441
|
size: 16,
|
|
5326
5442
|
className: "shrink-0 text-foreground",
|
|
5327
5443
|
"aria-hidden": true
|
|
5328
5444
|
}
|
|
5329
5445
|
),
|
|
5330
|
-
/* @__PURE__ */ (0,
|
|
5446
|
+
/* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "truncate text-sm font-medium leading-none text-foreground", children: sectionLabel })
|
|
5331
5447
|
] })
|
|
5332
5448
|
] })
|
|
5333
5449
|
] });
|
|
5334
5450
|
}
|
|
5335
5451
|
|
|
5336
5452
|
// src/ui/link-modal/SectionTreeItem.tsx
|
|
5337
|
-
var
|
|
5338
|
-
var
|
|
5453
|
+
var import_lucide_react7 = require("lucide-react");
|
|
5454
|
+
var import_jsx_runtime15 = require("react/jsx-runtime");
|
|
5339
5455
|
function SectionTreeItem({
|
|
5340
5456
|
section,
|
|
5341
5457
|
onSelect,
|
|
5342
5458
|
selected
|
|
5343
5459
|
}) {
|
|
5344
5460
|
const interactive = Boolean(onSelect);
|
|
5345
|
-
return /* @__PURE__ */ (0,
|
|
5346
|
-
/* @__PURE__ */ (0,
|
|
5461
|
+
return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className: "flex h-9 w-full items-end pl-3", children: [
|
|
5462
|
+
/* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
|
|
5347
5463
|
"div",
|
|
5348
5464
|
{
|
|
5349
5465
|
className: "mr-[-1px] h-9 w-2 shrink-0 rounded-bl-sm border-b border-l border-border mb-4",
|
|
5350
5466
|
"aria-hidden": true
|
|
5351
5467
|
}
|
|
5352
5468
|
),
|
|
5353
|
-
/* @__PURE__ */ (0,
|
|
5469
|
+
/* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
|
|
5354
5470
|
"div",
|
|
5355
5471
|
{
|
|
5356
5472
|
role: interactive ? "button" : void 0,
|
|
@@ -5368,15 +5484,15 @@ function SectionTreeItem({
|
|
|
5368
5484
|
interactive && selected && "border-primary"
|
|
5369
5485
|
),
|
|
5370
5486
|
children: [
|
|
5371
|
-
/* @__PURE__ */ (0,
|
|
5372
|
-
|
|
5487
|
+
/* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
|
|
5488
|
+
import_lucide_react7.GalleryVertical,
|
|
5373
5489
|
{
|
|
5374
5490
|
size: 16,
|
|
5375
5491
|
className: "shrink-0 text-foreground",
|
|
5376
5492
|
"aria-hidden": true
|
|
5377
5493
|
}
|
|
5378
5494
|
),
|
|
5379
|
-
/* @__PURE__ */ (0,
|
|
5495
|
+
/* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "truncate text-sm font-normal leading-5 text-foreground", children: section.label })
|
|
5380
5496
|
]
|
|
5381
5497
|
}
|
|
5382
5498
|
)
|
|
@@ -5388,10 +5504,10 @@ var import_react4 = require("react");
|
|
|
5388
5504
|
|
|
5389
5505
|
// src/ui/input.tsx
|
|
5390
5506
|
var React9 = __toESM(require("react"), 1);
|
|
5391
|
-
var
|
|
5507
|
+
var import_jsx_runtime16 = require("react/jsx-runtime");
|
|
5392
5508
|
var Input = React9.forwardRef(
|
|
5393
5509
|
({ className, type, ...props }, ref) => {
|
|
5394
|
-
return /* @__PURE__ */ (0,
|
|
5510
|
+
return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
|
|
5395
5511
|
"input",
|
|
5396
5512
|
{
|
|
5397
5513
|
type,
|
|
@@ -5410,9 +5526,9 @@ Input.displayName = "Input";
|
|
|
5410
5526
|
|
|
5411
5527
|
// src/ui/label.tsx
|
|
5412
5528
|
var import_radix_ui6 = require("radix-ui");
|
|
5413
|
-
var
|
|
5529
|
+
var import_jsx_runtime17 = require("react/jsx-runtime");
|
|
5414
5530
|
function Label({ className, ...props }) {
|
|
5415
|
-
return /* @__PURE__ */ (0,
|
|
5531
|
+
return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
|
|
5416
5532
|
import_radix_ui6.Label.Root,
|
|
5417
5533
|
{
|
|
5418
5534
|
"data-slot": "label",
|
|
@@ -5423,12 +5539,12 @@ function Label({ className, ...props }) {
|
|
|
5423
5539
|
}
|
|
5424
5540
|
|
|
5425
5541
|
// src/ui/link-modal/UrlOrPageInput.tsx
|
|
5426
|
-
var
|
|
5427
|
-
var
|
|
5542
|
+
var import_lucide_react8 = require("lucide-react");
|
|
5543
|
+
var import_jsx_runtime18 = require("react/jsx-runtime");
|
|
5428
5544
|
function FieldChevron({
|
|
5429
5545
|
onClick
|
|
5430
5546
|
}) {
|
|
5431
|
-
return /* @__PURE__ */ (0,
|
|
5547
|
+
return /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
|
|
5432
5548
|
"button",
|
|
5433
5549
|
{
|
|
5434
5550
|
type: "button",
|
|
@@ -5436,7 +5552,7 @@ function FieldChevron({
|
|
|
5436
5552
|
onClick,
|
|
5437
5553
|
"aria-label": "Open page list",
|
|
5438
5554
|
tabIndex: -1,
|
|
5439
|
-
children: /* @__PURE__ */ (0,
|
|
5555
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react8.ChevronDown, { size: 16 })
|
|
5440
5556
|
}
|
|
5441
5557
|
);
|
|
5442
5558
|
}
|
|
@@ -5497,19 +5613,19 @@ function UrlOrPageInput({
|
|
|
5497
5613
|
"data-ohw-link-field flex h-[36px] w-full items-center overflow-hidden rounded-md border bg-background pl-3 pr-3 py-2 outline-none transition-[border-color,box-shadow]",
|
|
5498
5614
|
urlError ? "border-destructive shadow-[0_0_0_1px_var(--ohw-destructive)]" : isFocused ? "border-primary shadow-[0_0_0_1px_var(--ohw-primary)]" : "border-input"
|
|
5499
5615
|
);
|
|
5500
|
-
return /* @__PURE__ */ (0,
|
|
5501
|
-
/* @__PURE__ */ (0,
|
|
5502
|
-
/* @__PURE__ */ (0,
|
|
5503
|
-
/* @__PURE__ */ (0,
|
|
5504
|
-
selectedPage ? /* @__PURE__ */ (0,
|
|
5505
|
-
|
|
5616
|
+
return /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex w-full flex-col gap-2 p-0", children: [
|
|
5617
|
+
/* @__PURE__ */ (0, import_jsx_runtime18.jsx)(Label, { htmlFor: inputId, className: cn(urlError && "text-destructive"), children: "Destination" }),
|
|
5618
|
+
/* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { ref: rootRef, className: "relative w-full", children: [
|
|
5619
|
+
/* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { "data-ohw-link-field": true, className: fieldClassName, children: [
|
|
5620
|
+
selectedPage ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { className: "flex shrink-0 items-center pr-2", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
|
|
5621
|
+
import_lucide_react8.File,
|
|
5506
5622
|
{
|
|
5507
5623
|
size: 16,
|
|
5508
5624
|
className: "shrink-0 text-foreground",
|
|
5509
5625
|
"aria-hidden": true
|
|
5510
5626
|
}
|
|
5511
5627
|
) }) : null,
|
|
5512
|
-
readOnly ? /* @__PURE__ */ (0,
|
|
5628
|
+
readOnly ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "min-w-0 flex-1 truncate text-sm leading-5 text-foreground", children: selectedPage?.title ?? value }) : /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
|
|
5513
5629
|
Input,
|
|
5514
5630
|
{
|
|
5515
5631
|
ref: inputRef,
|
|
@@ -5535,7 +5651,7 @@ function UrlOrPageInput({
|
|
|
5535
5651
|
)
|
|
5536
5652
|
}
|
|
5537
5653
|
),
|
|
5538
|
-
selectedPage && !readOnly ? /* @__PURE__ */ (0,
|
|
5654
|
+
selectedPage && !readOnly ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
|
|
5539
5655
|
"button",
|
|
5540
5656
|
{
|
|
5541
5657
|
type: "button",
|
|
@@ -5543,26 +5659,26 @@ function UrlOrPageInput({
|
|
|
5543
5659
|
onMouseDown: clearSelection,
|
|
5544
5660
|
"aria-label": "Clear selected page",
|
|
5545
5661
|
tabIndex: -1,
|
|
5546
|
-
children: /* @__PURE__ */ (0,
|
|
5662
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react8.X, { size: 16, "aria-hidden": true })
|
|
5547
5663
|
}
|
|
5548
5664
|
) : null,
|
|
5549
|
-
!readOnly ? /* @__PURE__ */ (0,
|
|
5665
|
+
!readOnly ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(FieldChevron, { onClick: toggleDropdown }) : null
|
|
5550
5666
|
] }),
|
|
5551
|
-
dropdownOpen && !readOnly && filteredPages.length > 0 ? /* @__PURE__ */ (0,
|
|
5667
|
+
dropdownOpen && !readOnly && filteredPages.length > 0 ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
|
|
5552
5668
|
"div",
|
|
5553
5669
|
{
|
|
5554
5670
|
"data-ohw-link-page-dropdown": "",
|
|
5555
5671
|
className: "absolute left-0 right-0 top-[calc(100%+4px)] z-50 max-h-48 overflow-auto rounded-lg border border-border bg-popover py-1 shadow-lg",
|
|
5556
5672
|
onMouseDown: (e) => e.preventDefault(),
|
|
5557
|
-
children: filteredPages.map((page) => /* @__PURE__ */ (0,
|
|
5673
|
+
children: filteredPages.map((page) => /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
|
|
5558
5674
|
"button",
|
|
5559
5675
|
{
|
|
5560
5676
|
type: "button",
|
|
5561
5677
|
className: "flex h-9 w-full items-center gap-2 border-0 bg-transparent px-3 text-left text-sm leading-5 text-foreground outline-none hover:bg-muted",
|
|
5562
5678
|
onClick: () => onPageSelect(page),
|
|
5563
5679
|
children: [
|
|
5564
|
-
/* @__PURE__ */ (0,
|
|
5565
|
-
/* @__PURE__ */ (0,
|
|
5680
|
+
/* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react8.File, { size: 16, className: "shrink-0", "aria-hidden": true }),
|
|
5681
|
+
/* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "truncate", children: page.title })
|
|
5566
5682
|
]
|
|
5567
5683
|
},
|
|
5568
5684
|
page.path
|
|
@@ -5570,34 +5686,34 @@ function UrlOrPageInput({
|
|
|
5570
5686
|
}
|
|
5571
5687
|
) : null
|
|
5572
5688
|
] }),
|
|
5573
|
-
urlError ? /* @__PURE__ */ (0,
|
|
5689
|
+
urlError ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("p", { className: "text-sm font-medium text-destructive", children: urlError }) : null
|
|
5574
5690
|
] });
|
|
5575
5691
|
}
|
|
5576
5692
|
|
|
5577
5693
|
// src/ui/link-modal/LinkEditorPanel.tsx
|
|
5578
|
-
var
|
|
5694
|
+
var import_jsx_runtime19 = require("react/jsx-runtime");
|
|
5579
5695
|
function LinkEditorPanel({ state, onClose }) {
|
|
5580
5696
|
const isCancel = state.secondaryLabel === "Cancel" || state.secondaryLabel === "Back to sections";
|
|
5581
|
-
return /* @__PURE__ */ (0,
|
|
5582
|
-
/* @__PURE__ */ (0,
|
|
5697
|
+
return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(import_jsx_runtime19.Fragment, { children: [
|
|
5698
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)(DialogClose, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
|
|
5583
5699
|
"button",
|
|
5584
5700
|
{
|
|
5585
5701
|
type: "button",
|
|
5586
5702
|
className: "absolute right-[9px] top-[9px] rounded-sm p-1.5 text-foreground hover:bg-muted/50 h-7",
|
|
5587
5703
|
"aria-label": "Close",
|
|
5588
5704
|
onClick: onClose,
|
|
5589
|
-
children: /* @__PURE__ */ (0,
|
|
5705
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(import_lucide_react9.X, { size: 16, "aria-hidden": true })
|
|
5590
5706
|
}
|
|
5591
5707
|
) }),
|
|
5592
|
-
/* @__PURE__ */ (0,
|
|
5593
|
-
/* @__PURE__ */ (0,
|
|
5594
|
-
state.showBreadcrumb && state.selectedPage && state.selectedSection ? /* @__PURE__ */ (0,
|
|
5708
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)(DialogHeader, { className: "w-full gap-1.5 p-6 pr-12", children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(DialogTitle, { className: "m-0 w-full break-words", children: state.title }) }),
|
|
5709
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "flex w-full flex-col gap-3 px-6 pb-8 pt-1", children: [
|
|
5710
|
+
state.showBreadcrumb && state.selectedPage && state.selectedSection ? /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
|
|
5595
5711
|
DestinationBreadcrumb,
|
|
5596
5712
|
{
|
|
5597
5713
|
pageTitle: state.selectedPage.title,
|
|
5598
5714
|
sectionLabel: state.selectedSection.label
|
|
5599
5715
|
}
|
|
5600
|
-
) : /* @__PURE__ */ (0,
|
|
5716
|
+
) : /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
|
|
5601
5717
|
UrlOrPageInput,
|
|
5602
5718
|
{
|
|
5603
5719
|
value: state.searchValue,
|
|
@@ -5610,8 +5726,8 @@ function LinkEditorPanel({ state, onClose }) {
|
|
|
5610
5726
|
urlError: state.urlError
|
|
5611
5727
|
}
|
|
5612
5728
|
),
|
|
5613
|
-
state.showChooseSection ? /* @__PURE__ */ (0,
|
|
5614
|
-
/* @__PURE__ */ (0,
|
|
5729
|
+
state.showChooseSection ? /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "flex flex-col justify-center gap-2", children: [
|
|
5730
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
|
|
5615
5731
|
Button,
|
|
5616
5732
|
{
|
|
5617
5733
|
type: "button",
|
|
@@ -5622,15 +5738,15 @@ function LinkEditorPanel({ state, onClose }) {
|
|
|
5622
5738
|
children: "Choose a section"
|
|
5623
5739
|
}
|
|
5624
5740
|
),
|
|
5625
|
-
/* @__PURE__ */ (0,
|
|
5626
|
-
/* @__PURE__ */ (0,
|
|
5627
|
-
/* @__PURE__ */ (0,
|
|
5741
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "flex items-center gap-1 text-sm text-muted-foreground", children: [
|
|
5742
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)(import_lucide_react9.Info, { size: 16, className: "shrink-0", "aria-hidden": true }),
|
|
5743
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { children: "Pick a section this link should scroll to." })
|
|
5628
5744
|
] })
|
|
5629
5745
|
] }) : null,
|
|
5630
|
-
state.showSectionRow && state.selectedSection ? /* @__PURE__ */ (0,
|
|
5746
|
+
state.showSectionRow && state.selectedSection ? /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(SectionTreeItem, { section: state.selectedSection, selected: true }) : null
|
|
5631
5747
|
] }),
|
|
5632
|
-
/* @__PURE__ */ (0,
|
|
5633
|
-
/* @__PURE__ */ (0,
|
|
5748
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(DialogFooter, { className: "w-full px-6 pb-6", children: [
|
|
5749
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
|
|
5634
5750
|
Button,
|
|
5635
5751
|
{
|
|
5636
5752
|
type: "button",
|
|
@@ -5645,7 +5761,7 @@ function LinkEditorPanel({ state, onClose }) {
|
|
|
5645
5761
|
children: state.secondaryLabel
|
|
5646
5762
|
}
|
|
5647
5763
|
),
|
|
5648
|
-
/* @__PURE__ */ (0,
|
|
5764
|
+
/* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
|
|
5649
5765
|
Button,
|
|
5650
5766
|
{
|
|
5651
5767
|
type: "button",
|
|
@@ -5666,9 +5782,9 @@ function LinkEditorPanel({ state, onClose }) {
|
|
|
5666
5782
|
// src/ui/link-modal/SectionPickerOverlay.tsx
|
|
5667
5783
|
var import_react5 = require("react");
|
|
5668
5784
|
var import_react_dom = require("react-dom");
|
|
5669
|
-
var
|
|
5785
|
+
var import_lucide_react10 = require("lucide-react");
|
|
5670
5786
|
var import_navigation = require("next/navigation");
|
|
5671
|
-
var
|
|
5787
|
+
var import_jsx_runtime20 = require("react/jsx-runtime");
|
|
5672
5788
|
var DIM_OVERLAY = "rgba(0, 0, 0, 0.45)";
|
|
5673
5789
|
function rectsEqual(a, b) {
|
|
5674
5790
|
if (a.size !== b.size) return false;
|
|
@@ -5897,7 +6013,7 @@ function SectionPickerOverlay({
|
|
|
5897
6013
|
const portalRoot = typeof document !== "undefined" ? document.querySelector("[data-ohw-bridge-root]") ?? document.body : null;
|
|
5898
6014
|
if (!portalRoot) return null;
|
|
5899
6015
|
return (0, import_react_dom.createPortal)(
|
|
5900
|
-
/* @__PURE__ */ (0,
|
|
6016
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
5901
6017
|
"div",
|
|
5902
6018
|
{
|
|
5903
6019
|
"data-ohw-section-picker": "",
|
|
@@ -5907,12 +6023,12 @@ function SectionPickerOverlay({
|
|
|
5907
6023
|
role: "dialog",
|
|
5908
6024
|
"aria-label": "Choose a section",
|
|
5909
6025
|
children: [
|
|
5910
|
-
/* @__PURE__ */ (0,
|
|
6026
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
5911
6027
|
"div",
|
|
5912
6028
|
{
|
|
5913
6029
|
className: "pointer-events-auto fixed left-5 z-[2]",
|
|
5914
6030
|
style: { top: chromeClip.top + 20 },
|
|
5915
|
-
children: /* @__PURE__ */ (0,
|
|
6031
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
5916
6032
|
Button,
|
|
5917
6033
|
{
|
|
5918
6034
|
type: "button",
|
|
@@ -5921,14 +6037,14 @@ function SectionPickerOverlay({
|
|
|
5921
6037
|
className: "h-8 min-w-0 gap-1 border-border bg-background px-2 py-1.5 shadow-sm hover:bg-muted cursor-pointer",
|
|
5922
6038
|
onClick: onBack,
|
|
5923
6039
|
children: [
|
|
5924
|
-
/* @__PURE__ */ (0,
|
|
6040
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react10.ArrowLeft, { className: "size-4 shrink-0", "aria-hidden": true }),
|
|
5925
6041
|
"Back"
|
|
5926
6042
|
]
|
|
5927
6043
|
}
|
|
5928
6044
|
)
|
|
5929
6045
|
}
|
|
5930
6046
|
),
|
|
5931
|
-
/* @__PURE__ */ (0,
|
|
6047
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
5932
6048
|
"div",
|
|
5933
6049
|
{
|
|
5934
6050
|
className: "pointer-events-none fixed left-1/2 z-[2] rounded-lg px-4 py-3 text-xs leading-4 tracking-[0.18px] text-white shadow-md",
|
|
@@ -5941,7 +6057,7 @@ function SectionPickerOverlay({
|
|
|
5941
6057
|
children: "Click on section to select"
|
|
5942
6058
|
}
|
|
5943
6059
|
),
|
|
5944
|
-
!isOnTargetPage ? /* @__PURE__ */ (0,
|
|
6060
|
+
!isOnTargetPage ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
5945
6061
|
"div",
|
|
5946
6062
|
{
|
|
5947
6063
|
className: "pointer-events-none fixed left-1/2 z-[1] -translate-x-1/2 rounded-md px-3 py-2 text-sm text-muted-foreground shadow-sm",
|
|
@@ -5949,14 +6065,14 @@ function SectionPickerOverlay({
|
|
|
5949
6065
|
children: "Loading page preview\u2026"
|
|
5950
6066
|
}
|
|
5951
6067
|
) : null,
|
|
5952
|
-
isOnTargetPage && liveSections.length === 0 ? /* @__PURE__ */ (0,
|
|
6068
|
+
isOnTargetPage && liveSections.length === 0 ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("div", { className: "pointer-events-auto fixed inset-0 z-[1] flex items-center justify-center bg-muted/40", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("p", { className: "text-sm text-muted-foreground", children: "No sections found on this page." }) }) : null,
|
|
5953
6069
|
isOnTargetPage ? liveSections.map((section) => {
|
|
5954
6070
|
const rect = rects.get(section.id);
|
|
5955
6071
|
if (!rect || rect.width <= 0 || rect.height <= 0) return null;
|
|
5956
6072
|
const isSelected = selectedId === section.id;
|
|
5957
6073
|
const isHovered = hoveredId === section.id;
|
|
5958
6074
|
const isLit = isSelected || isHovered;
|
|
5959
|
-
return /* @__PURE__ */ (0,
|
|
6075
|
+
return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
5960
6076
|
"button",
|
|
5961
6077
|
{
|
|
5962
6078
|
type: "button",
|
|
@@ -5971,7 +6087,7 @@ function SectionPickerOverlay({
|
|
|
5971
6087
|
"aria-label": `Select section ${section.label}`,
|
|
5972
6088
|
onClick: () => handleSelect(section),
|
|
5973
6089
|
children: [
|
|
5974
|
-
isLit ? /* @__PURE__ */ (0,
|
|
6090
|
+
isLit ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
5975
6091
|
"span",
|
|
5976
6092
|
{
|
|
5977
6093
|
className: "pointer-events-none absolute",
|
|
@@ -5984,13 +6100,13 @@ function SectionPickerOverlay({
|
|
|
5984
6100
|
"aria-hidden": true
|
|
5985
6101
|
}
|
|
5986
6102
|
) : null,
|
|
5987
|
-
isSelected ? /* @__PURE__ */ (0,
|
|
6103
|
+
isSelected ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
5988
6104
|
"span",
|
|
5989
6105
|
{
|
|
5990
6106
|
className: "absolute right-3 top-3 flex size-8 items-center justify-center rounded-full text-white",
|
|
5991
6107
|
style: { backgroundColor: "var(--ohw-primary, #0885fe)" },
|
|
5992
6108
|
"aria-hidden": true,
|
|
5993
|
-
children: /* @__PURE__ */ (0,
|
|
6109
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react10.Check, { className: "size-5" })
|
|
5994
6110
|
}
|
|
5995
6111
|
) : null
|
|
5996
6112
|
]
|
|
@@ -6170,7 +6286,7 @@ function useLinkModalState({
|
|
|
6170
6286
|
}
|
|
6171
6287
|
|
|
6172
6288
|
// src/ui/link-modal/LinkPopover.tsx
|
|
6173
|
-
var
|
|
6289
|
+
var import_jsx_runtime21 = require("react/jsx-runtime");
|
|
6174
6290
|
function postToParent(data) {
|
|
6175
6291
|
window.parent?.postMessage(data, "*");
|
|
6176
6292
|
}
|
|
@@ -6266,15 +6382,15 @@ function LinkPopover({
|
|
|
6266
6382
|
);
|
|
6267
6383
|
};
|
|
6268
6384
|
}, [open, sectionPickerActive]);
|
|
6269
|
-
return /* @__PURE__ */ (0,
|
|
6270
|
-
/* @__PURE__ */ (0,
|
|
6385
|
+
return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(import_jsx_runtime21.Fragment, { children: [
|
|
6386
|
+
/* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
6271
6387
|
Dialog2,
|
|
6272
6388
|
{
|
|
6273
6389
|
open: open && !sectionPickerActive,
|
|
6274
6390
|
onOpenChange: (next) => {
|
|
6275
6391
|
if (!next) onClose?.();
|
|
6276
6392
|
},
|
|
6277
|
-
children: /* @__PURE__ */ (0,
|
|
6393
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
6278
6394
|
DialogContent,
|
|
6279
6395
|
{
|
|
6280
6396
|
ref: panelRef,
|
|
@@ -6284,12 +6400,12 @@ function LinkPopover({
|
|
|
6284
6400
|
"data-ohw-bridge": "",
|
|
6285
6401
|
showCloseButton: false,
|
|
6286
6402
|
className: "gap-0 p-0 w-full max-w-[448px] pointer-events-auto z-[2147483646] overflow-visible",
|
|
6287
|
-
children: /* @__PURE__ */ (0,
|
|
6403
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(LinkEditorPanel, { state, onClose })
|
|
6288
6404
|
}
|
|
6289
6405
|
)
|
|
6290
6406
|
}
|
|
6291
6407
|
),
|
|
6292
|
-
sectionPickerActive && state.selectedPage ? /* @__PURE__ */ (0,
|
|
6408
|
+
sectionPickerActive && state.selectedPage ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
6293
6409
|
SectionPickerOverlay,
|
|
6294
6410
|
{
|
|
6295
6411
|
pagePath: state.selectedPage.path,
|
|
@@ -6661,6 +6777,8 @@ function applyNavOrderToContainer(container, order) {
|
|
|
6661
6777
|
if (current.length === expected.length && current.every((key, i) => key === expected[i])) {
|
|
6662
6778
|
return;
|
|
6663
6779
|
}
|
|
6780
|
+
const lastCurrentLinkEl = current.length > 0 ? findCounterpartByHrefKey(current[current.length - 1], container) : null;
|
|
6781
|
+
const anchor = lastCurrentLinkEl?.parentElement === container ? lastCurrentLinkEl.nextElementSibling : null;
|
|
6664
6782
|
const seen = /* @__PURE__ */ new Set();
|
|
6665
6783
|
for (const hrefKey of desired) {
|
|
6666
6784
|
if (seen.has(hrefKey)) continue;
|
|
@@ -6675,7 +6793,9 @@ function applyNavOrderToContainer(container, order) {
|
|
|
6675
6793
|
orderedEls.push(el);
|
|
6676
6794
|
}
|
|
6677
6795
|
for (const el of orderedEls) {
|
|
6678
|
-
if (
|
|
6796
|
+
if (anchor) {
|
|
6797
|
+
if (el.nextSibling !== anchor) container.insertBefore(el, anchor);
|
|
6798
|
+
} else if (container.lastElementChild !== el) {
|
|
6679
6799
|
container.appendChild(el);
|
|
6680
6800
|
}
|
|
6681
6801
|
}
|
|
@@ -7007,7 +7127,195 @@ function parseFooterOrder(content) {
|
|
|
7007
7127
|
return null;
|
|
7008
7128
|
}
|
|
7009
7129
|
}
|
|
7130
|
+
var FOOTER_HEADING_RE = /^footer-(\d+)-heading$/;
|
|
7131
|
+
var FOOTER_LABEL_RE = /^footer-(\d+)-(\d+)-label$/;
|
|
7132
|
+
var DEFAULT_FOOTER_COLUMN_HEADING = "New";
|
|
7133
|
+
var DEFAULT_FOOTER_COLUMN_LINK_LABEL = "New link";
|
|
7134
|
+
var DEFAULT_FOOTER_COLUMN_LINK_HREF = "";
|
|
7135
|
+
function isFooterLinksContainer(el) {
|
|
7136
|
+
return el.hasAttribute("data-ohw-footer-links") || el.classList.contains("rb-footer-links");
|
|
7137
|
+
}
|
|
7138
|
+
function getFooterColumnIndicesInDom() {
|
|
7139
|
+
const indices = /* @__PURE__ */ new Set();
|
|
7140
|
+
for (const col of listFooterColumns()) {
|
|
7141
|
+
const attr = col.getAttribute("data-ohw-footer-col");
|
|
7142
|
+
if (attr != null) {
|
|
7143
|
+
const n = parseInt(attr, 10);
|
|
7144
|
+
if (Number.isFinite(n)) indices.add(n);
|
|
7145
|
+
}
|
|
7146
|
+
for (const link of listFooterLinksInColumn(col)) {
|
|
7147
|
+
const parsed = parseFooterHrefKey(link.getAttribute("data-ohw-href-key"));
|
|
7148
|
+
if (parsed) indices.add(parsed.col);
|
|
7149
|
+
}
|
|
7150
|
+
const heading = col.querySelector('[data-ohw-key^="footer-"][data-ohw-key$="-heading"]');
|
|
7151
|
+
const headingKey = heading?.getAttribute("data-ohw-key");
|
|
7152
|
+
if (headingKey) {
|
|
7153
|
+
const match = headingKey.match(FOOTER_HEADING_RE);
|
|
7154
|
+
if (match) indices.add(parseInt(match[1], 10));
|
|
7155
|
+
}
|
|
7156
|
+
}
|
|
7157
|
+
return [...indices].sort((a, b) => a - b);
|
|
7158
|
+
}
|
|
7159
|
+
function getNextFooterColumnIndex() {
|
|
7160
|
+
const indices = getFooterColumnIndicesInDom();
|
|
7161
|
+
if (indices.length === 0) return 0;
|
|
7162
|
+
return Math.max(...indices) + 1;
|
|
7163
|
+
}
|
|
7164
|
+
function cloneFooterLinkShell(template) {
|
|
7165
|
+
const anchor = document.createElement("a");
|
|
7166
|
+
if (template) {
|
|
7167
|
+
anchor.style.cssText = template.style.cssText;
|
|
7168
|
+
if (template.className) anchor.className = template.className;
|
|
7169
|
+
}
|
|
7170
|
+
anchor.style.cursor = "pointer";
|
|
7171
|
+
anchor.style.textDecoration = "none";
|
|
7172
|
+
return anchor;
|
|
7173
|
+
}
|
|
7174
|
+
function buildFooterHeading(colIndex, text) {
|
|
7175
|
+
const heading = document.createElement("p");
|
|
7176
|
+
heading.setAttribute("data-ohw-editable", "text");
|
|
7177
|
+
heading.setAttribute("data-ohw-key", `footer-${colIndex}-heading`);
|
|
7178
|
+
heading.textContent = text;
|
|
7179
|
+
heading.style.cssText = [
|
|
7180
|
+
"color: var(--espresso, #3d312b)",
|
|
7181
|
+
"font-size: 14px",
|
|
7182
|
+
"font-weight: 800",
|
|
7183
|
+
"opacity: 0.82",
|
|
7184
|
+
"margin: 0 0 6px",
|
|
7185
|
+
"padding: 0",
|
|
7186
|
+
"line-height: 1.2"
|
|
7187
|
+
].join(";");
|
|
7188
|
+
return heading;
|
|
7189
|
+
}
|
|
7190
|
+
function buildFooterLink(colIndex, itemIndex, href, label, template) {
|
|
7191
|
+
const anchor = cloneFooterLinkShell(template);
|
|
7192
|
+
anchor.setAttribute("href", href);
|
|
7193
|
+
anchor.setAttribute("data-ohw-href-key", `footer-${colIndex}-${itemIndex}-href`);
|
|
7194
|
+
const span = document.createElement("span");
|
|
7195
|
+
span.setAttribute("data-ohw-editable", "text");
|
|
7196
|
+
span.setAttribute("data-ohw-key", `footer-${colIndex}-${itemIndex}-label`);
|
|
7197
|
+
span.textContent = label;
|
|
7198
|
+
anchor.appendChild(span);
|
|
7199
|
+
return anchor;
|
|
7200
|
+
}
|
|
7201
|
+
function footerColumnExistsInDom(colIndex) {
|
|
7202
|
+
return document.querySelector(`[data-ohw-footer-col="${colIndex}"]`) !== null || document.querySelector(`[data-ohw-href-key^="footer-${colIndex}-"]`) !== null || document.querySelector(`[data-ohw-key="footer-${colIndex}-heading"]`) !== null;
|
|
7203
|
+
}
|
|
7204
|
+
function getFooterLinkTemplate() {
|
|
7205
|
+
for (const col of listFooterColumns()) {
|
|
7206
|
+
const link = listFooterLinksInColumn(col)[0];
|
|
7207
|
+
if (link) return link;
|
|
7208
|
+
}
|
|
7209
|
+
return null;
|
|
7210
|
+
}
|
|
7211
|
+
function getFooterColumnTemplate() {
|
|
7212
|
+
return listFooterColumns()[0] ?? null;
|
|
7213
|
+
}
|
|
7214
|
+
function insertFooterColumnDom(colIndex, heading, items) {
|
|
7215
|
+
const container = getFooterLinksContainer();
|
|
7216
|
+
if (!container) return null;
|
|
7217
|
+
const colTemplate = getFooterColumnTemplate();
|
|
7218
|
+
const linkTemplate = getFooterLinkTemplate();
|
|
7219
|
+
const column = document.createElement("div");
|
|
7220
|
+
if (colTemplate?.className) column.className = colTemplate.className;
|
|
7221
|
+
else column.className = "rb-footer-link-col";
|
|
7222
|
+
column.setAttribute("data-ohw-footer-col", String(colIndex));
|
|
7223
|
+
if (colTemplate) {
|
|
7224
|
+
const gap = getComputedStyle(colTemplate).gap;
|
|
7225
|
+
if (gap && gap !== "normal") column.style.gap = gap;
|
|
7226
|
+
column.style.display = getComputedStyle(colTemplate).display || "flex";
|
|
7227
|
+
column.style.flexDirection = "column";
|
|
7228
|
+
}
|
|
7229
|
+
column.appendChild(buildFooterHeading(colIndex, heading));
|
|
7230
|
+
let firstLink = null;
|
|
7231
|
+
items.forEach((item, itemIndex) => {
|
|
7232
|
+
const link = buildFooterLink(colIndex, itemIndex, item.href, item.label, linkTemplate);
|
|
7233
|
+
column.appendChild(link);
|
|
7234
|
+
if (!firstLink) firstLink = link;
|
|
7235
|
+
});
|
|
7236
|
+
container.appendChild(column);
|
|
7237
|
+
return { column, firstLink };
|
|
7238
|
+
}
|
|
7239
|
+
function insertFooterColumn(heading = DEFAULT_FOOTER_COLUMN_HEADING, linkLabel = DEFAULT_FOOTER_COLUMN_LINK_LABEL, linkHref = DEFAULT_FOOTER_COLUMN_LINK_HREF) {
|
|
7240
|
+
const colIndex = getNextFooterColumnIndex();
|
|
7241
|
+
const inserted = insertFooterColumnDom(colIndex, heading, [{ href: linkHref, label: linkLabel }]);
|
|
7242
|
+
if (!inserted?.firstLink) throw new Error("Failed to insert footer column");
|
|
7243
|
+
syncFooterColumnIndices(listFooterColumns());
|
|
7244
|
+
return {
|
|
7245
|
+
column: inserted.column,
|
|
7246
|
+
firstLink: inserted.firstLink,
|
|
7247
|
+
colIndex,
|
|
7248
|
+
headingKey: `footer-${colIndex}-heading`,
|
|
7249
|
+
hrefKey: `footer-${colIndex}-0-href`,
|
|
7250
|
+
labelKey: `footer-${colIndex}-0-label`,
|
|
7251
|
+
heading,
|
|
7252
|
+
label: linkLabel,
|
|
7253
|
+
href: linkHref,
|
|
7254
|
+
order: getFooterOrderFromDom()
|
|
7255
|
+
};
|
|
7256
|
+
}
|
|
7257
|
+
function collectFooterColumnIndicesFromContent(content) {
|
|
7258
|
+
const indices = /* @__PURE__ */ new Set();
|
|
7259
|
+
for (const key of Object.keys(content)) {
|
|
7260
|
+
const href = parseFooterHrefKey(key);
|
|
7261
|
+
if (href) indices.add(href.col);
|
|
7262
|
+
const heading = key.match(FOOTER_HEADING_RE);
|
|
7263
|
+
if (heading) indices.add(parseInt(heading[1], 10));
|
|
7264
|
+
const label = key.match(FOOTER_LABEL_RE);
|
|
7265
|
+
if (label) indices.add(parseInt(label[1], 10));
|
|
7266
|
+
}
|
|
7267
|
+
const order = parseFooterOrder(content);
|
|
7268
|
+
if (order) {
|
|
7269
|
+
for (const col of order) {
|
|
7270
|
+
for (const hrefKey of col) {
|
|
7271
|
+
const parsed = parseFooterHrefKey(hrefKey);
|
|
7272
|
+
if (parsed) indices.add(parsed.col);
|
|
7273
|
+
}
|
|
7274
|
+
}
|
|
7275
|
+
}
|
|
7276
|
+
return [...indices].sort((a, b) => a - b);
|
|
7277
|
+
}
|
|
7278
|
+
function collectFooterItemsForColumn(content, colIndex) {
|
|
7279
|
+
const itemIndices = /* @__PURE__ */ new Set();
|
|
7280
|
+
for (const key of Object.keys(content)) {
|
|
7281
|
+
const href = parseFooterHrefKey(key);
|
|
7282
|
+
if (href?.col === colIndex) itemIndices.add(href.item);
|
|
7283
|
+
const label = key.match(FOOTER_LABEL_RE);
|
|
7284
|
+
if (label && parseInt(label[1], 10) === colIndex) {
|
|
7285
|
+
itemIndices.add(parseInt(label[2], 10));
|
|
7286
|
+
}
|
|
7287
|
+
}
|
|
7288
|
+
const sorted = [...itemIndices].sort((a, b) => a - b);
|
|
7289
|
+
if (sorted.length === 0) {
|
|
7290
|
+
return [
|
|
7291
|
+
{
|
|
7292
|
+
href: content[`footer-${colIndex}-0-href`] ?? DEFAULT_FOOTER_COLUMN_LINK_HREF,
|
|
7293
|
+
label: content[`footer-${colIndex}-0-label`] ?? DEFAULT_FOOTER_COLUMN_LINK_LABEL
|
|
7294
|
+
}
|
|
7295
|
+
];
|
|
7296
|
+
}
|
|
7297
|
+
return sorted.map((itemIndex) => ({
|
|
7298
|
+
href: content[`footer-${colIndex}-${itemIndex}-href`] ?? DEFAULT_FOOTER_COLUMN_LINK_HREF,
|
|
7299
|
+
label: content[`footer-${colIndex}-${itemIndex}-label`] ?? DEFAULT_FOOTER_COLUMN_LINK_LABEL
|
|
7300
|
+
}));
|
|
7301
|
+
}
|
|
7302
|
+
function reconcileFooterColumnsFromContent(content) {
|
|
7303
|
+
const indices = collectFooterColumnIndicesFromContent(content);
|
|
7304
|
+
for (const colIndex of indices) {
|
|
7305
|
+
if (footerColumnExistsInDom(colIndex)) continue;
|
|
7306
|
+
const heading = content[`footer-${colIndex}-heading`] ?? DEFAULT_FOOTER_COLUMN_HEADING;
|
|
7307
|
+
const items = collectFooterItemsForColumn(content, colIndex);
|
|
7308
|
+
const hasPayload = Boolean(content[`footer-${colIndex}-heading`]) || items.some(
|
|
7309
|
+
(_, i) => content[`footer-${colIndex}-${i}-href`] !== void 0 || content[`footer-${colIndex}-${i}-label`] !== void 0
|
|
7310
|
+
) || (parseFooterOrder(content)?.some(
|
|
7311
|
+
(col) => col.some((k) => parseFooterHrefKey(k)?.col === colIndex)
|
|
7312
|
+
) ?? false);
|
|
7313
|
+
if (!hasPayload) continue;
|
|
7314
|
+
insertFooterColumnDom(colIndex, heading, items);
|
|
7315
|
+
}
|
|
7316
|
+
}
|
|
7010
7317
|
function reconcileFooterOrderFromContent(content) {
|
|
7318
|
+
reconcileFooterColumnsFromContent(content);
|
|
7011
7319
|
const order = parseFooterOrder(content);
|
|
7012
7320
|
if (!order?.length) return;
|
|
7013
7321
|
const current = getFooterOrderFromDom();
|
|
@@ -7017,6 +7325,31 @@ function reconcileFooterOrderFromContent(content) {
|
|
|
7017
7325
|
}
|
|
7018
7326
|
applyFooterOrder(order);
|
|
7019
7327
|
}
|
|
7328
|
+
function resolveFooterLinksContainerSelectionTarget(target, clientX, clientY, isPointOverItem) {
|
|
7329
|
+
const container = getFooterLinksContainer();
|
|
7330
|
+
if (!container) return null;
|
|
7331
|
+
const inContainer = target === container || container.contains(target) && Boolean(target.closest("[data-ohw-footer-links], .rb-footer-links"));
|
|
7332
|
+
if (!inContainer && target !== container) {
|
|
7333
|
+
const r2 = container.getBoundingClientRect();
|
|
7334
|
+
const over = clientX >= r2.left && clientX <= r2.right && clientY >= r2.top && clientY <= r2.bottom;
|
|
7335
|
+
if (!over) return null;
|
|
7336
|
+
}
|
|
7337
|
+
if (isPointOverItem(container, clientX, clientY)) return null;
|
|
7338
|
+
const column = target.closest("[data-ohw-footer-col], [data-ohw-footer-column]") ?? null;
|
|
7339
|
+
if (column && container.contains(column)) {
|
|
7340
|
+
if (target === column || column.contains(target)) return null;
|
|
7341
|
+
}
|
|
7342
|
+
if (target === container || container.contains(target) || inContainer) {
|
|
7343
|
+
if (target === container || isFooterLinksContainer(target)) return container;
|
|
7344
|
+
if (!column) return container;
|
|
7345
|
+
}
|
|
7346
|
+
return null;
|
|
7347
|
+
}
|
|
7348
|
+
function isRowLayoutColumn(links) {
|
|
7349
|
+
if (links.length < 2) return false;
|
|
7350
|
+
const firstTop = links[0].getBoundingClientRect().top;
|
|
7351
|
+
return links.every((link) => Math.abs(link.getBoundingClientRect().top - firstTop) < 4);
|
|
7352
|
+
}
|
|
7020
7353
|
function buildLinkDropSlots(column, columnIndex) {
|
|
7021
7354
|
const links = listFooterLinksInColumn(column);
|
|
7022
7355
|
const colRect = column.getBoundingClientRect();
|
|
@@ -7034,6 +7367,32 @@ function buildLinkDropSlots(column, columnIndex) {
|
|
|
7034
7367
|
});
|
|
7035
7368
|
return slots;
|
|
7036
7369
|
}
|
|
7370
|
+
if (isRowLayoutColumn(links)) {
|
|
7371
|
+
for (let i = 0; i <= links.length; i++) {
|
|
7372
|
+
let left;
|
|
7373
|
+
if (i === 0) {
|
|
7374
|
+
left = links[0].getBoundingClientRect().left - barThickness / 2;
|
|
7375
|
+
} else if (i === links.length) {
|
|
7376
|
+
const last = links[links.length - 1].getBoundingClientRect();
|
|
7377
|
+
left = last.right - barThickness / 2;
|
|
7378
|
+
} else {
|
|
7379
|
+
const prev = links[i - 1].getBoundingClientRect();
|
|
7380
|
+
const next = links[i].getBoundingClientRect();
|
|
7381
|
+
left = (prev.right + next.left) / 2 - barThickness / 2;
|
|
7382
|
+
}
|
|
7383
|
+
const heightRef = i === 0 ? links[0].getBoundingClientRect() : i === links.length ? links[links.length - 1].getBoundingClientRect() : links[i].getBoundingClientRect();
|
|
7384
|
+
slots.push({
|
|
7385
|
+
insertIndex: i,
|
|
7386
|
+
columnIndex,
|
|
7387
|
+
left,
|
|
7388
|
+
top: heightRef.top,
|
|
7389
|
+
width: barThickness,
|
|
7390
|
+
height: Math.max(heightRef.height, colRect.height * 0.8),
|
|
7391
|
+
direction: "vertical"
|
|
7392
|
+
});
|
|
7393
|
+
}
|
|
7394
|
+
return slots;
|
|
7395
|
+
}
|
|
7037
7396
|
for (let i = 0; i <= links.length; i++) {
|
|
7038
7397
|
let top;
|
|
7039
7398
|
if (i === 0) {
|
|
@@ -7117,8 +7476,7 @@ function hitTestLinkDropSlot(clientX, clientY, draggedHrefKey) {
|
|
|
7117
7476
|
return true;
|
|
7118
7477
|
});
|
|
7119
7478
|
for (const slot of slots) {
|
|
7120
|
-
const
|
|
7121
|
-
const dist = Math.abs(clientY - cy) + (inColX ? 0 : 1e3);
|
|
7479
|
+
const dist = slot.direction === "vertical" ? Math.abs(clientX - (slot.left + slot.width / 2)) : Math.abs(clientY - (slot.top + slot.height / 2));
|
|
7122
7480
|
if (!best || dist < best.dist) best = { slot, dist };
|
|
7123
7481
|
}
|
|
7124
7482
|
}
|
|
@@ -7142,6 +7500,30 @@ function hitTestColumnDropSlot(clientX, _clientY) {
|
|
|
7142
7500
|
return best?.slot ?? null;
|
|
7143
7501
|
}
|
|
7144
7502
|
|
|
7503
|
+
// src/lib/add-footer-column.ts
|
|
7504
|
+
function buildFooterColumnEditContentPatch(result) {
|
|
7505
|
+
return {
|
|
7506
|
+
[result.headingKey]: result.heading,
|
|
7507
|
+
[result.hrefKey]: result.href,
|
|
7508
|
+
[result.labelKey]: result.label,
|
|
7509
|
+
[FOOTER_ORDER_KEY]: JSON.stringify(result.order)
|
|
7510
|
+
};
|
|
7511
|
+
}
|
|
7512
|
+
function addFooterColumnWithPersist({
|
|
7513
|
+
postToParent: postToParent2
|
|
7514
|
+
}) {
|
|
7515
|
+
const result = insertFooterColumn();
|
|
7516
|
+
const patch = buildFooterColumnEditContentPatch(result);
|
|
7517
|
+
setStoredLinkHref(result.hrefKey, result.href);
|
|
7518
|
+
postToParent2({
|
|
7519
|
+
type: "ow:change",
|
|
7520
|
+
nodes: Object.entries(patch).map(([key, text]) => ({ key, text }))
|
|
7521
|
+
});
|
|
7522
|
+
postToParent2({ type: "ow:toast", title: "Item added", toastType: "success" });
|
|
7523
|
+
enforceLinkHrefs();
|
|
7524
|
+
return result;
|
|
7525
|
+
}
|
|
7526
|
+
|
|
7145
7527
|
// src/lib/item-drag-interaction.ts
|
|
7146
7528
|
function disableNativeHrefDrag(el) {
|
|
7147
7529
|
if (el.draggable) el.draggable = false;
|
|
@@ -7162,9 +7544,10 @@ function lockItemDuringDrag() {
|
|
|
7162
7544
|
clearTextSelection();
|
|
7163
7545
|
}
|
|
7164
7546
|
function unlockItemDragInteraction() {
|
|
7547
|
+
const wasDragging = document.documentElement.hasAttribute("data-ohw-item-dragging");
|
|
7165
7548
|
document.documentElement.removeAttribute("data-ohw-footer-press-drag");
|
|
7166
7549
|
document.documentElement.removeAttribute("data-ohw-item-dragging");
|
|
7167
|
-
clearTextSelection();
|
|
7550
|
+
if (wasDragging) clearTextSelection();
|
|
7168
7551
|
}
|
|
7169
7552
|
var armFooterPressDrag = armItemPressDrag;
|
|
7170
7553
|
var lockFooterDuringDrag = lockItemDuringDrag;
|
|
@@ -7541,7 +7924,6 @@ function useNavItemDrag({
|
|
|
7541
7924
|
const hrefKey = anchor?.getAttribute("data-ohw-href-key") ?? null;
|
|
7542
7925
|
if (!anchor || !isNavbarHrefKey(hrefKey)) return;
|
|
7543
7926
|
if (isNavbarButton3(anchor) || isDragHandleDisabled2(anchor)) return;
|
|
7544
|
-
armItemPressDrag();
|
|
7545
7927
|
navPointerDragRef.current = {
|
|
7546
7928
|
el: anchor,
|
|
7547
7929
|
startX: e.clientX,
|
|
@@ -7568,6 +7950,7 @@ function useNavItemDrag({
|
|
|
7568
7950
|
if (dx * dx + dy * dy < THRESHOLD * THRESHOLD) return;
|
|
7569
7951
|
e.preventDefault();
|
|
7570
7952
|
pending.started = true;
|
|
7953
|
+
armItemPressDrag();
|
|
7571
7954
|
clearTextSelection();
|
|
7572
7955
|
try {
|
|
7573
7956
|
document.body.setPointerCapture(pending.pointerId);
|
|
@@ -7595,7 +7978,8 @@ function useNavItemDrag({
|
|
|
7595
7978
|
}
|
|
7596
7979
|
} catch {
|
|
7597
7980
|
}
|
|
7598
|
-
if (!pending
|
|
7981
|
+
if (!pending) return;
|
|
7982
|
+
if (!pending.started) {
|
|
7599
7983
|
unlockItemDragInteraction();
|
|
7600
7984
|
return;
|
|
7601
7985
|
}
|
|
@@ -7647,7 +8031,6 @@ function useNavItemDrag({
|
|
|
7647
8031
|
const hrefKey = selected.getAttribute("data-ohw-href-key");
|
|
7648
8032
|
if (!hrefKey || !isNavbarHrefKey(hrefKey)) return false;
|
|
7649
8033
|
if (isNavbarButton3(selected) || isDragHandleDisabled2(selected)) return false;
|
|
7650
|
-
armItemPressDrag();
|
|
7651
8034
|
navPointerDragRef.current = {
|
|
7652
8035
|
el: selected,
|
|
7653
8036
|
startX: clientX,
|
|
@@ -7673,15 +8056,144 @@ function useNavItemDrag({
|
|
|
7673
8056
|
};
|
|
7674
8057
|
}
|
|
7675
8058
|
|
|
8059
|
+
// src/ui/footer-container-chrome.tsx
|
|
8060
|
+
var import_lucide_react11 = require("lucide-react");
|
|
8061
|
+
var import_jsx_runtime22 = require("react/jsx-runtime");
|
|
8062
|
+
function FooterContainerChrome({ rect, onAdd }) {
|
|
8063
|
+
const chromeGap = 6;
|
|
8064
|
+
const buttonMargin = 7;
|
|
8065
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TooltipProvider, { delayDuration: 0, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
8066
|
+
"div",
|
|
8067
|
+
{
|
|
8068
|
+
"data-ohw-footer-container-chrome": "",
|
|
8069
|
+
"data-ohw-bridge": "",
|
|
8070
|
+
className: "pointer-events-none fixed z-[2147483647]",
|
|
8071
|
+
style: {
|
|
8072
|
+
top: rect.top - chromeGap,
|
|
8073
|
+
left: rect.left - chromeGap,
|
|
8074
|
+
width: rect.width + chromeGap * 2,
|
|
8075
|
+
height: rect.height + chromeGap * 2
|
|
8076
|
+
},
|
|
8077
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(Tooltip, { children: [
|
|
8078
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
8079
|
+
"button",
|
|
8080
|
+
{
|
|
8081
|
+
type: "button",
|
|
8082
|
+
"data-ohw-footer-add-button": "",
|
|
8083
|
+
className: "pointer-events-auto absolute left-1/2 flex size-7 -translate-x-1/2 -translate-y-full items-center justify-center rounded-[10px] border border-border bg-background p-0.5 shadow-sm transition-colors hover:bg-muted/80",
|
|
8084
|
+
style: { top: chromeGap - buttonMargin },
|
|
8085
|
+
"aria-label": "Add item",
|
|
8086
|
+
onMouseDown: (e) => {
|
|
8087
|
+
e.preventDefault();
|
|
8088
|
+
e.stopPropagation();
|
|
8089
|
+
},
|
|
8090
|
+
onClick: (e) => {
|
|
8091
|
+
e.preventDefault();
|
|
8092
|
+
e.stopPropagation();
|
|
8093
|
+
onAdd();
|
|
8094
|
+
},
|
|
8095
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_lucide_react11.Plus, { className: "size-4 shrink-0 text-foreground", "aria-hidden": true })
|
|
8096
|
+
}
|
|
8097
|
+
) }),
|
|
8098
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TooltipContent, { side: "bottom", sideOffset: 9, children: "Add item" })
|
|
8099
|
+
] })
|
|
8100
|
+
}
|
|
8101
|
+
) });
|
|
8102
|
+
}
|
|
8103
|
+
|
|
8104
|
+
// src/lib/carousel.ts
|
|
8105
|
+
var import_react9 = require("react");
|
|
8106
|
+
var CAROUSEL_ATTR = "data-ohw-carousel";
|
|
8107
|
+
var CAROUSEL_VALUE_ATTR = "data-ohw-carousel-value";
|
|
8108
|
+
var CAROUSEL_SLIDE_ATTR = "data-ohw-carousel-slide";
|
|
8109
|
+
var CAROUSEL_EVENT = "ohw:carousel-change";
|
|
8110
|
+
function listCarouselKeys() {
|
|
8111
|
+
const keys = /* @__PURE__ */ new Set();
|
|
8112
|
+
document.querySelectorAll(`[${CAROUSEL_ATTR}]`).forEach((el) => {
|
|
8113
|
+
const key = el.getAttribute("data-ohw-key");
|
|
8114
|
+
if (key) keys.add(key);
|
|
8115
|
+
});
|
|
8116
|
+
return [...keys];
|
|
8117
|
+
}
|
|
8118
|
+
function containersForKey(key) {
|
|
8119
|
+
return Array.from(
|
|
8120
|
+
document.querySelectorAll(`[${CAROUSEL_ATTR}][data-ohw-key="${CSS.escape(key)}"]`)
|
|
8121
|
+
);
|
|
8122
|
+
}
|
|
8123
|
+
function isCarouselKey(key) {
|
|
8124
|
+
return containersForKey(key).length > 0;
|
|
8125
|
+
}
|
|
8126
|
+
function parseSlides(raw) {
|
|
8127
|
+
if (!raw) return [];
|
|
8128
|
+
try {
|
|
8129
|
+
const parsed = JSON.parse(raw);
|
|
8130
|
+
if (!Array.isArray(parsed)) return [];
|
|
8131
|
+
return parsed.filter((s) => Boolean(s) && typeof s === "object").map((s) => ({ src: String(s.src ?? ""), alt: String(s.alt ?? "") }));
|
|
8132
|
+
} catch {
|
|
8133
|
+
return [];
|
|
8134
|
+
}
|
|
8135
|
+
}
|
|
8136
|
+
function readCarouselValue(key) {
|
|
8137
|
+
const container = containersForKey(key)[0];
|
|
8138
|
+
if (!container) return [];
|
|
8139
|
+
const fromAttr = parseSlides(container.getAttribute(CAROUSEL_VALUE_ATTR));
|
|
8140
|
+
if (fromAttr.length > 0) return fromAttr;
|
|
8141
|
+
return Array.from(container.querySelectorAll(`[${CAROUSEL_SLIDE_ATTR}]`)).filter((slide) => slide.closest(`[${CAROUSEL_ATTR}]`) === container).sort((a, b) => slideIndex(a) - slideIndex(b)).map((slide) => {
|
|
8142
|
+
const img = slide instanceof HTMLImageElement ? slide : slide.querySelector("img");
|
|
8143
|
+
return { src: img?.src ?? "", alt: img?.alt ?? "" };
|
|
8144
|
+
});
|
|
8145
|
+
}
|
|
8146
|
+
function slideIndex(el) {
|
|
8147
|
+
const raw = el.getAttribute(CAROUSEL_SLIDE_ATTR);
|
|
8148
|
+
const n = raw ? parseInt(raw, 10) : NaN;
|
|
8149
|
+
return Number.isFinite(n) ? n : 0;
|
|
8150
|
+
}
|
|
8151
|
+
function applyCarouselValue(key, slides) {
|
|
8152
|
+
const value = JSON.stringify(slides);
|
|
8153
|
+
for (const container of containersForKey(key)) {
|
|
8154
|
+
if (container.getAttribute(CAROUSEL_VALUE_ATTR) === value) continue;
|
|
8155
|
+
container.setAttribute(CAROUSEL_VALUE_ATTR, value);
|
|
8156
|
+
container.dispatchEvent(
|
|
8157
|
+
new CustomEvent(CAROUSEL_EVENT, { detail: { images: slides } })
|
|
8158
|
+
);
|
|
8159
|
+
}
|
|
8160
|
+
}
|
|
8161
|
+
function applyCarouselNode(key, val) {
|
|
8162
|
+
if (!isCarouselKey(key)) return false;
|
|
8163
|
+
applyCarouselValue(key, parseSlides(val));
|
|
8164
|
+
return true;
|
|
8165
|
+
}
|
|
8166
|
+
function useOhwCarousel(key, initial) {
|
|
8167
|
+
const [images, setImages] = (0, import_react9.useState)(initial);
|
|
8168
|
+
(0, import_react9.useEffect)(() => {
|
|
8169
|
+
const el = document.querySelector(
|
|
8170
|
+
`[${CAROUSEL_ATTR}][data-ohw-key="${CSS.escape(key)}"]`
|
|
8171
|
+
);
|
|
8172
|
+
if (!el) return;
|
|
8173
|
+
const onChange = (e) => {
|
|
8174
|
+
const detail = e.detail;
|
|
8175
|
+
if (Array.isArray(detail?.images)) setImages(detail.images);
|
|
8176
|
+
};
|
|
8177
|
+
el.addEventListener(CAROUSEL_EVENT, onChange);
|
|
8178
|
+
return () => el.removeEventListener(CAROUSEL_EVENT, onChange);
|
|
8179
|
+
}, [key]);
|
|
8180
|
+
const bind = {
|
|
8181
|
+
[CAROUSEL_ATTR]: "",
|
|
8182
|
+
"data-ohw-key": key,
|
|
8183
|
+
[CAROUSEL_VALUE_ATTR]: JSON.stringify(images)
|
|
8184
|
+
};
|
|
8185
|
+
return { images, setImages, bind };
|
|
8186
|
+
}
|
|
8187
|
+
|
|
7676
8188
|
// src/ui/navbar-container-chrome.tsx
|
|
7677
|
-
var
|
|
7678
|
-
var
|
|
8189
|
+
var import_lucide_react12 = require("lucide-react");
|
|
8190
|
+
var import_jsx_runtime23 = require("react/jsx-runtime");
|
|
7679
8191
|
function NavbarContainerChrome({
|
|
7680
8192
|
rect,
|
|
7681
8193
|
onAdd
|
|
7682
8194
|
}) {
|
|
7683
8195
|
const chromeGap = 6;
|
|
7684
|
-
return /* @__PURE__ */ (0,
|
|
8196
|
+
return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
7685
8197
|
"div",
|
|
7686
8198
|
{
|
|
7687
8199
|
"data-ohw-navbar-container-chrome": "",
|
|
@@ -7693,7 +8205,7 @@ function NavbarContainerChrome({
|
|
|
7693
8205
|
width: rect.width + chromeGap * 2,
|
|
7694
8206
|
height: rect.height + chromeGap * 2
|
|
7695
8207
|
},
|
|
7696
|
-
children: /* @__PURE__ */ (0,
|
|
8208
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
7697
8209
|
"button",
|
|
7698
8210
|
{
|
|
7699
8211
|
type: "button",
|
|
@@ -7710,7 +8222,7 @@ function NavbarContainerChrome({
|
|
|
7710
8222
|
e.stopPropagation();
|
|
7711
8223
|
onAdd();
|
|
7712
8224
|
},
|
|
7713
|
-
children: /* @__PURE__ */ (0,
|
|
8225
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react12.Plus, { className: "size-4 shrink-0 text-foreground", "aria-hidden": true })
|
|
7714
8226
|
}
|
|
7715
8227
|
)
|
|
7716
8228
|
}
|
|
@@ -7719,7 +8231,7 @@ function NavbarContainerChrome({
|
|
|
7719
8231
|
|
|
7720
8232
|
// src/ui/drop-indicator.tsx
|
|
7721
8233
|
var React10 = __toESM(require("react"), 1);
|
|
7722
|
-
var
|
|
8234
|
+
var import_jsx_runtime24 = require("react/jsx-runtime");
|
|
7723
8235
|
var dropIndicatorVariants = cva(
|
|
7724
8236
|
"ov-gap-line pointer-events-none shrink-0 transition-opacity duration-150",
|
|
7725
8237
|
{
|
|
@@ -7743,7 +8255,7 @@ var dropIndicatorVariants = cva(
|
|
|
7743
8255
|
);
|
|
7744
8256
|
var DropIndicator = React10.forwardRef(
|
|
7745
8257
|
({ className, direction, state, ...props }, ref) => {
|
|
7746
|
-
return /* @__PURE__ */ (0,
|
|
8258
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
7747
8259
|
"div",
|
|
7748
8260
|
{
|
|
7749
8261
|
ref,
|
|
@@ -7760,7 +8272,7 @@ var DropIndicator = React10.forwardRef(
|
|
|
7760
8272
|
DropIndicator.displayName = "DropIndicator";
|
|
7761
8273
|
|
|
7762
8274
|
// src/ui/badge.tsx
|
|
7763
|
-
var
|
|
8275
|
+
var import_jsx_runtime25 = require("react/jsx-runtime");
|
|
7764
8276
|
var badgeVariants = cva(
|
|
7765
8277
|
"inline-flex items-center rounded-full border px-2.5 py-0.5 text-xs font-semibold transition-colors focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2",
|
|
7766
8278
|
{
|
|
@@ -7778,12 +8290,12 @@ var badgeVariants = cva(
|
|
|
7778
8290
|
}
|
|
7779
8291
|
);
|
|
7780
8292
|
function Badge({ className, variant, ...props }) {
|
|
7781
|
-
return /* @__PURE__ */ (0,
|
|
8293
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: cn(badgeVariants({ variant }), className), ...props });
|
|
7782
8294
|
}
|
|
7783
8295
|
|
|
7784
8296
|
// src/OhhwellsBridge.tsx
|
|
7785
|
-
var
|
|
7786
|
-
var
|
|
8297
|
+
var import_lucide_react13 = require("lucide-react");
|
|
8298
|
+
var import_jsx_runtime26 = require("react/jsx-runtime");
|
|
7787
8299
|
var PRIMARY2 = "#0885FE";
|
|
7788
8300
|
var IMAGE_FADE_MS = 300;
|
|
7789
8301
|
function runOpacityFade(el, onDone) {
|
|
@@ -7962,7 +8474,7 @@ function mountSchedulingWidget(insertAfter, notifyOnConnect = false, scheduleId,
|
|
|
7962
8474
|
const root = (0, import_client.createRoot)(container);
|
|
7963
8475
|
(0, import_react_dom2.flushSync)(() => {
|
|
7964
8476
|
root.render(
|
|
7965
|
-
/* @__PURE__ */ (0,
|
|
8477
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
7966
8478
|
SchedulingWidget,
|
|
7967
8479
|
{
|
|
7968
8480
|
notifyOnConnect,
|
|
@@ -8080,6 +8592,9 @@ function collectEditableNodes(extraContent) {
|
|
|
8080
8592
|
nodes.push({ key: `${key}${VIDEO_AUTOPLAY_SUFFIX}`, type: "video-setting", text: String(video.autoplay) });
|
|
8081
8593
|
nodes.push({ key: `${key}${VIDEO_MUTED_SUFFIX}`, type: "video-setting", text: String(video.muted) });
|
|
8082
8594
|
});
|
|
8595
|
+
for (const key of listCarouselKeys()) {
|
|
8596
|
+
nodes.push({ key, type: "carousel", text: JSON.stringify(readCarouselValue(key)) });
|
|
8597
|
+
}
|
|
8083
8598
|
const seen = /* @__PURE__ */ new Set();
|
|
8084
8599
|
return nodes.filter((node) => {
|
|
8085
8600
|
if (!node.key) return true;
|
|
@@ -8163,7 +8678,7 @@ function applyLinkByKey(key, val) {
|
|
|
8163
8678
|
}
|
|
8164
8679
|
function isInsideLinkEditor(target) {
|
|
8165
8680
|
return Boolean(
|
|
8166
|
-
target.closest("[data-ohw-link-popover-root]") || target.closest("[data-ohw-link-modal-root]") || target.closest("[data-ohw-link-page-dropdown]") || target.closest("[data-ohw-section-picker]") || target.closest("[data-ohw-navbar-container-chrome]") || target.closest("[data-ohw-navbar-add-button]") || target.closest('[data-slot="popover-content"]') || target.closest('[data-slot="dialog-content"]') || target.closest('[data-slot="dialog-overlay"]')
|
|
8681
|
+
target.closest("[data-ohw-link-popover-root]") || target.closest("[data-ohw-link-modal-root]") || target.closest("[data-ohw-link-page-dropdown]") || target.closest("[data-ohw-section-picker]") || target.closest("[data-ohw-navbar-container-chrome]") || target.closest("[data-ohw-navbar-add-button]") || target.closest("[data-ohw-footer-container-chrome]") || target.closest("[data-ohw-footer-add-button]") || target.closest('[data-slot="popover-content"]') || target.closest('[data-slot="dialog-content"]') || target.closest('[data-slot="dialog-overlay"]')
|
|
8167
8682
|
);
|
|
8168
8683
|
}
|
|
8169
8684
|
function getHrefKeyFromElement(el) {
|
|
@@ -8244,7 +8759,7 @@ function isInferredFooterGroup(el) {
|
|
|
8244
8759
|
return countFooterNavItems(el) >= 2;
|
|
8245
8760
|
}
|
|
8246
8761
|
function isNavigationContainer(el) {
|
|
8247
|
-
return el.hasAttribute("data-ohw-nav-container") || el.hasAttribute("data-ohw-footer-col") || el.hasAttribute("data-ohw-footer-column") || isNavigationRoot(el) || isInferredFooterGroup(el);
|
|
8762
|
+
return el.hasAttribute("data-ohw-nav-container") || isFooterLinksContainer(el) || el.hasAttribute("data-ohw-footer-col") || el.hasAttribute("data-ohw-footer-column") || isNavigationRoot(el) || isInferredFooterGroup(el);
|
|
8248
8763
|
}
|
|
8249
8764
|
function isNavbarLinksContainer(el) {
|
|
8250
8765
|
return el.hasAttribute("data-ohw-nav-container");
|
|
@@ -8263,6 +8778,9 @@ function isPointOverNavigation(x, y) {
|
|
|
8263
8778
|
const roots = /* @__PURE__ */ new Set();
|
|
8264
8779
|
const navRoot = document.querySelector("[data-ohw-nav-root]") ?? document.querySelector("nav");
|
|
8265
8780
|
if (navRoot) roots.add(navRoot);
|
|
8781
|
+
document.querySelectorAll("[data-ohw-nav-drawer], [data-ohw-nav-container]").forEach((el) => {
|
|
8782
|
+
roots.add(el);
|
|
8783
|
+
});
|
|
8266
8784
|
const footer = document.querySelector("footer");
|
|
8267
8785
|
if (footer) roots.add(footer);
|
|
8268
8786
|
for (const root of roots) {
|
|
@@ -8291,6 +8809,12 @@ function isPointOverNavItem(container, x, y) {
|
|
|
8291
8809
|
return x >= itemRect.left && x <= itemRect.right && y >= itemRect.top && y <= itemRect.bottom;
|
|
8292
8810
|
});
|
|
8293
8811
|
}
|
|
8812
|
+
function isPointOverFooterColumn(x, y) {
|
|
8813
|
+
return listFooterColumns().some((col) => {
|
|
8814
|
+
const r2 = col.getBoundingClientRect();
|
|
8815
|
+
return x >= r2.left && x <= r2.right && y >= r2.top && y <= r2.bottom;
|
|
8816
|
+
});
|
|
8817
|
+
}
|
|
8294
8818
|
function resolveNavContainerSelectionTarget(target, clientX, clientY) {
|
|
8295
8819
|
if (getNavigationItemAnchor(target)) return null;
|
|
8296
8820
|
if (target.closest('[data-ohw-role="navbar-button"]')) return null;
|
|
@@ -8321,7 +8845,10 @@ function getNavigationSelectionParent(el) {
|
|
|
8321
8845
|
if (footerGroup) return footerGroup;
|
|
8322
8846
|
return getNavigationRoot(el);
|
|
8323
8847
|
}
|
|
8324
|
-
if (el
|
|
8848
|
+
if (!isFooterLinksContainer(el) && (el.hasAttribute("data-ohw-footer-col") || el.hasAttribute("data-ohw-footer-column") || isInferredFooterGroup(el))) {
|
|
8849
|
+
return getFooterLinksContainer();
|
|
8850
|
+
}
|
|
8851
|
+
if (el.hasAttribute("data-ohw-nav-container") || el.hasAttribute("data-ohw-footer-col") || el.hasAttribute("data-ohw-footer-column") || isFooterLinksContainer(el) || isInferredFooterGroup(el)) {
|
|
8325
8852
|
return getNavigationRoot(el);
|
|
8326
8853
|
}
|
|
8327
8854
|
return null;
|
|
@@ -8492,9 +9019,16 @@ function sanitizeHtml(html) {
|
|
|
8492
9019
|
if (!SAFE_TAGS.has(el.tagName)) {
|
|
8493
9020
|
parent.replaceChild(document.createTextNode(el.textContent ?? ""), el);
|
|
8494
9021
|
} else {
|
|
8495
|
-
const
|
|
9022
|
+
const htmlEl = el;
|
|
9023
|
+
const textAlign = htmlEl.style?.textAlign || el.getAttribute("align") || "";
|
|
9024
|
+
const fontWeight = htmlEl.style?.fontWeight || "";
|
|
9025
|
+
const fontStyle = htmlEl.style?.fontStyle || "";
|
|
9026
|
+
const textDecorationLine = htmlEl.style?.textDecorationLine || htmlEl.style?.textDecoration || "";
|
|
8496
9027
|
for (const attr of Array.from(el.attributes)) el.removeAttribute(attr.name);
|
|
8497
|
-
if (textAlign)
|
|
9028
|
+
if (textAlign) htmlEl.style.textAlign = textAlign;
|
|
9029
|
+
if (fontWeight) htmlEl.style.fontWeight = fontWeight;
|
|
9030
|
+
if (fontStyle) htmlEl.style.fontStyle = fontStyle;
|
|
9031
|
+
if (textDecorationLine) htmlEl.style.textDecorationLine = textDecorationLine;
|
|
8498
9032
|
walk(el);
|
|
8499
9033
|
}
|
|
8500
9034
|
}
|
|
@@ -8541,7 +9075,7 @@ function EditGlowChrome({
|
|
|
8541
9075
|
hideHandle = false
|
|
8542
9076
|
}) {
|
|
8543
9077
|
const GAP = SELECTION_CHROME_GAP2;
|
|
8544
|
-
return /* @__PURE__ */ (0,
|
|
9078
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
|
|
8545
9079
|
"div",
|
|
8546
9080
|
{
|
|
8547
9081
|
ref: elRef,
|
|
@@ -8556,7 +9090,7 @@ function EditGlowChrome({
|
|
|
8556
9090
|
zIndex: 2147483646
|
|
8557
9091
|
},
|
|
8558
9092
|
children: [
|
|
8559
|
-
/* @__PURE__ */ (0,
|
|
9093
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8560
9094
|
"div",
|
|
8561
9095
|
{
|
|
8562
9096
|
style: {
|
|
@@ -8569,7 +9103,7 @@ function EditGlowChrome({
|
|
|
8569
9103
|
}
|
|
8570
9104
|
}
|
|
8571
9105
|
),
|
|
8572
|
-
reorderHrefKey && !hideHandle && /* @__PURE__ */ (0,
|
|
9106
|
+
reorderHrefKey && !hideHandle && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8573
9107
|
"div",
|
|
8574
9108
|
{
|
|
8575
9109
|
"data-ohw-drag-handle-container": "",
|
|
@@ -8581,7 +9115,7 @@ function EditGlowChrome({
|
|
|
8581
9115
|
transform: "translate(calc(-100% - 7px), -50%)",
|
|
8582
9116
|
pointerEvents: dragDisabled ? "none" : "auto"
|
|
8583
9117
|
},
|
|
8584
|
-
children: /* @__PURE__ */ (0,
|
|
9118
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8585
9119
|
DragHandle,
|
|
8586
9120
|
{
|
|
8587
9121
|
"aria-label": `Reorder ${reorderHrefKey}`,
|
|
@@ -8682,6 +9216,79 @@ function resolveItemInteractionState(rect, parentScroll) {
|
|
|
8682
9216
|
const { transform } = calcToolbarPos(rect, parentScroll, 120);
|
|
8683
9217
|
return transform.includes("translateY(-100%)") ? "active-top" : "active-bottom";
|
|
8684
9218
|
}
|
|
9219
|
+
function resolveSelectionStartElement(sel) {
|
|
9220
|
+
if (!sel || sel.rangeCount === 0) return null;
|
|
9221
|
+
const range = sel.getRangeAt(0);
|
|
9222
|
+
let startNode = range.startContainer;
|
|
9223
|
+
if (startNode.nodeType === Node.ELEMENT_NODE) {
|
|
9224
|
+
const el = startNode;
|
|
9225
|
+
startNode = el.childNodes[range.startOffset] ?? el.childNodes[range.startOffset - 1] ?? el;
|
|
9226
|
+
}
|
|
9227
|
+
return startNode.nodeType === Node.TEXT_NODE ? startNode.parentElement : startNode;
|
|
9228
|
+
}
|
|
9229
|
+
function detectActiveFormats(startEl, activeRoot) {
|
|
9230
|
+
const formats = /* @__PURE__ */ new Set();
|
|
9231
|
+
const cs = getComputedStyle(startEl);
|
|
9232
|
+
const weight = parseInt(cs.fontWeight, 10);
|
|
9233
|
+
let hasBold = cs.fontWeight === "bold" || !Number.isNaN(weight) && weight >= 600;
|
|
9234
|
+
let hasItalic = cs.fontStyle === "italic" || cs.fontStyle === "oblique";
|
|
9235
|
+
let hasUnderline = false;
|
|
9236
|
+
let hasStrike = false;
|
|
9237
|
+
let hasUl = false;
|
|
9238
|
+
let hasOl = false;
|
|
9239
|
+
for (let el = startEl; el; el = el.parentElement) {
|
|
9240
|
+
if (el.tagName === "B" || el.tagName === "STRONG") hasBold = true;
|
|
9241
|
+
if (el.tagName === "I" || el.tagName === "EM") hasItalic = true;
|
|
9242
|
+
const decoration = getComputedStyle(el).textDecorationLine;
|
|
9243
|
+
if (decoration.includes("underline") || el.tagName === "U" || el.tagName === "INS") hasUnderline = true;
|
|
9244
|
+
if (decoration.includes("line-through") || el.tagName === "S" || el.tagName === "STRIKE" || el.tagName === "DEL") hasStrike = true;
|
|
9245
|
+
if (el.tagName === "UL") hasUl = true;
|
|
9246
|
+
if (el.tagName === "OL") hasOl = true;
|
|
9247
|
+
if (el === activeRoot) break;
|
|
9248
|
+
}
|
|
9249
|
+
if (hasBold) formats.add("bold");
|
|
9250
|
+
if (hasItalic) formats.add("italic");
|
|
9251
|
+
if (hasUnderline) formats.add("underline");
|
|
9252
|
+
if (hasStrike) formats.add("strikeThrough");
|
|
9253
|
+
if (hasUl) formats.add("insertUnorderedList");
|
|
9254
|
+
if (hasOl) formats.add("insertOrderedList");
|
|
9255
|
+
const block = startEl.closest("div, p, h1, h2, h3, h4, h5, h6, li, td, th") ?? startEl;
|
|
9256
|
+
const align = getComputedStyle(block).textAlign;
|
|
9257
|
+
if (align === "center") formats.add("justifyCenter");
|
|
9258
|
+
else if (align === "right" || align === "end") formats.add("justifyRight");
|
|
9259
|
+
else formats.add("justifyLeft");
|
|
9260
|
+
return formats;
|
|
9261
|
+
}
|
|
9262
|
+
function setsEqual(a, b) {
|
|
9263
|
+
if (a.size !== b.size) return false;
|
|
9264
|
+
for (const item of a) {
|
|
9265
|
+
if (!b.has(item)) return false;
|
|
9266
|
+
}
|
|
9267
|
+
return true;
|
|
9268
|
+
}
|
|
9269
|
+
function textOffsetInRoot(root, node, offset) {
|
|
9270
|
+
const walker = document.createTreeWalker(root, NodeFilter.SHOW_TEXT);
|
|
9271
|
+
let total = 0;
|
|
9272
|
+
let current;
|
|
9273
|
+
while (current = walker.nextNode()) {
|
|
9274
|
+
if (current === node) return total + offset;
|
|
9275
|
+
total += (current.textContent ?? "").length;
|
|
9276
|
+
}
|
|
9277
|
+
return total;
|
|
9278
|
+
}
|
|
9279
|
+
function pointAtTextOffset(root, targetOffset) {
|
|
9280
|
+
const walker = document.createTreeWalker(root, NodeFilter.SHOW_TEXT);
|
|
9281
|
+
let total = 0;
|
|
9282
|
+
let current;
|
|
9283
|
+
let last = null;
|
|
9284
|
+
while (current = walker.nextNode()) {
|
|
9285
|
+
const len = (current.textContent ?? "").length;
|
|
9286
|
+
if (total + len >= targetOffset) return { node: current, offset: targetOffset - total };
|
|
9287
|
+
total += len;
|
|
9288
|
+
last = current;
|
|
9289
|
+
}
|
|
9290
|
+
return last ? { node: last, offset: (last.textContent ?? "").length } : null;
|
|
9291
|
+
}
|
|
8685
9292
|
function FloatingToolbar({
|
|
8686
9293
|
rect,
|
|
8687
9294
|
parentScroll,
|
|
@@ -8691,9 +9298,9 @@ function FloatingToolbar({
|
|
|
8691
9298
|
showEditLink,
|
|
8692
9299
|
onEditLink
|
|
8693
9300
|
}) {
|
|
8694
|
-
const localRef =
|
|
8695
|
-
const [measuredW, setMeasuredW] =
|
|
8696
|
-
const setRefs =
|
|
9301
|
+
const localRef = import_react10.default.useRef(null);
|
|
9302
|
+
const [measuredW, setMeasuredW] = import_react10.default.useState(330);
|
|
9303
|
+
const setRefs = import_react10.default.useCallback(
|
|
8697
9304
|
(node) => {
|
|
8698
9305
|
localRef.current = node;
|
|
8699
9306
|
if (typeof elRef === "function") elRef(node);
|
|
@@ -8705,7 +9312,7 @@ function FloatingToolbar({
|
|
|
8705
9312
|
},
|
|
8706
9313
|
[elRef]
|
|
8707
9314
|
);
|
|
8708
|
-
|
|
9315
|
+
import_react10.default.useLayoutEffect(() => {
|
|
8709
9316
|
const node = localRef.current;
|
|
8710
9317
|
if (!node) return;
|
|
8711
9318
|
const update = () => {
|
|
@@ -8718,7 +9325,7 @@ function FloatingToolbar({
|
|
|
8718
9325
|
return () => ro.disconnect();
|
|
8719
9326
|
}, [showEditLink, activeCommands]);
|
|
8720
9327
|
const { top, left, transform } = calcToolbarPos(rect, parentScroll, measuredW);
|
|
8721
|
-
return /* @__PURE__ */ (0,
|
|
9328
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8722
9329
|
"div",
|
|
8723
9330
|
{
|
|
8724
9331
|
ref: setRefs,
|
|
@@ -8730,12 +9337,12 @@ function FloatingToolbar({
|
|
|
8730
9337
|
zIndex: 2147483647,
|
|
8731
9338
|
pointerEvents: "auto"
|
|
8732
9339
|
},
|
|
8733
|
-
children: /* @__PURE__ */ (0,
|
|
8734
|
-
TOOLBAR_GROUPS.map((btns, gi) => /* @__PURE__ */ (0,
|
|
8735
|
-
gi > 0 && /* @__PURE__ */ (0,
|
|
9340
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(CustomToolbar, { children: [
|
|
9341
|
+
TOOLBAR_GROUPS.map((btns, gi) => /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(import_react10.default.Fragment, { children: [
|
|
9342
|
+
gi > 0 && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(CustomToolbarDivider, {}),
|
|
8736
9343
|
btns.map((btn) => {
|
|
8737
9344
|
const isActive = activeCommands.has(btn.cmd);
|
|
8738
|
-
return /* @__PURE__ */ (0,
|
|
9345
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8739
9346
|
CustomToolbarButton,
|
|
8740
9347
|
{
|
|
8741
9348
|
title: btn.title,
|
|
@@ -8744,7 +9351,7 @@ function FloatingToolbar({
|
|
|
8744
9351
|
e.preventDefault();
|
|
8745
9352
|
onCommand(btn.cmd);
|
|
8746
9353
|
},
|
|
8747
|
-
children: /* @__PURE__ */ (0,
|
|
9354
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8748
9355
|
"svg",
|
|
8749
9356
|
{
|
|
8750
9357
|
width: "16",
|
|
@@ -8765,7 +9372,7 @@ function FloatingToolbar({
|
|
|
8765
9372
|
);
|
|
8766
9373
|
})
|
|
8767
9374
|
] }, gi)),
|
|
8768
|
-
showEditLink ? /* @__PURE__ */ (0,
|
|
9375
|
+
showEditLink ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8769
9376
|
CustomToolbarButton,
|
|
8770
9377
|
{
|
|
8771
9378
|
type: "button",
|
|
@@ -8779,7 +9386,7 @@ function FloatingToolbar({
|
|
|
8779
9386
|
e.preventDefault();
|
|
8780
9387
|
e.stopPropagation();
|
|
8781
9388
|
},
|
|
8782
|
-
children: /* @__PURE__ */ (0,
|
|
9389
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(import_lucide_react13.Link, { className: "size-4 shrink-0", "aria-hidden": true })
|
|
8783
9390
|
}
|
|
8784
9391
|
) : null
|
|
8785
9392
|
] })
|
|
@@ -8796,7 +9403,7 @@ function StateToggle({
|
|
|
8796
9403
|
states,
|
|
8797
9404
|
onStateChange
|
|
8798
9405
|
}) {
|
|
8799
|
-
return /* @__PURE__ */ (0,
|
|
9406
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
8800
9407
|
ToggleGroup,
|
|
8801
9408
|
{
|
|
8802
9409
|
"data-ohw-state-toggle": "",
|
|
@@ -8810,7 +9417,7 @@ function StateToggle({
|
|
|
8810
9417
|
left: rect.right - 8,
|
|
8811
9418
|
transform: "translateX(-100%)"
|
|
8812
9419
|
},
|
|
8813
|
-
children: states.map((state) => /* @__PURE__ */ (0,
|
|
9420
|
+
children: states.map((state) => /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ToggleGroupItem, { value: state, size: "sm", children: state }, state))
|
|
8814
9421
|
}
|
|
8815
9422
|
);
|
|
8816
9423
|
}
|
|
@@ -8837,8 +9444,8 @@ function OhhwellsBridge() {
|
|
|
8837
9444
|
const router = (0, import_navigation2.useRouter)();
|
|
8838
9445
|
const searchParams = (0, import_navigation2.useSearchParams)();
|
|
8839
9446
|
const isEditMode = isEditSessionActive();
|
|
8840
|
-
const [bridgeRoot, setBridgeRoot] = (0,
|
|
8841
|
-
(0,
|
|
9447
|
+
const [bridgeRoot, setBridgeRoot] = (0, import_react10.useState)(null);
|
|
9448
|
+
(0, import_react10.useEffect)(() => {
|
|
8842
9449
|
const figtreeFontId = "ohw-figtree-font";
|
|
8843
9450
|
if (!document.getElementById(figtreeFontId)) {
|
|
8844
9451
|
const preconnect1 = Object.assign(document.createElement("link"), { rel: "preconnect", href: "https://fonts.googleapis.com" });
|
|
@@ -8866,97 +9473,99 @@ function OhhwellsBridge() {
|
|
|
8866
9473
|
const subdomainFromQuery = searchParams.get("subdomain");
|
|
8867
9474
|
const subdomain = resolveSubdomain(subdomainFromQuery);
|
|
8868
9475
|
useLinkHrefGuardian(pathname, subdomain, isEditMode);
|
|
8869
|
-
const postToParent2 = (0,
|
|
9476
|
+
const postToParent2 = (0, import_react10.useCallback)((data) => {
|
|
8870
9477
|
if (typeof window !== "undefined" && window.parent !== window) {
|
|
8871
9478
|
window.parent.postMessage(data, "*");
|
|
8872
9479
|
}
|
|
8873
9480
|
}, []);
|
|
8874
|
-
const [fetchState, setFetchState] = (0,
|
|
8875
|
-
const autoSaveTimers = (0,
|
|
8876
|
-
const activeElRef = (0,
|
|
8877
|
-
const
|
|
8878
|
-
const
|
|
8879
|
-
const
|
|
8880
|
-
const
|
|
8881
|
-
const
|
|
8882
|
-
const
|
|
8883
|
-
const
|
|
8884
|
-
const
|
|
8885
|
-
const
|
|
9481
|
+
const [fetchState, setFetchState] = (0, import_react10.useState)("idle");
|
|
9482
|
+
const autoSaveTimers = (0, import_react10.useRef)(/* @__PURE__ */ new Map());
|
|
9483
|
+
const activeElRef = (0, import_react10.useRef)(null);
|
|
9484
|
+
const pointerHeldRef = (0, import_react10.useRef)(false);
|
|
9485
|
+
const selectedElRef = (0, import_react10.useRef)(null);
|
|
9486
|
+
const selectedHrefKeyRef = (0, import_react10.useRef)(null);
|
|
9487
|
+
const selectedFooterColAttrRef = (0, import_react10.useRef)(null);
|
|
9488
|
+
const originalContentRef = (0, import_react10.useRef)(null);
|
|
9489
|
+
const activeStateElRef = (0, import_react10.useRef)(null);
|
|
9490
|
+
const parentScrollRef = (0, import_react10.useRef)(null);
|
|
9491
|
+
const visibleViewportRef = (0, import_react10.useRef)(null);
|
|
9492
|
+
const [dialogPortalContainer, setDialogPortalContainer] = (0, import_react10.useState)(null);
|
|
9493
|
+
const attachVisibleViewport = (0, import_react10.useCallback)((node) => {
|
|
8886
9494
|
visibleViewportRef.current = node;
|
|
8887
9495
|
setDialogPortalContainer(node);
|
|
8888
9496
|
if (node) applyVisibleViewport(node, parentScrollRef.current);
|
|
8889
9497
|
}, []);
|
|
8890
|
-
const toolbarElRef = (0,
|
|
8891
|
-
const glowElRef = (0,
|
|
8892
|
-
const hoveredImageRef = (0,
|
|
8893
|
-
const hoveredImageHasTextOverlapRef = (0,
|
|
8894
|
-
const dragOverElRef = (0,
|
|
8895
|
-
const [mediaHover, setMediaHover] = (0,
|
|
8896
|
-
const [
|
|
8897
|
-
const
|
|
8898
|
-
const
|
|
8899
|
-
const
|
|
8900
|
-
const
|
|
8901
|
-
const
|
|
9498
|
+
const toolbarElRef = (0, import_react10.useRef)(null);
|
|
9499
|
+
const glowElRef = (0, import_react10.useRef)(null);
|
|
9500
|
+
const hoveredImageRef = (0, import_react10.useRef)(null);
|
|
9501
|
+
const hoveredImageHasTextOverlapRef = (0, import_react10.useRef)(false);
|
|
9502
|
+
const dragOverElRef = (0, import_react10.useRef)(null);
|
|
9503
|
+
const [mediaHover, setMediaHover] = (0, import_react10.useState)(null);
|
|
9504
|
+
const [carouselHover, setCarouselHover] = (0, import_react10.useState)(null);
|
|
9505
|
+
const [uploadingRects, setUploadingRects] = (0, import_react10.useState)({});
|
|
9506
|
+
const hoveredGapRef = (0, import_react10.useRef)(null);
|
|
9507
|
+
const imageUnhoverTimerRef = (0, import_react10.useRef)(null);
|
|
9508
|
+
const imageShowTimerRef = (0, import_react10.useRef)(null);
|
|
9509
|
+
const editStylesRef = (0, import_react10.useRef)(null);
|
|
9510
|
+
const activateRef = (0, import_react10.useRef)(() => {
|
|
8902
9511
|
});
|
|
8903
|
-
const deactivateRef = (0,
|
|
9512
|
+
const deactivateRef = (0, import_react10.useRef)(() => {
|
|
8904
9513
|
});
|
|
8905
|
-
const selectRef = (0,
|
|
9514
|
+
const selectRef = (0, import_react10.useRef)(() => {
|
|
8906
9515
|
});
|
|
8907
|
-
const selectFrameRef = (0,
|
|
9516
|
+
const selectFrameRef = (0, import_react10.useRef)(() => {
|
|
8908
9517
|
});
|
|
8909
|
-
const deselectRef = (0,
|
|
9518
|
+
const deselectRef = (0, import_react10.useRef)(() => {
|
|
8910
9519
|
});
|
|
8911
|
-
const reselectNavigationItemRef = (0,
|
|
9520
|
+
const reselectNavigationItemRef = (0, import_react10.useRef)(() => {
|
|
8912
9521
|
});
|
|
8913
|
-
const commitNavigationTextEditRef = (0,
|
|
9522
|
+
const commitNavigationTextEditRef = (0, import_react10.useRef)(() => {
|
|
8914
9523
|
});
|
|
8915
|
-
const refreshActiveCommandsRef = (0,
|
|
9524
|
+
const refreshActiveCommandsRef = (0, import_react10.useRef)(() => {
|
|
8916
9525
|
});
|
|
8917
|
-
const postToParentRef = (0,
|
|
9526
|
+
const postToParentRef = (0, import_react10.useRef)(postToParent2);
|
|
8918
9527
|
postToParentRef.current = postToParent2;
|
|
8919
|
-
const sectionsLoadedRef = (0,
|
|
8920
|
-
const pendingScheduleConfigRequests = (0,
|
|
8921
|
-
const [toolbarRect, setToolbarRect] = (0,
|
|
8922
|
-
const [toolbarVariant, setToolbarVariant] = (0,
|
|
8923
|
-
const toolbarVariantRef = (0,
|
|
9528
|
+
const sectionsLoadedRef = (0, import_react10.useRef)(false);
|
|
9529
|
+
const pendingScheduleConfigRequests = (0, import_react10.useRef)([]);
|
|
9530
|
+
const [toolbarRect, setToolbarRect] = (0, import_react10.useState)(null);
|
|
9531
|
+
const [toolbarVariant, setToolbarVariant] = (0, import_react10.useState)("none");
|
|
9532
|
+
const toolbarVariantRef = (0, import_react10.useRef)("none");
|
|
8924
9533
|
toolbarVariantRef.current = toolbarVariant;
|
|
8925
|
-
const [selectedIsCta, setSelectedIsCta] = (0,
|
|
8926
|
-
const [reorderHrefKey, setReorderHrefKey] = (0,
|
|
8927
|
-
const [reorderDragDisabled, setReorderDragDisabled] = (0,
|
|
8928
|
-
const [toggleState, setToggleState] = (0,
|
|
8929
|
-
const [maxBadge, setMaxBadge] = (0,
|
|
8930
|
-
const [activeCommands, setActiveCommands] = (0,
|
|
8931
|
-
const [sectionGap, setSectionGap] = (0,
|
|
8932
|
-
const [toolbarShowEditLink, setToolbarShowEditLink] = (0,
|
|
8933
|
-
const hoveredNavContainerRef = (0,
|
|
8934
|
-
const [hoveredNavContainerRect, setHoveredNavContainerRect] = (0,
|
|
8935
|
-
const hoveredItemElRef = (0,
|
|
8936
|
-
const [hoveredItemRect, setHoveredItemRect] = (0,
|
|
8937
|
-
const siblingHintElRef = (0,
|
|
8938
|
-
const [siblingHintRect, setSiblingHintRect] = (0,
|
|
8939
|
-
const [siblingHintRects, setSiblingHintRects] = (0,
|
|
8940
|
-
const [isItemDragging, setIsItemDragging] = (0,
|
|
8941
|
-
const [isFooterFrameSelection, setIsFooterFrameSelection] = (0,
|
|
8942
|
-
const footerDragRef = (0,
|
|
8943
|
-
const [footerDropSlots, setFooterDropSlots] = (0,
|
|
8944
|
-
const [activeFooterDropIndex, setActiveFooterDropIndex] = (0,
|
|
8945
|
-
const [draggedItemRect, setDraggedItemRect] = (0,
|
|
8946
|
-
const footerPointerDragRef = (0,
|
|
8947
|
-
const suppressNextClickRef = (0,
|
|
8948
|
-
const suppressClickUntilRef = (0,
|
|
8949
|
-
const [linkPopover, setLinkPopover] = (0,
|
|
8950
|
-
const linkPopoverSessionRef = (0,
|
|
8951
|
-
const addNavAfterAnchorRef = (0,
|
|
8952
|
-
const editContentRef = (0,
|
|
8953
|
-
const [sitePages, setSitePages] = (0,
|
|
8954
|
-
const [sectionsByPath, setSectionsByPath] = (0,
|
|
8955
|
-
const sectionsPrefetchGenRef = (0,
|
|
8956
|
-
const setLinkPopoverRef = (0,
|
|
8957
|
-
const linkPopoverPanelRef = (0,
|
|
8958
|
-
const linkPopoverOpenRef = (0,
|
|
8959
|
-
const linkPopoverGraceUntilRef = (0,
|
|
9534
|
+
const [selectedIsCta, setSelectedIsCta] = (0, import_react10.useState)(false);
|
|
9535
|
+
const [reorderHrefKey, setReorderHrefKey] = (0, import_react10.useState)(null);
|
|
9536
|
+
const [reorderDragDisabled, setReorderDragDisabled] = (0, import_react10.useState)(false);
|
|
9537
|
+
const [toggleState, setToggleState] = (0, import_react10.useState)(null);
|
|
9538
|
+
const [maxBadge, setMaxBadge] = (0, import_react10.useState)(null);
|
|
9539
|
+
const [activeCommands, setActiveCommands] = (0, import_react10.useState)(/* @__PURE__ */ new Set());
|
|
9540
|
+
const [sectionGap, setSectionGap] = (0, import_react10.useState)(null);
|
|
9541
|
+
const [toolbarShowEditLink, setToolbarShowEditLink] = (0, import_react10.useState)(false);
|
|
9542
|
+
const hoveredNavContainerRef = (0, import_react10.useRef)(null);
|
|
9543
|
+
const [hoveredNavContainerRect, setHoveredNavContainerRect] = (0, import_react10.useState)(null);
|
|
9544
|
+
const hoveredItemElRef = (0, import_react10.useRef)(null);
|
|
9545
|
+
const [hoveredItemRect, setHoveredItemRect] = (0, import_react10.useState)(null);
|
|
9546
|
+
const siblingHintElRef = (0, import_react10.useRef)(null);
|
|
9547
|
+
const [siblingHintRect, setSiblingHintRect] = (0, import_react10.useState)(null);
|
|
9548
|
+
const [siblingHintRects, setSiblingHintRects] = (0, import_react10.useState)([]);
|
|
9549
|
+
const [isItemDragging, setIsItemDragging] = (0, import_react10.useState)(false);
|
|
9550
|
+
const [isFooterFrameSelection, setIsFooterFrameSelection] = (0, import_react10.useState)(false);
|
|
9551
|
+
const footerDragRef = (0, import_react10.useRef)(null);
|
|
9552
|
+
const [footerDropSlots, setFooterDropSlots] = (0, import_react10.useState)([]);
|
|
9553
|
+
const [activeFooterDropIndex, setActiveFooterDropIndex] = (0, import_react10.useState)(null);
|
|
9554
|
+
const [draggedItemRect, setDraggedItemRect] = (0, import_react10.useState)(null);
|
|
9555
|
+
const footerPointerDragRef = (0, import_react10.useRef)(null);
|
|
9556
|
+
const suppressNextClickRef = (0, import_react10.useRef)(false);
|
|
9557
|
+
const suppressClickUntilRef = (0, import_react10.useRef)(0);
|
|
9558
|
+
const [linkPopover, setLinkPopover] = (0, import_react10.useState)(null);
|
|
9559
|
+
const linkPopoverSessionRef = (0, import_react10.useRef)(null);
|
|
9560
|
+
const addNavAfterAnchorRef = (0, import_react10.useRef)(null);
|
|
9561
|
+
const editContentRef = (0, import_react10.useRef)({});
|
|
9562
|
+
const [sitePages, setSitePages] = (0, import_react10.useState)([]);
|
|
9563
|
+
const [sectionsByPath, setSectionsByPath] = (0, import_react10.useState)({});
|
|
9564
|
+
const sectionsPrefetchGenRef = (0, import_react10.useRef)(0);
|
|
9565
|
+
const setLinkPopoverRef = (0, import_react10.useRef)(setLinkPopover);
|
|
9566
|
+
const linkPopoverPanelRef = (0, import_react10.useRef)(null);
|
|
9567
|
+
const linkPopoverOpenRef = (0, import_react10.useRef)(false);
|
|
9568
|
+
const linkPopoverGraceUntilRef = (0, import_react10.useRef)(0);
|
|
8960
9569
|
setLinkPopoverRef.current = setLinkPopover;
|
|
8961
9570
|
linkPopoverSessionRef.current = linkPopover;
|
|
8962
9571
|
const {
|
|
@@ -8995,7 +9604,7 @@ function OhhwellsBridge() {
|
|
|
8995
9604
|
const bumpLinkPopoverGrace = () => {
|
|
8996
9605
|
linkPopoverGraceUntilRef.current = Date.now() + 350;
|
|
8997
9606
|
};
|
|
8998
|
-
const runSectionsPrefetch = (0,
|
|
9607
|
+
const runSectionsPrefetch = (0, import_react10.useCallback)((pages) => {
|
|
8999
9608
|
if (!isEditMode || shouldUseDevFixtures() || pages.length === 0) return;
|
|
9000
9609
|
const gen = ++sectionsPrefetchGenRef.current;
|
|
9001
9610
|
const paths = pages.map((p) => p.path);
|
|
@@ -9014,9 +9623,9 @@ function OhhwellsBridge() {
|
|
|
9014
9623
|
);
|
|
9015
9624
|
});
|
|
9016
9625
|
}, [isEditMode, pathname]);
|
|
9017
|
-
const runSectionsPrefetchRef = (0,
|
|
9626
|
+
const runSectionsPrefetchRef = (0, import_react10.useRef)(runSectionsPrefetch);
|
|
9018
9627
|
runSectionsPrefetchRef.current = runSectionsPrefetch;
|
|
9019
|
-
(0,
|
|
9628
|
+
(0, import_react10.useEffect)(() => {
|
|
9020
9629
|
if (!linkPopover) {
|
|
9021
9630
|
document.documentElement.removeAttribute("data-ohw-link-popover-open");
|
|
9022
9631
|
return;
|
|
@@ -9066,7 +9675,7 @@ function OhhwellsBridge() {
|
|
|
9066
9675
|
document.removeEventListener("touchmove", preventBackgroundScroll, scrollOpts);
|
|
9067
9676
|
};
|
|
9068
9677
|
}, [linkPopover, postToParent2]);
|
|
9069
|
-
(0,
|
|
9678
|
+
(0, import_react10.useEffect)(() => {
|
|
9070
9679
|
if (!isEditMode) return;
|
|
9071
9680
|
const useFixtures = shouldUseDevFixtures();
|
|
9072
9681
|
if (useFixtures) {
|
|
@@ -9090,14 +9699,14 @@ function OhhwellsBridge() {
|
|
|
9090
9699
|
if (!useFixtures) postToParent2({ type: "ow:request-site-pages" });
|
|
9091
9700
|
return () => window.removeEventListener("message", onSitePages);
|
|
9092
9701
|
}, [isEditMode, postToParent2]);
|
|
9093
|
-
(0,
|
|
9702
|
+
(0, import_react10.useEffect)(() => {
|
|
9094
9703
|
if (!isEditMode || shouldUseDevFixtures()) return;
|
|
9095
9704
|
void loadAllSectionsManifest().then((manifest) => {
|
|
9096
9705
|
if (Object.keys(manifest).length === 0) return;
|
|
9097
9706
|
setSectionsByPath((prev) => ({ ...manifest, ...prev }));
|
|
9098
9707
|
});
|
|
9099
9708
|
}, [isEditMode]);
|
|
9100
|
-
(0,
|
|
9709
|
+
(0, import_react10.useEffect)(() => {
|
|
9101
9710
|
const update = () => {
|
|
9102
9711
|
const el = activeElRef.current ?? selectedElRef.current;
|
|
9103
9712
|
if (el) setToolbarRect(getEditMeasureEl(el).getBoundingClientRect());
|
|
@@ -9121,10 +9730,10 @@ function OhhwellsBridge() {
|
|
|
9121
9730
|
vvp.removeEventListener("resize", update);
|
|
9122
9731
|
};
|
|
9123
9732
|
}, []);
|
|
9124
|
-
const refreshStateRules = (0,
|
|
9733
|
+
const refreshStateRules = (0, import_react10.useCallback)(() => {
|
|
9125
9734
|
editStylesRef.current?.forceHover && (editStylesRef.current.forceHover.textContent = collectStateRules());
|
|
9126
9735
|
}, []);
|
|
9127
|
-
const processConfigRequest = (0,
|
|
9736
|
+
const processConfigRequest = (0, import_react10.useCallback)((insertAfterVal) => {
|
|
9128
9737
|
const tracker = getSectionsTracker();
|
|
9129
9738
|
let entries = [];
|
|
9130
9739
|
try {
|
|
@@ -9147,7 +9756,7 @@ function OhhwellsBridge() {
|
|
|
9147
9756
|
}
|
|
9148
9757
|
window.postMessage({ type: "ow:schedule-config", insertAfter: insertAfterVal, scheduleId: null }, "*");
|
|
9149
9758
|
}, [isEditMode]);
|
|
9150
|
-
const deactivate = (0,
|
|
9759
|
+
const deactivate = (0, import_react10.useCallback)(() => {
|
|
9151
9760
|
const el = activeElRef.current;
|
|
9152
9761
|
if (!el) return;
|
|
9153
9762
|
const key = el.dataset.ohwKey;
|
|
@@ -9179,12 +9788,12 @@ function OhhwellsBridge() {
|
|
|
9179
9788
|
setToolbarShowEditLink(false);
|
|
9180
9789
|
postToParent2({ type: "ow:exit-edit" });
|
|
9181
9790
|
}, [postToParent2]);
|
|
9182
|
-
const clearSelectedAttr = (0,
|
|
9791
|
+
const clearSelectedAttr = (0, import_react10.useCallback)(() => {
|
|
9183
9792
|
document.querySelectorAll("[data-ohw-selected]").forEach((el) => {
|
|
9184
9793
|
el.removeAttribute("data-ohw-selected");
|
|
9185
9794
|
});
|
|
9186
9795
|
}, []);
|
|
9187
|
-
const deselect = (0,
|
|
9796
|
+
const deselect = (0, import_react10.useCallback)(() => {
|
|
9188
9797
|
clearSelectedAttr();
|
|
9189
9798
|
selectedElRef.current = null;
|
|
9190
9799
|
selectedHrefKeyRef.current = null;
|
|
@@ -9204,11 +9813,11 @@ function OhhwellsBridge() {
|
|
|
9204
9813
|
setToolbarVariant("none");
|
|
9205
9814
|
}
|
|
9206
9815
|
}, [clearSelectedAttr]);
|
|
9207
|
-
const markSelected = (0,
|
|
9816
|
+
const markSelected = (0, import_react10.useCallback)((el) => {
|
|
9208
9817
|
clearSelectedAttr();
|
|
9209
9818
|
el.setAttribute("data-ohw-selected", "");
|
|
9210
9819
|
}, [clearSelectedAttr]);
|
|
9211
|
-
const resolveHrefKeyElement = (0,
|
|
9820
|
+
const resolveHrefKeyElement = (0, import_react10.useCallback)((hrefKey) => {
|
|
9212
9821
|
if (isFooterHrefKey(hrefKey)) {
|
|
9213
9822
|
return document.querySelector(
|
|
9214
9823
|
`footer [data-ohw-href-key="${CSS.escape(hrefKey)}"]`
|
|
@@ -9223,7 +9832,7 @@ function OhhwellsBridge() {
|
|
|
9223
9832
|
`[data-ohw-href-key="${CSS.escape(hrefKey)}"]`
|
|
9224
9833
|
);
|
|
9225
9834
|
}, []);
|
|
9226
|
-
const resyncSelectedNavigationItem = (0,
|
|
9835
|
+
const resyncSelectedNavigationItem = (0, import_react10.useCallback)(() => {
|
|
9227
9836
|
const hrefKey = selectedHrefKeyRef.current;
|
|
9228
9837
|
if (hrefKey) {
|
|
9229
9838
|
const link = resolveHrefKeyElement(hrefKey);
|
|
@@ -9251,7 +9860,7 @@ function OhhwellsBridge() {
|
|
|
9251
9860
|
);
|
|
9252
9861
|
}
|
|
9253
9862
|
}, [resolveHrefKeyElement]);
|
|
9254
|
-
const reselectNavigationItem = (0,
|
|
9863
|
+
const reselectNavigationItem = (0, import_react10.useCallback)((navAnchor) => {
|
|
9255
9864
|
selectedElRef.current = navAnchor;
|
|
9256
9865
|
selectedHrefKeyRef.current = navAnchor.getAttribute("data-ohw-href-key");
|
|
9257
9866
|
selectedFooterColAttrRef.current = null;
|
|
@@ -9266,7 +9875,7 @@ function OhhwellsBridge() {
|
|
|
9266
9875
|
setToolbarShowEditLink(false);
|
|
9267
9876
|
setActiveCommands(/* @__PURE__ */ new Set());
|
|
9268
9877
|
}, [markSelected]);
|
|
9269
|
-
const commitNavigationTextEdit = (0,
|
|
9878
|
+
const commitNavigationTextEdit = (0, import_react10.useCallback)((navAnchor) => {
|
|
9270
9879
|
const el = activeElRef.current;
|
|
9271
9880
|
if (!el) return;
|
|
9272
9881
|
const key = el.dataset.ohwKey;
|
|
@@ -9293,7 +9902,7 @@ function OhhwellsBridge() {
|
|
|
9293
9902
|
postToParent2({ type: "ow:exit-edit" });
|
|
9294
9903
|
reselectNavigationItem(navAnchor);
|
|
9295
9904
|
}, [postToParent2, reselectNavigationItem]);
|
|
9296
|
-
const handleAddTopLevelNavItem = (0,
|
|
9905
|
+
const handleAddTopLevelNavItem = (0, import_react10.useCallback)(() => {
|
|
9297
9906
|
const items = listNavbarItems();
|
|
9298
9907
|
addNavAfterAnchorRef.current = items[items.length - 1] ?? null;
|
|
9299
9908
|
deselectRef.current();
|
|
@@ -9305,7 +9914,19 @@ function OhhwellsBridge() {
|
|
|
9305
9914
|
intent: "add-nav"
|
|
9306
9915
|
});
|
|
9307
9916
|
}, []);
|
|
9308
|
-
const
|
|
9917
|
+
const handleAddFooterColumn = (0, import_react10.useCallback)(() => {
|
|
9918
|
+
deselectRef.current();
|
|
9919
|
+
deactivateRef.current();
|
|
9920
|
+
const result = addFooterColumnWithPersist({ postToParent: postToParent2 });
|
|
9921
|
+
editContentRef.current = {
|
|
9922
|
+
...editContentRef.current,
|
|
9923
|
+
...buildFooterColumnEditContentPatch(result)
|
|
9924
|
+
};
|
|
9925
|
+
requestAnimationFrame(() => {
|
|
9926
|
+
selectRef.current(result.firstLink);
|
|
9927
|
+
});
|
|
9928
|
+
}, [postToParent2]);
|
|
9929
|
+
const clearFooterDragVisuals = (0, import_react10.useCallback)(() => {
|
|
9309
9930
|
footerDragRef.current = null;
|
|
9310
9931
|
setSiblingHintRects([]);
|
|
9311
9932
|
setFooterDropSlots([]);
|
|
@@ -9314,7 +9935,7 @@ function OhhwellsBridge() {
|
|
|
9314
9935
|
setIsItemDragging(false);
|
|
9315
9936
|
unlockFooterDragInteraction();
|
|
9316
9937
|
}, []);
|
|
9317
|
-
const refreshFooterDragVisuals = (0,
|
|
9938
|
+
const refreshFooterDragVisuals = (0, import_react10.useCallback)((session, activeSlot, clientX, clientY) => {
|
|
9318
9939
|
const dragged = session.draggedEl;
|
|
9319
9940
|
setDraggedItemRect(dragged.getBoundingClientRect());
|
|
9320
9941
|
if (typeof clientX === "number" && typeof clientY === "number") {
|
|
@@ -9339,13 +9960,13 @@ function OhhwellsBridge() {
|
|
|
9339
9960
|
const activeIdx = activeSlot ? slots.findIndex((s) => s.insertIndex === activeSlot.insertIndex) : -1;
|
|
9340
9961
|
setActiveFooterDropIndex(activeIdx >= 0 ? activeIdx : null);
|
|
9341
9962
|
}, []);
|
|
9342
|
-
const refreshFooterDragVisualsRef = (0,
|
|
9963
|
+
const refreshFooterDragVisualsRef = (0, import_react10.useRef)(refreshFooterDragVisuals);
|
|
9343
9964
|
refreshFooterDragVisualsRef.current = refreshFooterDragVisuals;
|
|
9344
|
-
const commitFooterDragRef = (0,
|
|
9965
|
+
const commitFooterDragRef = (0, import_react10.useRef)(() => {
|
|
9345
9966
|
});
|
|
9346
|
-
const beginFooterDragRef = (0,
|
|
9967
|
+
const beginFooterDragRef = (0, import_react10.useRef)(() => {
|
|
9347
9968
|
});
|
|
9348
|
-
const beginFooterDrag = (0,
|
|
9969
|
+
const beginFooterDrag = (0, import_react10.useCallback)(
|
|
9349
9970
|
(session) => {
|
|
9350
9971
|
const rect = session.draggedEl.getBoundingClientRect();
|
|
9351
9972
|
session.lastClientX = session.lastClientX || rect.left + rect.width / 2;
|
|
@@ -9365,7 +9986,7 @@ function OhhwellsBridge() {
|
|
|
9365
9986
|
[refreshFooterDragVisuals]
|
|
9366
9987
|
);
|
|
9367
9988
|
beginFooterDragRef.current = beginFooterDrag;
|
|
9368
|
-
const commitFooterDrag = (0,
|
|
9989
|
+
const commitFooterDrag = (0, import_react10.useCallback)(
|
|
9369
9990
|
(clientX, clientY) => {
|
|
9370
9991
|
const session = footerDragRef.current;
|
|
9371
9992
|
if (!session) {
|
|
@@ -9469,7 +10090,7 @@ function OhhwellsBridge() {
|
|
|
9469
10090
|
[clearFooterDragVisuals, resolveHrefKeyElement, resyncSelectedNavigationItem]
|
|
9470
10091
|
);
|
|
9471
10092
|
commitFooterDragRef.current = commitFooterDrag;
|
|
9472
|
-
const startFooterLinkDrag = (0,
|
|
10093
|
+
const startFooterLinkDrag = (0, import_react10.useCallback)(
|
|
9473
10094
|
(anchor, clientX, clientY, wasSelected) => {
|
|
9474
10095
|
const hrefKey = anchor.getAttribute("data-ohw-href-key");
|
|
9475
10096
|
if (!hrefKey || !isFooterHrefKey(hrefKey)) return false;
|
|
@@ -9490,7 +10111,7 @@ function OhhwellsBridge() {
|
|
|
9490
10111
|
},
|
|
9491
10112
|
[beginFooterDrag]
|
|
9492
10113
|
);
|
|
9493
|
-
const startFooterColumnDrag = (0,
|
|
10114
|
+
const startFooterColumnDrag = (0, import_react10.useCallback)(
|
|
9494
10115
|
(columnEl, clientX, clientY, wasSelected) => {
|
|
9495
10116
|
const columns = listFooterColumns();
|
|
9496
10117
|
const idx = columns.indexOf(columnEl);
|
|
@@ -9510,7 +10131,7 @@ function OhhwellsBridge() {
|
|
|
9510
10131
|
},
|
|
9511
10132
|
[beginFooterDrag]
|
|
9512
10133
|
);
|
|
9513
|
-
const handleItemDragStart = (0,
|
|
10134
|
+
const handleItemDragStart = (0, import_react10.useCallback)(
|
|
9514
10135
|
(e) => {
|
|
9515
10136
|
const selected = selectedElRef.current;
|
|
9516
10137
|
if (!selected) {
|
|
@@ -9530,7 +10151,7 @@ function OhhwellsBridge() {
|
|
|
9530
10151
|
},
|
|
9531
10152
|
[startFooterColumnDrag, startFooterLinkDrag, startNavLinkDrag]
|
|
9532
10153
|
);
|
|
9533
|
-
const handleItemDragEnd = (0,
|
|
10154
|
+
const handleItemDragEnd = (0, import_react10.useCallback)(
|
|
9534
10155
|
(e) => {
|
|
9535
10156
|
if (footerDragRef.current) {
|
|
9536
10157
|
const x = e?.clientX;
|
|
@@ -9556,11 +10177,10 @@ function OhhwellsBridge() {
|
|
|
9556
10177
|
},
|
|
9557
10178
|
[commitFooterDrag, commitNavDrag, navDragRef]
|
|
9558
10179
|
);
|
|
9559
|
-
const handleItemChromePointerDown = (0,
|
|
10180
|
+
const handleItemChromePointerDown = (0, import_react10.useCallback)((e) => {
|
|
9560
10181
|
if (e.button !== 0) return;
|
|
9561
10182
|
const selected = selectedElRef.current;
|
|
9562
10183
|
if (!selected) return;
|
|
9563
|
-
armFooterPressDrag();
|
|
9564
10184
|
const hrefKey = selected.getAttribute("data-ohw-href-key");
|
|
9565
10185
|
if (hrefKey && isFooterHrefKey(hrefKey)) {
|
|
9566
10186
|
footerPointerDragRef.current = {
|
|
@@ -9588,7 +10208,7 @@ function OhhwellsBridge() {
|
|
|
9588
10208
|
}
|
|
9589
10209
|
if (armNavPressFromChrome(selected, e.clientX, e.clientY, e.pointerId)) return;
|
|
9590
10210
|
}, [armNavPressFromChrome]);
|
|
9591
|
-
const handleItemChromeClick = (0,
|
|
10211
|
+
const handleItemChromeClick = (0, import_react10.useCallback)((clientX, clientY) => {
|
|
9592
10212
|
if (suppressNextClickRef.current || Date.now() < suppressClickUntilRef.current) {
|
|
9593
10213
|
suppressNextClickRef.current = false;
|
|
9594
10214
|
return;
|
|
@@ -9601,7 +10221,7 @@ function OhhwellsBridge() {
|
|
|
9601
10221
|
}, []);
|
|
9602
10222
|
reselectNavigationItemRef.current = reselectNavigationItem;
|
|
9603
10223
|
commitNavigationTextEditRef.current = commitNavigationTextEdit;
|
|
9604
|
-
const select = (0,
|
|
10224
|
+
const select = (0, import_react10.useCallback)((anchor) => {
|
|
9605
10225
|
if (!isNavigationItem(anchor)) return;
|
|
9606
10226
|
if (activeElRef.current) deactivate();
|
|
9607
10227
|
selectedElRef.current = anchor;
|
|
@@ -9627,10 +10247,10 @@ function OhhwellsBridge() {
|
|
|
9627
10247
|
setToolbarShowEditLink(false);
|
|
9628
10248
|
setActiveCommands(/* @__PURE__ */ new Set());
|
|
9629
10249
|
}, [deactivate, markSelected]);
|
|
9630
|
-
const selectFrame = (0,
|
|
10250
|
+
const selectFrame = (0, import_react10.useCallback)((el) => {
|
|
9631
10251
|
if (!isNavigationContainer(el)) return;
|
|
9632
10252
|
if (activeElRef.current) deactivate();
|
|
9633
|
-
const isFooterColumn = el.hasAttribute("data-ohw-footer-col") || Boolean(el.closest("footer") && isInferredFooterGroup(el));
|
|
10253
|
+
const isFooterColumn = !isFooterLinksContainer(el) && (el.hasAttribute("data-ohw-footer-col") || Boolean(el.closest("footer") && isInferredFooterGroup(el)));
|
|
9634
10254
|
selectedElRef.current = el;
|
|
9635
10255
|
selectedHrefKeyRef.current = null;
|
|
9636
10256
|
selectedFooterColAttrRef.current = isFooterColumn ? el.getAttribute("data-ohw-footer-col") ?? String(listFooterColumns().indexOf(el)) : null;
|
|
@@ -9655,7 +10275,7 @@ function OhhwellsBridge() {
|
|
|
9655
10275
|
setToolbarShowEditLink(false);
|
|
9656
10276
|
setActiveCommands(/* @__PURE__ */ new Set());
|
|
9657
10277
|
}, [deactivate, markSelected]);
|
|
9658
|
-
const activate = (0,
|
|
10278
|
+
const activate = (0, import_react10.useCallback)((el, options) => {
|
|
9659
10279
|
if (activeElRef.current === el) return;
|
|
9660
10280
|
clearSelectedAttr();
|
|
9661
10281
|
selectedElRef.current = null;
|
|
@@ -9672,6 +10292,8 @@ function OhhwellsBridge() {
|
|
|
9672
10292
|
setSiblingHintRect(null);
|
|
9673
10293
|
setSiblingHintRects([]);
|
|
9674
10294
|
setIsItemDragging(false);
|
|
10295
|
+
const preActivationSelection = window.getSelection();
|
|
10296
|
+
const preservedRange = preActivationSelection && preActivationSelection.rangeCount > 0 && !preActivationSelection.isCollapsed && el.contains(preActivationSelection.getRangeAt(0).commonAncestorContainer) ? preActivationSelection.getRangeAt(0).cloneRange() : null;
|
|
9675
10297
|
el.setAttribute("contenteditable", "true");
|
|
9676
10298
|
el.setAttribute("data-ohw-editing", "");
|
|
9677
10299
|
el.removeAttribute("data-ohw-hovered");
|
|
@@ -9679,7 +10301,11 @@ function OhhwellsBridge() {
|
|
|
9679
10301
|
activeElRef.current = el;
|
|
9680
10302
|
originalContentRef.current = el.innerHTML;
|
|
9681
10303
|
el.focus({ preventScroll: true });
|
|
9682
|
-
if (
|
|
10304
|
+
if (preservedRange) {
|
|
10305
|
+
const selection = window.getSelection();
|
|
10306
|
+
selection?.removeAllRanges();
|
|
10307
|
+
selection?.addRange(preservedRange);
|
|
10308
|
+
} else if (options?.caretX !== void 0 && options?.caretY !== void 0) {
|
|
9683
10309
|
const { caretX, caretY } = options;
|
|
9684
10310
|
placeCaretAtPoint(el, caretX, caretY);
|
|
9685
10311
|
requestAnimationFrame(() => {
|
|
@@ -9714,7 +10340,7 @@ function OhhwellsBridge() {
|
|
|
9714
10340
|
selectRef.current = select;
|
|
9715
10341
|
selectFrameRef.current = selectFrame;
|
|
9716
10342
|
deselectRef.current = deselect;
|
|
9717
|
-
(0,
|
|
10343
|
+
(0, import_react10.useLayoutEffect)(() => {
|
|
9718
10344
|
if (!subdomain || isEditMode) {
|
|
9719
10345
|
setFetchState("done");
|
|
9720
10346
|
return;
|
|
@@ -9724,6 +10350,7 @@ function OhhwellsBridge() {
|
|
|
9724
10350
|
for (const [key, val] of Object.entries(content)) {
|
|
9725
10351
|
if (key === "__ohw_sections") continue;
|
|
9726
10352
|
if (applyVideoSettingNode(key, val)) continue;
|
|
10353
|
+
if (applyCarouselNode(key, val)) continue;
|
|
9727
10354
|
document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
|
|
9728
10355
|
if (el.dataset.ohwEditable === "image") {
|
|
9729
10356
|
const img = el instanceof HTMLImageElement ? el : el.querySelector("img");
|
|
@@ -9784,7 +10411,7 @@ function OhhwellsBridge() {
|
|
|
9784
10411
|
cancelled = true;
|
|
9785
10412
|
};
|
|
9786
10413
|
}, [subdomain, isEditMode]);
|
|
9787
|
-
(0,
|
|
10414
|
+
(0, import_react10.useEffect)(() => {
|
|
9788
10415
|
if (!subdomain || isEditMode) return;
|
|
9789
10416
|
let debounceTimer = null;
|
|
9790
10417
|
let observer = null;
|
|
@@ -9797,6 +10424,7 @@ function OhhwellsBridge() {
|
|
|
9797
10424
|
for (const [key, val] of Object.entries(content)) {
|
|
9798
10425
|
if (key === "__ohw_sections") continue;
|
|
9799
10426
|
if (applyVideoSettingNode(key, val)) continue;
|
|
10427
|
+
if (applyCarouselNode(key, val)) continue;
|
|
9800
10428
|
document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
|
|
9801
10429
|
if (el.dataset.ohwEditable === "image") {
|
|
9802
10430
|
const img = el instanceof HTMLImageElement ? el : el.querySelector("img");
|
|
@@ -9834,16 +10462,16 @@ function OhhwellsBridge() {
|
|
|
9834
10462
|
if (debounceTimer) clearTimeout(debounceTimer);
|
|
9835
10463
|
};
|
|
9836
10464
|
}, [subdomain, isEditMode, pathname]);
|
|
9837
|
-
(0,
|
|
10465
|
+
(0, import_react10.useLayoutEffect)(() => {
|
|
9838
10466
|
const el = document.getElementById("ohw-loader");
|
|
9839
10467
|
if (!el) return;
|
|
9840
10468
|
const visible = Boolean(subdomain) && fetchState !== "done";
|
|
9841
10469
|
el.style.display = visible ? "flex" : "none";
|
|
9842
10470
|
}, [subdomain, fetchState]);
|
|
9843
|
-
(0,
|
|
10471
|
+
(0, import_react10.useEffect)(() => {
|
|
9844
10472
|
postToParent2({ type: "ow:navigation", path: pathname });
|
|
9845
10473
|
}, [pathname, postToParent2]);
|
|
9846
|
-
(0,
|
|
10474
|
+
(0, import_react10.useEffect)(() => {
|
|
9847
10475
|
if (!isEditMode) return;
|
|
9848
10476
|
if (linkPopoverSessionRef.current?.intent === "add-nav") return;
|
|
9849
10477
|
if (document.querySelector("[data-ohw-section-picker]")) return;
|
|
@@ -9851,7 +10479,7 @@ function OhhwellsBridge() {
|
|
|
9851
10479
|
deselectRef.current();
|
|
9852
10480
|
deactivateRef.current();
|
|
9853
10481
|
}, [pathname, isEditMode]);
|
|
9854
|
-
(0,
|
|
10482
|
+
(0, import_react10.useEffect)(() => {
|
|
9855
10483
|
const contentForNav = () => {
|
|
9856
10484
|
if (isEditMode) return editContentRef.current;
|
|
9857
10485
|
if (!subdomain) return {};
|
|
@@ -9916,7 +10544,7 @@ function OhhwellsBridge() {
|
|
|
9916
10544
|
observer?.disconnect();
|
|
9917
10545
|
};
|
|
9918
10546
|
}, [isEditMode, pathname, subdomain, fetchState, resyncSelectedNavigationItem]);
|
|
9919
|
-
(0,
|
|
10547
|
+
(0, import_react10.useEffect)(() => {
|
|
9920
10548
|
if (!isEditMode) return;
|
|
9921
10549
|
const measure = () => {
|
|
9922
10550
|
const h = document.body.scrollHeight;
|
|
@@ -9940,7 +10568,7 @@ function OhhwellsBridge() {
|
|
|
9940
10568
|
window.removeEventListener("resize", handleResize);
|
|
9941
10569
|
};
|
|
9942
10570
|
}, [pathname, isEditMode, postToParent2]);
|
|
9943
|
-
(0,
|
|
10571
|
+
(0, import_react10.useEffect)(() => {
|
|
9944
10572
|
if (!subdomainFromQuery || isEditMode) return;
|
|
9945
10573
|
const handleClick = (e) => {
|
|
9946
10574
|
const anchor = e.target.closest("a");
|
|
@@ -9956,7 +10584,7 @@ function OhhwellsBridge() {
|
|
|
9956
10584
|
document.addEventListener("click", handleClick, true);
|
|
9957
10585
|
return () => document.removeEventListener("click", handleClick, true);
|
|
9958
10586
|
}, [subdomainFromQuery, isEditMode, router]);
|
|
9959
|
-
(0,
|
|
10587
|
+
(0, import_react10.useEffect)(() => {
|
|
9960
10588
|
if (!isEditMode) {
|
|
9961
10589
|
editStylesRef.current?.base.remove();
|
|
9962
10590
|
editStylesRef.current?.forceHover.remove();
|
|
@@ -10135,7 +10763,9 @@ function OhhwellsBridge() {
|
|
|
10135
10763
|
if (inActive || inActiveNav) {
|
|
10136
10764
|
e.preventDefault();
|
|
10137
10765
|
e.stopPropagation();
|
|
10138
|
-
|
|
10766
|
+
const selection = window.getSelection();
|
|
10767
|
+
const hasRangeSelection = Boolean(selection && !selection.isCollapsed);
|
|
10768
|
+
if (e.detail < 2 && !hasRangeSelection) {
|
|
10139
10769
|
placeCaretAtPoint(active, e.clientX, e.clientY);
|
|
10140
10770
|
refreshActiveCommandsRef.current();
|
|
10141
10771
|
}
|
|
@@ -10178,7 +10808,7 @@ function OhhwellsBridge() {
|
|
|
10178
10808
|
}
|
|
10179
10809
|
e.preventDefault();
|
|
10180
10810
|
e.stopPropagation();
|
|
10181
|
-
activateRef.current(editable);
|
|
10811
|
+
activateRef.current(editable, { caretX: e.clientX, caretY: e.clientY });
|
|
10182
10812
|
return;
|
|
10183
10813
|
}
|
|
10184
10814
|
const hrefAnchor = getNavigationItemAnchor(target);
|
|
@@ -10205,6 +10835,18 @@ function OhhwellsBridge() {
|
|
|
10205
10835
|
selectFrameRef.current(footerColClick);
|
|
10206
10836
|
return;
|
|
10207
10837
|
}
|
|
10838
|
+
const footerLinksToSelect = resolveFooterLinksContainerSelectionTarget(
|
|
10839
|
+
target,
|
|
10840
|
+
e.clientX,
|
|
10841
|
+
e.clientY,
|
|
10842
|
+
isPointOverNavItem
|
|
10843
|
+
);
|
|
10844
|
+
if (footerLinksToSelect) {
|
|
10845
|
+
e.preventDefault();
|
|
10846
|
+
e.stopPropagation();
|
|
10847
|
+
selectFrameRef.current(footerLinksToSelect);
|
|
10848
|
+
return;
|
|
10849
|
+
}
|
|
10208
10850
|
const navContainerToSelect = resolveNavContainerSelectionTarget(target, e.clientX, e.clientY);
|
|
10209
10851
|
if (navContainerToSelect) {
|
|
10210
10852
|
e.preventDefault();
|
|
@@ -10263,8 +10905,8 @@ function OhhwellsBridge() {
|
|
|
10263
10905
|
return;
|
|
10264
10906
|
}
|
|
10265
10907
|
const navLabel = getNavigationLabelEditable(target);
|
|
10266
|
-
|
|
10267
|
-
|
|
10908
|
+
const editable = navLabel?.editable ?? target.closest('[data-ohw-editable="text"], [data-ohw-editable="plain"]');
|
|
10909
|
+
if (!editable || isMediaEditable(editable) || editable.dataset.ohwEditable === "link") return;
|
|
10268
10910
|
e.preventDefault();
|
|
10269
10911
|
e.stopPropagation();
|
|
10270
10912
|
if (activeElRef.current !== editable) {
|
|
@@ -10285,16 +10927,38 @@ function OhhwellsBridge() {
|
|
|
10285
10927
|
setHoveredNavContainerRect(null);
|
|
10286
10928
|
return;
|
|
10287
10929
|
}
|
|
10288
|
-
|
|
10289
|
-
const
|
|
10290
|
-
|
|
10291
|
-
|
|
10292
|
-
|
|
10293
|
-
|
|
10294
|
-
|
|
10295
|
-
|
|
10930
|
+
{
|
|
10931
|
+
const selected2 = selectedElRef.current;
|
|
10932
|
+
const selectedIsFooterColumn = Boolean(selected2) && !isFooterLinksContainer(selected2) && (selected2.hasAttribute("data-ohw-footer-col") || selected2.hasAttribute("data-ohw-footer-column") || Boolean(selected2.closest("footer") && isInferredFooterGroup(selected2)));
|
|
10933
|
+
const allowNavContainerHover = toolbarVariantRef.current !== "select-frame";
|
|
10934
|
+
const allowFooterLinksHover = toolbarVariantRef.current !== "select-frame" || selectedIsFooterColumn;
|
|
10935
|
+
if (allowNavContainerHover) {
|
|
10936
|
+
const navContainer = target.closest("[data-ohw-nav-container]");
|
|
10937
|
+
if (navContainer && !getNavigationItemAnchor(target)) {
|
|
10938
|
+
hoveredNavContainerRef.current = navContainer;
|
|
10939
|
+
setHoveredNavContainerRect(navContainer.getBoundingClientRect());
|
|
10940
|
+
hoveredItemElRef.current = null;
|
|
10941
|
+
setHoveredItemRect(null);
|
|
10942
|
+
return;
|
|
10943
|
+
}
|
|
10296
10944
|
}
|
|
10297
|
-
if (
|
|
10945
|
+
if (allowFooterLinksHover) {
|
|
10946
|
+
const navContainer = target.closest("[data-ohw-nav-container]");
|
|
10947
|
+
if (!navContainer) {
|
|
10948
|
+
const footerLinks = target.closest("[data-ohw-footer-links], .rb-footer-links") ?? null;
|
|
10949
|
+
if (footerLinks && selected2 !== footerLinks && !getNavigationItemAnchor(target) && !target.closest("[data-ohw-footer-col], [data-ohw-footer-column]")) {
|
|
10950
|
+
hoveredNavContainerRef.current = footerLinks;
|
|
10951
|
+
setHoveredNavContainerRect(footerLinks.getBoundingClientRect());
|
|
10952
|
+
hoveredItemElRef.current = null;
|
|
10953
|
+
setHoveredItemRect(null);
|
|
10954
|
+
return;
|
|
10955
|
+
}
|
|
10956
|
+
if (!footerLinks) {
|
|
10957
|
+
hoveredNavContainerRef.current = null;
|
|
10958
|
+
setHoveredNavContainerRect(null);
|
|
10959
|
+
}
|
|
10960
|
+
}
|
|
10961
|
+
} else if (toolbarVariantRef.current === "select-frame") {
|
|
10298
10962
|
hoveredNavContainerRef.current = null;
|
|
10299
10963
|
setHoveredNavContainerRect(null);
|
|
10300
10964
|
}
|
|
@@ -10336,9 +11000,9 @@ function OhhwellsBridge() {
|
|
|
10336
11000
|
};
|
|
10337
11001
|
const handleMouseOut = (e) => {
|
|
10338
11002
|
const target = e.target;
|
|
10339
|
-
if (target.closest("[data-ohw-nav-container], [data-ohw-footer-col], [data-ohw-footer-column]")) {
|
|
11003
|
+
if (target.closest("[data-ohw-nav-container], [data-ohw-footer-col], [data-ohw-footer-column], [data-ohw-footer-links], .rb-footer-links")) {
|
|
10340
11004
|
const related2 = e.relatedTarget instanceof Element ? e.relatedTarget : null;
|
|
10341
|
-
if (related2?.closest("[data-ohw-nav-container], [data-ohw-footer-col], [data-ohw-footer-column], [data-ohw-navbar-container-chrome], [data-ohw-navbar-add-button]")) {
|
|
11005
|
+
if (related2?.closest("[data-ohw-nav-container], [data-ohw-footer-col], [data-ohw-footer-column], [data-ohw-footer-links], .rb-footer-links, [data-ohw-navbar-container-chrome], [data-ohw-navbar-add-button], [data-ohw-footer-container-chrome], [data-ohw-footer-add-button]")) {
|
|
10342
11006
|
return;
|
|
10343
11007
|
}
|
|
10344
11008
|
hoveredNavContainerRef.current = null;
|
|
@@ -10433,6 +11097,15 @@ function OhhwellsBridge() {
|
|
|
10433
11097
|
if (track) track.setAttribute("data-ohw-hover-paused", "");
|
|
10434
11098
|
};
|
|
10435
11099
|
const clearImageHover = () => setMediaHover(null);
|
|
11100
|
+
const dismissImageHover = () => {
|
|
11101
|
+
if (hoveredImageRef.current) {
|
|
11102
|
+
hoveredImageRef.current = null;
|
|
11103
|
+
hoveredImageHasTextOverlapRef.current = false;
|
|
11104
|
+
resumeAnimTracks();
|
|
11105
|
+
postToParentRef.current({ type: "ow:image-unhover" });
|
|
11106
|
+
}
|
|
11107
|
+
clearImageHover();
|
|
11108
|
+
};
|
|
10436
11109
|
const findImageAtPoint = (clientX, clientY, fromParentViewport) => {
|
|
10437
11110
|
const { x, y } = toProbeCoords(clientX, clientY, fromParentViewport);
|
|
10438
11111
|
const images = Array.from(document.querySelectorAll(MEDIA_SELECTOR));
|
|
@@ -10476,16 +11149,13 @@ function OhhwellsBridge() {
|
|
|
10476
11149
|
}
|
|
10477
11150
|
return smallest;
|
|
10478
11151
|
};
|
|
10479
|
-
const dismissImageHover = () => {
|
|
10480
|
-
if (hoveredImageRef.current) {
|
|
10481
|
-
hoveredImageRef.current = null;
|
|
10482
|
-
hoveredImageHasTextOverlapRef.current = false;
|
|
10483
|
-
resumeAnimTracks();
|
|
10484
|
-
postToParentRef.current({ type: "ow:image-unhover" });
|
|
10485
|
-
}
|
|
10486
|
-
};
|
|
10487
11152
|
const probeNavigationHoverAt = (x, y) => {
|
|
10488
|
-
|
|
11153
|
+
const selected = selectedElRef.current;
|
|
11154
|
+
const selectedIsFooterColumn = Boolean(selected) && !isFooterLinksContainer(selected) && (selected.hasAttribute("data-ohw-footer-col") || selected.hasAttribute("data-ohw-footer-column") || Boolean(selected.closest("footer") && isInferredFooterGroup(selected)));
|
|
11155
|
+
const selectedIsFooterLinks = Boolean(selected && isFooterLinksContainer(selected));
|
|
11156
|
+
const allowNavContainerHover = toolbarVariantRef.current !== "select-frame";
|
|
11157
|
+
const allowFooterLinksHover = (toolbarVariantRef.current !== "select-frame" || selectedIsFooterColumn) && !selectedIsFooterLinks;
|
|
11158
|
+
if (toolbarVariantRef.current === "select-frame" && !allowFooterLinksHover) {
|
|
10489
11159
|
hoveredNavContainerRef.current = null;
|
|
10490
11160
|
setHoveredNavContainerRect(null);
|
|
10491
11161
|
}
|
|
@@ -10507,7 +11177,6 @@ function OhhwellsBridge() {
|
|
|
10507
11177
|
if (navItemHit) {
|
|
10508
11178
|
hoveredNavContainerRef.current = null;
|
|
10509
11179
|
setHoveredNavContainerRect(null);
|
|
10510
|
-
const selected = selectedElRef.current;
|
|
10511
11180
|
if (selected !== navItemHit) {
|
|
10512
11181
|
clearHrefKeyHover(navItemHit);
|
|
10513
11182
|
hoveredItemElRef.current = navItemHit;
|
|
@@ -10519,7 +11188,7 @@ function OhhwellsBridge() {
|
|
|
10519
11188
|
return;
|
|
10520
11189
|
}
|
|
10521
11190
|
}
|
|
10522
|
-
if (
|
|
11191
|
+
if (allowNavContainerHover) {
|
|
10523
11192
|
for (const container of navContainers) {
|
|
10524
11193
|
const containerRect = container.getBoundingClientRect();
|
|
10525
11194
|
const overContainer = x >= containerRect.left && x <= containerRect.right && y >= containerRect.top && y <= containerRect.bottom;
|
|
@@ -10531,12 +11200,23 @@ function OhhwellsBridge() {
|
|
|
10531
11200
|
setHoveredItemRect(null);
|
|
10532
11201
|
return;
|
|
10533
11202
|
}
|
|
10534
|
-
hoveredNavContainerRef.current = null;
|
|
10535
|
-
setHoveredNavContainerRect(null);
|
|
10536
|
-
} else {
|
|
10537
|
-
hoveredNavContainerRef.current = null;
|
|
10538
|
-
setHoveredNavContainerRect(null);
|
|
10539
11203
|
}
|
|
11204
|
+
if (allowFooterLinksHover) {
|
|
11205
|
+
const footerLinks = getFooterLinksContainer();
|
|
11206
|
+
if (footerLinks) {
|
|
11207
|
+
const containerRect = footerLinks.getBoundingClientRect();
|
|
11208
|
+
const overContainer = x >= containerRect.left && x <= containerRect.right && y >= containerRect.top && y <= containerRect.bottom;
|
|
11209
|
+
if (overContainer && !isPointOverNavItem(footerLinks, x, y) && !isPointOverFooterColumn(x, y)) {
|
|
11210
|
+
hoveredNavContainerRef.current = footerLinks;
|
|
11211
|
+
setHoveredNavContainerRect(footerLinks.getBoundingClientRect());
|
|
11212
|
+
hoveredItemElRef.current = null;
|
|
11213
|
+
setHoveredItemRect(null);
|
|
11214
|
+
return;
|
|
11215
|
+
}
|
|
11216
|
+
}
|
|
11217
|
+
}
|
|
11218
|
+
hoveredNavContainerRef.current = null;
|
|
11219
|
+
setHoveredNavContainerRect(null);
|
|
10540
11220
|
for (const column of footerColumns) {
|
|
10541
11221
|
const containerRect = column.getBoundingClientRect();
|
|
10542
11222
|
const overContainer = x >= containerRect.left && x <= containerRect.right && y >= containerRect.top && y <= containerRect.bottom;
|
|
@@ -10798,6 +11478,7 @@ function OhhwellsBridge() {
|
|
|
10798
11478
|
const ZONE = 20;
|
|
10799
11479
|
for (let i = 0; i < sections.length; i++) {
|
|
10800
11480
|
const a = sections[i];
|
|
11481
|
+
if (a.dataset.ohwSection === "footer") continue;
|
|
10801
11482
|
const b = sections[i + 1] ?? null;
|
|
10802
11483
|
const boundaryY = a.getBoundingClientRect().bottom;
|
|
10803
11484
|
if (Math.abs(y - boundaryY) <= ZONE) {
|
|
@@ -11019,6 +11700,7 @@ function OhhwellsBridge() {
|
|
|
11019
11700
|
continue;
|
|
11020
11701
|
}
|
|
11021
11702
|
if (applyVideoSettingNode(key, val)) continue;
|
|
11703
|
+
if (applyCarouselNode(key, val)) continue;
|
|
11022
11704
|
document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
|
|
11023
11705
|
if (el.dataset.ohwEditable === "image") {
|
|
11024
11706
|
const img = el instanceof HTMLImageElement ? el : el.querySelector("img");
|
|
@@ -11043,6 +11725,7 @@ function OhhwellsBridge() {
|
|
|
11043
11725
|
}
|
|
11044
11726
|
editContentRef.current = { ...editContentRef.current, ...content };
|
|
11045
11727
|
reconcileNavbarItemsFromContent(editContentRef.current);
|
|
11728
|
+
reconcileFooterOrderFromContent(editContentRef.current);
|
|
11046
11729
|
syncNavigationDragCursorAttrs();
|
|
11047
11730
|
enforceLinkHrefs();
|
|
11048
11731
|
postToParentRef.current({ type: "ow:hydrate-done" });
|
|
@@ -11097,6 +11780,11 @@ function OhhwellsBridge() {
|
|
|
11097
11780
|
}
|
|
11098
11781
|
if (selectedElRef.current) {
|
|
11099
11782
|
if (toolbarVariantRef.current === "select-frame") {
|
|
11783
|
+
const parent2 = getNavigationSelectionParent(selectedElRef.current);
|
|
11784
|
+
if (parent2 && isNavigationContainer(parent2) && isFooterLinksContainer(parent2) && !isFooterLinksContainer(selectedElRef.current)) {
|
|
11785
|
+
selectFrameRef.current(parent2);
|
|
11786
|
+
return;
|
|
11787
|
+
}
|
|
11100
11788
|
deselectRef.current();
|
|
11101
11789
|
return;
|
|
11102
11790
|
}
|
|
@@ -11112,13 +11800,10 @@ function OhhwellsBridge() {
|
|
|
11112
11800
|
const handleKeyDown = (e) => {
|
|
11113
11801
|
if (e.key === "Escape" && document.querySelector("[data-ohw-section-picker]")) return;
|
|
11114
11802
|
if ((e.ctrlKey || e.metaKey) && e.key.toLowerCase() === "a" && activeElRef.current) {
|
|
11115
|
-
|
|
11116
|
-
|
|
11117
|
-
|
|
11118
|
-
|
|
11119
|
-
refreshActiveCommandsRef.current();
|
|
11120
|
-
return;
|
|
11121
|
-
}
|
|
11803
|
+
e.preventDefault();
|
|
11804
|
+
selectAllTextInEditable(activeElRef.current);
|
|
11805
|
+
refreshActiveCommandsRef.current();
|
|
11806
|
+
return;
|
|
11122
11807
|
}
|
|
11123
11808
|
if (e.key === "Escape" && linkPopoverOpenRef.current) {
|
|
11124
11809
|
setLinkPopoverRef.current(null);
|
|
@@ -11126,6 +11811,12 @@ function OhhwellsBridge() {
|
|
|
11126
11811
|
}
|
|
11127
11812
|
if (e.key === "Escape" && selectedElRef.current && !activeElRef.current) {
|
|
11128
11813
|
if (toolbarVariantRef.current === "select-frame") {
|
|
11814
|
+
const parent2 = getNavigationSelectionParent(selectedElRef.current);
|
|
11815
|
+
if (parent2 && isNavigationContainer(parent2) && isFooterLinksContainer(parent2) && !isFooterLinksContainer(selectedElRef.current)) {
|
|
11816
|
+
e.preventDefault();
|
|
11817
|
+
selectFrameRef.current(parent2);
|
|
11818
|
+
return;
|
|
11819
|
+
}
|
|
11129
11820
|
deselectRef.current();
|
|
11130
11821
|
return;
|
|
11131
11822
|
}
|
|
@@ -11288,33 +11979,34 @@ function OhhwellsBridge() {
|
|
|
11288
11979
|
const h = document.documentElement.scrollHeight;
|
|
11289
11980
|
if (h > 50) postToParentRef.current({ type: "ow:height", height: h });
|
|
11290
11981
|
};
|
|
11982
|
+
let selectionChangeRaf = null;
|
|
11983
|
+
const runSelectionChange = () => {
|
|
11984
|
+
selectionChangeRaf = null;
|
|
11985
|
+
const activeRoot = activeElRef.current;
|
|
11986
|
+
if (!activeRoot) return;
|
|
11987
|
+
const startEl = resolveSelectionStartElement(window.getSelection());
|
|
11988
|
+
const next = startEl ? detectActiveFormats(startEl, activeRoot) : /* @__PURE__ */ new Set();
|
|
11989
|
+
setActiveCommands((prev) => setsEqual(prev, next) ? prev : next);
|
|
11990
|
+
};
|
|
11291
11991
|
const handleSelectionChange = () => {
|
|
11292
|
-
if (
|
|
11293
|
-
|
|
11294
|
-
|
|
11295
|
-
try {
|
|
11296
|
-
if (document.queryCommandState(cmd)) next.add(cmd);
|
|
11297
|
-
} catch {
|
|
11298
|
-
}
|
|
11299
|
-
}
|
|
11300
|
-
const sel = window.getSelection();
|
|
11301
|
-
const anchor = sel?.anchorNode;
|
|
11302
|
-
if (anchor) {
|
|
11303
|
-
const el = anchor.nodeType === Node.TEXT_NODE ? anchor.parentElement : anchor;
|
|
11304
|
-
const block = el?.closest("div, p, h1, h2, h3, h4, h5, h6, li, td, th") ?? el;
|
|
11305
|
-
if (block) {
|
|
11306
|
-
const align = getComputedStyle(block).textAlign;
|
|
11307
|
-
if (align === "center") next.add("justifyCenter");
|
|
11308
|
-
else if (align === "right" || align === "end") next.add("justifyRight");
|
|
11309
|
-
else next.add("justifyLeft");
|
|
11310
|
-
}
|
|
11311
|
-
}
|
|
11312
|
-
setActiveCommands(next);
|
|
11992
|
+
if (pointerHeldRef.current) return;
|
|
11993
|
+
if (selectionChangeRaf !== null) return;
|
|
11994
|
+
selectionChangeRaf = requestAnimationFrame(runSelectionChange);
|
|
11313
11995
|
};
|
|
11314
|
-
|
|
11996
|
+
const markPointerHeld = (e) => {
|
|
11997
|
+
if (e.button !== 0) return;
|
|
11998
|
+
pointerHeldRef.current = true;
|
|
11999
|
+
};
|
|
12000
|
+
const markPointerReleased = () => {
|
|
12001
|
+
if (!pointerHeldRef.current) return;
|
|
12002
|
+
pointerHeldRef.current = false;
|
|
12003
|
+
handleSelectionChange();
|
|
12004
|
+
};
|
|
12005
|
+
refreshActiveCommandsRef.current = runSelectionChange;
|
|
11315
12006
|
const handleDocMouseLeave = () => {
|
|
11316
12007
|
hoveredImageRef.current = null;
|
|
11317
12008
|
setMediaHover(null);
|
|
12009
|
+
setCarouselHover(null);
|
|
11318
12010
|
document.querySelectorAll("[data-ohw-state-hovered]").forEach((el) => el.removeAttribute("data-ohw-state-hovered"));
|
|
11319
12011
|
document.querySelectorAll("[data-ohw-hovered]").forEach((el) => el.removeAttribute("data-ohw-hovered"));
|
|
11320
12012
|
activeStateElRef.current = null;
|
|
@@ -11354,6 +12046,48 @@ function OhhwellsBridge() {
|
|
|
11354
12046
|
if (e.data?.type !== "ow:canvas-height" || typeof e.data.height !== "number") return;
|
|
11355
12047
|
document.documentElement.style.setProperty("--ohw-canvas-h", `${e.data.height}px`);
|
|
11356
12048
|
};
|
|
12049
|
+
const handleCarouselChange = (e) => {
|
|
12050
|
+
if (e.data?.type !== "ow:carousel-change") return;
|
|
12051
|
+
const { key, images } = e.data;
|
|
12052
|
+
if (!key || !Array.isArray(images)) return;
|
|
12053
|
+
const text = JSON.stringify(images);
|
|
12054
|
+
applyCarouselValue(key, images);
|
|
12055
|
+
editContentRef.current = { ...editContentRef.current, [key]: text };
|
|
12056
|
+
postToParentRef.current({ type: "ow:change", nodes: [{ key, text }] });
|
|
12057
|
+
setCarouselHover(null);
|
|
12058
|
+
};
|
|
12059
|
+
const findCarouselAtPoint = (clientX, clientY) => {
|
|
12060
|
+
const containers = Array.from(document.querySelectorAll(`[${CAROUSEL_ATTR}]`));
|
|
12061
|
+
for (let i = containers.length - 1; i >= 0; i--) {
|
|
12062
|
+
const r2 = containers[i].getBoundingClientRect();
|
|
12063
|
+
if (clientX >= r2.left && clientX <= r2.right && clientY >= r2.top && clientY <= r2.bottom) {
|
|
12064
|
+
return containers[i];
|
|
12065
|
+
}
|
|
12066
|
+
}
|
|
12067
|
+
return null;
|
|
12068
|
+
};
|
|
12069
|
+
const isPointOverEditable = (scope, clientX, clientY) => {
|
|
12070
|
+
const editables = scope.querySelectorAll("[data-ohw-editable], [data-ohw-href-key]");
|
|
12071
|
+
for (const el of editables) {
|
|
12072
|
+
const r2 = el.getBoundingClientRect();
|
|
12073
|
+
if (clientX >= r2.left && clientX <= r2.right && clientY >= r2.top && clientY <= r2.bottom) return true;
|
|
12074
|
+
}
|
|
12075
|
+
return false;
|
|
12076
|
+
};
|
|
12077
|
+
const handleCarouselHover = (e) => {
|
|
12078
|
+
const container = findCarouselAtPoint(e.clientX, e.clientY);
|
|
12079
|
+
const scope = container?.closest("[data-ohw-section]") ?? container?.parentElement ?? null;
|
|
12080
|
+
if (!container || !scope || isPointOverEditable(scope, e.clientX, e.clientY)) {
|
|
12081
|
+
setCarouselHover((prev) => prev ? null : prev);
|
|
12082
|
+
return;
|
|
12083
|
+
}
|
|
12084
|
+
const key = container.getAttribute("data-ohw-key") ?? "";
|
|
12085
|
+
if (!key) return;
|
|
12086
|
+
const r2 = getVisibleRect(container);
|
|
12087
|
+
setCarouselHover(
|
|
12088
|
+
(prev) => prev && prev.key === key && prev.rect.top === r2.top && prev.rect.left === r2.left && prev.rect.width === r2.width && prev.rect.height === r2.height ? prev : { key, rect: { top: r2.top, left: r2.left, width: r2.width, height: r2.height } }
|
|
12089
|
+
);
|
|
12090
|
+
};
|
|
11357
12091
|
const applyToolbarPos = (rect) => {
|
|
11358
12092
|
const ps = parentScrollRef.current;
|
|
11359
12093
|
const measuredW = toolbarElRef.current?.offsetWidth || 330;
|
|
@@ -11467,6 +12201,7 @@ function OhhwellsBridge() {
|
|
|
11467
12201
|
window.addEventListener("message", handleRemoveSchedulingSection);
|
|
11468
12202
|
window.addEventListener("message", handleImageUrl);
|
|
11469
12203
|
window.addEventListener("message", handleImageUploading);
|
|
12204
|
+
window.addEventListener("message", handleCarouselChange);
|
|
11470
12205
|
window.addEventListener("message", handleCanvasHeight);
|
|
11471
12206
|
window.addEventListener("message", handleParentScroll);
|
|
11472
12207
|
window.addEventListener("message", handlePointerSync);
|
|
@@ -11484,6 +12219,7 @@ function OhhwellsBridge() {
|
|
|
11484
12219
|
document.addEventListener("mouseover", handleMouseOver, true);
|
|
11485
12220
|
document.addEventListener("mouseout", handleMouseOut, true);
|
|
11486
12221
|
document.addEventListener("mousemove", handleMouseMove, true);
|
|
12222
|
+
document.addEventListener("mousemove", handleCarouselHover, true);
|
|
11487
12223
|
document.addEventListener("mouseleave", handleDocMouseLeave);
|
|
11488
12224
|
document.addEventListener("dragover", handleDragOver, true);
|
|
11489
12225
|
document.addEventListener("dragleave", handleDragLeave, true);
|
|
@@ -11499,6 +12235,7 @@ function OhhwellsBridge() {
|
|
|
11499
12235
|
document.removeEventListener("mouseover", handleMouseOver, true);
|
|
11500
12236
|
document.removeEventListener("mouseout", handleMouseOut, true);
|
|
11501
12237
|
document.removeEventListener("mousemove", handleMouseMove, true);
|
|
12238
|
+
document.removeEventListener("mousemove", handleCarouselHover, true);
|
|
11502
12239
|
document.removeEventListener("mouseleave", handleDocMouseLeave);
|
|
11503
12240
|
document.removeEventListener("dragover", handleDragOver, true);
|
|
11504
12241
|
document.removeEventListener("dragleave", handleDragLeave, true);
|
|
@@ -11514,6 +12251,7 @@ function OhhwellsBridge() {
|
|
|
11514
12251
|
window.removeEventListener("message", handleRemoveSchedulingSection);
|
|
11515
12252
|
window.removeEventListener("message", handleImageUrl);
|
|
11516
12253
|
window.removeEventListener("message", handleImageUploading);
|
|
12254
|
+
window.removeEventListener("message", handleCarouselChange);
|
|
11517
12255
|
window.removeEventListener("message", handleCanvasHeight);
|
|
11518
12256
|
window.removeEventListener("message", handleParentScroll);
|
|
11519
12257
|
window.removeEventListener("resize", handleViewportResize);
|
|
@@ -11528,7 +12266,7 @@ function OhhwellsBridge() {
|
|
|
11528
12266
|
if (imageShowTimerRef.current) clearTimeout(imageShowTimerRef.current);
|
|
11529
12267
|
};
|
|
11530
12268
|
}, [isEditMode, refreshStateRules]);
|
|
11531
|
-
(0,
|
|
12269
|
+
(0, import_react10.useEffect)(() => {
|
|
11532
12270
|
if (!isEditMode) return;
|
|
11533
12271
|
const THRESHOLD = 10;
|
|
11534
12272
|
const resolveWasSelected = (el) => {
|
|
@@ -11551,7 +12289,6 @@ function OhhwellsBridge() {
|
|
|
11551
12289
|
const anchor = getNavigationItemAnchor(target);
|
|
11552
12290
|
const hrefKey = anchor?.getAttribute("data-ohw-href-key") ?? null;
|
|
11553
12291
|
if (anchor && isFooterHrefKey(hrefKey)) {
|
|
11554
|
-
armFooterPressDrag();
|
|
11555
12292
|
footerPointerDragRef.current = {
|
|
11556
12293
|
el: anchor,
|
|
11557
12294
|
kind: "link",
|
|
@@ -11565,7 +12302,6 @@ function OhhwellsBridge() {
|
|
|
11565
12302
|
}
|
|
11566
12303
|
const col = target.closest("[data-ohw-footer-col]");
|
|
11567
12304
|
if (col && !getNavigationItemAnchor(target)) {
|
|
11568
|
-
armFooterPressDrag();
|
|
11569
12305
|
footerPointerDragRef.current = {
|
|
11570
12306
|
el: col,
|
|
11571
12307
|
kind: "column",
|
|
@@ -11594,6 +12330,7 @@ function OhhwellsBridge() {
|
|
|
11594
12330
|
if (dx * dx + dy * dy < THRESHOLD * THRESHOLD) return;
|
|
11595
12331
|
e.preventDefault();
|
|
11596
12332
|
pending.started = true;
|
|
12333
|
+
armFooterPressDrag();
|
|
11597
12334
|
clearTextSelection();
|
|
11598
12335
|
try {
|
|
11599
12336
|
document.body.setPointerCapture(pending.pointerId);
|
|
@@ -11647,7 +12384,8 @@ function OhhwellsBridge() {
|
|
|
11647
12384
|
}
|
|
11648
12385
|
} catch {
|
|
11649
12386
|
}
|
|
11650
|
-
if (!pending
|
|
12387
|
+
if (!pending) return;
|
|
12388
|
+
if (!pending.started) {
|
|
11651
12389
|
unlockFooterDragInteraction();
|
|
11652
12390
|
return;
|
|
11653
12391
|
}
|
|
@@ -11682,7 +12420,7 @@ function OhhwellsBridge() {
|
|
|
11682
12420
|
unlockFooterDragInteraction();
|
|
11683
12421
|
};
|
|
11684
12422
|
}, [isEditMode]);
|
|
11685
|
-
(0,
|
|
12423
|
+
(0, import_react10.useEffect)(() => {
|
|
11686
12424
|
const handler = (e) => {
|
|
11687
12425
|
if (e.data?.type !== "ow:request-schedule-config") return;
|
|
11688
12426
|
const insertAfterVal = e.data.insertAfter;
|
|
@@ -11698,7 +12436,7 @@ function OhhwellsBridge() {
|
|
|
11698
12436
|
window.addEventListener("message", handler);
|
|
11699
12437
|
return () => window.removeEventListener("message", handler);
|
|
11700
12438
|
}, [processConfigRequest]);
|
|
11701
|
-
(0,
|
|
12439
|
+
(0, import_react10.useEffect)(() => {
|
|
11702
12440
|
if (!isEditMode) return;
|
|
11703
12441
|
document.querySelectorAll("[data-ohw-active-state]").forEach((el) => {
|
|
11704
12442
|
el.removeAttribute("data-ohw-active-state");
|
|
@@ -11733,19 +12471,49 @@ function OhhwellsBridge() {
|
|
|
11733
12471
|
clearTimeout(timer);
|
|
11734
12472
|
};
|
|
11735
12473
|
}, [pathname, isEditMode, refreshStateRules, postToParent2]);
|
|
11736
|
-
(0,
|
|
12474
|
+
(0, import_react10.useEffect)(() => {
|
|
11737
12475
|
scrollToHashSectionWhenReady();
|
|
11738
12476
|
const onHashChange = () => scrollToHashSectionWhenReady();
|
|
11739
12477
|
window.addEventListener("hashchange", onHashChange);
|
|
11740
12478
|
return () => window.removeEventListener("hashchange", onHashChange);
|
|
11741
12479
|
}, [pathname]);
|
|
11742
|
-
const handleCommand = (0,
|
|
12480
|
+
const handleCommand = (0, import_react10.useCallback)((cmd) => {
|
|
12481
|
+
const el = activeElRef.current;
|
|
12482
|
+
const selBefore = window.getSelection();
|
|
12483
|
+
let savedOffsets = null;
|
|
12484
|
+
if (el && selBefore && selBefore.rangeCount > 0 && !selBefore.isCollapsed) {
|
|
12485
|
+
const r2 = selBefore.getRangeAt(0);
|
|
12486
|
+
if (el.contains(r2.commonAncestorContainer)) {
|
|
12487
|
+
savedOffsets = {
|
|
12488
|
+
start: textOffsetInRoot(el, r2.startContainer, r2.startOffset),
|
|
12489
|
+
end: textOffsetInRoot(el, r2.endContainer, r2.endOffset)
|
|
12490
|
+
};
|
|
12491
|
+
}
|
|
12492
|
+
}
|
|
12493
|
+
document.execCommand("styleWithCSS", false, true);
|
|
11743
12494
|
document.execCommand(cmd, false);
|
|
11744
|
-
|
|
11745
|
-
|
|
12495
|
+
if (el && document.activeElement !== el) {
|
|
12496
|
+
el.focus();
|
|
12497
|
+
}
|
|
12498
|
+
const selAfter = window.getSelection();
|
|
12499
|
+
if (el && savedOffsets && selAfter?.isCollapsed) {
|
|
12500
|
+
const start = pointAtTextOffset(el, savedOffsets.start);
|
|
12501
|
+
const end = pointAtTextOffset(el, savedOffsets.end);
|
|
12502
|
+
if (start && end) {
|
|
12503
|
+
try {
|
|
12504
|
+
const range = document.createRange();
|
|
12505
|
+
range.setStart(start.node, start.offset);
|
|
12506
|
+
range.setEnd(end.node, end.offset);
|
|
12507
|
+
selAfter.removeAllRanges();
|
|
12508
|
+
selAfter.addRange(range);
|
|
12509
|
+
} catch {
|
|
12510
|
+
}
|
|
12511
|
+
}
|
|
12512
|
+
}
|
|
12513
|
+
if (el) setToolbarRect(getEditMeasureEl(el).getBoundingClientRect());
|
|
11746
12514
|
refreshActiveCommandsRef.current();
|
|
11747
12515
|
}, []);
|
|
11748
|
-
const handleStateChange = (0,
|
|
12516
|
+
const handleStateChange = (0, import_react10.useCallback)((state) => {
|
|
11749
12517
|
if (!activeStateElRef.current) return;
|
|
11750
12518
|
const el = activeStateElRef.current;
|
|
11751
12519
|
if (state === "Default") {
|
|
@@ -11758,11 +12526,11 @@ function OhhwellsBridge() {
|
|
|
11758
12526
|
}
|
|
11759
12527
|
setToggleState((prev) => prev ? { ...prev, activeState: state } : null);
|
|
11760
12528
|
}, [deactivate]);
|
|
11761
|
-
const closeLinkPopover = (0,
|
|
12529
|
+
const closeLinkPopover = (0, import_react10.useCallback)(() => {
|
|
11762
12530
|
addNavAfterAnchorRef.current = null;
|
|
11763
12531
|
setLinkPopover(null);
|
|
11764
12532
|
}, []);
|
|
11765
|
-
const openLinkPopoverForActive = (0,
|
|
12533
|
+
const openLinkPopoverForActive = (0, import_react10.useCallback)(() => {
|
|
11766
12534
|
const hrefCtx = getHrefKeyFromElement(activeElRef.current);
|
|
11767
12535
|
if (!hrefCtx) return;
|
|
11768
12536
|
bumpLinkPopoverGrace();
|
|
@@ -11773,7 +12541,7 @@ function OhhwellsBridge() {
|
|
|
11773
12541
|
});
|
|
11774
12542
|
deactivate();
|
|
11775
12543
|
}, [deactivate]);
|
|
11776
|
-
const openLinkPopoverForSelected = (0,
|
|
12544
|
+
const openLinkPopoverForSelected = (0, import_react10.useCallback)(() => {
|
|
11777
12545
|
const anchor = selectedElRef.current;
|
|
11778
12546
|
if (!anchor) return;
|
|
11779
12547
|
const key = anchor.getAttribute("data-ohw-href-key");
|
|
@@ -11786,7 +12554,7 @@ function OhhwellsBridge() {
|
|
|
11786
12554
|
});
|
|
11787
12555
|
deselect();
|
|
11788
12556
|
}, [deselect]);
|
|
11789
|
-
const handleLinkPopoverSubmit = (0,
|
|
12557
|
+
const handleLinkPopoverSubmit = (0, import_react10.useCallback)(
|
|
11790
12558
|
(target) => {
|
|
11791
12559
|
const session = linkPopoverSessionRef.current;
|
|
11792
12560
|
if (!session) return;
|
|
@@ -11845,13 +12613,19 @@ function OhhwellsBridge() {
|
|
|
11845
12613
|
const showEditLink = toolbarShowEditLink;
|
|
11846
12614
|
const currentSections = sectionsByPath[pathname] ?? [];
|
|
11847
12615
|
linkPopoverOpenRef.current = linkPopover !== null;
|
|
11848
|
-
const handleMediaReplace = (0,
|
|
12616
|
+
const handleMediaReplace = (0, import_react10.useCallback)(
|
|
11849
12617
|
(key) => {
|
|
11850
12618
|
postToParent2({ type: "ow:image-pick", key, elementType: mediaHover?.elementType ?? "image" });
|
|
11851
12619
|
},
|
|
11852
12620
|
[postToParent2, mediaHover?.elementType]
|
|
11853
12621
|
);
|
|
11854
|
-
const
|
|
12622
|
+
const handleEditCarousel = (0, import_react10.useCallback)(
|
|
12623
|
+
(key) => {
|
|
12624
|
+
postToParent2({ type: "ow:carousel-open", key, images: readCarouselValue(key) });
|
|
12625
|
+
},
|
|
12626
|
+
[postToParent2]
|
|
12627
|
+
);
|
|
12628
|
+
const handleMediaFadeOutComplete = (0, import_react10.useCallback)((key) => {
|
|
11855
12629
|
setUploadingRects((prev) => {
|
|
11856
12630
|
if (!(key in prev)) return prev;
|
|
11857
12631
|
const next = { ...prev };
|
|
@@ -11859,7 +12633,7 @@ function OhhwellsBridge() {
|
|
|
11859
12633
|
return next;
|
|
11860
12634
|
});
|
|
11861
12635
|
}, []);
|
|
11862
|
-
const handleVideoSettingsChange = (0,
|
|
12636
|
+
const handleVideoSettingsChange = (0, import_react10.useCallback)(
|
|
11863
12637
|
(key, settings) => {
|
|
11864
12638
|
document.querySelectorAll(`[data-ohw-key="${key}"]`).forEach((el) => {
|
|
11865
12639
|
const video = getVideoEl(el);
|
|
@@ -11882,9 +12656,9 @@ function OhhwellsBridge() {
|
|
|
11882
12656
|
[postToParent2]
|
|
11883
12657
|
);
|
|
11884
12658
|
return bridgeRoot ? (0, import_react_dom3.createPortal)(
|
|
11885
|
-
/* @__PURE__ */ (0,
|
|
11886
|
-
/* @__PURE__ */ (0,
|
|
11887
|
-
Object.entries(uploadingRects).map(([key, { rect, fadingOut }]) => /* @__PURE__ */ (0,
|
|
12659
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(import_jsx_runtime26.Fragment, { children: [
|
|
12660
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { ref: attachVisibleViewport, "data-ohw-visible-viewport": "", "aria-hidden": true }),
|
|
12661
|
+
Object.entries(uploadingRects).map(([key, { rect, fadingOut }]) => /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11888
12662
|
MediaOverlay,
|
|
11889
12663
|
{
|
|
11890
12664
|
hover: { key, rect, elementType: "image", isDragOver: false, hasTextOverlap: false },
|
|
@@ -11895,7 +12669,7 @@ function OhhwellsBridge() {
|
|
|
11895
12669
|
},
|
|
11896
12670
|
`uploading-${key}`
|
|
11897
12671
|
)),
|
|
11898
|
-
mediaHover && !(mediaHover.key in uploadingRects) && /* @__PURE__ */ (0,
|
|
12672
|
+
mediaHover && !(mediaHover.key in uploadingRects) && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11899
12673
|
MediaOverlay,
|
|
11900
12674
|
{
|
|
11901
12675
|
hover: mediaHover,
|
|
@@ -11904,10 +12678,11 @@ function OhhwellsBridge() {
|
|
|
11904
12678
|
onVideoSettingsChange: handleVideoSettingsChange
|
|
11905
12679
|
}
|
|
11906
12680
|
),
|
|
11907
|
-
|
|
11908
|
-
|
|
11909
|
-
|
|
11910
|
-
isItemDragging &&
|
|
12681
|
+
carouselHover && !linkPopover && !isItemDragging && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(CarouselOverlay, { hover: carouselHover, onEdit: handleEditCarousel }),
|
|
12682
|
+
siblingHintRect && !linkPopover && !isItemDragging && siblingHintRects.length === 0 && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ItemInteractionLayer, { rect: siblingHintRect, state: "sibling-hint" }),
|
|
12683
|
+
siblingHintRects.length > 0 && !linkPopover && !isItemDragging && siblingHintRects.map((rect, i) => /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ItemInteractionLayer, { rect, state: "sibling-hint" }, `sibling-hint-${i}`)),
|
|
12684
|
+
isItemDragging && draggedItemRect && selectedElRef.current !== footerDragRef.current?.draggedEl && selectedElRef.current !== navDragRef.current?.draggedEl && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ItemInteractionLayer, { rect: draggedItemRect, state: "dragging" }),
|
|
12685
|
+
isItemDragging && footerDropSlots.map((slot, i) => /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11911
12686
|
"div",
|
|
11912
12687
|
{
|
|
11913
12688
|
className: "pointer-events-none fixed z-2147483646",
|
|
@@ -11917,7 +12692,7 @@ function OhhwellsBridge() {
|
|
|
11917
12692
|
width: slot.width,
|
|
11918
12693
|
height: slot.height
|
|
11919
12694
|
},
|
|
11920
|
-
children: /* @__PURE__ */ (0,
|
|
12695
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11921
12696
|
DropIndicator,
|
|
11922
12697
|
{
|
|
11923
12698
|
direction: slot.direction,
|
|
@@ -11928,7 +12703,7 @@ function OhhwellsBridge() {
|
|
|
11928
12703
|
},
|
|
11929
12704
|
`footer-drop-${slot.direction}-${slot.columnIndex}-${slot.insertIndex}-${i}`
|
|
11930
12705
|
)),
|
|
11931
|
-
isItemDragging && navDropSlots.map((slot, i) => /* @__PURE__ */ (0,
|
|
12706
|
+
isItemDragging && navDropSlots.map((slot, i) => /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11932
12707
|
"div",
|
|
11933
12708
|
{
|
|
11934
12709
|
className: "pointer-events-none fixed z-2147483646",
|
|
@@ -11938,7 +12713,7 @@ function OhhwellsBridge() {
|
|
|
11938
12713
|
width: slot.width,
|
|
11939
12714
|
height: slot.height
|
|
11940
12715
|
},
|
|
11941
|
-
children: /* @__PURE__ */ (0,
|
|
12716
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11942
12717
|
DropIndicator,
|
|
11943
12718
|
{
|
|
11944
12719
|
direction: slot.direction,
|
|
@@ -11949,10 +12724,11 @@ function OhhwellsBridge() {
|
|
|
11949
12724
|
},
|
|
11950
12725
|
`nav-drop-${slot.direction}-${slot.parentId ?? "root"}-${slot.insertIndex}-${i}`
|
|
11951
12726
|
)),
|
|
11952
|
-
hoveredNavContainerRect && toolbarVariant !== "select-frame" && !linkPopover && !isItemDragging && /* @__PURE__ */ (0,
|
|
11953
|
-
hoveredItemRect && !linkPopover && !hoveredNavContainerRect && !isItemDragging && hoveredItemElRef.current !== selectedElRef.current && /* @__PURE__ */ (0,
|
|
11954
|
-
toolbarVariant === "select-frame" && toolbarRect && !linkPopover && !isItemDragging && !isFooterFrameSelection && selectedElRef.current && isNavbarLinksContainer(selectedElRef.current) && /* @__PURE__ */ (0,
|
|
11955
|
-
toolbarRect && !linkPopover &&
|
|
12727
|
+
hoveredNavContainerRect && (toolbarVariant !== "select-frame" || isFooterFrameSelection) && !linkPopover && !isItemDragging && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ItemInteractionLayer, { rect: hoveredNavContainerRect, state: "hover" }),
|
|
12728
|
+
hoveredItemRect && !linkPopover && !hoveredNavContainerRect && !isItemDragging && hoveredItemElRef.current !== selectedElRef.current && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(ItemInteractionLayer, { rect: hoveredItemRect, state: "hover" }),
|
|
12729
|
+
toolbarVariant === "select-frame" && toolbarRect && !linkPopover && !isItemDragging && !isFooterFrameSelection && selectedElRef.current && isNavbarLinksContainer(selectedElRef.current) && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(NavbarContainerChrome, { rect: toolbarRect, onAdd: handleAddTopLevelNavItem }),
|
|
12730
|
+
toolbarVariant === "select-frame" && toolbarRect && !linkPopover && !isItemDragging && !isFooterFrameSelection && selectedElRef.current && isFooterLinksContainer(selectedElRef.current) && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(FooterContainerChrome, { rect: toolbarRect, onAdd: handleAddFooterColumn }),
|
|
12731
|
+
toolbarRect && !linkPopover && (toolbarVariant === "link-action" || toolbarVariant === "select-frame") && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11956
12732
|
ItemInteractionLayer,
|
|
11957
12733
|
{
|
|
11958
12734
|
rect: isItemDragging && draggedItemRect && (footerDragRef.current?.wasSelected || navDragRef.current?.wasSelected) ? draggedItemRect : toolbarRect,
|
|
@@ -11966,7 +12742,7 @@ function OhhwellsBridge() {
|
|
|
11966
12742
|
onItemPointerDown: handleItemChromePointerDown,
|
|
11967
12743
|
onItemClick: handleItemChromeClick,
|
|
11968
12744
|
itemDragSurface: !isFooterFrameSelection,
|
|
11969
|
-
toolbar: toolbarVariant === "link-action" && !isItemDragging ? /* @__PURE__ */ (0,
|
|
12745
|
+
toolbar: toolbarVariant === "link-action" && !isItemDragging ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11970
12746
|
ItemActionToolbar,
|
|
11971
12747
|
{
|
|
11972
12748
|
onEditLink: openLinkPopoverForSelected,
|
|
@@ -11979,8 +12755,8 @@ function OhhwellsBridge() {
|
|
|
11979
12755
|
) : void 0
|
|
11980
12756
|
}
|
|
11981
12757
|
),
|
|
11982
|
-
toolbarRect && toolbarVariant === "rich-text" && !linkPopover && /* @__PURE__ */ (0,
|
|
11983
|
-
/* @__PURE__ */ (0,
|
|
12758
|
+
toolbarRect && toolbarVariant === "rich-text" && !linkPopover && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(import_jsx_runtime26.Fragment, { children: [
|
|
12759
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11984
12760
|
EditGlowChrome,
|
|
11985
12761
|
{
|
|
11986
12762
|
rect: toolbarRect,
|
|
@@ -11990,7 +12766,7 @@ function OhhwellsBridge() {
|
|
|
11990
12766
|
hideHandle: isItemDragging
|
|
11991
12767
|
}
|
|
11992
12768
|
),
|
|
11993
|
-
/* @__PURE__ */ (0,
|
|
12769
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
11994
12770
|
FloatingToolbar,
|
|
11995
12771
|
{
|
|
11996
12772
|
rect: toolbarRect,
|
|
@@ -12003,7 +12779,7 @@ function OhhwellsBridge() {
|
|
|
12003
12779
|
}
|
|
12004
12780
|
)
|
|
12005
12781
|
] }),
|
|
12006
|
-
maxBadge && /* @__PURE__ */ (0,
|
|
12782
|
+
maxBadge && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
|
|
12007
12783
|
"div",
|
|
12008
12784
|
{
|
|
12009
12785
|
"data-ohw-max-badge": "",
|
|
@@ -12029,7 +12805,7 @@ function OhhwellsBridge() {
|
|
|
12029
12805
|
]
|
|
12030
12806
|
}
|
|
12031
12807
|
),
|
|
12032
|
-
toggleState && !linkPopover && /* @__PURE__ */ (0,
|
|
12808
|
+
toggleState && !linkPopover && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
12033
12809
|
StateToggle,
|
|
12034
12810
|
{
|
|
12035
12811
|
rect: toggleState.rect,
|
|
@@ -12038,15 +12814,15 @@ function OhhwellsBridge() {
|
|
|
12038
12814
|
onStateChange: handleStateChange
|
|
12039
12815
|
}
|
|
12040
12816
|
),
|
|
12041
|
-
sectionGap && !linkPopover && /* @__PURE__ */ (0,
|
|
12817
|
+
sectionGap && !linkPopover && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
|
|
12042
12818
|
"div",
|
|
12043
12819
|
{
|
|
12044
12820
|
"data-ohw-section-insert-line": "",
|
|
12045
12821
|
className: "fixed left-0 w-full z-2147483646 flex items-center pointer-events-none",
|
|
12046
12822
|
style: { top: sectionGap.y, transform: "translateY(-50%)" },
|
|
12047
12823
|
children: [
|
|
12048
|
-
/* @__PURE__ */ (0,
|
|
12049
|
-
/* @__PURE__ */ (0,
|
|
12824
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "flex-1 bg-primary", style: { height: 3 } }),
|
|
12825
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
12050
12826
|
Badge,
|
|
12051
12827
|
{
|
|
12052
12828
|
className: "px-8 py-1 bg-primary hover:bg-primary text-primary-foreground text-xs font-medium shrink-0 rounded-full cursor-pointer pointer-events-auto",
|
|
@@ -12063,11 +12839,11 @@ function OhhwellsBridge() {
|
|
|
12063
12839
|
children: "Add Section"
|
|
12064
12840
|
}
|
|
12065
12841
|
),
|
|
12066
|
-
/* @__PURE__ */ (0,
|
|
12842
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "flex-1 bg-primary", style: { height: 3 } })
|
|
12067
12843
|
]
|
|
12068
12844
|
}
|
|
12069
12845
|
),
|
|
12070
|
-
linkPopover && dialogPortalContainer ? /* @__PURE__ */ (0,
|
|
12846
|
+
linkPopover && dialogPortalContainer ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
12071
12847
|
LinkPopover,
|
|
12072
12848
|
{
|
|
12073
12849
|
panelRef: linkPopoverPanelRef,
|
|
@@ -12116,6 +12892,7 @@ function OhhwellsBridge() {
|
|
|
12116
12892
|
isValidUrl,
|
|
12117
12893
|
parseTarget,
|
|
12118
12894
|
toggleVariants,
|
|
12895
|
+
useOhwCarousel,
|
|
12119
12896
|
validateUrlInput
|
|
12120
12897
|
});
|
|
12121
12898
|
//# sourceMappingURL=index.cjs.map
|