@bigz-app/booking-widget 1.2.1 → 1.3.1
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/booking-widget.js +707 -180
- package/dist/booking-widget.js.map +1 -1
- package/dist/components/UniversalBookingWidget.d.ts +52 -2
- package/dist/components/UniversalBookingWidget.d.ts.map +1 -1
- package/dist/components/booking/BookingForm.d.ts +3 -0
- package/dist/components/booking/BookingForm.d.ts.map +1 -1
- package/dist/components/booking/BookingSuccessModal.d.ts.map +1 -1
- package/dist/components/events/EventTypeSelection.d.ts +14 -1
- package/dist/components/events/EventTypeSelection.d.ts.map +1 -1
- package/dist/components/events/SpecialsView.d.ts +13 -0
- package/dist/components/events/SpecialsView.d.ts.map +1 -0
- package/dist/components/events/index.d.ts +1 -0
- package/dist/components/events/index.d.ts.map +1 -1
- package/dist/components/shared/Button.d.ts.map +1 -1
- package/dist/components/shared/DialogPortal.d.ts.map +1 -1
- package/dist/components/upsells/UpsellCard.d.ts +2 -0
- package/dist/components/upsells/UpsellCard.d.ts.map +1 -1
- package/dist/components/upsells/UpsellsStep.d.ts +2 -0
- package/dist/components/upsells/UpsellsStep.d.ts.map +1 -1
- package/dist/i18n/i18n-context.d.ts.map +1 -1
- package/dist/i18n/locales/de.d.ts.map +1 -1
- package/dist/i18n/locales/en.d.ts.map +1 -1
- package/dist/i18n/locales/es.d.ts.map +1 -1
- package/dist/i18n/locales/pt.d.ts.map +1 -1
- package/dist/i18n/locales/sv.d.ts.map +1 -1
- package/dist/index.cjs +707 -180
- package/dist/index.cjs.map +1 -1
- package/dist/index.esm.js +708 -181
- package/dist/index.esm.js.map +1 -1
- package/dist/styles/StyleProvider.d.ts.map +1 -1
- package/dist/styles/shared-styles.d.ts +1 -0
- package/dist/styles/shared-styles.d.ts.map +1 -1
- package/dist/validation/booking-schema.d.ts +54 -13
- package/dist/validation/booking-schema.d.ts.map +1 -1
- package/package.json +1 -1
package/dist/booking-widget.js
CHANGED
|
@@ -291,6 +291,7 @@
|
|
|
291
291
|
"events.soldOut": "Ausgebucht",
|
|
292
292
|
"events.availableFrom": "Freie Plätze ab {{date}}",
|
|
293
293
|
"events.noAvailableDates": "Keine Termine frei",
|
|
294
|
+
"events.previewSectionTitle": "Specials & nächste Termine",
|
|
294
295
|
// Event instances
|
|
295
296
|
"instances.title": "Terminauswahl",
|
|
296
297
|
"instances.noAvailable": "Keine verfügbaren Termine",
|
|
@@ -307,6 +308,15 @@
|
|
|
307
308
|
"nextEvents.noUpcomingMessage": "Aktuell sind keine Termine verfügbar. Bitte schaue später noch einmal vorbei oder kontaktiere uns direkt.",
|
|
308
309
|
"nextEvents.showAll": "Alle Events anzeigen",
|
|
309
310
|
"nextEvents.priceOnRequest": "Preis auf Anfrage",
|
|
311
|
+
// Specials view
|
|
312
|
+
"specials.title": "Sonderangebote",
|
|
313
|
+
"specials.subtitle": "Unsere aktuellen Angebote auf einen Blick",
|
|
314
|
+
"specials.noSpecials": "Keine Sonderangebote",
|
|
315
|
+
"specials.noSpecialsMessage": "Derzeit sind keine Sonderangebote verfügbar. Bitte schaue später noch einmal vorbei.",
|
|
316
|
+
"specials.save": "Spare {{amount}}",
|
|
317
|
+
"specials.savePercent": "{{percent}}% Rabatt",
|
|
318
|
+
"specials.spotsLeft": "Noch {{count}} Plätze frei",
|
|
319
|
+
"specials.bookNow": "Jetzt buchen",
|
|
310
320
|
// Booking form
|
|
311
321
|
"booking.title": "Buchung - {{name}}",
|
|
312
322
|
"booking.notPossible": "Buchung nicht möglich",
|
|
@@ -328,6 +338,8 @@
|
|
|
328
338
|
"booking.participantName": "Name *",
|
|
329
339
|
"booking.participantNamePlaceholder": "Teilnehmername",
|
|
330
340
|
"booking.participantAge": "Alter",
|
|
341
|
+
"booking.participantLevel": "Level",
|
|
342
|
+
"booking.participantLevelPlaceholder": "Level wählen...",
|
|
331
343
|
"booking.addParticipant": "{{number}}. Teilnehmer hinzufügen",
|
|
332
344
|
"booking.maxParticipants": "Maximale Anzahl an Teilnehmern erreicht. Es sind nur noch {{count}} Plätze verfügbar.",
|
|
333
345
|
"booking.maxSpotsReached": "Maximal {{count}} Plätze verfügbar.",
|
|
@@ -476,7 +488,11 @@
|
|
|
476
488
|
"validation.emailInvalid": "Ungültiges E-Mail-Format",
|
|
477
489
|
"validation.emailDomainInvalid": "Ungültige E-Mail-Domain",
|
|
478
490
|
"validation.participantRequired": "Mindestens ein Teilnehmer erforderlich",
|
|
491
|
+
"validation.ageRequired": "Alter ist erforderlich",
|
|
492
|
+
"validation.levelRequired": "Bitte ein Level auswählen",
|
|
479
493
|
"validation.acceptTerms": "Bitte akzeptiere die Allgemeinen Geschäftsbedingungen",
|
|
494
|
+
"level.beginner": "Anfänger",
|
|
495
|
+
"level.advanced": "Fortgeschritten",
|
|
480
496
|
// Sidebar
|
|
481
497
|
"sidebar.close": "Schließen",
|
|
482
498
|
// Promo
|
|
@@ -551,6 +567,7 @@
|
|
|
551
567
|
"events.soldOut": "Sold out",
|
|
552
568
|
"events.availableFrom": "Available from {{date}}",
|
|
553
569
|
"events.noAvailableDates": "No dates available",
|
|
570
|
+
"events.previewSectionTitle": "Specials & upcoming dates",
|
|
554
571
|
// Event instances
|
|
555
572
|
"instances.title": "Select a date",
|
|
556
573
|
"instances.noAvailable": "No available dates",
|
|
@@ -567,6 +584,15 @@
|
|
|
567
584
|
"nextEvents.noUpcomingMessage": "There are currently no dates available. Please check back later or contact us directly.",
|
|
568
585
|
"nextEvents.showAll": "Show all events",
|
|
569
586
|
"nextEvents.priceOnRequest": "Price on request",
|
|
587
|
+
// Specials view
|
|
588
|
+
"specials.title": "Special Offers",
|
|
589
|
+
"specials.subtitle": "Our current deals at a glance",
|
|
590
|
+
"specials.noSpecials": "No special offers",
|
|
591
|
+
"specials.noSpecialsMessage": "There are currently no special offers available. Please check back later.",
|
|
592
|
+
"specials.save": "Save {{amount}}",
|
|
593
|
+
"specials.savePercent": "{{percent}}% off",
|
|
594
|
+
"specials.spotsLeft": "{{count}} spots left",
|
|
595
|
+
"specials.bookNow": "Book now",
|
|
570
596
|
// Booking form
|
|
571
597
|
"booking.title": "Booking - {{name}}",
|
|
572
598
|
"booking.notPossible": "Booking not possible",
|
|
@@ -588,6 +614,8 @@
|
|
|
588
614
|
"booking.participantName": "Name *",
|
|
589
615
|
"booking.participantNamePlaceholder": "Participant name",
|
|
590
616
|
"booking.participantAge": "Age",
|
|
617
|
+
"booking.participantLevel": "Level",
|
|
618
|
+
"booking.participantLevelPlaceholder": "Select level...",
|
|
591
619
|
"booking.addParticipant": "Add participant {{number}}",
|
|
592
620
|
"booking.maxParticipants": "Maximum number of participants reached. Only {{count}} spots are available.",
|
|
593
621
|
"booking.maxSpotsReached": "Maximum {{count}} spots available.",
|
|
@@ -736,7 +764,11 @@
|
|
|
736
764
|
"validation.emailInvalid": "Invalid email format",
|
|
737
765
|
"validation.emailDomainInvalid": "Invalid email domain",
|
|
738
766
|
"validation.participantRequired": "At least one participant is required",
|
|
767
|
+
"validation.ageRequired": "Age is required",
|
|
768
|
+
"validation.levelRequired": "Please select a level",
|
|
739
769
|
"validation.acceptTerms": "Please accept the terms and conditions",
|
|
770
|
+
"level.beginner": "Beginner",
|
|
771
|
+
"level.advanced": "Advanced",
|
|
740
772
|
// Sidebar
|
|
741
773
|
"sidebar.close": "Close",
|
|
742
774
|
// Promo
|
|
@@ -811,6 +843,7 @@
|
|
|
811
843
|
"events.soldOut": "Agotado",
|
|
812
844
|
"events.availableFrom": "Disponible desde {{date}}",
|
|
813
845
|
"events.noAvailableDates": "Sin fechas disponibles",
|
|
846
|
+
"events.previewSectionTitle": "Especiales & próximas fechas",
|
|
814
847
|
// Event instances
|
|
815
848
|
"instances.title": "Seleccionar fecha",
|
|
816
849
|
"instances.noAvailable": "Sin fechas disponibles",
|
|
@@ -827,6 +860,15 @@
|
|
|
827
860
|
"nextEvents.noUpcomingMessage": "Actualmente no hay fechas disponibles. Por favor, vuelve más tarde o contáctanos directamente.",
|
|
828
861
|
"nextEvents.showAll": "Mostrar todos los eventos",
|
|
829
862
|
"nextEvents.priceOnRequest": "Precio bajo consulta",
|
|
863
|
+
// Specials view
|
|
864
|
+
"specials.title": "Ofertas especiales",
|
|
865
|
+
"specials.subtitle": "Nuestras ofertas actuales de un vistazo",
|
|
866
|
+
"specials.noSpecials": "Sin ofertas especiales",
|
|
867
|
+
"specials.noSpecialsMessage": "Actualmente no hay ofertas especiales disponibles. Vuelve más tarde.",
|
|
868
|
+
"specials.save": "Ahorra {{amount}}",
|
|
869
|
+
"specials.savePercent": "{{percent}}% de descuento",
|
|
870
|
+
"specials.spotsLeft": "{{count}} plazas disponibles",
|
|
871
|
+
"specials.bookNow": "Reservar ahora",
|
|
830
872
|
// Booking form
|
|
831
873
|
"booking.title": "Reserva - {{name}}",
|
|
832
874
|
"booking.notPossible": "Reserva no posible",
|
|
@@ -848,6 +890,8 @@
|
|
|
848
890
|
"booking.participantName": "Nombre *",
|
|
849
891
|
"booking.participantNamePlaceholder": "Nombre del participante",
|
|
850
892
|
"booking.participantAge": "Edad",
|
|
893
|
+
"booking.participantLevel": "Nivel",
|
|
894
|
+
"booking.participantLevelPlaceholder": "Seleccionar nivel...",
|
|
851
895
|
"booking.addParticipant": "Añadir participante {{number}}",
|
|
852
896
|
"booking.maxParticipants": "Número máximo de participantes alcanzado. Solo quedan {{count}} plazas disponibles.",
|
|
853
897
|
"booking.maxSpotsReached": "Máximo {{count}} plazas disponibles.",
|
|
@@ -996,7 +1040,11 @@
|
|
|
996
1040
|
"validation.emailInvalid": "Formato de correo electrónico inválido",
|
|
997
1041
|
"validation.emailDomainInvalid": "Dominio de correo electrónico inválido",
|
|
998
1042
|
"validation.participantRequired": "Se requiere al menos un participante",
|
|
1043
|
+
"validation.ageRequired": "La edad es obligatoria",
|
|
1044
|
+
"validation.levelRequired": "Selecciona un nivel",
|
|
999
1045
|
"validation.acceptTerms": "Por favor, acepta los términos y condiciones",
|
|
1046
|
+
"level.beginner": "Principiante",
|
|
1047
|
+
"level.advanced": "Avanzado",
|
|
1000
1048
|
// Sidebar
|
|
1001
1049
|
"sidebar.close": "Cerrar",
|
|
1002
1050
|
// Promo
|
|
@@ -1071,6 +1119,7 @@
|
|
|
1071
1119
|
"events.soldOut": "Esgotado",
|
|
1072
1120
|
"events.availableFrom": "Disponível a partir de {{date}}",
|
|
1073
1121
|
"events.noAvailableDates": "Sem datas disponíveis",
|
|
1122
|
+
"events.previewSectionTitle": "Especiais & próximas datas",
|
|
1074
1123
|
// Event instances
|
|
1075
1124
|
"instances.title": "Selecionar data",
|
|
1076
1125
|
"instances.noAvailable": "Sem datas disponíveis",
|
|
@@ -1087,6 +1136,15 @@
|
|
|
1087
1136
|
"nextEvents.noUpcomingMessage": "Atualmente não há datas disponíveis. Por favor, volte mais tarde ou contacte-nos diretamente.",
|
|
1088
1137
|
"nextEvents.showAll": "Mostrar todos os eventos",
|
|
1089
1138
|
"nextEvents.priceOnRequest": "Preço sob consulta",
|
|
1139
|
+
// Specials view
|
|
1140
|
+
"specials.title": "Ofertas especiais",
|
|
1141
|
+
"specials.subtitle": "As nossas ofertas atuais num relance",
|
|
1142
|
+
"specials.noSpecials": "Sem ofertas especiais",
|
|
1143
|
+
"specials.noSpecialsMessage": "Atualmente não há ofertas especiais disponíveis. Por favor, volte mais tarde.",
|
|
1144
|
+
"specials.save": "Poupe {{amount}}",
|
|
1145
|
+
"specials.savePercent": "{{percent}}% de desconto",
|
|
1146
|
+
"specials.spotsLeft": "{{count}} lugares disponíveis",
|
|
1147
|
+
"specials.bookNow": "Reservar agora",
|
|
1090
1148
|
// Booking form
|
|
1091
1149
|
"booking.title": "Reserva - {{name}}",
|
|
1092
1150
|
"booking.notPossible": "Reserva não possível",
|
|
@@ -1108,6 +1166,8 @@
|
|
|
1108
1166
|
"booking.participantName": "Nome *",
|
|
1109
1167
|
"booking.participantNamePlaceholder": "Nome do participante",
|
|
1110
1168
|
"booking.participantAge": "Idade",
|
|
1169
|
+
"booking.participantLevel": "Nível",
|
|
1170
|
+
"booking.participantLevelPlaceholder": "Selecionar nível...",
|
|
1111
1171
|
"booking.addParticipant": "Adicionar participante {{number}}",
|
|
1112
1172
|
"booking.maxParticipants": "Número máximo de participantes atingido. Apenas {{count}} lugares disponíveis.",
|
|
1113
1173
|
"booking.maxSpotsReached": "Máximo {{count}} lugares disponíveis.",
|
|
@@ -1256,7 +1316,11 @@
|
|
|
1256
1316
|
"validation.emailInvalid": "Formato de email inválido",
|
|
1257
1317
|
"validation.emailDomainInvalid": "Domínio de email inválido",
|
|
1258
1318
|
"validation.participantRequired": "É necessário pelo menos um participante",
|
|
1319
|
+
"validation.ageRequired": "A idade é obrigatória",
|
|
1320
|
+
"validation.levelRequired": "Por favor selecione um nível",
|
|
1259
1321
|
"validation.acceptTerms": "Por favor, aceite os termos e condições",
|
|
1322
|
+
"level.beginner": "Iniciante",
|
|
1323
|
+
"level.advanced": "Avançado",
|
|
1260
1324
|
// Sidebar
|
|
1261
1325
|
"sidebar.close": "Fechar",
|
|
1262
1326
|
// Promo
|
|
@@ -1331,6 +1395,7 @@
|
|
|
1331
1395
|
"events.soldOut": "Fullbokat",
|
|
1332
1396
|
"events.availableFrom": "Lediga platser från {{date}}",
|
|
1333
1397
|
"events.noAvailableDates": "Inga datum lediga",
|
|
1398
|
+
"events.previewSectionTitle": "Specials & kommande datum",
|
|
1334
1399
|
// Event instances
|
|
1335
1400
|
"instances.title": "Välj datum",
|
|
1336
1401
|
"instances.noAvailable": "Inga tillgängliga datum",
|
|
@@ -1347,6 +1412,15 @@
|
|
|
1347
1412
|
"nextEvents.noUpcomingMessage": "Det finns för närvarande inga datum tillgängliga. Kom tillbaka senare eller kontakta oss direkt.",
|
|
1348
1413
|
"nextEvents.showAll": "Visa alla evenemang",
|
|
1349
1414
|
"nextEvents.priceOnRequest": "Pris på förfrågan",
|
|
1415
|
+
// Specials view
|
|
1416
|
+
"specials.title": "Specialerbjudanden",
|
|
1417
|
+
"specials.subtitle": "Våra aktuella erbjudanden i korthet",
|
|
1418
|
+
"specials.noSpecials": "Inga specialerbjudanden",
|
|
1419
|
+
"specials.noSpecialsMessage": "Det finns för närvarande inga specialerbjudanden tillgängliga. Kom tillbaka senare.",
|
|
1420
|
+
"specials.save": "Spara {{amount}}",
|
|
1421
|
+
"specials.savePercent": "{{percent}}% rabatt",
|
|
1422
|
+
"specials.spotsLeft": "{{count}} platser kvar",
|
|
1423
|
+
"specials.bookNow": "Boka nu",
|
|
1350
1424
|
// Booking form
|
|
1351
1425
|
"booking.title": "Bokning - {{name}}",
|
|
1352
1426
|
"booking.notPossible": "Bokning inte möjlig",
|
|
@@ -1368,6 +1442,8 @@
|
|
|
1368
1442
|
"booking.participantName": "Namn *",
|
|
1369
1443
|
"booking.participantNamePlaceholder": "Deltagarens namn",
|
|
1370
1444
|
"booking.participantAge": "Ålder",
|
|
1445
|
+
"booking.participantLevel": "Nivå",
|
|
1446
|
+
"booking.participantLevelPlaceholder": "Välj nivå...",
|
|
1371
1447
|
"booking.addParticipant": "Lägg till deltagare {{number}}",
|
|
1372
1448
|
"booking.maxParticipants": "Maximalt antal deltagare uppnått. Bara {{count}} platser är tillgängliga.",
|
|
1373
1449
|
"booking.maxSpotsReached": "Maximalt {{count}} platser tillgängliga.",
|
|
@@ -1516,7 +1592,11 @@
|
|
|
1516
1592
|
"validation.emailInvalid": "Ogiltigt e-postformat",
|
|
1517
1593
|
"validation.emailDomainInvalid": "Ogiltig e-postdomän",
|
|
1518
1594
|
"validation.participantRequired": "Minst en deltagare krävs",
|
|
1595
|
+
"validation.ageRequired": "Ålder krävs",
|
|
1596
|
+
"validation.levelRequired": "Välj en nivå",
|
|
1519
1597
|
"validation.acceptTerms": "Acceptera villkoren",
|
|
1598
|
+
"level.beginner": "Nybörjare",
|
|
1599
|
+
"level.advanced": "Avancerad",
|
|
1520
1600
|
// Sidebar
|
|
1521
1601
|
"sidebar.close": "Stäng",
|
|
1522
1602
|
// Promo
|
|
@@ -1609,18 +1689,9 @@
|
|
|
1609
1689
|
}
|
|
1610
1690
|
const I18nContext = R$2(null);
|
|
1611
1691
|
function I18nProvider({ configLocale, children }) {
|
|
1612
|
-
// Priority:
|
|
1613
|
-
//
|
|
1614
|
-
const [overrideLocale, setOverrideLocale] = d$1(() =>
|
|
1615
|
-
if (configLocale)
|
|
1616
|
-
return null;
|
|
1617
|
-
return readPersistedLocale();
|
|
1618
|
-
});
|
|
1619
|
-
y$1(() => {
|
|
1620
|
-
if (configLocale) {
|
|
1621
|
-
setOverrideLocale(null);
|
|
1622
|
-
}
|
|
1623
|
-
}, [configLocale]);
|
|
1692
|
+
// Priority: persisted user choice > configLocale (org default) > browser language > "de"
|
|
1693
|
+
// This keeps org locale as default, but remembers explicit user overrides across reloads.
|
|
1694
|
+
const [overrideLocale, setOverrideLocale] = d$1(() => readPersistedLocale());
|
|
1624
1695
|
const locale = overrideLocale ?? resolveLocale(configLocale);
|
|
1625
1696
|
const handleSetLocale = q$2((next) => {
|
|
1626
1697
|
persistLocale(next);
|
|
@@ -1752,129 +1823,153 @@
|
|
|
1752
1823
|
// If semantic resolution fails, use fallback or return the original value
|
|
1753
1824
|
return fallbackValue || colorValue;
|
|
1754
1825
|
};
|
|
1755
|
-
//
|
|
1826
|
+
// Legacy theme name redirects (old name → new name)
|
|
1827
|
+
const legacyThemeRedirects = {
|
|
1828
|
+
"light-fresh": "teal-minimal",
|
|
1829
|
+
"light-elegant": "blue-business",
|
|
1830
|
+
"light-vibrant": "orange-raw",
|
|
1831
|
+
"light-professional": "blue-business",
|
|
1832
|
+
"dark-night": "navy-night",
|
|
1833
|
+
"dark-modern": "navy-night",
|
|
1834
|
+
"dark-forest": "green-deep",
|
|
1835
|
+
};
|
|
1836
|
+
// Predefined themes
|
|
1756
1837
|
const themes = {
|
|
1757
1838
|
// --- Light Themes ---
|
|
1758
|
-
"
|
|
1759
|
-
highlight: "#00b1aa",
|
|
1760
|
-
background: "#f8fdfe",
|
|
1761
|
-
surface: "#ffffff",
|
|
1762
|
-
text: "#0e7490",
|
|
1763
|
-
border: "#bae6fd",
|
|
1764
|
-
success: "#38bdf8",
|
|
1765
|
-
warning: "#fbbf24",
|
|
1766
|
-
error: "#f43f5e",
|
|
1767
|
-
borderRadius: "18px",
|
|
1839
|
+
"teal-minimal": {
|
|
1840
|
+
highlight: "#00b1aa",
|
|
1841
|
+
background: "#f8fdfe",
|
|
1842
|
+
surface: "#ffffff",
|
|
1843
|
+
text: "#0e7490",
|
|
1844
|
+
border: "#bae6fd",
|
|
1845
|
+
success: "#38bdf8",
|
|
1846
|
+
warning: "#fbbf24",
|
|
1847
|
+
error: "#f43f5e",
|
|
1848
|
+
borderRadius: "18px",
|
|
1768
1849
|
fontFamily: "'Inter', system-ui, sans-serif",
|
|
1769
1850
|
},
|
|
1770
|
-
"
|
|
1771
|
-
highlight: "#
|
|
1772
|
-
background: "#
|
|
1773
|
-
surface: "#ffffff",
|
|
1774
|
-
text: "#
|
|
1775
|
-
border: "#
|
|
1776
|
-
success: "#
|
|
1777
|
-
warning: "#
|
|
1778
|
-
error: "#
|
|
1779
|
-
borderRadius: "
|
|
1780
|
-
fontFamily: "'
|
|
1851
|
+
"blue-business": {
|
|
1852
|
+
highlight: "#2563eb",
|
|
1853
|
+
background: "#f8fafc",
|
|
1854
|
+
surface: "#ffffff",
|
|
1855
|
+
text: "#0f172a",
|
|
1856
|
+
border: "#cbd5e1",
|
|
1857
|
+
success: "#059669",
|
|
1858
|
+
warning: "#d97706",
|
|
1859
|
+
error: "#b91c1c",
|
|
1860
|
+
borderRadius: "6px",
|
|
1861
|
+
fontFamily: "'Plus Jakarta Sans', system-ui, sans-serif",
|
|
1781
1862
|
},
|
|
1782
|
-
"
|
|
1783
|
-
highlight: "#ed702d",
|
|
1784
|
-
background: "#1f2630",
|
|
1785
|
-
surface: "#1f2630",
|
|
1786
|
-
text: "#f1f5f9",
|
|
1787
|
-
border: "#ed702d",
|
|
1788
|
-
success: "#22c55e",
|
|
1789
|
-
warning: "#eab308",
|
|
1790
|
-
error: "#ef4444",
|
|
1863
|
+
"orange-raw": {
|
|
1864
|
+
highlight: "#ed702d",
|
|
1865
|
+
background: "#1f2630",
|
|
1866
|
+
surface: "#1f2630",
|
|
1867
|
+
text: "#f1f5f9",
|
|
1868
|
+
border: "#ed702d",
|
|
1869
|
+
success: "#22c55e",
|
|
1870
|
+
warning: "#eab308",
|
|
1871
|
+
error: "#ef4444",
|
|
1791
1872
|
borderRadius: "0px",
|
|
1792
1873
|
fontFamily: "Inter, system-ui, sans-serif",
|
|
1793
1874
|
},
|
|
1794
|
-
|
|
1795
|
-
|
|
1796
|
-
|
|
1797
|
-
|
|
1798
|
-
|
|
1799
|
-
|
|
1800
|
-
|
|
1801
|
-
|
|
1802
|
-
|
|
1803
|
-
|
|
1804
|
-
|
|
1875
|
+
// --- Dark Themes ---
|
|
1876
|
+
"navy-night": {
|
|
1877
|
+
highlight: "#60a5fa",
|
|
1878
|
+
background: "#0b1120",
|
|
1879
|
+
surface: "#111827",
|
|
1880
|
+
text: "#e2e8f0",
|
|
1881
|
+
border: "#1e3a5f",
|
|
1882
|
+
success: "#34d399",
|
|
1883
|
+
warning: "#fbbf24",
|
|
1884
|
+
error: "#f87171",
|
|
1885
|
+
borderRadius: "10px",
|
|
1886
|
+
fontFamily: "'Outfit', system-ui, sans-serif",
|
|
1805
1887
|
},
|
|
1806
|
-
"
|
|
1807
|
-
highlight: "#
|
|
1808
|
-
background: "#
|
|
1809
|
-
surface: "#
|
|
1810
|
-
text: "#
|
|
1811
|
-
border: "#
|
|
1812
|
-
success: "#
|
|
1813
|
-
warning: "#
|
|
1814
|
-
error: "#
|
|
1815
|
-
borderRadius: "8px",
|
|
1816
|
-
fontFamily: "Inter, system-ui, sans-serif",
|
|
1817
|
-
},
|
|
1818
|
-
"dark-modern": {
|
|
1819
|
-
highlight: "#3b82f6", // blue-500 - bright blue accent
|
|
1820
|
-
background: "#0f172a", // slate-900 - dark background
|
|
1821
|
-
surface: "#1e293b", // slate-800 - dark cards
|
|
1822
|
-
text: "#f1f5f9", // slate-100 - light text
|
|
1823
|
-
border: "#334155", // slate-700 - subtle borders
|
|
1824
|
-
success: "#22c55e", // green-500
|
|
1825
|
-
warning: "#eab308", // yellow-500
|
|
1826
|
-
error: "#ef4444", // red-500
|
|
1827
|
-
borderRadius: "8px",
|
|
1828
|
-
fontFamily: "Inter, system-ui, sans-serif",
|
|
1829
|
-
},
|
|
1830
|
-
"dark-forest": {
|
|
1831
|
-
highlight: "#34d399", // Emerald 400
|
|
1832
|
-
background: "#05140d",
|
|
1833
|
-
surface: "#062215",
|
|
1834
|
-
text: "#d1fae5", // Emerald 100
|
|
1835
|
-
border: "#043322",
|
|
1836
|
-
success: "#4ade80", // Green 400
|
|
1837
|
-
warning: "#facc15", // Yellow 400
|
|
1838
|
-
error: "#f87171", // Red 400
|
|
1888
|
+
"green-deep": {
|
|
1889
|
+
highlight: "#34d399",
|
|
1890
|
+
background: "#030d07",
|
|
1891
|
+
surface: "#051a0e",
|
|
1892
|
+
text: "#d1fae5",
|
|
1893
|
+
border: "#064e20",
|
|
1894
|
+
success: "#4ade80",
|
|
1895
|
+
warning: "#facc15",
|
|
1896
|
+
error: "#f87171",
|
|
1839
1897
|
borderRadius: "12px",
|
|
1840
|
-
fontFamily: "system-ui,
|
|
1898
|
+
fontFamily: "'Instrument Sans', system-ui, sans-serif",
|
|
1841
1899
|
},
|
|
1842
|
-
"
|
|
1843
|
-
highlight: "#
|
|
1900
|
+
"green-matrix": {
|
|
1901
|
+
highlight: "#39ff14",
|
|
1844
1902
|
background: "#000000",
|
|
1845
|
-
surface: "#
|
|
1846
|
-
text: "#
|
|
1847
|
-
border: "#
|
|
1848
|
-
success: "#
|
|
1903
|
+
surface: "#060f06",
|
|
1904
|
+
text: "#00ff41",
|
|
1905
|
+
border: "#0d2b0d",
|
|
1906
|
+
success: "#39ff14",
|
|
1849
1907
|
warning: "#ffff00",
|
|
1850
1908
|
error: "#ff3333",
|
|
1851
1909
|
borderRadius: "0px",
|
|
1852
|
-
fontFamily: "'
|
|
1910
|
+
fontFamily: "'Share Tech Mono', monospace",
|
|
1853
1911
|
},
|
|
1854
|
-
"
|
|
1855
|
-
highlight: "#fde047",
|
|
1856
|
-
background: "#1c1917",
|
|
1857
|
-
surface: "#292524",
|
|
1858
|
-
text: "#fafaf9",
|
|
1859
|
-
border: "#44403c",
|
|
1860
|
-
success: "#a3e635",
|
|
1861
|
-
warning: "#f59e0b",
|
|
1862
|
-
error: "#fca5a5",
|
|
1912
|
+
"gold-luxury": {
|
|
1913
|
+
highlight: "#fde047",
|
|
1914
|
+
background: "#1c1917",
|
|
1915
|
+
surface: "#292524",
|
|
1916
|
+
text: "#fafaf9",
|
|
1917
|
+
border: "#44403c",
|
|
1918
|
+
success: "#a3e635",
|
|
1919
|
+
warning: "#f59e0b",
|
|
1920
|
+
error: "#fca5a5",
|
|
1863
1921
|
borderRadius: "24px",
|
|
1864
|
-
fontFamily: "'
|
|
1922
|
+
fontFamily: "'Bodoni Moda', serif",
|
|
1865
1923
|
},
|
|
1866
|
-
"
|
|
1867
|
-
highlight: "#d946ef",
|
|
1868
|
-
background: "#
|
|
1869
|
-
surface: "#
|
|
1870
|
-
text: "#f3e8ff",
|
|
1871
|
-
border: "#
|
|
1872
|
-
success: "#4ade80",
|
|
1873
|
-
warning: "#facc15",
|
|
1874
|
-
error: "#f87171",
|
|
1924
|
+
"purple-electric": {
|
|
1925
|
+
highlight: "#d946ef",
|
|
1926
|
+
background: "#110820",
|
|
1927
|
+
surface: "#1a0d30",
|
|
1928
|
+
text: "#f3e8ff",
|
|
1929
|
+
border: "#3b0764",
|
|
1930
|
+
success: "#4ade80",
|
|
1931
|
+
warning: "#facc15",
|
|
1932
|
+
error: "#f87171",
|
|
1875
1933
|
borderRadius: "14px",
|
|
1876
1934
|
fontFamily: "'Geologica', sans-serif",
|
|
1877
1935
|
},
|
|
1936
|
+
"dark-neon-brutalism": {
|
|
1937
|
+
highlight: "#00e5cc",
|
|
1938
|
+
background: "#0e1420",
|
|
1939
|
+
surface: "#0e1420",
|
|
1940
|
+
text: "#e8eef5",
|
|
1941
|
+
border: "#00e5cc",
|
|
1942
|
+
success: "#00e5cc",
|
|
1943
|
+
warning: "#ffe45e",
|
|
1944
|
+
error: "#ff4d6d",
|
|
1945
|
+
borderRadius: "4px",
|
|
1946
|
+
fontFamily: "'JetBrains Mono', monospace",
|
|
1947
|
+
buttonTextColor: "#0e1420",
|
|
1948
|
+
},
|
|
1949
|
+
"rose-editorial": {
|
|
1950
|
+
highlight: "#be3455",
|
|
1951
|
+
background: "#fdf8f5",
|
|
1952
|
+
surface: "#ffffff",
|
|
1953
|
+
text: "#1a0a0f",
|
|
1954
|
+
border: "#f2d5db",
|
|
1955
|
+
success: "#2d6a4f",
|
|
1956
|
+
warning: "#b5451b",
|
|
1957
|
+
error: "#9b1d20",
|
|
1958
|
+
borderRadius: "0px",
|
|
1959
|
+
fontFamily: "'Cormorant', serif",
|
|
1960
|
+
},
|
|
1961
|
+
"amber-retro": {
|
|
1962
|
+
highlight: "#f59e0b",
|
|
1963
|
+
background: "#1a1008",
|
|
1964
|
+
surface: "#241a0a",
|
|
1965
|
+
text: "#fef3c7",
|
|
1966
|
+
border: "#78350f",
|
|
1967
|
+
success: "#84cc16",
|
|
1968
|
+
warning: "#f59e0b",
|
|
1969
|
+
error: "#ef4444",
|
|
1970
|
+
borderRadius: "6px",
|
|
1971
|
+
fontFamily: "'Syne', sans-serif",
|
|
1972
|
+
},
|
|
1878
1973
|
};
|
|
1879
1974
|
const StyleProvider = ({ config, children, }) => {
|
|
1880
1975
|
// Track hydration state to prevent mismatches
|
|
@@ -1884,8 +1979,10 @@
|
|
|
1884
1979
|
}, []);
|
|
1885
1980
|
// PERFORMANCE OPTIMIZATION: Memoize style calculations
|
|
1886
1981
|
const themedStyles = T$2(() => {
|
|
1887
|
-
const
|
|
1888
|
-
|
|
1982
|
+
const rawThemeName = config.theme || "teal-minimal";
|
|
1983
|
+
// Redirect legacy theme names to new names
|
|
1984
|
+
const themeName = legacyThemeRedirects[rawThemeName] || rawThemeName;
|
|
1985
|
+
const themeDefaults = themes[themeName] || themes["teal-minimal"];
|
|
1889
1986
|
const getCSSValue = (value, fallback) => {
|
|
1890
1987
|
if (!value)
|
|
1891
1988
|
return fallback;
|
|
@@ -1955,6 +2052,7 @@
|
|
|
1955
2052
|
"--bw-surface-color": finalColors.surface,
|
|
1956
2053
|
"--bw-text-color": finalColors.text,
|
|
1957
2054
|
"--bw-text-muted": addOpacity(finalColors.text, 0.7),
|
|
2055
|
+
"--bw-button-text-color": themeDefaults.buttonTextColor || "#ffffff",
|
|
1958
2056
|
"--bw-border-color": finalColors.border,
|
|
1959
2057
|
"--bw-success-color": finalColors.success,
|
|
1960
2058
|
"--bw-warning-color": finalColors.warning,
|
|
@@ -1972,7 +2070,7 @@
|
|
|
1972
2070
|
"--bw-highlight-muted": addOpacity(finalColors.highlight, 0.1),
|
|
1973
2071
|
"--bw-highlight-subtle": addOpacity(finalColors.highlight, 0.05),
|
|
1974
2072
|
"--bw-text-subtle": addOpacity(finalColors.text, 0.4),
|
|
1975
|
-
colorScheme:
|
|
2073
|
+
colorScheme: (["navy-night", "green-deep", "green-matrix", "gold-luxury", "purple-electric", "dark-neon-brutalism", "amber-retro", "orange-raw"].includes(themeName) || themeName.startsWith("dark-")) ? "dark" : "light",
|
|
1976
2074
|
};
|
|
1977
2075
|
}, [
|
|
1978
2076
|
config.theme,
|
|
@@ -4526,6 +4624,7 @@
|
|
|
4526
4624
|
"--bw-font-family": computedStyles.getPropertyValue("--bw-font-family").trim() || "system-ui, sans-serif",
|
|
4527
4625
|
"--bw-shadow-md": computedStyles.getPropertyValue("--bw-shadow-md").trim() ||
|
|
4528
4626
|
"0 4px 6px -1px rgba(0, 0, 0, 0.1)",
|
|
4627
|
+
"--bw-button-text-color": computedStyles.getPropertyValue("--bw-button-text-color").trim() || "#ffffff",
|
|
4529
4628
|
};
|
|
4530
4629
|
setFallbackStyles(fallbacks);
|
|
4531
4630
|
}
|
|
@@ -11243,16 +11342,37 @@
|
|
|
11243
11342
|
ZodUnion.create;
|
|
11244
11343
|
ZodIntersection.create;
|
|
11245
11344
|
ZodTuple.create;
|
|
11246
|
-
ZodEnum.create;
|
|
11345
|
+
const enumType = ZodEnum.create;
|
|
11247
11346
|
ZodPromise.create;
|
|
11248
11347
|
ZodOptional.create;
|
|
11249
11348
|
ZodNullable.create;
|
|
11349
|
+
const preprocessType = ZodEffects.createWithPreprocess;
|
|
11250
11350
|
|
|
11251
|
-
const
|
|
11252
|
-
name:
|
|
11351
|
+
const DEFAULT_PARTICIPANT_FIELDS_CONFIG = {
|
|
11352
|
+
name: { enabled: true, required: true },
|
|
11353
|
+
age: { enabled: true, required: false },
|
|
11354
|
+
level: { enabled: false, required: false },
|
|
11355
|
+
};
|
|
11356
|
+
const participantSchema = (t, fieldsConfig) => objectType({
|
|
11357
|
+
name: stringType().trim().optional(),
|
|
11253
11358
|
age: numberType().min(0).max(120).optional(),
|
|
11359
|
+
level: preprocessType((value) => (value === "" ? undefined : value), enumType(["beginner", "advanced"]).optional()),
|
|
11360
|
+
})
|
|
11361
|
+
.superRefine((value, ctx) => {
|
|
11362
|
+
if (fieldsConfig.name.required && (!value.name || value.name.trim().length < 1)) {
|
|
11363
|
+
ctx.addIssue({ code: ZodIssueCode.custom, message: t("validation.nameRequired"), path: ["name"] });
|
|
11364
|
+
}
|
|
11365
|
+
if (!fieldsConfig.name.enabled && value.name && value.name.trim().length > 0) {
|
|
11366
|
+
ctx.addIssue({ code: ZodIssueCode.custom, message: t("validation.nameRequired"), path: ["name"] });
|
|
11367
|
+
}
|
|
11368
|
+
if (fieldsConfig.age.required && typeof value.age !== "number") {
|
|
11369
|
+
ctx.addIssue({ code: ZodIssueCode.custom, message: t("validation.ageRequired"), path: ["age"] });
|
|
11370
|
+
}
|
|
11371
|
+
if (fieldsConfig.level.required && !value.level) {
|
|
11372
|
+
ctx.addIssue({ code: ZodIssueCode.custom, message: t("validation.levelRequired"), path: ["level"] });
|
|
11373
|
+
}
|
|
11254
11374
|
});
|
|
11255
|
-
function createBookingFormSchema(t) {
|
|
11375
|
+
function createBookingFormSchema(t, fieldsConfig = DEFAULT_PARTICIPANT_FIELDS_CONFIG) {
|
|
11256
11376
|
const tr = t ?? ((key) => key);
|
|
11257
11377
|
return objectType({
|
|
11258
11378
|
customerName: stringType().trim().min(2, tr("validation.nameMinLength")),
|
|
@@ -11262,7 +11382,7 @@
|
|
|
11262
11382
|
.email(tr("validation.emailInvalid"))
|
|
11263
11383
|
.regex(/\.[a-zA-Z]{2,}$/, tr("validation.emailDomainInvalid")),
|
|
11264
11384
|
customerPhone: stringType().trim().optional(),
|
|
11265
|
-
participants: arrayType(participantSchema(tr)).min(1, tr("validation.participantRequired")),
|
|
11385
|
+
participants: arrayType(participantSchema(tr, fieldsConfig)).min(1, tr("validation.participantRequired")),
|
|
11266
11386
|
discountCode: stringType().trim().optional(),
|
|
11267
11387
|
comment: stringType().trim().optional(),
|
|
11268
11388
|
acceptTerms: booleanType().refine((val) => val === true, {
|
|
@@ -11303,11 +11423,13 @@
|
|
|
11303
11423
|
whiteSpace: "nowrap",
|
|
11304
11424
|
border: "none",
|
|
11305
11425
|
};
|
|
11426
|
+
// CSS class name for button hover effects
|
|
11427
|
+
const buttonClassName = "bw-button-hover";
|
|
11306
11428
|
const buttonStyles = {
|
|
11307
11429
|
primary: {
|
|
11308
11430
|
...buttonBase,
|
|
11309
11431
|
backgroundColor: "var(--bw-highlight-color)",
|
|
11310
|
-
color: "#ffffff",
|
|
11432
|
+
color: "var(--bw-button-text-color, #ffffff)",
|
|
11311
11433
|
border: "none",
|
|
11312
11434
|
},
|
|
11313
11435
|
secondary: {
|
|
@@ -11403,7 +11525,8 @@
|
|
|
11403
11525
|
gap: "8px",
|
|
11404
11526
|
marginTop: "10px",
|
|
11405
11527
|
paddingTop: "10px",
|
|
11406
|
-
|
|
11528
|
+
paddingBottom: "25px",
|
|
11529
|
+
borderBottom: "1px dashed var(--bw-border-color)",
|
|
11407
11530
|
},
|
|
11408
11531
|
label: {
|
|
11409
11532
|
display: "inline-flex",
|
|
@@ -11461,6 +11584,8 @@
|
|
|
11461
11584
|
const { locale } = useLocale();
|
|
11462
11585
|
const timezone = useTimezone();
|
|
11463
11586
|
const roundEnabled = systemConfig?.roundPricesEnabled !== false;
|
|
11587
|
+
const participantFieldsConfig = eventDetails.participantFieldsConfig ?? DEFAULT_PARTICIPANT_FIELDS_CONFIG;
|
|
11588
|
+
const participantLevelOptions = eventDetails.participantLevelOptions ?? ["beginner", "advanced"];
|
|
11464
11589
|
const roundDiscountUp = (minorUnits) => Math.ceil(minorUnits / 100) * 100;
|
|
11465
11590
|
const calcPercentDiscountAmount = (baseAmount, basisPoints, round) => {
|
|
11466
11591
|
const raw = Math.round((baseAmount * basisPoints) / 10000);
|
|
@@ -11473,18 +11598,19 @@
|
|
|
11473
11598
|
// Per-participant upsell selections: participantIndex -> array of upsell package IDs
|
|
11474
11599
|
const [participantUpsells, setParticipantUpsells] = d$1({});
|
|
11475
11600
|
const form = useForm({
|
|
11476
|
-
resolver: t(createBookingFormSchema(t$1)),
|
|
11601
|
+
resolver: t(createBookingFormSchema(t$1, participantFieldsConfig)),
|
|
11477
11602
|
defaultValues: {
|
|
11478
11603
|
customerName: "",
|
|
11479
11604
|
customerEmail: "",
|
|
11480
11605
|
customerPhone: "",
|
|
11481
|
-
participants: [{ name: "" }],
|
|
11606
|
+
participants: [{ name: "", level: undefined }],
|
|
11482
11607
|
discountCode: "",
|
|
11483
11608
|
comment: "",
|
|
11484
11609
|
acceptTerms: false,
|
|
11485
11610
|
},
|
|
11486
11611
|
});
|
|
11487
11612
|
const watchedParticipants = form.watch("participants");
|
|
11613
|
+
const participantCount = watchedParticipants.length;
|
|
11488
11614
|
const watchedCustomerName = form.watch("customerName");
|
|
11489
11615
|
const watchedCustomerEmail = form.watch("customerEmail");
|
|
11490
11616
|
const watchedComment = form.watch("comment");
|
|
@@ -11526,14 +11652,13 @@
|
|
|
11526
11652
|
const calculateBaseTotal = q$2(() => {
|
|
11527
11653
|
if (!eventDetails)
|
|
11528
11654
|
return 0;
|
|
11529
|
-
return eventDetails.price *
|
|
11530
|
-
}, [eventDetails,
|
|
11655
|
+
return eventDetails.price * participantCount;
|
|
11656
|
+
}, [eventDetails, participantCount]);
|
|
11531
11657
|
// Calculate upsells total based on per-participant selections
|
|
11532
11658
|
const calculateUpsellsTotal = q$2(() => {
|
|
11533
11659
|
let total = 0;
|
|
11534
|
-
watchedParticipants.forEach((
|
|
11535
|
-
|
|
11536
|
-
if (participant.name.trim()) {
|
|
11660
|
+
watchedParticipants.forEach((_, index) => {
|
|
11661
|
+
if (participantCount > 0) {
|
|
11537
11662
|
const participantUpsellIds = participantUpsells[index] || [];
|
|
11538
11663
|
participantUpsellIds.forEach(upsellId => {
|
|
11539
11664
|
const upsell = upsells.find(u => u.id === upsellId);
|
|
@@ -11544,7 +11669,7 @@
|
|
|
11544
11669
|
}
|
|
11545
11670
|
});
|
|
11546
11671
|
return total;
|
|
11547
|
-
}, [participantUpsells, upsells, watchedParticipants]);
|
|
11672
|
+
}, [participantUpsells, upsells, watchedParticipants, participantCount]);
|
|
11548
11673
|
const calculateTotalDiscount = q$2(() => {
|
|
11549
11674
|
return appliedVouchers.reduce((total, voucher) => {
|
|
11550
11675
|
if (voucher.type === "discount") {
|
|
@@ -11565,8 +11690,7 @@
|
|
|
11565
11690
|
const calculateDeposit = () => {
|
|
11566
11691
|
if (!eventDetails || !eventDetails.deposit)
|
|
11567
11692
|
return 0;
|
|
11568
|
-
|
|
11569
|
-
return eventDetails.deposit * participantCount;
|
|
11693
|
+
return eventDetails.deposit * watchedParticipants.length;
|
|
11570
11694
|
};
|
|
11571
11695
|
const baseTotal = calculateBaseTotal();
|
|
11572
11696
|
const upsellsTotal = calculateUpsellsTotal();
|
|
@@ -11583,8 +11707,8 @@
|
|
|
11583
11707
|
// Includes participantIndices to track which participants selected each upsell
|
|
11584
11708
|
const aggregatedUpsellSelections = q$2(() => {
|
|
11585
11709
|
const upsellParticipantMap = {};
|
|
11586
|
-
watchedParticipants.forEach((
|
|
11587
|
-
if (
|
|
11710
|
+
watchedParticipants.forEach((_, index) => {
|
|
11711
|
+
if (participantCount > 0) {
|
|
11588
11712
|
const participantUpsellIds = participantUpsells[index] || [];
|
|
11589
11713
|
participantUpsellIds.forEach(upsellId => {
|
|
11590
11714
|
if (!upsellParticipantMap[upsellId]) {
|
|
@@ -11618,15 +11742,17 @@
|
|
|
11618
11742
|
setAppliedVouchers((prev) => prev.filter((v) => v.code !== code));
|
|
11619
11743
|
}, []);
|
|
11620
11744
|
const isReadyForPayment = () => {
|
|
11621
|
-
const participantsWithNames = watchedParticipants.filter((p) => p.name
|
|
11745
|
+
const participantsWithNames = watchedParticipants.filter((p) => p.name?.trim()).length;
|
|
11622
11746
|
const totalParticipantRows = watchedParticipants.length;
|
|
11623
|
-
const allParticipantsHaveNames =
|
|
11747
|
+
const allParticipantsHaveNames = participantFieldsConfig.name.required
|
|
11748
|
+
? participantsWithNames === totalParticipantRows
|
|
11749
|
+
: true;
|
|
11624
11750
|
const participantsWithinLimit = participantsWithNames <= (eventDetails?.availableSpots || 0);
|
|
11625
11751
|
const hasValidCustomerName = watchedCustomerName && watchedCustomerName.trim().length >= 2;
|
|
11626
11752
|
const hasValidCustomerEmail = watchedCustomerEmail && watchedCustomerEmail.trim().length > 0 && !customerEmailError;
|
|
11627
11753
|
return allParticipantsHaveNames &&
|
|
11628
11754
|
participantsWithinLimit &&
|
|
11629
|
-
participantsWithNames > 0 &&
|
|
11755
|
+
(participantFieldsConfig.name.required ? participantsWithNames > 0 : totalParticipantRows > 0) &&
|
|
11630
11756
|
hasValidCustomerName &&
|
|
11631
11757
|
hasValidCustomerEmail &&
|
|
11632
11758
|
watchedAcceptTerms;
|
|
@@ -11634,7 +11760,7 @@
|
|
|
11634
11760
|
y$1(() => {
|
|
11635
11761
|
if (appliedVouchers.length > 0) {
|
|
11636
11762
|
const newBaseTotal = eventDetails?.price
|
|
11637
|
-
? eventDetails.price * watchedParticipants.
|
|
11763
|
+
? eventDetails.price * watchedParticipants.length
|
|
11638
11764
|
: 0;
|
|
11639
11765
|
const currentUpsellsTotal = calculateUpsellsTotal();
|
|
11640
11766
|
const orderTotal = newBaseTotal + currentUpsellsTotal;
|
|
@@ -11679,7 +11805,7 @@
|
|
|
11679
11805
|
const currentParticipants = form.getValues("participants");
|
|
11680
11806
|
const availableSpots = eventDetails?.availableSpots || 0;
|
|
11681
11807
|
if (currentParticipants.length < availableSpots) {
|
|
11682
|
-
form.setValue("participants", [...currentParticipants, { name: "" }]);
|
|
11808
|
+
form.setValue("participants", [...currentParticipants, { name: "", level: undefined }]);
|
|
11683
11809
|
}
|
|
11684
11810
|
else {
|
|
11685
11811
|
alert(t$1("booking.maxParticipants", { count: availableSpots }));
|
|
@@ -11798,7 +11924,7 @@
|
|
|
11798
11924
|
justifyContent: "space-between",
|
|
11799
11925
|
alignItems: "center",
|
|
11800
11926
|
marginBottom: "16px",
|
|
11801
|
-
}, children: u$2("h2", { style: { ...sectionHeaderStyles$1, marginBottom: 0 }, children: t$1("booking.participants") }) }), u$2("div", { style: { display: "flex", flexDirection: "column", gap: "16px" }, children: [watchedParticipants.map((_, index) => (u$2("div", { style: { display: "flex", flexDirection: "column", gap: "8px" }, children: [u$2("div", { style: { display: "flex", gap: "12px", alignItems: "center" }, children: [u$2("div", { style: { flex: 1 }, children: [u$2("label", { htmlFor: `participant-name-${index}`, style: labelStyles$1, children: t$1("booking.participantName") }), u$2("input", { id: `participant-name-${index}`, ...form.register(`participants.${index}.name`), type: "text", style: inputStyles$1, placeholder: t$1("booking.participantNamePlaceholder") }), form.formState.errors.participants?.[index]?.name && (u$2("p", { style: errorTextStyles$1, children: form.formState.errors.participants[index]?.name?.message }))] }), u$2("div", { style: { width: "80px" }, children: [u$2("label", { htmlFor: `participant-age-${index}`, style: labelStyles$1, children: t$1("booking.participantAge") }), u$2("input", { id: `participant-age-${index}`, ...form.register(`participants.${index}.age`, {
|
|
11927
|
+
}, children: u$2("h2", { style: { ...sectionHeaderStyles$1, marginBottom: 0 }, children: t$1("booking.participants") }) }), u$2("div", { style: { display: "flex", flexDirection: "column", gap: "16px" }, children: [watchedParticipants.map((_, index) => (u$2("div", { style: { display: "flex", flexDirection: "column", gap: "8px" }, children: [u$2("div", { style: { display: "flex", gap: "12px", alignItems: "center" }, children: [participantFieldsConfig.name.enabled && (u$2("div", { style: { flex: 1 }, children: [u$2("label", { htmlFor: `participant-name-${index}`, style: labelStyles$1, children: t$1("booking.participantName") }), u$2("input", { id: `participant-name-${index}`, ...form.register(`participants.${index}.name`), type: "text", style: inputStyles$1, placeholder: t$1("booking.participantNamePlaceholder") }), form.formState.errors.participants?.[index]?.name && (u$2("p", { style: errorTextStyles$1, children: form.formState.errors.participants[index]?.name?.message }))] })), participantFieldsConfig.age.enabled && (u$2("div", { style: { width: "80px" }, children: [u$2("label", { htmlFor: `participant-age-${index}`, style: labelStyles$1, children: t$1("booking.participantAge") }), u$2("input", { id: `participant-age-${index}`, ...form.register(`participants.${index}.age`, {
|
|
11802
11928
|
setValueAs: (value) => {
|
|
11803
11929
|
if (value === "" || value === null || value === undefined) {
|
|
11804
11930
|
return undefined;
|
|
@@ -11806,7 +11932,7 @@
|
|
|
11806
11932
|
const num = Number(value);
|
|
11807
11933
|
return Number.isNaN(num) ? undefined : num;
|
|
11808
11934
|
},
|
|
11809
|
-
}), type: "number", min: "0", max: "120", style: inputStyles$1, placeholder: "25" })] }), watchedParticipants.length > 1 && (u$2("div", { children: [u$2("label", { style: { ...labelStyles$1, visibility: "hidden" }, children: "\u00A0" }), u$2("button", { type: "button", onClick: () => removeParticipant(index), style: {
|
|
11935
|
+
}), type: "number", min: "0", max: "120", style: inputStyles$1, placeholder: "25" })] })), watchedParticipants.length > 1 && (u$2("div", { children: [u$2("label", { style: { ...labelStyles$1, visibility: "hidden" }, children: "\u00A0" }), u$2("button", { type: "button", onClick: () => removeParticipant(index), style: {
|
|
11810
11936
|
color: "var(--bw-error-color)",
|
|
11811
11937
|
backgroundColor: "var(--bw-surface-color)",
|
|
11812
11938
|
border: "1px solid var(--bw-border-color)",
|
|
@@ -11822,7 +11948,7 @@
|
|
|
11822
11948
|
fontWeight: 700,
|
|
11823
11949
|
fontFamily: "var(--bw-font-family)",
|
|
11824
11950
|
padding: 0,
|
|
11825
|
-
}, children: "\u00D7" })] }))] }), upsells.length > 0 && (u$2("div", { style: participantUpsellStyles.container, children: upsells.map((upsell) => {
|
|
11951
|
+
}, children: "\u00D7" })] }))] }), participantFieldsConfig.level.enabled && (u$2("div", { style: { minWidth: "140px" }, children: [u$2("label", { htmlFor: `participant-level-${index}`, style: labelStyles$1, children: t$1("booking.participantLevel") }), u$2("select", { id: `participant-level-${index}`, ...form.register(`participants.${index}.level`), style: inputStyles$1, children: [u$2("option", { value: "", children: t$1("booking.participantLevelPlaceholder") }), participantLevelOptions.map((level) => (u$2("option", { value: level, children: t$1(`level.${level}`) }, level)))] }), form.formState.errors.participants?.[index]?.level && (u$2("p", { style: errorTextStyles$1, children: form.formState.errors.participants[index]?.level?.message }))] })), upsells.length > 0 && (u$2("div", { style: participantUpsellStyles.container, children: upsells.map((upsell) => {
|
|
11826
11952
|
const isSelected = (participantUpsells[index] || []).includes(upsell.id);
|
|
11827
11953
|
return (u$2("label", { htmlFor: `upsell-${index}-${upsell.id}`, style: isSelected ? participantUpsellStyles.labelSelected : participantUpsellStyles.label, children: [u$2("input", { id: `upsell-${index}-${upsell.id}`, type: "checkbox", style: participantUpsellStyles.checkbox, checked: isSelected, onChange: () => toggleParticipantUpsell(index, upsell.id) }), u$2("span", { style: { fontWeight: 500 }, children: upsell.name }), u$2("span", { style: { fontSize: "12px", opacity: 0.8 }, children: ["(+", formatCurrency(upsell.price), ")"] })] }, upsell.id));
|
|
11828
11954
|
}) }))] }, index))), watchedParticipants.length < eventDetails.availableSpots ? (u$2("div", { style: {
|
|
@@ -11851,9 +11977,9 @@
|
|
|
11851
11977
|
color: "var(--bw-text-color)",
|
|
11852
11978
|
fontWeight: 500,
|
|
11853
11979
|
fontFamily: "var(--bw-font-family)",
|
|
11854
|
-
}, children: [u$2("span", { style: { fontWeight: 200 }, children: [watchedParticipants.length > 1 ? watchedParticipants.
|
|
11980
|
+
}, children: [u$2("span", { style: { fontWeight: 200 }, children: [watchedParticipants.length > 1 ? watchedParticipants.length : 1, " x "] }), " ", formatCurrency(eventDetails.price)] })] }), upsellsTotal > 0 && (u$2("div", { style: { marginTop: "8px", paddingTop: "8px", borderTop: "1px dashed var(--bw-border-color)" }, children: [u$2("span", { style: { color: "var(--bw-text-muted)", fontFamily: "var(--bw-font-family)", fontSize: "13px", display: "block", marginBottom: "4px" }, children: [t$1("common.extras"), ":"] }), upsells.map((upsell) => {
|
|
11855
11981
|
// Count how many participants have this upsell selected
|
|
11856
|
-
const countWithUpsell = watchedParticipants.filter((
|
|
11982
|
+
const countWithUpsell = watchedParticipants.filter((_, idx) => (participantUpsells[idx] || []).includes(upsell.id)).length;
|
|
11857
11983
|
if (countWithUpsell === 0)
|
|
11858
11984
|
return null;
|
|
11859
11985
|
const upsellLineTotal = upsell.price * countWithUpsell;
|
|
@@ -11954,15 +12080,17 @@
|
|
|
11954
12080
|
}, children: t$1("summary.remainingOnSite", { amount: formatCurrency(totalAmount - depositAmount) }) }))] })] })] }), u$2("div", { ref: paymentSectionRef, children: (stripePromise || systemConfig?.paymentProvider === "mollie") &&
|
|
11955
12081
|
(() => {
|
|
11956
12082
|
if (!isReadyForPayment()) {
|
|
11957
|
-
const participantsWithNames = watchedParticipants.filter((p) => p.name
|
|
12083
|
+
const participantsWithNames = watchedParticipants.filter((p) => p.name?.trim()).length;
|
|
11958
12084
|
const totalParticipantRows = watchedParticipants.length;
|
|
11959
12085
|
const participantsWithoutNames = totalParticipantRows - participantsWithNames;
|
|
11960
12086
|
const missing = [];
|
|
11961
|
-
if (
|
|
11962
|
-
|
|
11963
|
-
|
|
11964
|
-
|
|
11965
|
-
|
|
12087
|
+
if (participantFieldsConfig.name.required) {
|
|
12088
|
+
if (participantsWithNames === 0) {
|
|
12089
|
+
missing.push(t$1("payment.needParticipant"));
|
|
12090
|
+
}
|
|
12091
|
+
else if (participantsWithoutNames > 0) {
|
|
12092
|
+
missing.push(t$1("payment.needAllNames", { count: totalParticipantRows }));
|
|
12093
|
+
}
|
|
11966
12094
|
}
|
|
11967
12095
|
if (participantsWithNames > (eventDetails?.availableSpots || 0)) {
|
|
11968
12096
|
missing.push(t$1("payment.reduceParticipants", { count: eventDetails?.availableSpots || 0 }));
|
|
@@ -12137,7 +12265,7 @@
|
|
|
12137
12265
|
try {
|
|
12138
12266
|
const response = await fetch(getApiUrl(config.apiBaseUrl, "/booking/get-booking-by-payment"), {
|
|
12139
12267
|
method: "POST",
|
|
12140
|
-
headers: createApiHeaders(config),
|
|
12268
|
+
headers: createApiHeaders(config, locale),
|
|
12141
12269
|
body: JSON.stringify(createRequestBody(config, {
|
|
12142
12270
|
paymentIntentId: targetPaymentIntentId,
|
|
12143
12271
|
})),
|
|
@@ -12371,7 +12499,7 @@
|
|
|
12371
12499
|
flexDirection: "column",
|
|
12372
12500
|
gap: "var(--bw-spacing-small)",
|
|
12373
12501
|
}, children: formData.participants
|
|
12374
|
-
.filter((p) => p.name
|
|
12502
|
+
.filter((p) => p.name?.trim() || p.age || p.level)
|
|
12375
12503
|
.map((participant, index) => (u$2("div", { className: "print-participant", style: {
|
|
12376
12504
|
display: "flex",
|
|
12377
12505
|
justifyContent: "space-between",
|
|
@@ -12382,11 +12510,15 @@
|
|
|
12382
12510
|
}, children: u$2("div", { className: "print-participant-info", children: [u$2("div", { className: "print-participant-name", style: {
|
|
12383
12511
|
color: "var(--bw-text-color)",
|
|
12384
12512
|
fontFamily: "var(--bw-font-family)",
|
|
12385
|
-
}, children: participant.name }), participant.age && (u$2("div", { className: "print-participant-age", style: {
|
|
12513
|
+
}, children: participant.name || `#${index + 1}` }), participant.age && (u$2("div", { className: "print-participant-age", style: {
|
|
12386
12514
|
color: "var(--bw-text-muted)",
|
|
12387
12515
|
fontSize: "var(--bw-font-size-small)",
|
|
12388
12516
|
fontFamily: "var(--bw-font-family)",
|
|
12389
|
-
}, children: t("success.age", { age: participant.age }) }))
|
|
12517
|
+
}, children: t("success.age", { age: participant.age }) })), participant.level && (u$2("div", { style: {
|
|
12518
|
+
color: "var(--bw-text-muted)",
|
|
12519
|
+
fontSize: "var(--bw-font-size-small)",
|
|
12520
|
+
fontFamily: "var(--bw-font-family)",
|
|
12521
|
+
}, children: [t("booking.participantLevel"), ": ", t(`level.${participant.level}`)] }))] }) }, index))) }) })] })), u$2("div", { className: "print-booking-card", style: {
|
|
12390
12522
|
backgroundColor: "var(--bw-surface-color)",
|
|
12391
12523
|
border: `1px solid var(--bw-border-color)`,
|
|
12392
12524
|
borderRadius: "var(--bw-border-radius)",
|
|
@@ -13794,8 +13926,48 @@
|
|
|
13794
13926
|
const rest = formatted.slice(0, -1).join(", ");
|
|
13795
13927
|
return `${t("duration.optionally")} ${rest} ${t("duration.or")} ${last} ${unitPlural}`;
|
|
13796
13928
|
}
|
|
13797
|
-
function
|
|
13929
|
+
function InfoBadge({ text }) {
|
|
13930
|
+
const [open, setOpen] = d$1(false);
|
|
13931
|
+
const ref = A$2(null);
|
|
13932
|
+
return (u$2("span", { ref: ref, onClick: (e) => { e.stopPropagation(); setOpen((v) => !v); }, style: {
|
|
13933
|
+
position: "relative",
|
|
13934
|
+
display: "inline-flex",
|
|
13935
|
+
alignItems: "center",
|
|
13936
|
+
justifyContent: "center",
|
|
13937
|
+
width: "16px",
|
|
13938
|
+
height: "16px",
|
|
13939
|
+
borderRadius: "50%",
|
|
13940
|
+
border: "1px solid var(--bw-highlight-color)",
|
|
13941
|
+
color: "var(--bw-highlight-color)",
|
|
13942
|
+
fontSize: "9px",
|
|
13943
|
+
fontWeight: 700,
|
|
13944
|
+
cursor: "pointer",
|
|
13945
|
+
flexShrink: 0,
|
|
13946
|
+
userSelect: "none",
|
|
13947
|
+
}, children: ["i", open && (u$2("span", { style: {
|
|
13948
|
+
position: "absolute",
|
|
13949
|
+
bottom: "calc(100% + 6px)",
|
|
13950
|
+
right: 0,
|
|
13951
|
+
backgroundColor: "var(--bw-surface-color)",
|
|
13952
|
+
border: "1px solid var(--bw-border-color)",
|
|
13953
|
+
borderRadius: "var(--bw-border-radius-small)",
|
|
13954
|
+
boxShadow: "var(--bw-shadow-md)",
|
|
13955
|
+
padding: "6px 10px",
|
|
13956
|
+
fontSize: "14px",
|
|
13957
|
+
color: "var(--bw-text-color)",
|
|
13958
|
+
fontWeight: 400,
|
|
13959
|
+
whiteSpace: "normal",
|
|
13960
|
+
width: "160px",
|
|
13961
|
+
lineHeight: 1.4,
|
|
13962
|
+
zIndex: 100,
|
|
13963
|
+
textAlign: "left",
|
|
13964
|
+
pointerEvents: "none",
|
|
13965
|
+
}, children: text }))] }));
|
|
13966
|
+
}
|
|
13967
|
+
function EventTypeSelection({ eventTypes, onEventTypeSelect, onInstancePreview, isLoading = false, skeletonCount = 4, showVoucherAttachment = false, onVoucherClick, }) {
|
|
13798
13968
|
const t = useTranslations();
|
|
13969
|
+
const { locale } = useLocale();
|
|
13970
|
+
const timezone = useTimezone();
|
|
13799
13971
|
// State for details dialog
|
|
13800
13972
|
const [detailsDialogOpen, setDetailsDialogOpen] = d$1(false);
|
|
13801
13973
|
const [selectedEventTypeForDetails, setSelectedEventTypeForDetails] = d$1(null);
|
|
@@ -13905,7 +14077,7 @@
|
|
|
13905
14077
|
display: "flex",
|
|
13906
14078
|
flexDirection: "column",
|
|
13907
14079
|
justifyContent: "space-between",
|
|
13908
|
-
height: "
|
|
14080
|
+
height: "490px",
|
|
13909
14081
|
}, children: [u$2("div", { children: [u$2("h2", { className: "event-type-title", style: {
|
|
13910
14082
|
fontSize: "clamp(1.1rem, 2.5vw, 24px)",
|
|
13911
14083
|
fontWeight: 700,
|
|
@@ -13986,7 +14158,43 @@
|
|
|
13986
14158
|
color: "var(--bw-text-color)",
|
|
13987
14159
|
fontFamily: "var(--bw-font-family)",
|
|
13988
14160
|
textAlign: "right",
|
|
13989
|
-
}, children: u$2("span", { children: [t("common.from"), " ", formatCurrency(eventType.minPrice)] }) })] }),
|
|
14161
|
+
}, children: u$2("span", { children: [t("common.from"), " ", formatCurrency(eventType.minPrice)] }) })] }), (() => {
|
|
14162
|
+
const preview = eventType.cardPreview ?? [];
|
|
14163
|
+
return (u$2("div", { style: {
|
|
14164
|
+
marginTop: "12px",
|
|
14165
|
+
borderTop: "1px solid var(--bw-border-color)",
|
|
14166
|
+
paddingTop: "8px",
|
|
14167
|
+
marginBottom: "16px",
|
|
14168
|
+
}, children: [u$2("div", { style: {
|
|
14169
|
+
fontSize: "11px",
|
|
14170
|
+
fontWeight: 700,
|
|
14171
|
+
color: "var(--bw-text-muted)",
|
|
14172
|
+
textTransform: "uppercase",
|
|
14173
|
+
letterSpacing: "0.05em",
|
|
14174
|
+
marginBottom: "4px",
|
|
14175
|
+
}, children: t("events.previewSectionTitle") }), u$2("div", { style: { height: "102px" }, children: Array.from({ length: 3 }).map((_, i) => {
|
|
14176
|
+
const item = preview[i];
|
|
14177
|
+
if (!item)
|
|
14178
|
+
return u$2("div", { style: { height: "34px" } }, i);
|
|
14179
|
+
const hasDiscount = item.basePrice > 0 && item.price < item.basePrice;
|
|
14180
|
+
return (u$2("div", { onClick: (e) => { e.stopPropagation(); onInstancePreview?.(item.id, eventType.id); }, onMouseEnter: (e) => { if (onInstancePreview)
|
|
14181
|
+
e.currentTarget.style.backgroundColor = "var(--bw-border-color)"; }, onMouseLeave: (e) => { e.currentTarget.style.backgroundColor = "transparent"; }, style: {
|
|
14182
|
+
height: "34px",
|
|
14183
|
+
display: "grid",
|
|
14184
|
+
gridTemplateColumns: "auto 1fr auto 20px",
|
|
14185
|
+
alignItems: "center",
|
|
14186
|
+
gap: "8px",
|
|
14187
|
+
width: "100%",
|
|
14188
|
+
fontSize: "13px",
|
|
14189
|
+
color: "var(--bw-text-muted)",
|
|
14190
|
+
cursor: onInstancePreview ? "pointer" : "default",
|
|
14191
|
+
borderRadius: "4px",
|
|
14192
|
+
padding: "0 2px",
|
|
14193
|
+
transition: "background 0.15s",
|
|
14194
|
+
boxSizing: "border-box",
|
|
14195
|
+
}, children: [u$2("span", { style: { whiteSpace: "nowrap", display: "flex", alignItems: "center", gap: "3px" }, children: [item.isSpecial && (u$2("span", { style: { color: "var(--bw-highlight-color)", fontSize: "11px", lineHeight: 1 }, children: "\u2605" })), formatWeekday(item.startTime, timezone, locale), " ", formatDate(item.startTime, timezone, locale)] }), u$2("span", { style: { overflow: "hidden", textOverflow: "ellipsis", whiteSpace: "nowrap", opacity: 0.75 }, children: item.name }), u$2("span", { style: { display: "flex", alignItems: "center", gap: "4px", whiteSpace: "nowrap" }, children: [hasDiscount && (u$2("span", { style: { textDecoration: "line-through", opacity: 0.55, fontSize: "11px" }, children: formatCurrency(item.basePrice) })), u$2("span", { style: { fontWeight: 700, color: item.isSpecial ? "var(--bw-highlight-color)" : "var(--bw-text-color)" }, children: formatCurrency(item.price) })] }), item.specialDescription ? (u$2(InfoBadge, { text: item.specialDescription })) : (u$2("span", {}))] }, item.id));
|
|
14196
|
+
}) })] }));
|
|
14197
|
+
})(), u$2("div", { style: {
|
|
13990
14198
|
display: "flex",
|
|
13991
14199
|
justifyContent: "flex-end",
|
|
13992
14200
|
alignItems: "center",
|
|
@@ -14001,7 +14209,6 @@
|
|
|
14001
14209
|
backgroundColor: "var(--bw-surface-color)",
|
|
14002
14210
|
padding: "12px",
|
|
14003
14211
|
borderRadius: "var(--bw-border-radius)",
|
|
14004
|
-
fontSize: "clamp(0.8rem, 2vw, 16px)",
|
|
14005
14212
|
fontWeight: 600,
|
|
14006
14213
|
fontFamily: "var(--bw-font-family)",
|
|
14007
14214
|
display: "flex",
|
|
@@ -14014,7 +14221,7 @@
|
|
|
14014
14221
|
}, children: t("button.moreDetails") })), isAvailable && (u$2("div", { style: {
|
|
14015
14222
|
backgroundColor: "var(--bw-highlight-color)",
|
|
14016
14223
|
color: "var(--bw-surface-color)",
|
|
14017
|
-
padding: "12px
|
|
14224
|
+
padding: "12px 14px",
|
|
14018
14225
|
borderRadius: "var(--bw-border-radius)",
|
|
14019
14226
|
fontSize: "clamp(1rem, 2vw, 16px)",
|
|
14020
14227
|
fontWeight: 600,
|
|
@@ -14672,6 +14879,172 @@
|
|
|
14672
14879
|
}, children: "\u27F3" }), t("common.loading")] })) : (showAllButtonText) }) }))] }));
|
|
14673
14880
|
}
|
|
14674
14881
|
|
|
14882
|
+
function SpecialsView({ specials, onEventSelect, isLoading = false, showSavingsAmount = true, showSavingsPercent = false, emptyStateText, isLoadingEventDetails = false, }) {
|
|
14883
|
+
const t = useTranslations();
|
|
14884
|
+
const { locale } = useLocale();
|
|
14885
|
+
const timezone = useTimezone();
|
|
14886
|
+
const [selectedId, setSelectedId] = d$1(null);
|
|
14887
|
+
const handleSelect = (id) => {
|
|
14888
|
+
setSelectedId(id);
|
|
14889
|
+
onEventSelect(id);
|
|
14890
|
+
};
|
|
14891
|
+
if (isLoading) {
|
|
14892
|
+
return u$2(NextEventsSkeleton, { count: 3 });
|
|
14893
|
+
}
|
|
14894
|
+
if (specials.length === 0) {
|
|
14895
|
+
return (u$2("div", { style: { maxWidth: "500px", margin: "0 auto", padding: "16px" }, children: u$2("div", { style: {
|
|
14896
|
+
display: "flex",
|
|
14897
|
+
flexDirection: "column",
|
|
14898
|
+
alignItems: "center",
|
|
14899
|
+
justifyContent: "center",
|
|
14900
|
+
textAlign: "center",
|
|
14901
|
+
backgroundColor: "var(--bw-surface-color)",
|
|
14902
|
+
border: "1px solid var(--bw-border-color)",
|
|
14903
|
+
borderRadius: "var(--bw-border-radius)",
|
|
14904
|
+
padding: "24px",
|
|
14905
|
+
fontFamily: "var(--bw-font-family)",
|
|
14906
|
+
minHeight: "300px",
|
|
14907
|
+
}, children: [u$2("div", { style: {
|
|
14908
|
+
display: "flex",
|
|
14909
|
+
alignItems: "center",
|
|
14910
|
+
justifyContent: "center",
|
|
14911
|
+
borderRadius: "50%",
|
|
14912
|
+
width: "64px",
|
|
14913
|
+
height: "64px",
|
|
14914
|
+
backgroundColor: "var(--bw-highlight-color)",
|
|
14915
|
+
marginBottom: "16px",
|
|
14916
|
+
fontSize: "32px",
|
|
14917
|
+
color: "#ffffff",
|
|
14918
|
+
opacity: 0.8,
|
|
14919
|
+
}, children: "\uD83C\uDFF7\uFE0F" }), u$2("h3", { style: {
|
|
14920
|
+
fontWeight: 600,
|
|
14921
|
+
margin: "0 0 8px 0",
|
|
14922
|
+
fontSize: "20px",
|
|
14923
|
+
color: "var(--bw-text-color)",
|
|
14924
|
+
fontFamily: "var(--bw-font-family)",
|
|
14925
|
+
}, children: t("specials.noSpecials") }), u$2("p", { style: {
|
|
14926
|
+
margin: 0,
|
|
14927
|
+
color: "var(--bw-text-muted)",
|
|
14928
|
+
fontSize: "16px",
|
|
14929
|
+
lineHeight: 1.6,
|
|
14930
|
+
fontFamily: "var(--bw-font-family)",
|
|
14931
|
+
maxWidth: "400px",
|
|
14932
|
+
}, children: emptyStateText ?? t("specials.noSpecialsMessage") })] }) }));
|
|
14933
|
+
}
|
|
14934
|
+
return (u$2("div", { style: {
|
|
14935
|
+
maxWidth: "500px",
|
|
14936
|
+
margin: "0 auto",
|
|
14937
|
+
padding: "16px",
|
|
14938
|
+
fontFamily: "var(--bw-font-family)",
|
|
14939
|
+
}, children: [u$2("div", { style: { textAlign: "center", marginBottom: "24px" }, children: [u$2("h2", { style: {
|
|
14940
|
+
fontWeight: 600,
|
|
14941
|
+
margin: "0 0 8px 0",
|
|
14942
|
+
fontSize: "18px",
|
|
14943
|
+
color: "var(--bw-text-color)",
|
|
14944
|
+
fontFamily: "var(--bw-font-family)",
|
|
14945
|
+
}, children: t("specials.title") }), u$2("p", { style: {
|
|
14946
|
+
margin: 0,
|
|
14947
|
+
fontSize: "16px",
|
|
14948
|
+
color: "var(--bw-text-muted)",
|
|
14949
|
+
fontFamily: "var(--bw-font-family)",
|
|
14950
|
+
}, children: t("specials.subtitle") })] }), u$2("div", { style: { display: "flex", flexDirection: "column", gap: "12px" }, children: specials.map((special) => {
|
|
14951
|
+
const isFullyBooked = special.availableSpots === 0;
|
|
14952
|
+
const isDisabled = isFullyBooked || !special.bookingOpen;
|
|
14953
|
+
const hasDiscount = special.basePrice > 0 && special.price < special.basePrice;
|
|
14954
|
+
return (u$2("div", { style: {
|
|
14955
|
+
position: "relative",
|
|
14956
|
+
backgroundColor: "var(--bw-surface-color)",
|
|
14957
|
+
borderRadius: "var(--bw-border-radius)",
|
|
14958
|
+
border: "1px solid var(--bw-highlight-color)",
|
|
14959
|
+
overflow: "hidden",
|
|
14960
|
+
opacity: isDisabled ? 0.5 : 1,
|
|
14961
|
+
cursor: isDisabled ? "not-allowed" : "pointer",
|
|
14962
|
+
transition: "all 0.2s ease",
|
|
14963
|
+
}, onClick: () => {
|
|
14964
|
+
if (!isDisabled)
|
|
14965
|
+
handleSelect(special.id);
|
|
14966
|
+
}, children: [selectedId === special.id && isLoadingEventDetails && (u$2("div", { style: {
|
|
14967
|
+
position: "absolute",
|
|
14968
|
+
inset: 0,
|
|
14969
|
+
display: "flex",
|
|
14970
|
+
alignItems: "center",
|
|
14971
|
+
justifyContent: "center",
|
|
14972
|
+
backgroundColor: "rgba(15, 23, 42, 0.8)",
|
|
14973
|
+
borderRadius: "var(--bw-border-radius)",
|
|
14974
|
+
zIndex: 10,
|
|
14975
|
+
}, children: u$2("div", { style: { fontSize: "32px", color: "var(--bw-highlight-color)", animation: "spin 1s linear infinite" }, children: "\u27F3" }) })), u$2("div", { style: { display: "flex", gap: "12px", padding: "12px" }, children: [special.images.length > 0 && (u$2("div", { style: {
|
|
14976
|
+
flexShrink: 0,
|
|
14977
|
+
width: "72px",
|
|
14978
|
+
height: "72px",
|
|
14979
|
+
borderRadius: "var(--bw-border-radius-small)",
|
|
14980
|
+
overflow: "hidden",
|
|
14981
|
+
}, children: u$2("img", { src: special.images[0], alt: special.eventTypeName, style: { width: "100%", height: "100%", objectFit: "cover" } }) })), u$2("div", { style: { flex: 1, minWidth: 0 }, children: [u$2("div", { style: { marginBottom: "4px" }, children: u$2("span", { style: {
|
|
14982
|
+
fontSize: "11px",
|
|
14983
|
+
fontWeight: 600,
|
|
14984
|
+
color: "var(--bw-text-muted)",
|
|
14985
|
+
textTransform: "uppercase",
|
|
14986
|
+
letterSpacing: "0.05em",
|
|
14987
|
+
}, children: special.categoryName }) }), u$2("h4", { style: {
|
|
14988
|
+
margin: "0 0 2px 0",
|
|
14989
|
+
fontSize: "15px",
|
|
14990
|
+
fontWeight: 600,
|
|
14991
|
+
color: "var(--bw-text-color)",
|
|
14992
|
+
lineHeight: 1.3,
|
|
14993
|
+
overflow: "hidden",
|
|
14994
|
+
textOverflow: "ellipsis",
|
|
14995
|
+
whiteSpace: "nowrap",
|
|
14996
|
+
}, children: special.eventTypeName }), u$2("div", { style: {
|
|
14997
|
+
fontSize: "13px",
|
|
14998
|
+
fontWeight: 500,
|
|
14999
|
+
color: "var(--bw-highlight-color)",
|
|
15000
|
+
marginBottom: "2px",
|
|
15001
|
+
overflow: "hidden",
|
|
15002
|
+
textOverflow: "ellipsis",
|
|
15003
|
+
whiteSpace: "nowrap",
|
|
15004
|
+
}, children: ["\u2605 ", special.name] }), special.specialDescription && (u$2("div", { style: {
|
|
15005
|
+
fontSize: "12px",
|
|
15006
|
+
color: "var(--bw-text-muted)",
|
|
15007
|
+
marginBottom: "6px",
|
|
15008
|
+
lineHeight: 1.4,
|
|
15009
|
+
}, children: special.specialDescription })), u$2("div", { style: { fontSize: "13px", color: "var(--bw-text-muted)", marginBottom: "8px" }, children: [formatWeekday(special.startTime, timezone, locale), ",", " ", formatDate(special.startTime, timezone, locale)] }), u$2("div", { style: { display: "flex", alignItems: "center", gap: "8px", flexWrap: "wrap" }, children: [hasDiscount && (u$2("span", { style: {
|
|
15010
|
+
fontSize: "13px",
|
|
15011
|
+
color: "var(--bw-text-muted)",
|
|
15012
|
+
textDecoration: "line-through",
|
|
15013
|
+
}, children: formatCurrency(special.basePrice) })), u$2("span", { style: {
|
|
15014
|
+
fontSize: "16px",
|
|
15015
|
+
fontWeight: 700,
|
|
15016
|
+
color: "var(--bw-highlight-color)",
|
|
15017
|
+
}, children: formatCurrency(special.price) }), hasDiscount && showSavingsAmount && (u$2("span", { style: {
|
|
15018
|
+
fontSize: "12px",
|
|
15019
|
+
fontWeight: 600,
|
|
15020
|
+
color: "#ffffff",
|
|
15021
|
+
backgroundColor: "var(--bw-success-color, #22c55e)",
|
|
15022
|
+
borderRadius: "4px",
|
|
15023
|
+
padding: "2px 6px",
|
|
15024
|
+
}, children: t("specials.save").replace("{{amount}}", formatCurrency(special.savings)) })), hasDiscount && showSavingsPercent && (u$2("span", { style: {
|
|
15025
|
+
fontSize: "12px",
|
|
15026
|
+
fontWeight: 600,
|
|
15027
|
+
color: "#ffffff",
|
|
15028
|
+
backgroundColor: "var(--bw-success-color, #22c55e)",
|
|
15029
|
+
borderRadius: "4px",
|
|
15030
|
+
padding: "2px 6px",
|
|
15031
|
+
}, children: t("specials.savePercent").replace("{{percent}}", String(special.savingsPercent)) }))] })] })] }), u$2("div", { style: {
|
|
15032
|
+
borderTop: "1px solid var(--bw-border-color)",
|
|
15033
|
+
padding: "8px 12px",
|
|
15034
|
+
display: "flex",
|
|
15035
|
+
justifyContent: "space-between",
|
|
15036
|
+
alignItems: "center",
|
|
15037
|
+
backgroundColor: "var(--bw-background-color)",
|
|
15038
|
+
}, children: [u$2("span", { style: { fontSize: "12px", color: "var(--bw-text-muted)" }, children: isFullyBooked
|
|
15039
|
+
? t("common.fullyBooked")
|
|
15040
|
+
: t("specials.spotsLeft").replace("{{count}}", String(special.availableSpots)) }), u$2("span", { style: {
|
|
15041
|
+
fontSize: "13px",
|
|
15042
|
+
fontWeight: 600,
|
|
15043
|
+
color: "var(--bw-highlight-color)",
|
|
15044
|
+
}, children: [t("specials.bookNow"), " \u2192"] })] })] }, special.id));
|
|
15045
|
+
}) })] }));
|
|
15046
|
+
}
|
|
15047
|
+
|
|
14675
15048
|
const getThemeConfig = (theme = "generic") => {
|
|
14676
15049
|
switch (theme) {
|
|
14677
15050
|
case "christmas":
|
|
@@ -14931,8 +15304,8 @@
|
|
|
14931
15304
|
};
|
|
14932
15305
|
const checkboxContainerStyles = {
|
|
14933
15306
|
position: "absolute",
|
|
14934
|
-
|
|
14935
|
-
|
|
15307
|
+
bottom: "12px",
|
|
15308
|
+
left: "12px",
|
|
14936
15309
|
zIndex: 1,
|
|
14937
15310
|
};
|
|
14938
15311
|
const checkboxInnerStyles = {
|
|
@@ -15027,6 +15400,7 @@
|
|
|
15027
15400
|
alignItems: "flex-end",
|
|
15028
15401
|
marginTop: "8px",
|
|
15029
15402
|
paddingTop: "8px",
|
|
15403
|
+
paddingBottom: "0px",
|
|
15030
15404
|
borderTop: "1px solid var(--bw-border-color)",
|
|
15031
15405
|
};
|
|
15032
15406
|
const pricePerPersonStyles = {
|
|
@@ -15118,7 +15492,7 @@
|
|
|
15118
15492
|
};
|
|
15119
15493
|
const selectedTotal = calculateTotal();
|
|
15120
15494
|
const selectedCount = selectedUpsells.length;
|
|
15121
|
-
const footerContent = (u$2(k$3, { children: [u$2("button", { type: "button", onClick: onBack, style: mergeStyles(buttonStyles.secondary, buttonStyles.fullWidth), children: t("common.back") }), u$2("button", { type: "button", onClick: onContinue, style: mergeStyles(buttonStyles.primary, buttonStyles.fullWidth), children: selectedCount === 0 ? t("button.continueWithout") : t("button.continue") })] }));
|
|
15495
|
+
const footerContent = (u$2(k$3, { children: [u$2("button", { type: "button", onClick: onBack, style: mergeStyles(buttonStyles.secondary, buttonStyles.fullWidth), className: buttonClassName, children: t("common.back") }), u$2("button", { type: "button", onClick: onContinue, style: mergeStyles(buttonStyles.primary, buttonStyles.fullWidth), className: buttonClassName, children: selectedCount === 0 ? t("button.continueWithout") : t("button.continue") })] }));
|
|
15122
15496
|
return (u$2(Sidebar, { isOpen: isOpen, onClose: onClose, title: t("upsells.title"), footer: footerContent, children: u$2("div", { style: { display: "flex", flexDirection: "column", height: "100%", padding: "16px 16px" }, children: [isLoading && (u$2("div", { style: { display: "flex", flexDirection: "column", alignItems: "center", justifyContent: "center", gap: "12px", padding: "40px 20px", ...textStyles.muted }, children: [spinner(), u$2("span", { children: t("upsells.loading") })] })), !isLoading && upsells.length === 0 && (u$2("div", { style: { textAlign: "center", padding: "40px 20px", ...textStyles.muted }, children: u$2("p", { children: t("upsells.noExtras") }) })), !isLoading && upsells.length > 0 && (u$2("div", { style: { display: "flex", flexDirection: "column", gap: "12px", flex: 1, overflowY: "auto", paddingBottom: "16px" }, children: upsells.map((upsell) => (u$2(UpsellCard, { upsell: upsell, isSelected: isSelected(upsell.id), participantCount: participantCount, onSelect: () => selectUpsell(upsell.id) }, upsell.id))) })), selectedCount > 0 && (u$2("div", { style: { display: "flex", justifyContent: "space-between", alignItems: "center", marginTop: "16px", paddingBottom: "16px", paddingTop: "16px", borderTop: "1px solid var(--bw-border-color)", fontSize: "14px" }, children: [u$2("span", { style: textStyles.muted, children: selectedCount === 1 ? t("upsells.selected", { count: selectedCount }) : t("upsells.selectedPlural", { count: selectedCount }) }), u$2("span", { style: { fontWeight: 600, color: "var(--bw-highlight-color)", fontFamily: "var(--bw-font-family)" }, children: ["+", formatCurrency(selectedTotal)] })] }))] }) }));
|
|
15123
15497
|
}
|
|
15124
15498
|
|
|
@@ -15166,6 +15540,8 @@
|
|
|
15166
15540
|
: (config.voucherIntegration ?? (hasEventSelection && !isDirectInstanceMode));
|
|
15167
15541
|
// Selection flow state
|
|
15168
15542
|
const [currentStep, setCurrentStep] = d$1("eventTypes");
|
|
15543
|
+
// Tracks where to return when closing the booking form
|
|
15544
|
+
const bookingReturnStep = A$2("eventInstances");
|
|
15169
15545
|
const [eventTypes, setEventTypes] = d$1([]);
|
|
15170
15546
|
const [selectedEventType, setSelectedEventType] = d$1(null);
|
|
15171
15547
|
const [eventInstances, setEventInstances] = d$1([]);
|
|
@@ -15178,6 +15554,9 @@
|
|
|
15178
15554
|
// State for upcoming events (next-events view mode)
|
|
15179
15555
|
const [upcomingEvents, setUpcomingEvents] = d$1([]);
|
|
15180
15556
|
const [showingPreview, setShowingPreview] = d$1(true);
|
|
15557
|
+
// State for specials view mode
|
|
15558
|
+
const [specials, setSpecials] = d$1([]);
|
|
15559
|
+
const [isLoadingSpecials, setIsLoadingSpecials] = d$1(false);
|
|
15181
15560
|
// New: sidebar open state for single event type mode
|
|
15182
15561
|
const [sidebarOpen, setSidebarOpen] = d$1(false);
|
|
15183
15562
|
// Booking flow state
|
|
@@ -15328,6 +15707,11 @@
|
|
|
15328
15707
|
await loadUpcomingEvents();
|
|
15329
15708
|
return;
|
|
15330
15709
|
}
|
|
15710
|
+
// Specials view mode: load special offers
|
|
15711
|
+
if (viewMode === "specials") {
|
|
15712
|
+
await loadSpecials();
|
|
15713
|
+
return;
|
|
15714
|
+
}
|
|
15331
15715
|
// Single event type mode: load event type and instances, but don't open sidebar yet
|
|
15332
15716
|
if (isSingleEventTypeMode) {
|
|
15333
15717
|
await loadEventTypes();
|
|
@@ -15551,6 +15935,45 @@
|
|
|
15551
15935
|
setError(data.error || t("error.loadUpcomingEvents"));
|
|
15552
15936
|
}
|
|
15553
15937
|
};
|
|
15938
|
+
const loadSpecials = async () => {
|
|
15939
|
+
setIsLoadingSpecials(true);
|
|
15940
|
+
const specialsSettings = config.specialsSettings ?? {};
|
|
15941
|
+
const requestBody = {
|
|
15942
|
+
organizationId: config.organizationId,
|
|
15943
|
+
limit: specialsSettings.count ?? 20,
|
|
15944
|
+
};
|
|
15945
|
+
if (config.categoryId) {
|
|
15946
|
+
requestBody.categoryId = config.categoryId;
|
|
15947
|
+
}
|
|
15948
|
+
else if (config.eventTypeIds) {
|
|
15949
|
+
requestBody.eventTypeIds = config.eventTypeIds;
|
|
15950
|
+
}
|
|
15951
|
+
else if (config.eventTypeId) {
|
|
15952
|
+
requestBody.eventTypeId = config.eventTypeId;
|
|
15953
|
+
}
|
|
15954
|
+
try {
|
|
15955
|
+
const response = await fetch(getApiUrl(config.apiBaseUrl, "/booking/specials"), {
|
|
15956
|
+
method: "POST",
|
|
15957
|
+
headers: createApiHeaders(config, locale),
|
|
15958
|
+
body: JSON.stringify(requestBody),
|
|
15959
|
+
});
|
|
15960
|
+
const data = await response.json();
|
|
15961
|
+
if (response.ok) {
|
|
15962
|
+
const wl = extractWidgetLanguagePayload(data);
|
|
15963
|
+
if (wl) {
|
|
15964
|
+
onWidgetLanguage?.(wl);
|
|
15965
|
+
onTimezone?.(wl.timezone);
|
|
15966
|
+
}
|
|
15967
|
+
setSpecials(data.specials || []);
|
|
15968
|
+
}
|
|
15969
|
+
else {
|
|
15970
|
+
setError(data.error || t("error.loadUpcomingEvents"));
|
|
15971
|
+
}
|
|
15972
|
+
}
|
|
15973
|
+
finally {
|
|
15974
|
+
setIsLoadingSpecials(false);
|
|
15975
|
+
}
|
|
15976
|
+
};
|
|
15554
15977
|
const loadEventInstances = async (eventTypeId) => {
|
|
15555
15978
|
const response = await fetch(getApiUrl(config.apiBaseUrl, "/booking/event-instances"), {
|
|
15556
15979
|
method: "POST",
|
|
@@ -15735,6 +16158,7 @@
|
|
|
15735
16158
|
// Event instance selection handlers
|
|
15736
16159
|
const handleEventInstanceSelect = async (eventInstance) => {
|
|
15737
16160
|
setSelectedEventInstance(eventInstance);
|
|
16161
|
+
bookingReturnStep.current = "eventInstances";
|
|
15738
16162
|
// Set default participant count for upsell calculations
|
|
15739
16163
|
const defaultParticipantCount = 1;
|
|
15740
16164
|
setTempParticipantCount(defaultParticipantCount);
|
|
@@ -15747,7 +16171,14 @@
|
|
|
15747
16171
|
if (availableUpsells.length > 0) {
|
|
15748
16172
|
// Show upsells step
|
|
15749
16173
|
setUpsells(availableUpsells);
|
|
15750
|
-
|
|
16174
|
+
// Pre-select default-checked upsells
|
|
16175
|
+
const defaultSelections = availableUpsells
|
|
16176
|
+
.filter((upsell) => upsell.defaultChecked && upsell.available)
|
|
16177
|
+
.map((upsell) => ({
|
|
16178
|
+
upsellPackageId: upsell.id,
|
|
16179
|
+
quantity: defaultParticipantCount,
|
|
16180
|
+
}));
|
|
16181
|
+
setSelectedUpsells(defaultSelections);
|
|
15751
16182
|
setCurrentStep("upsells");
|
|
15752
16183
|
setIsLoadingUpsells(false);
|
|
15753
16184
|
return; // Don't proceed to booking yet
|
|
@@ -15778,7 +16209,7 @@
|
|
|
15778
16209
|
setEventInstances([]);
|
|
15779
16210
|
};
|
|
15780
16211
|
const handleBackToEventInstances = () => {
|
|
15781
|
-
setCurrentStep(
|
|
16212
|
+
setCurrentStep(bookingReturnStep.current);
|
|
15782
16213
|
setSelectedEventInstance(null);
|
|
15783
16214
|
setEventDetails(null);
|
|
15784
16215
|
};
|
|
@@ -15812,8 +16243,7 @@
|
|
|
15812
16243
|
}
|
|
15813
16244
|
};
|
|
15814
16245
|
const handleUpsellsBack = () => {
|
|
15815
|
-
|
|
15816
|
-
setCurrentStep("eventInstances");
|
|
16246
|
+
setCurrentStep(bookingReturnStep.current);
|
|
15817
16247
|
setSelectedUpsells([]);
|
|
15818
16248
|
setUpsells([]);
|
|
15819
16249
|
};
|
|
@@ -15848,10 +16278,36 @@
|
|
|
15848
16278
|
setError(errorMessage);
|
|
15849
16279
|
config.onError?.(errorMessage);
|
|
15850
16280
|
};
|
|
15851
|
-
const handleUpcomingEventSelect = async (eventInstanceId) => {
|
|
16281
|
+
const handleUpcomingEventSelect = async (eventInstanceId, eventTypeId) => {
|
|
16282
|
+
// Resolve the event type — may come from card preview (eventTypeId provided) or
|
|
16283
|
+
// from the next-events list where selectedEventType is already set
|
|
16284
|
+
const resolvedEventType = eventTypeId != null
|
|
16285
|
+
? (eventTypes.find((et) => et.id === eventTypeId) ?? selectedEventType)
|
|
16286
|
+
: selectedEventType;
|
|
16287
|
+
if (resolvedEventType && resolvedEventType !== selectedEventType) {
|
|
16288
|
+
setSelectedEventType(resolvedEventType);
|
|
16289
|
+
}
|
|
16290
|
+
// Check if this is coming from a card preview (eventTypeId was provided)
|
|
16291
|
+
// In that case, we need to load event instances so back navigation works properly
|
|
16292
|
+
const isFromCardPreview = eventTypeId != null;
|
|
16293
|
+
if (isFromCardPreview && resolvedEventType) {
|
|
16294
|
+
// Load event instances in background so back navigation shows instances
|
|
16295
|
+
setShouldRenderInstanceSelection(true);
|
|
16296
|
+
void loadEventInstances(resolvedEventType.id);
|
|
16297
|
+
// Record that we should return to instance selection (not event types)
|
|
16298
|
+
bookingReturnStep.current = "eventInstances";
|
|
16299
|
+
}
|
|
16300
|
+
else {
|
|
16301
|
+
// Record where to return when the booking form is closed
|
|
16302
|
+
bookingReturnStep.current = currentStep === "eventInstances" ? "eventInstances" : "eventTypes";
|
|
16303
|
+
}
|
|
16304
|
+
// First try to find the event in upcomingEvents (for next-events view mode)
|
|
15852
16305
|
const upcomingEvent = upcomingEvents.find((event) => event.id === eventInstanceId);
|
|
15853
|
-
|
|
15854
|
-
|
|
16306
|
+
// If not found in upcomingEvents, try to find in card preview items
|
|
16307
|
+
const cardPreviewItem = !upcomingEvent && resolvedEventType?.cardPreview?.find((item) => item.id === eventInstanceId);
|
|
16308
|
+
// Build the event instance from either source
|
|
16309
|
+
const eventInstance = upcomingEvent
|
|
16310
|
+
? {
|
|
15855
16311
|
id: upcomingEvent.id,
|
|
15856
16312
|
name: upcomingEvent.name,
|
|
15857
16313
|
startTime: upcomingEvent.startTime,
|
|
@@ -15865,13 +16321,63 @@
|
|
|
15865
16321
|
bookingOpen: upcomingEvent.bookingOpen,
|
|
15866
16322
|
...(upcomingEvent.deposit !== undefined && { deposit: upcomingEvent.deposit }),
|
|
15867
16323
|
...(upcomingEvent.notes !== undefined && { notes: upcomingEvent.notes }),
|
|
15868
|
-
}
|
|
16324
|
+
}
|
|
16325
|
+
: cardPreviewItem
|
|
16326
|
+
? {
|
|
16327
|
+
id: cardPreviewItem.id,
|
|
16328
|
+
name: cardPreviewItem.name,
|
|
16329
|
+
startTime: cardPreviewItem.startTime,
|
|
16330
|
+
endTime: cardPreviewItem.startTime,
|
|
16331
|
+
price: cardPreviewItem.price,
|
|
16332
|
+
maxParticipants: cardPreviewItem.availableSpots + 1,
|
|
16333
|
+
participantCount: 1,
|
|
16334
|
+
availableSpots: cardPreviewItem.availableSpots,
|
|
16335
|
+
durationDays: 1,
|
|
16336
|
+
durationPerDay: 1,
|
|
16337
|
+
bookingOpen: true,
|
|
16338
|
+
}
|
|
16339
|
+
: null;
|
|
16340
|
+
if (eventInstance) {
|
|
15869
16341
|
setSelectedEventInstance(eventInstance);
|
|
15870
16342
|
}
|
|
16343
|
+
setError(null);
|
|
16344
|
+
// Check for upsells before going to booking (same as handleEventInstanceSelect)
|
|
16345
|
+
const eventTypeForUpsells = resolvedEventType;
|
|
16346
|
+
if (eventTypeForUpsells) {
|
|
16347
|
+
const defaultParticipantCount = 1;
|
|
16348
|
+
setTempParticipantCount(defaultParticipantCount);
|
|
16349
|
+
setIsLoadingUpsells(true);
|
|
16350
|
+
setShouldRenderUpsells(true);
|
|
16351
|
+
try {
|
|
16352
|
+
const availableUpsells = await loadUpsells(eventTypeForUpsells.id, eventInstanceId, defaultParticipantCount);
|
|
16353
|
+
if (availableUpsells.length > 0) {
|
|
16354
|
+
setUpsells(availableUpsells);
|
|
16355
|
+
// Pre-select default-checked upsells
|
|
16356
|
+
const defaultSelections = availableUpsells
|
|
16357
|
+
.filter((upsell) => upsell.defaultChecked && upsell.available)
|
|
16358
|
+
.map((upsell) => ({
|
|
16359
|
+
upsellPackageId: upsell.id,
|
|
16360
|
+
quantity: defaultParticipantCount,
|
|
16361
|
+
}));
|
|
16362
|
+
setSelectedUpsells(defaultSelections);
|
|
16363
|
+
setCurrentStep("upsells");
|
|
16364
|
+
setIsLoadingUpsells(false);
|
|
16365
|
+
// Load event details in background for when user continues past upsells
|
|
16366
|
+
void loadEventDetails(eventInstanceId);
|
|
16367
|
+
return;
|
|
16368
|
+
}
|
|
16369
|
+
}
|
|
16370
|
+
catch (err) {
|
|
16371
|
+
console.error("Error loading upsells:", err);
|
|
16372
|
+
}
|
|
16373
|
+
finally {
|
|
16374
|
+
setIsLoadingUpsells(false);
|
|
16375
|
+
}
|
|
16376
|
+
}
|
|
16377
|
+
// No upsells — go directly to booking
|
|
15871
16378
|
setCurrentStep("booking");
|
|
15872
16379
|
setShouldRenderBookingForm(true);
|
|
15873
16380
|
setIsLoadingEventDetails(true);
|
|
15874
|
-
setError(null);
|
|
15875
16381
|
try {
|
|
15876
16382
|
await loadEventDetails(eventInstanceId);
|
|
15877
16383
|
}
|
|
@@ -16028,6 +16534,31 @@
|
|
|
16028
16534
|
window.history.replaceState({}, "", url.toString());
|
|
16029
16535
|
}, config: config, onError: setError, paymentIntentId: successPaymentId })] }), showPromoDialog && config.promo && (u$2(PromoDialog, { config: config.promo, onClose: handlePromoDialogClose, onCtaClick: handlePromoCtaClick }))] }));
|
|
16030
16536
|
}
|
|
16537
|
+
if (viewMode === "specials" && showingPreview) {
|
|
16538
|
+
return (u$2(StyleProvider, { config: config, children: [u$2("div", { ref: setWidgetContainerRef, children: [u$2(SpecialsView, { specials: specials, onEventSelect: handleUpcomingEventSelect, isLoading: isLoadingSpecials, showSavingsAmount: config.specialsSettings?.showSavingsAmount ?? true, showSavingsPercent: config.specialsSettings?.showSavingsPercent ?? false, emptyStateText: config.specialsSettings?.emptyStateText }), shouldRenderBookingForm && eventDetails && (u$2(BookingForm, { config: config, eventDetails: eventDetails, stripePromise: stripePromise, onSuccess: handleBookingSuccess, onError: handleBookingError, onBackToEventInstances: () => {
|
|
16539
|
+
setCurrentStep("eventTypes");
|
|
16540
|
+
setShowingPreview(true);
|
|
16541
|
+
setEventDetails(null);
|
|
16542
|
+
}, onBackToEventTypes: () => {
|
|
16543
|
+
setCurrentStep("eventTypes");
|
|
16544
|
+
setShowingPreview(true);
|
|
16545
|
+
setEventDetails(null);
|
|
16546
|
+
}, selectedEventType: selectedEventType, selectedEventInstance: selectedEventInstance, isOpen: currentStep === "booking" && !!eventDetails, onClose: () => {
|
|
16547
|
+
setCurrentStep("eventTypes");
|
|
16548
|
+
setShowingPreview(true);
|
|
16549
|
+
setEventDetails(null);
|
|
16550
|
+
}, systemConfig: systemConfig, selectedUpsells: selectedUpsells, upsells: upsells })), u$2(BookingSuccessModal, { isOpen: isSuccess, onClose: () => {
|
|
16551
|
+
setIsSuccess(false);
|
|
16552
|
+
setCurrentStep("eventTypes");
|
|
16553
|
+
setShowingPreview(true);
|
|
16554
|
+
setSuccessPaymentId(null);
|
|
16555
|
+
setShouldRenderInstanceSelection(false);
|
|
16556
|
+
setShouldRenderUpsells(false);
|
|
16557
|
+
setShouldRenderBookingForm(false);
|
|
16558
|
+
setSelectedUpsells([]);
|
|
16559
|
+
setUpsells([]);
|
|
16560
|
+
}, config: config, onError: setError, paymentIntentId: successPaymentId })] }), showPromoDialog && config.promo && (u$2(PromoDialog, { config: config.promo, onClose: handlePromoDialogClose, onCtaClick: handlePromoCtaClick }))] }));
|
|
16561
|
+
}
|
|
16031
16562
|
if (viewMode === "next-events" && !showingPreview && currentStep === "eventInstances") {
|
|
16032
16563
|
return (u$2(StyleProvider, { config: config, children: [u$2("div", { ref: setWidgetContainerRef, children: [shouldRenderInstanceSelection && (u$2(EventInstanceSelection, { eventInstances: eventInstances, selectedEventType: selectedEventType, onEventInstanceSelect: handleEventInstanceSelect, onBackToEventTypes: () => {
|
|
16033
16564
|
setShowingPreview(true);
|
|
@@ -16098,7 +16629,7 @@
|
|
|
16098
16629
|
}, config: config, onError: setError, paymentIntentId: successPaymentId })] }), showPromoDialog && config.promo && (u$2(PromoDialog, { config: config.promo, onClose: handlePromoDialogClose, onCtaClick: handlePromoCtaClick }))] }));
|
|
16099
16630
|
}
|
|
16100
16631
|
// Cards mode (default) - show event type selection with optional voucher card
|
|
16101
|
-
const cardsView = (u$2(k$3, { children: [hasEventSelection && (u$2(EventTypeSelection, { eventTypes: eventTypes, onEventTypeSelect: handleEventTypeSelect, isLoading: isLoading, skeletonCount: getSkeletonCount(), showVoucherAttachment: Boolean(voucherConfig?.enabled && voucherCardIntegrationEnabled && !isStandaloneVoucherMode), onVoucherClick: handleVoucherAttachmentClick })), isStandaloneVoucherMode && (u$2(VoucherIntegration, { config: config, voucherConfig: voucherConfig, eventTypes: voucherEventTypes, systemConfig: systemConfig, isFormOpen: false, isLoadingConfig: isLoadingVoucherConfig, preselectedEventTypeId: null, voucherPurchaseResult: null, isSuccess: false, showStandaloneCard: Boolean(voucherConfig?.enabled && voucherCardIntegrationEnabled), onCardClick: handleVoucherCardClick, onFormClose: handleVoucherFormClose, onSuccess: handleVoucherSuccess, onError: handleVoucherError, onSuccessModalClose: () => { } })), isStandaloneVoucherMode && isLoading && !voucherConfig && (u$2("div", { style: { padding: "24px", textAlign: "center" }, children: u$2("div", { style: {
|
|
16632
|
+
const cardsView = (u$2(k$3, { children: [hasEventSelection && (u$2(EventTypeSelection, { eventTypes: eventTypes, onEventTypeSelect: handleEventTypeSelect, onInstancePreview: (instanceId, eventTypeId) => void handleUpcomingEventSelect(instanceId, eventTypeId), isLoading: isLoading, skeletonCount: getSkeletonCount(), showVoucherAttachment: Boolean(voucherConfig?.enabled && voucherCardIntegrationEnabled && !isStandaloneVoucherMode), onVoucherClick: handleVoucherAttachmentClick })), isStandaloneVoucherMode && (u$2(VoucherIntegration, { config: config, voucherConfig: voucherConfig, eventTypes: voucherEventTypes, systemConfig: systemConfig, isFormOpen: false, isLoadingConfig: isLoadingVoucherConfig, preselectedEventTypeId: null, voucherPurchaseResult: null, isSuccess: false, showStandaloneCard: Boolean(voucherConfig?.enabled && voucherCardIntegrationEnabled), onCardClick: handleVoucherCardClick, onFormClose: handleVoucherFormClose, onSuccess: handleVoucherSuccess, onError: handleVoucherError, onSuccessModalClose: () => { } })), isStandaloneVoucherMode && isLoading && !voucherConfig && (u$2("div", { style: { padding: "24px", textAlign: "center" }, children: u$2("div", { style: {
|
|
16102
16633
|
display: "inline-block",
|
|
16103
16634
|
width: "32px",
|
|
16104
16635
|
height: "32px",
|
|
@@ -16166,11 +16697,7 @@
|
|
|
16166
16697
|
function UniversalBookingWidget(props) {
|
|
16167
16698
|
const [languagePolicy, setLanguagePolicy] = d$1(null);
|
|
16168
16699
|
const [orgTimezone, setOrgTimezone] = d$1("Europe/Berlin");
|
|
16169
|
-
const
|
|
16170
|
-
? languagePolicy.organizationLocale
|
|
16171
|
-
: undefined;
|
|
16172
|
-
const i18nConfigLocale = serverLockedLocale !== undefined ? serverLockedLocale : props.config.locale;
|
|
16173
|
-
const providerProps = i18nConfigLocale ? { configLocale: i18nConfigLocale } : {};
|
|
16700
|
+
const providerProps = props.config.locale ? { configLocale: props.config.locale } : {};
|
|
16174
16701
|
const showLanguagePicker = props.config.showLanguagePicker !== false &&
|
|
16175
16702
|
(languagePolicy === null || languagePolicy.multiLanguageEnabled);
|
|
16176
16703
|
return (u$2(I18nProvider, { ...providerProps, children: u$2(ShowLanguagePickerProvider, { value: showLanguagePicker, children: u$2(TimezoneProvider, { value: orgTimezone, children: u$2(UniversalBookingWidgetInner, { ...props, onWidgetLanguage: setLanguagePolicy, onTimezone: setOrgTimezone }) }) }) }));
|
|
@@ -16208,7 +16735,7 @@
|
|
|
16208
16735
|
}
|
|
16209
16736
|
}
|
|
16210
16737
|
|
|
16211
|
-
var css_248z = ".booking-widget-container{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;box-sizing:border-box;color:var(--bw-text-color,#1e293b);direction:ltr;display:block;font-family:var(--bw-font-family,system-ui,-apple-system,sans-serif);font-size:var(--bw-font-size,14px);isolation:isolate;line-height:1.5;position:relative;text-align:left}.booking-widget-container *,.booking-widget-container :after,.booking-widget-container :before{box-sizing:border-box;margin:0;padding:0}.booking-widget-container input,.booking-widget-container select,.booking-widget-container textarea{font-family:inherit;font-size:inherit;line-height:inherit}.booking-widget-container button{background:none;border:none;cursor:pointer;font-family:inherit;font-size:inherit}.booking-widget-container a{color:inherit;text-decoration:none}.booking-widget-container img{display:block;height:auto;max-width:100%;vertical-align:middle}.booking-widget-container ol,.booking-widget-container ul{list-style:none}.booking-widget-container h1,.booking-widget-container h2,.booking-widget-container h3,.booking-widget-container h4,.booking-widget-container h5,.booking-widget-container h6{font-size:inherit;font-weight:inherit}#booking-widget-portal{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;color:var(--bw-text-color,#1e293b);direction:ltr;font-family:var(--bw-font-family,system-ui,-apple-system,sans-serif);font-size:var(--bw-font-size,14px);isolation:isolate;line-height:1.5;text-align:left}#booking-widget-portal *,#booking-widget-portal :after,#booking-widget-portal :before{box-sizing:border-box}#booking-widget-portal-root{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;color:var(--bw-text-color,#1e293b);font-family:var(--bw-font-family,system-ui,-apple-system,sans-serif);font-size:var(--bw-font-size,14px);line-height:1.5}:root{--bw-highlight-color:#00b1aa;--bw-highlight-color-rgb:0,177,170;--bw-background-color:#f8fdfe;--bw-surface-color:#fff;--bw-text-color:#0e7490;--bw-text-muted:rgba(14,116,144,.7);--bw-border-color:#bae6fd;--bw-success-color:#38bdf8;--bw-warning-color:#fbbf24;--bw-error-color:#f43f5e;--bw-border-radius:18px;--bw-border-radius-small:calc(var(--bw-border-radius)*0.8);--bw-spacing:16px;--bw-spacing-large:24px;--bw-font-family:\"Inter\",system-ui,sans-serif;--bw-font-size:14px;--bw-font-size-large:18px;--bw-font-size-small:12px;--bw-shadow-md:0 4px 6px -1px rgba(0,0,0,.1),0 2px 4px -1px rgba(0,0,0,.06);--bw-shadow-lg:0 10px 15px -3px rgba(0,0,0,.1),0 4px 6px -2px rgba(0,0,0,.05);--bw-highlight-muted:rgba(0,177,170,.1);--bw-highlight-subtle:rgba(0,177,170,.05);--bw-text-subtle:rgba(14,116,144,.4)}@keyframes spin{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}@keyframes shimmer{0%{transform:translateX(-100%)}to{transform:translateX(100%)}}@keyframes fade-in{0%{opacity:0}to{opacity:1}}@keyframes fade-out{0%{opacity:1}to{opacity:0}}@keyframes slide-in-right{0%{opacity:0;transform:translateX(100%)}to{opacity:1;transform:translateX(0)}}@keyframes slide-out-right{0%{opacity:1;transform:translateX(0)}to{opacity:0;transform:translateX(100%)}}@keyframes slide-in-up{0%{opacity:0;transform:translateY(20px)}to{opacity:1;transform:translateY(0)}}@keyframes scale-in{0%{opacity:0;transform:scale(.95)}to{opacity:1;transform:scale(1)}}@keyframes pulse{0%,to{opacity:1}50%{opacity:.5}}.animate-spin{animation:spin 1s linear infinite}.animate-shimmer{animation:shimmer 2s infinite}.animate-pulse{animation:pulse 2s cubic-bezier(.4,0,.6,1) infinite}.animate-fade-in{animation:fade-in .2s ease-out}.animate-slide-in-up{animation:slide-in-up .3s ease-out}.animate-scale-in{animation:scale-in .2s ease-out}.skeleton-shimmer{overflow:hidden;position:relative}.skeleton-shimmer:after{animation:shimmer 1.5s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.3),transparent);content:\"\";height:100%;left:0;position:absolute;top:0;width:100%}@media (max-width:768px){.sidebar-mobile{border-radius:0!important;max-width:100%!important;width:100%!important}}@media (max-width:600px){.event-type-list{gap:12px!important;padding:8px!important}.event-type-card{flex:1 1 100%!important;max-width:100%!important;padding:0!important}.event-type-img{height:160px!important}.event-type-title{font-size:1.1rem!important}.event-type-desc{font-size:.8rem!important;max-height:100px!important;min-height:100px!important}.event-type-content{padding:16px 24px!important}}.event-type-markdown{overflow:visible!important}.event-type-markdown p{color:var(--bw-text-muted);font-family:var(--bw-font-family);line-height:1.6;margin:0 0 8px}.event-type-markdown p:last-child{margin-bottom:0}.event-type-markdown h2{font-size:18px!important;font-weight:700!important;margin:12px 0 6px!important}.event-type-markdown h2,.event-type-markdown h3{color:var(--bw-text-color)!important;line-height:1.3!important}.event-type-markdown h3{font-size:16px!important;font-weight:600!important;margin:10px 0 4px!important}.event-type-markdown strong{color:var(--bw-text-color);font-weight:600}.event-type-markdown em{font-style:italic}.event-type-markdown u{text-decoration:underline}.event-type-markdown ul{list-style:none!important;margin:6px 0!important;padding:0 0 0 24px!important;position:relative!important}.event-type-markdown ul li{color:var(--bw-text-muted)!important;font-family:var(--bw-font-family)!important;margin-bottom:2px!important;padding-left:0!important;position:relative!important}.event-type-markdown ul li:before{color:var(--bw-text-color)!important;content:\"•\"!important;font-weight:700!important;left:-16px!important;position:absolute!important;top:0!important}.event-type-markdown ol{counter-reset:list-counter!important;list-style:none!important;margin:6px 0!important;padding:0 0 0 24px!important;position:relative!important}.event-type-markdown ol li{color:var(--bw-text-muted)!important;counter-increment:list-counter!important;font-family:var(--bw-font-family)!important;margin-bottom:2px!important;padding-left:0!important;position:relative!important}.event-type-markdown ol li:before{color:var(--bw-text-color)!important;content:counter(list-counter) \".\"!important;font-weight:700!important;left:-20px!important;position:absolute!important;top:0!important}.event-type-markdown blockquote{border-left:2px solid var(--bw-border-color);color:var(--bw-text-muted);font-style:italic;margin:4px 0;padding-left:12px}.event-type-markdown a{color:var(--bw-highlight-color);text-decoration:underline}.markdown-content h1,.markdown-content h2,.markdown-content h3,.markdown-content h4,.markdown-content h5,.markdown-content h6{color:var(--bw-text-color);font-weight:600;margin-bottom:.5em}.markdown-content h1{font-size:1.5em}.markdown-content h2{font-size:1.25em}.markdown-content h3{font-size:1.1em}.markdown-content p{line-height:1.6;margin-bottom:1em}.markdown-content ol,.markdown-content ul{margin-bottom:1em;padding-left:1.5em}.markdown-content ul{list-style-type:disc}.markdown-content ol{list-style-type:decimal}.markdown-content li{margin-bottom:.25em}.markdown-content a{color:var(--bw-highlight-color);text-decoration:underline}.markdown-content a:hover{opacity:.8}.markdown-content strong{font-weight:600}.markdown-content em{font-style:italic}.markdown-content code{background:var(--bw-highlight-subtle);border-radius:4px;font-family:monospace;font-size:.9em;padding:.125em .25em}.markdown-content blockquote{border-left:3px solid var(--bw-highlight-color);color:var(--bw-text-muted);margin:1em 0;padding-left:1em}.print-only{display:none}.print-hidden{display:block}@media print{.print-only{display:block}.print-hidden{display:none!important}.print-booking-header{border-bottom:2px solid #000;display:block;margin-bottom:24px;padding-bottom:16px;text-align:center}.print-booking-header h1{font-size:24px;margin:0 0 8px}.print-booking-header .subtitle{color:#666;font-size:14px}.print-booking-card{border:1px solid #ccc;border-radius:8px;margin-bottom:16px;padding:16px;page-break-inside:avoid}.print-section-title{border-bottom:1px solid #ddd;display:block;font-size:16px;font-weight:600;margin-bottom:12px;padding-bottom:8px}.print-detail-grid{display:grid;gap:12px;grid-template-columns:1fr 1fr}.print-detail-item{margin-bottom:8px}.print-detail-label{color:#666;font-size:12px;margin-bottom:4px}.print-detail-value{font-size:14px;font-weight:600}.print-status-badge{border-radius:9999px;display:inline-block;font-size:12px;font-weight:600;padding:4px 12px}.print-status-paid{background-color:#dcfce7;color:#166534;display:inline-block}.print-participant{align-items:center;background-color:#f9fafb;border-radius:4px;display:flex;justify-content:space-between;margin-bottom:8px;padding:8px}.print-participant-name{font-weight:600}.print-participant-age{color:#666;font-size:12px}.print-payment-summary{display:block}.print-payment-row{border-bottom:1px solid #eee;display:flex;justify-content:space-between;padding:4px 0}.print-payment-row:last-child{border-bottom:none;font-weight:600}.print-footer{border-top:1px solid #ddd;color:#666;display:block;font-size:12px;margin-top:24px;padding-top:16px;text-align:center}.print-footer p{margin:4px 0}}";
|
|
16738
|
+
var css_248z = ".booking-widget-container{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;box-sizing:border-box;color:var(--bw-text-color,#1e293b);direction:ltr;display:block;font-family:var(--bw-font-family,system-ui,-apple-system,sans-serif);font-size:var(--bw-font-size,14px);isolation:isolate;line-height:1.5;position:relative;text-align:left}.booking-widget-container *,.booking-widget-container :after,.booking-widget-container :before{box-sizing:border-box;margin:0;padding:0}.booking-widget-container input,.booking-widget-container select,.booking-widget-container textarea{font-family:inherit;font-size:inherit;line-height:inherit}.booking-widget-container button{background:none;border:none;cursor:pointer;font-family:inherit;font-size:inherit}.booking-widget-container a{color:inherit;text-decoration:none}.booking-widget-container img{display:block;height:auto;max-width:100%;vertical-align:middle}.booking-widget-container ol,.booking-widget-container ul{list-style:none}.booking-widget-container h1,.booking-widget-container h2,.booking-widget-container h3,.booking-widget-container h4,.booking-widget-container h5,.booking-widget-container h6{font-size:inherit;font-weight:inherit}#booking-widget-portal{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;color:var(--bw-text-color,#1e293b);direction:ltr;font-family:var(--bw-font-family,system-ui,-apple-system,sans-serif);font-size:var(--bw-font-size,14px);isolation:isolate;line-height:1.5;text-align:left}#booking-widget-portal *,#booking-widget-portal :after,#booking-widget-portal :before{box-sizing:border-box}#booking-widget-portal-root{-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;color:var(--bw-text-color,#1e293b);font-family:var(--bw-font-family,system-ui,-apple-system,sans-serif);font-size:var(--bw-font-size,14px);line-height:1.5}:root{--bw-highlight-color:#00b1aa;--bw-highlight-color-rgb:0,177,170;--bw-background-color:#f8fdfe;--bw-surface-color:#fff;--bw-text-color:#0e7490;--bw-text-muted:rgba(14,116,144,.7);--bw-border-color:#bae6fd;--bw-success-color:#38bdf8;--bw-warning-color:#fbbf24;--bw-error-color:#f43f5e;--bw-border-radius:18px;--bw-border-radius-small:calc(var(--bw-border-radius)*0.8);--bw-spacing:16px;--bw-spacing-large:24px;--bw-font-family:\"Inter\",system-ui,sans-serif;--bw-font-size:14px;--bw-font-size-large:18px;--bw-font-size-small:12px;--bw-shadow-md:0 4px 6px -1px rgba(0,0,0,.1),0 2px 4px -1px rgba(0,0,0,.06);--bw-shadow-lg:0 10px 15px -3px rgba(0,0,0,.1),0 4px 6px -2px rgba(0,0,0,.05);--bw-highlight-muted:rgba(0,177,170,.1);--bw-highlight-subtle:rgba(0,177,170,.05);--bw-text-subtle:rgba(14,116,144,.4)}@keyframes spin{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}@keyframes shimmer{0%{transform:translateX(-100%)}to{transform:translateX(100%)}}@keyframes fade-in{0%{opacity:0}to{opacity:1}}@keyframes fade-out{0%{opacity:1}to{opacity:0}}@keyframes slide-in-right{0%{opacity:0;transform:translateX(100%)}to{opacity:1;transform:translateX(0)}}@keyframes slide-out-right{0%{opacity:1;transform:translateX(0)}to{opacity:0;transform:translateX(100%)}}@keyframes slide-in-up{0%{opacity:0;transform:translateY(20px)}to{opacity:1;transform:translateY(0)}}@keyframes scale-in{0%{opacity:0;transform:scale(.95)}to{opacity:1;transform:scale(1)}}@keyframes pulse{0%,to{opacity:1}50%{opacity:.5}}.animate-spin{animation:spin 1s linear infinite}.animate-shimmer{animation:shimmer 2s infinite}.animate-pulse{animation:pulse 2s cubic-bezier(.4,0,.6,1) infinite}.animate-fade-in{animation:fade-in .2s ease-out}.animate-slide-in-up{animation:slide-in-up .3s ease-out}.animate-scale-in{animation:scale-in .2s ease-out}.skeleton-shimmer{overflow:hidden;position:relative}.skeleton-shimmer:after{animation:shimmer 1.5s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.3),transparent);content:\"\";height:100%;left:0;position:absolute;top:0;width:100%}.bw-btn{transition:all .2s ease!important}.bw-btn:hover:not(:disabled):not([disabled]){box-shadow:0 4px 12px rgba(0,0,0,.15);transform:translateY(-1px)}.bw-btn:active:not(:disabled):not([disabled]){box-shadow:0 2px 4px rgba(0,0,0,.1)}.bw-btn-primary:hover:not(:disabled):not([disabled]){background-color:var(--bw-highlight-color);filter:brightness(1.1)}.bw-btn-secondary:hover:not(:disabled):not([disabled]){background-color:var(--bw-surface-color);border-color:var(--bw-highlight-color);color:var(--bw-highlight-color)}.bw-btn-ghost:hover:not(:disabled):not([disabled]){background-color:var(--bw-highlight-muted)}.bw-btn-outline:hover:not(:disabled):not([disabled]){background-color:var(--bw-highlight-color);color:var(--bw-button-text-color,#fff)}.bw-btn:disabled,.bw-btn[disabled]{cursor:not-allowed!important;opacity:.5!important}button[class*=bw-btn],button[style*=transition]{transition:all .2s ease!important}button[data-variant=primary]:hover:not(:disabled),button[style*=\"--bw-highlight-color\"]:hover:not(:disabled){box-shadow:0 4px 12px rgba(0,0,0,.15);filter:brightness(1.1);transform:translateY(-1px)}button[data-variant=secondary]:hover:not(:disabled){border-color:var(--bw-highlight-color)!important;color:var(--bw-highlight-color)!important}button[data-variant=ghost]:hover:not(:disabled){background-color:var(--bw-highlight-muted)!important}button[data-variant=outline]:hover:not(:disabled){background-color:var(--bw-highlight-color)!important;color:var(--bw-button-text-color,#fff)!important}.bw-button-hover:hover:not(:disabled){box-shadow:0 4px 12px rgba(0,0,0,.15);transform:translateY(-1px)}.bw-button-hover:active:not(:disabled){box-shadow:0 2px 4px rgba(0,0,0,.1);transform:translateY(0)}@media (max-width:768px){.sidebar-mobile{border-radius:0!important;max-width:100%!important;width:100%!important}}@media (max-width:600px){.event-type-list{gap:12px!important;padding:8px!important}.event-type-card{flex:1 1 100%!important;max-width:100%!important;padding:0!important}.event-type-img{height:160px!important}.event-type-title{font-size:1.1rem!important}.event-type-desc{font-size:.8rem!important;max-height:100px!important;min-height:100px!important}.event-type-content{padding:16px 24px!important}}.event-type-markdown{overflow:visible!important}.event-type-markdown p{color:var(--bw-text-muted);font-family:var(--bw-font-family);line-height:1.6;margin:0 0 8px}.event-type-markdown p:last-child{margin-bottom:0}.event-type-markdown h2{font-size:18px!important;font-weight:700!important;margin:12px 0 6px!important}.event-type-markdown h2,.event-type-markdown h3{color:var(--bw-text-color)!important;line-height:1.3!important}.event-type-markdown h3{font-size:16px!important;font-weight:600!important;margin:10px 0 4px!important}.event-type-markdown strong{color:var(--bw-text-color);font-weight:600}.event-type-markdown em{font-style:italic}.event-type-markdown u{text-decoration:underline}.event-type-markdown ul{list-style:none!important;margin:6px 0!important;padding:0 0 0 24px!important;position:relative!important}.event-type-markdown ul li{color:var(--bw-text-muted)!important;font-family:var(--bw-font-family)!important;margin-bottom:2px!important;padding-left:0!important;position:relative!important}.event-type-markdown ul li:before{color:var(--bw-text-color)!important;content:\"•\"!important;font-weight:700!important;left:-16px!important;position:absolute!important;top:0!important}.event-type-markdown ol{counter-reset:list-counter!important;list-style:none!important;margin:6px 0!important;padding:0 0 0 24px!important;position:relative!important}.event-type-markdown ol li{color:var(--bw-text-muted)!important;counter-increment:list-counter!important;font-family:var(--bw-font-family)!important;margin-bottom:2px!important;padding-left:0!important;position:relative!important}.event-type-markdown ol li:before{color:var(--bw-text-color)!important;content:counter(list-counter) \".\"!important;font-weight:700!important;left:-20px!important;position:absolute!important;top:0!important}.event-type-markdown blockquote{border-left:2px solid var(--bw-border-color);color:var(--bw-text-muted);font-style:italic;margin:4px 0;padding-left:12px}.event-type-markdown a{color:var(--bw-highlight-color);text-decoration:underline}.markdown-content h1,.markdown-content h2,.markdown-content h3,.markdown-content h4,.markdown-content h5,.markdown-content h6{color:var(--bw-text-color);font-weight:600;margin-bottom:.5em}.markdown-content h1{font-size:1.5em}.markdown-content h2{font-size:1.25em}.markdown-content h3{font-size:1.1em}.markdown-content p{line-height:1.6;margin-bottom:1em}.markdown-content ol,.markdown-content ul{margin-bottom:1em;padding-left:1.5em}.markdown-content ul{list-style-type:disc}.markdown-content ol{list-style-type:decimal}.markdown-content li{margin-bottom:.25em}.markdown-content a{color:var(--bw-highlight-color);text-decoration:underline}.markdown-content a:hover{opacity:.8}.markdown-content strong{font-weight:600}.markdown-content em{font-style:italic}.markdown-content code{background:var(--bw-highlight-subtle);border-radius:4px;font-family:monospace;font-size:.9em;padding:.125em .25em}.markdown-content blockquote{border-left:3px solid var(--bw-highlight-color);color:var(--bw-text-muted);margin:1em 0;padding-left:1em}.print-only{display:none}.print-hidden{display:block}@media print{.print-only{display:block}.print-hidden{display:none!important}.print-booking-header{border-bottom:2px solid #000;display:block;margin-bottom:24px;padding-bottom:16px;text-align:center}.print-booking-header h1{font-size:24px;margin:0 0 8px}.print-booking-header .subtitle{color:#666;font-size:14px}.print-booking-card{border:1px solid #ccc;border-radius:8px;margin-bottom:16px;padding:16px;page-break-inside:avoid}.print-section-title{border-bottom:1px solid #ddd;display:block;font-size:16px;font-weight:600;margin-bottom:12px;padding-bottom:8px}.print-detail-grid{display:grid;gap:12px;grid-template-columns:1fr 1fr}.print-detail-item{margin-bottom:8px}.print-detail-label{color:#666;font-size:12px;margin-bottom:4px}.print-detail-value{font-size:14px;font-weight:600}.print-status-badge{border-radius:9999px;display:inline-block;font-size:12px;font-weight:600;padding:4px 12px}.print-status-paid{background-color:#dcfce7;color:#166534;display:inline-block}.print-participant{align-items:center;background-color:#f9fafb;border-radius:4px;display:flex;justify-content:space-between;margin-bottom:8px;padding:8px}.print-participant-name{font-weight:600}.print-participant-age{color:#666;font-size:12px}.print-payment-summary{display:block}.print-payment-row{border-bottom:1px solid #eee;display:flex;justify-content:space-between;padding:4px 0}.print-payment-row:last-child{border-bottom:none;font-weight:600}.print-footer{border-top:1px solid #ddd;color:#666;display:block;font-size:12px;margin-top:24px;padding-top:16px;text-align:center}.print-footer p{margin:4px 0}}";
|
|
16212
16739
|
styleInject(css_248z);
|
|
16213
16740
|
|
|
16214
16741
|
// Export init function for vanilla JS usage with Preact
|