@getmicdrop/venue-calendar 4.0.67 → 4.0.68

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.
Files changed (62) hide show
  1. package/dist/{CarouselView.legacy-BBwlnHGY.js → CarouselView.legacy-DtlaKenI.js} +3 -3
  2. package/dist/{CarouselView.legacy-BBwlnHGY.js.map → CarouselView.legacy-DtlaKenI.js.map} +1 -1
  3. package/dist/{CartView-neRvx3wY.js → CartView-xAVJT3Wf.js} +3 -3
  4. package/dist/{CartView-neRvx3wY.js.map → CartView-xAVJT3Wf.js.map} +1 -1
  5. package/dist/{Checkout-neLq8bnZ.js → Checkout-C8E5Q9nl.js} +98 -98
  6. package/dist/{Checkout-neLq8bnZ.js.map → Checkout-C8E5Q9nl.js.map} +1 -1
  7. package/dist/{Checkout-CfaFR4jD.js → Checkout-WYIEsOZ0.js} +5 -5
  8. package/dist/{Checkout-CfaFR4jD.js.map → Checkout-WYIEsOZ0.js.map} +1 -1
  9. package/dist/{Checkout.legacy-ByS44kay.js → Checkout.legacy-Bjj390J_.js} +5 -5
  10. package/dist/{Checkout.legacy-ByS44kay.js.map → Checkout.legacy-Bjj390J_.js.map} +1 -1
  11. package/dist/{CheckoutTimer-DQsDJLwQ.js → CheckoutTimer-DlnXHs-c.js} +2 -2
  12. package/dist/{CheckoutTimer-DQsDJLwQ.js.map → CheckoutTimer-DlnXHs-c.js.map} +1 -1
  13. package/dist/{CollectionView-PIMXDMir.js → CollectionView-89AFwGuE.js} +5 -5
  14. package/dist/{CollectionView-PIMXDMir.js.map → CollectionView-89AFwGuE.js.map} +1 -1
  15. package/dist/{CollectionView.legacy-DpzdMxaY.js → CollectionView.legacy-Czq6UrTZ.js} +3 -3
  16. package/dist/{CollectionView.legacy-DpzdMxaY.js.map → CollectionView.legacy-Czq6UrTZ.js.map} +1 -1
  17. package/dist/{Event-YSQ84uZG.js → Event-DhvEjKVz.js} +4 -4
  18. package/dist/{Event-YSQ84uZG.js.map → Event-DhvEjKVz.js.map} +1 -1
  19. package/dist/{EventDetailsView-CYiyqOuR.js → EventDetailsView-4f1xNl1a.js} +6 -6
  20. package/dist/{EventDetailsView-CYiyqOuR.js.map → EventDetailsView-4f1xNl1a.js.map} +1 -1
  21. package/dist/{EventPage-DH2L98MK.js → EventPage-D75bt8XZ.js} +5 -5
  22. package/dist/{EventPage-DH2L98MK.js.map → EventPage-D75bt8XZ.js.map} +1 -1
  23. package/dist/{EventPage.legacy-2IjniLB2.js → EventPage.legacy-DU0ZcZg9.js} +5 -5
  24. package/dist/{EventPage.legacy-2IjniLB2.js.map → EventPage.legacy-DU0ZcZg9.js.map} +1 -1
  25. package/dist/{FeaturedView.legacy-BciGRyS4.js → FeaturedView.legacy-BgZu-R0y.js} +2 -2
  26. package/dist/{FeaturedView.legacy-BciGRyS4.js.map → FeaturedView.legacy-BgZu-R0y.js.map} +1 -1
  27. package/dist/{GalleryCard-Ccriw4rf.js → GalleryCard-DdHqVAXD.js} +2 -2
  28. package/dist/{GalleryCard-Ccriw4rf.js.map → GalleryCard-DdHqVAXD.js.map} +1 -1
  29. package/dist/{GalleryView.legacy-9yQBBGk4.js → GalleryView.legacy-F46Bwi9x.js} +3 -3
  30. package/dist/{GalleryView.legacy-9yQBBGk4.js.map → GalleryView.legacy-F46Bwi9x.js.map} +1 -1
  31. package/dist/{GroupedListView.legacy-DjmtlEHN.js → GroupedListView.legacy-CLnOs7Ls.js} +2 -2
  32. package/dist/{GroupedListView.legacy-DjmtlEHN.js.map → GroupedListView.legacy-CLnOs7Ls.js.map} +1 -1
  33. package/dist/{OrderSummary-DfYrkOm8.js → OrderSummary-BYSCmf9h.js} +2 -2
  34. package/dist/{OrderSummary-DfYrkOm8.js.map → OrderSummary-BYSCmf9h.js.map} +1 -1
  35. package/dist/{PromoCodeInput-2qhorZ4R.js → PromoCodeInput-B8agz1bc.js} +3 -3
  36. package/dist/{PromoCodeInput-2qhorZ4R.js.map → PromoCodeInput-B8agz1bc.js.map} +1 -1
  37. package/dist/{SeriesPage-DSp3Tk96.js → SeriesPage-CH8STWTA.js} +5 -5
  38. package/dist/{SeriesPage-DSp3Tk96.js.map → SeriesPage-CH8STWTA.js.map} +1 -1
  39. package/dist/{SeriesPage.legacy-Cp4kgJX0.js → SeriesPage.legacy-Cg5j7_1m.js} +2 -2
  40. package/dist/{SeriesPage.legacy-Cp4kgJX0.js.map → SeriesPage.legacy-Cg5j7_1m.js.map} +1 -1
  41. package/dist/{Success-4pmaO3_j.js → Success-DMGAgbh-.js} +6 -6
  42. package/dist/{Success-4pmaO3_j.js.map → Success-DMGAgbh-.js.map} +1 -1
  43. package/dist/{Success.legacy-C9kgMMJf.js → Success.legacy-CY33Nix8.js} +2 -2
  44. package/dist/{Success.legacy-C9kgMMJf.js.map → Success.legacy-CY33Nix8.js.map} +1 -1
  45. package/dist/{VenueCalendar-Blt02sO6.js → VenueCalendar-H0gMPiFX.js} +18 -18
  46. package/dist/{VenueCalendar-Blt02sO6.js.map → VenueCalendar-H0gMPiFX.js.map} +1 -1
  47. package/dist/{ViewTicketsEmbed-CjvjdfNp.js → ViewTicketsEmbed-DiGhZiyP.js} +2 -2
  48. package/dist/{ViewTicketsEmbed-CjvjdfNp.js.map → ViewTicketsEmbed-DiGhZiyP.js.map} +1 -1
  49. package/dist/{WaitlistModal-CJZwJnqM.js → WaitlistModal-CA8-Rcff.js} +2 -2
  50. package/dist/{WaitlistModal-CJZwJnqM.js.map → WaitlistModal-CA8-Rcff.js.map} +1 -1
  51. package/dist/{api-BEAW5Ft0.js → api-IWcZsS94.js} +2 -2
  52. package/dist/{api-BEAW5Ft0.js.map → api-IWcZsS94.js.map} +1 -1
  53. package/dist/{data-toggle-store.svelte-D9f6ubIy.js → data-toggle-store.svelte-D6pqR0Zt.js} +2 -2
  54. package/dist/{data-toggle-store.svelte-D9f6ubIy.js.map → data-toggle-store.svelte-D6pqR0Zt.js.map} +1 -1
  55. package/dist/{transform-qymk5ZMA.js → transform-BPCR9pPY.js} +2 -2
  56. package/dist/{transform-qymk5ZMA.js.map → transform-BPCR9pPY.js.map} +1 -1
  57. package/dist/venue-calendar.es.js +1 -1
  58. package/dist/venue-calendar.iife.js +43 -43
  59. package/dist/venue-calendar.iife.js.map +1 -1
  60. package/dist/venue-calendar.umd.js +26 -26
  61. package/dist/venue-calendar.umd.js.map +1 -1
  62. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"file":"FeaturedView.legacy-BciGRyS4.js","sources":["../src/components/Calendar/FeaturedView.legacy.svelte"],"sourcesContent":["<script>\r\n // @ts-nocheck legacy fallback (legacy=1 path), slated for deletion after VC finalization — not type-maintained\r\n import { formatFullDate, formatEventTime } from \"$lib/utils/datetime.js\";\r\n import { PLACEHOLDER_IMAGE } from \"$lib/utils/constants.js\";\r\n import { filterTodayAndFuture } from \"$lib/utils/browse-status.js\";\r\n\r\n let {\r\n events = [],\r\n featuredItem = null,\r\n oneventClick,\r\n } = $props();\r\n\r\n // Filter to today and future, sorted chronologically\r\n let futureEvents = $derived(filterTodayAndFuture(events));\r\n\r\n let heroEvent = $derived(futureEvents.length > 0 ? futureEvents[0] : null);\r\n\r\n function handleClick() {\r\n if (heroEvent) {\r\n oneventClick?.(heroEvent);\r\n }\r\n }\r\n</script>\r\n\r\n<section class=\"w-full\" aria-label=\"Featured event\">\r\n {#if featuredItem}\r\n <!-- Series or Collection hero -->\r\n <div class=\"featured-hero rounded-lg border border-border bg-card overflow-hidden\">\r\n {#if featuredItem.image}\r\n <div class=\"hero-image-container relative w-full bg-muted overflow-hidden\">\r\n <img\r\n src={featuredItem.image}\r\n alt=\"\"\r\n class=\"hero-image\"\r\n aria-hidden=\"true\"\r\n />\r\n </div>\r\n {:else}\r\n <div class=\"hero-image-container relative w-full bg-muted overflow-hidden flex items-center justify-center\">\r\n <svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.5\" class=\"w-16 h-16 text-muted-foreground\"><rect x=\"2\" y=\"2\" width=\"20\" height=\"20\" rx=\"2\"/><circle cx=\"8.5\" cy=\"8.5\" r=\"1.5\"/><path d=\"m21 15-5-5L5 21\"/></svg>\r\n </div>\r\n {/if}\r\n\r\n <div class=\"p-4 sm:p-5\">\r\n <div class=\"inline-flex items-center gap-1.5 text-xs font-semibold text-brand-primary uppercase tracking-wide mb-2\">\r\n {#if featuredItem.type === 'series'}\r\n <span class=\"w-1.5 h-1.5 rounded-full bg-brand-primary\"></span>\r\n Series\r\n {:else}\r\n <span class=\"w-1.5 h-1.5 rounded-full bg-brand-primary\"></span>\r\n Collection\r\n {/if}\r\n {#if featuredItem.subtitle}\r\n <span class=\"text-muted-foreground\">·</span>\r\n {featuredItem.subtitle}\r\n {/if}\r\n </div>\r\n\r\n <h2 class=\"hero-title text-xl sm:text-2xl font-bold text-text-primary mb-2\">{featuredItem.title}</h2>\r\n\r\n {#if heroEvent}\r\n <p class=\"text-base text-text-secondary font-medium\">\r\n Next: {formatFullDate(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {#if heroEvent.startDateTime}\r\n at {formatEventTime(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {/if}\r\n </p>\r\n {/if}\r\n </div>\r\n </div>\r\n {:else if heroEvent}\r\n <!-- Single event hero -->\r\n <div\r\n class=\"featured-hero featured-hero-clickable rounded-lg border border-border bg-card overflow-hidden cursor-pointer hover:border-stroke-primary focus-visible:outline-2 focus-visible:outline-brand-primary:outline-brand-primary focus-visible:outline-offset-2\"\r\n onclick={handleClick}\r\n onkeydown={(e) => (e.key === 'Enter' || e.key === ' ') && handleClick()}\r\n tabindex=\"0\"\r\n role=\"button\"\r\n aria-label=\"{heroEvent.name}, {formatFullDate(heroEvent.startDateTime, heroEvent.timeZone)}. Press Enter to view details.\"\r\n >\r\n <div class=\"hero-image-container relative w-full bg-muted overflow-hidden\">\r\n <img\r\n src={heroEvent.image || PLACEHOLDER_IMAGE}\r\n alt=\"\"\r\n class=\"hero-image\"\r\n aria-hidden=\"true\"\r\n />\r\n </div>\r\n\r\n <div class=\"p-4 sm:p-5\" aria-hidden=\"true\">\r\n <h2 class=\"hero-title text-xl sm:text-2xl font-bold text-text-primary mb-2\">{heroEvent.name}</h2>\r\n\r\n <p class=\"text-base text-text-secondary font-medium\">\r\n {formatFullDate(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {#if heroEvent.startDateTime}\r\n <span class=\"text-muted-foreground mx-1\">·</span>\r\n {formatEventTime(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {/if}\r\n </p>\r\n\r\n {#if heroEvent.description}\r\n <p class=\"hero-description text-sm text-text-secondary mt-2\">{heroEvent.description}</p>\r\n {/if}\r\n </div>\r\n </div>\r\n {:else}\r\n <!-- Empty state -->\r\n <div class=\"flex items-center justify-center py-12 rounded-lg border border-border bg-bg-secondary\">\r\n <p class=\"text-sm text-muted-foreground\">No upcoming events to feature</p>\r\n </div>\r\n {/if}\r\n</section>\r\n\r\n<style>\r\n .hero-image-container {\r\n aspect-ratio: 16 / 9;\r\n }\r\n\r\n .hero-image {\r\n width: 100%;\r\n height: 100%;\r\n object-fit: contain;\r\n }\r\n\r\n .hero-title {\r\n line-height: 1.3;\r\n }\r\n\r\n .featured-hero-clickable {\r\n transition: border-color 0.2s ease, box-shadow 0.2s ease;\r\n }\r\n\r\n .featured-hero-clickable:hover {\r\n box-shadow: 0 4px 12px color-mix(in srgb, black 10%, transparent);\r\n }\r\n\r\n .featured-hero-clickable:focus {\r\n outline: none;\r\n }\r\n\r\n .hero-description {\r\n display: -webkit-box;\r\n -webkit-line-clamp: 2;\r\n line-clamp: 2;\r\n -webkit-box-orient: vertical;\r\n overflow: hidden;\r\n }\r\n\r\n /* Reduced motion */\r\n @media (prefers-reduced-motion: reduce) {\r\n .featured-hero-clickable {\r\n transition: none;\r\n }\r\n }\r\n</style>\r\n"],"names":["events","$","$$props","featuredItem","futureEvents","filterTodayAndFuture","heroEvent","handleClick","section","root","div","root_1","div_1","root_2","img","div_2","root_3","$$render","consequent","alternate","div_3","node_1","div_4","consequent_1","alternate_1","text","consequent_2","h2","p","root_7","formatEventTime","consequent_3","formatFullDate","consequent_4","text_1","div_5","root_9","div_6","img_1","div_7","h2_1","p_1","consequent_6","p_2","root_11","text_7","consequent_7","$0","PLACEHOLDER_IMAGE","text_4","e","div_8","root_12","consequent_8","alternate_2"],"mappings":"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"}
1
+ {"version":3,"file":"FeaturedView.legacy-BgZu-R0y.js","sources":["../src/components/Calendar/FeaturedView.legacy.svelte"],"sourcesContent":["<script>\r\n // @ts-nocheck legacy fallback (legacy=1 path), slated for deletion after VC finalization — not type-maintained\r\n import { formatFullDate, formatEventTime } from \"$lib/utils/datetime.js\";\r\n import { PLACEHOLDER_IMAGE } from \"$lib/utils/constants.js\";\r\n import { filterTodayAndFuture } from \"$lib/utils/browse-status.js\";\r\n\r\n let {\r\n events = [],\r\n featuredItem = null,\r\n oneventClick,\r\n } = $props();\r\n\r\n // Filter to today and future, sorted chronologically\r\n let futureEvents = $derived(filterTodayAndFuture(events));\r\n\r\n let heroEvent = $derived(futureEvents.length > 0 ? futureEvents[0] : null);\r\n\r\n function handleClick() {\r\n if (heroEvent) {\r\n oneventClick?.(heroEvent);\r\n }\r\n }\r\n</script>\r\n\r\n<section class=\"w-full\" aria-label=\"Featured event\">\r\n {#if featuredItem}\r\n <!-- Series or Collection hero -->\r\n <div class=\"featured-hero rounded-lg border border-border bg-card overflow-hidden\">\r\n {#if featuredItem.image}\r\n <div class=\"hero-image-container relative w-full bg-muted overflow-hidden\">\r\n <img\r\n src={featuredItem.image}\r\n alt=\"\"\r\n class=\"hero-image\"\r\n aria-hidden=\"true\"\r\n />\r\n </div>\r\n {:else}\r\n <div class=\"hero-image-container relative w-full bg-muted overflow-hidden flex items-center justify-center\">\r\n <svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"1.5\" class=\"w-16 h-16 text-muted-foreground\"><rect x=\"2\" y=\"2\" width=\"20\" height=\"20\" rx=\"2\"/><circle cx=\"8.5\" cy=\"8.5\" r=\"1.5\"/><path d=\"m21 15-5-5L5 21\"/></svg>\r\n </div>\r\n {/if}\r\n\r\n <div class=\"p-4 sm:p-5\">\r\n <div class=\"inline-flex items-center gap-1.5 text-xs font-semibold text-brand-primary uppercase tracking-wide mb-2\">\r\n {#if featuredItem.type === 'series'}\r\n <span class=\"w-1.5 h-1.5 rounded-full bg-brand-primary\"></span>\r\n Series\r\n {:else}\r\n <span class=\"w-1.5 h-1.5 rounded-full bg-brand-primary\"></span>\r\n Collection\r\n {/if}\r\n {#if featuredItem.subtitle}\r\n <span class=\"text-muted-foreground\">·</span>\r\n {featuredItem.subtitle}\r\n {/if}\r\n </div>\r\n\r\n <h2 class=\"hero-title text-xl sm:text-2xl font-bold text-text-primary mb-2\">{featuredItem.title}</h2>\r\n\r\n {#if heroEvent}\r\n <p class=\"text-base text-text-secondary font-medium\">\r\n Next: {formatFullDate(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {#if heroEvent.startDateTime}\r\n at {formatEventTime(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {/if}\r\n </p>\r\n {/if}\r\n </div>\r\n </div>\r\n {:else if heroEvent}\r\n <!-- Single event hero -->\r\n <div\r\n class=\"featured-hero featured-hero-clickable rounded-lg border border-border bg-card overflow-hidden cursor-pointer hover:border-stroke-primary focus-visible:outline-2 focus-visible:outline-brand-primary:outline-brand-primary focus-visible:outline-offset-2\"\r\n onclick={handleClick}\r\n onkeydown={(e) => (e.key === 'Enter' || e.key === ' ') && handleClick()}\r\n tabindex=\"0\"\r\n role=\"button\"\r\n aria-label=\"{heroEvent.name}, {formatFullDate(heroEvent.startDateTime, heroEvent.timeZone)}. Press Enter to view details.\"\r\n >\r\n <div class=\"hero-image-container relative w-full bg-muted overflow-hidden\">\r\n <img\r\n src={heroEvent.image || PLACEHOLDER_IMAGE}\r\n alt=\"\"\r\n class=\"hero-image\"\r\n aria-hidden=\"true\"\r\n />\r\n </div>\r\n\r\n <div class=\"p-4 sm:p-5\" aria-hidden=\"true\">\r\n <h2 class=\"hero-title text-xl sm:text-2xl font-bold text-text-primary mb-2\">{heroEvent.name}</h2>\r\n\r\n <p class=\"text-base text-text-secondary font-medium\">\r\n {formatFullDate(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {#if heroEvent.startDateTime}\r\n <span class=\"text-muted-foreground mx-1\">·</span>\r\n {formatEventTime(heroEvent.startDateTime, heroEvent.timeZone)}\r\n {/if}\r\n </p>\r\n\r\n {#if heroEvent.description}\r\n <p class=\"hero-description text-sm text-text-secondary mt-2\">{heroEvent.description}</p>\r\n {/if}\r\n </div>\r\n </div>\r\n {:else}\r\n <!-- Empty state -->\r\n <div class=\"flex items-center justify-center py-12 rounded-lg border border-border bg-bg-secondary\">\r\n <p class=\"text-sm text-muted-foreground\">No upcoming events to feature</p>\r\n </div>\r\n {/if}\r\n</section>\r\n\r\n<style>\r\n .hero-image-container {\r\n aspect-ratio: 16 / 9;\r\n }\r\n\r\n .hero-image {\r\n width: 100%;\r\n height: 100%;\r\n object-fit: contain;\r\n }\r\n\r\n .hero-title {\r\n line-height: 1.3;\r\n }\r\n\r\n .featured-hero-clickable {\r\n transition: border-color 0.2s ease, box-shadow 0.2s ease;\r\n }\r\n\r\n .featured-hero-clickable:hover {\r\n box-shadow: 0 4px 12px color-mix(in srgb, black 10%, transparent);\r\n }\r\n\r\n .featured-hero-clickable:focus {\r\n outline: none;\r\n }\r\n\r\n .hero-description {\r\n display: -webkit-box;\r\n -webkit-line-clamp: 2;\r\n line-clamp: 2;\r\n -webkit-box-orient: vertical;\r\n overflow: hidden;\r\n }\r\n\r\n /* Reduced motion */\r\n @media (prefers-reduced-motion: reduce) {\r\n .featured-hero-clickable {\r\n transition: none;\r\n }\r\n }\r\n</style>\r\n"],"names":["events","$","$$props","featuredItem","futureEvents","filterTodayAndFuture","heroEvent","handleClick","section","root","div","root_1","div_1","root_2","img","div_2","root_3","$$render","consequent","alternate","div_3","node_1","div_4","consequent_1","alternate_1","text","consequent_2","h2","p","root_7","formatEventTime","consequent_3","formatFullDate","consequent_4","text_1","div_5","root_9","div_6","img_1","div_7","h2_1","p_1","consequent_6","p_2","root_11","text_7","consequent_7","$0","PLACEHOLDER_IMAGE","text_4","e","div_8","root_12","consequent_8","alternate_2"],"mappings":"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"}
@@ -1,6 +1,6 @@
1
1
  import "svelte/internal/disclose-version";
