@planetaexo/design-system 0.37.2 → 0.37.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +1599 -366
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +119 -20
- package/dist/index.d.ts +119 -20
- package/dist/index.js +1583 -350
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import * as
|
|
1
|
+
import * as React28 from 'react';
|
|
2
2
|
import { useState, useRef, useCallback, useEffect } from 'react';
|
|
3
3
|
import { cva } from 'class-variance-authority';
|
|
4
4
|
import { clsx } from 'clsx';
|
|
5
5
|
import { twMerge } from 'tailwind-merge';
|
|
6
6
|
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
7
|
-
import { XIcon, ChevronDownIcon, CalendarIcon, SearchIcon, ChevronRightIcon, ArrowLeftIcon, CheckCircle2Icon, MapIcon, LogOutIcon, UsersIcon, CreditCardIcon, AlertCircleIcon, MinusIcon, PlusIcon, CircleCheckIcon, ChevronLeftIcon, HomeIcon, SailboatIcon, CarIcon, WavesIcon, FootprintsIcon, InfoIcon, ClockIcon, CheckIcon, ChevronUpIcon,
|
|
7
|
+
import { XIcon, ChevronDownIcon, CalendarIcon, SearchIcon, ChevronRightIcon, ArrowLeftIcon, CheckCircle2Icon, MapIcon, LogOutIcon, UsersIcon, CreditCardIcon, AlertCircleIcon, MinusIcon, PlusIcon, CircleCheckIcon, SlidersHorizontalIcon, ChevronLeftIcon, HomeIcon, SailboatIcon, CarIcon, WavesIcon, FootprintsIcon, InfoIcon, ClockIcon, CheckIcon, ChevronUpIcon, MenuIcon, UserIcon, SunIcon, MoonIcon, MapPinIcon, PackageIcon, BedDoubleIcon, UtensilsIcon, CompassIcon, BackpackIcon, CherryIcon, ReceiptIcon, Loader2Icon, SendIcon, CheckCircleIcon, MailIcon, PhoneIcon, MessageCircleIcon, UserPlusIcon, ExternalLinkIcon, CopyIcon, PencilIcon, Trash2Icon, UserMinusIcon, AlertTriangleIcon, ZoomInIcon, StarIcon, TwitterIcon, YoutubeIcon, LinkedinIcon, InstagramIcon, FacebookIcon, ArrowRightIcon, LayoutGridIcon } from 'lucide-react';
|
|
8
8
|
import { Separator as Separator$1 } from '@base-ui/react/separator';
|
|
9
9
|
import { Dialog as Dialog$1 } from '@base-ui/react/dialog';
|
|
10
10
|
import { Button as Button$1 } from '@base-ui/react/button';
|
|
@@ -81,7 +81,7 @@ var buttonVariants = cva(
|
|
|
81
81
|
}
|
|
82
82
|
}
|
|
83
83
|
);
|
|
84
|
-
var Button =
|
|
84
|
+
var Button = React28.forwardRef(
|
|
85
85
|
(_a, ref) => {
|
|
86
86
|
var _b = _a, { className, variant, size } = _b, props = __objRest(_b, ["className", "variant", "size"]);
|
|
87
87
|
return /* @__PURE__ */ jsx(
|
|
@@ -165,6 +165,10 @@ function Dialog(_a) {
|
|
|
165
165
|
var props = __objRest(_a, []);
|
|
166
166
|
return /* @__PURE__ */ jsx(Dialog$1.Root, __spreadValues({ "data-slot": "dialog" }, props));
|
|
167
167
|
}
|
|
168
|
+
function DialogTrigger(_a) {
|
|
169
|
+
var props = __objRest(_a, []);
|
|
170
|
+
return /* @__PURE__ */ jsx(Dialog$1.Trigger, __spreadValues({ "data-slot": "dialog-trigger" }, props));
|
|
171
|
+
}
|
|
168
172
|
function DialogPortal(_a) {
|
|
169
173
|
var props = __objRest(_a, []);
|
|
170
174
|
return /* @__PURE__ */ jsx(Dialog$1.Portal, __spreadValues({ "data-slot": "dialog-portal" }, props));
|
|
@@ -302,10 +306,10 @@ function DialogDescription(_a) {
|
|
|
302
306
|
}, props)
|
|
303
307
|
);
|
|
304
308
|
}
|
|
305
|
-
var FloatingInput =
|
|
309
|
+
var FloatingInput = React28.forwardRef(
|
|
306
310
|
(_a, ref) => {
|
|
307
311
|
var _b = _a, { label, error, id, className, required } = _b, props = __objRest(_b, ["label", "error", "id", "className", "required"]);
|
|
308
|
-
const inputId = id != null ? id :
|
|
312
|
+
const inputId = id != null ? id : React28.useId();
|
|
309
313
|
return /* @__PURE__ */ jsxs("div", { className: cn("relative", className), children: [
|
|
310
314
|
/* @__PURE__ */ jsx(
|
|
311
315
|
"input",
|
|
@@ -345,10 +349,10 @@ var FloatingInput = React8.forwardRef(
|
|
|
345
349
|
}
|
|
346
350
|
);
|
|
347
351
|
FloatingInput.displayName = "FloatingInput";
|
|
348
|
-
var FloatingSelect =
|
|
352
|
+
var FloatingSelect = React28.forwardRef(
|
|
349
353
|
(_a, ref) => {
|
|
350
354
|
var _b = _a, { label, error, id, className, required, children, value } = _b, props = __objRest(_b, ["label", "error", "id", "className", "required", "children", "value"]);
|
|
351
|
-
const inputId = id != null ? id :
|
|
355
|
+
const inputId = id != null ? id : React28.useId();
|
|
352
356
|
const hasValue = typeof value === "string" ? value !== "" : value !== void 0 && value !== null;
|
|
353
357
|
return /* @__PURE__ */ jsxs("div", { className: cn("relative", className), children: [
|
|
354
358
|
/* @__PURE__ */ jsx(
|
|
@@ -612,11 +616,11 @@ function PhoneCountrySelect({
|
|
|
612
616
|
disabled
|
|
613
617
|
}) {
|
|
614
618
|
var _a;
|
|
615
|
-
const [open, setOpen] =
|
|
616
|
-
const containerRef =
|
|
617
|
-
const listRef =
|
|
619
|
+
const [open, setOpen] = React28.useState(false);
|
|
620
|
+
const containerRef = React28.useRef(null);
|
|
621
|
+
const listRef = React28.useRef(null);
|
|
618
622
|
const selected = (_a = PHONE_COUNTRIES.find((c) => c.code === value)) != null ? _a : PHONE_COUNTRIES[0];
|
|
619
|
-
|
|
623
|
+
React28.useEffect(() => {
|
|
620
624
|
if (!open) return;
|
|
621
625
|
const handler = (e) => {
|
|
622
626
|
var _a2;
|
|
@@ -627,7 +631,7 @@ function PhoneCountrySelect({
|
|
|
627
631
|
document.addEventListener("mousedown", handler);
|
|
628
632
|
return () => document.removeEventListener("mousedown", handler);
|
|
629
633
|
}, [open]);
|
|
630
|
-
|
|
634
|
+
React28.useEffect(() => {
|
|
631
635
|
if (!open || !listRef.current) return;
|
|
632
636
|
const activeEl = listRef.current.querySelector("[data-selected=true]");
|
|
633
637
|
activeEl == null ? void 0 : activeEl.scrollIntoView({ block: "nearest" });
|
|
@@ -897,8 +901,8 @@ function CalendarDayButton(_a) {
|
|
|
897
901
|
"locale"
|
|
898
902
|
]);
|
|
899
903
|
const defaultClassNames = getDefaultClassNames();
|
|
900
|
-
const ref =
|
|
901
|
-
|
|
904
|
+
const ref = React28.useRef(null);
|
|
905
|
+
React28.useEffect(() => {
|
|
902
906
|
var _a2;
|
|
903
907
|
if (modifiers.focused) (_a2 = ref.current) == null ? void 0 : _a2.focus();
|
|
904
908
|
}, [modifiers.focused]);
|
|
@@ -929,16 +933,16 @@ function BirthDateField({
|
|
|
929
933
|
className,
|
|
930
934
|
disabled
|
|
931
935
|
}) {
|
|
932
|
-
const [open, setOpen] =
|
|
933
|
-
const [text, setText] =
|
|
936
|
+
const [open, setOpen] = React28.useState(false);
|
|
937
|
+
const [text, setText] = React28.useState(
|
|
934
938
|
value ? format(value, "dd/MM/yyyy") : ""
|
|
935
939
|
);
|
|
936
|
-
const containerRef =
|
|
937
|
-
const inputId =
|
|
938
|
-
|
|
940
|
+
const containerRef = React28.useRef(null);
|
|
941
|
+
const inputId = React28.useId();
|
|
942
|
+
React28.useEffect(() => {
|
|
939
943
|
setText(value ? format(value, "dd/MM/yyyy") : "");
|
|
940
944
|
}, [value]);
|
|
941
|
-
|
|
945
|
+
React28.useEffect(() => {
|
|
942
946
|
if (!open) return;
|
|
943
947
|
const handler = (e) => {
|
|
944
948
|
var _a;
|
|
@@ -1147,14 +1151,14 @@ function CountrySearchField({
|
|
|
1147
1151
|
}) {
|
|
1148
1152
|
var _a;
|
|
1149
1153
|
const list = countries != null ? countries : COUNTRIES;
|
|
1150
|
-
const [query, setQuery] =
|
|
1151
|
-
const [open, setOpen] =
|
|
1152
|
-
const containerRef =
|
|
1153
|
-
const searchRef =
|
|
1154
|
+
const [query, setQuery] = React28.useState("");
|
|
1155
|
+
const [open, setOpen] = React28.useState(false);
|
|
1156
|
+
const containerRef = React28.useRef(null);
|
|
1157
|
+
const searchRef = React28.useRef(null);
|
|
1154
1158
|
const selected = list.find((c) => c.code === value);
|
|
1155
1159
|
const isFloated = open || !!selected;
|
|
1156
1160
|
const filtered = query.trim() ? list.filter((c) => c.name.toLowerCase().includes(query.toLowerCase())) : list;
|
|
1157
|
-
|
|
1161
|
+
React28.useEffect(() => {
|
|
1158
1162
|
if (!open) return;
|
|
1159
1163
|
const handler = (e) => {
|
|
1160
1164
|
var _a2;
|
|
@@ -1268,7 +1272,7 @@ function AdventureCard({
|
|
|
1268
1272
|
}) {
|
|
1269
1273
|
var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k;
|
|
1270
1274
|
const isControlled = (_b = (_a = adventure.optionals) == null ? void 0 : _a.some((o) => o.onCheckedChange !== void 0)) != null ? _b : false;
|
|
1271
|
-
const [checkedInternal, setCheckedInternal] =
|
|
1275
|
+
const [checkedInternal, setCheckedInternal] = React28.useState(
|
|
1272
1276
|
new Set((_d = (_c = adventure.optionals) == null ? void 0 : _c.filter((o) => o.defaultChecked).map((o) => o.id)) != null ? _d : [])
|
|
1273
1277
|
);
|
|
1274
1278
|
const isChecked = (opt) => {
|
|
@@ -1666,7 +1670,7 @@ function BookingShell({
|
|
|
1666
1670
|
return /* @__PURE__ */ jsxs("div", { className: "rounded-2xl border border-border bg-card overflow-hidden", children: [
|
|
1667
1671
|
/* @__PURE__ */ jsxs("div", { className: "border-b border-border px-5 py-4 bg-muted/20", children: [
|
|
1668
1672
|
/* @__PURE__ */ jsx("h3", { className: "text-base font-bold text-foreground font-heading mb-2", children: title }),
|
|
1669
|
-
/* @__PURE__ */ jsx("div", { className: "flex items-center gap-1.5 flex-wrap", children: steps.map((label, i) => /* @__PURE__ */ jsxs(
|
|
1673
|
+
/* @__PURE__ */ jsx("div", { className: "flex items-center gap-1.5 flex-wrap", children: steps.map((label, i) => /* @__PURE__ */ jsxs(React28.Fragment, { children: [
|
|
1670
1674
|
/* @__PURE__ */ jsx(
|
|
1671
1675
|
"span",
|
|
1672
1676
|
{
|
|
@@ -1865,7 +1869,7 @@ function TermsSection({
|
|
|
1865
1869
|
termsContent
|
|
1866
1870
|
}) {
|
|
1867
1871
|
var _a;
|
|
1868
|
-
const [modalOpen, setModalOpen] =
|
|
1872
|
+
const [modalOpen, setModalOpen] = React28.useState(false);
|
|
1869
1873
|
const i18n = (_a = TERMS_I18N[locale]) != null ? _a : TERMS_I18N.en;
|
|
1870
1874
|
return /* @__PURE__ */ jsxs("div", { className: "rounded-xl border border-border p-4 flex flex-col gap-3", children: [
|
|
1871
1875
|
/* @__PURE__ */ jsx("p", { className: "text-xs font-bold text-muted-foreground font-heading uppercase tracking-widest", children: title }),
|
|
@@ -2003,9 +2007,9 @@ function BookingWizard({
|
|
|
2003
2007
|
}) {
|
|
2004
2008
|
var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _A, _B, _C, _D, _E, _F, _G, _H, _I, _J, _K, _L, _M, _N, _O, _P, _Q, _R, _S, _T;
|
|
2005
2009
|
const wizardSteps = WIZARD_STEPS_FN(labels);
|
|
2006
|
-
const [step, setStep] =
|
|
2007
|
-
const [error, setError] =
|
|
2008
|
-
const [responsible, setResponsible] =
|
|
2010
|
+
const [step, setStep] = React28.useState("responsible");
|
|
2011
|
+
const [error, setError] = React28.useState(null);
|
|
2012
|
+
const [responsible, setResponsible] = React28.useState({
|
|
2009
2013
|
firstName: "",
|
|
2010
2014
|
lastName: "",
|
|
2011
2015
|
email: "",
|
|
@@ -2024,7 +2028,7 @@ function BookingWizard({
|
|
|
2024
2028
|
return s + ((_b2 = (_a2 = a.slots) == null ? void 0 : _a2.children) != null ? _b2 : 0);
|
|
2025
2029
|
}, 0);
|
|
2026
2030
|
const totalPax = totalAdults + totalChildren;
|
|
2027
|
-
const [travellers, setTravellers] =
|
|
2031
|
+
const [travellers, setTravellers] = React28.useState(
|
|
2028
2032
|
Array.from({ length: Math.max(totalPax, 1) }, () => ({
|
|
2029
2033
|
firstName: "",
|
|
2030
2034
|
lastName: "",
|
|
@@ -2032,9 +2036,9 @@ function BookingWizard({
|
|
|
2032
2036
|
email: ""
|
|
2033
2037
|
}))
|
|
2034
2038
|
);
|
|
2035
|
-
const [payAmount, setPayAmount] =
|
|
2036
|
-
const [payMethod, setPayMethod] =
|
|
2037
|
-
const [termsAccepted, setTermsAccepted] =
|
|
2039
|
+
const [payAmount, setPayAmount] = React28.useState("full");
|
|
2040
|
+
const [payMethod, setPayMethod] = React28.useState("stripe");
|
|
2041
|
+
const [termsAccepted, setTermsAccepted] = React28.useState(false);
|
|
2038
2042
|
const setR = (k, v) => setResponsible((p) => __spreadProps(__spreadValues({}, p), { [k]: v }));
|
|
2039
2043
|
const setT = (i, k, v) => setTravellers((prev) => prev.map((t, idx) => idx === i ? __spreadProps(__spreadValues({}, t), { [k]: v }) : t));
|
|
2040
2044
|
const setTDob = (i, v) => setTravellers((prev) => prev.map((t, idx) => idx === i ? __spreadProps(__spreadValues({}, t), { dateOfBirth: v }) : t));
|
|
@@ -2258,13 +2262,16 @@ function Offer({
|
|
|
2258
2262
|
labels,
|
|
2259
2263
|
confirmedState,
|
|
2260
2264
|
interactionsDisabled,
|
|
2265
|
+
internalDemoCheckout = false,
|
|
2261
2266
|
className
|
|
2262
2267
|
}) {
|
|
2263
2268
|
var _a, _b, _c;
|
|
2264
|
-
const [showBooking, setShowBooking] =
|
|
2265
|
-
const isShowingCheckout = !confirmedState && (!!checkoutSlot || showBooking);
|
|
2269
|
+
const [showBooking, setShowBooking] = React28.useState(false);
|
|
2270
|
+
const isShowingCheckout = !confirmedState && (!!checkoutSlot || internalDemoCheckout && showBooking);
|
|
2266
2271
|
const handleBook = () => {
|
|
2267
|
-
if (!checkoutSlot && !externalBookingFlow)
|
|
2272
|
+
if (!checkoutSlot && !externalBookingFlow && internalDemoCheckout) {
|
|
2273
|
+
setShowBooking(true);
|
|
2274
|
+
}
|
|
2268
2275
|
onContinue == null ? void 0 : onContinue();
|
|
2269
2276
|
};
|
|
2270
2277
|
return /* @__PURE__ */ jsxs("div", { className: cn("w-full max-w-5xl mx-auto px-4 sm:px-6 lg:px-8 flex flex-col gap-6 pb-20 lg:pb-12", className), children: [
|
|
@@ -2309,7 +2316,7 @@ function Offer({
|
|
|
2309
2316
|
labels
|
|
2310
2317
|
}
|
|
2311
2318
|
),
|
|
2312
|
-
isShowingCheckout && (checkoutSlot != null ? checkoutSlot : /* @__PURE__ */ jsx(
|
|
2319
|
+
isShowingCheckout && (checkoutSlot != null ? checkoutSlot : internalDemoCheckout ? /* @__PURE__ */ jsx(
|
|
2313
2320
|
BookingWizard,
|
|
2314
2321
|
{
|
|
2315
2322
|
adventures,
|
|
@@ -2318,7 +2325,7 @@ function Offer({
|
|
|
2318
2325
|
onCancel: () => setShowBooking(false),
|
|
2319
2326
|
labels
|
|
2320
2327
|
}
|
|
2321
|
-
))
|
|
2328
|
+
) : null)
|
|
2322
2329
|
] }) }),
|
|
2323
2330
|
/* @__PURE__ */ jsx("div", { className: "lg:sticky lg:top-8", children: /* @__PURE__ */ jsx(
|
|
2324
2331
|
OfferSidebar,
|
|
@@ -2626,7 +2633,7 @@ function AdventureSection({
|
|
|
2626
2633
|
labels
|
|
2627
2634
|
}) {
|
|
2628
2635
|
var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q, _r;
|
|
2629
|
-
const [detailsOpen, setDetailsOpen] =
|
|
2636
|
+
const [detailsOpen, setDetailsOpen] = React28.useState(false);
|
|
2630
2637
|
const handleCopyUrl = (url) => {
|
|
2631
2638
|
if (onCopyFormLink) {
|
|
2632
2639
|
onCopyFormLink(url);
|
|
@@ -3138,8 +3145,8 @@ function AddTravellerDialog({
|
|
|
3138
3145
|
errorMessage
|
|
3139
3146
|
}) {
|
|
3140
3147
|
var _a, _b, _c, _d, _e;
|
|
3141
|
-
const [form, setForm] =
|
|
3142
|
-
|
|
3148
|
+
const [form, setForm] = React28.useState(() => createInitialAddFormData(config));
|
|
3149
|
+
React28.useEffect(() => {
|
|
3143
3150
|
if (open) {
|
|
3144
3151
|
setForm(createInitialAddFormData(config));
|
|
3145
3152
|
}
|
|
@@ -3199,7 +3206,7 @@ function EditTravellerDialog({
|
|
|
3199
3206
|
errorMessage
|
|
3200
3207
|
}) {
|
|
3201
3208
|
var _a, _b, _c, _d, _e;
|
|
3202
|
-
const [form, setForm] =
|
|
3209
|
+
const [form, setForm] = React28.useState(() => ({
|
|
3203
3210
|
firstName: "",
|
|
3204
3211
|
lastName: "",
|
|
3205
3212
|
email: "",
|
|
@@ -3208,7 +3215,7 @@ function EditTravellerDialog({
|
|
|
3208
3215
|
birthDate: "",
|
|
3209
3216
|
personType: "ADULT"
|
|
3210
3217
|
}));
|
|
3211
|
-
|
|
3218
|
+
React28.useEffect(() => {
|
|
3212
3219
|
var _a2, _b2, _c2, _d2, _e2, _f;
|
|
3213
3220
|
if (open && traveller) {
|
|
3214
3221
|
setForm({
|
|
@@ -3543,48 +3550,48 @@ function BookingDetails({
|
|
|
3543
3550
|
const hasSubmitAddTraveller = !!onSubmitAddTraveller;
|
|
3544
3551
|
const hasSubmitEditTraveller = !!onSubmitEditTraveller;
|
|
3545
3552
|
const hasConfirmRemoveTraveller = !!onConfirmRemoveTraveller;
|
|
3546
|
-
const [addModalState, setAddModalState] =
|
|
3553
|
+
const [addModalState, setAddModalState] = React28.useState({
|
|
3547
3554
|
open: false,
|
|
3548
3555
|
adventureId: null
|
|
3549
3556
|
});
|
|
3550
|
-
const [editModalState, setEditModalState] =
|
|
3551
|
-
const [deleteModalState, setDeleteModalState] =
|
|
3552
|
-
const [resendInviteDialogState, setResendInviteDialogState] =
|
|
3553
|
-
const handleRequestOpenAddModal =
|
|
3557
|
+
const [editModalState, setEditModalState] = React28.useState({ open: false, adventureId: null, traveller: null });
|
|
3558
|
+
const [deleteModalState, setDeleteModalState] = React28.useState({ open: false, adventureId: null, traveller: null });
|
|
3559
|
+
const [resendInviteDialogState, setResendInviteDialogState] = React28.useState({ open: false, traveller: null });
|
|
3560
|
+
const handleRequestOpenAddModal = React28.useCallback((adventureId) => {
|
|
3554
3561
|
setAddModalState({ open: true, adventureId });
|
|
3555
3562
|
}, []);
|
|
3556
|
-
const handleRequestOpenEditModal =
|
|
3563
|
+
const handleRequestOpenEditModal = React28.useCallback(
|
|
3557
3564
|
(adventureId, traveller) => {
|
|
3558
3565
|
setEditModalState({ open: true, adventureId, traveller });
|
|
3559
3566
|
},
|
|
3560
3567
|
[]
|
|
3561
3568
|
);
|
|
3562
|
-
const handleRequestOpenDeleteModal =
|
|
3569
|
+
const handleRequestOpenDeleteModal = React28.useCallback(
|
|
3563
3570
|
(adventureId, traveller) => {
|
|
3564
3571
|
setDeleteModalState({ open: true, adventureId, traveller });
|
|
3565
3572
|
},
|
|
3566
3573
|
[]
|
|
3567
3574
|
);
|
|
3568
|
-
const handleRequestOpenResendInviteDialog =
|
|
3575
|
+
const handleRequestOpenResendInviteDialog = React28.useCallback(
|
|
3569
3576
|
(traveller) => {
|
|
3570
3577
|
setResendInviteDialogState({ open: true, traveller });
|
|
3571
3578
|
},
|
|
3572
3579
|
[]
|
|
3573
3580
|
);
|
|
3574
|
-
const closeAddModal =
|
|
3581
|
+
const closeAddModal = React28.useCallback(() => {
|
|
3575
3582
|
setAddModalState({ open: false, adventureId: null });
|
|
3576
3583
|
}, []);
|
|
3577
|
-
const closeEditModal =
|
|
3584
|
+
const closeEditModal = React28.useCallback(() => {
|
|
3578
3585
|
setEditModalState({ open: false, adventureId: null, traveller: null });
|
|
3579
3586
|
}, []);
|
|
3580
|
-
const closeDeleteModal =
|
|
3587
|
+
const closeDeleteModal = React28.useCallback(() => {
|
|
3581
3588
|
setDeleteModalState({ open: false, adventureId: null, traveller: null });
|
|
3582
3589
|
}, []);
|
|
3583
|
-
const closeResendInviteDialog =
|
|
3590
|
+
const closeResendInviteDialog = React28.useCallback(() => {
|
|
3584
3591
|
setResendInviteDialogState({ open: false, traveller: null });
|
|
3585
3592
|
}, []);
|
|
3586
|
-
const submitInFlightRef =
|
|
3587
|
-
const handleAddSubmit =
|
|
3593
|
+
const submitInFlightRef = React28.useRef(false);
|
|
3594
|
+
const handleAddSubmit = React28.useCallback(
|
|
3588
3595
|
async (adventureId, data) => {
|
|
3589
3596
|
if (!onSubmitAddTraveller) return;
|
|
3590
3597
|
if (submitInFlightRef.current) return;
|
|
@@ -3599,7 +3606,7 @@ function BookingDetails({
|
|
|
3599
3606
|
},
|
|
3600
3607
|
[onSubmitAddTraveller, closeAddModal]
|
|
3601
3608
|
);
|
|
3602
|
-
const handleEditSubmit =
|
|
3609
|
+
const handleEditSubmit = React28.useCallback(
|
|
3603
3610
|
async (adventureId, travellerId, data) => {
|
|
3604
3611
|
if (!onSubmitEditTraveller) return;
|
|
3605
3612
|
if (submitInFlightRef.current) return;
|
|
@@ -3614,7 +3621,7 @@ function BookingDetails({
|
|
|
3614
3621
|
},
|
|
3615
3622
|
[onSubmitEditTraveller, closeEditModal]
|
|
3616
3623
|
);
|
|
3617
|
-
const handleDeleteConfirm =
|
|
3624
|
+
const handleDeleteConfirm = React28.useCallback(
|
|
3618
3625
|
async (adventureId, travellerId) => {
|
|
3619
3626
|
if (!onConfirmRemoveTraveller) return;
|
|
3620
3627
|
if (submitInFlightRef.current) return;
|
|
@@ -5088,7 +5095,7 @@ function BookingCreatedEmail({
|
|
|
5088
5095
|
}, children: i + 1 }) }),
|
|
5089
5096
|
/* @__PURE__ */ jsx("td", { style: { verticalAlign: "top" }, children: /* @__PURE__ */ jsx("p", { style: { fontSize: "14px", color: emailTokens.bodyText, lineHeight: "1.6", margin: 0 }, children: step }) })
|
|
5090
5097
|
] }) }) }, i)) }),
|
|
5091
|
-
nextStepsImportant && nextStepsImportant.trim().length > 0 && /* @__PURE__ */ jsx("p", { style: { marginBottom: "32px", fontSize: "14px", color: emailTokens.foreground, lineHeight: "1.6" }, children: nextStepsImportant.split("\n").map((line, idx, arr) => /* @__PURE__ */ jsxs(
|
|
5098
|
+
nextStepsImportant && nextStepsImportant.trim().length > 0 && /* @__PURE__ */ jsx("p", { style: { marginBottom: "32px", fontSize: "14px", color: emailTokens.foreground, lineHeight: "1.6" }, children: nextStepsImportant.split("\n").map((line, idx, arr) => /* @__PURE__ */ jsxs(React28.Fragment, { children: [
|
|
5092
5099
|
idx === 0 ? /* @__PURE__ */ jsx("strong", { children: line }) : line,
|
|
5093
5100
|
idx < arr.length - 1 ? /* @__PURE__ */ jsx("br", {}) : null
|
|
5094
5101
|
] }, idx)) })
|
|
@@ -6457,11 +6464,11 @@ function DatePickerField({
|
|
|
6457
6464
|
fromDate,
|
|
6458
6465
|
className
|
|
6459
6466
|
}) {
|
|
6460
|
-
const [open, setOpen] =
|
|
6461
|
-
const containerRef =
|
|
6462
|
-
const [calendarWidth, setCalendarWidth] =
|
|
6467
|
+
const [open, setOpen] = React28.useState(false);
|
|
6468
|
+
const containerRef = React28.useRef(null);
|
|
6469
|
+
const [calendarWidth, setCalendarWidth] = React28.useState();
|
|
6463
6470
|
const hasValue = !!value;
|
|
6464
|
-
|
|
6471
|
+
React28.useEffect(() => {
|
|
6465
6472
|
if (!containerRef.current) return;
|
|
6466
6473
|
const observer = new ResizeObserver(([entry]) => {
|
|
6467
6474
|
setCalendarWidth(entry.contentRect.width);
|
|
@@ -6570,7 +6577,7 @@ function BookingForm({
|
|
|
6570
6577
|
subtitle = "Free enquiry \u2013 no commitment",
|
|
6571
6578
|
className
|
|
6572
6579
|
}) {
|
|
6573
|
-
const [values, setValues] =
|
|
6580
|
+
const [values, setValues] = React28.useState(__spreadValues(__spreadValues({}, defaultInitial), defaultValues));
|
|
6574
6581
|
const set = (key, value) => setValues((prev) => __spreadProps(__spreadValues({}, prev), { [key]: value }));
|
|
6575
6582
|
const handleSubmit = (e) => {
|
|
6576
6583
|
e.preventDefault();
|
|
@@ -7107,11 +7114,11 @@ function FloatingTextarea({
|
|
|
7107
7114
|
}
|
|
7108
7115
|
function SelectField({ field, value, onChange, error, disabled }) {
|
|
7109
7116
|
var _a, _b, _c;
|
|
7110
|
-
const [open, setOpen] =
|
|
7111
|
-
const containerRef =
|
|
7117
|
+
const [open, setOpen] = React28.useState(false);
|
|
7118
|
+
const containerRef = React28.useRef(null);
|
|
7112
7119
|
const options = (_a = field.options) != null ? _a : [];
|
|
7113
7120
|
const selectedOpt = (_b = options.find((o) => o.value === value)) != null ? _b : null;
|
|
7114
|
-
|
|
7121
|
+
React28.useEffect(() => {
|
|
7115
7122
|
if (!open) return;
|
|
7116
7123
|
const handleOutside = (e) => {
|
|
7117
7124
|
if (containerRef.current && !containerRef.current.contains(e.target)) {
|
|
@@ -7500,11 +7507,11 @@ function RegistrationForm({
|
|
|
7500
7507
|
readOnly = false
|
|
7501
7508
|
}) {
|
|
7502
7509
|
var _a;
|
|
7503
|
-
const L =
|
|
7510
|
+
const L = React28.useMemo(
|
|
7504
7511
|
() => __spreadValues(__spreadValues({}, DEFAULT_LABELS9), labels != null ? labels : {}),
|
|
7505
7512
|
[labels]
|
|
7506
7513
|
);
|
|
7507
|
-
const sortedFields =
|
|
7514
|
+
const sortedFields = React28.useMemo(
|
|
7508
7515
|
() => [...fields].sort((a, b) => {
|
|
7509
7516
|
var _a2, _b;
|
|
7510
7517
|
return ((_a2 = a.order) != null ? _a2 : 0) - ((_b = b.order) != null ? _b : 0);
|
|
@@ -7512,7 +7519,7 @@ function RegistrationForm({
|
|
|
7512
7519
|
[fields]
|
|
7513
7520
|
);
|
|
7514
7521
|
const isControlled = values !== void 0;
|
|
7515
|
-
const [internal, setInternal] =
|
|
7522
|
+
const [internal, setInternal] = React28.useState(
|
|
7516
7523
|
() => initializeValues(
|
|
7517
7524
|
sortedFields,
|
|
7518
7525
|
defaultValues != null ? defaultValues : {},
|
|
@@ -7520,9 +7527,9 @@ function RegistrationForm({
|
|
|
7520
7527
|
includeTerms
|
|
7521
7528
|
)
|
|
7522
7529
|
);
|
|
7523
|
-
const [submitAttempted, setSubmitAttempted] =
|
|
7524
|
-
const [validationErrors, setValidationErrors] =
|
|
7525
|
-
|
|
7530
|
+
const [submitAttempted, setSubmitAttempted] = React28.useState(false);
|
|
7531
|
+
const [validationErrors, setValidationErrors] = React28.useState({});
|
|
7532
|
+
React28.useEffect(() => {
|
|
7526
7533
|
if (isControlled) return;
|
|
7527
7534
|
setInternal((prev) => {
|
|
7528
7535
|
const next = initializeValues(
|
|
@@ -7579,7 +7586,7 @@ function RegistrationForm({
|
|
|
7579
7586
|
const termsError = submitAttempted && termsEnabled && !termsAccepted;
|
|
7580
7587
|
const firstErrorFieldId = Object.keys(fieldErrors)[0];
|
|
7581
7588
|
const scrollTargetId = firstErrorFieldId ? `rf-${firstErrorFieldId}` : termsError ? "rf-terms" : null;
|
|
7582
|
-
|
|
7589
|
+
React28.useEffect(() => {
|
|
7583
7590
|
if (!submitAttempted || !scrollTargetId) return;
|
|
7584
7591
|
const timer = setTimeout(() => {
|
|
7585
7592
|
const elem = document.getElementById(scrollTargetId);
|
|
@@ -8041,10 +8048,10 @@ var OTPCodeInput = ({
|
|
|
8041
8048
|
id,
|
|
8042
8049
|
required
|
|
8043
8050
|
}) => {
|
|
8044
|
-
const baseId = id != null ? id :
|
|
8045
|
-
const inputRef =
|
|
8046
|
-
const [focused, setFocused] =
|
|
8047
|
-
const digits =
|
|
8051
|
+
const baseId = id != null ? id : React28.useId();
|
|
8052
|
+
const inputRef = React28.useRef(null);
|
|
8053
|
+
const [focused, setFocused] = React28.useState(false);
|
|
8054
|
+
const digits = React28.useMemo(() => {
|
|
8048
8055
|
const arr = value.split("").slice(0, length);
|
|
8049
8056
|
while (arr.length < length) arr.push("");
|
|
8050
8057
|
return arr;
|
|
@@ -8142,7 +8149,7 @@ function Checkbox(_a) {
|
|
|
8142
8149
|
__spreadProps(__spreadValues({
|
|
8143
8150
|
"data-slot": "checkbox",
|
|
8144
8151
|
className: cn(
|
|
8145
|
-
"peer relative flex size-4 shrink-0 items-center justify-center rounded-[4px] border border-input transition-colors outline-none group-has-disabled/field:opacity-50 after:absolute after:-inset-x-3 after:-inset-y-2 focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/50 disabled:cursor-not-allowed disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-3 aria-invalid:ring-destructive/20 aria-invalid:aria-checked:border-primary dark:bg-input/30 dark:aria-invalid:border-destructive/50 dark:aria-invalid:ring-destructive/40 data-checked:border-primary data-checked:bg-primary data-checked:text-primary-foreground dark:data-checked:bg-primary",
|
|
8152
|
+
"peer relative flex size-4 shrink-0 items-center justify-center rounded-[4px] border border-input transition-colors outline-none group-has-disabled/field:opacity-50 after:absolute after:-inset-x-3 after:-inset-y-2 focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/50 disabled:cursor-not-allowed disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-3 aria-invalid:ring-destructive/20 aria-invalid:aria-checked:border-primary dark:bg-input/30 dark:aria-invalid:border-destructive/50 dark:aria-invalid:ring-destructive/40 data-checked:border-primary data-checked:bg-primary data-checked:text-primary-foreground data-indeterminate:border-primary data-indeterminate:bg-primary data-indeterminate:text-primary-foreground dark:data-checked:bg-primary",
|
|
8146
8153
|
className
|
|
8147
8154
|
)
|
|
8148
8155
|
}, props), {
|
|
@@ -8151,16 +8158,13 @@ function Checkbox(_a) {
|
|
|
8151
8158
|
{
|
|
8152
8159
|
"data-slot": "checkbox-indicator",
|
|
8153
8160
|
className: "grid place-content-center text-current transition-none [&>svg]:size-3.5",
|
|
8154
|
-
children: /* @__PURE__ */ jsx(
|
|
8155
|
-
CheckIcon,
|
|
8156
|
-
{}
|
|
8157
|
-
)
|
|
8161
|
+
children: props.indeterminate ? /* @__PURE__ */ jsx(MinusIcon, {}) : /* @__PURE__ */ jsx(CheckIcon, {})
|
|
8158
8162
|
}
|
|
8159
8163
|
)
|
|
8160
8164
|
})
|
|
8161
8165
|
);
|
|
8162
8166
|
}
|
|
8163
|
-
var AccordionVariantContext =
|
|
8167
|
+
var AccordionVariantContext = React28.createContext("default");
|
|
8164
8168
|
function Accordion(_a) {
|
|
8165
8169
|
var _b = _a, { className, variant = "default" } = _b, props = __objRest(_b, ["className", "variant"]);
|
|
8166
8170
|
return /* @__PURE__ */ jsx(AccordionVariantContext.Provider, { value: variant, children: /* @__PURE__ */ jsx(
|
|
@@ -8178,7 +8182,7 @@ function Accordion(_a) {
|
|
|
8178
8182
|
}
|
|
8179
8183
|
function AccordionItem(_a) {
|
|
8180
8184
|
var _b = _a, { className } = _b, props = __objRest(_b, ["className"]);
|
|
8181
|
-
const variant =
|
|
8185
|
+
const variant = React28.useContext(AccordionVariantContext);
|
|
8182
8186
|
return /* @__PURE__ */ jsx(
|
|
8183
8187
|
Accordion$1.Item,
|
|
8184
8188
|
__spreadValues({
|
|
@@ -8199,7 +8203,7 @@ function AccordionTrigger(_a) {
|
|
|
8199
8203
|
"className",
|
|
8200
8204
|
"children"
|
|
8201
8205
|
]);
|
|
8202
|
-
const variant =
|
|
8206
|
+
const variant = React28.useContext(AccordionVariantContext);
|
|
8203
8207
|
return /* @__PURE__ */ jsx(Accordion$1.Header, { className: "flex", children: /* @__PURE__ */ jsxs(
|
|
8204
8208
|
Accordion$1.Trigger,
|
|
8205
8209
|
__spreadProps(__spreadValues({
|
|
@@ -8253,7 +8257,7 @@ function AccordionContent(_a) {
|
|
|
8253
8257
|
"className",
|
|
8254
8258
|
"children"
|
|
8255
8259
|
]);
|
|
8256
|
-
const variant =
|
|
8260
|
+
const variant = React28.useContext(AccordionVariantContext);
|
|
8257
8261
|
return /* @__PURE__ */ jsx(
|
|
8258
8262
|
Accordion$1.Panel,
|
|
8259
8263
|
__spreadProps(__spreadValues({
|
|
@@ -8276,6 +8280,187 @@ function AccordionContent(_a) {
|
|
|
8276
8280
|
})
|
|
8277
8281
|
);
|
|
8278
8282
|
}
|
|
8283
|
+
function getLeafIds(item) {
|
|
8284
|
+
var _a;
|
|
8285
|
+
if (!((_a = item.children) == null ? void 0 : _a.length)) return [item.id];
|
|
8286
|
+
return item.children.flatMap(getLeafIds);
|
|
8287
|
+
}
|
|
8288
|
+
function getDefaultExpandedIds(items) {
|
|
8289
|
+
const out = [];
|
|
8290
|
+
const walk = (list) => {
|
|
8291
|
+
var _a;
|
|
8292
|
+
for (const i of list) {
|
|
8293
|
+
if ((_a = i.children) == null ? void 0 : _a.length) {
|
|
8294
|
+
if (i.defaultExpanded) out.push(i.id);
|
|
8295
|
+
walk(i.children);
|
|
8296
|
+
}
|
|
8297
|
+
}
|
|
8298
|
+
};
|
|
8299
|
+
walk(items);
|
|
8300
|
+
return out;
|
|
8301
|
+
}
|
|
8302
|
+
function getAllItemIds(items) {
|
|
8303
|
+
return items.flatMap(
|
|
8304
|
+
(i) => {
|
|
8305
|
+
var _a;
|
|
8306
|
+
return ((_a = i.children) == null ? void 0 : _a.length) ? [i.id, ...getAllItemIds(i.children)] : [i.id];
|
|
8307
|
+
}
|
|
8308
|
+
);
|
|
8309
|
+
}
|
|
8310
|
+
function findItemById(items, id) {
|
|
8311
|
+
var _a;
|
|
8312
|
+
for (const item of items) {
|
|
8313
|
+
if (item.id === id) return item;
|
|
8314
|
+
if ((_a = item.children) == null ? void 0 : _a.length) {
|
|
8315
|
+
const found = findItemById(item.children, id);
|
|
8316
|
+
if (found) return found;
|
|
8317
|
+
}
|
|
8318
|
+
}
|
|
8319
|
+
return void 0;
|
|
8320
|
+
}
|
|
8321
|
+
function resolveGroups(groups) {
|
|
8322
|
+
return groups.map((g) => {
|
|
8323
|
+
var _a;
|
|
8324
|
+
if (!g.scopeItemId) return g;
|
|
8325
|
+
const node = findItemById(g.items, g.scopeItemId);
|
|
8326
|
+
return __spreadProps(__spreadValues({}, g), { items: (_a = node == null ? void 0 : node.children) != null ? _a : [] });
|
|
8327
|
+
}).filter((g) => g.items.length > 0);
|
|
8328
|
+
}
|
|
8329
|
+
function FilterItemsList({
|
|
8330
|
+
items,
|
|
8331
|
+
groupId,
|
|
8332
|
+
groupSelected,
|
|
8333
|
+
onToggle,
|
|
8334
|
+
onBulkToggle,
|
|
8335
|
+
idPrefix,
|
|
8336
|
+
depth = 0,
|
|
8337
|
+
parentAsHeader = false,
|
|
8338
|
+
expandedItems,
|
|
8339
|
+
onToggleExpanded
|
|
8340
|
+
}) {
|
|
8341
|
+
return /* @__PURE__ */ jsx(
|
|
8342
|
+
"ul",
|
|
8343
|
+
{
|
|
8344
|
+
className: cn(
|
|
8345
|
+
"flex flex-col gap-0.5",
|
|
8346
|
+
!parentAsHeader && depth > 0 && "mt-0.5 ml-6 border-l border-border pl-3"
|
|
8347
|
+
),
|
|
8348
|
+
children: items.map((item) => {
|
|
8349
|
+
var _a, _b;
|
|
8350
|
+
const isParent = !!((_a = item.children) == null ? void 0 : _a.length);
|
|
8351
|
+
const checkboxId = `${idPrefix}-${groupId}-${item.id}`;
|
|
8352
|
+
if (!isParent) {
|
|
8353
|
+
const checked = groupSelected.includes(item.id);
|
|
8354
|
+
return /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsxs(
|
|
8355
|
+
"label",
|
|
8356
|
+
{
|
|
8357
|
+
htmlFor: checkboxId,
|
|
8358
|
+
className: "flex cursor-pointer items-center gap-3 rounded-md px-1 py-2 transition-colors hover:bg-muted/50",
|
|
8359
|
+
children: [
|
|
8360
|
+
/* @__PURE__ */ jsx(
|
|
8361
|
+
Checkbox,
|
|
8362
|
+
{
|
|
8363
|
+
id: checkboxId,
|
|
8364
|
+
checked,
|
|
8365
|
+
onCheckedChange: () => onToggle(item.id),
|
|
8366
|
+
className: "shrink-0"
|
|
8367
|
+
}
|
|
8368
|
+
),
|
|
8369
|
+
/* @__PURE__ */ jsx("span", { className: "flex-1 text-sm text-foreground font-ui", children: item.label }),
|
|
8370
|
+
item.count !== void 0 && /* @__PURE__ */ jsxs("span", { className: "text-xs font-medium text-primary font-ui", children: [
|
|
8371
|
+
"(",
|
|
8372
|
+
item.count,
|
|
8373
|
+
")"
|
|
8374
|
+
] })
|
|
8375
|
+
]
|
|
8376
|
+
}
|
|
8377
|
+
) }, item.id);
|
|
8378
|
+
}
|
|
8379
|
+
if (parentAsHeader) {
|
|
8380
|
+
return /* @__PURE__ */ jsxs("li", { className: cn(depth > 0 && "mt-1"), children: [
|
|
8381
|
+
/* @__PURE__ */ jsx("p", { className: "px-1 pt-2 pb-1 text-[11px] font-semibold uppercase tracking-wider text-muted-foreground", children: item.label }),
|
|
8382
|
+
/* @__PURE__ */ jsx(
|
|
8383
|
+
FilterItemsList,
|
|
8384
|
+
{
|
|
8385
|
+
items: item.children,
|
|
8386
|
+
groupId,
|
|
8387
|
+
groupSelected,
|
|
8388
|
+
onToggle,
|
|
8389
|
+
onBulkToggle,
|
|
8390
|
+
idPrefix,
|
|
8391
|
+
depth: depth + 1,
|
|
8392
|
+
parentAsHeader: true,
|
|
8393
|
+
expandedItems,
|
|
8394
|
+
onToggleExpanded
|
|
8395
|
+
}
|
|
8396
|
+
)
|
|
8397
|
+
] }, item.id);
|
|
8398
|
+
}
|
|
8399
|
+
const leafIds = item.children.flatMap(getLeafIds);
|
|
8400
|
+
const selectedLeaves = leafIds.filter((id) => groupSelected.includes(id));
|
|
8401
|
+
const allSelected = leafIds.length > 0 && selectedLeaves.length === leafIds.length;
|
|
8402
|
+
const someSelected = selectedLeaves.length > 0 && !allSelected;
|
|
8403
|
+
const isExpanded = (_b = expandedItems == null ? void 0 : expandedItems.has(item.id)) != null ? _b : false;
|
|
8404
|
+
const panelId = `${checkboxId}-children`;
|
|
8405
|
+
return /* @__PURE__ */ jsxs("li", { children: [
|
|
8406
|
+
/* @__PURE__ */ jsxs("div", { className: "group/parent flex items-center gap-3 rounded-md px-1 py-2 transition-colors hover:bg-muted/50", children: [
|
|
8407
|
+
/* @__PURE__ */ jsx(
|
|
8408
|
+
Checkbox,
|
|
8409
|
+
{
|
|
8410
|
+
id: checkboxId,
|
|
8411
|
+
checked: allSelected,
|
|
8412
|
+
indeterminate: someSelected,
|
|
8413
|
+
onCheckedChange: () => onBulkToggle(leafIds, !allSelected),
|
|
8414
|
+
className: "shrink-0"
|
|
8415
|
+
}
|
|
8416
|
+
),
|
|
8417
|
+
/* @__PURE__ */ jsxs(
|
|
8418
|
+
"button",
|
|
8419
|
+
{
|
|
8420
|
+
type: "button",
|
|
8421
|
+
onClick: () => onToggleExpanded == null ? void 0 : onToggleExpanded(item.id),
|
|
8422
|
+
"aria-expanded": isExpanded,
|
|
8423
|
+
"aria-controls": panelId,
|
|
8424
|
+
className: "flex flex-1 items-center gap-2 text-left focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring rounded-sm cursor-pointer",
|
|
8425
|
+
children: [
|
|
8426
|
+
/* @__PURE__ */ jsx("span", { className: "flex-1 text-sm font-bold text-foreground font-ui", children: item.label }),
|
|
8427
|
+
item.count !== void 0 && /* @__PURE__ */ jsxs("span", { className: "text-xs font-medium text-primary font-ui", children: [
|
|
8428
|
+
"(",
|
|
8429
|
+
item.count,
|
|
8430
|
+
")"
|
|
8431
|
+
] }),
|
|
8432
|
+
/* @__PURE__ */ jsx(
|
|
8433
|
+
ChevronDownIcon,
|
|
8434
|
+
{
|
|
8435
|
+
className: cn(
|
|
8436
|
+
"h-4 w-4 text-muted-foreground transition-transform",
|
|
8437
|
+
isExpanded && "rotate-180"
|
|
8438
|
+
)
|
|
8439
|
+
}
|
|
8440
|
+
)
|
|
8441
|
+
]
|
|
8442
|
+
}
|
|
8443
|
+
)
|
|
8444
|
+
] }),
|
|
8445
|
+
isExpanded && /* @__PURE__ */ jsx("div", { id: panelId, children: /* @__PURE__ */ jsx(
|
|
8446
|
+
FilterItemsList,
|
|
8447
|
+
{
|
|
8448
|
+
items: item.children,
|
|
8449
|
+
groupId,
|
|
8450
|
+
groupSelected,
|
|
8451
|
+
onToggle,
|
|
8452
|
+
onBulkToggle,
|
|
8453
|
+
idPrefix,
|
|
8454
|
+
depth: depth + 1,
|
|
8455
|
+
expandedItems,
|
|
8456
|
+
onToggleExpanded
|
|
8457
|
+
}
|
|
8458
|
+
) })
|
|
8459
|
+
] }, item.id);
|
|
8460
|
+
})
|
|
8461
|
+
}
|
|
8462
|
+
);
|
|
8463
|
+
}
|
|
8279
8464
|
function FilterPanel({
|
|
8280
8465
|
groups,
|
|
8281
8466
|
value,
|
|
@@ -8283,15 +8468,32 @@ function FilterPanel({
|
|
|
8283
8468
|
onClearAll,
|
|
8284
8469
|
alwaysShowClear = false,
|
|
8285
8470
|
title = "Filters",
|
|
8286
|
-
className
|
|
8471
|
+
className,
|
|
8472
|
+
variant = "sidebar",
|
|
8473
|
+
sortOptions,
|
|
8474
|
+
sort,
|
|
8475
|
+
onSortChange
|
|
8287
8476
|
}) {
|
|
8288
|
-
|
|
8477
|
+
var _a, _b;
|
|
8478
|
+
const resolvedGroups = React28.useMemo(() => resolveGroups(groups), [groups]);
|
|
8479
|
+
const [internalValue, setInternalValue] = React28.useState(
|
|
8289
8480
|
() => Object.fromEntries(groups.map((g) => [g.id, []]))
|
|
8290
8481
|
);
|
|
8291
8482
|
const selected = value != null ? value : internalValue;
|
|
8483
|
+
const [expandedItems, setExpandedItems] = React28.useState(
|
|
8484
|
+
() => new Set(groups.flatMap((g) => getDefaultExpandedIds(g.items)))
|
|
8485
|
+
);
|
|
8486
|
+
const toggleExpanded = React28.useCallback((id) => {
|
|
8487
|
+
setExpandedItems((prev) => {
|
|
8488
|
+
const next = new Set(prev);
|
|
8489
|
+
if (next.has(id)) next.delete(id);
|
|
8490
|
+
else next.add(id);
|
|
8491
|
+
return next;
|
|
8492
|
+
});
|
|
8493
|
+
}, []);
|
|
8292
8494
|
const handleToggle = (groupId, itemId) => {
|
|
8293
|
-
var
|
|
8294
|
-
const current = (
|
|
8495
|
+
var _a2;
|
|
8496
|
+
const current = (_a2 = selected[groupId]) != null ? _a2 : [];
|
|
8295
8497
|
const next = current.includes(itemId) ? current.filter((id) => id !== itemId) : [...current, itemId];
|
|
8296
8498
|
const nextValue = __spreadProps(__spreadValues({}, selected), { [groupId]: next });
|
|
8297
8499
|
if (onChange) {
|
|
@@ -8300,8 +8502,24 @@ function FilterPanel({
|
|
|
8300
8502
|
setInternalValue(nextValue);
|
|
8301
8503
|
}
|
|
8302
8504
|
};
|
|
8505
|
+
const handleBulkToggle = (groupId, itemIds, select) => {
|
|
8506
|
+
var _a2;
|
|
8507
|
+
const current = (_a2 = selected[groupId]) != null ? _a2 : [];
|
|
8508
|
+
const next = select ? Array.from(/* @__PURE__ */ new Set([...current, ...itemIds])) : current.filter((id) => !itemIds.includes(id));
|
|
8509
|
+
const nextValue = __spreadProps(__spreadValues({}, selected), { [groupId]: next });
|
|
8510
|
+
if (onChange) {
|
|
8511
|
+
onChange(nextValue);
|
|
8512
|
+
} else {
|
|
8513
|
+
setInternalValue(nextValue);
|
|
8514
|
+
}
|
|
8515
|
+
};
|
|
8303
8516
|
const handleClearAll = () => {
|
|
8304
|
-
|
|
8517
|
+
var _a2;
|
|
8518
|
+
const cleared = __spreadValues({}, selected);
|
|
8519
|
+
for (const g of resolvedGroups) {
|
|
8520
|
+
const visible = new Set(getAllItemIds(g.items));
|
|
8521
|
+
cleared[g.id] = ((_a2 = selected[g.id]) != null ? _a2 : []).filter((id) => !visible.has(id));
|
|
8522
|
+
}
|
|
8305
8523
|
if (onChange) {
|
|
8306
8524
|
onChange(cleared);
|
|
8307
8525
|
} else {
|
|
@@ -8309,9 +8527,289 @@ function FilterPanel({
|
|
|
8309
8527
|
}
|
|
8310
8528
|
onClearAll == null ? void 0 : onClearAll();
|
|
8311
8529
|
};
|
|
8312
|
-
const totalSelected =
|
|
8530
|
+
const totalSelected = resolvedGroups.reduce((sum, g) => {
|
|
8531
|
+
var _a2;
|
|
8532
|
+
const visible = new Set(getAllItemIds(g.items));
|
|
8533
|
+
return sum + ((_a2 = selected[g.id]) != null ? _a2 : []).filter((id) => visible.has(id)).length;
|
|
8534
|
+
}, 0);
|
|
8313
8535
|
const showClear = alwaysShowClear || totalSelected > 0;
|
|
8314
|
-
const defaultOpenValues =
|
|
8536
|
+
const defaultOpenValues = resolvedGroups.filter((g) => g.defaultOpen).map((g) => g.id);
|
|
8537
|
+
if (resolvedGroups.length === 0) return null;
|
|
8538
|
+
if (variant === "horizontal") {
|
|
8539
|
+
const activeSort = (_a = sortOptions == null ? void 0 : sortOptions.find((o) => o.id === sort)) != null ? _a : sortOptions == null ? void 0 : sortOptions[0];
|
|
8540
|
+
const drawerGroups = /* @__PURE__ */ jsx(Accordion, { defaultValue: defaultOpenValues, className: "flex flex-col gap-2", children: resolvedGroups.map((group) => {
|
|
8541
|
+
var _a2;
|
|
8542
|
+
const groupSelected = (_a2 = selected[group.id]) != null ? _a2 : [];
|
|
8543
|
+
return /* @__PURE__ */ jsxs(
|
|
8544
|
+
AccordionItem,
|
|
8545
|
+
{
|
|
8546
|
+
value: group.id,
|
|
8547
|
+
className: "border-0 border-b border-border last:border-b-0",
|
|
8548
|
+
children: [
|
|
8549
|
+
/* @__PURE__ */ jsx(AccordionTrigger, { className: "px-0 py-3.5 hover:no-underline transition-colors", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2.5", children: [
|
|
8550
|
+
group.icon && /* @__PURE__ */ jsx("span", { className: "text-primary shrink-0", children: group.icon }),
|
|
8551
|
+
/* @__PURE__ */ jsx("span", { className: "text-sm font-bold text-foreground font-ui", children: group.label }),
|
|
8552
|
+
groupSelected.length > 0 && /* @__PURE__ */ jsx("span", { className: "ml-1 inline-flex h-4 w-4 items-center justify-center rounded-full bg-primary text-[9px] font-bold text-primary-foreground", children: groupSelected.length })
|
|
8553
|
+
] }) }),
|
|
8554
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "px-4 pb-3 pt-1", children: /* @__PURE__ */ jsx(
|
|
8555
|
+
FilterItemsList,
|
|
8556
|
+
{
|
|
8557
|
+
items: group.items,
|
|
8558
|
+
groupId: group.id,
|
|
8559
|
+
groupSelected,
|
|
8560
|
+
onToggle: (id) => handleToggle(group.id, id),
|
|
8561
|
+
onBulkToggle: (ids, select) => handleBulkToggle(group.id, ids, select),
|
|
8562
|
+
idPrefix: "mobile-filter",
|
|
8563
|
+
expandedItems,
|
|
8564
|
+
onToggleExpanded: toggleExpanded
|
|
8565
|
+
}
|
|
8566
|
+
) })
|
|
8567
|
+
]
|
|
8568
|
+
},
|
|
8569
|
+
group.id
|
|
8570
|
+
);
|
|
8571
|
+
}) });
|
|
8572
|
+
return /* @__PURE__ */ jsxs("div", { className: cn("contents", className), children: [
|
|
8573
|
+
/* @__PURE__ */ jsxs("div", { className: "flex sm:hidden items-center gap-2", children: [
|
|
8574
|
+
/* @__PURE__ */ jsxs(Dialog, { children: [
|
|
8575
|
+
/* @__PURE__ */ jsxs(
|
|
8576
|
+
DialogTrigger,
|
|
8577
|
+
{
|
|
8578
|
+
render: /* @__PURE__ */ jsx(
|
|
8579
|
+
"button",
|
|
8580
|
+
{
|
|
8581
|
+
type: "button",
|
|
8582
|
+
className: cn(
|
|
8583
|
+
"flex-1 inline-flex items-center justify-between gap-2 rounded-xl border-2 border-foreground bg-background px-4 py-3",
|
|
8584
|
+
"text-sm font-ui font-bold text-foreground transition-colors hover:bg-muted",
|
|
8585
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring"
|
|
8586
|
+
)
|
|
8587
|
+
}
|
|
8588
|
+
),
|
|
8589
|
+
children: [
|
|
8590
|
+
/* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
8591
|
+
title,
|
|
8592
|
+
totalSelected > 0 && /* @__PURE__ */ jsx("span", { className: "inline-flex h-5 min-w-[20px] items-center justify-center rounded-full bg-primary px-1.5 text-[10px] font-bold text-primary-foreground", children: totalSelected })
|
|
8593
|
+
] }),
|
|
8594
|
+
/* @__PURE__ */ jsx(SlidersHorizontalIcon, { className: "h-4 w-4 text-foreground" })
|
|
8595
|
+
]
|
|
8596
|
+
}
|
|
8597
|
+
),
|
|
8598
|
+
/* @__PURE__ */ jsx(
|
|
8599
|
+
DialogContent,
|
|
8600
|
+
{
|
|
8601
|
+
className: cn(
|
|
8602
|
+
"p-0 sm:max-w-md",
|
|
8603
|
+
"max-w-none w-screen h-screen sm:h-auto sm:max-h-[90vh] rounded-none sm:rounded-2xl"
|
|
8604
|
+
),
|
|
8605
|
+
children: /* @__PURE__ */ jsxs("div", { className: "flex flex-col h-full max-h-[90vh]", children: [
|
|
8606
|
+
/* @__PURE__ */ jsx(DialogTitle, { className: "px-5 py-4 text-lg font-bold font-heading border-b border-border", children: title }),
|
|
8607
|
+
/* @__PURE__ */ jsx("div", { className: "flex-1 overflow-y-auto px-5 py-3", children: drawerGroups }),
|
|
8608
|
+
/* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between gap-3 px-5 py-4 border-t border-border", children: [
|
|
8609
|
+
/* @__PURE__ */ jsx(
|
|
8610
|
+
"button",
|
|
8611
|
+
{
|
|
8612
|
+
type: "button",
|
|
8613
|
+
onClick: handleClearAll,
|
|
8614
|
+
className: "text-sm font-ui font-semibold text-muted-foreground underline underline-offset-2 hover:text-foreground",
|
|
8615
|
+
children: "Clear all"
|
|
8616
|
+
}
|
|
8617
|
+
),
|
|
8618
|
+
/* @__PURE__ */ jsxs(
|
|
8619
|
+
DialogClose,
|
|
8620
|
+
{
|
|
8621
|
+
render: /* @__PURE__ */ jsx(
|
|
8622
|
+
"button",
|
|
8623
|
+
{
|
|
8624
|
+
type: "button",
|
|
8625
|
+
className: "inline-flex items-center justify-center rounded-full bg-foreground text-background px-6 py-2.5 text-sm font-ui font-bold hover:bg-foreground/90 transition-colors"
|
|
8626
|
+
}
|
|
8627
|
+
),
|
|
8628
|
+
children: [
|
|
8629
|
+
"Show ",
|
|
8630
|
+
totalSelected > 0 ? `(${totalSelected})` : "",
|
|
8631
|
+
" results"
|
|
8632
|
+
]
|
|
8633
|
+
}
|
|
8634
|
+
)
|
|
8635
|
+
] })
|
|
8636
|
+
] })
|
|
8637
|
+
}
|
|
8638
|
+
)
|
|
8639
|
+
] }),
|
|
8640
|
+
sortOptions && sortOptions.length > 0 && /* @__PURE__ */ jsxs(Popover, { children: [
|
|
8641
|
+
/* @__PURE__ */ jsxs(
|
|
8642
|
+
PopoverTrigger,
|
|
8643
|
+
{
|
|
8644
|
+
render: /* @__PURE__ */ jsx(
|
|
8645
|
+
"button",
|
|
8646
|
+
{
|
|
8647
|
+
type: "button",
|
|
8648
|
+
className: cn(
|
|
8649
|
+
"inline-flex items-center gap-1.5 rounded-xl border border-border bg-background px-4 py-3",
|
|
8650
|
+
"text-sm font-ui font-bold text-foreground transition-colors hover:bg-muted",
|
|
8651
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring"
|
|
8652
|
+
)
|
|
8653
|
+
}
|
|
8654
|
+
),
|
|
8655
|
+
children: [
|
|
8656
|
+
"Sort",
|
|
8657
|
+
/* @__PURE__ */ jsx(ChevronDownIcon, { className: "h-4 w-4 text-muted-foreground" })
|
|
8658
|
+
]
|
|
8659
|
+
}
|
|
8660
|
+
),
|
|
8661
|
+
/* @__PURE__ */ jsx(PopoverContent, { align: "end", sideOffset: 6, className: "w-52", children: /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-0.5 p-0.5", children: sortOptions.map((opt) => /* @__PURE__ */ jsx(
|
|
8662
|
+
"button",
|
|
8663
|
+
{
|
|
8664
|
+
type: "button",
|
|
8665
|
+
onClick: () => onSortChange == null ? void 0 : onSortChange(opt.id),
|
|
8666
|
+
className: cn(
|
|
8667
|
+
"flex items-center px-2 py-1.5 rounded-md text-sm text-left",
|
|
8668
|
+
opt.id === (activeSort == null ? void 0 : activeSort.id) ? "bg-muted text-foreground font-semibold" : "text-foreground/80 hover:bg-muted"
|
|
8669
|
+
),
|
|
8670
|
+
children: opt.label
|
|
8671
|
+
},
|
|
8672
|
+
opt.id
|
|
8673
|
+
)) }) })
|
|
8674
|
+
] })
|
|
8675
|
+
] }),
|
|
8676
|
+
/* @__PURE__ */ jsxs("div", { className: "hidden sm:flex items-center gap-2 flex-wrap", children: [
|
|
8677
|
+
resolvedGroups.map((group) => {
|
|
8678
|
+
var _a2, _b2;
|
|
8679
|
+
const selectedCount = ((_a2 = selected[group.id]) != null ? _a2 : []).length;
|
|
8680
|
+
const isActive = selectedCount > 0;
|
|
8681
|
+
return /* @__PURE__ */ jsxs(Popover, { children: [
|
|
8682
|
+
/* @__PURE__ */ jsxs(
|
|
8683
|
+
PopoverTrigger,
|
|
8684
|
+
{
|
|
8685
|
+
render: /* @__PURE__ */ jsx(
|
|
8686
|
+
"button",
|
|
8687
|
+
{
|
|
8688
|
+
type: "button",
|
|
8689
|
+
className: cn(
|
|
8690
|
+
"inline-flex items-center gap-1.5 rounded-full border px-3.5 py-1.5",
|
|
8691
|
+
"text-sm font-ui font-semibold transition-colors",
|
|
8692
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
|
|
8693
|
+
isActive ? "border-foreground bg-foreground text-background" : "border-border bg-background text-foreground hover:bg-muted"
|
|
8694
|
+
)
|
|
8695
|
+
}
|
|
8696
|
+
),
|
|
8697
|
+
children: [
|
|
8698
|
+
group.icon && /* @__PURE__ */ jsx(
|
|
8699
|
+
"span",
|
|
8700
|
+
{
|
|
8701
|
+
className: cn(
|
|
8702
|
+
"[&>svg]:h-3.5 [&>svg]:w-3.5",
|
|
8703
|
+
isActive ? "" : "text-muted-foreground"
|
|
8704
|
+
),
|
|
8705
|
+
children: group.icon
|
|
8706
|
+
}
|
|
8707
|
+
),
|
|
8708
|
+
group.label,
|
|
8709
|
+
selectedCount > 0 && /* @__PURE__ */ jsx(
|
|
8710
|
+
"span",
|
|
8711
|
+
{
|
|
8712
|
+
className: cn(
|
|
8713
|
+
"inline-flex items-center justify-center rounded-full text-[10px] font-bold px-1.5 min-w-[18px] h-[18px]",
|
|
8714
|
+
isActive ? "bg-background text-foreground" : "bg-foreground text-background"
|
|
8715
|
+
),
|
|
8716
|
+
children: selectedCount
|
|
8717
|
+
}
|
|
8718
|
+
),
|
|
8719
|
+
/* @__PURE__ */ jsx(
|
|
8720
|
+
ChevronDownIcon,
|
|
8721
|
+
{
|
|
8722
|
+
className: cn(
|
|
8723
|
+
"h-3.5 w-3.5",
|
|
8724
|
+
isActive ? "text-background/70" : "text-muted-foreground"
|
|
8725
|
+
)
|
|
8726
|
+
}
|
|
8727
|
+
)
|
|
8728
|
+
]
|
|
8729
|
+
}
|
|
8730
|
+
),
|
|
8731
|
+
/* @__PURE__ */ jsx(
|
|
8732
|
+
PopoverContent,
|
|
8733
|
+
{
|
|
8734
|
+
align: "start",
|
|
8735
|
+
sideOffset: 6,
|
|
8736
|
+
className: "w-72 max-h-[60vh] overflow-y-auto",
|
|
8737
|
+
children: /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-0.5 p-2", children: [
|
|
8738
|
+
/* @__PURE__ */ jsx("p", { className: "px-1 py-1 text-[11px] font-semibold uppercase tracking-wider text-muted-foreground", children: group.label }),
|
|
8739
|
+
/* @__PURE__ */ jsx(
|
|
8740
|
+
FilterItemsList,
|
|
8741
|
+
{
|
|
8742
|
+
items: group.items,
|
|
8743
|
+
groupId: group.id,
|
|
8744
|
+
groupSelected: (_b2 = selected[group.id]) != null ? _b2 : [],
|
|
8745
|
+
onToggle: (id) => handleToggle(group.id, id),
|
|
8746
|
+
onBulkToggle: (ids, select) => handleBulkToggle(group.id, ids, select),
|
|
8747
|
+
idPrefix: "popover-filter",
|
|
8748
|
+
parentAsHeader: true,
|
|
8749
|
+
expandedItems,
|
|
8750
|
+
onToggleExpanded: toggleExpanded
|
|
8751
|
+
}
|
|
8752
|
+
)
|
|
8753
|
+
] })
|
|
8754
|
+
}
|
|
8755
|
+
)
|
|
8756
|
+
] }, group.id);
|
|
8757
|
+
}),
|
|
8758
|
+
totalSelected > 0 && /* @__PURE__ */ jsxs(
|
|
8759
|
+
"button",
|
|
8760
|
+
{
|
|
8761
|
+
type: "button",
|
|
8762
|
+
onClick: handleClearAll,
|
|
8763
|
+
className: "inline-flex items-center gap-1 rounded-full px-3 py-1.5 text-xs font-ui font-semibold text-muted-foreground hover:text-foreground transition-colors",
|
|
8764
|
+
children: [
|
|
8765
|
+
/* @__PURE__ */ jsx(XIcon, { className: "h-3 w-3" }),
|
|
8766
|
+
"Clear all (",
|
|
8767
|
+
totalSelected,
|
|
8768
|
+
")"
|
|
8769
|
+
]
|
|
8770
|
+
}
|
|
8771
|
+
),
|
|
8772
|
+
sortOptions && sortOptions.length > 0 && /* @__PURE__ */ jsxs("div", { className: "ml-auto flex items-center gap-2", children: [
|
|
8773
|
+
/* @__PURE__ */ jsx("span", { className: "text-xs text-muted-foreground font-ui hidden sm:inline", children: "Sort by" }),
|
|
8774
|
+
/* @__PURE__ */ jsxs(Popover, { children: [
|
|
8775
|
+
/* @__PURE__ */ jsxs(
|
|
8776
|
+
PopoverTrigger,
|
|
8777
|
+
{
|
|
8778
|
+
render: /* @__PURE__ */ jsx(
|
|
8779
|
+
"button",
|
|
8780
|
+
{
|
|
8781
|
+
type: "button",
|
|
8782
|
+
className: cn(
|
|
8783
|
+
"inline-flex items-center gap-1.5 rounded-full border border-border bg-background px-3.5 py-1.5",
|
|
8784
|
+
"text-sm font-ui font-semibold text-foreground hover:bg-muted transition-colors",
|
|
8785
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring"
|
|
8786
|
+
)
|
|
8787
|
+
}
|
|
8788
|
+
),
|
|
8789
|
+
children: [
|
|
8790
|
+
(_b = activeSort == null ? void 0 : activeSort.label) != null ? _b : "Default",
|
|
8791
|
+
/* @__PURE__ */ jsx(ChevronDownIcon, { className: "h-3.5 w-3.5 text-muted-foreground" })
|
|
8792
|
+
]
|
|
8793
|
+
}
|
|
8794
|
+
),
|
|
8795
|
+
/* @__PURE__ */ jsx(PopoverContent, { align: "end", sideOffset: 6, className: "w-52", children: /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-0.5 p-0.5", children: sortOptions.map((opt) => /* @__PURE__ */ jsx(
|
|
8796
|
+
"button",
|
|
8797
|
+
{
|
|
8798
|
+
type: "button",
|
|
8799
|
+
onClick: () => onSortChange == null ? void 0 : onSortChange(opt.id),
|
|
8800
|
+
className: cn(
|
|
8801
|
+
"flex items-center px-2 py-1.5 rounded-md text-sm text-left",
|
|
8802
|
+
opt.id === (activeSort == null ? void 0 : activeSort.id) ? "bg-muted text-foreground font-semibold" : "text-foreground/80 hover:bg-muted"
|
|
8803
|
+
),
|
|
8804
|
+
children: opt.label
|
|
8805
|
+
},
|
|
8806
|
+
opt.id
|
|
8807
|
+
)) }) })
|
|
8808
|
+
] })
|
|
8809
|
+
] })
|
|
8810
|
+
] })
|
|
8811
|
+
] });
|
|
8812
|
+
}
|
|
8315
8813
|
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col gap-4", className), children: [
|
|
8316
8814
|
/* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between", children: [
|
|
8317
8815
|
/* @__PURE__ */ jsx("h3", { className: "text-base font-bold text-foreground font-ui", children: title }),
|
|
@@ -8322,9 +8820,9 @@ function FilterPanel({
|
|
|
8322
8820
|
{
|
|
8323
8821
|
defaultValue: defaultOpenValues,
|
|
8324
8822
|
className: "flex flex-col gap-2",
|
|
8325
|
-
children:
|
|
8326
|
-
var
|
|
8327
|
-
const groupSelected = (
|
|
8823
|
+
children: resolvedGroups.map((group) => {
|
|
8824
|
+
var _a2;
|
|
8825
|
+
const groupSelected = (_a2 = selected[group.id]) != null ? _a2 : [];
|
|
8328
8826
|
return /* @__PURE__ */ jsxs(
|
|
8329
8827
|
AccordionItem,
|
|
8330
8828
|
{
|
|
@@ -8336,34 +8834,19 @@ function FilterPanel({
|
|
|
8336
8834
|
/* @__PURE__ */ jsx("span", { className: "text-sm font-bold text-foreground font-ui", children: group.label }),
|
|
8337
8835
|
groupSelected.length > 0 && /* @__PURE__ */ jsx("span", { className: "ml-1 inline-flex h-4 w-4 items-center justify-center rounded-full bg-primary text-[9px] font-bold text-primary-foreground", children: groupSelected.length })
|
|
8338
8836
|
] }) }),
|
|
8339
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "px-4 pb-3 pt-1", children: /* @__PURE__ */ jsx(
|
|
8340
|
-
|
|
8341
|
-
|
|
8342
|
-
|
|
8343
|
-
|
|
8344
|
-
|
|
8345
|
-
|
|
8346
|
-
|
|
8347
|
-
|
|
8348
|
-
|
|
8349
|
-
|
|
8350
|
-
|
|
8351
|
-
|
|
8352
|
-
checked,
|
|
8353
|
-
onCheckedChange: () => handleToggle(group.id, item.id),
|
|
8354
|
-
className: "shrink-0"
|
|
8355
|
-
}
|
|
8356
|
-
),
|
|
8357
|
-
/* @__PURE__ */ jsx("span", { className: "flex-1 text-sm text-foreground font-ui", children: item.label }),
|
|
8358
|
-
item.count !== void 0 && /* @__PURE__ */ jsxs("span", { className: "text-xs font-medium text-primary font-ui", children: [
|
|
8359
|
-
"(",
|
|
8360
|
-
item.count,
|
|
8361
|
-
")"
|
|
8362
|
-
] })
|
|
8363
|
-
]
|
|
8364
|
-
}
|
|
8365
|
-
) }, item.id);
|
|
8366
|
-
}) }) })
|
|
8837
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "px-4 pb-3 pt-1", children: /* @__PURE__ */ jsx(
|
|
8838
|
+
FilterItemsList,
|
|
8839
|
+
{
|
|
8840
|
+
items: group.items,
|
|
8841
|
+
groupId: group.id,
|
|
8842
|
+
groupSelected,
|
|
8843
|
+
onToggle: (id) => handleToggle(group.id, id),
|
|
8844
|
+
onBulkToggle: (ids, select) => handleBulkToggle(group.id, ids, select),
|
|
8845
|
+
idPrefix: "filter",
|
|
8846
|
+
expandedItems,
|
|
8847
|
+
onToggleExpanded: toggleExpanded
|
|
8848
|
+
}
|
|
8849
|
+
) })
|
|
8367
8850
|
]
|
|
8368
8851
|
},
|
|
8369
8852
|
group.id
|
|
@@ -8384,70 +8867,182 @@ function FilterPanel({
|
|
|
8384
8867
|
var TRUSTPILOT_SCRIPT_SRC = "https://widget.trustpilot.com/bootstrap/v5/tp.widget.bootstrap.min.js";
|
|
8385
8868
|
function TrustpilotEmbed({ config }) {
|
|
8386
8869
|
var _a, _b, _c, _d, _e, _f;
|
|
8387
|
-
const ref =
|
|
8388
|
-
|
|
8870
|
+
const ref = React28.useRef(null);
|
|
8871
|
+
const [widgetReady, setWidgetReady] = React28.useState(false);
|
|
8872
|
+
const [delayPassed, setDelayPassed] = React28.useState(false);
|
|
8873
|
+
const showFallback = delayPassed && !widgetReady;
|
|
8874
|
+
React28.useEffect(() => {
|
|
8875
|
+
var _a2;
|
|
8389
8876
|
if (typeof document === "undefined" || !ref.current) return;
|
|
8877
|
+
const node = ref.current;
|
|
8390
8878
|
let cancelled = false;
|
|
8879
|
+
const checkRendered = () => {
|
|
8880
|
+
if (!node) return false;
|
|
8881
|
+
if (node.querySelector("iframe")) return true;
|
|
8882
|
+
if (node.innerHTML.length > 200) return true;
|
|
8883
|
+
return false;
|
|
8884
|
+
};
|
|
8885
|
+
const observer = new MutationObserver(() => {
|
|
8886
|
+
if (cancelled) return;
|
|
8887
|
+
if (checkRendered()) setWidgetReady(true);
|
|
8888
|
+
});
|
|
8889
|
+
observer.observe(node, { childList: true, subtree: true });
|
|
8890
|
+
if (checkRendered()) setWidgetReady(true);
|
|
8391
8891
|
const initWidget = () => {
|
|
8392
|
-
if (cancelled || !
|
|
8892
|
+
if (cancelled || !node) return;
|
|
8393
8893
|
const tp = window.Trustpilot;
|
|
8394
8894
|
if (tp == null ? void 0 : tp.loadFromElement) {
|
|
8395
|
-
tp.loadFromElement(
|
|
8895
|
+
tp.loadFromElement(node, true);
|
|
8396
8896
|
}
|
|
8397
8897
|
};
|
|
8398
8898
|
const existing = document.querySelector(
|
|
8399
8899
|
`script[src="${TRUSTPILOT_SCRIPT_SRC}"]`
|
|
8400
8900
|
);
|
|
8901
|
+
let cleanupScriptListener;
|
|
8401
8902
|
if (existing) {
|
|
8402
8903
|
const tp = window.Trustpilot;
|
|
8403
8904
|
if (tp == null ? void 0 : tp.loadFromElement) {
|
|
8404
8905
|
initWidget();
|
|
8405
8906
|
} else {
|
|
8406
8907
|
existing.addEventListener("load", initWidget, { once: true });
|
|
8908
|
+
cleanupScriptListener = () => existing.removeEventListener("load", initWidget);
|
|
8407
8909
|
}
|
|
8408
|
-
|
|
8409
|
-
|
|
8410
|
-
|
|
8411
|
-
|
|
8910
|
+
} else {
|
|
8911
|
+
const s = document.createElement("script");
|
|
8912
|
+
s.src = TRUSTPILOT_SCRIPT_SRC;
|
|
8913
|
+
s.async = true;
|
|
8914
|
+
s.addEventListener("load", initWidget, { once: true });
|
|
8915
|
+
document.body.appendChild(s);
|
|
8916
|
+
cleanupScriptListener = () => s.removeEventListener("load", initWidget);
|
|
8412
8917
|
}
|
|
8413
|
-
const
|
|
8414
|
-
|
|
8415
|
-
|
|
8416
|
-
|
|
8417
|
-
document.body.appendChild(s);
|
|
8918
|
+
const delay = (_a2 = config.fallbackDelayMs) != null ? _a2 : 3e3;
|
|
8919
|
+
const timeout = setTimeout(() => {
|
|
8920
|
+
if (!cancelled) setDelayPassed(true);
|
|
8921
|
+
}, delay);
|
|
8418
8922
|
return () => {
|
|
8419
8923
|
cancelled = true;
|
|
8420
|
-
|
|
8924
|
+
clearTimeout(timeout);
|
|
8925
|
+
observer.disconnect();
|
|
8926
|
+
cleanupScriptListener == null ? void 0 : cleanupScriptListener();
|
|
8421
8927
|
};
|
|
8422
8928
|
}, [config]);
|
|
8423
8929
|
const sku = Array.isArray(config.sku) ? config.sku.join(",") : config.sku;
|
|
8930
|
+
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
8931
|
+
/* @__PURE__ */ jsx(
|
|
8932
|
+
"div",
|
|
8933
|
+
{
|
|
8934
|
+
ref,
|
|
8935
|
+
className: "trustpilot-widget",
|
|
8936
|
+
"data-locale": (_a = config.locale) != null ? _a : "en-US",
|
|
8937
|
+
"data-template-id": (_b = config.templateId) != null ? _b : "5763bccae0a06d08e809ecbb",
|
|
8938
|
+
"data-businessunit-id": config.businessUnitId,
|
|
8939
|
+
"data-style-height": (_c = config.styleHeight) != null ? _c : "700px",
|
|
8940
|
+
"data-style-width": (_d = config.styleWidth) != null ? _d : "100%",
|
|
8941
|
+
"data-sku": sku,
|
|
8942
|
+
"data-no-reviews": (_e = config.noReviews) != null ? _e : "hide",
|
|
8943
|
+
"data-fullwidth": "true",
|
|
8944
|
+
"data-theme": config.theme,
|
|
8945
|
+
"data-token": config.token,
|
|
8946
|
+
"data-scroll-to-list": config.scrollToList ? "true" : void 0,
|
|
8947
|
+
"data-style-alignment": config.styleAlignment,
|
|
8948
|
+
"data-star-color": config.starColor,
|
|
8949
|
+
children: /* @__PURE__ */ jsx(
|
|
8950
|
+
"a",
|
|
8951
|
+
{
|
|
8952
|
+
href: (_f = config.fallbackHref) != null ? _f : "https://www.trustpilot.com/",
|
|
8953
|
+
target: "_blank",
|
|
8954
|
+
rel: "noopener noreferrer",
|
|
8955
|
+
children: "Trustpilot"
|
|
8956
|
+
}
|
|
8957
|
+
)
|
|
8958
|
+
}
|
|
8959
|
+
),
|
|
8960
|
+
showFallback && /* @__PURE__ */ jsx(TrustpilotFallback, { config })
|
|
8961
|
+
] });
|
|
8962
|
+
}
|
|
8963
|
+
function FallbackStar({ filled, className }) {
|
|
8424
8964
|
return /* @__PURE__ */ jsx(
|
|
8425
|
-
"
|
|
8965
|
+
"span",
|
|
8426
8966
|
{
|
|
8427
|
-
|
|
8428
|
-
className:
|
|
8429
|
-
|
|
8430
|
-
|
|
8431
|
-
|
|
8432
|
-
|
|
8433
|
-
"
|
|
8434
|
-
|
|
8435
|
-
|
|
8436
|
-
|
|
8437
|
-
|
|
8438
|
-
|
|
8439
|
-
|
|
8440
|
-
|
|
8441
|
-
|
|
8442
|
-
|
|
8443
|
-
|
|
8444
|
-
|
|
8445
|
-
|
|
8446
|
-
|
|
8447
|
-
|
|
8448
|
-
|
|
8449
|
-
|
|
8450
|
-
|
|
8967
|
+
"aria-hidden": true,
|
|
8968
|
+
className: cn(
|
|
8969
|
+
"inline-flex items-center justify-center",
|
|
8970
|
+
filled ? "bg-[#00b67a] text-white" : "bg-muted text-muted-foreground",
|
|
8971
|
+
className
|
|
8972
|
+
),
|
|
8973
|
+
children: /* @__PURE__ */ jsx("svg", { viewBox: "0 0 24 24", className: "h-[60%] w-[60%]", fill: "currentColor", children: /* @__PURE__ */ jsx("path", { d: "M12 2l3.09 6.26L22 9.27l-5 4.87 1.18 6.88L12 17.77l-6.18 3.25L7 14.14 2 9.27l6.91-1.01L12 2z" }) })
|
|
8974
|
+
}
|
|
8975
|
+
);
|
|
8976
|
+
}
|
|
8977
|
+
function TrustpilotFallback({ config }) {
|
|
8978
|
+
var _a, _b, _c, _d, _e, _f;
|
|
8979
|
+
const score = (_a = config.fallbackScore) != null ? _a : 4.8;
|
|
8980
|
+
const count = (_b = config.fallbackCount) != null ? _b : 0;
|
|
8981
|
+
const label = (_c = config.fallbackLabel) != null ? _c : "Excellent";
|
|
8982
|
+
const href = (_d = config.fallbackHref) != null ? _d : "https://www.trustpilot.com/";
|
|
8983
|
+
const isDark = config.theme === "dark";
|
|
8984
|
+
const styleHeightPx = parseInt((_e = config.styleHeight) != null ? _e : "", 10);
|
|
8985
|
+
const autoVariant = Number.isFinite(styleHeightPx) && styleHeightPx > 0 && styleHeightPx < 120 ? "mini" : "card";
|
|
8986
|
+
const variant = (_f = config.fallbackVariant) != null ? _f : autoVariant;
|
|
8987
|
+
const filledStars = Math.round(score);
|
|
8988
|
+
if (variant === "mini") {
|
|
8989
|
+
return /* @__PURE__ */ jsxs(
|
|
8990
|
+
"a",
|
|
8991
|
+
{
|
|
8992
|
+
href,
|
|
8993
|
+
target: "_blank",
|
|
8994
|
+
rel: "noopener noreferrer",
|
|
8995
|
+
className: cn(
|
|
8996
|
+
"inline-flex items-center gap-2 text-sm font-ui no-underline hover:opacity-80 transition-opacity",
|
|
8997
|
+
isDark ? "text-white" : "text-foreground"
|
|
8998
|
+
),
|
|
8999
|
+
children: [
|
|
9000
|
+
/* @__PURE__ */ jsx("div", { className: "flex items-center gap-0.5", children: Array.from({ length: 5 }).map((_, i) => /* @__PURE__ */ jsx(FallbackStar, { filled: i < filledStars, className: "h-4 w-4 rounded-[2px]" }, i)) }),
|
|
9001
|
+
/* @__PURE__ */ jsx("span", { className: "font-bold", children: score.toFixed(1) }),
|
|
9002
|
+
count > 0 && /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
9003
|
+
/* @__PURE__ */ jsx("span", { className: cn(isDark ? "text-white/60" : "text-muted-foreground"), children: "\xB7" }),
|
|
9004
|
+
/* @__PURE__ */ jsxs("span", { className: cn("text-xs", isDark ? "text-white/80" : "text-muted-foreground"), children: [
|
|
9005
|
+
count.toLocaleString(),
|
|
9006
|
+
" reviews"
|
|
9007
|
+
] })
|
|
9008
|
+
] }),
|
|
9009
|
+
/* @__PURE__ */ jsx("span", { className: cn("text-xs", isDark ? "text-white/60" : "text-muted-foreground"), children: "on Trustpilot" })
|
|
9010
|
+
]
|
|
9011
|
+
}
|
|
9012
|
+
);
|
|
9013
|
+
}
|
|
9014
|
+
return /* @__PURE__ */ jsxs(
|
|
9015
|
+
"a",
|
|
9016
|
+
{
|
|
9017
|
+
href,
|
|
9018
|
+
target: "_blank",
|
|
9019
|
+
rel: "noopener noreferrer",
|
|
9020
|
+
className: "block max-w-md mx-auto rounded-2xl border border-border bg-card p-8 text-center no-underline shadow-sm hover:shadow-md transition-shadow",
|
|
9021
|
+
children: [
|
|
9022
|
+
/* @__PURE__ */ jsx("div", { className: "flex justify-center items-center gap-1 mb-3", children: Array.from({ length: 5 }).map((_, i) => /* @__PURE__ */ jsx(FallbackStar, { filled: i < filledStars, className: "h-7 w-7 rounded-[3px]" }, i)) }),
|
|
9023
|
+
/* @__PURE__ */ jsxs("p", { className: "text-2xl font-bold text-foreground font-heading", children: [
|
|
9024
|
+
label,
|
|
9025
|
+
" ",
|
|
9026
|
+
/* @__PURE__ */ jsxs("span", { className: "text-muted-foreground font-normal", children: [
|
|
9027
|
+
"\xB7 ",
|
|
9028
|
+
score.toFixed(1),
|
|
9029
|
+
" / 5"
|
|
9030
|
+
] })
|
|
9031
|
+
] }),
|
|
9032
|
+
count > 0 && /* @__PURE__ */ jsxs("p", { className: "text-sm text-muted-foreground mt-2", children: [
|
|
9033
|
+
"Based on ",
|
|
9034
|
+
/* @__PURE__ */ jsx("span", { className: "font-semibold text-foreground", children: count.toLocaleString() }),
|
|
9035
|
+
" reviews"
|
|
9036
|
+
] }),
|
|
9037
|
+
/* @__PURE__ */ jsx("p", { className: "text-xs text-muted-foreground mt-4", children: "Reviews powered by Trustpilot" }),
|
|
9038
|
+
/* @__PURE__ */ jsxs("span", { className: "mt-5 inline-flex items-center gap-1.5 text-sm font-semibold text-primary border-b border-primary/40 pb-0.5", children: [
|
|
9039
|
+
"Read all reviews on Trustpilot",
|
|
9040
|
+
/* @__PURE__ */ jsxs("svg", { className: "h-3.5 w-3.5", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2.2", strokeLinecap: "round", strokeLinejoin: "round", children: [
|
|
9041
|
+
/* @__PURE__ */ jsx("line", { x1: "5", y1: "12", x2: "19", y2: "12" }),
|
|
9042
|
+
/* @__PURE__ */ jsx("polyline", { points: "12 5 19 12 12 19" })
|
|
9043
|
+
] })
|
|
9044
|
+
] })
|
|
9045
|
+
]
|
|
8451
9046
|
}
|
|
8452
9047
|
);
|
|
8453
9048
|
}
|
|
@@ -8517,11 +9112,11 @@ function ItineraryModal({
|
|
|
8517
9112
|
onNext
|
|
8518
9113
|
}) {
|
|
8519
9114
|
var _a, _b, _c;
|
|
8520
|
-
const [imgIndex, setImgIndex] =
|
|
9115
|
+
const [imgIndex, setImgIndex] = React28.useState(0);
|
|
8521
9116
|
const images = stop ? [stop.coverImage, ...(_a = stop.images) != null ? _a : []] : [];
|
|
8522
9117
|
const isFirst = (stop == null ? void 0 : stop.dayNumber) === ((_b = allStops[0]) == null ? void 0 : _b.dayNumber);
|
|
8523
9118
|
const isLast = (stop == null ? void 0 : stop.dayNumber) === ((_c = allStops[allStops.length - 1]) == null ? void 0 : _c.dayNumber);
|
|
8524
|
-
|
|
9119
|
+
React28.useEffect(() => {
|
|
8525
9120
|
setImgIndex(0);
|
|
8526
9121
|
}, [stop == null ? void 0 : stop.dayNumber]);
|
|
8527
9122
|
if (!stop) return null;
|
|
@@ -8648,8 +9243,8 @@ function ItineraryModal({
|
|
|
8648
9243
|
) });
|
|
8649
9244
|
}
|
|
8650
9245
|
function Itinerary({ title, subtitle, stops, className }) {
|
|
8651
|
-
const [activeIndex, setActiveIndex] =
|
|
8652
|
-
const scrollRef =
|
|
9246
|
+
const [activeIndex, setActiveIndex] = React28.useState(null);
|
|
9247
|
+
const scrollRef = React28.useRef(null);
|
|
8653
9248
|
const activeStop = activeIndex !== null ? stops[activeIndex] : null;
|
|
8654
9249
|
const scrollBy = (dir) => {
|
|
8655
9250
|
if (!scrollRef.current) return;
|
|
@@ -8741,18 +9336,18 @@ function Lightbox({
|
|
|
8741
9336
|
onClose
|
|
8742
9337
|
}) {
|
|
8743
9338
|
var _a;
|
|
8744
|
-
const [index, setIndex] =
|
|
9339
|
+
const [index, setIndex] = React28.useState(initialIndex);
|
|
8745
9340
|
const total = photos.length;
|
|
8746
9341
|
const photo = photos[index];
|
|
8747
|
-
const prev =
|
|
9342
|
+
const prev = React28.useCallback(
|
|
8748
9343
|
() => setIndex((i) => (i - 1 + total) % total),
|
|
8749
9344
|
[total]
|
|
8750
9345
|
);
|
|
8751
|
-
const next =
|
|
9346
|
+
const next = React28.useCallback(
|
|
8752
9347
|
() => setIndex((i) => (i + 1) % total),
|
|
8753
9348
|
[total]
|
|
8754
9349
|
);
|
|
8755
|
-
|
|
9350
|
+
React28.useEffect(() => {
|
|
8756
9351
|
const onKey = (e) => {
|
|
8757
9352
|
if (e.key === "Escape") onClose();
|
|
8758
9353
|
if (e.key === "ArrowLeft") prev();
|
|
@@ -8918,7 +9513,7 @@ function GridGallery({
|
|
|
8918
9513
|
initialVisible,
|
|
8919
9514
|
onOpen
|
|
8920
9515
|
}) {
|
|
8921
|
-
const [expanded, setExpanded] =
|
|
9516
|
+
const [expanded, setExpanded] = React28.useState(false);
|
|
8922
9517
|
const cols = gridCols(photos.length);
|
|
8923
9518
|
const hasMore = photos.length > initialVisible;
|
|
8924
9519
|
const visible = expanded || !hasMore ? photos : photos.slice(0, initialVisible);
|
|
@@ -8943,12 +9538,41 @@ function GridGallery({
|
|
|
8943
9538
|
)
|
|
8944
9539
|
] });
|
|
8945
9540
|
}
|
|
9541
|
+
function CompactGridGallery({
|
|
9542
|
+
photos,
|
|
9543
|
+
initialVisible,
|
|
9544
|
+
onOpen
|
|
9545
|
+
}) {
|
|
9546
|
+
const [expanded, setExpanded] = React28.useState(false);
|
|
9547
|
+
const hasMore = photos.length > initialVisible;
|
|
9548
|
+
const visible = expanded || !hasMore ? photos : photos.slice(0, initialVisible);
|
|
9549
|
+
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
9550
|
+
/* @__PURE__ */ jsx("div", { className: "grid grid-cols-2 lg:grid-cols-4", children: visible.map((p, i) => /* @__PURE__ */ jsx(
|
|
9551
|
+
PhotoTile,
|
|
9552
|
+
{
|
|
9553
|
+
photo: p,
|
|
9554
|
+
index: i,
|
|
9555
|
+
className: "aspect-[4/3]",
|
|
9556
|
+
onClick: () => onOpen(i)
|
|
9557
|
+
},
|
|
9558
|
+
i
|
|
9559
|
+
)) }),
|
|
9560
|
+
hasMore && /* @__PURE__ */ jsx(
|
|
9561
|
+
ShowMoreButton,
|
|
9562
|
+
{
|
|
9563
|
+
count: photos.length - initialVisible,
|
|
9564
|
+
expanded,
|
|
9565
|
+
onClick: () => setExpanded((v) => !v)
|
|
9566
|
+
}
|
|
9567
|
+
)
|
|
9568
|
+
] });
|
|
9569
|
+
}
|
|
8946
9570
|
function MasonryGallery({
|
|
8947
9571
|
photos,
|
|
8948
9572
|
initialVisible,
|
|
8949
9573
|
onOpen
|
|
8950
9574
|
}) {
|
|
8951
|
-
const [expanded, setExpanded] =
|
|
9575
|
+
const [expanded, setExpanded] = React28.useState(false);
|
|
8952
9576
|
const hasMore = photos.length > initialVisible;
|
|
8953
9577
|
const visible = expanded || !hasMore ? photos : photos.slice(0, initialVisible);
|
|
8954
9578
|
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
@@ -9021,7 +9645,7 @@ function FeaturedGallery({
|
|
|
9021
9645
|
photos,
|
|
9022
9646
|
onOpen
|
|
9023
9647
|
}) {
|
|
9024
|
-
const [expanded, setExpanded] =
|
|
9648
|
+
const [expanded, setExpanded] = React28.useState(false);
|
|
9025
9649
|
const featured = photos.slice(0, 3);
|
|
9026
9650
|
const extra = photos.slice(3);
|
|
9027
9651
|
return /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
@@ -9188,9 +9812,9 @@ function PhotoGallery({
|
|
|
9188
9812
|
onPhotoClick,
|
|
9189
9813
|
className
|
|
9190
9814
|
}) {
|
|
9191
|
-
const [lightboxIndex, setLightboxIndex] =
|
|
9192
|
-
const [carouselIndex, setCarouselIndex] =
|
|
9193
|
-
const normalised =
|
|
9815
|
+
const [lightboxIndex, setLightboxIndex] = React28.useState(null);
|
|
9816
|
+
const [carouselIndex, setCarouselIndex] = React28.useState(0);
|
|
9817
|
+
const normalised = React28.useMemo(() => photos.map(normalise), [photos]);
|
|
9194
9818
|
const handleOpen = (index) => {
|
|
9195
9819
|
setLightboxIndex(index);
|
|
9196
9820
|
onPhotoClick == null ? void 0 : onPhotoClick(normalised[index].src, index);
|
|
@@ -9232,6 +9856,14 @@ function PhotoGallery({
|
|
|
9232
9856
|
onOpen: handleOpen
|
|
9233
9857
|
}
|
|
9234
9858
|
),
|
|
9859
|
+
variant === "gridCompact" && /* @__PURE__ */ jsx(
|
|
9860
|
+
CompactGridGallery,
|
|
9861
|
+
{
|
|
9862
|
+
photos: normalised,
|
|
9863
|
+
initialVisible,
|
|
9864
|
+
onOpen: handleOpen
|
|
9865
|
+
}
|
|
9866
|
+
),
|
|
9235
9867
|
variant === "masonry" && /* @__PURE__ */ jsx(
|
|
9236
9868
|
MasonryGallery,
|
|
9237
9869
|
{
|
|
@@ -9266,7 +9898,7 @@ function ItineraryDay({
|
|
|
9266
9898
|
photoLayout = "rounded",
|
|
9267
9899
|
className
|
|
9268
9900
|
}) {
|
|
9269
|
-
const photoList =
|
|
9901
|
+
const photoList = React28.useMemo(() => normalisePhotos(photos), [photos]);
|
|
9270
9902
|
const isFullBleed = photoLayout === "fullBleed" || photoLayout === "fullBleedBottom";
|
|
9271
9903
|
const photoPosition = photoLayout === "fullBleedBottom" ? "bottom" : "top";
|
|
9272
9904
|
const gallery = photoList.length > 0 && /* @__PURE__ */ jsx(
|
|
@@ -9285,13 +9917,16 @@ function ItineraryDay({
|
|
|
9285
9917
|
specs && specs.length > 0 && /* @__PURE__ */ jsx("ul", { className: "flex flex-col gap-3 sm:gap-2.5", children: specs.map((spec, i) => /* @__PURE__ */ jsxs(
|
|
9286
9918
|
"li",
|
|
9287
9919
|
{
|
|
9288
|
-
className: "flex
|
|
9920
|
+
className: "flex items-start gap-3 text-base text-foreground font-ui",
|
|
9289
9921
|
children: [
|
|
9290
|
-
/* @__PURE__ */
|
|
9291
|
-
|
|
9292
|
-
|
|
9293
|
-
|
|
9294
|
-
|
|
9922
|
+
/* @__PURE__ */ jsx("span", { className: "mt-0.5 shrink-0 text-foreground", "aria-hidden": true, children: spec.icon }),
|
|
9923
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-col", children: [
|
|
9924
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-wrap items-baseline gap-x-2", children: [
|
|
9925
|
+
/* @__PURE__ */ jsx("span", { className: "font-semibold", children: spec.label }),
|
|
9926
|
+
spec.detail && /* @__PURE__ */ jsx("span", { className: "text-muted-foreground", children: spec.detail })
|
|
9927
|
+
] }),
|
|
9928
|
+
spec.subdetail && /* @__PURE__ */ jsx("span", { className: "text-sm text-muted-foreground", children: spec.subdetail })
|
|
9929
|
+
] })
|
|
9295
9930
|
]
|
|
9296
9931
|
},
|
|
9297
9932
|
i
|
|
@@ -9318,8 +9953,8 @@ function MenuTrip({
|
|
|
9318
9953
|
bold = true,
|
|
9319
9954
|
className
|
|
9320
9955
|
}) {
|
|
9321
|
-
const scrollRef =
|
|
9322
|
-
|
|
9956
|
+
const scrollRef = React28.useRef(null);
|
|
9957
|
+
React28.useEffect(() => {
|
|
9323
9958
|
if (!scrollRef.current || !activeSection) return;
|
|
9324
9959
|
const container = scrollRef.current;
|
|
9325
9960
|
const btn = container.querySelector(
|
|
@@ -9510,8 +10145,8 @@ function PricingTrip({
|
|
|
9510
10145
|
className
|
|
9511
10146
|
}) {
|
|
9512
10147
|
const rOuter = sharp ? "rounded-none" : "rounded-2xl";
|
|
9513
|
-
const [showEstimates, setShowEstimates] =
|
|
9514
|
-
const [showPriceInfo, setShowPriceInfo] =
|
|
10148
|
+
const [showEstimates, setShowEstimates] = React28.useState(false);
|
|
10149
|
+
const [showPriceInfo, setShowPriceInfo] = React28.useState(false);
|
|
9515
10150
|
if (variant === "compact") {
|
|
9516
10151
|
const showOverlay = showPriceInfo && (!!priceInfo || !!currencyEstimates && currencyEstimates.length > 0);
|
|
9517
10152
|
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col gap-2", className), children: [
|
|
@@ -9795,8 +10430,7 @@ var VARIANT = {
|
|
|
9795
10430
|
mobileLink: "text-white hover:text-primary-400 border-b border-white/10",
|
|
9796
10431
|
mobileSub: "text-white/70 font-bold hover:text-primary-400 border-b border-white/8",
|
|
9797
10432
|
mobileLangActive: "text-primary-400 font-semibold",
|
|
9798
|
-
mobileLangIdle: "text-white/40 hover:text-primary-400"
|
|
9799
|
-
logoBlend: "mix-blend-screen"
|
|
10433
|
+
mobileLangIdle: "text-white/40 hover:text-primary-400"
|
|
9800
10434
|
},
|
|
9801
10435
|
white: {
|
|
9802
10436
|
header: "bg-white border-b border-border shadow-sm",
|
|
@@ -9812,8 +10446,7 @@ var VARIANT = {
|
|
|
9812
10446
|
mobileLink: "text-foreground/80 hover:text-foreground border-b border-border",
|
|
9813
10447
|
mobileSub: "text-foreground/50 font-bold hover:text-foreground border-b border-border/40",
|
|
9814
10448
|
mobileLangActive: "text-primary font-semibold",
|
|
9815
|
-
mobileLangIdle: "text-muted-foreground hover:text-foreground"
|
|
9816
|
-
logoBlend: "invert mix-blend-multiply"
|
|
10449
|
+
mobileLangIdle: "text-muted-foreground hover:text-foreground"
|
|
9817
10450
|
},
|
|
9818
10451
|
dark: {
|
|
9819
10452
|
header: "bg-neutral-950 border-b border-white/10",
|
|
@@ -9829,8 +10462,7 @@ var VARIANT = {
|
|
|
9829
10462
|
mobileLink: "text-white/80 hover:text-white border-b border-white/8",
|
|
9830
10463
|
mobileSub: "text-white/45 font-bold hover:text-white border-b border-white/5",
|
|
9831
10464
|
mobileLangActive: "text-white font-semibold",
|
|
9832
|
-
mobileLangIdle: "text-white/35 hover:text-white/60"
|
|
9833
|
-
logoBlend: "mix-blend-screen"
|
|
10465
|
+
mobileLangIdle: "text-white/35 hover:text-white/60"
|
|
9834
10466
|
}
|
|
9835
10467
|
};
|
|
9836
10468
|
var DEFAULT_HEADER_LINKS = [
|
|
@@ -9940,7 +10572,9 @@ function LangDropdown({
|
|
|
9940
10572
|
function SiteHeader({
|
|
9941
10573
|
variant = "transparent",
|
|
9942
10574
|
links = DEFAULT_HEADER_LINKS,
|
|
9943
|
-
|
|
10575
|
+
logoSrcLight = "/logo-planetaexo-white.png",
|
|
10576
|
+
logoSrcDark = "/logo-planetaexo-green.png",
|
|
10577
|
+
logoSrc,
|
|
9944
10578
|
logoAlt = "Planeta Exo",
|
|
9945
10579
|
languages = DEFAULT_LANGUAGES,
|
|
9946
10580
|
currentLanguage = "EN",
|
|
@@ -9951,14 +10585,15 @@ function SiteHeader({
|
|
|
9951
10585
|
className
|
|
9952
10586
|
}) {
|
|
9953
10587
|
const t = VARIANT[variant];
|
|
9954
|
-
const
|
|
9955
|
-
const [
|
|
9956
|
-
const [
|
|
9957
|
-
const [
|
|
9958
|
-
const [
|
|
10588
|
+
const resolvedLogo = logoSrc != null ? logoSrc : variant === "white" ? logoSrcDark : logoSrcLight;
|
|
10589
|
+
const [openMenu, setOpenMenu] = React28.useState(null);
|
|
10590
|
+
const [langOpen, setLangOpen] = React28.useState(false);
|
|
10591
|
+
const [mobileOpen, setMobileOpen] = React28.useState(false);
|
|
10592
|
+
const [openMobileSection, setOpenMobileSection] = React28.useState(null);
|
|
10593
|
+
const [activeLang, setActiveLang] = React28.useState(currentLanguage);
|
|
9959
10594
|
const toggleMobileSection = (label) => setOpenMobileSection((prev) => prev === label ? null : label);
|
|
9960
|
-
const menuCloseTimer =
|
|
9961
|
-
const langCloseTimer =
|
|
10595
|
+
const menuCloseTimer = React28.useRef(void 0);
|
|
10596
|
+
const langCloseTimer = React28.useRef(void 0);
|
|
9962
10597
|
const handleMenuEnter = (label) => {
|
|
9963
10598
|
clearTimeout(menuCloseTimer.current);
|
|
9964
10599
|
setOpenMenu(label);
|
|
@@ -9979,7 +10614,7 @@ function SiteHeader({
|
|
|
9979
10614
|
setOpenMenu(null);
|
|
9980
10615
|
setLangOpen(false);
|
|
9981
10616
|
};
|
|
9982
|
-
|
|
10617
|
+
React28.useEffect(() => () => {
|
|
9983
10618
|
clearTimeout(menuCloseTimer.current);
|
|
9984
10619
|
clearTimeout(langCloseTimer.current);
|
|
9985
10620
|
}, []);
|
|
@@ -9999,17 +10634,41 @@ function SiteHeader({
|
|
|
9999
10634
|
className
|
|
10000
10635
|
),
|
|
10001
10636
|
children: [
|
|
10002
|
-
variant === "transparent" && /* @__PURE__ */ jsx("div", { className: "absolute inset-x-0 top-0 h-52 bg-gradient-to-b from-black/
|
|
10637
|
+
variant === "transparent" && /* @__PURE__ */ jsx("div", { className: "absolute inset-x-0 top-0 h-52 bg-gradient-to-b from-black/70 via-black/30 to-transparent pointer-events-none" }),
|
|
10003
10638
|
/* @__PURE__ */ jsxs("div", { className: "relative flex items-center gap-2 px-6 sm:px-10 h-[72px]", children: [
|
|
10004
|
-
/* @__PURE__ */ jsx(
|
|
10005
|
-
"
|
|
10639
|
+
/* @__PURE__ */ jsx(
|
|
10640
|
+
"button",
|
|
10006
10641
|
{
|
|
10007
|
-
|
|
10008
|
-
|
|
10009
|
-
|
|
10010
|
-
|
|
10642
|
+
type: "button",
|
|
10643
|
+
onClick: () => setMobileOpen(true),
|
|
10644
|
+
"aria-label": "Open menu",
|
|
10645
|
+
className: cn(
|
|
10646
|
+
"flex lg:hidden h-9 w-9 items-center justify-center rounded-full transition-colors -ml-1.5",
|
|
10647
|
+
t.mobileTrigger
|
|
10648
|
+
),
|
|
10649
|
+
children: /* @__PURE__ */ jsx(MenuIcon, { className: "h-[18px] w-[18px]" })
|
|
10011
10650
|
}
|
|
10012
|
-
)
|
|
10651
|
+
),
|
|
10652
|
+
/* @__PURE__ */ jsx(
|
|
10653
|
+
"a",
|
|
10654
|
+
{
|
|
10655
|
+
href: "#",
|
|
10656
|
+
className: cn(
|
|
10657
|
+
"shrink-0 flex items-center",
|
|
10658
|
+
"absolute left-1/2 -translate-x-1/2",
|
|
10659
|
+
"lg:static lg:translate-x-0 lg:mr-4"
|
|
10660
|
+
),
|
|
10661
|
+
children: /* @__PURE__ */ jsx(
|
|
10662
|
+
"img",
|
|
10663
|
+
{
|
|
10664
|
+
src: resolvedLogo,
|
|
10665
|
+
alt: logoAlt,
|
|
10666
|
+
className: "h-14 w-auto select-none",
|
|
10667
|
+
draggable: false
|
|
10668
|
+
}
|
|
10669
|
+
)
|
|
10670
|
+
}
|
|
10671
|
+
),
|
|
10013
10672
|
/* @__PURE__ */ jsx("nav", { className: "hidden lg:flex items-center gap-0.5 mx-auto", children: links.map((link) => {
|
|
10014
10673
|
var _a, _b;
|
|
10015
10674
|
const hasDropdown = !!((_a = link.items) == null ? void 0 : _a.length);
|
|
@@ -10133,19 +10792,6 @@ function SiteHeader({
|
|
|
10133
10792
|
),
|
|
10134
10793
|
children: /* @__PURE__ */ jsx(UserIcon, { className: "h-[18px] w-[18px]" })
|
|
10135
10794
|
}
|
|
10136
|
-
),
|
|
10137
|
-
/* @__PURE__ */ jsx(
|
|
10138
|
-
"button",
|
|
10139
|
-
{
|
|
10140
|
-
type: "button",
|
|
10141
|
-
onClick: () => setMobileOpen(true),
|
|
10142
|
-
"aria-label": "Open menu",
|
|
10143
|
-
className: cn(
|
|
10144
|
-
"flex lg:hidden h-9 w-9 items-center justify-center rounded-full transition-colors ml-0.5",
|
|
10145
|
-
t.mobileTrigger
|
|
10146
|
-
),
|
|
10147
|
-
children: /* @__PURE__ */ jsx(MenuIcon, { className: "h-[18px] w-[18px]" })
|
|
10148
|
-
}
|
|
10149
10795
|
)
|
|
10150
10796
|
] })
|
|
10151
10797
|
] }),
|
|
@@ -10161,9 +10807,9 @@ function SiteHeader({
|
|
|
10161
10807
|
/* @__PURE__ */ jsx("a", { href: "#", className: "shrink-0 flex items-center", onClick: () => setMobileOpen(false), children: /* @__PURE__ */ jsx(
|
|
10162
10808
|
"img",
|
|
10163
10809
|
{
|
|
10164
|
-
src:
|
|
10810
|
+
src: resolvedLogo,
|
|
10165
10811
|
alt: logoAlt,
|
|
10166
|
-
className:
|
|
10812
|
+
className: "h-14 w-auto select-none",
|
|
10167
10813
|
draggable: false
|
|
10168
10814
|
}
|
|
10169
10815
|
) }),
|
|
@@ -10244,7 +10890,7 @@ function SiteHeader({
|
|
|
10244
10890
|
), children: [
|
|
10245
10891
|
/* @__PURE__ */ jsx("div", { className: "flex items-center gap-1.5 flex-wrap", children: languages.map((lang, i) => {
|
|
10246
10892
|
const isActive = lang.code === activeLang;
|
|
10247
|
-
return /* @__PURE__ */ jsxs(
|
|
10893
|
+
return /* @__PURE__ */ jsxs(React28.Fragment, { children: [
|
|
10248
10894
|
i > 0 && /* @__PURE__ */ jsx("span", { className: cn(
|
|
10249
10895
|
"text-xs select-none",
|
|
10250
10896
|
variant === "white" ? "text-border" : "text-white/15"
|
|
@@ -10306,8 +10952,8 @@ function SiteHeader({
|
|
|
10306
10952
|
);
|
|
10307
10953
|
}
|
|
10308
10954
|
function ThemeToggle({ className }) {
|
|
10309
|
-
const [dark, setDark] =
|
|
10310
|
-
|
|
10955
|
+
const [dark, setDark] = React28.useState(false);
|
|
10956
|
+
React28.useEffect(() => {
|
|
10311
10957
|
const saved = localStorage.getItem("theme");
|
|
10312
10958
|
const prefersDark = window.matchMedia("(prefers-color-scheme: dark)").matches;
|
|
10313
10959
|
const isDark = saved === "dark" || !saved && prefersDark;
|
|
@@ -10336,6 +10982,44 @@ function ThemeToggle({ className }) {
|
|
|
10336
10982
|
}
|
|
10337
10983
|
);
|
|
10338
10984
|
}
|
|
10985
|
+
var chipVariants = cva(
|
|
10986
|
+
"inline-flex items-center rounded-full font-ui font-medium transition-colors whitespace-nowrap",
|
|
10987
|
+
{
|
|
10988
|
+
variants: {
|
|
10989
|
+
variant: {
|
|
10990
|
+
glass: "border border-white/15 bg-black/30 text-white/85 backdrop-blur-sm hover:bg-white/10 hover:border-white/50 hover:text-white",
|
|
10991
|
+
solid: "bg-muted text-foreground/80 hover:bg-primary hover:text-primary-foreground",
|
|
10992
|
+
outline: "border border-border text-foreground/80 hover:bg-primary hover:border-primary hover:text-primary-foreground"
|
|
10993
|
+
},
|
|
10994
|
+
size: {
|
|
10995
|
+
sm: "px-2.5 py-0.5 text-[11px] leading-5",
|
|
10996
|
+
md: "px-3 py-1 text-xs leading-5",
|
|
10997
|
+
lg: "px-4 py-1.5 text-sm leading-5"
|
|
10998
|
+
}
|
|
10999
|
+
},
|
|
11000
|
+
defaultVariants: {
|
|
11001
|
+
variant: "glass",
|
|
11002
|
+
size: "sm"
|
|
11003
|
+
}
|
|
11004
|
+
}
|
|
11005
|
+
);
|
|
11006
|
+
var Chip = React28.forwardRef(function Chip2(_a, ref) {
|
|
11007
|
+
var _b = _a, { className, variant, size, href, children } = _b, props = __objRest(_b, ["className", "variant", "size", "href", "children"]);
|
|
11008
|
+
const classes = cn(chipVariants({ variant, size }), className);
|
|
11009
|
+
if (href) {
|
|
11010
|
+
return /* @__PURE__ */ jsx(
|
|
11011
|
+
"a",
|
|
11012
|
+
__spreadProps(__spreadValues({
|
|
11013
|
+
ref,
|
|
11014
|
+
href,
|
|
11015
|
+
className: classes
|
|
11016
|
+
}, props), {
|
|
11017
|
+
children
|
|
11018
|
+
})
|
|
11019
|
+
);
|
|
11020
|
+
}
|
|
11021
|
+
return /* @__PURE__ */ jsx("span", __spreadProps(__spreadValues({ ref, className: classes }, props), { children }));
|
|
11022
|
+
});
|
|
10339
11023
|
function CalendarIcon6() {
|
|
10340
11024
|
return /* @__PURE__ */ jsxs("svg", { width: "13", height: "13", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2.2", strokeLinecap: "round", strokeLinejoin: "round", children: [
|
|
10341
11025
|
/* @__PURE__ */ jsx("rect", { x: "3", y: "4", width: "18", height: "18", rx: "2" }),
|
|
@@ -10386,19 +11070,125 @@ var statusConfig = {
|
|
|
10386
11070
|
icon: /* @__PURE__ */ jsx(TrendingIcon, {})
|
|
10387
11071
|
}
|
|
10388
11072
|
};
|
|
10389
|
-
function
|
|
10390
|
-
|
|
10391
|
-
|
|
10392
|
-
|
|
10393
|
-
|
|
10394
|
-
|
|
10395
|
-
|
|
10396
|
-
|
|
10397
|
-
|
|
10398
|
-
|
|
10399
|
-
|
|
10400
|
-
|
|
10401
|
-
})
|
|
11073
|
+
function HeartIcon({ filled = false }) {
|
|
11074
|
+
return /* @__PURE__ */ jsx(
|
|
11075
|
+
"svg",
|
|
11076
|
+
{
|
|
11077
|
+
width: "16",
|
|
11078
|
+
height: "16",
|
|
11079
|
+
viewBox: "0 0 24 24",
|
|
11080
|
+
fill: filled ? "currentColor" : "none",
|
|
11081
|
+
stroke: "currentColor",
|
|
11082
|
+
strokeWidth: "2",
|
|
11083
|
+
strokeLinecap: "round",
|
|
11084
|
+
strokeLinejoin: "round",
|
|
11085
|
+
children: /* @__PURE__ */ jsx("path", { d: "M20.84 4.61a5.5 5.5 0 0 0-7.78 0L12 5.67l-1.06-1.06a5.5 5.5 0 0 0-7.78 7.78l1.06 1.06L12 21.23l7.78-7.78 1.06-1.06a5.5 5.5 0 0 0 0-7.78z" })
|
|
11086
|
+
}
|
|
11087
|
+
);
|
|
11088
|
+
}
|
|
11089
|
+
function TripCardEditorial(props) {
|
|
11090
|
+
const {
|
|
11091
|
+
image,
|
|
11092
|
+
imageAlt = "",
|
|
11093
|
+
title,
|
|
11094
|
+
description,
|
|
11095
|
+
nights,
|
|
11096
|
+
price,
|
|
11097
|
+
href,
|
|
11098
|
+
className,
|
|
11099
|
+
favoritable,
|
|
11100
|
+
favorited: favoritedProp,
|
|
11101
|
+
onFavoriteToggle,
|
|
11102
|
+
location,
|
|
11103
|
+
difficulty,
|
|
11104
|
+
tag
|
|
11105
|
+
} = props;
|
|
11106
|
+
const [internalFav, setInternalFav] = React28.useState(false);
|
|
11107
|
+
const favorited = favoritedProp != null ? favoritedProp : internalFav;
|
|
11108
|
+
const handleFav = (e) => {
|
|
11109
|
+
e.preventDefault();
|
|
11110
|
+
e.stopPropagation();
|
|
11111
|
+
const next = !favorited;
|
|
11112
|
+
if (favoritedProp === void 0) setInternalFav(next);
|
|
11113
|
+
onFavoriteToggle == null ? void 0 : onFavoriteToggle(next);
|
|
11114
|
+
};
|
|
11115
|
+
const body = /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
11116
|
+
/* @__PURE__ */ jsxs("div", { className: "relative aspect-[4/3] overflow-hidden bg-muted", children: [
|
|
11117
|
+
/* @__PURE__ */ jsx(
|
|
11118
|
+
"img",
|
|
11119
|
+
{
|
|
11120
|
+
src: image,
|
|
11121
|
+
alt: imageAlt,
|
|
11122
|
+
loading: "lazy",
|
|
11123
|
+
className: "absolute inset-0 h-full w-full object-cover transition-transform duration-500 group-hover:scale-105"
|
|
11124
|
+
}
|
|
11125
|
+
),
|
|
11126
|
+
/* @__PURE__ */ jsx("div", { className: "absolute inset-0 bg-gradient-to-t from-black/85 via-black/20 to-transparent" }),
|
|
11127
|
+
tag && /* @__PURE__ */ jsx("div", { className: "absolute top-3 left-3 z-10 max-w-[calc(100%-4.5rem)]", children: /* @__PURE__ */ jsx(Chip, { variant: "glass", size: "sm", children: tag }) }),
|
|
11128
|
+
favoritable && /* @__PURE__ */ jsx(
|
|
11129
|
+
"button",
|
|
11130
|
+
{
|
|
11131
|
+
type: "button",
|
|
11132
|
+
"aria-label": favorited ? "Remove from favorites" : "Add to favorites",
|
|
11133
|
+
"aria-pressed": favorited,
|
|
11134
|
+
onClick: handleFav,
|
|
11135
|
+
className: cn(
|
|
11136
|
+
"absolute top-3 right-3 flex h-9 w-9 items-center justify-center rounded-full",
|
|
11137
|
+
"border border-white/15 bg-black/30 backdrop-blur-sm",
|
|
11138
|
+
"transition-colors hover:bg-white/10 hover:border-white/50",
|
|
11139
|
+
favorited ? "text-white" : "text-white/85 hover:text-white"
|
|
11140
|
+
),
|
|
11141
|
+
children: /* @__PURE__ */ jsx(HeartIcon, { filled: favorited })
|
|
11142
|
+
}
|
|
11143
|
+
),
|
|
11144
|
+
/* @__PURE__ */ jsx("div", { className: "absolute inset-x-0 bottom-0 p-5 text-white", children: /* @__PURE__ */ jsx("h3", { className: "text-lg sm:text-xl font-bold font-heading leading-tight", children: title }) })
|
|
11145
|
+
] }),
|
|
11146
|
+
(description || price || nights || location || difficulty) && /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-4 bg-card p-6", children: [
|
|
11147
|
+
(location || difficulty) && /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between gap-3", children: [
|
|
11148
|
+
location ? /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-1.5 text-foreground/85", children: [
|
|
11149
|
+
/* @__PURE__ */ jsx(MapPinIcon, { className: "h-4 w-4 shrink-0 text-muted-foreground" }),
|
|
11150
|
+
/* @__PURE__ */ jsx("span", { className: "text-sm font-ui font-semibold", children: location })
|
|
11151
|
+
] }) : /* @__PURE__ */ jsx("span", {}),
|
|
11152
|
+
difficulty && /* @__PURE__ */ jsx(Chip, { variant: "outline", size: "sm", className: "capitalize text-muted-foreground", children: difficulty })
|
|
11153
|
+
] }),
|
|
11154
|
+
description && /* @__PURE__ */ jsx("p", { className: "text-sm text-muted-foreground leading-relaxed line-clamp-3", children: description }),
|
|
11155
|
+
(nights || price) && /* @__PURE__ */ jsxs("div", { className: "mt-auto flex items-center justify-between gap-3", children: [
|
|
11156
|
+
nights ? /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-1.5 text-foreground/80", children: [
|
|
11157
|
+
/* @__PURE__ */ jsx(MoonIcon, { className: "h-4 w-4 shrink-0 text-muted-foreground" }),
|
|
11158
|
+
/* @__PURE__ */ jsxs("span", { className: "text-sm font-ui font-semibold", children: [
|
|
11159
|
+
nights,
|
|
11160
|
+
" ",
|
|
11161
|
+
nights === 1 ? "night" : "nights"
|
|
11162
|
+
] })
|
|
11163
|
+
] }) : /* @__PURE__ */ jsx("span", {}),
|
|
11164
|
+
price && /* @__PURE__ */ jsx("p", { className: "text-base font-bold text-foreground font-ui", children: price })
|
|
11165
|
+
] })
|
|
11166
|
+
] })
|
|
11167
|
+
] });
|
|
11168
|
+
const baseClasses = cn(
|
|
11169
|
+
"group relative flex flex-col overflow-hidden rounded-2xl bg-card border border-border/50",
|
|
11170
|
+
"shadow-md transition-shadow duration-300 hover:shadow-xl",
|
|
11171
|
+
className
|
|
11172
|
+
);
|
|
11173
|
+
return href ? /* @__PURE__ */ jsx("a", { href, className: baseClasses, "aria-label": title, children: body }) : /* @__PURE__ */ jsx("div", { className: baseClasses, children: body });
|
|
11174
|
+
}
|
|
11175
|
+
function TripCard(props) {
|
|
11176
|
+
if (props.variant === "editorial") {
|
|
11177
|
+
return /* @__PURE__ */ jsx(TripCardEditorial, __spreadValues({}, props));
|
|
11178
|
+
}
|
|
11179
|
+
const {
|
|
11180
|
+
image,
|
|
11181
|
+
imageAlt = "",
|
|
11182
|
+
status,
|
|
11183
|
+
nights,
|
|
11184
|
+
period,
|
|
11185
|
+
title,
|
|
11186
|
+
description,
|
|
11187
|
+
cta,
|
|
11188
|
+
price,
|
|
11189
|
+
size = "md",
|
|
11190
|
+
className
|
|
11191
|
+
} = props;
|
|
10402
11192
|
const s = sizeConfig[size];
|
|
10403
11193
|
const statusInfo = status ? statusConfig[status] : null;
|
|
10404
11194
|
const meta = [
|
|
@@ -10458,7 +11248,7 @@ function TripCard({
|
|
|
10458
11248
|
);
|
|
10459
11249
|
}
|
|
10460
11250
|
function useHlsVideo(videoRef, src) {
|
|
10461
|
-
|
|
11251
|
+
React28.useEffect(() => {
|
|
10462
11252
|
if (!src || !videoRef.current) return;
|
|
10463
11253
|
const video = videoRef.current;
|
|
10464
11254
|
if (!src.includes(".m3u8")) return;
|
|
@@ -10495,17 +11285,18 @@ function TripHeader({
|
|
|
10495
11285
|
destination,
|
|
10496
11286
|
duration,
|
|
10497
11287
|
tagline,
|
|
11288
|
+
chips,
|
|
10498
11289
|
belowMeta,
|
|
10499
11290
|
siteHeader,
|
|
10500
11291
|
uiVariant = "v1",
|
|
10501
11292
|
className
|
|
10502
11293
|
}) {
|
|
10503
11294
|
var _a;
|
|
10504
|
-
const [heroIndex, setHeroIndex] =
|
|
10505
|
-
const [videoReady, setVideoReady] =
|
|
10506
|
-
const videoRef =
|
|
11295
|
+
const [heroIndex, setHeroIndex] = React28.useState(0);
|
|
11296
|
+
const [videoReady, setVideoReady] = React28.useState(false);
|
|
11297
|
+
const videoRef = React28.useRef(null);
|
|
10507
11298
|
const isHls = !!(videoUrl == null ? void 0 : videoUrl.includes(".m3u8"));
|
|
10508
|
-
const validImages =
|
|
11299
|
+
const validImages = React28.useMemo(
|
|
10509
11300
|
() => images.map((u) => u == null ? void 0 : u.trim()).filter(Boolean),
|
|
10510
11301
|
[images]
|
|
10511
11302
|
);
|
|
@@ -10520,7 +11311,7 @@ function TripHeader({
|
|
|
10520
11311
|
const nights = duration ? (_a = duration.nights) != null ? _a : Math.max(duration.days - 1, 1) : null;
|
|
10521
11312
|
const hasMeta = !!(destination || duration);
|
|
10522
11313
|
useHlsVideo(videoRef, isHls ? videoUrl : void 0);
|
|
10523
|
-
|
|
11314
|
+
React28.useEffect(() => {
|
|
10524
11315
|
if (!videoUrl) return;
|
|
10525
11316
|
const el = videoRef.current;
|
|
10526
11317
|
if (!el) return;
|
|
@@ -10654,15 +11445,15 @@ function TripHeader({
|
|
|
10654
11445
|
]
|
|
10655
11446
|
}
|
|
10656
11447
|
),
|
|
10657
|
-
/* @__PURE__ */ jsx("div", { className: "mx-auto w-full max-w-
|
|
11448
|
+
/* @__PURE__ */ jsx("div", { className: "mx-auto w-full max-w-6xl px-6 sm:px-8", children: /* @__PURE__ */ jsxs(
|
|
10658
11449
|
"div",
|
|
10659
11450
|
{
|
|
10660
11451
|
className: cn(
|
|
10661
11452
|
"relative z-10 pb-10",
|
|
10662
|
-
siteHeader ? "-mt-44" : "-mt-36"
|
|
11453
|
+
chips && chips.length > 0 ? siteHeader ? "-mt-[200px] sm:-mt-[214px]" : "-mt-[168px] sm:-mt-[182px]" : siteHeader ? "-mt-44" : "-mt-36"
|
|
10663
11454
|
),
|
|
10664
11455
|
children: [
|
|
10665
|
-
breadcrumb && breadcrumb.length > 0 && /* @__PURE__ */ jsx("div", { className: "mb-3 flex items-center gap-1.5 flex-wrap", children: breadcrumb.map((crumb, i) => /* @__PURE__ */ jsxs(
|
|
11456
|
+
breadcrumb && breadcrumb.length > 0 && /* @__PURE__ */ jsx("div", { className: "mb-3 flex items-center gap-1.5 flex-wrap", children: breadcrumb.map((crumb, i) => /* @__PURE__ */ jsxs(React28.Fragment, { children: [
|
|
10666
11457
|
i > 0 && /* @__PURE__ */ jsx(ChevronRightIcon, { className: "h-3 w-3 text-white/50 shrink-0" }),
|
|
10667
11458
|
/* @__PURE__ */ jsx("span", { className: "text-xs text-white/70 font-ui hover:text-white/90 cursor-default", children: crumb.label })
|
|
10668
11459
|
] }, i)) }),
|
|
@@ -10688,6 +11479,7 @@ function TripHeader({
|
|
|
10688
11479
|
] })
|
|
10689
11480
|
] })
|
|
10690
11481
|
] }) : tagline ? /* @__PURE__ */ jsx("p", { className: "mt-2 text-sm sm:text-base text-white/80 font-ui", children: tagline }) : null,
|
|
11482
|
+
chips && chips.length > 0 && /* @__PURE__ */ jsx("div", { className: "mt-3 flex flex-wrap items-center gap-1.5", children: chips.map((chip, i) => /* @__PURE__ */ jsx(Chip, { href: chip.href, children: chip.label }, i)) }),
|
|
10691
11483
|
belowMeta && /* @__PURE__ */ jsx("div", { className: "mt-3", children: belowMeta })
|
|
10692
11484
|
]
|
|
10693
11485
|
}
|
|
@@ -10696,6 +11488,427 @@ function TripHeader({
|
|
|
10696
11488
|
}
|
|
10697
11489
|
);
|
|
10698
11490
|
}
|
|
11491
|
+
var VARIANT2 = {
|
|
11492
|
+
light: {
|
|
11493
|
+
footer: "bg-primary-50 text-foreground",
|
|
11494
|
+
heading: "text-foreground",
|
|
11495
|
+
body: "text-foreground/75",
|
|
11496
|
+
muted: "text-foreground/60",
|
|
11497
|
+
link: "text-foreground/85 hover:text-primary-800 underline decoration-foreground/25 underline-offset-4 hover:decoration-primary-800",
|
|
11498
|
+
badgeStroke: "text-foreground/80",
|
|
11499
|
+
/** Inverts white logos so they read on the light background. */
|
|
11500
|
+
badgeFilter: "[filter:invert(1)_brightness(0.2)]",
|
|
11501
|
+
socialBtn: "bg-foreground text-white hover:bg-primary-800",
|
|
11502
|
+
langTrigger: "text-foreground hover:bg-white",
|
|
11503
|
+
langOpen: "text-foreground bg-white",
|
|
11504
|
+
langChevron: "text-foreground/40",
|
|
11505
|
+
bottomBar: "border-t border-foreground/10",
|
|
11506
|
+
bottomText: "text-foreground/60",
|
|
11507
|
+
bottomLink: "text-foreground/80 hover:text-foreground underline decoration-foreground/20 underline-offset-4 hover:decoration-foreground"
|
|
11508
|
+
},
|
|
11509
|
+
dark: {
|
|
11510
|
+
footer: "bg-brand-charcoal text-white",
|
|
11511
|
+
heading: "text-white",
|
|
11512
|
+
body: "text-white/75",
|
|
11513
|
+
muted: "text-white/55",
|
|
11514
|
+
link: "text-white/85 hover:text-primary-400 underline decoration-white/20 underline-offset-4 hover:decoration-primary-400",
|
|
11515
|
+
badgeStroke: "text-white",
|
|
11516
|
+
badgeFilter: "",
|
|
11517
|
+
socialBtn: "bg-white/10 text-white hover:bg-primary-400 hover:text-primary-900",
|
|
11518
|
+
langTrigger: "text-white/85 hover:bg-white/10",
|
|
11519
|
+
langOpen: "text-white bg-white/10",
|
|
11520
|
+
langChevron: "text-white/40",
|
|
11521
|
+
bottomBar: "border-t border-white/10",
|
|
11522
|
+
bottomText: "text-white/55",
|
|
11523
|
+
bottomLink: "text-white/80 hover:text-white underline decoration-white/20 underline-offset-4 hover:decoration-white"
|
|
11524
|
+
}
|
|
11525
|
+
};
|
|
11526
|
+
var DEFAULT_FOOTER_THEMES = [
|
|
11527
|
+
{ label: "Roadtrips", href: "#" },
|
|
11528
|
+
{ label: "Saf\xE1ri", href: "#" },
|
|
11529
|
+
{ label: "Trilhas", href: "#" },
|
|
11530
|
+
{ label: "Caiaque & Canoa", href: "#" },
|
|
11531
|
+
{ label: "Aurora boreal", href: "#" },
|
|
11532
|
+
{ label: "Micro-aventuras", href: "#" },
|
|
11533
|
+
{ label: "Packrafting", href: "#" },
|
|
11534
|
+
{ label: "Glamping", href: "#" },
|
|
11535
|
+
{ label: "Surf", href: "#" },
|
|
11536
|
+
{ label: "Viagens em fam\xEDlia", href: "#" }
|
|
11537
|
+
];
|
|
11538
|
+
var DEFAULT_FOOTER_DESTINATIONS = [
|
|
11539
|
+
{ label: "Brasil", href: "#" },
|
|
11540
|
+
{ label: "Patag\xF4nia", href: "#" },
|
|
11541
|
+
{ label: "Argentina", href: "#" },
|
|
11542
|
+
{ label: "Chile", href: "#" },
|
|
11543
|
+
{ label: "Bol\xEDvia", href: "#" },
|
|
11544
|
+
{ label: "Peru", href: "#" },
|
|
11545
|
+
{ label: "Equador", href: "#" },
|
|
11546
|
+
{ label: "Col\xF4mbia", href: "#" },
|
|
11547
|
+
{ label: "Costa Rica", href: "#" },
|
|
11548
|
+
{ label: "Filipinas", href: "#" }
|
|
11549
|
+
];
|
|
11550
|
+
var DEFAULT_FOOTER_PAGES = [
|
|
11551
|
+
{ label: "Contato", href: "#" },
|
|
11552
|
+
{ label: "Pol\xEDtica de cookies", href: "#" },
|
|
11553
|
+
{ label: "FAQ", href: "#" },
|
|
11554
|
+
{ label: "Sobre n\xF3s", href: "#" }
|
|
11555
|
+
];
|
|
11556
|
+
var DEFAULT_FOOTER_LEGAL = [
|
|
11557
|
+
{ label: "Termos e condi\xE7\xF5es", href: "#" },
|
|
11558
|
+
{ label: "Mapa do site", href: "#" }
|
|
11559
|
+
];
|
|
11560
|
+
var DEFAULT_FOOTER_LANGUAGES = [
|
|
11561
|
+
{ code: "PT", label: "Portugu\xEAs" },
|
|
11562
|
+
{ code: "EN", label: "English" },
|
|
11563
|
+
{ code: "NL", label: "Nederlands" },
|
|
11564
|
+
{ code: "DE", label: "Deutsch" },
|
|
11565
|
+
{ code: "FR", label: "Fran\xE7ais" },
|
|
11566
|
+
{ code: "ES", label: "Espa\xF1ol" }
|
|
11567
|
+
];
|
|
11568
|
+
var DEFAULT_FOOTER_SOCIALS = [
|
|
11569
|
+
{ network: "facebook", href: "#" },
|
|
11570
|
+
{ network: "instagram", href: "#" },
|
|
11571
|
+
{ network: "linkedin", href: "#" }
|
|
11572
|
+
];
|
|
11573
|
+
var DEFAULT_FOOTER_BADGES = [
|
|
11574
|
+
{
|
|
11575
|
+
src: "https://static.planetaexo.com/trips/wp-content/uploads/2025/04/member_of_TLR-white-1.png",
|
|
11576
|
+
alt: "Member of The Long Run",
|
|
11577
|
+
height: 80
|
|
11578
|
+
},
|
|
11579
|
+
{
|
|
11580
|
+
src: "https://static.planetaexo.com/trips/wp-content/uploads/2025/04/atta-member_white.png",
|
|
11581
|
+
alt: "Member \xB7 Adventure Travel Trade Association",
|
|
11582
|
+
height: 56
|
|
11583
|
+
}
|
|
11584
|
+
];
|
|
11585
|
+
var SOCIAL_ICON = {
|
|
11586
|
+
facebook: FacebookIcon,
|
|
11587
|
+
instagram: InstagramIcon,
|
|
11588
|
+
linkedin: LinkedinIcon,
|
|
11589
|
+
youtube: YoutubeIcon,
|
|
11590
|
+
twitter: TwitterIcon
|
|
11591
|
+
};
|
|
11592
|
+
var SOCIAL_LABEL = {
|
|
11593
|
+
facebook: "Facebook",
|
|
11594
|
+
instagram: "Instagram",
|
|
11595
|
+
linkedin: "LinkedIn",
|
|
11596
|
+
youtube: "YouTube",
|
|
11597
|
+
twitter: "Twitter"
|
|
11598
|
+
};
|
|
11599
|
+
function ColumnHeading({
|
|
11600
|
+
children,
|
|
11601
|
+
className
|
|
11602
|
+
}) {
|
|
11603
|
+
return /* @__PURE__ */ jsx(
|
|
11604
|
+
"h3",
|
|
11605
|
+
{
|
|
11606
|
+
className: cn(
|
|
11607
|
+
"font-heading font-black text-base mb-5 tracking-tight",
|
|
11608
|
+
className
|
|
11609
|
+
),
|
|
11610
|
+
children
|
|
11611
|
+
}
|
|
11612
|
+
);
|
|
11613
|
+
}
|
|
11614
|
+
function LanguagePicker({
|
|
11615
|
+
variant,
|
|
11616
|
+
languages,
|
|
11617
|
+
currentLanguage,
|
|
11618
|
+
onChange
|
|
11619
|
+
}) {
|
|
11620
|
+
var _a;
|
|
11621
|
+
const t = VARIANT2[variant];
|
|
11622
|
+
const [open, setOpen] = React28.useState(false);
|
|
11623
|
+
const ref = React28.useRef(null);
|
|
11624
|
+
const active = (_a = languages.find((l) => l.code === currentLanguage)) != null ? _a : languages[0];
|
|
11625
|
+
React28.useEffect(() => {
|
|
11626
|
+
if (!open) return;
|
|
11627
|
+
const onDocClick = (e) => {
|
|
11628
|
+
if (ref.current && !ref.current.contains(e.target)) {
|
|
11629
|
+
setOpen(false);
|
|
11630
|
+
}
|
|
11631
|
+
};
|
|
11632
|
+
document.addEventListener("mousedown", onDocClick);
|
|
11633
|
+
return () => document.removeEventListener("mousedown", onDocClick);
|
|
11634
|
+
}, [open]);
|
|
11635
|
+
return /* @__PURE__ */ jsxs("div", { ref, className: "relative inline-block", children: [
|
|
11636
|
+
/* @__PURE__ */ jsxs(
|
|
11637
|
+
"button",
|
|
11638
|
+
{
|
|
11639
|
+
type: "button",
|
|
11640
|
+
onClick: () => setOpen((v) => !v),
|
|
11641
|
+
"aria-haspopup": "listbox",
|
|
11642
|
+
"aria-expanded": open,
|
|
11643
|
+
className: cn(
|
|
11644
|
+
"inline-flex items-center gap-1 px-3 py-1.5 rounded-full text-sm font-ui transition-colors",
|
|
11645
|
+
t.langTrigger,
|
|
11646
|
+
open && t.langOpen
|
|
11647
|
+
),
|
|
11648
|
+
children: [
|
|
11649
|
+
active == null ? void 0 : active.code,
|
|
11650
|
+
/* @__PURE__ */ jsx(
|
|
11651
|
+
ChevronDownIcon,
|
|
11652
|
+
{
|
|
11653
|
+
className: cn(
|
|
11654
|
+
"h-3 w-3 transition-transform duration-150",
|
|
11655
|
+
t.langChevron,
|
|
11656
|
+
open && "rotate-180"
|
|
11657
|
+
)
|
|
11658
|
+
}
|
|
11659
|
+
)
|
|
11660
|
+
]
|
|
11661
|
+
}
|
|
11662
|
+
),
|
|
11663
|
+
open && /* @__PURE__ */ jsx(
|
|
11664
|
+
"div",
|
|
11665
|
+
{
|
|
11666
|
+
role: "listbox",
|
|
11667
|
+
className: "absolute left-0 bottom-[calc(100%+8px)] min-w-[180px] rounded-xl bg-white shadow-2xl border border-black/8 py-1.5 z-10",
|
|
11668
|
+
children: languages.map((lang) => {
|
|
11669
|
+
const isActive = lang.code === (active == null ? void 0 : active.code);
|
|
11670
|
+
return /* @__PURE__ */ jsxs(
|
|
11671
|
+
"button",
|
|
11672
|
+
{
|
|
11673
|
+
type: "button",
|
|
11674
|
+
role: "option",
|
|
11675
|
+
"aria-selected": isActive,
|
|
11676
|
+
onClick: () => {
|
|
11677
|
+
onChange == null ? void 0 : onChange(lang.code);
|
|
11678
|
+
setOpen(false);
|
|
11679
|
+
},
|
|
11680
|
+
className: cn(
|
|
11681
|
+
"flex items-center gap-3 w-full px-5 py-2.5 text-sm font-ui text-left transition-colors hover:bg-muted",
|
|
11682
|
+
isActive ? "text-primary font-semibold" : "text-foreground"
|
|
11683
|
+
),
|
|
11684
|
+
children: [
|
|
11685
|
+
/* @__PURE__ */ jsx("span", { className: "font-semibold w-8 shrink-0", children: lang.code }),
|
|
11686
|
+
/* @__PURE__ */ jsx("span", { className: "text-muted-foreground", children: lang.label })
|
|
11687
|
+
]
|
|
11688
|
+
},
|
|
11689
|
+
lang.code
|
|
11690
|
+
);
|
|
11691
|
+
})
|
|
11692
|
+
}
|
|
11693
|
+
)
|
|
11694
|
+
] });
|
|
11695
|
+
}
|
|
11696
|
+
function SiteFooter({
|
|
11697
|
+
variant = "dark",
|
|
11698
|
+
brandTitle = "PlanetaEXO",
|
|
11699
|
+
logoSrcLight = "/logo-planetaexo-white.png",
|
|
11700
|
+
logoSrcDark = "/logo-planetaexo-green.png",
|
|
11701
|
+
logoSrc,
|
|
11702
|
+
logoAlt = "PlanetaEXO",
|
|
11703
|
+
logoHref = "#",
|
|
11704
|
+
brandDescription = /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
11705
|
+
"A PlanetaEXO \xE9 uma ag\xEAncia brasileira especializada em viagens de ecoturismo e aventura. Operamos com guias locais credenciados e parceiros que respeitam comunidades e ecossistemas.",
|
|
11706
|
+
" ",
|
|
11707
|
+
/* @__PURE__ */ jsx(
|
|
11708
|
+
"a",
|
|
11709
|
+
{
|
|
11710
|
+
href: "#",
|
|
11711
|
+
className: "font-bold underline decoration-current/30 underline-offset-4 hover:decoration-current",
|
|
11712
|
+
children: "Pol\xEDtica de privacidade"
|
|
11713
|
+
}
|
|
11714
|
+
)
|
|
11715
|
+
] }),
|
|
11716
|
+
badges = DEFAULT_FOOTER_BADGES,
|
|
11717
|
+
languages = DEFAULT_FOOTER_LANGUAGES,
|
|
11718
|
+
currentLanguage = "PT",
|
|
11719
|
+
onLanguageChange,
|
|
11720
|
+
address = {
|
|
11721
|
+
title: "Basecamp S\xE3o Paulo",
|
|
11722
|
+
lines: ["Av. Paulista, 1234", "01310-100 S\xE3o Paulo \xB7 Brasil"]
|
|
11723
|
+
},
|
|
11724
|
+
phone = "+55 11 9999-0000",
|
|
11725
|
+
email = "ola@planetaexo.com",
|
|
11726
|
+
socials = DEFAULT_FOOTER_SOCIALS,
|
|
11727
|
+
themesTitle = "Temas",
|
|
11728
|
+
themes = DEFAULT_FOOTER_THEMES,
|
|
11729
|
+
destinationsTitle = "Destinos",
|
|
11730
|
+
destinations = DEFAULT_FOOTER_DESTINATIONS,
|
|
11731
|
+
destinationsMore = { label: "Ver todos os destinos", href: "#" },
|
|
11732
|
+
pagesTitle = "P\xE1ginas",
|
|
11733
|
+
pages = DEFAULT_FOOTER_PAGES,
|
|
11734
|
+
cta = {
|
|
11735
|
+
title: "Colaborar?",
|
|
11736
|
+
label: "parceiros@planetaexo.com",
|
|
11737
|
+
href: "mailto:parceiros@planetaexo.com"
|
|
11738
|
+
},
|
|
11739
|
+
copyright,
|
|
11740
|
+
legalLinks = DEFAULT_FOOTER_LEGAL,
|
|
11741
|
+
className
|
|
11742
|
+
}) {
|
|
11743
|
+
const t = VARIANT2[variant];
|
|
11744
|
+
const resolvedLogo = logoSrc != null ? logoSrc : variant === "light" ? logoSrcDark : logoSrcLight;
|
|
11745
|
+
const year = (/* @__PURE__ */ new Date()).getFullYear();
|
|
11746
|
+
const copy = copyright != null ? copyright : `\xA9 ${year} ${brandTitle}. Todos os direitos reservados.`;
|
|
11747
|
+
return /* @__PURE__ */ jsxs("footer", { className: cn(t.footer, className), children: [
|
|
11748
|
+
/* @__PURE__ */ jsx("div", { className: "max-w-7xl mx-auto px-6 sm:px-10 pt-16 pb-10", children: /* @__PURE__ */ jsxs("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-12 gap-x-8 gap-y-12", children: [
|
|
11749
|
+
/* @__PURE__ */ jsxs("div", { className: "lg:col-span-4 space-y-6", children: [
|
|
11750
|
+
/* @__PURE__ */ jsx(
|
|
11751
|
+
"a",
|
|
11752
|
+
{
|
|
11753
|
+
href: logoHref,
|
|
11754
|
+
className: "inline-flex items-center",
|
|
11755
|
+
"aria-label": logoAlt,
|
|
11756
|
+
children: /* @__PURE__ */ jsx(
|
|
11757
|
+
"img",
|
|
11758
|
+
{
|
|
11759
|
+
src: resolvedLogo,
|
|
11760
|
+
alt: logoAlt,
|
|
11761
|
+
className: "h-16 w-auto select-none",
|
|
11762
|
+
draggable: false
|
|
11763
|
+
}
|
|
11764
|
+
)
|
|
11765
|
+
}
|
|
11766
|
+
),
|
|
11767
|
+
brandDescription && /* @__PURE__ */ jsx("p", { className: cn("font-sans text-sm leading-relaxed", t.body), children: brandDescription }),
|
|
11768
|
+
address && /* @__PURE__ */ jsxs("div", { className: "space-y-2", children: [
|
|
11769
|
+
/* @__PURE__ */ jsx("h4", { className: cn("font-heading font-black text-base", t.heading), children: address.title }),
|
|
11770
|
+
/* @__PURE__ */ jsx("address", { className: cn("not-italic text-sm leading-relaxed font-sans", t.body), children: address.lines.map((line, i) => /* @__PURE__ */ jsx("div", { children: line }, i)) })
|
|
11771
|
+
] }),
|
|
11772
|
+
(phone || email) && /* @__PURE__ */ jsxs("div", { className: "space-y-1.5 text-sm font-ui font-bold", children: [
|
|
11773
|
+
phone && /* @__PURE__ */ jsx("div", { children: /* @__PURE__ */ jsx("a", { href: `tel:${phone.replace(/\s+/g, "")}`, className: t.link, children: phone }) }),
|
|
11774
|
+
email && /* @__PURE__ */ jsx("div", { children: /* @__PURE__ */ jsx("a", { href: `mailto:${email}`, className: t.link, children: email }) })
|
|
11775
|
+
] }),
|
|
11776
|
+
socials.length > 0 && /* @__PURE__ */ jsx("div", { className: "flex items-center gap-2", children: socials.map((s) => {
|
|
11777
|
+
var _a;
|
|
11778
|
+
const Icon = SOCIAL_ICON[s.network];
|
|
11779
|
+
const label = (_a = s.label) != null ? _a : SOCIAL_LABEL[s.network];
|
|
11780
|
+
return /* @__PURE__ */ jsx(
|
|
11781
|
+
"a",
|
|
11782
|
+
{
|
|
11783
|
+
href: s.href,
|
|
11784
|
+
"aria-label": label,
|
|
11785
|
+
className: cn(
|
|
11786
|
+
"flex h-9 w-9 items-center justify-center rounded-full transition-colors",
|
|
11787
|
+
t.socialBtn
|
|
11788
|
+
),
|
|
11789
|
+
children: /* @__PURE__ */ jsx(Icon, { className: "h-4 w-4", strokeWidth: 2.25 })
|
|
11790
|
+
},
|
|
11791
|
+
s.network + s.href
|
|
11792
|
+
);
|
|
11793
|
+
}) }),
|
|
11794
|
+
badges && badges.length > 0 && /* @__PURE__ */ jsx("div", { className: "flex flex-wrap items-center gap-5 pt-2", children: badges.map((b, i) => {
|
|
11795
|
+
var _a, _b;
|
|
11796
|
+
const content = (_b = b.node) != null ? _b : /* @__PURE__ */ jsx(
|
|
11797
|
+
"img",
|
|
11798
|
+
{
|
|
11799
|
+
src: b.src,
|
|
11800
|
+
alt: b.alt,
|
|
11801
|
+
style: { height: (_a = b.height) != null ? _a : 56 },
|
|
11802
|
+
className: "block w-auto object-contain",
|
|
11803
|
+
draggable: false
|
|
11804
|
+
}
|
|
11805
|
+
);
|
|
11806
|
+
const wrapper = /* @__PURE__ */ jsx(
|
|
11807
|
+
"span",
|
|
11808
|
+
{
|
|
11809
|
+
className: cn(
|
|
11810
|
+
"inline-flex items-center",
|
|
11811
|
+
t.badgeStroke,
|
|
11812
|
+
t.badgeFilter
|
|
11813
|
+
),
|
|
11814
|
+
children: content
|
|
11815
|
+
}
|
|
11816
|
+
);
|
|
11817
|
+
return b.href ? /* @__PURE__ */ jsx(
|
|
11818
|
+
"a",
|
|
11819
|
+
{
|
|
11820
|
+
href: b.href,
|
|
11821
|
+
"aria-label": b.alt,
|
|
11822
|
+
className: "hover:opacity-80 transition-opacity",
|
|
11823
|
+
children: wrapper
|
|
11824
|
+
},
|
|
11825
|
+
b.alt + i
|
|
11826
|
+
) : /* @__PURE__ */ jsx(React28.Fragment, { children: wrapper }, b.alt + i);
|
|
11827
|
+
}) })
|
|
11828
|
+
] }),
|
|
11829
|
+
themes.length > 0 && /* @__PURE__ */ jsxs("div", { className: "lg:col-span-3", children: [
|
|
11830
|
+
/* @__PURE__ */ jsx(ColumnHeading, { className: t.heading, children: themesTitle }),
|
|
11831
|
+
/* @__PURE__ */ jsx("ul", { className: "space-y-2.5", children: themes.map((c) => /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsx(
|
|
11832
|
+
"a",
|
|
11833
|
+
{
|
|
11834
|
+
href: c.href,
|
|
11835
|
+
className: cn("text-sm font-ui font-bold", t.link),
|
|
11836
|
+
children: c.label
|
|
11837
|
+
}
|
|
11838
|
+
) }, c.label)) })
|
|
11839
|
+
] }),
|
|
11840
|
+
destinations.length > 0 && /* @__PURE__ */ jsxs("div", { className: "lg:col-span-3", children: [
|
|
11841
|
+
/* @__PURE__ */ jsx(ColumnHeading, { className: t.heading, children: destinationsTitle }),
|
|
11842
|
+
/* @__PURE__ */ jsx("ul", { className: "space-y-2.5", children: destinations.map((c) => /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsx(
|
|
11843
|
+
"a",
|
|
11844
|
+
{
|
|
11845
|
+
href: c.href,
|
|
11846
|
+
className: cn("text-sm font-ui font-bold", t.link),
|
|
11847
|
+
children: c.label
|
|
11848
|
+
}
|
|
11849
|
+
) }, c.label)) }),
|
|
11850
|
+
destinationsMore && /* @__PURE__ */ jsxs(
|
|
11851
|
+
"a",
|
|
11852
|
+
{
|
|
11853
|
+
href: destinationsMore.href,
|
|
11854
|
+
className: cn(
|
|
11855
|
+
"inline-flex items-center gap-1.5 mt-5 text-sm font-ui font-bold",
|
|
11856
|
+
t.link
|
|
11857
|
+
),
|
|
11858
|
+
children: [
|
|
11859
|
+
destinationsMore.label,
|
|
11860
|
+
/* @__PURE__ */ jsx(ArrowRightIcon, { className: "h-3.5 w-3.5 no-underline" })
|
|
11861
|
+
]
|
|
11862
|
+
}
|
|
11863
|
+
)
|
|
11864
|
+
] }),
|
|
11865
|
+
/* @__PURE__ */ jsxs("div", { className: "lg:col-span-2 space-y-8", children: [
|
|
11866
|
+
pages.length > 0 && /* @__PURE__ */ jsxs("div", { children: [
|
|
11867
|
+
/* @__PURE__ */ jsx(ColumnHeading, { className: t.heading, children: pagesTitle }),
|
|
11868
|
+
/* @__PURE__ */ jsx("ul", { className: "space-y-2.5", children: pages.map((p) => /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsx(
|
|
11869
|
+
"a",
|
|
11870
|
+
{
|
|
11871
|
+
href: p.href,
|
|
11872
|
+
className: cn("text-sm font-ui font-bold", t.link),
|
|
11873
|
+
children: p.label
|
|
11874
|
+
}
|
|
11875
|
+
) }, p.label)) })
|
|
11876
|
+
] }),
|
|
11877
|
+
cta && /* @__PURE__ */ jsxs("div", { children: [
|
|
11878
|
+
/* @__PURE__ */ jsx(ColumnHeading, { className: t.heading, children: cta.title }),
|
|
11879
|
+
/* @__PURE__ */ jsx(
|
|
11880
|
+
"a",
|
|
11881
|
+
{
|
|
11882
|
+
href: cta.href,
|
|
11883
|
+
className: cn("text-sm font-ui font-bold break-all", t.link),
|
|
11884
|
+
children: cta.label
|
|
11885
|
+
}
|
|
11886
|
+
)
|
|
11887
|
+
] })
|
|
11888
|
+
] })
|
|
11889
|
+
] }) }),
|
|
11890
|
+
/* @__PURE__ */ jsx("div", { className: cn(t.bottomBar), children: /* @__PURE__ */ jsxs("div", { className: "max-w-7xl mx-auto px-6 sm:px-10 py-4 flex flex-wrap items-center gap-x-6 gap-y-3", children: [
|
|
11891
|
+
languages.length > 0 && /* @__PURE__ */ jsx(
|
|
11892
|
+
LanguagePicker,
|
|
11893
|
+
{
|
|
11894
|
+
variant,
|
|
11895
|
+
languages,
|
|
11896
|
+
currentLanguage,
|
|
11897
|
+
onChange: onLanguageChange
|
|
11898
|
+
}
|
|
11899
|
+
),
|
|
11900
|
+
/* @__PURE__ */ jsx("p", { className: cn("text-xs font-ui", t.bottomText), children: copy }),
|
|
11901
|
+
legalLinks.length > 0 && /* @__PURE__ */ jsx("ul", { className: "flex flex-wrap items-center gap-x-6 gap-y-2", children: legalLinks.map((l) => /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsx(
|
|
11902
|
+
"a",
|
|
11903
|
+
{
|
|
11904
|
+
href: l.href,
|
|
11905
|
+
className: cn("text-xs font-ui font-bold", t.bottomLink),
|
|
11906
|
+
children: l.label
|
|
11907
|
+
}
|
|
11908
|
+
) }, l.label)) })
|
|
11909
|
+
] }) })
|
|
11910
|
+
] });
|
|
11911
|
+
}
|
|
10699
11912
|
function Stars({ count = 5 }) {
|
|
10700
11913
|
return /* @__PURE__ */ jsx("span", { className: "flex gap-0.5", children: Array.from({ length: 5 }).map((_, i) => /* @__PURE__ */ jsx(
|
|
10701
11914
|
StarIcon,
|
|
@@ -10739,9 +11952,9 @@ function TripPage({
|
|
|
10739
11952
|
images,
|
|
10740
11953
|
videoUrl,
|
|
10741
11954
|
breadcrumb,
|
|
11955
|
+
chips,
|
|
10742
11956
|
highlights,
|
|
10743
|
-
|
|
10744
|
-
keyInfo,
|
|
11957
|
+
howToGetThere,
|
|
10745
11958
|
recommendedFor,
|
|
10746
11959
|
overview,
|
|
10747
11960
|
overviewHighlights,
|
|
@@ -10759,6 +11972,7 @@ function TripPage({
|
|
|
10759
11972
|
meetingPoints,
|
|
10760
11973
|
meetingPoint,
|
|
10761
11974
|
faqs,
|
|
11975
|
+
faqInitialCount = 5,
|
|
10762
11976
|
sectionIcons,
|
|
10763
11977
|
reviews,
|
|
10764
11978
|
trustpilot,
|
|
@@ -10778,11 +11992,12 @@ function TripPage({
|
|
|
10778
11992
|
features,
|
|
10779
11993
|
className
|
|
10780
11994
|
}) {
|
|
10781
|
-
const [activeSection, setActiveSection] =
|
|
10782
|
-
const [accordionValue, setAccordionValue] =
|
|
10783
|
-
const
|
|
11995
|
+
const [activeSection, setActiveSection] = React28.useState("");
|
|
11996
|
+
const [accordionValue, setAccordionValue] = React28.useState([]);
|
|
11997
|
+
const [faqsExpanded, setFaqsExpanded] = React28.useState(false);
|
|
11998
|
+
const accordionSectionIds = React28.useMemo(
|
|
10784
11999
|
() => /* @__PURE__ */ new Set([
|
|
10785
|
-
"
|
|
12000
|
+
"how-to-get-there",
|
|
10786
12001
|
"what-to-bring",
|
|
10787
12002
|
"weather",
|
|
10788
12003
|
"optional-extras",
|
|
@@ -10793,18 +12008,18 @@ function TripPage({
|
|
|
10793
12008
|
]),
|
|
10794
12009
|
[]
|
|
10795
12010
|
);
|
|
10796
|
-
const [navFloating, setNavFloating] =
|
|
10797
|
-
const [navHidden, setNavHidden] =
|
|
10798
|
-
const [isFloating, setIsFloating] =
|
|
10799
|
-
const [sidebarPos, setSidebarPos] =
|
|
10800
|
-
const [pricingBarVisible, setPricingBarVisible] =
|
|
10801
|
-
const navRef =
|
|
10802
|
-
const navSentinelRef =
|
|
10803
|
-
const sentinelRef =
|
|
10804
|
-
const sidebarPlaceholderRef =
|
|
10805
|
-
const pricingBarRef =
|
|
10806
|
-
const galleryRef =
|
|
10807
|
-
const sections =
|
|
12011
|
+
const [navFloating, setNavFloating] = React28.useState(false);
|
|
12012
|
+
const [navHidden, setNavHidden] = React28.useState(false);
|
|
12013
|
+
const [isFloating, setIsFloating] = React28.useState(false);
|
|
12014
|
+
const [sidebarPos, setSidebarPos] = React28.useState(null);
|
|
12015
|
+
const [pricingBarVisible, setPricingBarVisible] = React28.useState(false);
|
|
12016
|
+
const navRef = React28.useRef(null);
|
|
12017
|
+
const navSentinelRef = React28.useRef(null);
|
|
12018
|
+
const sentinelRef = React28.useRef(null);
|
|
12019
|
+
const sidebarPlaceholderRef = React28.useRef(null);
|
|
12020
|
+
const pricingBarRef = React28.useRef(null);
|
|
12021
|
+
const galleryRef = React28.useRef(null);
|
|
12022
|
+
const sections = React28.useMemo(
|
|
10808
12023
|
() => [
|
|
10809
12024
|
{ id: "overview", label: "Overview", show: !!(overview || (overviewHighlights == null ? void 0 : overviewHighlights.length)) },
|
|
10810
12025
|
{
|
|
@@ -10822,7 +12037,7 @@ function TripPage({
|
|
|
10822
12037
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
10823
12038
|
[]
|
|
10824
12039
|
);
|
|
10825
|
-
|
|
12040
|
+
React28.useEffect(() => {
|
|
10826
12041
|
const sentinel = navSentinelRef.current;
|
|
10827
12042
|
if (!sentinel) return;
|
|
10828
12043
|
const update = () => setNavFloating(sentinel.getBoundingClientRect().top < 1);
|
|
@@ -10830,7 +12045,7 @@ function TripPage({
|
|
|
10830
12045
|
update();
|
|
10831
12046
|
return () => document.removeEventListener("scroll", update, { capture: true });
|
|
10832
12047
|
}, []);
|
|
10833
|
-
|
|
12048
|
+
React28.useEffect(() => {
|
|
10834
12049
|
const sentinel = sentinelRef.current;
|
|
10835
12050
|
if (!sentinel) return;
|
|
10836
12051
|
const update = () => setIsFloating(sentinel.getBoundingClientRect().top < 1);
|
|
@@ -10838,7 +12053,7 @@ function TripPage({
|
|
|
10838
12053
|
update();
|
|
10839
12054
|
return () => document.removeEventListener("scroll", update, { capture: true });
|
|
10840
12055
|
}, []);
|
|
10841
|
-
|
|
12056
|
+
React28.useEffect(() => {
|
|
10842
12057
|
const measure = () => {
|
|
10843
12058
|
if (!sidebarPlaceholderRef.current) return;
|
|
10844
12059
|
const rect = sidebarPlaceholderRef.current.getBoundingClientRect();
|
|
@@ -10848,7 +12063,7 @@ function TripPage({
|
|
|
10848
12063
|
window.addEventListener("resize", measure);
|
|
10849
12064
|
return () => window.removeEventListener("resize", measure);
|
|
10850
12065
|
}, [isFloating]);
|
|
10851
|
-
|
|
12066
|
+
React28.useEffect(() => {
|
|
10852
12067
|
const check = () => {
|
|
10853
12068
|
var _a;
|
|
10854
12069
|
const target = (_a = galleryRef.current) != null ? _a : pricingBarRef.current;
|
|
@@ -10859,7 +12074,7 @@ function TripPage({
|
|
|
10859
12074
|
check();
|
|
10860
12075
|
return () => document.removeEventListener("scroll", check, { capture: true });
|
|
10861
12076
|
}, []);
|
|
10862
|
-
|
|
12077
|
+
React28.useEffect(() => {
|
|
10863
12078
|
const check = () => {
|
|
10864
12079
|
if (!pricingBarRef.current) return;
|
|
10865
12080
|
setNavHidden(pricingBarRef.current.getBoundingClientRect().top < window.innerHeight * 0.92);
|
|
@@ -10868,7 +12083,7 @@ function TripPage({
|
|
|
10868
12083
|
check();
|
|
10869
12084
|
return () => document.removeEventListener("scroll", check, { capture: true });
|
|
10870
12085
|
}, []);
|
|
10871
|
-
|
|
12086
|
+
React28.useEffect(() => {
|
|
10872
12087
|
if (sections.length === 0) return;
|
|
10873
12088
|
setActiveSection(sections[0].id);
|
|
10874
12089
|
const update = () => {
|
|
@@ -10943,6 +12158,7 @@ function TripPage({
|
|
|
10943
12158
|
destination,
|
|
10944
12159
|
duration,
|
|
10945
12160
|
tagline,
|
|
12161
|
+
chips,
|
|
10946
12162
|
siteHeader,
|
|
10947
12163
|
uiVariant,
|
|
10948
12164
|
belowMeta: trustpilotHero ? /* @__PURE__ */ jsx(TrustpilotEmbed, { config: trustpilotHero }) : void 0
|
|
@@ -10976,10 +12192,7 @@ function TripPage({
|
|
|
10976
12192
|
/* @__PURE__ */ jsxs("div", { className: "flex flex-col lg:flex-row gap-8 mt-4", children: [
|
|
10977
12193
|
/* @__PURE__ */ jsxs("div", { className: "flex-1 min-w-0 space-y-12 pb-12", children: [
|
|
10978
12194
|
(overview || (overviewHighlights == null ? void 0 : overviewHighlights.length)) && /* @__PURE__ */ jsxs("section", { id: "trip-section-overview", className: "scroll-mt-20", children: [
|
|
10979
|
-
/* @__PURE__ */
|
|
10980
|
-
(sectionIcons == null ? void 0 : sectionIcons.overview) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.overview }) : /* @__PURE__ */ jsx(InfoIcon, { className: "h-5 w-5 text-primary" }),
|
|
10981
|
-
"Overview"
|
|
10982
|
-
] }),
|
|
12195
|
+
/* @__PURE__ */ jsx("h2", { className: "text-xl font-bold text-foreground font-heading mb-4", children: "Overview" }),
|
|
10983
12196
|
overview && /* @__PURE__ */ jsx("div", { className: "text-lg text-foreground leading-relaxed space-y-3 [&_strong]:font-semibold [&_a]:text-primary [&_a]:underline", children: overview }),
|
|
10984
12197
|
overviewHighlights && overviewHighlights.length > 0 && /* @__PURE__ */ jsx("ul", { className: cn("flex flex-col gap-5", overview && "mt-8"), children: overviewHighlights.map((h, i) => /* @__PURE__ */ jsxs("li", { className: "flex items-start gap-4", children: [
|
|
10985
12198
|
h.icon && /* @__PURE__ */ jsx("span", { className: "flex h-10 w-10 shrink-0 items-center justify-center text-foreground [&_svg]:h-8 [&_svg]:w-8", children: h.icon }),
|
|
@@ -11026,7 +12239,7 @@ function TripPage({
|
|
|
11026
12239
|
}
|
|
11027
12240
|
)
|
|
11028
12241
|
] }),
|
|
11029
|
-
(
|
|
12242
|
+
(howToGetThere || (whatToBring == null ? void 0 : whatToBring.length) || weather || optionalExtras || accommodation || food || (meetingPoints == null ? void 0 : meetingPoints.length) || meetingPoint || termsAndConditions) && /* @__PURE__ */ jsxs(
|
|
11030
12243
|
Accordion,
|
|
11031
12244
|
{
|
|
11032
12245
|
multiple: false,
|
|
@@ -11034,25 +12247,33 @@ function TripPage({
|
|
|
11034
12247
|
onValueChange: setAccordionValue,
|
|
11035
12248
|
className: "border-t border-border",
|
|
11036
12249
|
children: [
|
|
11037
|
-
|
|
12250
|
+
accommodation && /* @__PURE__ */ jsxs(
|
|
12251
|
+
AccordionItem,
|
|
12252
|
+
{
|
|
12253
|
+
value: "accommodation",
|
|
12254
|
+
id: "trip-section-accommodation",
|
|
12255
|
+
className: "scroll-mt-20 border-b border-border",
|
|
12256
|
+
children: [
|
|
12257
|
+
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
12258
|
+
(sectionIcons == null ? void 0 : sectionIcons.accommodation) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.accommodation }) : /* @__PURE__ */ jsx(BedDoubleIcon, { className: "h-5 w-5 text-primary" }),
|
|
12259
|
+
"Accommodation"
|
|
12260
|
+
] }) }),
|
|
12261
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-3 [&_strong]:font-semibold [&_a]:text-primary [&_a]:underline", children: accommodation }) })
|
|
12262
|
+
]
|
|
12263
|
+
}
|
|
12264
|
+
),
|
|
12265
|
+
food && /* @__PURE__ */ jsxs(
|
|
11038
12266
|
AccordionItem,
|
|
11039
12267
|
{
|
|
11040
|
-
value: "
|
|
11041
|
-
id: "trip-section-
|
|
12268
|
+
value: "food",
|
|
12269
|
+
id: "trip-section-food",
|
|
11042
12270
|
className: "scroll-mt-20 border-b border-border",
|
|
11043
12271
|
children: [
|
|
11044
12272
|
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
11045
|
-
(sectionIcons == null ? void 0 : sectionIcons.
|
|
11046
|
-
"
|
|
12273
|
+
(sectionIcons == null ? void 0 : sectionIcons.food) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.food }) : /* @__PURE__ */ jsx(UtensilsIcon, { className: "h-5 w-5 text-primary" }),
|
|
12274
|
+
"Food"
|
|
11047
12275
|
] }) }),
|
|
11048
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children:
|
|
11049
|
-
/* @__PURE__ */ jsxs("div", { className: "flex items-center gap-2 mb-3", children: [
|
|
11050
|
-
group.icon && /* @__PURE__ */ jsx("span", { className: "text-primary", children: group.icon }),
|
|
11051
|
-
/* @__PURE__ */ jsx("h3", { className: "text-base font-bold text-foreground font-heading", children: group.title })
|
|
11052
|
-
] }),
|
|
11053
|
-
/* @__PURE__ */ jsx(Checklist, { items: group.items }),
|
|
11054
|
-
i < infoGroups.length - 1 && /* @__PURE__ */ jsx(Separator, { className: "mt-6" })
|
|
11055
|
-
] }, i)) }) })
|
|
12276
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-3 [&_strong]:font-semibold [&_a]:text-primary [&_a]:underline", children: food }) })
|
|
11056
12277
|
]
|
|
11057
12278
|
}
|
|
11058
12279
|
),
|
|
@@ -11078,78 +12299,63 @@ function TripPage({
|
|
|
11078
12299
|
]
|
|
11079
12300
|
}
|
|
11080
12301
|
),
|
|
11081
|
-
|
|
12302
|
+
howToGetThere && /* @__PURE__ */ jsxs(
|
|
11082
12303
|
AccordionItem,
|
|
11083
12304
|
{
|
|
11084
|
-
value: "
|
|
11085
|
-
id: "trip-section-
|
|
12305
|
+
value: "how-to-get-there",
|
|
12306
|
+
id: "trip-section-how-to-get-there",
|
|
11086
12307
|
className: "scroll-mt-20 border-b border-border",
|
|
11087
12308
|
children: [
|
|
11088
12309
|
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
11089
|
-
(sectionIcons == null ? void 0 : sectionIcons.
|
|
11090
|
-
"
|
|
12310
|
+
(sectionIcons == null ? void 0 : sectionIcons.howToGetThere) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.howToGetThere }) : /* @__PURE__ */ jsx(CompassIcon, { className: "h-5 w-5 text-primary" }),
|
|
12311
|
+
"How to get there"
|
|
11091
12312
|
] }) }),
|
|
11092
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-3 [&_strong]:font-semibold [&_a]:text-primary [&_a]:underline", children:
|
|
12313
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-3 [&_strong]:font-semibold [&_a]:text-primary [&_a]:underline", children: howToGetThere }) })
|
|
11093
12314
|
]
|
|
11094
12315
|
}
|
|
11095
12316
|
),
|
|
11096
|
-
|
|
11097
|
-
AccordionItem,
|
|
11098
|
-
{
|
|
11099
|
-
value: "what-to-bring",
|
|
11100
|
-
id: "trip-section-what-to-bring",
|
|
11101
|
-
className: "scroll-mt-20 border-b border-border",
|
|
11102
|
-
children: [
|
|
11103
|
-
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
11104
|
-
(sectionIcons == null ? void 0 : sectionIcons.whatToBring) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.whatToBring }) : /* @__PURE__ */ jsx(BackpackIcon, { className: "h-5 w-5 text-primary" }),
|
|
11105
|
-
"What to bring"
|
|
11106
|
-
] }) }),
|
|
11107
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx(Checklist, { items: whatToBring, icon: /* @__PURE__ */ jsx(InfoIcon, { className: "h-4 w-4" }) }) })
|
|
11108
|
-
]
|
|
11109
|
-
}
|
|
11110
|
-
),
|
|
11111
|
-
accommodation && /* @__PURE__ */ jsxs(
|
|
12317
|
+
weather && /* @__PURE__ */ jsxs(
|
|
11112
12318
|
AccordionItem,
|
|
11113
12319
|
{
|
|
11114
|
-
value: "
|
|
11115
|
-
id: "trip-section-
|
|
12320
|
+
value: "weather",
|
|
12321
|
+
id: "trip-section-weather",
|
|
11116
12322
|
className: "scroll-mt-20 border-b border-border",
|
|
11117
12323
|
children: [
|
|
11118
12324
|
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
11119
|
-
(sectionIcons == null ? void 0 : sectionIcons.
|
|
11120
|
-
"
|
|
12325
|
+
(sectionIcons == null ? void 0 : sectionIcons.weather) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.weather }) : /* @__PURE__ */ jsx(SunIcon, { className: "h-5 w-5 text-primary" }),
|
|
12326
|
+
"Weather"
|
|
11121
12327
|
] }) }),
|
|
11122
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-
|
|
12328
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "flex items-start gap-3 rounded-xl bg-muted/60 border border-border p-5", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-2 [&_strong]:font-semibold", children: weather }) }) })
|
|
11123
12329
|
]
|
|
11124
12330
|
}
|
|
11125
12331
|
),
|
|
11126
|
-
|
|
12332
|
+
whatToBring && whatToBring.length > 0 && /* @__PURE__ */ jsxs(
|
|
11127
12333
|
AccordionItem,
|
|
11128
12334
|
{
|
|
11129
|
-
value: "
|
|
11130
|
-
id: "trip-section-
|
|
12335
|
+
value: "what-to-bring",
|
|
12336
|
+
id: "trip-section-what-to-bring",
|
|
11131
12337
|
className: "scroll-mt-20 border-b border-border",
|
|
11132
12338
|
children: [
|
|
11133
12339
|
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
11134
|
-
(sectionIcons == null ? void 0 : sectionIcons.
|
|
11135
|
-
"
|
|
12340
|
+
(sectionIcons == null ? void 0 : sectionIcons.whatToBring) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.whatToBring }) : /* @__PURE__ */ jsx(BackpackIcon, { className: "h-5 w-5 text-primary" }),
|
|
12341
|
+
"What to bring"
|
|
11136
12342
|
] }) }),
|
|
11137
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx(
|
|
12343
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx(Checklist, { items: whatToBring, icon: /* @__PURE__ */ jsx(InfoIcon, { className: "h-4 w-4" }) }) })
|
|
11138
12344
|
]
|
|
11139
12345
|
}
|
|
11140
12346
|
),
|
|
11141
|
-
|
|
12347
|
+
optionalExtras && /* @__PURE__ */ jsxs(
|
|
11142
12348
|
AccordionItem,
|
|
11143
12349
|
{
|
|
11144
|
-
value: "
|
|
11145
|
-
id: "trip-section-
|
|
12350
|
+
value: "optional-extras",
|
|
12351
|
+
id: "trip-section-optional-extras",
|
|
11146
12352
|
className: "scroll-mt-20 border-b border-border",
|
|
11147
12353
|
children: [
|
|
11148
12354
|
/* @__PURE__ */ jsx(AccordionTrigger, { className: "py-5 text-xl font-bold text-foreground font-heading hover:no-underline", children: /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-2", children: [
|
|
11149
|
-
(sectionIcons == null ? void 0 : sectionIcons.
|
|
11150
|
-
"
|
|
12355
|
+
(sectionIcons == null ? void 0 : sectionIcons.optionalExtras) ? /* @__PURE__ */ jsx("span", { className: "text-primary [&>svg]:h-5 [&>svg]:w-5", children: sectionIcons.optionalExtras }) : /* @__PURE__ */ jsx(CherryIcon, { className: "h-5 w-5 text-primary" }),
|
|
12356
|
+
"Optional extras"
|
|
11151
12357
|
] }) }),
|
|
11152
|
-
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "
|
|
12358
|
+
/* @__PURE__ */ jsx(AccordionContent, { className: "pb-6", children: /* @__PURE__ */ jsx("div", { className: "text-base text-foreground leading-relaxed space-y-3 [&_strong]:font-semibold [&_a]:text-primary [&_a]:underline", children: optionalExtras }) })
|
|
11153
12359
|
]
|
|
11154
12360
|
}
|
|
11155
12361
|
),
|
|
@@ -11171,13 +12377,39 @@ function TripPage({
|
|
|
11171
12377
|
]
|
|
11172
12378
|
}
|
|
11173
12379
|
),
|
|
11174
|
-
faqs && faqs.length > 0 &&
|
|
11175
|
-
|
|
11176
|
-
|
|
11177
|
-
|
|
11178
|
-
/* @__PURE__ */ jsx(
|
|
11179
|
-
|
|
11180
|
-
|
|
12380
|
+
faqs && faqs.length > 0 && (() => {
|
|
12381
|
+
const visibleFaqs = faqsExpanded ? faqs : faqs.slice(0, faqInitialCount);
|
|
12382
|
+
const hiddenCount = faqs.length - visibleFaqs.length;
|
|
12383
|
+
return /* @__PURE__ */ jsxs("section", { id: "trip-section-faq", className: "scroll-mt-20", children: [
|
|
12384
|
+
/* @__PURE__ */ jsx("h2", { className: "text-xl font-bold text-foreground font-heading mb-6", children: "FAQ" }),
|
|
12385
|
+
/* @__PURE__ */ jsx(Accordion, { variant: "faq", children: visibleFaqs.map((faq, i) => /* @__PURE__ */ jsxs(AccordionItem, { value: `faq-${i}`, children: [
|
|
12386
|
+
/* @__PURE__ */ jsx(AccordionTrigger, { children: faq.question }),
|
|
12387
|
+
/* @__PURE__ */ jsx(AccordionContent, { children: faq.answer })
|
|
12388
|
+
] }, i)) }),
|
|
12389
|
+
faqs.length > faqInitialCount && /* @__PURE__ */ jsx("div", { className: "mt-5 flex justify-center", children: /* @__PURE__ */ jsx(
|
|
12390
|
+
"button",
|
|
12391
|
+
{
|
|
12392
|
+
type: "button",
|
|
12393
|
+
onClick: () => setFaqsExpanded((v) => !v),
|
|
12394
|
+
className: cn(
|
|
12395
|
+
"inline-flex items-center gap-2 rounded-full border border-border bg-background px-5 py-2.5",
|
|
12396
|
+
"text-sm font-semibold text-foreground shadow-sm",
|
|
12397
|
+
"hover:bg-muted transition-colors duration-150",
|
|
12398
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring"
|
|
12399
|
+
),
|
|
12400
|
+
children: faqsExpanded ? /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
12401
|
+
/* @__PURE__ */ jsx(ChevronUpIcon, { className: "h-4 w-4 text-muted-foreground" }),
|
|
12402
|
+
"Show less"
|
|
12403
|
+
] }) : /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
12404
|
+
/* @__PURE__ */ jsx(ChevronDownIcon, { className: "h-4 w-4 text-muted-foreground" }),
|
|
12405
|
+
"See more (",
|
|
12406
|
+
hiddenCount,
|
|
12407
|
+
")"
|
|
12408
|
+
] })
|
|
12409
|
+
}
|
|
12410
|
+
) })
|
|
12411
|
+
] });
|
|
12412
|
+
})(),
|
|
11181
12413
|
trustpilot ? /* @__PURE__ */ jsxs("section", { id: "trip-section-reviews", className: "scroll-mt-20", children: [
|
|
11182
12414
|
/* @__PURE__ */ jsx(Separator, { className: "mb-10" }),
|
|
11183
12415
|
/* @__PURE__ */ jsx("h2", { className: "text-xl font-bold text-foreground font-heading mb-5", children: "What our guests think" }),
|
|
@@ -11266,8 +12498,8 @@ function TripPage({
|
|
|
11266
12498
|
PhotoGallery,
|
|
11267
12499
|
{
|
|
11268
12500
|
photos: gallery,
|
|
11269
|
-
variant: "
|
|
11270
|
-
initialVisible:
|
|
12501
|
+
variant: "gridCompact",
|
|
12502
|
+
initialVisible: 8
|
|
11271
12503
|
}
|
|
11272
12504
|
) }),
|
|
11273
12505
|
gallery && gallery.length > 0 && /* @__PURE__ */ jsx("div", { ref: pricingBarRef, className: "mx-auto w-full max-w-6xl px-6 sm:px-8 py-12", children: /* @__PURE__ */ jsx("div", { id: "trip-booking-form", className: "rounded-2xl border border-border bg-card p-8 shadow-sm", children: /* @__PURE__ */ jsx(BookingForm, { onSubmit: onBook ? (values) => onBook() : void 0 }) }) }),
|
|
@@ -11284,7 +12516,8 @@ function TripPage({
|
|
|
11284
12516
|
currencyEstimates
|
|
11285
12517
|
}
|
|
11286
12518
|
) }),
|
|
11287
|
-
/* @__PURE__ */ jsx("div", { className: "h-20 lg:hidden" })
|
|
12519
|
+
/* @__PURE__ */ jsx("div", { className: "h-20 lg:hidden" }),
|
|
12520
|
+
/* @__PURE__ */ jsx(SiteFooter, {})
|
|
11288
12521
|
]
|
|
11289
12522
|
}
|
|
11290
12523
|
);
|
|
@@ -11390,12 +12623,12 @@ function Toast({
|
|
|
11390
12623
|
duration = 6e3,
|
|
11391
12624
|
className
|
|
11392
12625
|
}) {
|
|
11393
|
-
const [mounted, setMounted] =
|
|
11394
|
-
const [visible, setVisible] =
|
|
11395
|
-
|
|
12626
|
+
const [mounted, setMounted] = React28.useState(false);
|
|
12627
|
+
const [visible, setVisible] = React28.useState(true);
|
|
12628
|
+
React28.useEffect(() => {
|
|
11396
12629
|
setMounted(true);
|
|
11397
12630
|
}, []);
|
|
11398
|
-
|
|
12631
|
+
React28.useEffect(() => {
|
|
11399
12632
|
if (duration === 0) return;
|
|
11400
12633
|
const t = setTimeout(() => {
|
|
11401
12634
|
setVisible(false);
|