2
2
  import * as e from "svelte/internal/client";
3
- import { aP as Z, aQ as p, aT as A, aR as B, ah as C, a0 as b, ad as G, $ as L } from "./VenueCalendar-Blt02sO6.js";
3
+ import { aP as Z, aQ as p, aT as A, aR as B, ah as C, a0 as b, ad as G, $ as L } from "./VenueCalendar-H0gMPiFX.js";
4
4
  var O = e.from_html('<div class="badge-overlay svelte-18a25gb" aria-hidden="true"><span> </span></div>'), P = e.from_html('<div class="badge-overlay svelte-18a25gb" aria-hidden="true"><!></div>'), H = e.from_html("<time> </time>"), U = e.from_html('<span class="meta-separator svelte-18a25gb" aria-hidden="true">•</span> <span> </span>', 1), j = e.from_html('<a><div class="card-image-container svelte-18a25gb"><img alt="" class="card-image svelte-18a25gb" loading="lazy" aria-hidden="true"/> <!></div> <div class="card-content svelte-18a25gb" aria-hidden="true"><h3 class="card-title svelte-18a25gb"> </h3> <div class="card-meta svelte-18a25gb"><!> <!></div></div></a>');
5
5
  function I(h, i) {
6
6
  e.push(i, !0);
@@ -89,4 +89,4 @@ e.delegate(["click"]);
89
89
  export {
90
90
  I as G
91
91
  };
92
- //# sourceMappingURL=GalleryCard-Ccriw4rf.js.map
92
+ //# sourceMappingURL=GalleryCard-DdHqVAXD.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"GalleryCard-Ccriw4rf.js","sources":["../src/components/Calendar/GalleryCard.svelte"],"sourcesContent":["<script>\r\n import ScarcityBadge from \"../ScarcityBadge.svelte\";\r\n import { formatBrowseDate, formatFullDate, formatEventTime } from \"$lib/utils/datetime.js\";\r\n import { PLACEHOLDER_IMAGE } from \"$lib/utils/constants.js\";\r\n import { getBrowseStatus, isEventUnavailable } from \"$lib/utils/browse-status.js\";\r\n import { buildEventHref } from \"$lib/url-manager/params\";\r\n\r\n let { event, oneventClick, labels = {} } = $props();\r\n\r\n let browseStatus = $derived(getBrowseStatus(event));\r\n let isUnavailable = $derived(isEventUnavailable(browseStatus));\r\n\r\n // Build comprehensive aria-label for event card\r\n function getEventAriaLabel(event) {\r\n const parts = [event.name];\r\n if (event.startDateTime) {\r\n parts.push(`on ${formatFullDate(event.startDateTime, event.timeZone)}`);\r\n }\r\n if (event.startDateTime) {\r\n parts.push(`at ${formatEventTime(event.startDateTime, event.timeZone)}`);\r\n }\r\n if (browseStatus) {\r\n parts.push(browseStatus.text);\r\n } else if (event.status && event.status !== (labels.statusOnSale || 'On Sale')) {\r\n parts.push(event.status);\r\n }\r\n parts.push(labels.pressEnterToView || 'Press Enter to view details');\r\n return parts.join(', ');\r\n }\r\n</script>\r\n\r\n<a\r\n href={buildEventHref(event)}\r\n class=\"gallery-card\"\r\n class:card-unavailable={isUnavailable}\r\n onclick={(e) => { e.preventDefault(); oneventClick?.(event); }}\r\n aria-label={getEventAriaLabel(event)}\r\n>\r\n <!-- Fixed height image container -->\r\n <div class=\"card-image-container\">\r\n <!-- @component-image-escape: scoped-CSS selector targets this img; aria-hidden not supported by SC Image -->\r\n <img\r\n src={event.image || PLACEHOLDER_IMAGE}\r\n alt=\"\"\r\n class=\"card-image\"\r\n loading=\"lazy\"\r\n aria-hidden=\"true\"\r\n />\r\n <!-- Status Badge overlay -->\r\n {#if browseStatus}\r\n <div class=\"badge-overlay\" aria-hidden=\"true\">\r\n <span class=\"status-badge status-{browseStatus.type}\">{browseStatus.text}</span>\r\n </div>\r\n {:else if event.ticketsTotal > 0 || event.ticketsRemaining === 0}\r\n <div class=\"badge-overlay\" aria-hidden=\"true\">\r\n <ScarcityBadge\r\n remaining={event.ticketsRemaining ?? 0}\r\n total={event.ticketsTotal ?? 0}\r\n context=\"browse\"\r\n {labels}\r\n />\r\n </div>\r\n {/if}\r\n </div>\r\n\r\n <!-- Event Details -->\r\n <div class=\"card-content\" aria-hidden=\"true\">\r\n <h3 class=\"card-title\">{event.name}</h3>\r\n <div class=\"card-meta\">\r\n {#if event.startDateTime}\r\n <time datetime={event.startDateTime}>\r\n {formatBrowseDate(event.startDateTime, event.timeZone)}\r\n </time>\r\n {/if}\r\n {#if event.startDateTime}\r\n <span class=\"meta-separator\" aria-hidden=\"true\">•</span>\r\n <span>{formatEventTime(event.startDateTime, event.timeZone)}</span>\r\n {/if}\r\n </div>\r\n </div>\r\n</a>\r\n\r\n<style>\r\n /* @apply-escape: GalleryCard's component-scoped <style> block uses\r\n * @apply to extract repeated Tailwind utility combinations into\r\n * named component classes (card root, image wrapper, content\r\n * sections, hover/focus states). This is the canonical Tailwind v4\r\n * component-layer pattern — same shape as VC src/lib/styles/components.css.\r\n * Atlas css-style-cheats — file-level exempt per filterByFileLevelMarker.\r\n */\r\n @reference \"../../app.css\";\r\n\r\n .gallery-card {\r\n @apply rounded-lg border bg-card border-border;\r\n @apply overflow-hidden cursor-pointer block;\r\n\r\n text-decoration: none;\r\n color: inherit;\r\n transition: transform var(--motion-fast) var(--ease-out), box-shadow var(--motion-fast) var(--ease-out), border-color var(--motion-fast) var(--ease-out);\r\n }\r\n\r\n .gallery-card:hover {\r\n @apply border-stroke-primary;\r\n\r\n transform: translateY(-2px);\r\n box-shadow: 0 4px 12px color-mix(in srgb, black 10%, transparent);\r\n }\r\n\r\n .gallery-card:focus {\r\n @apply outline-none;\r\n }\r\n\r\n .gallery-card:focus-visible {\r\n @apply outline-2 outline-focus-ring outline-offset-2;\r\n }\r\n\r\n .gallery-card:active {\r\n transform: translateY(0);\r\n }\r\n\r\n /* Fixed height image container */\r\n .card-image-container {\r\n @apply relative w-full bg-muted overflow-hidden;\r\n\r\n height: 200px;\r\n }\r\n\r\n @media (width <= 639px) {\r\n .card-image-container {\r\n height: 220px;\r\n }\r\n }\r\n\r\n @media (width >= 1024px) {\r\n .card-image-container {\r\n height: 180px;\r\n }\r\n }\r\n\r\n .card-image {\r\n width: 100%;\r\n height: 100%;\r\n object-fit: contain;\r\n }\r\n\r\n .badge-overlay {\r\n position: absolute;\r\n top: 8px;\r\n left: 8px;\r\n }\r\n\r\n .card-content {\r\n @apply p-3;\r\n }\r\n\r\n @media (width >= 640px) {\r\n .card-content {\r\n @apply p-3.5;\r\n }\r\n }\r\n\r\n .card-title {\r\n @apply text-base font-semibold text-text-primary mb-1.5;\r\n\r\n line-height: 1.3;\r\n display: -webkit-box;\r\n -webkit-line-clamp: 2;\r\n line-clamp: 2;\r\n -webkit-box-orient: vertical;\r\n overflow: hidden;\r\n }\r\n\r\n @media (width <= 639px) {\r\n .card-title {\r\n @apply text-lg;\r\n }\r\n }\r\n\r\n .card-meta {\r\n @apply text-sm text-text-secondary font-medium;\r\n }\r\n\r\n @media (width <= 639px) {\r\n .card-meta {\r\n @apply text-base;\r\n }\r\n }\r\n\r\n .meta-separator {\r\n @apply text-muted-foreground mx-1;\r\n }\r\n\r\n /* Unavailable event dimming */\r\n .card-unavailable {\r\n @apply opacity-60;\r\n }\r\n\r\n .card-unavailable .card-image {\r\n filter: grayscale(0.5);\r\n }\r\n\r\n /* Status badges — distinct visual treatments for each status */\r\n .status-badge {\r\n @apply inline-flex items-center text-xs font-bold px-2.5 py-1 rounded;\r\n\r\n box-shadow: 0 2px 6px color-mix(in srgb, black 25%, transparent);\r\n letter-spacing: 0.02em;\r\n }\r\n\r\n .status-cancelled {\r\n @apply text-white bg-gradient-to-br from-rose-900 to-red-700;\r\n\r\n text-decoration: line-through;\r\n text-decoration-thickness: 1.5px;\r\n }\r\n\r\n .status-past {\r\n @apply text-muted-foreground bg-overlay-bg;\r\n\r\n backdrop-filter: blur(4px);\r\n }\r\n\r\n .status-sold_out {\r\n @apply text-white uppercase tracking-wider bg-gradient-to-br from-red-600 to-red-400;\r\n\r\n font-size: 0.65rem;\r\n }\r\n\r\n .status-sales_ended {\r\n @apply text-muted-foreground bg-bg-secondary/90 border border-stroke-primary/30;\r\n\r\n backdrop-filter: blur(4px);\r\n }\r\n\r\n .status-coming_soon {\r\n @apply text-white bg-gradient-to-br from-blue-600 to-indigo-500;\r\n }\r\n\r\n /* Reduced motion */\r\n @media (prefers-reduced-motion: reduce) {\r\n .gallery-card {\r\n transition: none;\r\n }\r\n\r\n .gallery-card:hover {\r\n transform: none;\r\n }\r\n }\r\n</style>\r\n"],"names":["labels","$","$$props","browseStatus","getBrowseStatus","isUnavailable","isEventUnavailable","getEventAriaLabel","event","parts","formatFullDate","formatEventTime","a","root","div","img","div_1","root_1","span","text","div_2","root_2","$0","$1","ScarcityBadge","node_1","$$render","consequent_1","div_3","h3","div_4","time","root_3","formatBrowseDate","consequent_2","span_1","fragment","consequent_3","classes","PLACEHOLDER_IMAGE","buildEventHref","e"],"mappings":";;;;iBAAA;;MAO6BA,IAAMC,EAAA,KAAAC,GAAA,UAAA,IAAA,OAAA,CAAA,EAAA,GAE7BC,oBAAwBC,EAAeF,EAAA,KAAA,CAAA,GACvCG,IAAaJ,EAAA,QAAA,MAAYK,EAAkBL,EAAA,IAACE,CAAY,CAAA,CAAA;WAGnDI,EAAkBC,GAAO;UAC1BC,IAAK,CAAID,EAAM,IAAI;WACrBA,EAAM,iBACRC,EAAM,KAAI,MAAOC,EAAeF,EAAM,eAAeA,EAAM,QAAQ,CAAA,EAAA,GAEjEA,EAAM,iBACRC,EAAM,KAAI,MAAOE,EAAgBH,EAAM,eAAeA,EAAM,QAAQ,CAAA,EAAA,GAElEP,EAAA,IAAAE,CAAY,IACdM,EAAM,KAAIR,EAAA,IAACE,CAAY,EAAC,IAAI,IACnBK,EAAM,UAAUA,EAAM,YAAYR,EAAM,EAAC,gBAAgB,cAClES,EAAM,KAAKD,EAAM,MAAM,GAEzBC,EAAM,KAAKT,IAAO,oBAAoB,6BAA6B,GAC5DS,EAAM,KAAK,IAAI;AAAA,EACxB;MAGDG,IAACC,EAAA;;AAQC,MAAAC,YARFF,CAAC,GAUGG,YAFFD,CAAG,iBAEDC,GAAG,CAAA;;;UASDC,IAAGC,EAAA,GACDC,YADFF,CAAG,eACDE,GAAI,EAAA;cAAJA,CAAI,WADNF,CAAG;oBACDE,GAAI,GAAA,uBAAAjB,EAAA,IAA6BE,CAAY,EAAC,QAAI,EAAA,IAAA,gBAAA,GAAIF,EAAA,SAAAkB,GAAAlB,EAAA,IAAAE,CAAY,EAAC,IAAI;AAAA,sBADzEa,CAAG;AAAA;UAIHI,IAAGC,EAAA,eAAHD,CAAG;;AAEiB,YAAAE,IAAArB,EAAA,QAAA,MAAAC,EAAA,MAAA,oBAAoB,CAAC,GACzBqB,IAAAtB,EAAA,QAAA,MAAAC,EAAA,MAAA,gBAAgB,CAAC;AAF/B,QAAAsB,EAAaC,GAAA;AAAA;;;;;;;;mBAIXzB,EAAM;AAAA;;;cALVoB,CAAG,eAAHA,CAAG;AAAA;;AALD,MAAAnB,EAAA,IAAAE,CAAY,oBAID,eAAe,KAACD,EAAA,MAAU,qBAAqB,MAACwB,EAAAC,GAAA,CAAA;AAAA;;UAdjEb,CAAG;AA2BH,MAAAc,cA3BAd,GAAG,CAAA,GA4BDe,YADFD,CAAG,eACDC,GAAE,EAAA;UAAFA,CAAE;AACF,MAAAC,cADAD,GAAE,CAAA,eACFC,CAAG;;;UAECC,IAAIC,EAAA,eAAJD,GAAI,EAAA;cAAJA,CAAI;;AAAJ,UAAA9B,EAAA,cAAA8B,uBAAqB,aAAa;;;gBAChCE,EAAgB/B,EAAA,MAAO,eAAaA,EAAA,MAAQ,QAAQ;AAAA;qBADtD6B,CAAI;AAAA;;cADI,iBAAaL,EAAAQ,CAAA;AAAA;;;;;mBAOrBC,IAAIlC,EAAA,QAAAA,EAAA,YAAAmC,CAAA,GAAA,CAAA,eAAJD,GAAI,EAAA;cAAJA,CAAI;cAAExB,EAAeT,EAAA,MAAO,eAAaA,EAAA,MAAQ,QAAQ;AAAA;;;cAFjD,iBAAawB,EAAAW,CAAA;AAAA;;UANzBP,CAAG,WAFLF,CAAG,WAnCLhB,CAAC;;sBAADA,GAAC,QAAAU,CAAA,GAADgB,IAAArC,EAAA,UAAAW,0EAGyBP,CAAa,EAAA,CAAA,mBAHtCO,GAAC,cAAAW,CAAA,mBAUGR,GAAG,OAAAb,EAAA,MACS,SAASqC,CAAiB,yBAyBT,IAAI;AAAA;;YAnC9BC,EAActC,EAAA,KAAA;AAAA,YAIRK,EAAiBL,EAAA,KAAA;AAAA;0BAL9BU,GAAC,CAIU6B,MAAM;AAAE,IAAAA,EAAE,eAAc;EAA2B,CAAC,eAJ/D7B,CAAC;AAFM;;"}
1
+ {"version":3,"file":"GalleryCard-DdHqVAXD.js","sources":["../src/components/Calendar/GalleryCard.svelte"],"sourcesContent":["<script>\r\n import ScarcityBadge from \"../ScarcityBadge.svelte\";\r\n import { formatBrowseDate, formatFullDate, formatEventTime } from \"$lib/utils/datetime.js\";\r\n import { PLACEHOLDER_IMAGE } from \"$lib/utils/constants.js\";\r\n import { getBrowseStatus, isEventUnavailable } from \"$lib/utils/browse-status.js\";\r\n import { buildEventHref } from \"$lib/url-manager/params\";\r\n\r\n let { event, oneventClick, labels = {} } = $props();\r\n\r\n let browseStatus = $derived(getBrowseStatus(event));\r\n let isUnavailable = $derived(isEventUnavailable(browseStatus));\r\n\r\n // Build comprehensive aria-label for event card\r\n function getEventAriaLabel(event) {\r\n const parts = [event.name];\r\n if (event.startDateTime) {\r\n parts.push(`on ${formatFullDate(event.startDateTime, event.timeZone)}`);\r\n }\r\n if (event.startDateTime) {\r\n parts.push(`at ${formatEventTime(event.startDateTime, event.timeZone)}`);\r\n }\r\n if (browseStatus) {\r\n parts.push(browseStatus.text);\r\n } else if (event.status && event.status !== (labels.statusOnSale || 'On Sale')) {\r\n parts.push(event.status);\r\n }\r\n parts.push(labels.pressEnterToView || 'Press Enter to view details');\r\n return parts.join(', ');\r\n }\r\n</script>\r\n\r\n<a\r\n href={buildEventHref(event)}\r\n class=\"gallery-card\"\r\n class:card-unavailable={isUnavailable}\r\n onclick={(e) => { e.preventDefault(); oneventClick?.(event); }}\r\n aria-label={getEventAriaLabel(event)}\r\n>\r\n <!-- Fixed height image container -->\r\n <div class=\"card-image-container\">\r\n <!-- @component-image-escape: scoped-CSS selector targets this img; aria-hidden not supported by SC Image -->\r\n <img\r\n src={event.image || PLACEHOLDER_IMAGE}\r\n alt=\"\"\r\n class=\"card-image\"\r\n loading=\"lazy\"\r\n aria-hidden=\"true\"\r\n />\r\n <!-- Status Badge overlay -->\r\n {#if browseStatus}\r\n <div class=\"badge-overlay\" aria-hidden=\"true\">\r\n <span class=\"status-badge status-{browseStatus.type}\">{browseStatus.text}</span>\r\n </div>\r\n {:else if event.ticketsTotal > 0 || event.ticketsRemaining === 0}\r\n <div class=\"badge-overlay\" aria-hidden=\"true\">\r\n <ScarcityBadge\r\n remaining={event.ticketsRemaining ?? 0}\r\n total={event.ticketsTotal ?? 0}\r\n context=\"browse\"\r\n {labels}\r\n />\r\n </div>\r\n {/if}\r\n </div>\r\n\r\n <!-- Event Details -->\r\n <div class=\"card-content\" aria-hidden=\"true\">\r\n <h3 class=\"card-title\">{event.name}</h3>\r\n <div class=\"card-meta\">\r\n {#if event.startDateTime}\r\n <time datetime={event.startDateTime}>\r\n {formatBrowseDate(event.startDateTime, event.timeZone)}\r\n </time>\r\n {/if}\r\n {#if event.startDateTime}\r\n <span class=\"meta-separator\" aria-hidden=\"true\">•</span>\r\n <span>{formatEventTime(event.startDateTime, event.timeZone)}</span>\r\n {/if}\r\n </div>\r\n </div>\r\n</a>\r\n\r\n<style>\r\n /* @apply-escape: GalleryCard's component-scoped <style> block uses\r\n * @apply to extract repeated Tailwind utility combinations into\r\n * named component classes (card root, image wrapper, content\r\n * sections, hover/focus states). This is the canonical Tailwind v4\r\n * component-layer pattern — same shape as VC src/lib/styles/components.css.\r\n * Atlas css-style-cheats — file-level exempt per filterByFileLevelMarker.\r\n */\r\n @reference \"../../app.css\";\r\n\r\n .gallery-card {\r\n @apply rounded-lg border bg-card border-border;\r\n @apply overflow-hidden cursor-pointer block;\r\n\r\n text-decoration: none;\r\n color: inherit;\r\n transition: transform var(--motion-fast) var(--ease-out), box-shadow var(--motion-fast) var(--ease-out), border-color var(--motion-fast) var(--ease-out);\r\n }\r\n\r\n .gallery-card:hover {\r\n @apply border-stroke-primary;\r\n\r\n transform: translateY(-2px);\r\n box-shadow: 0 4px 12px color-mix(in srgb, black 10%, transparent);\r\n }\r\n\r\n .gallery-card:focus {\r\n @apply outline-none;\r\n }\r\n\r\n .gallery-card:focus-visible {\r\n @apply outline-2 outline-focus-ring outline-offset-2;\r\n }\r\n\r\n .gallery-card:active {\r\n transform: translateY(0);\r\n }\r\n\r\n /* Fixed height image container */\r\n .card-image-container {\r\n @apply relative w-full bg-muted overflow-hidden;\r\n\r\n height: 200px;\r\n }\r\n\r\n @media (width <= 639px) {\r\n .card-image-container {\r\n height: 220px;\r\n }\r\n }\r\n\r\n @media (width >= 1024px) {\r\n .card-image-container {\r\n height: 180px;\r\n }\r\n }\r\n\r\n .card-image {\r\n width: 100%;\r\n height: 100%;\r\n object-fit: contain;\r\n }\r\n\r\n .badge-overlay {\r\n position: absolute;\r\n top: 8px;\r\n left: 8px;\r\n }\r\n\r\n .card-content {\r\n @apply p-3;\r\n }\r\n\r\n @media (width >= 640px) {\r\n .card-content {\r\n @apply p-3.5;\r\n }\r\n }\r\n\r\n .card-title {\r\n @apply text-base font-semibold text-text-primary mb-1.5;\r\n\r\n line-height: 1.3;\r\n display: -webkit-box;\r\n -webkit-line-clamp: 2;\r\n line-clamp: 2;\r\n -webkit-box-orient: vertical;\r\n overflow: hidden;\r\n }\r\n\r\n @media (width <= 639px) {\r\n .card-title {\r\n @apply text-lg;\r\n }\r\n }\r\n\r\n .card-meta {\r\n @apply text-sm text-text-secondary font-medium;\r\n }\r\n\r\n @media (width <= 639px) {\r\n .card-meta {\r\n @apply text-base;\r\n }\r\n }\r\n\r\n .meta-separator {\r\n @apply text-muted-foreground mx-1;\r\n }\r\n\r\n /* Unavailable event dimming */\r\n .card-unavailable {\r\n @apply opacity-60;\r\n }\r\n\r\n .card-unavailable .card-image {\r\n filter: grayscale(0.5);\r\n }\r\n\r\n /* Status badges — distinct visual treatments for each status */\r\n .status-badge {\r\n @apply inline-flex items-center text-xs font-bold px-2.5 py-1 rounded;\r\n\r\n box-shadow: 0 2px 6px color-mix(in srgb, black 25%, transparent);\r\n letter-spacing: 0.02em;\r\n }\r\n\r\n .status-cancelled {\r\n @apply text-white bg-gradient-to-br from-rose-900 to-red-700;\r\n\r\n text-decoration: line-through;\r\n text-decoration-thickness: 1.5px;\r\n }\r\n\r\n .status-past {\r\n @apply text-muted-foreground bg-overlay-bg;\r\n\r\n backdrop-filter: blur(4px);\r\n }\r\n\r\n .status-sold_out {\r\n @apply text-white uppercase tracking-wider bg-gradient-to-br from-red-600 to-red-400;\r\n\r\n font-size: 0.65rem;\r\n }\r\n\r\n .status-sales_ended {\r\n @apply text-muted-foreground bg-bg-secondary/90 border border-stroke-primary/30;\r\n\r\n backdrop-filter: blur(4px);\r\n }\r\n\r\n .status-coming_soon {\r\n @apply text-white bg-gradient-to-br from-blue-600 to-indigo-500;\r\n }\r\n\r\n /* Reduced motion */\r\n @media (prefers-reduced-motion: reduce) {\r\n .gallery-card {\r\n transition: none;\r\n }\r\n\r\n .gallery-card:hover {\r\n transform: none;\r\n }\r\n }\r\n</style>\r\n"],"names":["labels","$","$$props","browseStatus","getBrowseStatus","isUnavailable","isEventUnavailable","getEventAriaLabel","event","parts","formatFullDate","formatEventTime","a","root","div","img","div_1","root_1","span","text","div_2","root_2","$0","$1","ScarcityBadge","node_1","$$render","consequent_1","div_3","h3","div_4","time","root_3","formatBrowseDate","consequent_2","span_1","fragment","consequent_3","classes","PLACEHOLDER_IMAGE","buildEventHref","e"],"mappings":";;;;iBAAA;;MAO6BA,IAAMC,EAAA,KAAAC,GAAA,UAAA,IAAA,OAAA,CAAA,EAAA,GAE7BC,oBAAwBC,EAAeF,EAAA,KAAA,CAAA,GACvCG,IAAaJ,EAAA,QAAA,MAAYK,EAAkBL,EAAA,IAACE,CAAY,CAAA,CAAA;WAGnDI,EAAkBC,GAAO;UAC1BC,IAAK,CAAID,EAAM,IAAI;WACrBA,EAAM,iBACRC,EAAM,KAAI,MAAOC,EAAeF,EAAM,eAAeA,EAAM,QAAQ,CAAA,EAAA,GAEjEA,EAAM,iBACRC,EAAM,KAAI,MAAOE,EAAgBH,EAAM,eAAeA,EAAM,QAAQ,CAAA,EAAA,GAElEP,EAAA,IAAAE,CAAY,IACdM,EAAM,KAAIR,EAAA,IAACE,CAAY,EAAC,IAAI,IACnBK,EAAM,UAAUA,EAAM,YAAYR,EAAM,EAAC,gBAAgB,cAClES,EAAM,KAAKD,EAAM,MAAM,GAEzBC,EAAM,KAAKT,IAAO,oBAAoB,6BAA6B,GAC5DS,EAAM,KAAK,IAAI;AAAA,EACxB;MAGDG,IAACC,EAAA;;AAQC,MAAAC,YARFF,CAAC,GAUGG,YAFFD,CAAG,iBAEDC,GAAG,CAAA;;;UASDC,IAAGC,EAAA,GACDC,YADFF,CAAG,eACDE,GAAI,EAAA;cAAJA,CAAI,WADNF,CAAG;oBACDE,GAAI,GAAA,uBAAAjB,EAAA,IAA6BE,CAAY,EAAC,QAAI,EAAA,IAAA,gBAAA,GAAIF,EAAA,SAAAkB,GAAAlB,EAAA,IAAAE,CAAY,EAAC,IAAI;AAAA,sBADzEa,CAAG;AAAA;UAIHI,IAAGC,EAAA,eAAHD,CAAG;;AAEiB,YAAAE,IAAArB,EAAA,QAAA,MAAAC,EAAA,MAAA,oBAAoB,CAAC,GACzBqB,IAAAtB,EAAA,QAAA,MAAAC,EAAA,MAAA,gBAAgB,CAAC;AAF/B,QAAAsB,EAAaC,GAAA;AAAA;;;;;;;;mBAIXzB,EAAM;AAAA;;;cALVoB,CAAG,eAAHA,CAAG;AAAA;;AALD,MAAAnB,EAAA,IAAAE,CAAY,oBAID,eAAe,KAACD,EAAA,MAAU,qBAAqB,MAACwB,EAAAC,GAAA,CAAA;AAAA;;UAdjEb,CAAG;AA2BH,MAAAc,cA3BAd,GAAG,CAAA,GA4BDe,YADFD,CAAG,eACDC,GAAE,EAAA;UAAFA,CAAE;AACF,MAAAC,cADAD,GAAE,CAAA,eACFC,CAAG;;;UAECC,IAAIC,EAAA,eAAJD,GAAI,EAAA;cAAJA,CAAI;;AAAJ,UAAA9B,EAAA,cAAA8B,uBAAqB,aAAa;;;gBAChCE,EAAgB/B,EAAA,MAAO,eAAaA,EAAA,MAAQ,QAAQ;AAAA;qBADtD6B,CAAI;AAAA;;cADI,iBAAaL,EAAAQ,CAAA;AAAA;;;;;mBAOrBC,IAAIlC,EAAA,QAAAA,EAAA,YAAAmC,CAAA,GAAA,CAAA,eAAJD,GAAI,EAAA;cAAJA,CAAI;cAAExB,EAAeT,EAAA,MAAO,eAAaA,EAAA,MAAQ,QAAQ;AAAA;;;cAFjD,iBAAawB,EAAAW,CAAA;AAAA;;UANzBP,CAAG,WAFLF,CAAG,WAnCLhB,CAAC;;sBAADA,GAAC,QAAAU,CAAA,GAADgB,IAAArC,EAAA,UAAAW,0EAGyBP,CAAa,EAAA,CAAA,mBAHtCO,GAAC,cAAAW,CAAA,mBAUGR,GAAG,OAAAb,EAAA,MACS,SAASqC,CAAiB,yBAyBT,IAAI;AAAA;;YAnC9BC,EAActC,EAAA,KAAA;AAAA,YAIRK,EAAiBL,EAAA,KAAA;AAAA;0BAL9BU,GAAC,CAIU6B,MAAM;AAAE,IAAAA,EAAE,eAAc;EAA2B,CAAC,eAJ/D7B,CAAC;AAFM;;"}
@@ -1,8 +1,8 @@
1
1
  import "svelte/internal/disclose-version";
2
2
  import * as e from "svelte/internal/client";
3
3
  import { onMount as C, onDestroy as M } from "svelte";
4
- import { G as x } from "./GalleryCard-Ccriw4rf.js";
5
- import { aX as k } from "./VenueCalendar-Blt02sO6.js";
4
+ import { G as x } from "./GalleryCard-DdHqVAXD.js";
5
+ import { aX as k } from "./VenueCalendar-H0gMPiFX.js";
6
6
  var w = e.from_html('<li class="list-none"><!></li>'), E = e.from_html('<div class="flex items-center justify-center gap-2 py-2 p-6" role="status" aria-live="polite"><span class="text-sm text-muted-foreground">Loading more events...</span></div>'), G = e.from_html('<section class="w-full" aria-label="Events gallery"><h2 class="sr-only svelte-lb0ck7">Upcoming events</h2> <ul class="grid grid-cols-1 gap-4 bg-bg-secondary p-2 sm:grid-cols-2 sm:gap-4 sm:p-3 md:grid-cols-3 md:gap-5 md:p-4 lg:grid-cols-4 lg:gap-6 lg:p-5" role="list"></ul> <!></section>');
7
7
  function D(v, i) {
8
8
  e.push(i, !0);
@@ -49,4 +49,4 @@ function D(v, i) {
49
49
  export {
50
50
  D as default
51
51
  };
52
- //# sourceMappingURL=GalleryView.legacy-9yQBBGk4.js.map
52
+ //# sourceMappingURL=GalleryView.legacy-F46Bwi9x.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"GalleryView.legacy-9yQBBGk4.js","sources":["../src/components/Calendar/GalleryView.legacy.svelte"],"sourcesContent":["<script>\r\n // @ts-nocheck legacy fallback (legacy=1 path), slated for deletion after VC finalization — not type-maintained\r\n import { onMount, onDestroy } from \"svelte\";\r\n import GalleryCard from \"./GalleryCard.svelte\";\r\n import { filterTodayAndFuture } from \"$lib/utils/browse-status.js\";\r\n\r\n let { events = [], initialCount = 12, loadMoreCount = 12, oneventClick } = $props();\r\n\r\n let displayedCount = initialCount;\r\n let loadMoreTrigger;\r\n let observer;\r\n\r\n // Filter to today and future, sorted chronologically\r\n let futureEvents = $derived(filterTodayAndFuture(events));\r\n let displayedEvents = $derived(futureEvents.slice(0, displayedCount));\r\n let hasMore = $derived(displayedCount < futureEvents.length);\r\n\r\n function loadMore() {\r\n displayedCount += loadMoreCount;\r\n }\r\n\r\n onMount(() => {\r\n observer = new IntersectionObserver(\r\n (entries) => {\r\n if (entries[0].isIntersecting && hasMore) {\r\n loadMore();\r\n }\r\n },\r\n { rootMargin: '100px' }\r\n );\r\n\r\n if (loadMoreTrigger) {\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n\r\n onDestroy(() => {\r\n if (observer) {\r\n observer.disconnect();\r\n }\r\n });\r\n\r\n // Re-observe when trigger element changes\r\n $effect(() => {\r\n if (observer && loadMoreTrigger) {\r\n observer.disconnect();\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n</script>\r\n\r\n<section class=\"w-full\" aria-label=\"Events gallery\">\r\n <h2 class=\"sr-only\">Upcoming events</h2>\r\n <ul class=\"grid grid-cols-1 gap-4 bg-bg-secondary p-2 sm:grid-cols-2 sm:gap-4 sm:p-3 md:grid-cols-3 md:gap-5 md:p-4 lg:grid-cols-4 lg:gap-6 lg:p-5\" role=\"list\">\r\n {#each displayedEvents as event}\r\n <li class=\"list-none\">\r\n <GalleryCard {event} {oneventClick} />\r\n </li>\r\n {/each}\r\n </ul>\r\n\r\n <!-- Infinite scroll trigger -->\r\n {#if hasMore}\r\n <div bind:this={loadMoreTrigger} class=\"flex items-center justify-center gap-2 py-2 p-6\" role=\"status\" aria-live=\"polite\">\r\n <span class=\"text-sm text-muted-foreground\">Loading more events...</span>\r\n </div>\r\n {/if}\r\n</section>\r\n\r\n<style>\r\n /* Screen reader only text */\r\n .sr-only {\r\n position: absolute;\r\n width: 1px;\r\n height: 1px;\r\n padding: 0;\r\n margin: -1px;\r\n overflow: hidden;\r\n clip: rect(0, 0, 0, 0);\r\n white-space: nowrap;\r\n border-width: 0;\r\n }\r\n</style>\r\n"],"names":["events","$","$$props","initialCount","loadMoreCount","displayedCount","loadMoreTrigger","observer","futureEvents","filterTodayAndFuture","displayedEvents","hasMore","loadMore","onMount","entries","onDestroy","section","root","ul","$$anchor","event","li","root_1","GalleryCard","node","div","root_2","$$value","$$render","consequent"],"mappings":";;;;;;iBAAA;;MAMQA,IAAMC,EAAA,KAAAC,GAAA,UAAA,IAAA,MAAA,EAAA,GAAOC,iCAAe,EAAE,GAAEC,kCAAgB,EAAE,GAEpDC,IAAiBF,EAAY,GAC7BG,GACAC,GAGAC,IAAYP,EAAA,QAAA,MAAYQ,EAAqBT,EAAM,CAAA,CAAA,GACnDU,0BAA2BF,CAAY,EAAC,MAAM,GAAGH,CAAc,CAAA,GAC/DM,IAAOV,EAAA,QAAA,MAAYI,IAAcJ,EAAA,IAAGO,CAAY,EAAC,MAAM;AAElD,WAAAI,IAAW;AAClB,IAAAP,KAAkBD,EAAa;AAAA,EACjC;AAEA,EAAAS,QAAc;AACZ,IAAAN,QAAe;AAAA,MACZ,CAAAO,MAAY;AACP,QAAAA,EAAQ,CAAC,EAAE,kBAAcb,EAAA,IAAIU,CAAO,KACtCC,EAAQ;AAAA,MAEZ;AAAA,MACE,EAAA,YAAY,QAAO;AAAA,OAGnBN,KACFC,EAAS,QAAQD,CAAe;AAAA,EAEpC,CAAC,GAEDS,QAAgB;AACV,IAAAR,KACFA,EAAS,WAAU;AAAA,EAEvB,CAAC,GAGDN,EAAA,kBAAc;IACRM,KAAYD,MACdC,EAAS,WAAU,GACnBA,EAAS,QAAQD,CAAe;AAAA,EAEpC,CAAC;MAGFU,IAAOC,EAAA,GAELC,sBAFFF,CAAO,GAAA,CAAA;SAELE,GAAE,IAAA,MAAAjB,EAAA,IACMS,CAAe,GAAAT,EAAA,OAAA,CAAAkB,GAAIC,MAAK;QAC5BC,IAAEC,EAAA,eAAFD,CAAE;AACA,IAAAE,EAAWC,GAAA;AAAA;qBAAEJ,CAAK;AAAA;;;;gBADpBC,CAAE,eAAFA,CAAE;AAAA,cAFNH,CAAE;oBAAFA,GAAE,CAAA;;;UAUAO,IAAGC,EAAA;kBAAHD,GAAG,CAAAE,MAAYrB,IAAeqB,GAAA,MAAfrB,CAAe,eAA9BmB,CAAG;AAAA;;YADDd,CAAO,KAAAiB,EAAAC,CAAA;AAAA;;UAXbb,CAAO,eAAPA,CAAO;AAFA;"}
1
+ {"version":3,"file":"GalleryView.legacy-F46Bwi9x.js","sources":["../src/components/Calendar/GalleryView.legacy.svelte"],"sourcesContent":["<script>\r\n // @ts-nocheck legacy fallback (legacy=1 path), slated for deletion after VC finalization — not type-maintained\r\n import { onMount, onDestroy } from \"svelte\";\r\n import GalleryCard from \"./GalleryCard.svelte\";\r\n import { filterTodayAndFuture } from \"$lib/utils/browse-status.js\";\r\n\r\n let { events = [], initialCount = 12, loadMoreCount = 12, oneventClick } = $props();\r\n\r\n let displayedCount = initialCount;\r\n let loadMoreTrigger;\r\n let observer;\r\n\r\n // Filter to today and future, sorted chronologically\r\n let futureEvents = $derived(filterTodayAndFuture(events));\r\n let displayedEvents = $derived(futureEvents.slice(0, displayedCount));\r\n let hasMore = $derived(displayedCount < futureEvents.length);\r\n\r\n function loadMore() {\r\n displayedCount += loadMoreCount;\r\n }\r\n\r\n onMount(() => {\r\n observer = new IntersectionObserver(\r\n (entries) => {\r\n if (entries[0].isIntersecting && hasMore) {\r\n loadMore();\r\n }\r\n },\r\n { rootMargin: '100px' }\r\n );\r\n\r\n if (loadMoreTrigger) {\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n\r\n onDestroy(() => {\r\n if (observer) {\r\n observer.disconnect();\r\n }\r\n });\r\n\r\n // Re-observe when trigger element changes\r\n $effect(() => {\r\n if (observer && loadMoreTrigger) {\r\n observer.disconnect();\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n</script>\r\n\r\n<section class=\"w-full\" aria-label=\"Events gallery\">\r\n <h2 class=\"sr-only\">Upcoming events</h2>\r\n <ul class=\"grid grid-cols-1 gap-4 bg-bg-secondary p-2 sm:grid-cols-2 sm:gap-4 sm:p-3 md:grid-cols-3 md:gap-5 md:p-4 lg:grid-cols-4 lg:gap-6 lg:p-5\" role=\"list\">\r\n {#each displayedEvents as event}\r\n <li class=\"list-none\">\r\n <GalleryCard {event} {oneventClick} />\r\n </li>\r\n {/each}\r\n </ul>\r\n\r\n <!-- Infinite scroll trigger -->\r\n {#if hasMore}\r\n <div bind:this={loadMoreTrigger} class=\"flex items-center justify-center gap-2 py-2 p-6\" role=\"status\" aria-live=\"polite\">\r\n <span class=\"text-sm text-muted-foreground\">Loading more events...</span>\r\n </div>\r\n {/if}\r\n</section>\r\n\r\n<style>\r\n /* Screen reader only text */\r\n .sr-only {\r\n position: absolute;\r\n width: 1px;\r\n height: 1px;\r\n padding: 0;\r\n margin: -1px;\r\n overflow: hidden;\r\n clip: rect(0, 0, 0, 0);\r\n white-space: nowrap;\r\n border-width: 0;\r\n }\r\n</style>\r\n"],"names":["events","$","$$props","initialCount","loadMoreCount","displayedCount","loadMoreTrigger","observer","futureEvents","filterTodayAndFuture","displayedEvents","hasMore","loadMore","onMount","entries","onDestroy","section","root","ul","$$anchor","event","li","root_1","GalleryCard","node","div","root_2","$$value","$$render","consequent"],"mappings":";;;;;;iBAAA;;MAMQA,IAAMC,EAAA,KAAAC,GAAA,UAAA,IAAA,MAAA,EAAA,GAAOC,iCAAe,EAAE,GAAEC,kCAAgB,EAAE,GAEpDC,IAAiBF,EAAY,GAC7BG,GACAC,GAGAC,IAAYP,EAAA,QAAA,MAAYQ,EAAqBT,EAAM,CAAA,CAAA,GACnDU,0BAA2BF,CAAY,EAAC,MAAM,GAAGH,CAAc,CAAA,GAC/DM,IAAOV,EAAA,QAAA,MAAYI,IAAcJ,EAAA,IAAGO,CAAY,EAAC,MAAM;AAElD,WAAAI,IAAW;AAClB,IAAAP,KAAkBD,EAAa;AAAA,EACjC;AAEA,EAAAS,QAAc;AACZ,IAAAN,QAAe;AAAA,MACZ,CAAAO,MAAY;AACP,QAAAA,EAAQ,CAAC,EAAE,kBAAcb,EAAA,IAAIU,CAAO,KACtCC,EAAQ;AAAA,MAEZ;AAAA,MACE,EAAA,YAAY,QAAO;AAAA,OAGnBN,KACFC,EAAS,QAAQD,CAAe;AAAA,EAEpC,CAAC,GAEDS,QAAgB;AACV,IAAAR,KACFA,EAAS,WAAU;AAAA,EAEvB,CAAC,GAGDN,EAAA,kBAAc;IACRM,KAAYD,MACdC,EAAS,WAAU,GACnBA,EAAS,QAAQD,CAAe;AAAA,EAEpC,CAAC;MAGFU,IAAOC,EAAA,GAELC,sBAFFF,CAAO,GAAA,CAAA;SAELE,GAAE,IAAA,MAAAjB,EAAA,IACMS,CAAe,GAAAT,EAAA,OAAA,CAAAkB,GAAIC,MAAK;QAC5BC,IAAEC,EAAA,eAAFD,CAAE;AACA,IAAAE,EAAWC,GAAA;AAAA;qBAAEJ,CAAK;AAAA;;;;gBADpBC,CAAE,eAAFA,CAAE;AAAA,cAFNH,CAAE;oBAAFA,GAAE,CAAA;;;UAUAO,IAAGC,EAAA;kBAAHD,GAAG,CAAAE,MAAYrB,IAAeqB,GAAA,MAAfrB,CAAe,eAA9BmB,CAAG;AAAA;;YADDd,CAAO,KAAAiB,EAAAC,CAAA;AAAA;;UAXbb,CAAO,eAAPA,CAAO;AAFA;"}
@@ -1,7 +1,7 @@
1
1
  import "svelte/internal/disclose-version";
2
2
  import * as e from "svelte/internal/client";
3
3
  import { onMount as te, onDestroy as ae } from "svelte";
4
- import { aX as re, aY as se, aP as ie, aQ as le, aT as ne, ah as F, a0 as L, ad as oe } from "./VenueCalendar-Blt02sO6.js";
4
+ import { aX as re, aY as se, aP as ie, aQ as le, aT as ne, ah as F, a0 as L, ad as oe } from "./VenueCalendar-H0gMPiFX.js";
5
5
  var de = e.from_html('<div class="w-16 min-w-16 py-4 px-2.5 flex flex-col items-center justify-start bg-bg-secondary border-r border-border max-sm:w-12 max-sm:min-w-12 max-sm:py-2.5 max-sm:px-1.5" aria-hidden="true"><span class="text-xs font-semibold text-text-secondary uppercase tracking-tight"> </span> <span class="text-2xl max-sm:text-lg font-bold text-text-primary leading-tight"> </span> <span class="text-xs font-semibold text-text-secondary uppercase tracking-tight"> </span></div>'), me = e.from_html('<p class="event-description text-sm text-text-secondary mt-1.5 mb-0 line-clamp-2 max-sm:hidden svelte-r2wh13"> </p>'), ce = e.from_html("<span> </span>"), ge = e.from_html('<li class="list-none"><div tabindex="0" role="button"><div class="w-36 h-24 min-w-36 max-sm:w-20 max-sm:h-16 max-sm:min-w-20 rounded-lg overflow-hidden bg-bg-secondary flex items-center justify-center" aria-hidden="true"><img alt="" class="w-full h-full object-contain svelte-r2wh13" loading="lazy"/></div> <div class="flex-1 flex flex-col gap-1.5 min-w-0" aria-hidden="true"><h3 class="text-lg max-sm:text-sm font-semibold text-text-primary m-0 leading-snug"> </h3> <time class="text-sm max-sm:text-xs font-medium text-text-secondary"> </time> <!></div> <div class="flex items-start pt-0.5" aria-hidden="true"><!></div></div></li>'), fe = e.from_html('<div class="date-group flex border-b border-border last:border-b-0 svelte-r2wh13" role="group"><!> <ul class="events-column flex-1 flex flex-col list-none p-0 m-0 svelte-r2wh13"></ul></div>'), ve = e.from_html('<div class="flex justify-center items-center p-6 text-text-secondary" role="status" aria-live="polite"><span class="text-sm">Loading more events...</span></div>'), ue = e.from_html('<section aria-label="Event listings"><h2 class="sr-only svelte-r2wh13">Event list grouped by date</h2> <!> <!></section>');
6
6
  function he(P, m) {
7
7
  e.push(m, !0);
@@ -141,4 +141,4 @@ e.delegate(["click", "keydown"]);
141
141
  export {
142
142
  he as default
143
143
  };
144
- //# sourceMappingURL=GroupedListView.legacy-DjmtlEHN.js.map
144
+ //# sourceMappingURL=GroupedListView.legacy-CLnOs7Ls.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"GroupedListView.legacy-DjmtlEHN.js","sources":["../src/components/Calendar/GroupedListView.legacy.svelte"],"sourcesContent":["<script>\r\n // @ts-nocheck legacy fallback (legacy=1 path), slated for deletion after VC finalization — not type-maintained\r\n import { onMount, onDestroy } from \"svelte\";\r\n import { PLACEHOLDER_IMAGE } from \"$lib/utils/constants.js\";\r\n import { getDateParts, formatFullDate, formatEventTime } from \"$lib/utils/datetime.js\";\r\n import { getBrowseStatus, isEventUnavailable, filterTodayAndFuture } from \"$lib/utils/browse-status.js\";\r\n import ScarcityBadge from \"../ScarcityBadge.svelte\";\r\n\r\n let {\r\n events = [],\r\n initialCount = 10,\r\n loadMoreCount = 10,\r\n showDateColumn = true,\r\n filterFutureOnly = true,\r\n oneventClick\r\n } = $props();\r\n\r\n let displayedCount = initialCount;\r\n let loadMoreTrigger;\r\n let observer;\r\n\r\n // Filter to today and future (if enabled), then group by date\r\n let filteredEvents = $derived(filterFutureOnly ? filterTodayAndFuture(events) : events);\r\n let groupedEvents = $derived(groupEventsByDate(filteredEvents.slice(0, displayedCount)));\r\n let hasMore = $derived(displayedCount < filteredEvents.length);\r\n\r\n function loadMore() {\r\n displayedCount += loadMoreCount;\r\n }\r\n\r\n onMount(() => {\r\n observer = new IntersectionObserver(\r\n (entries) => {\r\n if (entries[0].isIntersecting && hasMore) {\r\n loadMore();\r\n }\r\n },\r\n { rootMargin: '100px' }\r\n );\r\n\r\n if (loadMoreTrigger) {\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n\r\n onDestroy(() => {\r\n if (observer) {\r\n observer.disconnect();\r\n }\r\n });\r\n\r\n // Re-observe when trigger element changes\r\n $effect(() => {\r\n if (observer && loadMoreTrigger) {\r\n observer.disconnect();\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n\r\n function groupEventsByDate(eventList) {\r\n const groups = {};\r\n\r\n for (const event of eventList) {\r\n const dateKey = event.date; // YYYY-MM-DD format\r\n if (!groups[dateKey]) {\r\n groups[dateKey] = [];\r\n }\r\n groups[dateKey].push(event);\r\n }\r\n\r\n // Convert to array sorted by date\r\n return Object.entries(groups)\r\n .sort(([a], [b]) => new Date(a) - new Date(b))\r\n .map(([date, events]) => ({\r\n date,\r\n events,\r\n formattedDate: formatGroupDate(events),\r\n }));\r\n }\r\n\r\n function formatGroupDate(events) {\r\n // Use the first event in the group to get timezone-aware date parts\r\n const firstEvent = events[0];\r\n if (!firstEvent?.startDateTime) return { month: '', day: '', weekday: '' };\r\n const parts = getDateParts(firstEvent.startDateTime, firstEvent.timeZone);\r\n return {\r\n month: parts.month.toUpperCase(),\r\n day: String(parts.date).padStart(2, '0'),\r\n weekday: parts.day.toUpperCase(),\r\n };\r\n }\r\n\r\n function handleEventClick(event) {\r\n oneventClick?.(event);\r\n }\r\n\r\n function handleKeydown(e, event) {\r\n if (e.key === 'Enter' || e.key === ' ') {\r\n e.preventDefault();\r\n handleEventClick(event);\r\n }\r\n }\r\n</script>\r\n\r\n<section class=\"flex flex-col gap-0\" class:no-date-column={!showDateColumn} aria-label=\"Event listings\">\r\n <h2 class=\"sr-only\">Event list grouped by date</h2>\r\n {#each groupedEvents as group}\r\n <div class=\"date-group flex border-b border-border last:border-b-0\" role=\"group\" aria-label=\"Events on {group.events[0]?.startDateTime ? formatFullDate(group.events[0].startDateTime, group.events[0].timeZone) : group.date}\">\r\n <!-- Date Column -->\r\n {#if showDateColumn}\r\n <div class=\"w-16 min-w-16 py-4 px-2.5 flex flex-col items-center justify-start bg-bg-secondary border-r border-border max-sm:w-12 max-sm:min-w-12 max-sm:py-2.5 max-sm:px-1.5\" aria-hidden=\"true\">\r\n <span class=\"text-xs font-semibold text-text-secondary uppercase tracking-tight\">{group.formattedDate.month}</span>\r\n <span class=\"text-2xl max-sm:text-lg font-bold text-text-primary leading-tight\">{group.formattedDate.day}</span>\r\n <span class=\"text-xs font-semibold text-text-secondary uppercase tracking-tight\">{group.formattedDate.weekday}</span>\r\n </div>\r\n {/if}\r\n\r\n <!-- Events Column -->\r\n <ul class=\"events-column flex-1 flex flex-col list-none p-0 m-0\">\r\n {#each group.events as event, eventIndex}\r\n {@const eventStatus = getBrowseStatus(event)}\r\n {@const isUnavailable = isEventUnavailable(eventStatus)}\r\n <li class=\"list-none\">\r\n <div\r\n class=\"event-row flex gap-4 max-sm:gap-2.5 p-5 max-sm:p-3 cursor-pointer transition-colors duration-150 bg-card border-b border-border/50 last:border-b-0 hover:bg-bg-secondary focus:outline-2 focus:outline-brand-primary focus:-outline-offset-2 focus-visible:outline-2 focus-visible:outline-brand-primary:outline-brand-primary focus-visible:-outline-offset-2\"\r\n class:row-unavailable={isUnavailable}\r\n onclick={() => handleEventClick(event)}\r\n onkeydown={(e) => handleKeydown(e, event)}\r\n tabindex=\"0\"\r\n role=\"button\"\r\n aria-label={`${event.name} on ${event.startDateTime ? formatFullDate(event.startDateTime, event.timeZone) : group.date} at ${event.startDateTime ? formatEventTime(event.startDateTime, event.timeZone) : ''}, ${eventStatus?.text || event.status || 'On Sale'}. Press Enter to view details.`}\r\n >\r\n <!-- Event Image -->\r\n <div class=\"w-36 h-24 min-w-36 max-sm:w-20 max-sm:h-16 max-sm:min-w-20 rounded-lg overflow-hidden bg-bg-secondary flex items-center justify-center\" aria-hidden=\"true\">\r\n <img\r\n src={event.image || PLACEHOLDER_IMAGE}\r\n alt=\"\"\r\n class=\"w-full h-full object-contain\"\r\n loading=\"lazy\"\r\n />\r\n </div>\r\n\r\n <!-- Event Details (visually shown but also in aria-label, so hide from SR) -->\r\n <div class=\"flex-1 flex flex-col gap-1.5 min-w-0\" aria-hidden=\"true\">\r\n <h3 class=\"text-lg max-sm:text-sm font-semibold text-text-primary m-0 leading-snug\">{event.name}</h3>\r\n <time class=\"text-sm max-sm:text-xs font-medium text-text-secondary\" datetime={event.startDateTime || group.date}>{event.startDateTime ? formatEventTime(event.startDateTime, event.timeZone) : ''}</time>\r\n {#if event.description}\r\n <p class=\"event-description text-sm text-text-secondary mt-1.5 mb-0 line-clamp-2 max-sm:hidden\">{event.description}</p>\r\n {/if}\r\n </div>\r\n\r\n <!-- Status / Scarcity Badge -->\r\n <div class=\"flex items-start pt-0.5\" aria-hidden=\"true\">\r\n {#if eventStatus}\r\n <span class=\"status-badge status-{eventStatus.type}\">{eventStatus.text}</span>\r\n {:else if event.ticketsTotal > 0 || event.ticketsRemaining === 0}\r\n <ScarcityBadge\r\n remaining={event.ticketsRemaining ?? 0}\r\n total={event.ticketsTotal ?? 0}\r\n context=\"browse\"\r\n />\r\n {/if}\r\n </div>\r\n </div>\r\n </li>\r\n {/each}\r\n </ul>\r\n </div>\r\n {/each}\r\n\r\n <!-- Infinite scroll trigger -->\r\n {#if hasMore}\r\n <div bind:this={loadMoreTrigger} class=\"flex justify-center items-center p-6 text-text-secondary\" role=\"status\" aria-live=\"polite\">\r\n <span class=\"text-sm\">Loading more events...</span>\r\n </div>\r\n {/if}\r\n</section>\r\n\r\n<style>\r\n /* When no date column, remove left border styling */\r\n .no-date-column .date-group {\r\n border-bottom: 0;\r\n }\r\n\r\n .no-date-column .events-column {\r\n border-left: 0;\r\n }\r\n\r\n .event-description {\r\n display: -webkit-box;\r\n -webkit-box-orient: vertical;\r\n overflow: hidden;\r\n }\r\n\r\n /* Unavailable row dimming */\r\n .row-unavailable {\r\n opacity: 0.6;\r\n }\r\n\r\n .row-unavailable img {\r\n filter: grayscale(0.5);\r\n }\r\n\r\n /* Status badges -- distinct visual treatments matching gallery cards */\r\n .status-badge {\r\n display: inline-flex;\r\n align-items: center;\r\n font-size: 0.75rem;\r\n line-height: 1rem;\r\n font-weight: 700;\r\n padding: 0.25rem 0.625rem;\r\n border-radius: 0.25rem;\r\n white-space: nowrap;\r\n letter-spacing: 0.02em;\r\n }\r\n\r\n .status-cancelled {\r\n background-color: hsl(var(--accent-danger) / 10%);\r\n color: hsl(var(--accent-danger));\r\n text-decoration: line-through;\r\n text-decoration-thickness: 1.5px;\r\n\r\n \r\n }\r\n\r\n .status-past {\r\n background-color: hsl(var(--bg-tertiary));\r\n color: hsl(var(--text-tertiary));\r\n\r\n \r\n }\r\n\r\n .status-sold_out {\r\n background-color: hsl(var(--accent-danger) / 10%);\r\n color: hsl(var(--accent-danger));\r\n text-transform: uppercase;\r\n letter-spacing: 0.05em;\r\n font-size: 0.65rem;\r\n\r\n \r\n }\r\n\r\n .status-sales_ended {\r\n background-color: hsl(var(--bg-tertiary));\r\n color: hsl(var(--text-tertiary));\r\n border: 1px solid hsl(var(--stroke-primary));\r\n\r\n \r\n }\r\n\r\n .status-coming_soon {\r\n background-color: hsl(var(--brand-primary) / 15%);\r\n color: hsl(var(--brand-primary));\r\n\r\n \r\n }\r\n\r\n /* Reduced motion */\r\n @media (prefers-reduced-motion: reduce) {\r\n .event-row {\r\n transition: none;\r\n }\r\n }\r\n\r\n /* Screen reader only text */\r\n .sr-only {\r\n position: absolute;\r\n width: 1px;\r\n height: 1px;\r\n padding: 0;\r\n margin: -1px;\r\n overflow: hidden;\r\n clip: rect(0, 0, 0, 0);\r\n white-space: nowrap;\r\n border-width: 0;\r\n }\r\n</style>\r\n"],"names":["events","$","$$props","initialCount","loadMoreCount","showDateColumn","filterFutureOnly","displayedCount","loadMoreTrigger","observer","filteredEvents","filterTodayAndFuture","groupedEvents","groupEventsByDate","hasMore","loadMore","onMount","entries","onDestroy","eventList","groups","event","dateKey","a","b","date","formatGroupDate","firstEvent","parts","getDateParts","handleEventClick","handleKeydown","e","section","root","node","group","div","root_1","div_1","root_2","span","span_1","span_2","$$render","consequent","ul","node_1","eventStatus","getBrowseStatus","isUnavailable","isEventUnavailable","li","root_3","div_2","div_3","img","div_4","h3","time","p","root_4","text_5","consequent_1","div_5","span_3","root_5","text_6","ScarcityBadge","$$anchor","consequent_2","consequent_3","classes_1","$0","PLACEHOLDER_IMAGE","text_3","formatFullDate","formatEventTime","div_6","root_7","$$value","consequent_4","classes"],"mappings":"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"}
1
+ {"version":3,"file":"GroupedListView.legacy-CLnOs7Ls.js","sources":["../src/components/Calendar/GroupedListView.legacy.svelte"],"sourcesContent":["<script>\r\n // @ts-nocheck legacy fallback (legacy=1 path), slated for deletion after VC finalization — not type-maintained\r\n import { onMount, onDestroy } from \"svelte\";\r\n import { PLACEHOLDER_IMAGE } from \"$lib/utils/constants.js\";\r\n import { getDateParts, formatFullDate, formatEventTime } from \"$lib/utils/datetime.js\";\r\n import { getBrowseStatus, isEventUnavailable, filterTodayAndFuture } from \"$lib/utils/browse-status.js\";\r\n import ScarcityBadge from \"../ScarcityBadge.svelte\";\r\n\r\n let {\r\n events = [],\r\n initialCount = 10,\r\n loadMoreCount = 10,\r\n showDateColumn = true,\r\n filterFutureOnly = true,\r\n oneventClick\r\n } = $props();\r\n\r\n let displayedCount = initialCount;\r\n let loadMoreTrigger;\r\n let observer;\r\n\r\n // Filter to today and future (if enabled), then group by date\r\n let filteredEvents = $derived(filterFutureOnly ? filterTodayAndFuture(events) : events);\r\n let groupedEvents = $derived(groupEventsByDate(filteredEvents.slice(0, displayedCount)));\r\n let hasMore = $derived(displayedCount < filteredEvents.length);\r\n\r\n function loadMore() {\r\n displayedCount += loadMoreCount;\r\n }\r\n\r\n onMount(() => {\r\n observer = new IntersectionObserver(\r\n (entries) => {\r\n if (entries[0].isIntersecting && hasMore) {\r\n loadMore();\r\n }\r\n },\r\n { rootMargin: '100px' }\r\n );\r\n\r\n if (loadMoreTrigger) {\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n\r\n onDestroy(() => {\r\n if (observer) {\r\n observer.disconnect();\r\n }\r\n });\r\n\r\n // Re-observe when trigger element changes\r\n $effect(() => {\r\n if (observer && loadMoreTrigger) {\r\n observer.disconnect();\r\n observer.observe(loadMoreTrigger);\r\n }\r\n });\r\n\r\n function groupEventsByDate(eventList) {\r\n const groups = {};\r\n\r\n for (const event of eventList) {\r\n const dateKey = event.date; // YYYY-MM-DD format\r\n if (!groups[dateKey]) {\r\n groups[dateKey] = [];\r\n }\r\n groups[dateKey].push(event);\r\n }\r\n\r\n // Convert to array sorted by date\r\n return Object.entries(groups)\r\n .sort(([a], [b]) => new Date(a) - new Date(b))\r\n .map(([date, events]) => ({\r\n date,\r\n events,\r\n formattedDate: formatGroupDate(events),\r\n }));\r\n }\r\n\r\n function formatGroupDate(events) {\r\n // Use the first event in the group to get timezone-aware date parts\r\n const firstEvent = events[0];\r\n if (!firstEvent?.startDateTime) return { month: '', day: '', weekday: '' };\r\n const parts = getDateParts(firstEvent.startDateTime, firstEvent.timeZone);\r\n return {\r\n month: parts.month.toUpperCase(),\r\n day: String(parts.date).padStart(2, '0'),\r\n weekday: parts.day.toUpperCase(),\r\n };\r\n }\r\n\r\n function handleEventClick(event) {\r\n oneventClick?.(event);\r\n }\r\n\r\n function handleKeydown(e, event) {\r\n if (e.key === 'Enter' || e.key === ' ') {\r\n e.preventDefault();\r\n handleEventClick(event);\r\n }\r\n }\r\n</script>\r\n\r\n<section class=\"flex flex-col gap-0\" class:no-date-column={!showDateColumn} aria-label=\"Event listings\">\r\n <h2 class=\"sr-only\">Event list grouped by date</h2>\r\n {#each groupedEvents as group}\r\n <div class=\"date-group flex border-b border-border last:border-b-0\" role=\"group\" aria-label=\"Events on {group.events[0]?.startDateTime ? formatFullDate(group.events[0].startDateTime, group.events[0].timeZone) : group.date}\">\r\n <!-- Date Column -->\r\n {#if showDateColumn}\r\n <div class=\"w-16 min-w-16 py-4 px-2.5 flex flex-col items-center justify-start bg-bg-secondary border-r border-border max-sm:w-12 max-sm:min-w-12 max-sm:py-2.5 max-sm:px-1.5\" aria-hidden=\"true\">\r\n <span class=\"text-xs font-semibold text-text-secondary uppercase tracking-tight\">{group.formattedDate.month}</span>\r\n <span class=\"text-2xl max-sm:text-lg font-bold text-text-primary leading-tight\">{group.formattedDate.day}</span>\r\n <span class=\"text-xs font-semibold text-text-secondary uppercase tracking-tight\">{group.formattedDate.weekday}</span>\r\n </div>\r\n {/if}\r\n\r\n <!-- Events Column -->\r\n <ul class=\"events-column flex-1 flex flex-col list-none p-0 m-0\">\r\n {#each group.events as event, eventIndex}\r\n {@const eventStatus = getBrowseStatus(event)}\r\n {@const isUnavailable = isEventUnavailable(eventStatus)}\r\n <li class=\"list-none\">\r\n <div\r\n class=\"event-row flex gap-4 max-sm:gap-2.5 p-5 max-sm:p-3 cursor-pointer transition-colors duration-150 bg-card border-b border-border/50 last:border-b-0 hover:bg-bg-secondary focus:outline-2 focus:outline-brand-primary focus:-outline-offset-2 focus-visible:outline-2 focus-visible:outline-brand-primary:outline-brand-primary focus-visible:-outline-offset-2\"\r\n class:row-unavailable={isUnavailable}\r\n onclick={() => handleEventClick(event)}\r\n onkeydown={(e) => handleKeydown(e, event)}\r\n tabindex=\"0\"\r\n role=\"button\"\r\n aria-label={`${event.name} on ${event.startDateTime ? formatFullDate(event.startDateTime, event.timeZone) : group.date} at ${event.startDateTime ? formatEventTime(event.startDateTime, event.timeZone) : ''}, ${eventStatus?.text || event.status || 'On Sale'}. Press Enter to view details.`}\r\n >\r\n <!-- Event Image -->\r\n <div class=\"w-36 h-24 min-w-36 max-sm:w-20 max-sm:h-16 max-sm:min-w-20 rounded-lg overflow-hidden bg-bg-secondary flex items-center justify-center\" aria-hidden=\"true\">\r\n <img\r\n src={event.image || PLACEHOLDER_IMAGE}\r\n alt=\"\"\r\n class=\"w-full h-full object-contain\"\r\n loading=\"lazy\"\r\n />\r\n </div>\r\n\r\n <!-- Event Details (visually shown but also in aria-label, so hide from SR) -->\r\n <div class=\"flex-1 flex flex-col gap-1.5 min-w-0\" aria-hidden=\"true\">\r\n <h3 class=\"text-lg max-sm:text-sm font-semibold text-text-primary m-0 leading-snug\">{event.name}</h3>\r\n <time class=\"text-sm max-sm:text-xs font-medium text-text-secondary\" datetime={event.startDateTime || group.date}>{event.startDateTime ? formatEventTime(event.startDateTime, event.timeZone) : ''}</time>\r\n {#if event.description}\r\n <p class=\"event-description text-sm text-text-secondary mt-1.5 mb-0 line-clamp-2 max-sm:hidden\">{event.description}</p>\r\n {/if}\r\n </div>\r\n\r\n <!-- Status / Scarcity Badge -->\r\n <div class=\"flex items-start pt-0.5\" aria-hidden=\"true\">\r\n {#if eventStatus}\r\n <span class=\"status-badge status-{eventStatus.type}\">{eventStatus.text}</span>\r\n {:else if event.ticketsTotal > 0 || event.ticketsRemaining === 0}\r\n <ScarcityBadge\r\n remaining={event.ticketsRemaining ?? 0}\r\n total={event.ticketsTotal ?? 0}\r\n context=\"browse\"\r\n />\r\n {/if}\r\n </div>\r\n </div>\r\n </li>\r\n {/each}\r\n </ul>\r\n </div>\r\n {/each}\r\n\r\n <!-- Infinite scroll trigger -->\r\n {#if hasMore}\r\n <div bind:this={loadMoreTrigger} class=\"flex justify-center items-center p-6 text-text-secondary\" role=\"status\" aria-live=\"polite\">\r\n <span class=\"text-sm\">Loading more events...</span>\r\n </div>\r\n {/if}\r\n</section>\r\n\r\n<style>\r\n /* When no date column, remove left border styling */\r\n .no-date-column .date-group {\r\n border-bottom: 0;\r\n }\r\n\r\n .no-date-column .events-column {\r\n border-left: 0;\r\n }\r\n\r\n .event-description {\r\n display: -webkit-box;\r\n -webkit-box-orient: vertical;\r\n overflow: hidden;\r\n }\r\n\r\n /* Unavailable row dimming */\r\n .row-unavailable {\r\n opacity: 0.6;\r\n }\r\n\r\n .row-unavailable img {\r\n filter: grayscale(0.5);\r\n }\r\n\r\n /* Status badges -- distinct visual treatments matching gallery cards */\r\n .status-badge {\r\n display: inline-flex;\r\n align-items: center;\r\n font-size: 0.75rem;\r\n line-height: 1rem;\r\n font-weight: 700;\r\n padding: 0.25rem 0.625rem;\r\n border-radius: 0.25rem;\r\n white-space: nowrap;\r\n letter-spacing: 0.02em;\r\n }\r\n\r\n .status-cancelled {\r\n background-color: hsl(var(--accent-danger) / 10%);\r\n color: hsl(var(--accent-danger));\r\n text-decoration: line-through;\r\n text-decoration-thickness: 1.5px;\r\n\r\n \r\n }\r\n\r\n .status-past {\r\n background-color: hsl(var(--bg-tertiary));\r\n color: hsl(var(--text-tertiary));\r\n\r\n \r\n }\r\n\r\n .status-sold_out {\r\n background-color: hsl(var(--accent-danger) / 10%);\r\n color: hsl(var(--accent-danger));\r\n text-transform: uppercase;\r\n letter-spacing: 0.05em;\r\n font-size: 0.65rem;\r\n\r\n \r\n }\r\n\r\n .status-sales_ended {\r\n background-color: hsl(var(--bg-tertiary));\r\n color: hsl(var(--text-tertiary));\r\n border: 1px solid hsl(var(--stroke-primary));\r\n\r\n \r\n }\r\n\r\n .status-coming_soon {\r\n background-color: hsl(var(--brand-primary) / 15%);\r\n color: hsl(var(--brand-primary));\r\n\r\n \r\n }\r\n\r\n /* Reduced motion */\r\n @media (prefers-reduced-motion: reduce) {\r\n .event-row {\r\n transition: none;\r\n }\r\n }\r\n\r\n /* Screen reader only text */\r\n .sr-only {\r\n position: absolute;\r\n width: 1px;\r\n height: 1px;\r\n padding: 0;\r\n margin: -1px;\r\n overflow: hidden;\r\n clip: rect(0, 0, 0, 0);\r\n white-space: nowrap;\r\n border-width: 0;\r\n }\r\n</style>\r\n"],"names":["events","$","$$props","initialCount","loadMoreCount","showDateColumn","filterFutureOnly","displayedCount","loadMoreTrigger","observer","filteredEvents","filterTodayAndFuture","groupedEvents","groupEventsByDate","hasMore","loadMore","onMount","entries","onDestroy","eventList","groups","event","dateKey","a","b","date","formatGroupDate","firstEvent","parts","getDateParts","handleEventClick","handleKeydown","e","section","root","node","group","div","root_1","div_1","root_2","span","span_1","span_2","$$render","consequent","ul","node_1","eventStatus","getBrowseStatus","isUnavailable","isEventUnavailable","li","root_3","div_2","div_3","img","div_4","h3","time","p","root_4","text_5","consequent_1","div_5","span_3","root_5","text_6","ScarcityBadge","$$anchor","consequent_2","consequent_3","classes_1","$0","PLACEHOLDER_IMAGE","text_3","formatFullDate","formatEventTime","div_6","root_7","$$value","consequent_4","classes"],"mappings":"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"}
@@ -1,6 +1,6 @@
1
1
  import "svelte/internal/disclose-version";
2
2
  import * as e from "svelte/internal/client";
3
- import { ae as A, as as M, P as j, g as C } from "./VenueCalendar-Blt02sO6.js";
3
+ import { ae as A, as as M, P as j, g as C } from "./VenueCalendar-H0gMPiFX.js";
4
4
  import { T as v } from "./Text-CXR2fhx6.js";
5
5
  import "svelte/transition";
6
6
  import "svelte/easing";
@@ -494,4 +494,4 @@ export {
494
494
  ne as g,
495
495
  N as h
496
496
  };
497
- //# sourceMappingURL=OrderSummary-DfYrkOm8.js.map
497
+ //# sourceMappingURL=OrderSummary-BYSCmf9h.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"OrderSummary-DfYrkOm8.js","sources":["../src/lib/api/cta.ts","../src/lib/public-calendar-flow/defaults.ts","../src/lib/public-calendar-flow/OrderSummary.svelte"],"sourcesContent":["/**\r\n * CTA state computation.\r\n *\r\n * Pure function (no I/O) — derives the buy-button state from an event and\r\n * its ticket list. Lives in `api/` because it is the canonical, single\r\n * source of truth that replaces the duplicate implementations previously\r\n * scattered across utils/api.js, core/api-client.js, and a few components.\r\n */\r\n\r\n// Import from the specific subpath (not the bare entry) so the api/\r\n// bundle doesn't pull in the entire SC component graph (Accordion etc.)\r\n// and break `npm run build:api`.\r\nimport {\r\n formatDateRaw,\r\n formatTime,\r\n} from '@getmicdrop/svelte-components/utils/formatters';\r\n\r\nexport interface CtaStateOptions {\r\n cancelled?: boolean;\r\n isRegistration?: boolean;\r\n waitlistEnabled?: boolean;\r\n}\r\n\r\nexport interface CtaState {\r\n text: string;\r\n disabled: boolean;\r\n reason:\r\n | 'cancelled'\r\n | 'event_past'\r\n | 'no_tickets'\r\n | 'available'\r\n | 'coming_soon'\r\n | 'sold_out_waitlist'\r\n | 'sold_out'\r\n | 'sales_ended'\r\n | 'hidden_only';\r\n}\r\n\r\ninterface CtaEvent {\r\n startDateTime?: string | null;\r\n endDateTime?: string | null;\r\n hasPurchasableHiddenTickets?: boolean;\r\n}\r\n\r\ninterface CtaTicket {\r\n salesChannel?: number;\r\n salesBegin?: string | null;\r\n salesStart?: string | null;\r\n saleBegin?: string | null;\r\n onSaleStart?: string | null;\r\n salesEnd?: string | null;\r\n saleEnd?: string | null;\r\n onSaleEnd?: string | null;\r\n remainingCapacity?: number | null;\r\n quantityRemaining?: number | null;\r\n quantity?: number | null;\r\n soldOut?: boolean;\r\n isHidden?: boolean;\r\n visibility?: number;\r\n}\r\n\r\n// A hidden ticket (visibility>=2 or isHidden) that's still on sale drives the\r\n// \"Sales ended\" / \"Sold out\" / \"No tickets\" → \"Get tickets\" override. The user\r\n// just needs the promo code to see it.\r\nexport function isHiddenTicketPurchasable(ticket: CtaTicket): boolean {\r\n if (!ticket) return false;\r\n const isHidden =\r\n ticket.isHidden === true ||\r\n (typeof ticket.visibility === 'number' && ticket.visibility >= 2);\r\n if (!isHidden) return false;\r\n if (ticket.salesChannel === 2) return false;\r\n\r\n const now = new Date();\r\n const salesBegin =\r\n ticket.salesBegin ||\r\n ticket.salesStart ||\r\n ticket.saleBegin ||\r\n ticket.onSaleStart;\r\n const salesEnd = ticket.salesEnd || ticket.saleEnd || ticket.onSaleEnd;\r\n if (salesBegin && new Date(salesBegin) > now) return false;\r\n if (salesEnd && new Date(salesEnd) < now) return false;\r\n\r\n const remaining =\r\n ticket.remainingCapacity ?? ticket.quantityRemaining ?? ticket.quantity;\r\n const isSoldOut =\r\n ticket.soldOut ||\r\n (remaining !== null && remaining !== undefined && remaining <= 0);\r\n if (isSoldOut) return false;\r\n\r\n return true;\r\n}\r\n\r\nexport function computeCtaState(\r\n event: CtaEvent,\r\n tickets: CtaTicket[] | undefined,\r\n options: CtaStateOptions = {}\r\n): CtaState {\r\n const {\r\n cancelled = false,\r\n isRegistration = false,\r\n waitlistEnabled = false,\r\n } = options;\r\n const now = new Date();\r\n\r\n if (cancelled)\r\n return { text: 'Cancelled', disabled: true, reason: 'cancelled' };\r\n\r\n const eventEnd = event.endDateTime || event.startDateTime;\r\n if (eventEnd && new Date(eventEnd) < now) {\r\n return { text: 'Sales ended', disabled: true, reason: 'event_past' };\r\n }\r\n\r\n const hiddenAvailable =\r\n event?.hasPurchasableHiddenTickets === true ||\r\n (Array.isArray(tickets) && tickets.some(isHiddenTicketPurchasable));\r\n\r\n const publicTickets = (tickets || []).filter(\r\n t =>\r\n t.salesChannel !== 2 &&\r\n !t.isHidden &&\r\n !(typeof t.visibility === 'number' && t.visibility >= 2)\r\n );\r\n if (publicTickets.length === 0) {\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n return {\r\n text: 'No tickets available',\r\n disabled: true,\r\n reason: 'no_tickets',\r\n };\r\n }\r\n\r\n let hasPurchasable = false;\r\n let allSoldOut = true;\r\n let allComingSoon = true;\r\n let earliestSalesStart: Date | null = null;\r\n\r\n for (const ticket of publicTickets) {\r\n const salesBegin =\r\n ticket.salesBegin ||\r\n ticket.salesStart ||\r\n ticket.saleBegin ||\r\n ticket.onSaleStart;\r\n const salesEnd = ticket.salesEnd || ticket.saleEnd || ticket.onSaleEnd;\r\n const remaining =\r\n ticket.remainingCapacity ?? ticket.quantityRemaining ?? ticket.quantity;\r\n const isSoldOut =\r\n ticket.soldOut ||\r\n (remaining !== null && remaining !== undefined && remaining <= 0);\r\n\r\n const isScheduled = salesBegin ? new Date(salesBegin) > now : false;\r\n const hasSalesEnded = salesEnd ? new Date(salesEnd) < now : false;\r\n const isPurchasable = !isSoldOut && !isScheduled && !hasSalesEnded;\r\n\r\n if (isPurchasable) hasPurchasable = true;\r\n if (!isSoldOut) allSoldOut = false;\r\n if (!isScheduled) allComingSoon = false;\r\n\r\n if (isScheduled && salesBegin && !isSoldOut && !hasSalesEnded) {\r\n const startDate = new Date(salesBegin);\r\n if (!earliestSalesStart || startDate < earliestSalesStart) {\r\n earliestSalesStart = startDate;\r\n }\r\n }\r\n }\r\n\r\n if (hasPurchasable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'available',\r\n };\r\n }\r\n\r\n if (allComingSoon && earliestSalesStart) {\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n const diffMs = earliestSalesStart.getTime() - now.getTime();\r\n const diffHours = diffMs / (1000 * 60 * 60);\r\n const diffDays = diffMs / (1000 * 60 * 60 * 24);\r\n let dateText: string;\r\n if (diffHours < 24) {\r\n dateText = formatTime(earliestSalesStart, { hour12: true }, 'en-US');\r\n } else if (diffDays <= 7) {\r\n dateText = formatDateRaw(\r\n earliestSalesStart,\r\n { weekday: 'short', hour: 'numeric', minute: '2-digit', hour12: true },\r\n 'en-US'\r\n );\r\n } else {\r\n const d = formatDateRaw(\r\n earliestSalesStart,\r\n { month: 'short', day: 'numeric' },\r\n 'en-US'\r\n );\r\n const t = formatTime(earliestSalesStart, { hour12: true }, 'en-US');\r\n dateText = `${d} ${t}`;\r\n }\r\n return {\r\n text: `On sale ${dateText}`,\r\n disabled: true,\r\n reason: 'coming_soon',\r\n };\r\n }\r\n\r\n if (allSoldOut) {\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n if (waitlistEnabled) {\r\n return {\r\n text: 'Join Waitlist',\r\n disabled: false,\r\n reason: 'sold_out_waitlist',\r\n };\r\n }\r\n return { text: 'Sold out', disabled: true, reason: 'sold_out' };\r\n }\r\n\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n\r\n return { text: 'Sales ended', disabled: true, reason: 'sales_ended' };\r\n}\r\n","// @currency-escape: feeCents / 100 in calculateServiceFee is arithmetic,\r\n// not display. Produces a dollar-magnitude number used in the fee formula\r\n// `price * (feePercentage / 100) + feeCents / 100`. Per Atlas\r\n// utility-currency convergence record; the no-handrolled-currency\r\n// ESLint rule's divideByHundred detector treats variable-name `Cents`\r\n// as drift but here it's real math.\r\n\r\n// Premium Ticket Experience — Constants & Defaults\r\n// Used by all design variants. DO NOT MODIFY per-variant.\r\n\r\n// @raw-intl-datetimeformat-escape: formatSmartSalesDate is a date-formatter\r\n// implementation (smart relative-date thresholds → \"on Friday at 8 PM\" / \"on Mar 15\").\r\n// The weekday-long (\"Friday\") and month-short+day (\"Mar 15\") fragments are interpolated\r\n// into smart-threshold strings; SC formatDate/DATE_FORMATS has no preset that emits a\r\n// bare weekday or a bare month+day, so it cannot reproduce these byte-identical fragments.\r\n// This file is the canonical formatter module for public-calendar-flow (it wraps + re-exports\r\n// scFormatDate/scFormatTime), not a call site.\r\n\r\nimport type {\r\n EventData,\r\n TicketTypeData,\r\n ScarcityLevel,\r\n CtaConfig,\r\n PromoCodeState,\r\n} from './types';\r\nimport { computeCtaState } from '$lib/api';\r\nimport type { Cents } from '@getmicdrop/svelte-components';\r\nimport {\r\n formatDate as scFormatDate,\r\n formatTime as scFormatTime,\r\n roundCurrency,\r\n} from '@getmicdrop/svelte-components';\r\nimport {\r\n formatFullDate,\r\n formatFullDateCompact,\r\n formatEventTime,\r\n formatTimeRange,\r\n formatDoorsTime,\r\n formatSalesDate,\r\n formatBrowseDate,\r\n formatEventDate,\r\n formatCleanTimeRange,\r\n getDateParts,\r\n} from '$lib/utils/datetime.js';\r\n\r\n// --- Re-export production date/time formatters (timezone-aware) ---\r\nexport {\r\n formatFullDate,\r\n formatFullDateCompact,\r\n formatEventTime,\r\n formatTimeRange,\r\n formatDoorsTime,\r\n formatSalesDate,\r\n formatBrowseDate,\r\n formatEventDate,\r\n formatCleanTimeRange,\r\n getDateParts,\r\n};\r\n\r\n// --- Scarcity Badge Rules ---\r\nexport const SCARCITY_THRESHOLDS = {\r\n SOLD_OUT: 0,\r\n URGENT: 0.1, // ≤10% remaining → urgent (\"Only X left\")\r\n LOW: 0.2, // ≤20% remaining (80%+ sold) → \"Selling fast\"\r\n MAX_EXACT_COUNT: 20, // Don't show exact count above 20\r\n} as const;\r\n\r\nexport function getScarcityLevel(\r\n remaining: number,\r\n total: number\r\n): ScarcityLevel {\r\n if (total === 0) return 'none';\r\n if (remaining <= 0) return 'sold_out';\r\n const pct = remaining / total;\r\n if (pct <= SCARCITY_THRESHOLDS.URGENT) return 'urgent';\r\n if (pct <= SCARCITY_THRESHOLDS.LOW) return 'low';\r\n return 'none';\r\n}\r\n\r\nexport function getScarcityText(\r\n level: ScarcityLevel,\r\n remaining: number,\r\n context: 'browse' | 'event' | 'ticket',\r\n options?: { isFree?: boolean }\r\n): string | null {\r\n if (level === 'none') return null;\r\n if (level === 'sold_out') return 'Sold out';\r\n // No scarcity badges on free events/tickets — nothing to lose = no urgency\r\n if (options?.isFree) return null;\r\n if (\r\n level === 'urgent' &&\r\n context !== 'browse' &&\r\n remaining <= SCARCITY_THRESHOLDS.MAX_EXACT_COUNT\r\n ) {\r\n return `Only ${remaining} left`;\r\n }\r\n if (level === 'low' || level === 'urgent') return 'Selling fast';\r\n return null;\r\n}\r\n\r\n// --- CTA Rules ---\r\n// Delegates to production computeCtaState() but adapts our EventData shape.\r\n// Components keep calling getCtaConfig(event) — internal logic is production-aligned.\r\nexport function getCtaConfig(event: EventData): CtaConfig {\r\n // Map our EventData tickets to the shape computeCtaState expects.\r\n // `isHidden` flows through so computeCtaState can apply the hidden-only\r\n // \"Sales ended\" → \"Get tickets\" override (MIC-1039).\r\n const apiTickets = event.tickets.map(t => ({\r\n salesBegin: t.salesStartDate,\r\n salesEnd: t.salesEndDate,\r\n remainingCapacity: t.quantityAvailable,\r\n totalCapacity: t.quantityTotal,\r\n soldOut: t.status === 'sold_out',\r\n salesChannel: 1, // All our tickets are online (not \"at the door only\")\r\n isHidden: t.isHidden,\r\n }));\r\n\r\n // Handle statuses that computeCtaState doesn't compute from tickets\r\n if (event.status === 'cancelled') {\r\n return {\r\n text: 'Cancelled',\r\n disabled: true,\r\n reason: 'This event has been cancelled',\r\n };\r\n }\r\n if (event.status === 'past') {\r\n return {\r\n text: 'Event ended',\r\n disabled: true,\r\n reason: 'This event has ended',\r\n };\r\n }\r\n\r\n const result = computeCtaState(\r\n { startDateTime: event.startDateTime, endDateTime: event.endDateTime },\r\n apiTickets,\r\n {\r\n cancelled: false,\r\n isRegistration: event.isRegistrationEvent,\r\n waitlistEnabled: false,\r\n }\r\n );\r\n\r\n return {\r\n text: result.text,\r\n disabled: result.disabled,\r\n reason: result.disabled ? toFriendlyReason(result.reason) : undefined,\r\n };\r\n}\r\n\r\n/**\r\n * computeCtaState() returns machine-enum reasons ('event_past', 'sold_out',\r\n * 'coming_soon', etc) intended for branching, not display. The BookingWidget\r\n * and MobileCta render `reason` directly as supplementary copy below the\r\n * button text — which leaks raw enum strings to users.\r\n *\r\n * Map each enum to a friendly sentence, OR return undefined when the button\r\n * `text` already says everything (\"Sales ended\" / \"Sold out\" — no need for\r\n * a second line repeating it).\r\n */\r\nfunction toFriendlyReason(reason: string | undefined): string | undefined {\r\n if (!reason) return undefined;\r\n switch (reason) {\r\n case 'cancelled':\r\n return 'This event has been cancelled.';\r\n case 'event_past':\r\n return 'This event has already happened.';\r\n case 'no_tickets':\r\n return 'There are no tickets configured for this event.';\r\n case 'coming_soon':\r\n return undefined; // text already shows \"On sale <date>\"\r\n case 'sold_out':\r\n return undefined; // text already shows \"Sold out\"\r\n case 'sold_out_waitlist':\r\n return 'All tickets are claimed. Join the waitlist to be notified.';\r\n case 'sales_ended':\r\n return undefined; // text already shows \"Sales ended\"\r\n default:\r\n return undefined; // unknown enum — never leak it\r\n }\r\n}\r\n\r\n// --- Price Display Rules (from DECISIONS.md #1) ---\r\nexport function getPriceDisplay(event: EventData): string | null {\r\n const visibleTickets = event.tickets.filter(\r\n t => t.status === 'on_sale' && !t.isHidden\r\n );\r\n if (visibleTickets.length === 0) return null;\r\n\r\n const hasDonation = visibleTickets.some(\r\n t => t.isDonation || t.ticketType === 2\r\n );\r\n const paidTickets = visibleTickets.filter(\r\n t => !t.isDonation && t.ticketType !== 2\r\n );\r\n const hasFree = paidTickets.some(t => t.price === 0);\r\n const pricedTickets = paidTickets.filter(t => t.price > 0);\r\n\r\n // Only donation tickets → \"Donation\"\r\n if (pricedTickets.length === 0 && !hasFree && hasDonation) return 'Donation';\r\n\r\n // Only free tickets (no paid, no donation) → null (BookingWidget shows \"Free\" via isFreeEvent)\r\n if (pricedTickets.length === 0 && hasFree) return null;\r\n\r\n const minPrice = Math.min(...pricedTickets.map(t => t.price));\r\n\r\n // Free + paid → \"Free\" (free dominates the display)\r\n if (hasFree) return null;\r\n\r\n // Donation + paid → \"From $X\" (donation is an alternative option)\r\n if (hasDonation) return `From $${minPrice}`;\r\n\r\n // Single paid ticket type → \"$X\"\r\n if (pricedTickets.length === 1) return `$${minPrice}`;\r\n\r\n // Multiple paid ticket types → \"From $X\"\r\n return `From $${minPrice}`;\r\n}\r\n\r\n// --- Fee Calculation ---\r\nexport function calculateFee(\r\n price: number,\r\n feePercentage: number,\r\n feeCents: Cents\r\n): number {\r\n return roundCurrency(price * (feePercentage / 100) + feeCents / 100);\r\n}\r\n\r\nexport function calculateTax(amount: number, taxPercentage: number): number {\r\n return roundCurrency(amount * (taxPercentage / 100));\r\n}\r\n\r\n// --- Date Formatting ---\r\n// PREFERRED: Use the timezone-aware production formatters re-exported above:\r\n// formatBrowseDate(iso, tz) → \"Fri, Feb 20\"\r\n// formatFullDateCompact(iso, tz) → \"Friday, February 20\"\r\n// formatEventTime(iso, tz) → \"8:00 PM\"\r\n// formatTimeRange(start, end, tz) → \"8:00 PM - 10:00 PM\"\r\n// formatDoorsTime(doors, tz) → \"7:00 PM\"\r\n//\r\n// DEPRECATED: The functions below are backward-compatible wrappers for variants\r\n// not yet migrated to timezone-aware formatters. They use browser-local timezone.\r\n// Migrate to the production formatters above when updating each variant.\r\n\r\n/** @deprecated Use formatBrowseDate(dateStr, timezone) instead */\r\nexport function formatDate(dateStr: string): string {\r\n return scFormatDate(dateStr, { weekday: 'short', year: undefined });\r\n}\r\n\r\n/** @deprecated Use formatEventTime(dateStr, timezone) instead */\r\nexport function formatTime(dateStr: string): string {\r\n return scFormatTime(dateStr);\r\n}\r\n\r\n/** @deprecated Use formatBrowseDate + formatTimeRange instead */\r\nexport function formatDateRange(start: string, end: string): string {\r\n const tz = Intl.DateTimeFormat().resolvedOptions().timeZone;\r\n return `${formatBrowseDate(start, tz)} · ${formatTimeRange(start, end, tz)}`;\r\n}\r\n\r\n// --- Animation Durations ---\r\nexport const DURATION = {\r\n instant: 100,\r\n micro: 150,\r\n fast: 200,\r\n normal: 300,\r\n slow: 400,\r\n elaborate: 600,\r\n} as const;\r\n\r\n// --- Smart Sales Date Formatting ---\r\n// Ported from production TicketBlock.svelte — smart thresholds for human-readable dates\r\nexport function formatSmartSalesDate(dateStr: string): string {\r\n if (!dateStr) return '';\r\n const date = new Date(dateStr);\r\n const now = new Date();\r\n const diffMs = date.getTime() - now.getTime();\r\n const diffMinutes = Math.round(diffMs / (1000 * 60));\r\n const diffHours = diffMs / (1000 * 60 * 60);\r\n\r\n // < 1 hour: \"in X minutes\"\r\n if (diffMinutes > 0 && diffMinutes < 60) {\r\n const mins = Math.max(1, diffMinutes);\r\n return `in ${mins} minute${mins !== 1 ? 's' : ''}`;\r\n }\r\n\r\n // 1-24 hours: \"in X hours\"\r\n if (diffHours > 0 && diffHours < 24) {\r\n const hours = Math.max(1, Math.round(diffHours));\r\n return `in ${hours} hour${hours !== 1 ? 's' : ''}`;\r\n }\r\n\r\n // Tomorrow: \"tomorrow at X PM\"\r\n const tomorrow = new Date(now);\r\n tomorrow.setDate(tomorrow.getDate() + 1);\r\n if (date.toDateString() === tomorrow.toDateString()) {\r\n const timeStr = scFormatTime(\r\n date,\r\n { hour: 'numeric', minute: '2-digit' },\r\n 'en-US'\r\n );\r\n return `tomorrow at ${timeStr}`;\r\n }\r\n\r\n // 2-7 days: \"on Friday at X PM\"\r\n const diffDays = diffMs / (1000 * 60 * 60 * 24);\r\n if (diffDays > 0 && diffDays <= 7) {\r\n const dayName = new Intl.DateTimeFormat('en-US', {\r\n weekday: 'long',\r\n }).format(date);\r\n const timeStr = scFormatTime(\r\n date,\r\n { hour: 'numeric', minute: '2-digit' },\r\n 'en-US'\r\n );\r\n return `on ${dayName} at ${timeStr}`;\r\n }\r\n\r\n // > 7 days: \"on Mar 15\"\r\n const dateFormatted = new Intl.DateTimeFormat('en-US', {\r\n month: 'short',\r\n day: 'numeric',\r\n }).format(date);\r\n return `on ${dateFormatted}`;\r\n}\r\n\r\n// --- Promo Code State Factory ---\r\nexport function createDefaultPromoState(): PromoCodeState {\r\n return {\r\n code: '',\r\n isApplied: false,\r\n isValidating: false,\r\n error: '',\r\n hint: '',\r\n discountAmount: 0,\r\n discountType: '',\r\n discountTicketIds: [],\r\n revealHiddenTickets: false,\r\n revealTicketIds: [],\r\n };\r\n}\r\n\r\n// --- Ticket helpers ---\r\nexport function getAvailableTickets(\r\n tickets: TicketTypeData[]\r\n): TicketTypeData[] {\r\n return tickets.filter(t => !t.isHidden && t.status === 'on_sale');\r\n}\r\n","<script lang=\"ts\">\r\n\timport type { USD } from '@getmicdrop/svelte-components';\r\n\timport { Text, formatCurrency } from '@getmicdrop/svelte-components';\r\n\timport type { OrderTotals } from '$lib/public-calendar-flow/types';\r\n\timport { DURATION } from '$lib/public-calendar-flow/defaults';\r\n\r\n\tinterface Props {\r\n\t\torderTotals: OrderTotals;\r\n\t\tlabels?: Record<string, string>;\r\n\t\t/**\r\n\t\t * Which section to render.\r\n\t\t * - `full` (default): ticket lines + totals stacked together.\r\n\t\t * - `lines` : ticket-line items only. Use when the parent scrolls\r\n\t\t * this section in a flex column.\r\n\t\t * - `totals` : subtotal/fees/taxes/promo/total only. Use in a fixed\r\n\t\t * footer alongside the action button.\r\n\t\t *\r\n\t\t * Splitting via `lines` / `totals` lets the sticky sidebars scroll\r\n\t\t * just the variable-length ticket list while keeping the summary\r\n\t\t * block and CTA always visible.\r\n\t\t */\r\n\t\tmode?: 'full' | 'lines' | 'totals';\r\n\t}\r\n\r\n\tlet { orderTotals, labels = {}, mode = 'full' }: Props = $props();\r\n</script>\r\n\r\n<div\r\n\tclass=\"space-y-2\"\r\n\tstyle=\"transition-duration: {DURATION.normal}ms;\"\r\n>\r\n\t{#if mode !== 'totals'}\r\n\t\t<!-- Line items -->\r\n\t\t{#each orderTotals.lines as line (line.ticketId)}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\">{line.quantity}x {line.ticketName}</Text>\r\n\t\t\t\t<Text size=\"sm\">{formatCurrency(line.subtotal as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/each}\r\n\t{/if}\r\n\r\n\t{#if mode !== 'lines'}\r\n\t\t<!-- Subtotal. In `totals` mode the parent supplies the separator above\r\n\t\t this block (BookingWidget wraps the totals block in border-t); a\r\n\t\t second internal border would render as a double line. Only show\r\n\t\t the internal border-t in `full` mode where lines + totals stack\r\n\t\t in one container with no external separator. -->\r\n\t\t{#if mode === 'full' && orderTotals.lines.length > 1}\r\n\t\t\t<div class=\"flex justify-between pt-1 border-t border-default\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.subtotal || 'Subtotal'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.subtotal as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{:else if orderTotals.lines.length > 1}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.subtotal || 'Subtotal'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.subtotal as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Fees -->\r\n\t\t{#if orderTotals.fees > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.serviceFees || 'Service fees'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.fees as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Taxes -->\r\n\t\t{#if orderTotals.taxes > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.taxes || 'Taxes'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.taxes as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Promo discount -->\r\n\t\t{#if orderTotals.promoDiscount > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">{labels.promoDiscount || 'Promo discount'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">-{formatCurrency(orderTotals.promoDiscount as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Gift card — deduction from the amount due; `total` already reflects it -->\r\n\t\t{#if orderTotals.giftCardAmount > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">{labels.giftCard || 'Gift card'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">-{formatCurrency(orderTotals.giftCardAmount as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Total -->\r\n\t\t<div class=\"flex justify-between pt-2 border-t border-default\">\r\n\t\t\t<Text size=\"base\" class=\"font-semibold\">{labels.total || 'Total'}</Text>\r\n\t\t\t<Text size=\"base\" class=\"font-semibold\">{formatCurrency(orderTotals.total as USD)}</Text>\r\n\t\t</div>\r\n\t{/if}\r\n</div>\r\n"],"names":["isHiddenTicketPurchasable","ticket","now","salesBegin","salesEnd","remaining","computeCtaState","event","tickets","options","cancelled","isRegistration","waitlistEnabled","eventEnd","hiddenAvailable","publicTickets","t","hasPurchasable","allSoldOut","allComingSoon","earliestSalesStart","isSoldOut","isScheduled","hasSalesEnded","startDate","diffMs","diffHours","diffDays","dateText","formatTime","formatDateRaw","d","SCARCITY_THRESHOLDS","getScarcityLevel","total","pct","getScarcityText","level","context","getCtaConfig","apiTickets","result","toFriendlyReason","reason","getPriceDisplay","visibleTickets","hasDonation","paidTickets","hasFree","pricedTickets","minPrice","calculateTax","amount","taxPercentage","roundCurrency","DURATION","formatSmartSalesDate","dateStr","date","diffMinutes","mins","hours","tomorrow","scFormatTime","dayName","timeStr","createDefaultPromoState","labels","$","$$props","mode","div","root","node_1","line","div_1","root_2","Text","node_2","text","node_3","formatCurrency","$$render","consequent","div_2","root_6","node_6","node_7","$0","text_3","div_3","root_9","node_8","node_9","text_5","consequent_1","consequent_2","div_4","root_12","node_11","node_12","text_7","consequent_3","div_5","root_15","node_14","node_15","text_9","consequent_4","div_6","root_18","node_17","node_18","text_11","consequent_5","div_7","root_21","node_20","node_21","text_13","consequent_6","div_8","node_19","node_22","node_23","text_15","consequent_7"],"mappings":"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"}
1
+ {"version":3,"file":"OrderSummary-BYSCmf9h.js","sources":["../src/lib/api/cta.ts","../src/lib/public-calendar-flow/defaults.ts","../src/lib/public-calendar-flow/OrderSummary.svelte"],"sourcesContent":["/**\r\n * CTA state computation.\r\n *\r\n * Pure function (no I/O) — derives the buy-button state from an event and\r\n * its ticket list. Lives in `api/` because it is the canonical, single\r\n * source of truth that replaces the duplicate implementations previously\r\n * scattered across utils/api.js, core/api-client.js, and a few components.\r\n */\r\n\r\n// Import from the specific subpath (not the bare entry) so the api/\r\n// bundle doesn't pull in the entire SC component graph (Accordion etc.)\r\n// and break `npm run build:api`.\r\nimport {\r\n formatDateRaw,\r\n formatTime,\r\n} from '@getmicdrop/svelte-components/utils/formatters';\r\n\r\nexport interface CtaStateOptions {\r\n cancelled?: boolean;\r\n isRegistration?: boolean;\r\n waitlistEnabled?: boolean;\r\n}\r\n\r\nexport interface CtaState {\r\n text: string;\r\n disabled: boolean;\r\n reason:\r\n | 'cancelled'\r\n | 'event_past'\r\n | 'no_tickets'\r\n | 'available'\r\n | 'coming_soon'\r\n | 'sold_out_waitlist'\r\n | 'sold_out'\r\n | 'sales_ended'\r\n | 'hidden_only';\r\n}\r\n\r\ninterface CtaEvent {\r\n startDateTime?: string | null;\r\n endDateTime?: string | null;\r\n hasPurchasableHiddenTickets?: boolean;\r\n}\r\n\r\ninterface CtaTicket {\r\n salesChannel?: number;\r\n salesBegin?: string | null;\r\n salesStart?: string | null;\r\n saleBegin?: string | null;\r\n onSaleStart?: string | null;\r\n salesEnd?: string | null;\r\n saleEnd?: string | null;\r\n onSaleEnd?: string | null;\r\n remainingCapacity?: number | null;\r\n quantityRemaining?: number | null;\r\n quantity?: number | null;\r\n soldOut?: boolean;\r\n isHidden?: boolean;\r\n visibility?: number;\r\n}\r\n\r\n// A hidden ticket (visibility>=2 or isHidden) that's still on sale drives the\r\n// \"Sales ended\" / \"Sold out\" / \"No tickets\" → \"Get tickets\" override. The user\r\n// just needs the promo code to see it.\r\nexport function isHiddenTicketPurchasable(ticket: CtaTicket): boolean {\r\n if (!ticket) return false;\r\n const isHidden =\r\n ticket.isHidden === true ||\r\n (typeof ticket.visibility === 'number' && ticket.visibility >= 2);\r\n if (!isHidden) return false;\r\n if (ticket.salesChannel === 2) return false;\r\n\r\n const now = new Date();\r\n const salesBegin =\r\n ticket.salesBegin ||\r\n ticket.salesStart ||\r\n ticket.saleBegin ||\r\n ticket.onSaleStart;\r\n const salesEnd = ticket.salesEnd || ticket.saleEnd || ticket.onSaleEnd;\r\n if (salesBegin && new Date(salesBegin) > now) return false;\r\n if (salesEnd && new Date(salesEnd) < now) return false;\r\n\r\n const remaining =\r\n ticket.remainingCapacity ?? ticket.quantityRemaining ?? ticket.quantity;\r\n const isSoldOut =\r\n ticket.soldOut ||\r\n (remaining !== null && remaining !== undefined && remaining <= 0);\r\n if (isSoldOut) return false;\r\n\r\n return true;\r\n}\r\n\r\nexport function computeCtaState(\r\n event: CtaEvent,\r\n tickets: CtaTicket[] | undefined,\r\n options: CtaStateOptions = {}\r\n): CtaState {\r\n const {\r\n cancelled = false,\r\n isRegistration = false,\r\n waitlistEnabled = false,\r\n } = options;\r\n const now = new Date();\r\n\r\n if (cancelled)\r\n return { text: 'Cancelled', disabled: true, reason: 'cancelled' };\r\n\r\n const eventEnd = event.endDateTime || event.startDateTime;\r\n if (eventEnd && new Date(eventEnd) < now) {\r\n return { text: 'Sales ended', disabled: true, reason: 'event_past' };\r\n }\r\n\r\n const hiddenAvailable =\r\n event?.hasPurchasableHiddenTickets === true ||\r\n (Array.isArray(tickets) && tickets.some(isHiddenTicketPurchasable));\r\n\r\n const publicTickets = (tickets || []).filter(\r\n t =>\r\n t.salesChannel !== 2 &&\r\n !t.isHidden &&\r\n !(typeof t.visibility === 'number' && t.visibility >= 2)\r\n );\r\n if (publicTickets.length === 0) {\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n return {\r\n text: 'No tickets available',\r\n disabled: true,\r\n reason: 'no_tickets',\r\n };\r\n }\r\n\r\n let hasPurchasable = false;\r\n let allSoldOut = true;\r\n let allComingSoon = true;\r\n let earliestSalesStart: Date | null = null;\r\n\r\n for (const ticket of publicTickets) {\r\n const salesBegin =\r\n ticket.salesBegin ||\r\n ticket.salesStart ||\r\n ticket.saleBegin ||\r\n ticket.onSaleStart;\r\n const salesEnd = ticket.salesEnd || ticket.saleEnd || ticket.onSaleEnd;\r\n const remaining =\r\n ticket.remainingCapacity ?? ticket.quantityRemaining ?? ticket.quantity;\r\n const isSoldOut =\r\n ticket.soldOut ||\r\n (remaining !== null && remaining !== undefined && remaining <= 0);\r\n\r\n const isScheduled = salesBegin ? new Date(salesBegin) > now : false;\r\n const hasSalesEnded = salesEnd ? new Date(salesEnd) < now : false;\r\n const isPurchasable = !isSoldOut && !isScheduled && !hasSalesEnded;\r\n\r\n if (isPurchasable) hasPurchasable = true;\r\n if (!isSoldOut) allSoldOut = false;\r\n if (!isScheduled) allComingSoon = false;\r\n\r\n if (isScheduled && salesBegin && !isSoldOut && !hasSalesEnded) {\r\n const startDate = new Date(salesBegin);\r\n if (!earliestSalesStart || startDate < earliestSalesStart) {\r\n earliestSalesStart = startDate;\r\n }\r\n }\r\n }\r\n\r\n if (hasPurchasable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'available',\r\n };\r\n }\r\n\r\n if (allComingSoon && earliestSalesStart) {\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n const diffMs = earliestSalesStart.getTime() - now.getTime();\r\n const diffHours = diffMs / (1000 * 60 * 60);\r\n const diffDays = diffMs / (1000 * 60 * 60 * 24);\r\n let dateText: string;\r\n if (diffHours < 24) {\r\n dateText = formatTime(earliestSalesStart, { hour12: true }, 'en-US');\r\n } else if (diffDays <= 7) {\r\n dateText = formatDateRaw(\r\n earliestSalesStart,\r\n { weekday: 'short', hour: 'numeric', minute: '2-digit', hour12: true },\r\n 'en-US'\r\n );\r\n } else {\r\n const d = formatDateRaw(\r\n earliestSalesStart,\r\n { month: 'short', day: 'numeric' },\r\n 'en-US'\r\n );\r\n const t = formatTime(earliestSalesStart, { hour12: true }, 'en-US');\r\n dateText = `${d} ${t}`;\r\n }\r\n return {\r\n text: `On sale ${dateText}`,\r\n disabled: true,\r\n reason: 'coming_soon',\r\n };\r\n }\r\n\r\n if (allSoldOut) {\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n if (waitlistEnabled) {\r\n return {\r\n text: 'Join Waitlist',\r\n disabled: false,\r\n reason: 'sold_out_waitlist',\r\n };\r\n }\r\n return { text: 'Sold out', disabled: true, reason: 'sold_out' };\r\n }\r\n\r\n if (hiddenAvailable) {\r\n return {\r\n text: isRegistration ? 'Reserve a spot' : 'Get tickets',\r\n disabled: false,\r\n reason: 'hidden_only',\r\n };\r\n }\r\n\r\n return { text: 'Sales ended', disabled: true, reason: 'sales_ended' };\r\n}\r\n","// @currency-escape: feeCents / 100 in calculateServiceFee is arithmetic,\r\n// not display. Produces a dollar-magnitude number used in the fee formula\r\n// `price * (feePercentage / 100) + feeCents / 100`. Per Atlas\r\n// utility-currency convergence record; the no-handrolled-currency\r\n// ESLint rule's divideByHundred detector treats variable-name `Cents`\r\n// as drift but here it's real math.\r\n\r\n// Premium Ticket Experience — Constants & Defaults\r\n// Used by all design variants. DO NOT MODIFY per-variant.\r\n\r\n// @raw-intl-datetimeformat-escape: formatSmartSalesDate is a date-formatter\r\n// implementation (smart relative-date thresholds → \"on Friday at 8 PM\" / \"on Mar 15\").\r\n// The weekday-long (\"Friday\") and month-short+day (\"Mar 15\") fragments are interpolated\r\n// into smart-threshold strings; SC formatDate/DATE_FORMATS has no preset that emits a\r\n// bare weekday or a bare month+day, so it cannot reproduce these byte-identical fragments.\r\n// This file is the canonical formatter module for public-calendar-flow (it wraps + re-exports\r\n// scFormatDate/scFormatTime), not a call site.\r\n\r\nimport type {\r\n EventData,\r\n TicketTypeData,\r\n ScarcityLevel,\r\n CtaConfig,\r\n PromoCodeState,\r\n} from './types';\r\nimport { computeCtaState } from '$lib/api';\r\nimport type { Cents } from '@getmicdrop/svelte-components';\r\nimport {\r\n formatDate as scFormatDate,\r\n formatTime as scFormatTime,\r\n roundCurrency,\r\n} from '@getmicdrop/svelte-components';\r\nimport {\r\n formatFullDate,\r\n formatFullDateCompact,\r\n formatEventTime,\r\n formatTimeRange,\r\n formatDoorsTime,\r\n formatSalesDate,\r\n formatBrowseDate,\r\n formatEventDate,\r\n formatCleanTimeRange,\r\n getDateParts,\r\n} from '$lib/utils/datetime.js';\r\n\r\n// --- Re-export production date/time formatters (timezone-aware) ---\r\nexport {\r\n formatFullDate,\r\n formatFullDateCompact,\r\n formatEventTime,\r\n formatTimeRange,\r\n formatDoorsTime,\r\n formatSalesDate,\r\n formatBrowseDate,\r\n formatEventDate,\r\n formatCleanTimeRange,\r\n getDateParts,\r\n};\r\n\r\n// --- Scarcity Badge Rules ---\r\nexport const SCARCITY_THRESHOLDS = {\r\n SOLD_OUT: 0,\r\n URGENT: 0.1, // ≤10% remaining → urgent (\"Only X left\")\r\n LOW: 0.2, // ≤20% remaining (80%+ sold) → \"Selling fast\"\r\n MAX_EXACT_COUNT: 20, // Don't show exact count above 20\r\n} as const;\r\n\r\nexport function getScarcityLevel(\r\n remaining: number,\r\n total: number\r\n): ScarcityLevel {\r\n if (total === 0) return 'none';\r\n if (remaining <= 0) return 'sold_out';\r\n const pct = remaining / total;\r\n if (pct <= SCARCITY_THRESHOLDS.URGENT) return 'urgent';\r\n if (pct <= SCARCITY_THRESHOLDS.LOW) return 'low';\r\n return 'none';\r\n}\r\n\r\nexport function getScarcityText(\r\n level: ScarcityLevel,\r\n remaining: number,\r\n context: 'browse' | 'event' | 'ticket',\r\n options?: { isFree?: boolean }\r\n): string | null {\r\n if (level === 'none') return null;\r\n if (level === 'sold_out') return 'Sold out';\r\n // No scarcity badges on free events/tickets — nothing to lose = no urgency\r\n if (options?.isFree) return null;\r\n if (\r\n level === 'urgent' &&\r\n context !== 'browse' &&\r\n remaining <= SCARCITY_THRESHOLDS.MAX_EXACT_COUNT\r\n ) {\r\n return `Only ${remaining} left`;\r\n }\r\n if (level === 'low' || level === 'urgent') return 'Selling fast';\r\n return null;\r\n}\r\n\r\n// --- CTA Rules ---\r\n// Delegates to production computeCtaState() but adapts our EventData shape.\r\n// Components keep calling getCtaConfig(event) — internal logic is production-aligned.\r\nexport function getCtaConfig(event: EventData): CtaConfig {\r\n // Map our EventData tickets to the shape computeCtaState expects.\r\n // `isHidden` flows through so computeCtaState can apply the hidden-only\r\n // \"Sales ended\" → \"Get tickets\" override (MIC-1039).\r\n const apiTickets = event.tickets.map(t => ({\r\n salesBegin: t.salesStartDate,\r\n salesEnd: t.salesEndDate,\r\n remainingCapacity: t.quantityAvailable,\r\n totalCapacity: t.quantityTotal,\r\n soldOut: t.status === 'sold_out',\r\n salesChannel: 1, // All our tickets are online (not \"at the door only\")\r\n isHidden: t.isHidden,\r\n }));\r\n\r\n // Handle statuses that computeCtaState doesn't compute from tickets\r\n if (event.status === 'cancelled') {\r\n return {\r\n text: 'Cancelled',\r\n disabled: true,\r\n reason: 'This event has been cancelled',\r\n };\r\n }\r\n if (event.status === 'past') {\r\n return {\r\n text: 'Event ended',\r\n disabled: true,\r\n reason: 'This event has ended',\r\n };\r\n }\r\n\r\n const result = computeCtaState(\r\n { startDateTime: event.startDateTime, endDateTime: event.endDateTime },\r\n apiTickets,\r\n {\r\n cancelled: false,\r\n isRegistration: event.isRegistrationEvent,\r\n waitlistEnabled: false,\r\n }\r\n );\r\n\r\n return {\r\n text: result.text,\r\n disabled: result.disabled,\r\n reason: result.disabled ? toFriendlyReason(result.reason) : undefined,\r\n };\r\n}\r\n\r\n/**\r\n * computeCtaState() returns machine-enum reasons ('event_past', 'sold_out',\r\n * 'coming_soon', etc) intended for branching, not display. The BookingWidget\r\n * and MobileCta render `reason` directly as supplementary copy below the\r\n * button text — which leaks raw enum strings to users.\r\n *\r\n * Map each enum to a friendly sentence, OR return undefined when the button\r\n * `text` already says everything (\"Sales ended\" / \"Sold out\" — no need for\r\n * a second line repeating it).\r\n */\r\nfunction toFriendlyReason(reason: string | undefined): string | undefined {\r\n if (!reason) return undefined;\r\n switch (reason) {\r\n case 'cancelled':\r\n return 'This event has been cancelled.';\r\n case 'event_past':\r\n return 'This event has already happened.';\r\n case 'no_tickets':\r\n return 'There are no tickets configured for this event.';\r\n case 'coming_soon':\r\n return undefined; // text already shows \"On sale <date>\"\r\n case 'sold_out':\r\n return undefined; // text already shows \"Sold out\"\r\n case 'sold_out_waitlist':\r\n return 'All tickets are claimed. Join the waitlist to be notified.';\r\n case 'sales_ended':\r\n return undefined; // text already shows \"Sales ended\"\r\n default:\r\n return undefined; // unknown enum — never leak it\r\n }\r\n}\r\n\r\n// --- Price Display Rules (from DECISIONS.md #1) ---\r\nexport function getPriceDisplay(event: EventData): string | null {\r\n const visibleTickets = event.tickets.filter(\r\n t => t.status === 'on_sale' && !t.isHidden\r\n );\r\n if (visibleTickets.length === 0) return null;\r\n\r\n const hasDonation = visibleTickets.some(\r\n t => t.isDonation || t.ticketType === 2\r\n );\r\n const paidTickets = visibleTickets.filter(\r\n t => !t.isDonation && t.ticketType !== 2\r\n );\r\n const hasFree = paidTickets.some(t => t.price === 0);\r\n const pricedTickets = paidTickets.filter(t => t.price > 0);\r\n\r\n // Only donation tickets → \"Donation\"\r\n if (pricedTickets.length === 0 && !hasFree && hasDonation) return 'Donation';\r\n\r\n // Only free tickets (no paid, no donation) → null (BookingWidget shows \"Free\" via isFreeEvent)\r\n if (pricedTickets.length === 0 && hasFree) return null;\r\n\r\n const minPrice = Math.min(...pricedTickets.map(t => t.price));\r\n\r\n // Free + paid → \"Free\" (free dominates the display)\r\n if (hasFree) return null;\r\n\r\n // Donation + paid → \"From $X\" (donation is an alternative option)\r\n if (hasDonation) return `From $${minPrice}`;\r\n\r\n // Single paid ticket type → \"$X\"\r\n if (pricedTickets.length === 1) return `$${minPrice}`;\r\n\r\n // Multiple paid ticket types → \"From $X\"\r\n return `From $${minPrice}`;\r\n}\r\n\r\n// --- Fee Calculation ---\r\nexport function calculateFee(\r\n price: number,\r\n feePercentage: number,\r\n feeCents: Cents\r\n): number {\r\n return roundCurrency(price * (feePercentage / 100) + feeCents / 100);\r\n}\r\n\r\nexport function calculateTax(amount: number, taxPercentage: number): number {\r\n return roundCurrency(amount * (taxPercentage / 100));\r\n}\r\n\r\n// --- Date Formatting ---\r\n// PREFERRED: Use the timezone-aware production formatters re-exported above:\r\n// formatBrowseDate(iso, tz) → \"Fri, Feb 20\"\r\n// formatFullDateCompact(iso, tz) → \"Friday, February 20\"\r\n// formatEventTime(iso, tz) → \"8:00 PM\"\r\n// formatTimeRange(start, end, tz) → \"8:00 PM - 10:00 PM\"\r\n// formatDoorsTime(doors, tz) → \"7:00 PM\"\r\n//\r\n// DEPRECATED: The functions below are backward-compatible wrappers for variants\r\n// not yet migrated to timezone-aware formatters. They use browser-local timezone.\r\n// Migrate to the production formatters above when updating each variant.\r\n\r\n/** @deprecated Use formatBrowseDate(dateStr, timezone) instead */\r\nexport function formatDate(dateStr: string): string {\r\n return scFormatDate(dateStr, { weekday: 'short', year: undefined });\r\n}\r\n\r\n/** @deprecated Use formatEventTime(dateStr, timezone) instead */\r\nexport function formatTime(dateStr: string): string {\r\n return scFormatTime(dateStr);\r\n}\r\n\r\n/** @deprecated Use formatBrowseDate + formatTimeRange instead */\r\nexport function formatDateRange(start: string, end: string): string {\r\n const tz = Intl.DateTimeFormat().resolvedOptions().timeZone;\r\n return `${formatBrowseDate(start, tz)} · ${formatTimeRange(start, end, tz)}`;\r\n}\r\n\r\n// --- Animation Durations ---\r\nexport const DURATION = {\r\n instant: 100,\r\n micro: 150,\r\n fast: 200,\r\n normal: 300,\r\n slow: 400,\r\n elaborate: 600,\r\n} as const;\r\n\r\n// --- Smart Sales Date Formatting ---\r\n// Ported from production TicketBlock.svelte — smart thresholds for human-readable dates\r\nexport function formatSmartSalesDate(dateStr: string): string {\r\n if (!dateStr) return '';\r\n const date = new Date(dateStr);\r\n const now = new Date();\r\n const diffMs = date.getTime() - now.getTime();\r\n const diffMinutes = Math.round(diffMs / (1000 * 60));\r\n const diffHours = diffMs / (1000 * 60 * 60);\r\n\r\n // < 1 hour: \"in X minutes\"\r\n if (diffMinutes > 0 && diffMinutes < 60) {\r\n const mins = Math.max(1, diffMinutes);\r\n return `in ${mins} minute${mins !== 1 ? 's' : ''}`;\r\n }\r\n\r\n // 1-24 hours: \"in X hours\"\r\n if (diffHours > 0 && diffHours < 24) {\r\n const hours = Math.max(1, Math.round(diffHours));\r\n return `in ${hours} hour${hours !== 1 ? 's' : ''}`;\r\n }\r\n\r\n // Tomorrow: \"tomorrow at X PM\"\r\n const tomorrow = new Date(now);\r\n tomorrow.setDate(tomorrow.getDate() + 1);\r\n if (date.toDateString() === tomorrow.toDateString()) {\r\n const timeStr = scFormatTime(\r\n date,\r\n { hour: 'numeric', minute: '2-digit' },\r\n 'en-US'\r\n );\r\n return `tomorrow at ${timeStr}`;\r\n }\r\n\r\n // 2-7 days: \"on Friday at X PM\"\r\n const diffDays = diffMs / (1000 * 60 * 60 * 24);\r\n if (diffDays > 0 && diffDays <= 7) {\r\n const dayName = new Intl.DateTimeFormat('en-US', {\r\n weekday: 'long',\r\n }).format(date);\r\n const timeStr = scFormatTime(\r\n date,\r\n { hour: 'numeric', minute: '2-digit' },\r\n 'en-US'\r\n );\r\n return `on ${dayName} at ${timeStr}`;\r\n }\r\n\r\n // > 7 days: \"on Mar 15\"\r\n const dateFormatted = new Intl.DateTimeFormat('en-US', {\r\n month: 'short',\r\n day: 'numeric',\r\n }).format(date);\r\n return `on ${dateFormatted}`;\r\n}\r\n\r\n// --- Promo Code State Factory ---\r\nexport function createDefaultPromoState(): PromoCodeState {\r\n return {\r\n code: '',\r\n isApplied: false,\r\n isValidating: false,\r\n error: '',\r\n hint: '',\r\n discountAmount: 0,\r\n discountType: '',\r\n discountTicketIds: [],\r\n revealHiddenTickets: false,\r\n revealTicketIds: [],\r\n };\r\n}\r\n\r\n// --- Ticket helpers ---\r\nexport function getAvailableTickets(\r\n tickets: TicketTypeData[]\r\n): TicketTypeData[] {\r\n return tickets.filter(t => !t.isHidden && t.status === 'on_sale');\r\n}\r\n","<script lang=\"ts\">\r\n\timport type { USD } from '@getmicdrop/svelte-components';\r\n\timport { Text, formatCurrency } from '@getmicdrop/svelte-components';\r\n\timport type { OrderTotals } from '$lib/public-calendar-flow/types';\r\n\timport { DURATION } from '$lib/public-calendar-flow/defaults';\r\n\r\n\tinterface Props {\r\n\t\torderTotals: OrderTotals;\r\n\t\tlabels?: Record<string, string>;\r\n\t\t/**\r\n\t\t * Which section to render.\r\n\t\t * - `full` (default): ticket lines + totals stacked together.\r\n\t\t * - `lines` : ticket-line items only. Use when the parent scrolls\r\n\t\t * this section in a flex column.\r\n\t\t * - `totals` : subtotal/fees/taxes/promo/total only. Use in a fixed\r\n\t\t * footer alongside the action button.\r\n\t\t *\r\n\t\t * Splitting via `lines` / `totals` lets the sticky sidebars scroll\r\n\t\t * just the variable-length ticket list while keeping the summary\r\n\t\t * block and CTA always visible.\r\n\t\t */\r\n\t\tmode?: 'full' | 'lines' | 'totals';\r\n\t}\r\n\r\n\tlet { orderTotals, labels = {}, mode = 'full' }: Props = $props();\r\n</script>\r\n\r\n<div\r\n\tclass=\"space-y-2\"\r\n\tstyle=\"transition-duration: {DURATION.normal}ms;\"\r\n>\r\n\t{#if mode !== 'totals'}\r\n\t\t<!-- Line items -->\r\n\t\t{#each orderTotals.lines as line (line.ticketId)}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\">{line.quantity}x {line.ticketName}</Text>\r\n\t\t\t\t<Text size=\"sm\">{formatCurrency(line.subtotal as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/each}\r\n\t{/if}\r\n\r\n\t{#if mode !== 'lines'}\r\n\t\t<!-- Subtotal. In `totals` mode the parent supplies the separator above\r\n\t\t this block (BookingWidget wraps the totals block in border-t); a\r\n\t\t second internal border would render as a double line. Only show\r\n\t\t the internal border-t in `full` mode where lines + totals stack\r\n\t\t in one container with no external separator. -->\r\n\t\t{#if mode === 'full' && orderTotals.lines.length > 1}\r\n\t\t\t<div class=\"flex justify-between pt-1 border-t border-default\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.subtotal || 'Subtotal'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.subtotal as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{:else if orderTotals.lines.length > 1}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.subtotal || 'Subtotal'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.subtotal as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Fees -->\r\n\t\t{#if orderTotals.fees > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.serviceFees || 'Service fees'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.fees as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Taxes -->\r\n\t\t{#if orderTotals.taxes > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{labels.taxes || 'Taxes'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"muted\">{formatCurrency(orderTotals.taxes as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Promo discount -->\r\n\t\t{#if orderTotals.promoDiscount > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">{labels.promoDiscount || 'Promo discount'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">-{formatCurrency(orderTotals.promoDiscount as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Gift card — deduction from the amount due; `total` already reflects it -->\r\n\t\t{#if orderTotals.giftCardAmount > 0}\r\n\t\t\t<div class=\"flex justify-between\">\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">{labels.giftCard || 'Gift card'}</Text>\r\n\t\t\t\t<Text size=\"sm\" color=\"success\">-{formatCurrency(orderTotals.giftCardAmount as USD)}</Text>\r\n\t\t\t</div>\r\n\t\t{/if}\r\n\r\n\t\t<!-- Total -->\r\n\t\t<div class=\"flex justify-between pt-2 border-t border-default\">\r\n\t\t\t<Text size=\"base\" class=\"font-semibold\">{labels.total || 'Total'}</Text>\r\n\t\t\t<Text size=\"base\" class=\"font-semibold\">{formatCurrency(orderTotals.total as USD)}</Text>\r\n\t\t</div>\r\n\t{/if}\r\n</div>\r\n"],"names":["isHiddenTicketPurchasable","ticket","now","salesBegin","salesEnd","remaining","computeCtaState","event","tickets","options","cancelled","isRegistration","waitlistEnabled","eventEnd","hiddenAvailable","publicTickets","t","hasPurchasable","allSoldOut","allComingSoon","earliestSalesStart","isSoldOut","isScheduled","hasSalesEnded","startDate","diffMs","diffHours","diffDays","dateText","formatTime","formatDateRaw","d","SCARCITY_THRESHOLDS","getScarcityLevel","total","pct","getScarcityText","level","context","getCtaConfig","apiTickets","result","toFriendlyReason","reason","getPriceDisplay","visibleTickets","hasDonation","paidTickets","hasFree","pricedTickets","minPrice","calculateTax","amount","taxPercentage","roundCurrency","DURATION","formatSmartSalesDate","dateStr","date","diffMinutes","mins","hours","tomorrow","scFormatTime","dayName","timeStr","createDefaultPromoState","labels","$","$$props","mode","div","root","node_1","line","div_1","root_2","Text","node_2","text","node_3","formatCurrency","$$render","consequent","div_2","root_6","node_6","node_7","$0","text_3","div_3","root_9","node_8","node_9","text_5","consequent_1","consequent_2","div_4","root_12","node_11","node_12","text_7","consequent_3","div_5","root_15","node_14","node_15","text_9","consequent_4","div_6","root_18","node_17","node_18","text_11","consequent_5","div_7","root_21","node_20","node_21","text_13","consequent_6","div_8","node_19","node_22","node_23","text_15","consequent_7"],"mappings":"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"}
@@ -1,11 +1,11 @@
1
1
  import "svelte/internal/disclose-version";
2
2
  import * as e from "svelte/internal/client";
3
- import { g as Q, aJ as j, ad as ke, ac as te, B as R, aa as ye, ab as be, h as G } from "./VenueCalendar-Blt02sO6.js";
3
+ import { g as Q, aJ as j, ad as ke, ac as te, B as R, aa as ye, ab as be, h as G } from "./VenueCalendar-H0gMPiFX.js";
4
4
  import { H as Pe } from "./Heading-AFd3o0xt.js";
5
5
  import { T as $ } from "./Text-CXR2fhx6.js";
6
6
  import "svelte/transition";
7
7
  import "svelte/easing";
8
- import { g as Se, b as qe, f as De, D as ae } from "./OrderSummary-DfYrkOm8.js";
8
+ import { g as Se, b as qe, f as De, D as ae } from "./OrderSummary-BYSCmf9h.js";
9
9
  function ee(w = "light") {
10
10
  if (typeof window > "u" || typeof navigator > "u" || !navigator.vibrate) return;
11
11
  const t = w === "light" ? 8 : w === "medium" ? 18 : 32;
@@ -412,4 +412,4 @@ export {
412
412
  Ke as T,
413
413
  ee as t
414
414
  };
415
- //# sourceMappingURL=PromoCodeInput-2qhorZ4R.js.map
415
+ //# sourceMappingURL=PromoCodeInput-B8agz1bc.js.map