@billingos/sdk 0.1.4 → 0.1.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.cts +41 -8
- package/dist/index.d.ts +41 -8
- package/dist/index.js +524 -792
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +528 -797
- package/dist/index.mjs.map +1 -1
- package/package.json +4 -1
package/dist/index.js
CHANGED
|
@@ -114,6 +114,7 @@ __export(index_exports, {
|
|
|
114
114
|
SheetTrigger: () => SheetTrigger,
|
|
115
115
|
Skeleton: () => Skeleton,
|
|
116
116
|
SubscriptionTab: () => SubscriptionTab,
|
|
117
|
+
Switch: () => Switch,
|
|
117
118
|
Tabs: () => Tabs,
|
|
118
119
|
TabsContent: () => TabsContent,
|
|
119
120
|
TabsList: () => TabsList,
|
|
@@ -211,7 +212,7 @@ module.exports = __toCommonJS(index_exports);
|
|
|
211
212
|
if (document.getElementById(id)) return;
|
|
212
213
|
var s = document.createElement("style");
|
|
213
214
|
s.id = id;
|
|
214
|
-
s.textContent = '/*! tailwindcss v4.1.18 | MIT License | https://tailwindcss.com */\n@layer properties;\n@layer theme, base, components, utilities;\n@layer theme {\n :root, :host {\n --font-sans: ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji",\n "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji";\n --font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono",\n "Courier New", monospace;\n --color-red-50: oklch(97.1% 0.013 17.38);\n --color-red-100: oklch(93.6% 0.032 17.717);\n --color-red-500: oklch(63.7% 0.237 25.331);\n --color-red-600: oklch(57.7% 0.245 27.325);\n --color-red-800: oklch(44.4% 0.177 26.899);\n --color-amber-500: oklch(76.9% 0.188 70.08);\n --color-yellow-50: oklch(98.7% 0.026 102.212);\n --color-yellow-100: oklch(97.3% 0.071 103.193);\n --color-yellow-500: oklch(79.5% 0.184 86.047);\n --color-yellow-600: oklch(68.1% 0.162 75.834);\n --color-yellow-800: oklch(47.6% 0.114 61.907);\n --color-yellow-900: oklch(42.1% 0.095 57.708);\n --color-green-50: oklch(98.2% 0.018 155.826);\n --color-green-100: oklch(96.2% 0.044 156.743);\n --color-green-200: oklch(92.5% 0.084 155.995);\n --color-green-300: oklch(87.1% 0.15 154.449);\n --color-green-400: oklch(79.2% 0.209 151.711);\n --color-green-500: oklch(72.3% 0.219 149.579);\n --color-green-600: oklch(62.7% 0.194 149.214);\n --color-green-700: oklch(52.7% 0.154 150.069);\n --color-green-800: oklch(44.8% 0.119 151.328);\n --color-green-900: oklch(39.3% 0.095 152.535);\n --color-blue-100: oklch(93.2% 0.032 255.585);\n --color-blue-500: oklch(62.3% 0.214 259.815);\n --color-blue-600: oklch(54.6% 0.245 262.881);\n --color-blue-700: oklch(48.8% 0.243 264.376);\n --color-blue-800: oklch(42.4% 0.199 265.638);\n --color-purple-100: oklch(94.6% 0.033 307.174);\n --color-purple-600: oklch(55.8% 0.288 302.321);\n --color-purple-700: oklch(49.6% 0.265 301.924);\n --color-gray-50: oklch(98.5% 0.002 247.839);\n --color-gray-100: oklch(96.7% 0.003 264.542);\n --color-gray-200: oklch(92.8% 0.006 264.531);\n --color-gray-300: oklch(87.2% 0.01 258.338);\n --color-gray-400: oklch(70.7% 0.022 261.325);\n --color-gray-500: oklch(55.1% 0.027 264.364);\n --color-gray-600: oklch(44.6% 0.03 256.802);\n --color-gray-700: oklch(37.3% 0.034 259.733);\n --color-gray-900: oklch(21% 0.034 264.665);\n --color-black: #000;\n --color-white: #fff;\n --spacing: 0.25rem;\n --container-sm: 24rem;\n --container-md: 28rem;\n --container-lg: 32rem;\n --container-2xl: 42rem;\n --container-4xl: 56rem;\n --container-6xl: 72rem;\n --container-7xl: 80rem;\n --text-xs: 0.75rem;\n --text-xs--line-height: calc(1 / 0.75);\n --text-sm: 0.875rem;\n --text-sm--line-height: calc(1.25 / 0.875);\n --text-base: 1rem;\n --text-base--line-height: calc(1.5 / 1);\n --text-lg: 1.125rem;\n --text-lg--line-height: calc(1.75 / 1.125);\n --text-xl: 1.25rem;\n --text-xl--line-height: calc(1.75 / 1.25);\n --text-2xl: 1.5rem;\n --text-2xl--line-height: calc(2 / 1.5);\n --text-3xl: 1.875rem;\n --text-3xl--line-height: calc(2.25 / 1.875);\n --text-4xl: 2.25rem;\n --text-4xl--line-height: calc(2.5 / 2.25);\n --text-5xl: 3rem;\n --text-5xl--line-height: 1;\n --font-weight-normal: 400;\n --font-weight-medium: 500;\n --font-weight-semibold: 600;\n --font-weight-bold: 700;\n --tracking-tight: -0.025em;\n --leading-tight: 1.25;\n --leading-relaxed: 1.625;\n --radius-2xl: 1rem;\n --ease-out: cubic-bezier(0, 0, 0.2, 1);\n --ease-in-out: cubic-bezier(0.4, 0, 0.2, 1);\n --animate-spin: spin 1s linear infinite;\n --animate-pulse: pulse 2s cubic-bezier(0.4, 0, 0.6, 1) infinite;\n --blur-sm: 8px;\n --default-transition-duration: 150ms;\n --default-transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);\n --default-font-family: var(--font-sans);\n --default-mono-font-family: var(--font-mono);\n }\n}\n@layer base {\n *, ::after, ::before, ::backdrop, ::file-selector-button {\n box-sizing: border-box;\n margin: 0;\n padding: 0;\n border: 0 solid;\n }\n html, :host {\n line-height: 1.5;\n -webkit-text-size-adjust: 100%;\n tab-size: 4;\n font-family: var(--default-font-family, ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji");\n font-feature-settings: var(--default-font-feature-settings, normal);\n font-variation-settings: var(--default-font-variation-settings, normal);\n -webkit-tap-highlight-color: transparent;\n }\n hr {\n height: 0;\n color: inherit;\n border-top-width: 1px;\n }\n abbr:where([title]) {\n -webkit-text-decoration: underline dotted;\n text-decoration: underline dotted;\n }\n h1, h2, h3, h4, h5, h6 {\n font-size: inherit;\n font-weight: inherit;\n }\n a {\n color: inherit;\n -webkit-text-decoration: inherit;\n text-decoration: inherit;\n }\n b, strong {\n font-weight: bolder;\n }\n code, kbd, samp, pre {\n font-family: var(--default-mono-font-family, ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace);\n font-feature-settings: var(--default-mono-font-feature-settings, normal);\n font-variation-settings: var(--default-mono-font-variation-settings, normal);\n font-size: 1em;\n }\n small {\n font-size: 80%;\n }\n sub, sup {\n font-size: 75%;\n line-height: 0;\n position: relative;\n vertical-align: baseline;\n }\n sub {\n bottom: -0.25em;\n }\n sup {\n top: -0.5em;\n }\n table {\n text-indent: 0;\n border-color: inherit;\n border-collapse: collapse;\n }\n :-moz-focusring {\n outline: auto;\n }\n progress {\n vertical-align: baseline;\n }\n summary {\n display: list-item;\n }\n ol, ul, menu {\n list-style: none;\n }\n img, svg, video, canvas, audio, iframe, embed, object {\n display: block;\n vertical-align: middle;\n }\n img, video {\n max-width: 100%;\n height: auto;\n }\n button, input, select, optgroup, textarea, ::file-selector-button {\n font: inherit;\n font-feature-settings: inherit;\n font-variation-settings: inherit;\n letter-spacing: inherit;\n color: inherit;\n border-radius: 0;\n background-color: transparent;\n opacity: 1;\n }\n :where(select:is([multiple], [size])) optgroup {\n font-weight: bolder;\n }\n :where(select:is([multiple], [size])) optgroup option {\n padding-inline-start: 20px;\n }\n ::file-selector-button {\n margin-inline-end: 4px;\n }\n ::placeholder {\n opacity: 1;\n }\n @supports (not (-webkit-appearance: -apple-pay-button)) or (contain-intrinsic-size: 1px) {\n ::placeholder {\n color: currentcolor;\n @supports (color: color-mix(in lab, red, red)) {\n color: color-mix(in oklab, currentcolor 50%, transparent);\n }\n }\n }\n textarea {\n resize: vertical;\n }\n ::-webkit-search-decoration {\n -webkit-appearance: none;\n }\n ::-webkit-date-and-time-value {\n min-height: 1lh;\n text-align: inherit;\n }\n ::-webkit-datetime-edit {\n display: inline-flex;\n }\n ::-webkit-datetime-edit-fields-wrapper {\n padding: 0;\n }\n ::-webkit-datetime-edit, ::-webkit-datetime-edit-year-field, ::-webkit-datetime-edit-month-field, ::-webkit-datetime-edit-day-field, ::-webkit-datetime-edit-hour-field, ::-webkit-datetime-edit-minute-field, ::-webkit-datetime-edit-second-field, ::-webkit-datetime-edit-millisecond-field, ::-webkit-datetime-edit-meridiem-field {\n padding-block: 0;\n }\n ::-webkit-calendar-picker-indicator {\n line-height: 1;\n }\n :-moz-ui-invalid {\n box-shadow: none;\n }\n button, input:where([type="button"], [type="reset"], [type="submit"]), ::file-selector-button {\n appearance: button;\n }\n ::-webkit-inner-spin-button, ::-webkit-outer-spin-button {\n height: auto;\n }\n [hidden]:where(:not([hidden="until-found"])) {\n display: none !important;\n }\n}\n@layer utilities {\n .pointer-events-none {\n pointer-events: none;\n }\n .visible {\n visibility: visible;\n }\n .sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n margin: -1px;\n overflow: hidden;\n clip-path: inset(50%);\n white-space: nowrap;\n border-width: 0;\n }\n .absolute {\n position: absolute;\n }\n .fixed {\n position: fixed;\n }\n .relative {\n position: relative;\n }\n .static {\n position: static;\n }\n .inset-0 {\n inset: calc(var(--spacing) * 0);\n }\n .inset-x-0 {\n inset-inline: calc(var(--spacing) * 0);\n }\n .inset-y-0 {\n inset-block: calc(var(--spacing) * 0);\n }\n .-top-3 {\n top: calc(var(--spacing) * -3);\n }\n .-top-4 {\n top: calc(var(--spacing) * -4);\n }\n .top-0 {\n top: calc(var(--spacing) * 0);\n }\n .top-2 {\n top: calc(var(--spacing) * 2);\n }\n .top-3 {\n top: calc(var(--spacing) * 3);\n }\n .top-4 {\n top: calc(var(--spacing) * 4);\n }\n .right-0 {\n right: calc(var(--spacing) * 0);\n }\n .right-0\\.5 {\n right: calc(var(--spacing) * 0.5);\n }\n .right-2 {\n right: calc(var(--spacing) * 2);\n }\n .right-3 {\n right: calc(var(--spacing) * 3);\n }\n .right-4 {\n right: calc(var(--spacing) * 4);\n }\n .bottom-0 {\n bottom: calc(var(--spacing) * 0);\n }\n .bottom-4 {\n bottom: calc(var(--spacing) * 4);\n }\n .left-0 {\n left: calc(var(--spacing) * 0);\n }\n .left-1\\/2 {\n left: calc(1/2 * 100%);\n }\n .isolate {\n isolation: isolate;\n }\n .z-10 {\n z-index: 10;\n }\n .z-20 {\n z-index: 20;\n }\n .z-50 {\n z-index: 50;\n }\n .container {\n width: 100%;\n @media (width >= 40rem) {\n max-width: 40rem;\n }\n @media (width >= 48rem) {\n max-width: 48rem;\n }\n @media (width >= 64rem) {\n max-width: 64rem;\n }\n @media (width >= 80rem) {\n max-width: 80rem;\n }\n @media (width >= 96rem) {\n max-width: 96rem;\n }\n }\n .m-0 {\n margin: calc(var(--spacing) * 0);\n }\n .mx-auto {\n margin-inline: auto;\n }\n .my-2 {\n margin-block: calc(var(--spacing) * 2);\n }\n .mt-0 {\n margin-top: calc(var(--spacing) * 0);\n }\n .mt-0\\.5 {\n margin-top: calc(var(--spacing) * 0.5);\n }\n .mt-1 {\n margin-top: calc(var(--spacing) * 1);\n }\n .mt-2 {\n margin-top: calc(var(--spacing) * 2);\n }\n .mt-3 {\n margin-top: calc(var(--spacing) * 3);\n }\n .mt-4 {\n margin-top: calc(var(--spacing) * 4);\n }\n .mt-6 {\n margin-top: calc(var(--spacing) * 6);\n }\n .mt-8 {\n margin-top: calc(var(--spacing) * 8);\n }\n .mr-1 {\n margin-right: calc(var(--spacing) * 1);\n }\n .mr-2 {\n margin-right: calc(var(--spacing) * 2);\n }\n .mb-1 {\n margin-bottom: calc(var(--spacing) * 1);\n }\n .mb-2 {\n margin-bottom: calc(var(--spacing) * 2);\n }\n .mb-3 {\n margin-bottom: calc(var(--spacing) * 3);\n }\n .mb-4 {\n margin-bottom: calc(var(--spacing) * 4);\n }\n .mb-6 {\n margin-bottom: calc(var(--spacing) * 6);\n }\n .mb-8 {\n margin-bottom: calc(var(--spacing) * 8);\n }\n .mb-12 {\n margin-bottom: calc(var(--spacing) * 12);\n }\n .ml-1 {\n margin-left: calc(var(--spacing) * 1);\n }\n .ml-3 {\n margin-left: calc(var(--spacing) * 3);\n }\n .ml-4 {\n margin-left: calc(var(--spacing) * 4);\n }\n .block {\n display: block;\n }\n .flex {\n display: flex;\n }\n .grid {\n display: grid;\n }\n .hidden {\n display: none;\n }\n .inline {\n display: inline;\n }\n .inline-block {\n display: inline-block;\n }\n .inline-flex {\n display: inline-flex;\n }\n .table {\n display: table;\n }\n .aspect-square {\n aspect-ratio: 1 / 1;\n }\n .h-1\\.5 {\n height: calc(var(--spacing) * 1.5);\n }\n .h-2 {\n height: calc(var(--spacing) * 2);\n }\n .h-2\\.5 {\n height: calc(var(--spacing) * 2.5);\n }\n .h-3 {\n height: calc(var(--spacing) * 3);\n }\n .h-4 {\n height: calc(var(--spacing) * 4);\n }\n .h-5 {\n height: calc(var(--spacing) * 5);\n }\n .h-6 {\n height: calc(var(--spacing) * 6);\n }\n .h-8 {\n height: calc(var(--spacing) * 8);\n }\n .h-9 {\n height: calc(var(--spacing) * 9);\n }\n .h-10 {\n height: calc(var(--spacing) * 10);\n }\n .h-11 {\n height: calc(var(--spacing) * 11);\n }\n .h-12 {\n height: calc(var(--spacing) * 12);\n }\n .h-16 {\n height: calc(var(--spacing) * 16);\n }\n .h-20 {\n height: calc(var(--spacing) * 20);\n }\n .h-40 {\n height: calc(var(--spacing) * 40);\n }\n .h-\\[1px\\] {\n height: 1px;\n }\n .h-\\[600px\\] {\n height: 600px;\n }\n .h-\\[650px\\] {\n height: 650px;\n }\n .h-full {\n height: 100%;\n }\n .max-h-\\[80vh\\] {\n max-height: 80vh;\n }\n .max-h-\\[90vh\\] {\n max-height: 90vh;\n }\n .min-h-0 {\n min-height: calc(var(--spacing) * 0);\n }\n .min-h-\\[80px\\] {\n min-height: 80px;\n }\n .min-h-screen {\n min-height: 100vh;\n }\n .w-1\\.5 {\n width: calc(var(--spacing) * 1.5);\n }\n .w-1\\/4 {\n width: calc(1/4 * 100%);\n }\n .w-2\\.5 {\n width: calc(var(--spacing) * 2.5);\n }\n .w-3 {\n width: calc(var(--spacing) * 3);\n }\n .w-3\\/4 {\n width: calc(3/4 * 100%);\n }\n .w-4 {\n width: calc(var(--spacing) * 4);\n }\n .w-5 {\n width: calc(var(--spacing) * 5);\n }\n .w-6 {\n width: calc(var(--spacing) * 6);\n }\n .w-8 {\n width: calc(var(--spacing) * 8);\n }\n .w-10 {\n width: calc(var(--spacing) * 10);\n }\n .w-12 {\n width: calc(var(--spacing) * 12);\n }\n .w-16 {\n width: calc(var(--spacing) * 16);\n }\n .w-20 {\n width: calc(var(--spacing) * 20);\n }\n .w-24 {\n width: calc(var(--spacing) * 24);\n }\n .w-28 {\n width: calc(var(--spacing) * 28);\n }\n .w-32 {\n width: calc(var(--spacing) * 32);\n }\n .w-36 {\n width: calc(var(--spacing) * 36);\n }\n .w-40 {\n width: calc(var(--spacing) * 40);\n }\n .w-44 {\n width: calc(var(--spacing) * 44);\n }\n .w-48 {\n width: calc(var(--spacing) * 48);\n }\n .w-64 {\n width: calc(var(--spacing) * 64);\n }\n .w-80 {\n width: calc(var(--spacing) * 80);\n }\n .w-96 {\n width: calc(var(--spacing) * 96);\n }\n .w-\\[1px\\] {\n width: 1px;\n }\n .w-\\[200px\\] {\n width: 200px;\n }\n .w-\\[450px\\] {\n width: 450px;\n }\n .w-full {\n width: 100%;\n }\n .max-w-2xl {\n max-width: var(--container-2xl);\n }\n .max-w-4xl {\n max-width: var(--container-4xl);\n }\n .max-w-7xl {\n max-width: var(--container-7xl);\n }\n .max-w-\\[200px\\] {\n max-width: 200px;\n }\n .max-w-\\[calc\\(100vw-2rem\\)\\] {\n max-width: calc(100vw - 2rem);\n }\n .max-w-lg {\n max-width: var(--container-lg);\n }\n .max-w-md {\n max-width: var(--container-md);\n }\n .min-w-0 {\n min-width: calc(var(--spacing) * 0);\n }\n .flex-1 {\n flex: 1;\n }\n .flex-shrink-0 {\n flex-shrink: 0;\n }\n .shrink-0 {\n flex-shrink: 0;\n }\n .caption-bottom {\n caption-side: bottom;\n }\n .-translate-x-1\\/2 {\n --tw-translate-x: calc(calc(1/2 * 100%) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n .scale-105 {\n --tw-scale-x: 105%;\n --tw-scale-y: 105%;\n --tw-scale-z: 105%;\n scale: var(--tw-scale-x) var(--tw-scale-y);\n }\n .transform {\n transform: var(--tw-rotate-x,) var(--tw-rotate-y,) var(--tw-rotate-z,) var(--tw-skew-x,) var(--tw-skew-y,);\n }\n .animate-pulse {\n animation: var(--animate-pulse);\n }\n .animate-spin {\n animation: var(--animate-spin);\n }\n .cursor-default {\n cursor: default;\n }\n .cursor-pointer {\n cursor: pointer;\n }\n .touch-none {\n touch-action: none;\n }\n .resize {\n resize: both;\n }\n .resize-none {\n resize: none;\n }\n .list-inside {\n list-style-position: inside;\n }\n .list-disc {\n list-style-type: disc;\n }\n .grid-cols-1 {\n grid-template-columns: repeat(1, minmax(0, 1fr));\n }\n .grid-cols-2 {\n grid-template-columns: repeat(2, minmax(0, 1fr));\n }\n .grid-cols-4 {\n grid-template-columns: repeat(4, minmax(0, 1fr));\n }\n .flex-col {\n flex-direction: column;\n }\n .flex-col-reverse {\n flex-direction: column-reverse;\n }\n .flex-wrap {\n flex-wrap: wrap;\n }\n .items-baseline {\n align-items: baseline;\n }\n .items-center {\n align-items: center;\n }\n .items-start {\n align-items: flex-start;\n }\n .justify-between {\n justify-content: space-between;\n }\n .justify-center {\n justify-content: center;\n }\n .justify-end {\n justify-content: flex-end;\n }\n .gap-1 {\n gap: calc(var(--spacing) * 1);\n }\n .gap-2 {\n gap: calc(var(--spacing) * 2);\n }\n .gap-3 {\n gap: calc(var(--spacing) * 3);\n }\n .gap-4 {\n gap: calc(var(--spacing) * 4);\n }\n .gap-8 {\n gap: calc(var(--spacing) * 8);\n }\n .space-y-1 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 1) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 1) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-1\\.5 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 1.5) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 1.5) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-2 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 2) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-3 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 3) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 3) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-4 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 4) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 4) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-6 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 6) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 6) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-x-2 {\n :where(& > :not(:last-child)) {\n --tw-space-x-reverse: 0;\n margin-inline-start: calc(calc(var(--spacing) * 2) * var(--tw-space-x-reverse));\n margin-inline-end: calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-x-reverse)));\n }\n }\n .space-x-4 {\n :where(& > :not(:last-child)) {\n --tw-space-x-reverse: 0;\n margin-inline-start: calc(calc(var(--spacing) * 4) * var(--tw-space-x-reverse));\n margin-inline-end: calc(calc(var(--spacing) * 4) * calc(1 - var(--tw-space-x-reverse)));\n }\n }\n .overflow-auto {\n overflow: auto;\n }\n .overflow-hidden {\n overflow: hidden;\n }\n .overflow-x-auto {\n overflow-x: auto;\n }\n .overflow-x-hidden {\n overflow-x: hidden;\n }\n .overflow-y-auto {\n overflow-y: auto;\n }\n .overflow-y-hidden {\n overflow-y: hidden;\n }\n .rounded {\n border-radius: 0.25rem;\n }\n .rounded-2xl {\n border-radius: var(--radius-2xl);\n }\n .rounded-\\[inherit\\] {\n border-radius: inherit;\n }\n .rounded-full {\n border-radius: calc(infinity * 1px);\n }\n .rounded-lg {\n border-radius: var(--radius);\n }\n .rounded-md {\n border-radius: calc(var(--radius) - 2px);\n }\n .rounded-sm {\n border-radius: calc(var(--radius) - 4px);\n }\n .rounded-t-\\[10px\\] {\n border-top-left-radius: 10px;\n border-top-right-radius: 10px;\n }\n .border {\n border-style: var(--tw-border-style);\n border-width: 1px;\n }\n .border-0 {\n border-style: var(--tw-border-style);\n border-width: 0px;\n }\n .border-2 {\n border-style: var(--tw-border-style);\n border-width: 2px;\n }\n .border-t {\n border-top-style: var(--tw-border-style);\n border-top-width: 1px;\n }\n .border-r {\n border-right-style: var(--tw-border-style);\n border-right-width: 1px;\n }\n .border-b {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 1px;\n }\n .border-b-2 {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 2px;\n }\n .border-l {\n border-left-style: var(--tw-border-style);\n border-left-width: 1px;\n }\n .border-dashed {\n --tw-border-style: dashed;\n border-style: dashed;\n }\n .border-none {\n --tw-border-style: none;\n border-style: none;\n }\n .border-blue-600 {\n border-color: var(--color-blue-600);\n }\n .border-destructive\\/50 {\n border-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, hsl(var(--destructive)) 50%, transparent);\n }\n }\n .border-gray-200 {\n border-color: var(--color-gray-200);\n }\n .border-gray-300 {\n border-color: var(--color-gray-300);\n }\n .border-green-200 {\n border-color: var(--color-green-200);\n }\n .border-green-500\\/50 {\n border-color: color-mix(in srgb, oklch(72.3% 0.219 149.579) 50%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, var(--color-green-500) 50%, transparent);\n }\n }\n .border-green-600 {\n border-color: var(--color-green-600);\n }\n .border-input {\n border-color: hsl(var(--input));\n }\n .border-primary {\n border-color: hsl(var(--primary));\n }\n .border-primary\\/20 {\n border-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, hsl(var(--primary)) 20%, transparent);\n }\n }\n .border-primary\\/50 {\n border-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, hsl(var(--primary)) 50%, transparent);\n }\n }\n .border-transparent {\n border-color: transparent;\n }\n .border-yellow-500\\/50 {\n border-color: color-mix(in srgb, oklch(79.5% 0.184 86.047) 50%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, var(--color-yellow-500) 50%, transparent);\n }\n }\n .border-t-transparent {\n border-top-color: transparent;\n }\n .border-l-transparent {\n border-left-color: transparent;\n }\n .bg-background {\n background-color: hsl(var(--background));\n }\n .bg-black\\/50 {\n background-color: color-mix(in srgb, #000 50%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-black) 50%, transparent);\n }\n }\n .bg-black\\/80 {\n background-color: color-mix(in srgb, #000 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-black) 80%, transparent);\n }\n }\n .bg-blue-600 {\n background-color: var(--color-blue-600);\n }\n .bg-border {\n background-color: hsl(var(--border));\n }\n .bg-card {\n background-color: hsl(var(--card));\n }\n .bg-destructive {\n background-color: hsl(var(--destructive));\n }\n .bg-destructive\\/10 {\n background-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--destructive)) 10%, transparent);\n }\n }\n .bg-foreground {\n background-color: hsl(var(--foreground));\n }\n .bg-foreground\\/5 {\n background-color: hsl(var(--foreground));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--foreground)) 5%, transparent);\n }\n }\n .bg-gray-50 {\n background-color: var(--color-gray-50);\n }\n .bg-gray-100 {\n background-color: var(--color-gray-100);\n }\n .bg-gray-200 {\n background-color: var(--color-gray-200);\n }\n .bg-gray-400 {\n background-color: var(--color-gray-400);\n }\n .bg-gray-600 {\n background-color: var(--color-gray-600);\n }\n .bg-green-50 {\n background-color: var(--color-green-50);\n }\n .bg-green-100 {\n background-color: var(--color-green-100);\n }\n .bg-green-500 {\n background-color: var(--color-green-500);\n }\n .bg-muted {\n background-color: hsl(var(--muted));\n }\n .bg-muted-foreground\\/30 {\n background-color: hsl(var(--muted-foreground));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--muted-foreground)) 30%, transparent);\n }\n }\n .bg-muted\\/50 {\n background-color: hsl(var(--muted));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--muted)) 50%, transparent);\n }\n }\n .bg-primary {\n background-color: hsl(var(--primary));\n }\n .bg-primary\\/10 {\n background-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--primary)) 10%, transparent);\n }\n }\n .bg-red-50 {\n background-color: var(--color-red-50);\n }\n .bg-red-100 {\n background-color: var(--color-red-100);\n }\n .bg-red-500 {\n background-color: var(--color-red-500);\n }\n .bg-secondary {\n background-color: hsl(var(--secondary));\n }\n .bg-white {\n background-color: var(--color-white);\n }\n .bg-white\\/80 {\n background-color: color-mix(in srgb, #fff 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-white) 80%, transparent);\n }\n }\n .bg-yellow-50 {\n background-color: var(--color-yellow-50);\n }\n .bg-yellow-100 {\n background-color: var(--color-yellow-100);\n }\n .bg-yellow-500 {\n background-color: var(--color-yellow-500);\n }\n .bg-gradient-to-br {\n --tw-gradient-position: to bottom right in oklab;\n background-image: linear-gradient(var(--tw-gradient-stops));\n }\n .bg-gradient-to-r {\n --tw-gradient-position: to right in oklab;\n background-image: linear-gradient(var(--tw-gradient-stops));\n }\n .from-blue-100 {\n --tw-gradient-from: var(--color-blue-100);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .from-blue-500 {\n --tw-gradient-from: var(--color-blue-500);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .from-blue-600 {\n --tw-gradient-from: var(--color-blue-600);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .to-purple-100 {\n --tw-gradient-to: var(--color-purple-100);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .to-purple-600 {\n --tw-gradient-to: var(--color-purple-600);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .p-0 {\n padding: calc(var(--spacing) * 0);\n }\n .p-1 {\n padding: calc(var(--spacing) * 1);\n }\n .p-2 {\n padding: calc(var(--spacing) * 2);\n }\n .p-3 {\n padding: calc(var(--spacing) * 3);\n }\n .p-4 {\n padding: calc(var(--spacing) * 4);\n }\n .p-6 {\n padding: calc(var(--spacing) * 6);\n }\n .p-8 {\n padding: calc(var(--spacing) * 8);\n }\n .p-\\[1px\\] {\n padding: 1px;\n }\n .px-2 {\n padding-inline: calc(var(--spacing) * 2);\n }\n .px-2\\.5 {\n padding-inline: calc(var(--spacing) * 2.5);\n }\n .px-3 {\n padding-inline: calc(var(--spacing) * 3);\n }\n .px-4 {\n padding-inline: calc(var(--spacing) * 4);\n }\n .px-6 {\n padding-inline: calc(var(--spacing) * 6);\n }\n .px-8 {\n padding-inline: calc(var(--spacing) * 8);\n }\n .py-0\\.5 {\n padding-block: calc(var(--spacing) * 0.5);\n }\n .py-1 {\n padding-block: calc(var(--spacing) * 1);\n }\n .py-1\\.5 {\n padding-block: calc(var(--spacing) * 1.5);\n }\n .py-2 {\n padding-block: calc(var(--spacing) * 2);\n }\n .py-3 {\n padding-block: calc(var(--spacing) * 3);\n }\n .py-4 {\n padding-block: calc(var(--spacing) * 4);\n }\n .py-6 {\n padding-block: calc(var(--spacing) * 6);\n }\n .py-8 {\n padding-block: calc(var(--spacing) * 8);\n }\n .py-12 {\n padding-block: calc(var(--spacing) * 12);\n }\n .pt-0 {\n padding-top: calc(var(--spacing) * 0);\n }\n .pt-2 {\n padding-top: calc(var(--spacing) * 2);\n }\n .pt-4 {\n padding-top: calc(var(--spacing) * 4);\n }\n .pt-6 {\n padding-top: calc(var(--spacing) * 6);\n }\n .pt-8 {\n padding-top: calc(var(--spacing) * 8);\n }\n .pr-4 {\n padding-right: calc(var(--spacing) * 4);\n }\n .pr-6 {\n padding-right: calc(var(--spacing) * 6);\n }\n .pr-8 {\n padding-right: calc(var(--spacing) * 8);\n }\n .pb-2 {\n padding-bottom: calc(var(--spacing) * 2);\n }\n .pb-4 {\n padding-bottom: calc(var(--spacing) * 4);\n }\n .pb-6 {\n padding-bottom: calc(var(--spacing) * 6);\n }\n .text-center {\n text-align: center;\n }\n .text-left {\n text-align: left;\n }\n .text-right {\n text-align: right;\n }\n .align-middle {\n vertical-align: middle;\n }\n .text-2xl {\n font-size: var(--text-2xl);\n line-height: var(--tw-leading, var(--text-2xl--line-height));\n }\n .text-3xl {\n font-size: var(--text-3xl);\n line-height: var(--tw-leading, var(--text-3xl--line-height));\n }\n .text-4xl {\n font-size: var(--text-4xl);\n line-height: var(--tw-leading, var(--text-4xl--line-height));\n }\n .text-5xl {\n font-size: var(--text-5xl);\n line-height: var(--tw-leading, var(--text-5xl--line-height));\n }\n .text-base {\n font-size: var(--text-base);\n line-height: var(--tw-leading, var(--text-base--line-height));\n }\n .text-lg {\n font-size: var(--text-lg);\n line-height: var(--tw-leading, var(--text-lg--line-height));\n }\n .text-sm {\n font-size: var(--text-sm);\n line-height: var(--tw-leading, var(--text-sm--line-height));\n }\n .text-xl {\n font-size: var(--text-xl);\n line-height: var(--tw-leading, var(--text-xl--line-height));\n }\n .text-xs {\n font-size: var(--text-xs);\n line-height: var(--tw-leading, var(--text-xs--line-height));\n }\n .leading-none {\n --tw-leading: 1;\n line-height: 1;\n }\n .leading-tight {\n --tw-leading: var(--leading-tight);\n line-height: var(--leading-tight);\n }\n .font-bold {\n --tw-font-weight: var(--font-weight-bold);\n font-weight: var(--font-weight-bold);\n }\n .font-medium {\n --tw-font-weight: var(--font-weight-medium);\n font-weight: var(--font-weight-medium);\n }\n .font-normal {\n --tw-font-weight: var(--font-weight-normal);\n font-weight: var(--font-weight-normal);\n }\n .font-semibold {\n --tw-font-weight: var(--font-weight-semibold);\n font-weight: var(--font-weight-semibold);\n }\n .tracking-tight {\n --tw-tracking: var(--tracking-tight);\n letter-spacing: var(--tracking-tight);\n }\n .whitespace-nowrap {\n white-space: nowrap;\n }\n .text-amber-500 {\n color: var(--color-amber-500);\n }\n .text-background {\n color: hsl(var(--background));\n }\n .text-background\\/70 {\n color: hsl(var(--background));\n @supports (color: color-mix(in lab, red, red)) {\n color: color-mix(in oklab, hsl(var(--background)) 70%, transparent);\n }\n }\n .text-blue-800 {\n color: var(--color-blue-800);\n }\n .text-card-foreground {\n color: hsl(var(--card-foreground));\n }\n .text-destructive {\n color: hsl(var(--destructive));\n }\n .text-destructive-foreground {\n color: hsl(var(--destructive-foreground));\n }\n .text-foreground {\n color: hsl(var(--foreground));\n }\n .text-gray-400 {\n color: var(--color-gray-400);\n }\n .text-gray-500 {\n color: var(--color-gray-500);\n }\n .text-gray-600 {\n color: var(--color-gray-600);\n }\n .text-gray-700 {\n color: var(--color-gray-700);\n }\n .text-gray-900 {\n color: var(--color-gray-900);\n }\n .text-green-500 {\n color: var(--color-green-500);\n }\n .text-green-600 {\n color: var(--color-green-600);\n }\n .text-green-700 {\n color: var(--color-green-700);\n }\n .text-green-800 {\n color: var(--color-green-800);\n }\n .text-green-900 {\n color: var(--color-green-900);\n }\n .text-muted-foreground {\n color: hsl(var(--muted-foreground));\n }\n .text-primary {\n color: hsl(var(--primary));\n }\n .text-primary-foreground {\n color: hsl(var(--primary-foreground));\n }\n .text-red-500 {\n color: var(--color-red-500);\n }\n .text-red-600 {\n color: var(--color-red-600);\n }\n .text-red-800 {\n color: var(--color-red-800);\n }\n .text-secondary-foreground {\n color: hsl(var(--secondary-foreground));\n }\n .text-white {\n color: var(--color-white);\n }\n .text-yellow-600 {\n color: var(--color-yellow-600);\n }\n .text-yellow-800 {\n color: var(--color-yellow-800);\n }\n .text-yellow-900 {\n color: var(--color-yellow-900);\n }\n .uppercase {\n text-transform: uppercase;\n }\n .underline {\n text-decoration-line: underline;\n }\n .underline-offset-4 {\n text-underline-offset: 4px;\n }\n .opacity-0 {\n opacity: 0%;\n }\n .opacity-25 {\n opacity: 25%;\n }\n .opacity-50 {\n opacity: 50%;\n }\n .opacity-60 {\n opacity: 60%;\n }\n .opacity-70 {\n opacity: 70%;\n }\n .opacity-75 {\n opacity: 75%;\n }\n .opacity-100 {\n opacity: 100%;\n }\n .shadow {\n --tw-shadow: 0 1px 3px 0 var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 1px 2px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-lg {\n --tw-shadow: 0 10px 15px -3px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 4px 6px -4px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-sm {\n --tw-shadow: 0 1px 3px 0 var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 1px 2px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-xl {\n --tw-shadow: 0 20px 25px -5px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 8px 10px -6px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .ring {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .ring-2 {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .ring-primary {\n --tw-ring-color: hsl(var(--primary));\n }\n .ring-offset-background {\n --tw-ring-offset-color: hsl(var(--background));\n }\n .outline {\n outline-style: var(--tw-outline-style);\n outline-width: 1px;\n }\n .filter {\n filter: var(--tw-blur,) var(--tw-brightness,) var(--tw-contrast,) var(--tw-grayscale,) var(--tw-hue-rotate,) var(--tw-invert,) var(--tw-saturate,) var(--tw-sepia,) var(--tw-drop-shadow,);\n }\n .backdrop-blur-sm {\n --tw-backdrop-blur: blur(var(--blur-sm));\n -webkit-backdrop-filter: var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,);\n backdrop-filter: var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,);\n }\n .transition-all {\n transition-property: all;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-colors {\n transition-property: color, background-color, border-color, outline-color, text-decoration-color, fill, stroke, --tw-gradient-from, --tw-gradient-via, --tw-gradient-to;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-opacity {\n transition-property: opacity;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-transform {\n transition-property: transform, translate, scale, rotate;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .duration-150 {\n --tw-duration: 150ms;\n transition-duration: 150ms;\n }\n .duration-200 {\n --tw-duration: 200ms;\n transition-duration: 200ms;\n }\n .duration-300 {\n --tw-duration: 300ms;\n transition-duration: 300ms;\n }\n .duration-400 {\n --tw-duration: 400ms;\n transition-duration: 400ms;\n }\n .ease-in-out {\n --tw-ease: var(--ease-in-out);\n transition-timing-function: var(--ease-in-out);\n }\n .ease-out {\n --tw-ease: var(--ease-out);\n transition-timing-function: var(--ease-out);\n }\n .select-none {\n -webkit-user-select: none;\n user-select: none;\n }\n .\\[-ms-overflow-style\\:none\\] {\n -ms-overflow-style: none;\n }\n .\\[scrollbar-width\\:none\\] {\n scrollbar-width: none;\n }\n .peer-disabled\\:cursor-not-allowed {\n &:is(:where(.peer):disabled ~ *) {\n cursor: not-allowed;\n }\n }\n .peer-disabled\\:opacity-70 {\n &:is(:where(.peer):disabled ~ *) {\n opacity: 70%;\n }\n }\n .file\\:border-0 {\n &::file-selector-button {\n border-style: var(--tw-border-style);\n border-width: 0px;\n }\n }\n .file\\:bg-transparent {\n &::file-selector-button {\n background-color: transparent;\n }\n }\n .file\\:text-sm {\n &::file-selector-button {\n font-size: var(--text-sm);\n line-height: var(--tw-leading, var(--text-sm--line-height));\n }\n }\n .file\\:font-medium {\n &::file-selector-button {\n --tw-font-weight: var(--font-weight-medium);\n font-weight: var(--font-weight-medium);\n }\n }\n .file\\:text-foreground {\n &::file-selector-button {\n color: hsl(var(--foreground));\n }\n }\n .placeholder\\:text-muted-foreground {\n &::placeholder {\n color: hsl(var(--muted-foreground));\n }\n }\n .checked\\:bg-primary {\n &:checked {\n background-color: hsl(var(--primary));\n }\n }\n .checked\\:text-primary-foreground {\n &:checked {\n color: hsl(var(--primary-foreground));\n }\n }\n .hover\\:border-gray-300 {\n &:hover {\n @media (hover: hover) {\n border-color: var(--color-gray-300);\n }\n }\n }\n .hover\\:border-primary {\n &:hover {\n @media (hover: hover) {\n border-color: hsl(var(--primary));\n }\n }\n }\n .hover\\:bg-accent {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--accent));\n }\n }\n }\n .hover\\:bg-background\\/50 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--background));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--background)) 50%, transparent);\n }\n }\n }\n }\n .hover\\:bg-destructive\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--destructive)) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-destructive\\/90 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--destructive)) 90%, transparent);\n }\n }\n }\n }\n .hover\\:bg-foreground\\/90 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--foreground));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--foreground)) 90%, transparent);\n }\n }\n }\n }\n .hover\\:bg-gray-200 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-200);\n }\n }\n }\n .hover\\:bg-gray-300 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-300);\n }\n }\n }\n .hover\\:bg-gray-600 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-600);\n }\n }\n }\n .hover\\:bg-gray-700 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-700);\n }\n }\n }\n .hover\\:bg-green-500\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: color-mix(in srgb, oklch(72.3% 0.219 149.579) 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-green-500) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-muted {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--muted));\n }\n }\n }\n .hover\\:bg-muted\\/50 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--muted));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--muted)) 50%, transparent);\n }\n }\n }\n }\n .hover\\:bg-primary\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--primary)) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-primary\\/90 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--primary)) 90%, transparent);\n }\n }\n }\n }\n .hover\\:bg-secondary\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--secondary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--secondary)) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-transparent {\n &:hover {\n @media (hover: hover) {\n background-color: transparent;\n }\n }\n }\n .hover\\:bg-yellow-500\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: color-mix(in srgb, oklch(79.5% 0.184 86.047) 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-yellow-500) 80%, transparent);\n }\n }\n }\n }\n .hover\\:from-blue-700 {\n &:hover {\n @media (hover: hover) {\n --tw-gradient-from: var(--color-blue-700);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n }\n }\n .hover\\:to-purple-700 {\n &:hover {\n @media (hover: hover) {\n --tw-gradient-to: var(--color-purple-700);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n }\n }\n .hover\\:text-accent-foreground {\n &:hover {\n @media (hover: hover) {\n color: hsl(var(--accent-foreground));\n }\n }\n }\n .hover\\:text-destructive {\n &:hover {\n @media (hover: hover) {\n color: hsl(var(--destructive));\n }\n }\n }\n .hover\\:text-foreground {\n &:hover {\n @media (hover: hover) {\n color: hsl(var(--foreground));\n }\n }\n }\n .hover\\:text-gray-700 {\n &:hover {\n @media (hover: hover) {\n color: var(--color-gray-700);\n }\n }\n }\n .hover\\:text-yellow-900 {\n &:hover {\n @media (hover: hover) {\n color: var(--color-yellow-900);\n }\n }\n }\n .hover\\:underline {\n &:hover {\n @media (hover: hover) {\n text-decoration-line: underline;\n }\n }\n }\n .hover\\:opacity-100 {\n &:hover {\n @media (hover: hover) {\n opacity: 100%;\n }\n }\n }\n .hover\\:shadow-lg {\n &:hover {\n @media (hover: hover) {\n --tw-shadow: 0 10px 15px -3px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 4px 6px -4px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n }\n }\n .focus\\:ring-2 {\n &:focus {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n }\n .focus\\:ring-blue-500 {\n &:focus {\n --tw-ring-color: var(--color-blue-500);\n }\n }\n .focus\\:ring-ring {\n &:focus {\n --tw-ring-color: hsl(var(--ring));\n }\n }\n .focus\\:ring-offset-2 {\n &:focus {\n --tw-ring-offset-width: 2px;\n --tw-ring-offset-shadow: var(--tw-ring-inset,) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);\n }\n }\n .focus\\:outline-none {\n &:focus {\n --tw-outline-style: none;\n outline-style: none;\n }\n }\n .focus-visible\\:ring-2 {\n &:focus-visible {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n }\n .focus-visible\\:ring-ring {\n &:focus-visible {\n --tw-ring-color: hsl(var(--ring));\n }\n }\n .focus-visible\\:ring-offset-2 {\n &:focus-visible {\n --tw-ring-offset-width: 2px;\n --tw-ring-offset-shadow: var(--tw-ring-inset,) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);\n }\n }\n .focus-visible\\:outline-none {\n &:focus-visible {\n --tw-outline-style: none;\n outline-style: none;\n }\n }\n .disabled\\:pointer-events-none {\n &:disabled {\n pointer-events: none;\n }\n }\n .disabled\\:cursor-not-allowed {\n &:disabled {\n cursor: not-allowed;\n }\n }\n .disabled\\:opacity-50 {\n &:disabled {\n opacity: 50%;\n }\n }\n .data-\\[state\\=selected\\]\\:bg-muted {\n &[data-state="selected"] {\n background-color: hsl(var(--muted));\n }\n }\n .sm\\:max-w-2xl {\n @media (width >= 40rem) {\n max-width: var(--container-2xl);\n }\n }\n .sm\\:max-w-6xl {\n @media (width >= 40rem) {\n max-width: var(--container-6xl);\n }\n }\n .sm\\:max-w-\\[500px\\] {\n @media (width >= 40rem) {\n max-width: 500px;\n }\n }\n .sm\\:max-w-\\[600px\\] {\n @media (width >= 40rem) {\n max-width: 600px;\n }\n }\n .sm\\:max-w-\\[800px\\] {\n @media (width >= 40rem) {\n max-width: 800px;\n }\n }\n .sm\\:max-w-lg {\n @media (width >= 40rem) {\n max-width: var(--container-lg);\n }\n }\n .sm\\:max-w-md {\n @media (width >= 40rem) {\n max-width: var(--container-md);\n }\n }\n .sm\\:max-w-sm {\n @media (width >= 40rem) {\n max-width: var(--container-sm);\n }\n }\n .sm\\:flex-1 {\n @media (width >= 40rem) {\n flex: 1;\n }\n }\n .sm\\:flex-row {\n @media (width >= 40rem) {\n flex-direction: row;\n }\n }\n .sm\\:justify-end {\n @media (width >= 40rem) {\n justify-content: flex-end;\n }\n }\n .sm\\:space-x-2 {\n @media (width >= 40rem) {\n :where(& > :not(:last-child)) {\n --tw-space-x-reverse: 0;\n margin-inline-start: calc(calc(var(--spacing) * 2) * var(--tw-space-x-reverse));\n margin-inline-end: calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-x-reverse)));\n }\n }\n }\n .sm\\:rounded-lg {\n @media (width >= 40rem) {\n border-radius: var(--radius);\n }\n }\n .sm\\:px-6 {\n @media (width >= 40rem) {\n padding-inline: calc(var(--spacing) * 6);\n }\n }\n .sm\\:text-left {\n @media (width >= 40rem) {\n text-align: left;\n }\n }\n .md\\:inset-auto {\n @media (width >= 48rem) {\n inset: auto;\n }\n }\n .md\\:top-1\\/2 {\n @media (width >= 48rem) {\n top: calc(1/2 * 100%);\n }\n }\n .md\\:left-1\\/2 {\n @media (width >= 48rem) {\n left: calc(1/2 * 100%);\n }\n }\n .md\\:hidden {\n @media (width >= 48rem) {\n display: none;\n }\n }\n .md\\:max-h-\\[90vh\\] {\n @media (width >= 48rem) {\n max-height: 90vh;\n }\n }\n .md\\:max-h-\\[calc\\(90vh-2rem\\)\\] {\n @media (width >= 48rem) {\n max-height: calc(90vh - 2rem);\n }\n }\n .md\\:w-full {\n @media (width >= 48rem) {\n width: 100%;\n }\n }\n .md\\:max-w-\\[500px\\] {\n @media (width >= 48rem) {\n max-width: 500px;\n }\n }\n .md\\:-translate-x-1\\/2 {\n @media (width >= 48rem) {\n --tw-translate-x: calc(calc(1/2 * 100%) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n .md\\:-translate-y-1\\/2 {\n @media (width >= 48rem) {\n --tw-translate-y: calc(calc(1/2 * 100%) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n .md\\:grid-cols-2 {\n @media (width >= 48rem) {\n grid-template-columns: repeat(2, minmax(0, 1fr));\n }\n }\n .md\\:rounded-lg {\n @media (width >= 48rem) {\n border-radius: var(--radius);\n }\n }\n .md\\:border {\n @media (width >= 48rem) {\n border-style: var(--tw-border-style);\n border-width: 1px;\n }\n }\n .md\\:pt-6 {\n @media (width >= 48rem) {\n padding-top: calc(var(--spacing) * 6);\n }\n }\n .md\\:text-sm {\n @media (width >= 48rem) {\n font-size: var(--text-sm);\n line-height: var(--tw-leading, var(--text-sm--line-height));\n }\n }\n .lg\\:grid-cols-3 {\n @media (width >= 64rem) {\n grid-template-columns: repeat(3, minmax(0, 1fr));\n }\n }\n .lg\\:px-8 {\n @media (width >= 64rem) {\n padding-inline: calc(var(--spacing) * 8);\n }\n }\n .dark\\:border-destructive {\n @media (prefers-color-scheme: dark) {\n border-color: hsl(var(--destructive));\n }\n }\n .dark\\:border-green-800 {\n @media (prefers-color-scheme: dark) {\n border-color: var(--color-green-800);\n }\n }\n .dark\\:bg-green-900 {\n @media (prefers-color-scheme: dark) {\n background-color: var(--color-green-900);\n }\n }\n .dark\\:bg-green-900\\/10 {\n @media (prefers-color-scheme: dark) {\n background-color: color-mix(in srgb, oklch(39.3% 0.095 152.535) 10%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-green-900) 10%, transparent);\n }\n }\n }\n .dark\\:bg-green-900\\/20 {\n @media (prefers-color-scheme: dark) {\n background-color: color-mix(in srgb, oklch(39.3% 0.095 152.535) 20%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-green-900) 20%, transparent);\n }\n }\n }\n .dark\\:bg-yellow-900\\/10 {\n @media (prefers-color-scheme: dark) {\n background-color: color-mix(in srgb, oklch(42.1% 0.095 57.708) 10%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-yellow-900) 10%, transparent);\n }\n }\n }\n .dark\\:text-green-200 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-green-200);\n }\n }\n .dark\\:text-green-300 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-green-300);\n }\n }\n .dark\\:text-green-400 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-green-400);\n }\n }\n .dark\\:text-green-500 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-green-500);\n }\n }\n .dark\\:text-yellow-500 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-yellow-500);\n }\n }\n .\\[\\&_p\\]\\:leading-relaxed {\n & p {\n --tw-leading: var(--leading-relaxed);\n line-height: var(--leading-relaxed);\n }\n }\n .\\[\\&_svg\\]\\:pointer-events-none {\n & svg {\n pointer-events: none;\n }\n }\n .\\[\\&_svg\\]\\:size-4 {\n & svg {\n width: calc(var(--spacing) * 4);\n height: calc(var(--spacing) * 4);\n }\n }\n .\\[\\&_svg\\]\\:shrink-0 {\n & svg {\n flex-shrink: 0;\n }\n }\n .\\[\\&_tr\\]\\:border-b {\n & tr {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 1px;\n }\n }\n .\\[\\&_tr\\:last-child\\]\\:border-0 {\n & tr:last-child {\n border-style: var(--tw-border-style);\n border-width: 0px;\n }\n }\n .\\[\\&\\:\\:-webkit-scrollbar\\]\\:hidden {\n &::-webkit-scrollbar {\n display: none;\n }\n }\n .\\[\\&\\:has\\(\\[role\\=checkbox\\]\\)\\]\\:pr-0 {\n &:has([role=checkbox]) {\n padding-right: calc(var(--spacing) * 0);\n }\n }\n .\\[\\&\\>svg\\]\\:absolute {\n &>svg {\n position: absolute;\n }\n }\n .\\[\\&\\>svg\\]\\:top-4 {\n &>svg {\n top: calc(var(--spacing) * 4);\n }\n }\n .\\[\\&\\>svg\\]\\:left-4 {\n &>svg {\n left: calc(var(--spacing) * 4);\n }\n }\n .\\[\\&\\>svg\\]\\:text-destructive {\n &>svg {\n color: hsl(var(--destructive));\n }\n }\n .\\[\\&\\>svg\\]\\:text-foreground {\n &>svg {\n color: hsl(var(--foreground));\n }\n }\n .\\[\\&\\>svg\\]\\:text-green-500 {\n &>svg {\n color: var(--color-green-500);\n }\n }\n .\\[\\&\\>svg\\]\\:text-yellow-500 {\n &>svg {\n color: var(--color-yellow-500);\n }\n }\n .\\[\\&\\>svg\\+div\\]\\:translate-y-\\[-3px\\] {\n &>svg+div {\n --tw-translate-y: -3px;\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n .\\[\\&\\>svg\\~\\*\\]\\:pl-7 {\n &>svg~* {\n padding-left: calc(var(--spacing) * 7);\n }\n }\n .\\[\\&\\>tr\\]\\:last\\:border-b-0 {\n &>tr {\n &:last-child {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 0px;\n }\n }\n }\n}\n:root {\n --background: 0 0% 100%;\n --foreground: 222.2 84% 4.9%;\n --card: 0 0% 100%;\n --card-foreground: 222.2 84% 4.9%;\n --popover: 0 0% 100%;\n --popover-foreground: 222.2 84% 4.9%;\n --primary: 222.2 47.4% 11.2%;\n --primary-foreground: 210 40% 98%;\n --secondary: 210 40% 96.1%;\n --secondary-foreground: 222.2 47.4% 11.2%;\n --muted: 210 40% 96.1%;\n --muted-foreground: 215.4 16.3% 46.9%;\n --accent: 210 40% 96.1%;\n --accent-foreground: 222.2 47.4% 11.2%;\n --destructive: 0 84.2% 60.2%;\n --destructive-foreground: 210 40% 98%;\n --border: 214.3 31.8% 91.4%;\n --input: 214.3 31.8% 91.4%;\n --ring: 222.2 84% 4.9%;\n --radius: 0.5rem;\n}\n.dark {\n --background: 222.2 84% 4.9%;\n --foreground: 210 40% 98%;\n --card: 222.2 84% 4.9%;\n --card-foreground: 210 40% 98%;\n --popover: 222.2 84% 4.9%;\n --popover-foreground: 210 40% 98%;\n --primary: 210 40% 98%;\n --primary-foreground: 222.2 47.4% 11.2%;\n --secondary: 217.2 32.6% 17.5%;\n --secondary-foreground: 210 40% 98%;\n --muted: 217.2 32.6% 17.5%;\n --muted-foreground: 215 20.2% 65.1%;\n --accent: 217.2 32.6% 17.5%;\n --accent-foreground: 210 40% 98%;\n --destructive: 0 62.8% 30.6%;\n --destructive-foreground: 210 40% 98%;\n --border: 217.2 32.6% 17.5%;\n --input: 217.2 32.6% 17.5%;\n --ring: 212.7 26.8% 83.9%;\n}\n@layer base {\n * {\n border-color: hsl(var(--border));\n }\n body {\n background-color: hsl(var(--background));\n color: hsl(var(--foreground));\n }\n}\n@keyframes accordion-down {\n from {\n height: 0;\n }\n to {\n height: var(--radix-accordion-content-height);\n }\n}\n@keyframes accordion-up {\n from {\n height: var(--radix-accordion-content-height);\n }\n to {\n height: 0;\n }\n}\n.animate-accordion-down {\n animation: accordion-down 0.2s ease-out;\n}\n.animate-accordion-up {\n animation: accordion-up 0.2s ease-out;\n}\n@property --tw-translate-x {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-translate-y {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-translate-z {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-scale-x {\n syntax: "*";\n inherits: false;\n initial-value: 1;\n}\n@property --tw-scale-y {\n syntax: "*";\n inherits: false;\n initial-value: 1;\n}\n@property --tw-scale-z {\n syntax: "*";\n inherits: false;\n initial-value: 1;\n}\n@property --tw-rotate-x {\n syntax: "*";\n inherits: false;\n}\n@property --tw-rotate-y {\n syntax: "*";\n inherits: false;\n}\n@property --tw-rotate-z {\n syntax: "*";\n inherits: false;\n}\n@property --tw-skew-x {\n syntax: "*";\n inherits: false;\n}\n@property --tw-skew-y {\n syntax: "*";\n inherits: false;\n}\n@property --tw-space-y-reverse {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-space-x-reverse {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-border-style {\n syntax: "*";\n inherits: false;\n initial-value: solid;\n}\n@property --tw-gradient-position {\n syntax: "*";\n inherits: false;\n}\n@property --tw-gradient-from {\n syntax: "<color>";\n inherits: false;\n initial-value: #0000;\n}\n@property --tw-gradient-via {\n syntax: "<color>";\n inherits: false;\n initial-value: #0000;\n}\n@property --tw-gradient-to {\n syntax: "<color>";\n inherits: false;\n initial-value: #0000;\n}\n@property --tw-gradient-stops {\n syntax: "*";\n inherits: false;\n}\n@property --tw-gradient-via-stops {\n syntax: "*";\n inherits: false;\n}\n@property --tw-gradient-from-position {\n syntax: "<length-percentage>";\n inherits: false;\n initial-value: 0%;\n}\n@property --tw-gradient-via-position {\n syntax: "<length-percentage>";\n inherits: false;\n initial-value: 50%;\n}\n@property --tw-gradient-to-position {\n syntax: "<length-percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-leading {\n syntax: "*";\n inherits: false;\n}\n@property --tw-font-weight {\n syntax: "*";\n inherits: false;\n}\n@property --tw-tracking {\n syntax: "*";\n inherits: false;\n}\n@property --tw-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-shadow-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-shadow-alpha {\n syntax: "<percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-inset-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-inset-shadow-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-inset-shadow-alpha {\n syntax: "<percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-ring-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-ring-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-inset-ring-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-inset-ring-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-ring-inset {\n syntax: "*";\n inherits: false;\n}\n@property --tw-ring-offset-width {\n syntax: "<length>";\n inherits: false;\n initial-value: 0px;\n}\n@property --tw-ring-offset-color {\n syntax: "*";\n inherits: false;\n initial-value: #fff;\n}\n@property --tw-ring-offset-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-outline-style {\n syntax: "*";\n inherits: false;\n initial-value: solid;\n}\n@property --tw-blur {\n syntax: "*";\n inherits: false;\n}\n@property --tw-brightness {\n syntax: "*";\n inherits: false;\n}\n@property --tw-contrast {\n syntax: "*";\n inherits: false;\n}\n@property --tw-grayscale {\n syntax: "*";\n inherits: false;\n}\n@property --tw-hue-rotate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-invert {\n syntax: "*";\n inherits: false;\n}\n@property --tw-opacity {\n syntax: "*";\n inherits: false;\n}\n@property --tw-saturate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-sepia {\n syntax: "*";\n inherits: false;\n}\n@property --tw-drop-shadow {\n syntax: "*";\n inherits: false;\n}\n@property --tw-drop-shadow-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-drop-shadow-alpha {\n syntax: "<percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-drop-shadow-size {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-blur {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-brightness {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-contrast {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-grayscale {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-hue-rotate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-invert {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-opacity {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-saturate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-sepia {\n syntax: "*";\n inherits: false;\n}\n@property --tw-duration {\n syntax: "*";\n inherits: false;\n}\n@property --tw-ease {\n syntax: "*";\n inherits: false;\n}\n@keyframes spin {\n to {\n transform: rotate(360deg);\n }\n}\n@keyframes pulse {\n 50% {\n opacity: 0.5;\n }\n}\n@layer properties {\n @supports ((-webkit-hyphens: none) and (not (margin-trim: inline))) or ((-moz-orient: inline) and (not (color:rgb(from red r g b)))) {\n *, ::before, ::after, ::backdrop {\n --tw-translate-x: 0;\n --tw-translate-y: 0;\n --tw-translate-z: 0;\n --tw-scale-x: 1;\n --tw-scale-y: 1;\n --tw-scale-z: 1;\n --tw-rotate-x: initial;\n --tw-rotate-y: initial;\n --tw-rotate-z: initial;\n --tw-skew-x: initial;\n --tw-skew-y: initial;\n --tw-space-y-reverse: 0;\n --tw-space-x-reverse: 0;\n --tw-border-style: solid;\n --tw-gradient-position: initial;\n --tw-gradient-from: #0000;\n --tw-gradient-via: #0000;\n --tw-gradient-to: #0000;\n --tw-gradient-stops: initial;\n --tw-gradient-via-stops: initial;\n --tw-gradient-from-position: 0%;\n --tw-gradient-via-position: 50%;\n --tw-gradient-to-position: 100%;\n --tw-leading: initial;\n --tw-font-weight: initial;\n --tw-tracking: initial;\n --tw-shadow: 0 0 #0000;\n --tw-shadow-color: initial;\n --tw-shadow-alpha: 100%;\n --tw-inset-shadow: 0 0 #0000;\n --tw-inset-shadow-color: initial;\n --tw-inset-shadow-alpha: 100%;\n --tw-ring-color: initial;\n --tw-ring-shadow: 0 0 #0000;\n --tw-inset-ring-color: initial;\n --tw-inset-ring-shadow: 0 0 #0000;\n --tw-ring-inset: initial;\n --tw-ring-offset-width: 0px;\n --tw-ring-offset-color: #fff;\n --tw-ring-offset-shadow: 0 0 #0000;\n --tw-outline-style: solid;\n --tw-blur: initial;\n --tw-brightness: initial;\n --tw-contrast: initial;\n --tw-grayscale: initial;\n --tw-hue-rotate: initial;\n --tw-invert: initial;\n --tw-opacity: initial;\n --tw-saturate: initial;\n --tw-sepia: initial;\n --tw-drop-shadow: initial;\n --tw-drop-shadow-color: initial;\n --tw-drop-shadow-alpha: 100%;\n --tw-drop-shadow-size: initial;\n --tw-backdrop-blur: initial;\n --tw-backdrop-brightness: initial;\n --tw-backdrop-contrast: initial;\n --tw-backdrop-grayscale: initial;\n --tw-backdrop-hue-rotate: initial;\n --tw-backdrop-invert: initial;\n --tw-backdrop-opacity: initial;\n --tw-backdrop-saturate: initial;\n --tw-backdrop-sepia: initial;\n --tw-duration: initial;\n --tw-ease: initial;\n }\n }\n}';
|
|
215
|
+
s.textContent = '/*! tailwindcss v4.1.18 | MIT License | https://tailwindcss.com */\n@layer properties;\n@layer theme, base, components, utilities;\n@layer theme {\n :root, :host {\n --font-sans: ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji",\n "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji";\n --font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono",\n "Courier New", monospace;\n --color-red-50: oklch(97.1% 0.013 17.38);\n --color-red-100: oklch(93.6% 0.032 17.717);\n --color-red-500: oklch(63.7% 0.237 25.331);\n --color-red-600: oklch(57.7% 0.245 27.325);\n --color-red-800: oklch(44.4% 0.177 26.899);\n --color-amber-50: oklch(98.7% 0.022 95.277);\n --color-amber-200: oklch(92.4% 0.12 95.746);\n --color-amber-500: oklch(76.9% 0.188 70.08);\n --color-amber-700: oklch(55.5% 0.163 48.998);\n --color-yellow-50: oklch(98.7% 0.026 102.212);\n --color-yellow-100: oklch(97.3% 0.071 103.193);\n --color-yellow-500: oklch(79.5% 0.184 86.047);\n --color-yellow-600: oklch(68.1% 0.162 75.834);\n --color-yellow-800: oklch(47.6% 0.114 61.907);\n --color-yellow-900: oklch(42.1% 0.095 57.708);\n --color-green-50: oklch(98.2% 0.018 155.826);\n --color-green-100: oklch(96.2% 0.044 156.743);\n --color-green-200: oklch(92.5% 0.084 155.995);\n --color-green-500: oklch(72.3% 0.219 149.579);\n --color-green-600: oklch(62.7% 0.194 149.214);\n --color-green-800: oklch(44.8% 0.119 151.328);\n --color-green-900: oklch(39.3% 0.095 152.535);\n --color-emerald-100: oklch(95% 0.052 163.051);\n --color-emerald-600: oklch(59.6% 0.145 163.225);\n --color-emerald-700: oklch(50.8% 0.118 165.612);\n --color-blue-100: oklch(93.2% 0.032 255.585);\n --color-blue-200: oklch(88.2% 0.059 254.128);\n --color-blue-500: oklch(62.3% 0.214 259.815);\n --color-blue-600: oklch(54.6% 0.245 262.881);\n --color-blue-700: oklch(48.8% 0.243 264.376);\n --color-purple-600: oklch(55.8% 0.288 302.321);\n --color-purple-700: oklch(49.6% 0.265 301.924);\n --color-slate-50: oklch(98.4% 0.003 247.858);\n --color-slate-100: oklch(96.8% 0.007 247.896);\n --color-slate-200: oklch(92.9% 0.013 255.508);\n --color-slate-300: oklch(86.9% 0.022 252.894);\n --color-slate-400: oklch(70.4% 0.04 256.788);\n --color-slate-500: oklch(55.4% 0.046 257.417);\n --color-slate-700: oklch(37.2% 0.044 257.287);\n --color-slate-900: oklch(20.8% 0.042 265.755);\n --color-gray-50: oklch(98.5% 0.002 247.839);\n --color-gray-100: oklch(96.7% 0.003 264.542);\n --color-gray-200: oklch(92.8% 0.006 264.531);\n --color-gray-300: oklch(87.2% 0.01 258.338);\n --color-gray-400: oklch(70.7% 0.022 261.325);\n --color-gray-500: oklch(55.1% 0.027 264.364);\n --color-gray-600: oklch(44.6% 0.03 256.802);\n --color-gray-700: oklch(37.3% 0.034 259.733);\n --color-gray-900: oklch(21% 0.034 264.665);\n --color-black: #000;\n --color-white: #fff;\n --spacing: 0.25rem;\n --container-sm: 24rem;\n --container-md: 28rem;\n --container-lg: 32rem;\n --container-2xl: 42rem;\n --container-3xl: 48rem;\n --container-4xl: 56rem;\n --container-5xl: 64rem;\n --container-6xl: 72rem;\n --container-7xl: 80rem;\n --text-xs: 0.75rem;\n --text-xs--line-height: calc(1 / 0.75);\n --text-sm: 0.875rem;\n --text-sm--line-height: calc(1.25 / 0.875);\n --text-base: 1rem;\n --text-base--line-height: calc(1.5 / 1);\n --text-lg: 1.125rem;\n --text-lg--line-height: calc(1.75 / 1.125);\n --text-xl: 1.25rem;\n --text-xl--line-height: calc(1.75 / 1.25);\n --text-2xl: 1.5rem;\n --text-2xl--line-height: calc(2 / 1.5);\n --text-3xl: 1.875rem;\n --text-3xl--line-height: calc(2.25 / 1.875);\n --text-4xl: 2.25rem;\n --text-4xl--line-height: calc(2.5 / 2.25);\n --text-5xl: 3rem;\n --text-5xl--line-height: 1;\n --font-weight-normal: 400;\n --font-weight-medium: 500;\n --font-weight-semibold: 600;\n --font-weight-bold: 700;\n --tracking-tight: -0.025em;\n --tracking-wider: 0.05em;\n --leading-tight: 1.25;\n --leading-relaxed: 1.625;\n --radius-xl: 0.75rem;\n --radius-2xl: 1rem;\n --ease-out: cubic-bezier(0, 0, 0.2, 1);\n --ease-in-out: cubic-bezier(0.4, 0, 0.2, 1);\n --animate-spin: spin 1s linear infinite;\n --animate-pulse: pulse 2s cubic-bezier(0.4, 0, 0.6, 1) infinite;\n --blur-sm: 8px;\n --default-transition-duration: 150ms;\n --default-transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);\n --default-font-family: var(--font-sans);\n --default-mono-font-family: var(--font-mono);\n }\n}\n@layer base {\n *, ::after, ::before, ::backdrop, ::file-selector-button {\n box-sizing: border-box;\n margin: 0;\n padding: 0;\n border: 0 solid;\n }\n html, :host {\n line-height: 1.5;\n -webkit-text-size-adjust: 100%;\n tab-size: 4;\n font-family: var(--default-font-family, ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji");\n font-feature-settings: var(--default-font-feature-settings, normal);\n font-variation-settings: var(--default-font-variation-settings, normal);\n -webkit-tap-highlight-color: transparent;\n }\n hr {\n height: 0;\n color: inherit;\n border-top-width: 1px;\n }\n abbr:where([title]) {\n -webkit-text-decoration: underline dotted;\n text-decoration: underline dotted;\n }\n h1, h2, h3, h4, h5, h6 {\n font-size: inherit;\n font-weight: inherit;\n }\n a {\n color: inherit;\n -webkit-text-decoration: inherit;\n text-decoration: inherit;\n }\n b, strong {\n font-weight: bolder;\n }\n code, kbd, samp, pre {\n font-family: var(--default-mono-font-family, ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace);\n font-feature-settings: var(--default-mono-font-feature-settings, normal);\n font-variation-settings: var(--default-mono-font-variation-settings, normal);\n font-size: 1em;\n }\n small {\n font-size: 80%;\n }\n sub, sup {\n font-size: 75%;\n line-height: 0;\n position: relative;\n vertical-align: baseline;\n }\n sub {\n bottom: -0.25em;\n }\n sup {\n top: -0.5em;\n }\n table {\n text-indent: 0;\n border-color: inherit;\n border-collapse: collapse;\n }\n :-moz-focusring {\n outline: auto;\n }\n progress {\n vertical-align: baseline;\n }\n summary {\n display: list-item;\n }\n ol, ul, menu {\n list-style: none;\n }\n img, svg, video, canvas, audio, iframe, embed, object {\n display: block;\n vertical-align: middle;\n }\n img, video {\n max-width: 100%;\n height: auto;\n }\n button, input, select, optgroup, textarea, ::file-selector-button {\n font: inherit;\n font-feature-settings: inherit;\n font-variation-settings: inherit;\n letter-spacing: inherit;\n color: inherit;\n border-radius: 0;\n background-color: transparent;\n opacity: 1;\n }\n :where(select:is([multiple], [size])) optgroup {\n font-weight: bolder;\n }\n :where(select:is([multiple], [size])) optgroup option {\n padding-inline-start: 20px;\n }\n ::file-selector-button {\n margin-inline-end: 4px;\n }\n ::placeholder {\n opacity: 1;\n }\n @supports (not (-webkit-appearance: -apple-pay-button)) or (contain-intrinsic-size: 1px) {\n ::placeholder {\n color: currentcolor;\n @supports (color: color-mix(in lab, red, red)) {\n color: color-mix(in oklab, currentcolor 50%, transparent);\n }\n }\n }\n textarea {\n resize: vertical;\n }\n ::-webkit-search-decoration {\n -webkit-appearance: none;\n }\n ::-webkit-date-and-time-value {\n min-height: 1lh;\n text-align: inherit;\n }\n ::-webkit-datetime-edit {\n display: inline-flex;\n }\n ::-webkit-datetime-edit-fields-wrapper {\n padding: 0;\n }\n ::-webkit-datetime-edit, ::-webkit-datetime-edit-year-field, ::-webkit-datetime-edit-month-field, ::-webkit-datetime-edit-day-field, ::-webkit-datetime-edit-hour-field, ::-webkit-datetime-edit-minute-field, ::-webkit-datetime-edit-second-field, ::-webkit-datetime-edit-millisecond-field, ::-webkit-datetime-edit-meridiem-field {\n padding-block: 0;\n }\n ::-webkit-calendar-picker-indicator {\n line-height: 1;\n }\n :-moz-ui-invalid {\n box-shadow: none;\n }\n button, input:where([type="button"], [type="reset"], [type="submit"]), ::file-selector-button {\n appearance: button;\n }\n ::-webkit-inner-spin-button, ::-webkit-outer-spin-button {\n height: auto;\n }\n [hidden]:where(:not([hidden="until-found"])) {\n display: none !important;\n }\n}\n@layer utilities {\n .pointer-events-none {\n pointer-events: none;\n }\n .visible {\n visibility: visible;\n }\n .sr-only {\n position: absolute;\n width: 1px;\n height: 1px;\n padding: 0;\n margin: -1px;\n overflow: hidden;\n clip-path: inset(50%);\n white-space: nowrap;\n border-width: 0;\n }\n .absolute {\n position: absolute;\n }\n .fixed {\n position: fixed;\n }\n .relative {\n position: relative;\n }\n .static {\n position: static;\n }\n .inset-0 {\n inset: calc(var(--spacing) * 0);\n }\n .inset-x-0 {\n inset-inline: calc(var(--spacing) * 0);\n }\n .inset-y-0 {\n inset-block: calc(var(--spacing) * 0);\n }\n .-top-3 {\n top: calc(var(--spacing) * -3);\n }\n .-top-4 {\n top: calc(var(--spacing) * -4);\n }\n .top-0 {\n top: calc(var(--spacing) * 0);\n }\n .top-2 {\n top: calc(var(--spacing) * 2);\n }\n .top-3 {\n top: calc(var(--spacing) * 3);\n }\n .top-4 {\n top: calc(var(--spacing) * 4);\n }\n .right-0 {\n right: calc(var(--spacing) * 0);\n }\n .right-0\\.5 {\n right: calc(var(--spacing) * 0.5);\n }\n .right-2 {\n right: calc(var(--spacing) * 2);\n }\n .right-3 {\n right: calc(var(--spacing) * 3);\n }\n .right-4 {\n right: calc(var(--spacing) * 4);\n }\n .bottom-0 {\n bottom: calc(var(--spacing) * 0);\n }\n .bottom-4 {\n bottom: calc(var(--spacing) * 4);\n }\n .left-0 {\n left: calc(var(--spacing) * 0);\n }\n .left-1\\/2 {\n left: calc(1/2 * 100%);\n }\n .isolate {\n isolation: isolate;\n }\n .z-10 {\n z-index: 10;\n }\n .z-20 {\n z-index: 20;\n }\n .z-50 {\n z-index: 50;\n }\n .container {\n width: 100%;\n @media (width >= 40rem) {\n max-width: 40rem;\n }\n @media (width >= 48rem) {\n max-width: 48rem;\n }\n @media (width >= 64rem) {\n max-width: 64rem;\n }\n @media (width >= 80rem) {\n max-width: 80rem;\n }\n @media (width >= 96rem) {\n max-width: 96rem;\n }\n }\n .m-0 {\n margin: calc(var(--spacing) * 0);\n }\n .mx-auto {\n margin-inline: auto;\n }\n .my-2 {\n margin-block: calc(var(--spacing) * 2);\n }\n .mt-0 {\n margin-top: calc(var(--spacing) * 0);\n }\n .mt-0\\.5 {\n margin-top: calc(var(--spacing) * 0.5);\n }\n .mt-1 {\n margin-top: calc(var(--spacing) * 1);\n }\n .mt-2 {\n margin-top: calc(var(--spacing) * 2);\n }\n .mt-3 {\n margin-top: calc(var(--spacing) * 3);\n }\n .mt-4 {\n margin-top: calc(var(--spacing) * 4);\n }\n .mt-6 {\n margin-top: calc(var(--spacing) * 6);\n }\n .mt-8 {\n margin-top: calc(var(--spacing) * 8);\n }\n .mt-16 {\n margin-top: calc(var(--spacing) * 16);\n }\n .mr-1 {\n margin-right: calc(var(--spacing) * 1);\n }\n .mr-2 {\n margin-right: calc(var(--spacing) * 2);\n }\n .mb-1 {\n margin-bottom: calc(var(--spacing) * 1);\n }\n .mb-2 {\n margin-bottom: calc(var(--spacing) * 2);\n }\n .mb-3 {\n margin-bottom: calc(var(--spacing) * 3);\n }\n .mb-4 {\n margin-bottom: calc(var(--spacing) * 4);\n }\n .mb-6 {\n margin-bottom: calc(var(--spacing) * 6);\n }\n .mb-8 {\n margin-bottom: calc(var(--spacing) * 8);\n }\n .mb-12 {\n margin-bottom: calc(var(--spacing) * 12);\n }\n .mb-16 {\n margin-bottom: calc(var(--spacing) * 16);\n }\n .ml-1 {\n margin-left: calc(var(--spacing) * 1);\n }\n .ml-2 {\n margin-left: calc(var(--spacing) * 2);\n }\n .ml-3 {\n margin-left: calc(var(--spacing) * 3);\n }\n .ml-4 {\n margin-left: calc(var(--spacing) * 4);\n }\n .block {\n display: block;\n }\n .flex {\n display: flex;\n }\n .grid {\n display: grid;\n }\n .hidden {\n display: none;\n }\n .inline {\n display: inline;\n }\n .inline-block {\n display: inline-block;\n }\n .inline-flex {\n display: inline-flex;\n }\n .table {\n display: table;\n }\n .aspect-square {\n aspect-ratio: 1 / 1;\n }\n .h-1\\.5 {\n height: calc(var(--spacing) * 1.5);\n }\n .h-2 {\n height: calc(var(--spacing) * 2);\n }\n .h-2\\.5 {\n height: calc(var(--spacing) * 2.5);\n }\n .h-3 {\n height: calc(var(--spacing) * 3);\n }\n .h-4 {\n height: calc(var(--spacing) * 4);\n }\n .h-5 {\n height: calc(var(--spacing) * 5);\n }\n .h-6 {\n height: calc(var(--spacing) * 6);\n }\n .h-8 {\n height: calc(var(--spacing) * 8);\n }\n .h-9 {\n height: calc(var(--spacing) * 9);\n }\n .h-10 {\n height: calc(var(--spacing) * 10);\n }\n .h-11 {\n height: calc(var(--spacing) * 11);\n }\n .h-12 {\n height: calc(var(--spacing) * 12);\n }\n .h-16 {\n height: calc(var(--spacing) * 16);\n }\n .h-20 {\n height: calc(var(--spacing) * 20);\n }\n .h-40 {\n height: calc(var(--spacing) * 40);\n }\n .h-\\[1px\\] {\n height: 1px;\n }\n .h-\\[480px\\] {\n height: 480px;\n }\n .h-\\[650px\\] {\n height: 650px;\n }\n .h-full {\n height: 100%;\n }\n .max-h-\\[80vh\\] {\n max-height: 80vh;\n }\n .max-h-\\[90vh\\] {\n max-height: 90vh;\n }\n .min-h-0 {\n min-height: calc(var(--spacing) * 0);\n }\n .min-h-\\[80px\\] {\n min-height: 80px;\n }\n .min-h-screen {\n min-height: 100vh;\n }\n .w-1\\.5 {\n width: calc(var(--spacing) * 1.5);\n }\n .w-1\\/4 {\n width: calc(1/4 * 100%);\n }\n .w-2\\.5 {\n width: calc(var(--spacing) * 2.5);\n }\n .w-3 {\n width: calc(var(--spacing) * 3);\n }\n .w-3\\/4 {\n width: calc(3/4 * 100%);\n }\n .w-4 {\n width: calc(var(--spacing) * 4);\n }\n .w-5 {\n width: calc(var(--spacing) * 5);\n }\n .w-6 {\n width: calc(var(--spacing) * 6);\n }\n .w-8 {\n width: calc(var(--spacing) * 8);\n }\n .w-10 {\n width: calc(var(--spacing) * 10);\n }\n .w-11 {\n width: calc(var(--spacing) * 11);\n }\n .w-12 {\n width: calc(var(--spacing) * 12);\n }\n .w-16 {\n width: calc(var(--spacing) * 16);\n }\n .w-20 {\n width: calc(var(--spacing) * 20);\n }\n .w-24 {\n width: calc(var(--spacing) * 24);\n }\n .w-28 {\n width: calc(var(--spacing) * 28);\n }\n .w-32 {\n width: calc(var(--spacing) * 32);\n }\n .w-36 {\n width: calc(var(--spacing) * 36);\n }\n .w-40 {\n width: calc(var(--spacing) * 40);\n }\n .w-44 {\n width: calc(var(--spacing) * 44);\n }\n .w-48 {\n width: calc(var(--spacing) * 48);\n }\n .w-72 {\n width: calc(var(--spacing) * 72);\n }\n .w-80 {\n width: calc(var(--spacing) * 80);\n }\n .w-96 {\n width: calc(var(--spacing) * 96);\n }\n .w-\\[1px\\] {\n width: 1px;\n }\n .w-\\[450px\\] {\n width: 450px;\n }\n .w-full {\n width: 100%;\n }\n .max-w-2xl {\n max-width: var(--container-2xl);\n }\n .max-w-3xl {\n max-width: var(--container-3xl);\n }\n .max-w-4xl {\n max-width: var(--container-4xl);\n }\n .max-w-5xl {\n max-width: var(--container-5xl);\n }\n .max-w-7xl {\n max-width: var(--container-7xl);\n }\n .max-w-\\[800px\\] {\n max-width: 800px;\n }\n .max-w-\\[calc\\(100vw-2rem\\)\\] {\n max-width: calc(100vw - 2rem);\n }\n .max-w-lg {\n max-width: var(--container-lg);\n }\n .max-w-md {\n max-width: var(--container-md);\n }\n .max-w-sm {\n max-width: var(--container-sm);\n }\n .min-w-0 {\n min-width: calc(var(--spacing) * 0);\n }\n .flex-1 {\n flex: 1;\n }\n .flex-shrink-0 {\n flex-shrink: 0;\n }\n .shrink-0 {\n flex-shrink: 0;\n }\n .caption-bottom {\n caption-side: bottom;\n }\n .-translate-x-1\\/2 {\n --tw-translate-x: calc(calc(1/2 * 100%) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n .translate-x-0 {\n --tw-translate-x: calc(var(--spacing) * 0);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n .translate-x-5 {\n --tw-translate-x: calc(var(--spacing) * 5);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n .scale-105 {\n --tw-scale-x: 105%;\n --tw-scale-y: 105%;\n --tw-scale-z: 105%;\n scale: var(--tw-scale-x) var(--tw-scale-y);\n }\n .transform {\n transform: var(--tw-rotate-x,) var(--tw-rotate-y,) var(--tw-rotate-z,) var(--tw-skew-x,) var(--tw-skew-y,);\n }\n .animate-pulse {\n animation: var(--animate-pulse);\n }\n .animate-spin {\n animation: var(--animate-spin);\n }\n .cursor-default {\n cursor: default;\n }\n .cursor-not-allowed {\n cursor: not-allowed;\n }\n .cursor-pointer {\n cursor: pointer;\n }\n .touch-none {\n touch-action: none;\n }\n .resize {\n resize: both;\n }\n .resize-none {\n resize: none;\n }\n .list-inside {\n list-style-position: inside;\n }\n .list-disc {\n list-style-type: disc;\n }\n .grid-cols-1 {\n grid-template-columns: repeat(1, minmax(0, 1fr));\n }\n .grid-cols-2 {\n grid-template-columns: repeat(2, minmax(0, 1fr));\n }\n .grid-cols-4 {\n grid-template-columns: repeat(4, minmax(0, 1fr));\n }\n .flex-col {\n flex-direction: column;\n }\n .flex-col-reverse {\n flex-direction: column-reverse;\n }\n .flex-wrap {\n flex-wrap: wrap;\n }\n .items-baseline {\n align-items: baseline;\n }\n .items-center {\n align-items: center;\n }\n .items-start {\n align-items: flex-start;\n }\n .justify-between {\n justify-content: space-between;\n }\n .justify-center {\n justify-content: center;\n }\n .justify-end {\n justify-content: flex-end;\n }\n .gap-1 {\n gap: calc(var(--spacing) * 1);\n }\n .gap-2 {\n gap: calc(var(--spacing) * 2);\n }\n .gap-3 {\n gap: calc(var(--spacing) * 3);\n }\n .gap-4 {\n gap: calc(var(--spacing) * 4);\n }\n .gap-8 {\n gap: calc(var(--spacing) * 8);\n }\n .space-y-1 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 1) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 1) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-1\\.5 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 1.5) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 1.5) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-2 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 2) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-3 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 3) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 3) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-4 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 4) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 4) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-y-6 {\n :where(& > :not(:last-child)) {\n --tw-space-y-reverse: 0;\n margin-block-start: calc(calc(var(--spacing) * 6) * var(--tw-space-y-reverse));\n margin-block-end: calc(calc(var(--spacing) * 6) * calc(1 - var(--tw-space-y-reverse)));\n }\n }\n .space-x-4 {\n :where(& > :not(:last-child)) {\n --tw-space-x-reverse: 0;\n margin-inline-start: calc(calc(var(--spacing) * 4) * var(--tw-space-x-reverse));\n margin-inline-end: calc(calc(var(--spacing) * 4) * calc(1 - var(--tw-space-x-reverse)));\n }\n }\n .overflow-auto {\n overflow: auto;\n }\n .overflow-hidden {\n overflow: hidden;\n }\n .overflow-x-auto {\n overflow-x: auto;\n }\n .overflow-x-hidden {\n overflow-x: hidden;\n }\n .overflow-y-auto {\n overflow-y: auto;\n }\n .overflow-y-hidden {\n overflow-y: hidden;\n }\n .rounded {\n border-radius: 0.25rem;\n }\n .rounded-2xl {\n border-radius: var(--radius-2xl);\n }\n .rounded-\\[inherit\\] {\n border-radius: inherit;\n }\n .rounded-full {\n border-radius: calc(infinity * 1px);\n }\n .rounded-lg {\n border-radius: var(--radius);\n }\n .rounded-md {\n border-radius: calc(var(--radius) - 2px);\n }\n .rounded-sm {\n border-radius: calc(var(--radius) - 4px);\n }\n .rounded-xl {\n border-radius: var(--radius-xl);\n }\n .rounded-t-\\[10px\\] {\n border-top-left-radius: 10px;\n border-top-right-radius: 10px;\n }\n .border {\n border-style: var(--tw-border-style);\n border-width: 1px;\n }\n .border-0 {\n border-style: var(--tw-border-style);\n border-width: 0px;\n }\n .border-2 {\n border-style: var(--tw-border-style);\n border-width: 2px;\n }\n .border-t {\n border-top-style: var(--tw-border-style);\n border-top-width: 1px;\n }\n .border-r {\n border-right-style: var(--tw-border-style);\n border-right-width: 1px;\n }\n .border-b {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 1px;\n }\n .border-b-2 {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 2px;\n }\n .border-l {\n border-left-style: var(--tw-border-style);\n border-left-width: 1px;\n }\n .border-dashed {\n --tw-border-style: dashed;\n border-style: dashed;\n }\n .border-none {\n --tw-border-style: none;\n border-style: none;\n }\n .border-amber-200 {\n border-color: var(--color-amber-200);\n }\n .border-blue-200 {\n border-color: var(--color-blue-200);\n }\n .border-blue-600 {\n border-color: var(--color-blue-600);\n }\n .border-destructive\\/50 {\n border-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, hsl(var(--destructive)) 50%, transparent);\n }\n }\n .border-gray-200 {\n border-color: var(--color-gray-200);\n }\n .border-gray-300 {\n border-color: var(--color-gray-300);\n }\n .border-green-200 {\n border-color: var(--color-green-200);\n }\n .border-green-500\\/50 {\n border-color: color-mix(in srgb, oklch(72.3% 0.219 149.579) 50%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, var(--color-green-500) 50%, transparent);\n }\n }\n .border-green-600 {\n border-color: var(--color-green-600);\n }\n .border-input {\n border-color: hsl(var(--input));\n }\n .border-primary {\n border-color: hsl(var(--primary));\n }\n .border-primary\\/20 {\n border-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, hsl(var(--primary)) 20%, transparent);\n }\n }\n .border-slate-200 {\n border-color: var(--color-slate-200);\n }\n .border-transparent {\n border-color: transparent;\n }\n .border-yellow-500\\/50 {\n border-color: color-mix(in srgb, oklch(79.5% 0.184 86.047) 50%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n border-color: color-mix(in oklab, var(--color-yellow-500) 50%, transparent);\n }\n }\n .border-t-transparent {\n border-top-color: transparent;\n }\n .border-l-transparent {\n border-left-color: transparent;\n }\n .bg-amber-50 {\n background-color: var(--color-amber-50);\n }\n .bg-background {\n background-color: hsl(var(--background));\n }\n .bg-black\\/50 {\n background-color: color-mix(in srgb, #000 50%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-black) 50%, transparent);\n }\n }\n .bg-black\\/80 {\n background-color: color-mix(in srgb, #000 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-black) 80%, transparent);\n }\n }\n .bg-blue-100 {\n background-color: var(--color-blue-100);\n }\n .bg-blue-600 {\n background-color: var(--color-blue-600);\n }\n .bg-border {\n background-color: hsl(var(--border));\n }\n .bg-card {\n background-color: hsl(var(--card));\n }\n .bg-destructive {\n background-color: hsl(var(--destructive));\n }\n .bg-destructive\\/10 {\n background-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--destructive)) 10%, transparent);\n }\n }\n .bg-emerald-100 {\n background-color: var(--color-emerald-100);\n }\n .bg-emerald-600 {\n background-color: var(--color-emerald-600);\n }\n .bg-gray-50 {\n background-color: var(--color-gray-50);\n }\n .bg-gray-100 {\n background-color: var(--color-gray-100);\n }\n .bg-gray-200 {\n background-color: var(--color-gray-200);\n }\n .bg-gray-300 {\n background-color: var(--color-gray-300);\n }\n .bg-gray-400 {\n background-color: var(--color-gray-400);\n }\n .bg-gray-600 {\n background-color: var(--color-gray-600);\n }\n .bg-green-50 {\n background-color: var(--color-green-50);\n }\n .bg-green-100 {\n background-color: var(--color-green-100);\n }\n .bg-green-500 {\n background-color: var(--color-green-500);\n }\n .bg-muted {\n background-color: hsl(var(--muted));\n }\n .bg-muted-foreground\\/30 {\n background-color: hsl(var(--muted-foreground));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--muted-foreground)) 30%, transparent);\n }\n }\n .bg-muted\\/50 {\n background-color: hsl(var(--muted));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--muted)) 50%, transparent);\n }\n }\n .bg-primary {\n background-color: hsl(var(--primary));\n }\n .bg-primary\\/10 {\n background-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--primary)) 10%, transparent);\n }\n }\n .bg-red-50 {\n background-color: var(--color-red-50);\n }\n .bg-red-100 {\n background-color: var(--color-red-100);\n }\n .bg-red-500 {\n background-color: var(--color-red-500);\n }\n .bg-secondary {\n background-color: hsl(var(--secondary));\n }\n .bg-slate-50 {\n background-color: var(--color-slate-50);\n }\n .bg-slate-100 {\n background-color: var(--color-slate-100);\n }\n .bg-white {\n background-color: var(--color-white);\n }\n .bg-white\\/80 {\n background-color: color-mix(in srgb, #fff 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-white) 80%, transparent);\n }\n }\n .bg-yellow-50 {\n background-color: var(--color-yellow-50);\n }\n .bg-yellow-100 {\n background-color: var(--color-yellow-100);\n }\n .bg-yellow-500 {\n background-color: var(--color-yellow-500);\n }\n .bg-gradient-to-br {\n --tw-gradient-position: to bottom right in oklab;\n background-image: linear-gradient(var(--tw-gradient-stops));\n }\n .bg-gradient-to-r {\n --tw-gradient-position: to right in oklab;\n background-image: linear-gradient(var(--tw-gradient-stops));\n }\n .from-blue-500 {\n --tw-gradient-from: var(--color-blue-500);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .from-blue-600 {\n --tw-gradient-from: var(--color-blue-600);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .to-purple-600 {\n --tw-gradient-to: var(--color-purple-600);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n .p-0 {\n padding: calc(var(--spacing) * 0);\n }\n .p-1 {\n padding: calc(var(--spacing) * 1);\n }\n .p-2 {\n padding: calc(var(--spacing) * 2);\n }\n .p-3 {\n padding: calc(var(--spacing) * 3);\n }\n .p-4 {\n padding: calc(var(--spacing) * 4);\n }\n .p-6 {\n padding: calc(var(--spacing) * 6);\n }\n .p-8 {\n padding: calc(var(--spacing) * 8);\n }\n .p-\\[1px\\] {\n padding: 1px;\n }\n .px-2 {\n padding-inline: calc(var(--spacing) * 2);\n }\n .px-2\\.5 {\n padding-inline: calc(var(--spacing) * 2.5);\n }\n .px-3 {\n padding-inline: calc(var(--spacing) * 3);\n }\n .px-4 {\n padding-inline: calc(var(--spacing) * 4);\n }\n .px-6 {\n padding-inline: calc(var(--spacing) * 6);\n }\n .px-8 {\n padding-inline: calc(var(--spacing) * 8);\n }\n .py-0\\.5 {\n padding-block: calc(var(--spacing) * 0.5);\n }\n .py-1 {\n padding-block: calc(var(--spacing) * 1);\n }\n .py-1\\.5 {\n padding-block: calc(var(--spacing) * 1.5);\n }\n .py-2 {\n padding-block: calc(var(--spacing) * 2);\n }\n .py-3 {\n padding-block: calc(var(--spacing) * 3);\n }\n .py-4 {\n padding-block: calc(var(--spacing) * 4);\n }\n .py-8 {\n padding-block: calc(var(--spacing) * 8);\n }\n .py-12 {\n padding-block: calc(var(--spacing) * 12);\n }\n .py-20 {\n padding-block: calc(var(--spacing) * 20);\n }\n .pt-0 {\n padding-top: calc(var(--spacing) * 0);\n }\n .pt-2 {\n padding-top: calc(var(--spacing) * 2);\n }\n .pt-4 {\n padding-top: calc(var(--spacing) * 4);\n }\n .pt-6 {\n padding-top: calc(var(--spacing) * 6);\n }\n .pr-4 {\n padding-right: calc(var(--spacing) * 4);\n }\n .pr-6 {\n padding-right: calc(var(--spacing) * 6);\n }\n .pr-8 {\n padding-right: calc(var(--spacing) * 8);\n }\n .pb-2 {\n padding-bottom: calc(var(--spacing) * 2);\n }\n .pb-4 {\n padding-bottom: calc(var(--spacing) * 4);\n }\n .pb-6 {\n padding-bottom: calc(var(--spacing) * 6);\n }\n .text-center {\n text-align: center;\n }\n .text-left {\n text-align: left;\n }\n .text-right {\n text-align: right;\n }\n .align-middle {\n vertical-align: middle;\n }\n .text-2xl {\n font-size: var(--text-2xl);\n line-height: var(--tw-leading, var(--text-2xl--line-height));\n }\n .text-3xl {\n font-size: var(--text-3xl);\n line-height: var(--tw-leading, var(--text-3xl--line-height));\n }\n .text-4xl {\n font-size: var(--text-4xl);\n line-height: var(--tw-leading, var(--text-4xl--line-height));\n }\n .text-5xl {\n font-size: var(--text-5xl);\n line-height: var(--tw-leading, var(--text-5xl--line-height));\n }\n .text-base {\n font-size: var(--text-base);\n line-height: var(--tw-leading, var(--text-base--line-height));\n }\n .text-lg {\n font-size: var(--text-lg);\n line-height: var(--tw-leading, var(--text-lg--line-height));\n }\n .text-sm {\n font-size: var(--text-sm);\n line-height: var(--tw-leading, var(--text-sm--line-height));\n }\n .text-xl {\n font-size: var(--text-xl);\n line-height: var(--tw-leading, var(--text-xl--line-height));\n }\n .text-xs {\n font-size: var(--text-xs);\n line-height: var(--tw-leading, var(--text-xs--line-height));\n }\n .leading-none {\n --tw-leading: 1;\n line-height: 1;\n }\n .leading-tight {\n --tw-leading: var(--leading-tight);\n line-height: var(--leading-tight);\n }\n .font-bold {\n --tw-font-weight: var(--font-weight-bold);\n font-weight: var(--font-weight-bold);\n }\n .font-medium {\n --tw-font-weight: var(--font-weight-medium);\n font-weight: var(--font-weight-medium);\n }\n .font-normal {\n --tw-font-weight: var(--font-weight-normal);\n font-weight: var(--font-weight-normal);\n }\n .font-semibold {\n --tw-font-weight: var(--font-weight-semibold);\n font-weight: var(--font-weight-semibold);\n }\n .tracking-tight {\n --tw-tracking: var(--tracking-tight);\n letter-spacing: var(--tracking-tight);\n }\n .tracking-wider {\n --tw-tracking: var(--tracking-wider);\n letter-spacing: var(--tracking-wider);\n }\n .whitespace-nowrap {\n white-space: nowrap;\n }\n .text-amber-500 {\n color: var(--color-amber-500);\n }\n .text-amber-700 {\n color: var(--color-amber-700);\n }\n .text-blue-600 {\n color: var(--color-blue-600);\n }\n .text-card-foreground {\n color: hsl(var(--card-foreground));\n }\n .text-destructive {\n color: hsl(var(--destructive));\n }\n .text-destructive-foreground {\n color: hsl(var(--destructive-foreground));\n }\n .text-emerald-600 {\n color: var(--color-emerald-600);\n }\n .text-emerald-700 {\n color: var(--color-emerald-700);\n }\n .text-foreground {\n color: hsl(var(--foreground));\n }\n .text-gray-400 {\n color: var(--color-gray-400);\n }\n .text-gray-500 {\n color: var(--color-gray-500);\n }\n .text-gray-600 {\n color: var(--color-gray-600);\n }\n .text-gray-700 {\n color: var(--color-gray-700);\n }\n .text-gray-900 {\n color: var(--color-gray-900);\n }\n .text-green-500 {\n color: var(--color-green-500);\n }\n .text-green-600 {\n color: var(--color-green-600);\n }\n .text-green-800 {\n color: var(--color-green-800);\n }\n .text-green-900 {\n color: var(--color-green-900);\n }\n .text-muted-foreground {\n color: hsl(var(--muted-foreground));\n }\n .text-primary {\n color: hsl(var(--primary));\n }\n .text-primary-foreground {\n color: hsl(var(--primary-foreground));\n }\n .text-red-500 {\n color: var(--color-red-500);\n }\n .text-red-600 {\n color: var(--color-red-600);\n }\n .text-red-800 {\n color: var(--color-red-800);\n }\n .text-secondary-foreground {\n color: hsl(var(--secondary-foreground));\n }\n .text-slate-300 {\n color: var(--color-slate-300);\n }\n .text-slate-400 {\n color: var(--color-slate-400);\n }\n .text-slate-500 {\n color: var(--color-slate-500);\n }\n .text-slate-700 {\n color: var(--color-slate-700);\n }\n .text-slate-900 {\n color: var(--color-slate-900);\n }\n .text-white {\n color: var(--color-white);\n }\n .text-yellow-600 {\n color: var(--color-yellow-600);\n }\n .text-yellow-800 {\n color: var(--color-yellow-800);\n }\n .text-yellow-900 {\n color: var(--color-yellow-900);\n }\n .uppercase {\n text-transform: uppercase;\n }\n .underline {\n text-decoration-line: underline;\n }\n .underline-offset-4 {\n text-underline-offset: 4px;\n }\n .opacity-0 {\n opacity: 0%;\n }\n .opacity-25 {\n opacity: 25%;\n }\n .opacity-50 {\n opacity: 50%;\n }\n .opacity-60 {\n opacity: 60%;\n }\n .opacity-70 {\n opacity: 70%;\n }\n .opacity-75 {\n opacity: 75%;\n }\n .opacity-100 {\n opacity: 100%;\n }\n .shadow {\n --tw-shadow: 0 1px 3px 0 var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 1px 2px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-lg {\n --tw-shadow: 0 10px 15px -3px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 4px 6px -4px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-md {\n --tw-shadow: 0 4px 6px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 2px 4px -2px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-sm {\n --tw-shadow: 0 1px 3px 0 var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 1px 2px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-xl {\n --tw-shadow: 0 20px 25px -5px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 8px 10px -6px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .ring {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .ring-0 {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(0px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .ring-2 {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n .shadow-blue-500\\/10 {\n --tw-shadow-color: color-mix(in srgb, oklch(62.3% 0.214 259.815) 10%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n --tw-shadow-color: color-mix(in oklab, color-mix(in oklab, var(--color-blue-500) 10%, transparent) var(--tw-shadow-alpha), transparent);\n }\n }\n .shadow-blue-500\\/25 {\n --tw-shadow-color: color-mix(in srgb, oklch(62.3% 0.214 259.815) 25%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n --tw-shadow-color: color-mix(in oklab, color-mix(in oklab, var(--color-blue-500) 25%, transparent) var(--tw-shadow-alpha), transparent);\n }\n }\n .ring-blue-600 {\n --tw-ring-color: var(--color-blue-600);\n }\n .ring-primary {\n --tw-ring-color: hsl(var(--primary));\n }\n .ring-offset-background {\n --tw-ring-offset-color: hsl(var(--background));\n }\n .outline {\n outline-style: var(--tw-outline-style);\n outline-width: 1px;\n }\n .filter {\n filter: var(--tw-blur,) var(--tw-brightness,) var(--tw-contrast,) var(--tw-grayscale,) var(--tw-hue-rotate,) var(--tw-invert,) var(--tw-saturate,) var(--tw-sepia,) var(--tw-drop-shadow,);\n }\n .backdrop-blur-sm {\n --tw-backdrop-blur: blur(var(--blur-sm));\n -webkit-backdrop-filter: var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,);\n backdrop-filter: var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,);\n }\n .transition {\n transition-property: color, background-color, border-color, outline-color, text-decoration-color, fill, stroke, --tw-gradient-from, --tw-gradient-via, --tw-gradient-to, opacity, box-shadow, transform, translate, scale, rotate, filter, -webkit-backdrop-filter, backdrop-filter, display, content-visibility, overlay, pointer-events;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-all {\n transition-property: all;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-colors {\n transition-property: color, background-color, border-color, outline-color, text-decoration-color, fill, stroke, --tw-gradient-from, --tw-gradient-via, --tw-gradient-to;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-opacity {\n transition-property: opacity;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .transition-transform {\n transition-property: transform, translate, scale, rotate;\n transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));\n transition-duration: var(--tw-duration, var(--default-transition-duration));\n }\n .duration-150 {\n --tw-duration: 150ms;\n transition-duration: 150ms;\n }\n .duration-200 {\n --tw-duration: 200ms;\n transition-duration: 200ms;\n }\n .duration-300 {\n --tw-duration: 300ms;\n transition-duration: 300ms;\n }\n .duration-400 {\n --tw-duration: 400ms;\n transition-duration: 400ms;\n }\n .ease-in-out {\n --tw-ease: var(--ease-in-out);\n transition-timing-function: var(--ease-in-out);\n }\n .ease-out {\n --tw-ease: var(--ease-out);\n transition-timing-function: var(--ease-out);\n }\n .select-none {\n -webkit-user-select: none;\n user-select: none;\n }\n .\\[-ms-overflow-style\\:none\\] {\n -ms-overflow-style: none;\n }\n .\\[scrollbar-width\\:none\\] {\n scrollbar-width: none;\n }\n .peer-disabled\\:cursor-not-allowed {\n &:is(:where(.peer):disabled ~ *) {\n cursor: not-allowed;\n }\n }\n .peer-disabled\\:opacity-70 {\n &:is(:where(.peer):disabled ~ *) {\n opacity: 70%;\n }\n }\n .file\\:border-0 {\n &::file-selector-button {\n border-style: var(--tw-border-style);\n border-width: 0px;\n }\n }\n .file\\:bg-transparent {\n &::file-selector-button {\n background-color: transparent;\n }\n }\n .file\\:text-sm {\n &::file-selector-button {\n font-size: var(--text-sm);\n line-height: var(--tw-leading, var(--text-sm--line-height));\n }\n }\n .file\\:font-medium {\n &::file-selector-button {\n --tw-font-weight: var(--font-weight-medium);\n font-weight: var(--font-weight-medium);\n }\n }\n .file\\:text-foreground {\n &::file-selector-button {\n color: hsl(var(--foreground));\n }\n }\n .placeholder\\:text-muted-foreground {\n &::placeholder {\n color: hsl(var(--muted-foreground));\n }\n }\n .checked\\:bg-primary {\n &:checked {\n background-color: hsl(var(--primary));\n }\n }\n .checked\\:text-primary-foreground {\n &:checked {\n color: hsl(var(--primary-foreground));\n }\n }\n .hover\\:-translate-y-1 {\n &:hover {\n @media (hover: hover) {\n --tw-translate-y: calc(var(--spacing) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n }\n .hover\\:border-gray-300 {\n &:hover {\n @media (hover: hover) {\n border-color: var(--color-gray-300);\n }\n }\n }\n .hover\\:border-primary {\n &:hover {\n @media (hover: hover) {\n border-color: hsl(var(--primary));\n }\n }\n }\n .hover\\:border-slate-300 {\n &:hover {\n @media (hover: hover) {\n border-color: var(--color-slate-300);\n }\n }\n }\n .hover\\:bg-accent {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--accent));\n }\n }\n }\n .hover\\:bg-background\\/50 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--background));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--background)) 50%, transparent);\n }\n }\n }\n }\n .hover\\:bg-blue-700 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-blue-700);\n }\n }\n }\n .hover\\:bg-destructive\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--destructive)) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-destructive\\/90 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--destructive));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--destructive)) 90%, transparent);\n }\n }\n }\n }\n .hover\\:bg-gray-200 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-200);\n }\n }\n }\n .hover\\:bg-gray-300 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-300);\n }\n }\n }\n .hover\\:bg-gray-600 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-600);\n }\n }\n }\n .hover\\:bg-gray-700 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-gray-700);\n }\n }\n }\n .hover\\:bg-green-500\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: color-mix(in srgb, oklch(72.3% 0.219 149.579) 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-green-500) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-muted {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--muted));\n }\n }\n }\n .hover\\:bg-muted\\/50 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--muted));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--muted)) 50%, transparent);\n }\n }\n }\n }\n .hover\\:bg-primary\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--primary)) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-primary\\/90 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--primary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--primary)) 90%, transparent);\n }\n }\n }\n }\n .hover\\:bg-secondary\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: hsl(var(--secondary));\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, hsl(var(--secondary)) 80%, transparent);\n }\n }\n }\n }\n .hover\\:bg-slate-100 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-slate-100);\n }\n }\n }\n .hover\\:bg-slate-200 {\n &:hover {\n @media (hover: hover) {\n background-color: var(--color-slate-200);\n }\n }\n }\n .hover\\:bg-yellow-500\\/80 {\n &:hover {\n @media (hover: hover) {\n background-color: color-mix(in srgb, oklch(79.5% 0.184 86.047) 80%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-yellow-500) 80%, transparent);\n }\n }\n }\n }\n .hover\\:from-blue-700 {\n &:hover {\n @media (hover: hover) {\n --tw-gradient-from: var(--color-blue-700);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n }\n }\n .hover\\:to-purple-700 {\n &:hover {\n @media (hover: hover) {\n --tw-gradient-to: var(--color-purple-700);\n --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position));\n }\n }\n }\n .hover\\:text-accent-foreground {\n &:hover {\n @media (hover: hover) {\n color: hsl(var(--accent-foreground));\n }\n }\n }\n .hover\\:text-destructive {\n &:hover {\n @media (hover: hover) {\n color: hsl(var(--destructive));\n }\n }\n }\n .hover\\:text-foreground {\n &:hover {\n @media (hover: hover) {\n color: hsl(var(--foreground));\n }\n }\n }\n .hover\\:text-gray-700 {\n &:hover {\n @media (hover: hover) {\n color: var(--color-gray-700);\n }\n }\n }\n .hover\\:text-yellow-900 {\n &:hover {\n @media (hover: hover) {\n color: var(--color-yellow-900);\n }\n }\n }\n .hover\\:underline {\n &:hover {\n @media (hover: hover) {\n text-decoration-line: underline;\n }\n }\n }\n .hover\\:opacity-100 {\n &:hover {\n @media (hover: hover) {\n opacity: 100%;\n }\n }\n }\n .hover\\:shadow-lg {\n &:hover {\n @media (hover: hover) {\n --tw-shadow: 0 10px 15px -3px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 4px 6px -4px var(--tw-shadow-color, rgb(0 0 0 / 0.1));\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n }\n }\n .focus\\:ring-2 {\n &:focus {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n }\n .focus\\:ring-blue-500 {\n &:focus {\n --tw-ring-color: var(--color-blue-500);\n }\n }\n .focus\\:ring-ring {\n &:focus {\n --tw-ring-color: hsl(var(--ring));\n }\n }\n .focus\\:ring-offset-2 {\n &:focus {\n --tw-ring-offset-width: 2px;\n --tw-ring-offset-shadow: var(--tw-ring-inset,) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);\n }\n }\n .focus\\:outline-none {\n &:focus {\n --tw-outline-style: none;\n outline-style: none;\n }\n }\n .focus-visible\\:ring-2 {\n &:focus-visible {\n --tw-ring-shadow: var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color, currentcolor);\n box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);\n }\n }\n .focus-visible\\:ring-ring {\n &:focus-visible {\n --tw-ring-color: hsl(var(--ring));\n }\n }\n .focus-visible\\:ring-offset-2 {\n &:focus-visible {\n --tw-ring-offset-width: 2px;\n --tw-ring-offset-shadow: var(--tw-ring-inset,) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);\n }\n }\n .focus-visible\\:outline-none {\n &:focus-visible {\n --tw-outline-style: none;\n outline-style: none;\n }\n }\n .disabled\\:pointer-events-none {\n &:disabled {\n pointer-events: none;\n }\n }\n .disabled\\:cursor-not-allowed {\n &:disabled {\n cursor: not-allowed;\n }\n }\n .disabled\\:opacity-50 {\n &:disabled {\n opacity: 50%;\n }\n }\n .data-\\[state\\=selected\\]\\:bg-muted {\n &[data-state="selected"] {\n background-color: hsl(var(--muted));\n }\n }\n .sm\\:max-w-2xl {\n @media (width >= 40rem) {\n max-width: var(--container-2xl);\n }\n }\n .sm\\:max-w-6xl {\n @media (width >= 40rem) {\n max-width: var(--container-6xl);\n }\n }\n .sm\\:max-w-\\[600px\\] {\n @media (width >= 40rem) {\n max-width: 600px;\n }\n }\n .sm\\:max-w-\\[800px\\] {\n @media (width >= 40rem) {\n max-width: 800px;\n }\n }\n .sm\\:max-w-lg {\n @media (width >= 40rem) {\n max-width: var(--container-lg);\n }\n }\n .sm\\:max-w-md {\n @media (width >= 40rem) {\n max-width: var(--container-md);\n }\n }\n .sm\\:max-w-sm {\n @media (width >= 40rem) {\n max-width: var(--container-sm);\n }\n }\n .sm\\:flex-1 {\n @media (width >= 40rem) {\n flex: 1;\n }\n }\n .sm\\:flex-row {\n @media (width >= 40rem) {\n flex-direction: row;\n }\n }\n .sm\\:justify-end {\n @media (width >= 40rem) {\n justify-content: flex-end;\n }\n }\n .sm\\:space-x-2 {\n @media (width >= 40rem) {\n :where(& > :not(:last-child)) {\n --tw-space-x-reverse: 0;\n margin-inline-start: calc(calc(var(--spacing) * 2) * var(--tw-space-x-reverse));\n margin-inline-end: calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-x-reverse)));\n }\n }\n }\n .sm\\:rounded-lg {\n @media (width >= 40rem) {\n border-radius: var(--radius);\n }\n }\n .sm\\:px-6 {\n @media (width >= 40rem) {\n padding-inline: calc(var(--spacing) * 6);\n }\n }\n .sm\\:text-left {\n @media (width >= 40rem) {\n text-align: left;\n }\n }\n .md\\:inset-auto {\n @media (width >= 48rem) {\n inset: auto;\n }\n }\n .md\\:top-1\\/2 {\n @media (width >= 48rem) {\n top: calc(1/2 * 100%);\n }\n }\n .md\\:left-1\\/2 {\n @media (width >= 48rem) {\n left: calc(1/2 * 100%);\n }\n }\n .md\\:hidden {\n @media (width >= 48rem) {\n display: none;\n }\n }\n .md\\:max-h-\\[90vh\\] {\n @media (width >= 48rem) {\n max-height: 90vh;\n }\n }\n .md\\:max-h-\\[calc\\(90vh-2rem\\)\\] {\n @media (width >= 48rem) {\n max-height: calc(90vh - 2rem);\n }\n }\n .md\\:w-full {\n @media (width >= 48rem) {\n width: 100%;\n }\n }\n .md\\:max-w-\\[500px\\] {\n @media (width >= 48rem) {\n max-width: 500px;\n }\n }\n .md\\:-translate-x-1\\/2 {\n @media (width >= 48rem) {\n --tw-translate-x: calc(calc(1/2 * 100%) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n .md\\:-translate-y-1\\/2 {\n @media (width >= 48rem) {\n --tw-translate-y: calc(calc(1/2 * 100%) * -1);\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n .md\\:scale-105 {\n @media (width >= 48rem) {\n --tw-scale-x: 105%;\n --tw-scale-y: 105%;\n --tw-scale-z: 105%;\n scale: var(--tw-scale-x) var(--tw-scale-y);\n }\n }\n .md\\:grid-cols-2 {\n @media (width >= 48rem) {\n grid-template-columns: repeat(2, minmax(0, 1fr));\n }\n }\n .md\\:grid-cols-3 {\n @media (width >= 48rem) {\n grid-template-columns: repeat(3, minmax(0, 1fr));\n }\n }\n .md\\:rounded-lg {\n @media (width >= 48rem) {\n border-radius: var(--radius);\n }\n }\n .md\\:border {\n @media (width >= 48rem) {\n border-style: var(--tw-border-style);\n border-width: 1px;\n }\n }\n .md\\:pt-6 {\n @media (width >= 48rem) {\n padding-top: calc(var(--spacing) * 6);\n }\n }\n .md\\:text-5xl {\n @media (width >= 48rem) {\n font-size: var(--text-5xl);\n line-height: var(--tw-leading, var(--text-5xl--line-height));\n }\n }\n .md\\:text-sm {\n @media (width >= 48rem) {\n font-size: var(--text-sm);\n line-height: var(--tw-leading, var(--text-sm--line-height));\n }\n }\n .lg\\:grid-cols-3 {\n @media (width >= 64rem) {\n grid-template-columns: repeat(3, minmax(0, 1fr));\n }\n }\n .lg\\:px-8 {\n @media (width >= 64rem) {\n padding-inline: calc(var(--spacing) * 8);\n }\n }\n .dark\\:border-destructive {\n @media (prefers-color-scheme: dark) {\n border-color: hsl(var(--destructive));\n }\n }\n .dark\\:bg-green-900\\/10 {\n @media (prefers-color-scheme: dark) {\n background-color: color-mix(in srgb, oklch(39.3% 0.095 152.535) 10%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-green-900) 10%, transparent);\n }\n }\n }\n .dark\\:bg-yellow-900\\/10 {\n @media (prefers-color-scheme: dark) {\n background-color: color-mix(in srgb, oklch(42.1% 0.095 57.708) 10%, transparent);\n @supports (color: color-mix(in lab, red, red)) {\n background-color: color-mix(in oklab, var(--color-yellow-900) 10%, transparent);\n }\n }\n }\n .dark\\:text-green-500 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-green-500);\n }\n }\n .dark\\:text-yellow-500 {\n @media (prefers-color-scheme: dark) {\n color: var(--color-yellow-500);\n }\n }\n .\\[\\&_p\\]\\:leading-relaxed {\n & p {\n --tw-leading: var(--leading-relaxed);\n line-height: var(--leading-relaxed);\n }\n }\n .\\[\\&_svg\\]\\:pointer-events-none {\n & svg {\n pointer-events: none;\n }\n }\n .\\[\\&_svg\\]\\:size-4 {\n & svg {\n width: calc(var(--spacing) * 4);\n height: calc(var(--spacing) * 4);\n }\n }\n .\\[\\&_svg\\]\\:shrink-0 {\n & svg {\n flex-shrink: 0;\n }\n }\n .\\[\\&_tr\\]\\:border-b {\n & tr {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 1px;\n }\n }\n .\\[\\&_tr\\:last-child\\]\\:border-0 {\n & tr:last-child {\n border-style: var(--tw-border-style);\n border-width: 0px;\n }\n }\n .\\[\\&\\:\\:-webkit-scrollbar\\]\\:hidden {\n &::-webkit-scrollbar {\n display: none;\n }\n }\n .\\[\\&\\:has\\(\\[role\\=checkbox\\]\\)\\]\\:pr-0 {\n &:has([role=checkbox]) {\n padding-right: calc(var(--spacing) * 0);\n }\n }\n .\\[\\&\\>svg\\]\\:absolute {\n &>svg {\n position: absolute;\n }\n }\n .\\[\\&\\>svg\\]\\:top-4 {\n &>svg {\n top: calc(var(--spacing) * 4);\n }\n }\n .\\[\\&\\>svg\\]\\:left-4 {\n &>svg {\n left: calc(var(--spacing) * 4);\n }\n }\n .\\[\\&\\>svg\\]\\:text-destructive {\n &>svg {\n color: hsl(var(--destructive));\n }\n }\n .\\[\\&\\>svg\\]\\:text-foreground {\n &>svg {\n color: hsl(var(--foreground));\n }\n }\n .\\[\\&\\>svg\\]\\:text-green-500 {\n &>svg {\n color: var(--color-green-500);\n }\n }\n .\\[\\&\\>svg\\]\\:text-yellow-500 {\n &>svg {\n color: var(--color-yellow-500);\n }\n }\n .\\[\\&\\>svg\\+div\\]\\:translate-y-\\[-3px\\] {\n &>svg+div {\n --tw-translate-y: -3px;\n translate: var(--tw-translate-x) var(--tw-translate-y);\n }\n }\n .\\[\\&\\>svg\\~\\*\\]\\:pl-7 {\n &>svg~* {\n padding-left: calc(var(--spacing) * 7);\n }\n }\n .\\[\\&\\>tr\\]\\:last\\:border-b-0 {\n &>tr {\n &:last-child {\n border-bottom-style: var(--tw-border-style);\n border-bottom-width: 0px;\n }\n }\n }\n}\n:root {\n --background: 0 0% 100%;\n --foreground: 222.2 84% 4.9%;\n --card: 0 0% 100%;\n --card-foreground: 222.2 84% 4.9%;\n --popover: 0 0% 100%;\n --popover-foreground: 222.2 84% 4.9%;\n --primary: 222.2 47.4% 11.2%;\n --primary-foreground: 210 40% 98%;\n --secondary: 210 40% 96.1%;\n --secondary-foreground: 222.2 47.4% 11.2%;\n --muted: 210 40% 96.1%;\n --muted-foreground: 215.4 16.3% 46.9%;\n --accent: 210 40% 96.1%;\n --accent-foreground: 222.2 47.4% 11.2%;\n --destructive: 0 84.2% 60.2%;\n --destructive-foreground: 210 40% 98%;\n --border: 214.3 31.8% 91.4%;\n --input: 214.3 31.8% 91.4%;\n --ring: 222.2 84% 4.9%;\n --radius: 0.5rem;\n}\n.dark {\n --background: 222.2 84% 4.9%;\n --foreground: 210 40% 98%;\n --card: 222.2 84% 4.9%;\n --card-foreground: 210 40% 98%;\n --popover: 222.2 84% 4.9%;\n --popover-foreground: 210 40% 98%;\n --primary: 210 40% 98%;\n --primary-foreground: 222.2 47.4% 11.2%;\n --secondary: 217.2 32.6% 17.5%;\n --secondary-foreground: 210 40% 98%;\n --muted: 217.2 32.6% 17.5%;\n --muted-foreground: 215 20.2% 65.1%;\n --accent: 217.2 32.6% 17.5%;\n --accent-foreground: 210 40% 98%;\n --destructive: 0 62.8% 30.6%;\n --destructive-foreground: 210 40% 98%;\n --border: 217.2 32.6% 17.5%;\n --input: 217.2 32.6% 17.5%;\n --ring: 212.7 26.8% 83.9%;\n}\n@layer base {\n * {\n border-color: hsl(var(--border));\n }\n body {\n background-color: hsl(var(--background));\n color: hsl(var(--foreground));\n }\n}\n@keyframes accordion-down {\n from {\n height: 0;\n }\n to {\n height: var(--radix-accordion-content-height);\n }\n}\n@keyframes accordion-up {\n from {\n height: var(--radix-accordion-content-height);\n }\n to {\n height: 0;\n }\n}\n.animate-accordion-down {\n animation: accordion-down 0.2s ease-out;\n}\n.animate-accordion-up {\n animation: accordion-up 0.2s ease-out;\n}\n@property --tw-translate-x {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-translate-y {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-translate-z {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-scale-x {\n syntax: "*";\n inherits: false;\n initial-value: 1;\n}\n@property --tw-scale-y {\n syntax: "*";\n inherits: false;\n initial-value: 1;\n}\n@property --tw-scale-z {\n syntax: "*";\n inherits: false;\n initial-value: 1;\n}\n@property --tw-rotate-x {\n syntax: "*";\n inherits: false;\n}\n@property --tw-rotate-y {\n syntax: "*";\n inherits: false;\n}\n@property --tw-rotate-z {\n syntax: "*";\n inherits: false;\n}\n@property --tw-skew-x {\n syntax: "*";\n inherits: false;\n}\n@property --tw-skew-y {\n syntax: "*";\n inherits: false;\n}\n@property --tw-space-y-reverse {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-space-x-reverse {\n syntax: "*";\n inherits: false;\n initial-value: 0;\n}\n@property --tw-border-style {\n syntax: "*";\n inherits: false;\n initial-value: solid;\n}\n@property --tw-gradient-position {\n syntax: "*";\n inherits: false;\n}\n@property --tw-gradient-from {\n syntax: "<color>";\n inherits: false;\n initial-value: #0000;\n}\n@property --tw-gradient-via {\n syntax: "<color>";\n inherits: false;\n initial-value: #0000;\n}\n@property --tw-gradient-to {\n syntax: "<color>";\n inherits: false;\n initial-value: #0000;\n}\n@property --tw-gradient-stops {\n syntax: "*";\n inherits: false;\n}\n@property --tw-gradient-via-stops {\n syntax: "*";\n inherits: false;\n}\n@property --tw-gradient-from-position {\n syntax: "<length-percentage>";\n inherits: false;\n initial-value: 0%;\n}\n@property --tw-gradient-via-position {\n syntax: "<length-percentage>";\n inherits: false;\n initial-value: 50%;\n}\n@property --tw-gradient-to-position {\n syntax: "<length-percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-leading {\n syntax: "*";\n inherits: false;\n}\n@property --tw-font-weight {\n syntax: "*";\n inherits: false;\n}\n@property --tw-tracking {\n syntax: "*";\n inherits: false;\n}\n@property --tw-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-shadow-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-shadow-alpha {\n syntax: "<percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-inset-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-inset-shadow-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-inset-shadow-alpha {\n syntax: "<percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-ring-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-ring-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-inset-ring-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-inset-ring-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-ring-inset {\n syntax: "*";\n inherits: false;\n}\n@property --tw-ring-offset-width {\n syntax: "<length>";\n inherits: false;\n initial-value: 0px;\n}\n@property --tw-ring-offset-color {\n syntax: "*";\n inherits: false;\n initial-value: #fff;\n}\n@property --tw-ring-offset-shadow {\n syntax: "*";\n inherits: false;\n initial-value: 0 0 #0000;\n}\n@property --tw-outline-style {\n syntax: "*";\n inherits: false;\n initial-value: solid;\n}\n@property --tw-blur {\n syntax: "*";\n inherits: false;\n}\n@property --tw-brightness {\n syntax: "*";\n inherits: false;\n}\n@property --tw-contrast {\n syntax: "*";\n inherits: false;\n}\n@property --tw-grayscale {\n syntax: "*";\n inherits: false;\n}\n@property --tw-hue-rotate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-invert {\n syntax: "*";\n inherits: false;\n}\n@property --tw-opacity {\n syntax: "*";\n inherits: false;\n}\n@property --tw-saturate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-sepia {\n syntax: "*";\n inherits: false;\n}\n@property --tw-drop-shadow {\n syntax: "*";\n inherits: false;\n}\n@property --tw-drop-shadow-color {\n syntax: "*";\n inherits: false;\n}\n@property --tw-drop-shadow-alpha {\n syntax: "<percentage>";\n inherits: false;\n initial-value: 100%;\n}\n@property --tw-drop-shadow-size {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-blur {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-brightness {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-contrast {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-grayscale {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-hue-rotate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-invert {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-opacity {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-saturate {\n syntax: "*";\n inherits: false;\n}\n@property --tw-backdrop-sepia {\n syntax: "*";\n inherits: false;\n}\n@property --tw-duration {\n syntax: "*";\n inherits: false;\n}\n@property --tw-ease {\n syntax: "*";\n inherits: false;\n}\n@keyframes spin {\n to {\n transform: rotate(360deg);\n }\n}\n@keyframes pulse {\n 50% {\n opacity: 0.5;\n }\n}\n@layer properties {\n @supports ((-webkit-hyphens: none) and (not (margin-trim: inline))) or ((-moz-orient: inline) and (not (color:rgb(from red r g b)))) {\n *, ::before, ::after, ::backdrop {\n --tw-translate-x: 0;\n --tw-translate-y: 0;\n --tw-translate-z: 0;\n --tw-scale-x: 1;\n --tw-scale-y: 1;\n --tw-scale-z: 1;\n --tw-rotate-x: initial;\n --tw-rotate-y: initial;\n --tw-rotate-z: initial;\n --tw-skew-x: initial;\n --tw-skew-y: initial;\n --tw-space-y-reverse: 0;\n --tw-space-x-reverse: 0;\n --tw-border-style: solid;\n --tw-gradient-position: initial;\n --tw-gradient-from: #0000;\n --tw-gradient-via: #0000;\n --tw-gradient-to: #0000;\n --tw-gradient-stops: initial;\n --tw-gradient-via-stops: initial;\n --tw-gradient-from-position: 0%;\n --tw-gradient-via-position: 50%;\n --tw-gradient-to-position: 100%;\n --tw-leading: initial;\n --tw-font-weight: initial;\n --tw-tracking: initial;\n --tw-shadow: 0 0 #0000;\n --tw-shadow-color: initial;\n --tw-shadow-alpha: 100%;\n --tw-inset-shadow: 0 0 #0000;\n --tw-inset-shadow-color: initial;\n --tw-inset-shadow-alpha: 100%;\n --tw-ring-color: initial;\n --tw-ring-shadow: 0 0 #0000;\n --tw-inset-ring-color: initial;\n --tw-inset-ring-shadow: 0 0 #0000;\n --tw-ring-inset: initial;\n --tw-ring-offset-width: 0px;\n --tw-ring-offset-color: #fff;\n --tw-ring-offset-shadow: 0 0 #0000;\n --tw-outline-style: solid;\n --tw-blur: initial;\n --tw-brightness: initial;\n --tw-contrast: initial;\n --tw-grayscale: initial;\n --tw-hue-rotate: initial;\n --tw-invert: initial;\n --tw-opacity: initial;\n --tw-saturate: initial;\n --tw-sepia: initial;\n --tw-drop-shadow: initial;\n --tw-drop-shadow-color: initial;\n --tw-drop-shadow-alpha: 100%;\n --tw-drop-shadow-size: initial;\n --tw-backdrop-blur: initial;\n --tw-backdrop-brightness: initial;\n --tw-backdrop-contrast: initial;\n --tw-backdrop-grayscale: initial;\n --tw-backdrop-hue-rotate: initial;\n --tw-backdrop-invert: initial;\n --tw-backdrop-opacity: initial;\n --tw-backdrop-saturate: initial;\n --tw-backdrop-sepia: initial;\n --tw-duration: initial;\n --tw-ease: initial;\n }\n }\n}';
|
|
215
216
|
document.head.appendChild(s);
|
|
216
217
|
})();
|
|
217
218
|
|
|
@@ -1281,7 +1282,7 @@ var DialogContent = React2.forwardRef(({ className, children, ...props }, ref) =
|
|
|
1281
1282
|
if (!open) return null;
|
|
1282
1283
|
return /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)("div", { className: "fixed inset-0 z-50 flex items-center justify-center p-4", children: [
|
|
1283
1284
|
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(DialogOverlay, {}),
|
|
1284
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.
|
|
1285
|
+
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
|
|
1285
1286
|
"div",
|
|
1286
1287
|
{
|
|
1287
1288
|
ref,
|
|
@@ -1291,39 +1292,7 @@ var DialogContent = React2.forwardRef(({ className, children, ...props }, ref) =
|
|
|
1291
1292
|
className
|
|
1292
1293
|
),
|
|
1293
1294
|
...props,
|
|
1294
|
-
children
|
|
1295
|
-
children,
|
|
1296
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(
|
|
1297
|
-
"button",
|
|
1298
|
-
{
|
|
1299
|
-
type: "button",
|
|
1300
|
-
onClick: () => onOpenChange(false),
|
|
1301
|
-
className: "absolute right-4 top-4 rounded-sm opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:pointer-events-none",
|
|
1302
|
-
children: [
|
|
1303
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(
|
|
1304
|
-
"svg",
|
|
1305
|
-
{
|
|
1306
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
1307
|
-
width: "24",
|
|
1308
|
-
height: "24",
|
|
1309
|
-
viewBox: "0 0 24 24",
|
|
1310
|
-
fill: "none",
|
|
1311
|
-
stroke: "currentColor",
|
|
1312
|
-
strokeWidth: "2",
|
|
1313
|
-
strokeLinecap: "round",
|
|
1314
|
-
strokeLinejoin: "round",
|
|
1315
|
-
className: "h-4 w-4",
|
|
1316
|
-
children: [
|
|
1317
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("path", { d: "M18 6 6 18" }),
|
|
1318
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("path", { d: "m6 6 12 12" })
|
|
1319
|
-
]
|
|
1320
|
-
}
|
|
1321
|
-
),
|
|
1322
|
-
/* @__PURE__ */ (0, import_jsx_runtime2.jsx)("span", { className: "sr-only", children: "Close" })
|
|
1323
|
-
]
|
|
1324
|
-
}
|
|
1325
|
-
)
|
|
1326
|
-
]
|
|
1295
|
+
children
|
|
1327
1296
|
}
|
|
1328
1297
|
)
|
|
1329
1298
|
] });
|
|
@@ -1415,7 +1384,8 @@ function useCheckoutSession({
|
|
|
1415
1384
|
customer,
|
|
1416
1385
|
couponCode,
|
|
1417
1386
|
metadata,
|
|
1418
|
-
existingSubscriptionId
|
|
1387
|
+
existingSubscriptionId,
|
|
1388
|
+
adaptivePricing = true
|
|
1419
1389
|
}) {
|
|
1420
1390
|
const { client, appUrl, debug } = useBillingOS();
|
|
1421
1391
|
const [sessionId, setSessionId] = (0, import_react4.useState)(null);
|
|
@@ -1425,7 +1395,11 @@ function useCheckoutSession({
|
|
|
1425
1395
|
const initiatedForPriceRef = (0, import_react4.useRef)(null);
|
|
1426
1396
|
const createSession = async () => {
|
|
1427
1397
|
if (!enabled || !priceId || !client) return;
|
|
1428
|
-
if (debug)
|
|
1398
|
+
if (debug)
|
|
1399
|
+
console.log("[BillingOS] Creating checkout session...", {
|
|
1400
|
+
priceId,
|
|
1401
|
+
customer
|
|
1402
|
+
});
|
|
1429
1403
|
setLoading(true);
|
|
1430
1404
|
setError(null);
|
|
1431
1405
|
try {
|
|
@@ -1436,10 +1410,12 @@ function useCheckoutSession({
|
|
|
1436
1410
|
metadata,
|
|
1437
1411
|
existingSubscriptionId,
|
|
1438
1412
|
// Return URLs will be handled by postMessage instead
|
|
1439
|
-
mode: "embedded"
|
|
1413
|
+
mode: "embedded",
|
|
1414
|
+
adaptivePricing
|
|
1440
1415
|
});
|
|
1441
1416
|
setSessionId(session.id);
|
|
1442
|
-
if (debug)
|
|
1417
|
+
if (debug)
|
|
1418
|
+
console.log("[BillingOS] Checkout session created:", session.id);
|
|
1443
1419
|
const iframeUrl = `${appUrl}/embed/checkout/${session.id}`;
|
|
1444
1420
|
setSessionUrl(iframeUrl);
|
|
1445
1421
|
if (debug) console.log("[BillingOS] Iframe URL:", iframeUrl);
|
|
@@ -1578,7 +1554,8 @@ function CheckoutModal({
|
|
|
1578
1554
|
onSuccess,
|
|
1579
1555
|
onError,
|
|
1580
1556
|
onCancel,
|
|
1581
|
-
debug = false
|
|
1557
|
+
debug = false,
|
|
1558
|
+
adaptivePricing = true
|
|
1582
1559
|
}) {
|
|
1583
1560
|
const { appUrl, debug: contextDebug } = useBillingOS();
|
|
1584
1561
|
const isDebug = debug || contextDebug;
|
|
@@ -1586,19 +1563,16 @@ function CheckoutModal({
|
|
|
1586
1563
|
const [error, setError] = (0, import_react6.useState)(null);
|
|
1587
1564
|
const [iframeHeight, setIframeHeight] = (0, import_react6.useState)(600);
|
|
1588
1565
|
const iframeRef = (0, import_react6.useRef)(null);
|
|
1589
|
-
(0, import_react6.useEffect)(() => {
|
|
1590
|
-
if (isDebug) console.log("[BillingOS] CheckoutModal mounted");
|
|
1591
|
-
}, []);
|
|
1592
1566
|
const { sessionId, sessionUrl, loading, error: sessionError } = useCheckoutSession({
|
|
1593
1567
|
enabled: open,
|
|
1594
1568
|
priceId,
|
|
1595
1569
|
customer,
|
|
1596
1570
|
couponCode,
|
|
1597
1571
|
metadata,
|
|
1598
|
-
existingSubscriptionId
|
|
1572
|
+
existingSubscriptionId,
|
|
1573
|
+
adaptivePricing
|
|
1599
1574
|
});
|
|
1600
1575
|
const handleIframeMessage = (0, import_react6.useCallback)((message) => {
|
|
1601
|
-
if (isDebug) console.log("[BillingOS] Iframe message:", message.type, message);
|
|
1602
1576
|
switch (message.type) {
|
|
1603
1577
|
case "CHECKOUT_READY":
|
|
1604
1578
|
setState("ready");
|
|
@@ -1670,14 +1644,10 @@ function CheckoutModal({
|
|
|
1670
1644
|
DialogContent,
|
|
1671
1645
|
{
|
|
1672
1646
|
className: cn(
|
|
1673
|
-
"
|
|
1647
|
+
"max-w-[800px] w-full p-0 overflow-hidden",
|
|
1674
1648
|
"max-h-[90vh] relative"
|
|
1675
1649
|
),
|
|
1676
1650
|
children: [
|
|
1677
|
-
/* @__PURE__ */ (0, import_jsx_runtime4.jsxs)("div", { className: "absolute top-2 right-2 z-20 flex items-center gap-1 bg-gradient-to-r from-blue-600 to-purple-600 text-white text-xs font-medium px-2 py-1 rounded-full shadow-lg", children: [
|
|
1678
|
-
/* @__PURE__ */ (0, import_jsx_runtime4.jsx)("svg", { className: "w-3 h-3", fill: "currentColor", viewBox: "0 0 20 20", children: /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("path", { fillRule: "evenodd", d: "M2.166 4.999A11.954 11.954 0 0010 1.944 11.954 11.954 0 0017.834 5c.11.65.166 1.32.166 2.001 0 5.225-3.34 9.67-8 11.317C5.34 16.67 2 12.225 2 7c0-.682.057-1.35.166-2.001zm11.541 3.708a1 1 0 00-1.414-1.414L9 10.586 7.707 9.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4z", clipRule: "evenodd" }) }),
|
|
1679
|
-
/* @__PURE__ */ (0, import_jsx_runtime4.jsx)("span", { children: "Secure Iframe" })
|
|
1680
|
-
] }),
|
|
1681
1651
|
showError ? /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)("div", { className: "p-8 text-center", children: [
|
|
1682
1652
|
/* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "text-red-600 mb-2", children: /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
|
|
1683
1653
|
"svg",
|
|
@@ -1708,11 +1678,7 @@ function CheckoutModal({
|
|
|
1708
1678
|
}
|
|
1709
1679
|
)
|
|
1710
1680
|
] }) : /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)(import_jsx_runtime4.Fragment, { children: [
|
|
1711
|
-
showSpinner && /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "absolute inset-0 flex items-center justify-center bg-white z-10", children: /* @__PURE__ */ (0, import_jsx_runtime4.
|
|
1712
|
-
/* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "animate-spin rounded-full h-12 w-12 border-b-2 border-blue-600" }),
|
|
1713
|
-
/* @__PURE__ */ (0, import_jsx_runtime4.jsx)("p", { className: "mt-4 text-gray-600 font-medium", children: "Loading secure checkout..." }),
|
|
1714
|
-
/* @__PURE__ */ (0, import_jsx_runtime4.jsx)("p", { className: "mt-2 text-xs text-gray-500", children: "Iframe-based \u2022 PCI Compliant" })
|
|
1715
|
-
] }) }),
|
|
1681
|
+
showSpinner && /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "absolute inset-0 flex items-center justify-center bg-white z-10", children: /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "animate-spin rounded-full h-10 w-10 border-b-2 border-blue-600" }) }),
|
|
1716
1682
|
sessionUrl && /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
|
|
1717
1683
|
CheckoutIframe,
|
|
1718
1684
|
{
|
|
@@ -1724,20 +1690,6 @@ function CheckoutModal({
|
|
|
1724
1690
|
showSpinner ? "opacity-0" : "opacity-100"
|
|
1725
1691
|
),
|
|
1726
1692
|
onLoad: () => {
|
|
1727
|
-
console.log(
|
|
1728
|
-
"%c\u2705 Iframe loaded successfully",
|
|
1729
|
-
"color: #10b981; font-weight: 600;",
|
|
1730
|
-
`
|
|
1731
|
-
URL: ${sessionUrl}`
|
|
1732
|
-
);
|
|
1733
|
-
if (debug) {
|
|
1734
|
-
console.log("[CheckoutModal] Full iframe details:", {
|
|
1735
|
-
sessionUrl,
|
|
1736
|
-
sessionId,
|
|
1737
|
-
state,
|
|
1738
|
-
height: iframeHeight
|
|
1739
|
-
});
|
|
1740
|
-
}
|
|
1741
1693
|
}
|
|
1742
1694
|
}
|
|
1743
1695
|
),
|
|
@@ -1805,6 +1757,7 @@ var CheckoutAPI = class {
|
|
|
1805
1757
|
metadata: options.metadata,
|
|
1806
1758
|
theme: options.theme,
|
|
1807
1759
|
locale: options.locale,
|
|
1760
|
+
adaptivePricing: options.adaptivePricing ?? true,
|
|
1808
1761
|
onSuccess: (subscription) => {
|
|
1809
1762
|
if (options.onSuccess) {
|
|
1810
1763
|
options.onSuccess(subscription);
|
|
@@ -3053,9 +3006,38 @@ function Skeleton({
|
|
|
3053
3006
|
);
|
|
3054
3007
|
}
|
|
3055
3008
|
|
|
3009
|
+
// src/components/ui/switch.tsx
|
|
3010
|
+
var import_jsx_runtime20 = require("react/jsx-runtime");
|
|
3011
|
+
function Switch({ checked, onCheckedChange, className, ...props }) {
|
|
3012
|
+
return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
3013
|
+
"button",
|
|
3014
|
+
{
|
|
3015
|
+
type: "button",
|
|
3016
|
+
role: "switch",
|
|
3017
|
+
"aria-checked": checked,
|
|
3018
|
+
onClick: () => onCheckedChange(!checked),
|
|
3019
|
+
className: cn(
|
|
3020
|
+
"relative inline-flex h-6 w-11 flex-shrink-0 cursor-pointer rounded-full border-2 border-transparent transition-colors duration-200 ease-in-out focus:outline-none focus-visible:ring-2 focus-visible:ring-ring",
|
|
3021
|
+
checked ? "bg-blue-600" : "bg-gray-300",
|
|
3022
|
+
className
|
|
3023
|
+
),
|
|
3024
|
+
...props,
|
|
3025
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
3026
|
+
"span",
|
|
3027
|
+
{
|
|
3028
|
+
className: cn(
|
|
3029
|
+
"pointer-events-none inline-block h-5 w-5 transform rounded-full bg-white shadow ring-0 transition duration-200 ease-in-out",
|
|
3030
|
+
checked ? "translate-x-5" : "translate-x-0"
|
|
3031
|
+
)
|
|
3032
|
+
}
|
|
3033
|
+
)
|
|
3034
|
+
}
|
|
3035
|
+
);
|
|
3036
|
+
}
|
|
3037
|
+
|
|
3056
3038
|
// src/components/ui/tabs.tsx
|
|
3057
3039
|
var React18 = __toESM(require("react"), 1);
|
|
3058
|
-
var
|
|
3040
|
+
var import_jsx_runtime21 = require("react/jsx-runtime");
|
|
3059
3041
|
var TabsContext = React18.createContext(null);
|
|
3060
3042
|
function useTabsContext() {
|
|
3061
3043
|
const context = React18.useContext(TabsContext);
|
|
@@ -3069,11 +3051,11 @@ var Tabs = React18.forwardRef(
|
|
|
3069
3051
|
const [internalValue, setInternalValue] = React18.useState(defaultValue ?? "");
|
|
3070
3052
|
const currentValue = value ?? internalValue;
|
|
3071
3053
|
const handleValueChange = onValueChange ?? setInternalValue;
|
|
3072
|
-
return /* @__PURE__ */ (0,
|
|
3054
|
+
return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TabsContext.Provider, { value: { value: currentValue, onValueChange: handleValueChange }, children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { ref, className: cn("", className), ...props, children }) });
|
|
3073
3055
|
}
|
|
3074
3056
|
);
|
|
3075
3057
|
Tabs.displayName = "Tabs";
|
|
3076
|
-
var TabsList = React18.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0,
|
|
3058
|
+
var TabsList = React18.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
3077
3059
|
"div",
|
|
3078
3060
|
{
|
|
3079
3061
|
ref,
|
|
@@ -3090,7 +3072,7 @@ var TabsTrigger = React18.forwardRef(
|
|
|
3090
3072
|
({ className, value, ...props }, ref) => {
|
|
3091
3073
|
const { value: currentValue, onValueChange } = useTabsContext();
|
|
3092
3074
|
const isSelected = currentValue === value;
|
|
3093
|
-
return /* @__PURE__ */ (0,
|
|
3075
|
+
return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
3094
3076
|
"button",
|
|
3095
3077
|
{
|
|
3096
3078
|
ref,
|
|
@@ -3115,7 +3097,7 @@ var TabsContent = React18.forwardRef(
|
|
|
3115
3097
|
const { value: currentValue } = useTabsContext();
|
|
3116
3098
|
const isSelected = currentValue === value;
|
|
3117
3099
|
if (!isSelected) return null;
|
|
3118
|
-
return /* @__PURE__ */ (0,
|
|
3100
|
+
return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
|
|
3119
3101
|
"div",
|
|
3120
3102
|
{
|
|
3121
3103
|
ref,
|
|
@@ -3135,9 +3117,9 @@ TabsContent.displayName = "TabsContent";
|
|
|
3135
3117
|
|
|
3136
3118
|
// src/components/ui/textarea.tsx
|
|
3137
3119
|
var React19 = __toESM(require("react"), 1);
|
|
3138
|
-
var
|
|
3120
|
+
var import_jsx_runtime22 = require("react/jsx-runtime");
|
|
3139
3121
|
var Textarea = React19.forwardRef(({ className, ...props }, ref) => {
|
|
3140
|
-
return /* @__PURE__ */ (0,
|
|
3122
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
3141
3123
|
"textarea",
|
|
3142
3124
|
{
|
|
3143
3125
|
className: cn(
|
|
@@ -3156,10 +3138,10 @@ var import_react12 = require("react");
|
|
|
3156
3138
|
|
|
3157
3139
|
// src/components/CustomerPortal/PortalIframe.tsx
|
|
3158
3140
|
var import_react9 = require("react");
|
|
3159
|
-
var
|
|
3141
|
+
var import_jsx_runtime23 = require("react/jsx-runtime");
|
|
3160
3142
|
var PortalIframe = (0, import_react9.forwardRef)(
|
|
3161
3143
|
({ src, height = 600, className, onLoad }, ref) => {
|
|
3162
|
-
return /* @__PURE__ */ (0,
|
|
3144
|
+
return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3163
3145
|
"iframe",
|
|
3164
3146
|
{
|
|
3165
3147
|
ref,
|
|
@@ -3285,87 +3267,9 @@ function usePortalMessaging({
|
|
|
3285
3267
|
}
|
|
3286
3268
|
|
|
3287
3269
|
// src/components/PricingTable/PricingTable.tsx
|
|
3288
|
-
var
|
|
3270
|
+
var React24 = __toESM(require("react"), 1);
|
|
3289
3271
|
var import_react_query10 = require("@tanstack/react-query");
|
|
3290
3272
|
|
|
3291
|
-
// src/components/ui/table.tsx
|
|
3292
|
-
var React20 = __toESM(require("react"), 1);
|
|
3293
|
-
var import_jsx_runtime23 = require("react/jsx-runtime");
|
|
3294
|
-
var Table = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "relative w-full overflow-auto", children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3295
|
-
"table",
|
|
3296
|
-
{
|
|
3297
|
-
ref,
|
|
3298
|
-
className: cn("w-full caption-bottom text-sm", className),
|
|
3299
|
-
...props
|
|
3300
|
-
}
|
|
3301
|
-
) }));
|
|
3302
|
-
Table.displayName = "Table";
|
|
3303
|
-
var TableHeader = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("thead", { ref, className: cn("[&_tr]:border-b", className), ...props }));
|
|
3304
|
-
TableHeader.displayName = "TableHeader";
|
|
3305
|
-
var TableBody = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3306
|
-
"tbody",
|
|
3307
|
-
{
|
|
3308
|
-
ref,
|
|
3309
|
-
className: cn("[&_tr:last-child]:border-0", className),
|
|
3310
|
-
...props
|
|
3311
|
-
}
|
|
3312
|
-
));
|
|
3313
|
-
TableBody.displayName = "TableBody";
|
|
3314
|
-
var TableFooter = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3315
|
-
"tfoot",
|
|
3316
|
-
{
|
|
3317
|
-
ref,
|
|
3318
|
-
className: cn(
|
|
3319
|
-
"border-t bg-muted/50 font-medium [&>tr]:last:border-b-0",
|
|
3320
|
-
className
|
|
3321
|
-
),
|
|
3322
|
-
...props
|
|
3323
|
-
}
|
|
3324
|
-
));
|
|
3325
|
-
TableFooter.displayName = "TableFooter";
|
|
3326
|
-
var TableRow = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3327
|
-
"tr",
|
|
3328
|
-
{
|
|
3329
|
-
ref,
|
|
3330
|
-
className: cn(
|
|
3331
|
-
"border-b transition-colors hover:bg-muted/50 data-[state=selected]:bg-muted",
|
|
3332
|
-
className
|
|
3333
|
-
),
|
|
3334
|
-
...props
|
|
3335
|
-
}
|
|
3336
|
-
));
|
|
3337
|
-
TableRow.displayName = "TableRow";
|
|
3338
|
-
var TableHead = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3339
|
-
"th",
|
|
3340
|
-
{
|
|
3341
|
-
ref,
|
|
3342
|
-
className: cn(
|
|
3343
|
-
"h-12 px-4 text-left align-middle font-medium text-muted-foreground [&:has([role=checkbox])]:pr-0",
|
|
3344
|
-
className
|
|
3345
|
-
),
|
|
3346
|
-
...props
|
|
3347
|
-
}
|
|
3348
|
-
));
|
|
3349
|
-
TableHead.displayName = "TableHead";
|
|
3350
|
-
var TableCell = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3351
|
-
"td",
|
|
3352
|
-
{
|
|
3353
|
-
ref,
|
|
3354
|
-
className: cn("p-4 align-middle [&:has([role=checkbox])]:pr-0", className),
|
|
3355
|
-
...props
|
|
3356
|
-
}
|
|
3357
|
-
));
|
|
3358
|
-
TableCell.displayName = "TableCell";
|
|
3359
|
-
var TableCaption = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
|
|
3360
|
-
"caption",
|
|
3361
|
-
{
|
|
3362
|
-
ref,
|
|
3363
|
-
className: cn("mt-4 text-sm text-muted-foreground", className),
|
|
3364
|
-
...props
|
|
3365
|
-
}
|
|
3366
|
-
));
|
|
3367
|
-
TableCaption.displayName = "TableCaption";
|
|
3368
|
-
|
|
3369
3273
|
// src/components/PricingTable/hooks/useProducts.ts
|
|
3370
3274
|
var import_react_query7 = require("@tanstack/react-query");
|
|
3371
3275
|
function useProducts2(options = {}) {
|
|
@@ -3384,16 +3288,152 @@ function useProducts2(options = {}) {
|
|
|
3384
3288
|
});
|
|
3385
3289
|
}
|
|
3386
3290
|
|
|
3291
|
+
// src/components/PricingTable/PricingCard.tsx
|
|
3292
|
+
var import_lucide_react = require("lucide-react");
|
|
3293
|
+
var import_jsx_runtime24 = require("react/jsx-runtime");
|
|
3294
|
+
function formatPrice(price) {
|
|
3295
|
+
const amount = price.amount / 100;
|
|
3296
|
+
return amount % 1 === 0 ? `$${amount.toFixed(0)}` : `$${amount.toFixed(2)}`;
|
|
3297
|
+
}
|
|
3298
|
+
function formatLimit(limit, unit) {
|
|
3299
|
+
if (!limit) return null;
|
|
3300
|
+
const n = limit >= 1e3 ? `${(limit / 1e3).toFixed(limit % 1e3 === 0 ? 0 : 1)}k` : limit.toLocaleString();
|
|
3301
|
+
return unit ? `${n} ${unit}` : n;
|
|
3302
|
+
}
|
|
3303
|
+
function getYearlySavings(monthly, yearly) {
|
|
3304
|
+
const yearlyFromMonthly = monthly * 12;
|
|
3305
|
+
return Math.round((yearlyFromMonthly - yearly) / yearlyFromMonthly * 100);
|
|
3306
|
+
}
|
|
3307
|
+
function PricingCard({
|
|
3308
|
+
product,
|
|
3309
|
+
allFeatures,
|
|
3310
|
+
isYearly,
|
|
3311
|
+
currentSubscription,
|
|
3312
|
+
currentPlanAmount,
|
|
3313
|
+
onSelectPlan
|
|
3314
|
+
}) {
|
|
3315
|
+
const monthlyPrice = product.prices.find((p) => p.interval === "month");
|
|
3316
|
+
const yearlyPrice = product.prices.find((p) => p.interval === "year");
|
|
3317
|
+
const currentPrice = isYearly && yearlyPrice ? yearlyPrice : monthlyPrice;
|
|
3318
|
+
const savings = monthlyPrice && yearlyPrice ? getYearlySavings(monthlyPrice.amount, yearlyPrice.amount) : 0;
|
|
3319
|
+
const isHighlighted = product.highlighted || product.isCurrentPlan;
|
|
3320
|
+
const isFree = (monthlyPrice?.amount ?? 0) === 0;
|
|
3321
|
+
const getButtonLabel = () => {
|
|
3322
|
+
if (product.isCurrentPlan) return "Current Plan";
|
|
3323
|
+
if (!currentSubscription) return isFree ? "Get Started Free" : "Get Started";
|
|
3324
|
+
const thisAmount = currentPrice?.amount ?? 0;
|
|
3325
|
+
if (thisAmount > currentPlanAmount) return "Upgrade Now";
|
|
3326
|
+
if (thisAmount < currentPlanAmount) return "Downgrade";
|
|
3327
|
+
return "Switch Plan";
|
|
3328
|
+
};
|
|
3329
|
+
const handleClick = () => {
|
|
3330
|
+
if (!product.isCurrentPlan && currentPrice) {
|
|
3331
|
+
onSelectPlan(currentPrice.id);
|
|
3332
|
+
}
|
|
3333
|
+
};
|
|
3334
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
3335
|
+
"div",
|
|
3336
|
+
{
|
|
3337
|
+
className: cn(
|
|
3338
|
+
"relative rounded-2xl border bg-white p-8 transition-all duration-300",
|
|
3339
|
+
isHighlighted ? "border-blue-200 ring-2 ring-blue-600 shadow-xl shadow-blue-500/10 md:scale-105 z-10" : "border-slate-200 hover:border-slate-300 hover:shadow-lg hover:-translate-y-1"
|
|
3340
|
+
),
|
|
3341
|
+
children: [
|
|
3342
|
+
(product.highlighted || product.isCurrentPlan) && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "absolute -top-3 left-1/2 -translate-x-1/2", children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
3343
|
+
Badge,
|
|
3344
|
+
{
|
|
3345
|
+
className: cn(
|
|
3346
|
+
"border-0 px-4 py-1 text-xs font-semibold",
|
|
3347
|
+
product.isCurrentPlan ? "bg-emerald-600 text-white" : "bg-blue-600 text-white"
|
|
3348
|
+
),
|
|
3349
|
+
children: product.isCurrentPlan ? "Current Plan" : "Most Popular"
|
|
3350
|
+
}
|
|
3351
|
+
) }),
|
|
3352
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "mb-6", children: [
|
|
3353
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("h3", { className: "text-xl font-semibold text-slate-900 mb-1", children: product.name }),
|
|
3354
|
+
product.description && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "text-sm text-slate-500", children: product.description })
|
|
3355
|
+
] }),
|
|
3356
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "mb-6", children: [
|
|
3357
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "flex items-baseline gap-1", children: [
|
|
3358
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "text-4xl font-bold text-slate-900", children: currentPrice ? formatPrice(currentPrice) : "$0" }),
|
|
3359
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "text-slate-500 text-sm", children: isYearly ? "/year" : "/mo" })
|
|
3360
|
+
] }),
|
|
3361
|
+
isYearly && savings > 0 && /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("p", { className: "text-sm text-emerald-600 font-medium mt-1", children: [
|
|
3362
|
+
"Save ",
|
|
3363
|
+
savings,
|
|
3364
|
+
"% yearly"
|
|
3365
|
+
] }),
|
|
3366
|
+
!isYearly && yearlyPrice && savings > 0 && /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("p", { className: "text-sm text-slate-400 mt-1", children: [
|
|
3367
|
+
"Switch to yearly & save ",
|
|
3368
|
+
savings,
|
|
3369
|
+
"%"
|
|
3370
|
+
] })
|
|
3371
|
+
] }),
|
|
3372
|
+
product.trialDays > 0 && !product.isCurrentPlan && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "mb-6", children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(Badge, { variant: "outline", className: "bg-amber-50 text-amber-700 border-amber-200", children: [
|
|
3373
|
+
product.trialDays,
|
|
3374
|
+
"-day free trial"
|
|
3375
|
+
] }) }),
|
|
3376
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
3377
|
+
Button,
|
|
3378
|
+
{
|
|
3379
|
+
disabled: product.isCurrentPlan,
|
|
3380
|
+
onClick: handleClick,
|
|
3381
|
+
className: cn(
|
|
3382
|
+
"w-full mb-8 h-11 rounded-xl font-medium transition-all border-0",
|
|
3383
|
+
product.isCurrentPlan ? "bg-slate-100 text-slate-400 cursor-not-allowed hover:bg-slate-100" : isHighlighted ? "bg-blue-600 hover:bg-blue-700 text-white shadow-md shadow-blue-500/25" : "bg-slate-100 hover:bg-slate-200 text-slate-700"
|
|
3384
|
+
),
|
|
3385
|
+
children: getButtonLabel()
|
|
3386
|
+
}
|
|
3387
|
+
),
|
|
3388
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "space-y-4", children: [
|
|
3389
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "text-xs font-semibold uppercase tracking-wider text-slate-400", children: "What's included" }),
|
|
3390
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("ul", { className: "space-y-3", children: allFeatures.map((featureMeta) => {
|
|
3391
|
+
const productFeature = product.features.find((f) => f.name === featureMeta.name);
|
|
3392
|
+
const hasFeature = !!productFeature;
|
|
3393
|
+
const limit = productFeature?.properties?.limit;
|
|
3394
|
+
const unit = productFeature?.properties?.unit;
|
|
3395
|
+
const displayValue = hasFeature && typeof limit === "number" && limit !== -1 ? formatLimit(limit, unit) : null;
|
|
3396
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
3397
|
+
"li",
|
|
3398
|
+
{
|
|
3399
|
+
className: cn(
|
|
3400
|
+
"flex items-center gap-3 text-sm",
|
|
3401
|
+
hasFeature ? "text-slate-700" : "text-slate-300"
|
|
3402
|
+
),
|
|
3403
|
+
children: [
|
|
3404
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
3405
|
+
"div",
|
|
3406
|
+
{
|
|
3407
|
+
className: cn(
|
|
3408
|
+
"flex items-center justify-center w-5 h-5 rounded-full flex-shrink-0",
|
|
3409
|
+
hasFeature ? "bg-blue-100" : "bg-slate-100"
|
|
3410
|
+
),
|
|
3411
|
+
children: hasFeature ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(import_lucide_react.Check, { className: "w-3 h-3 text-blue-600" }) : /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(import_lucide_react.X, { className: "w-3 h-3 text-slate-400" })
|
|
3412
|
+
}
|
|
3413
|
+
),
|
|
3414
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "flex-1", children: limit === -1 ? `Unlimited ${featureMeta.title}` : featureMeta.title }),
|
|
3415
|
+
displayValue && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "flex-shrink-0 text-xs bg-slate-100 text-slate-500 font-medium px-2 py-0.5 rounded", children: displayValue })
|
|
3416
|
+
]
|
|
3417
|
+
},
|
|
3418
|
+
featureMeta.name
|
|
3419
|
+
);
|
|
3420
|
+
}) })
|
|
3421
|
+
] })
|
|
3422
|
+
]
|
|
3423
|
+
}
|
|
3424
|
+
);
|
|
3425
|
+
}
|
|
3426
|
+
|
|
3387
3427
|
// src/components/PaymentBottomSheet/PaymentBottomSheet.tsx
|
|
3388
|
-
var
|
|
3428
|
+
var React23 = __toESM(require("react"), 1);
|
|
3389
3429
|
var import_stripe_js = require("@stripe/stripe-js");
|
|
3390
3430
|
var import_react_stripe_js2 = require("@stripe/react-stripe-js");
|
|
3391
3431
|
var import_react_query9 = require("@tanstack/react-query");
|
|
3392
3432
|
|
|
3393
3433
|
// src/components/ErrorBoundary.tsx
|
|
3394
|
-
var
|
|
3395
|
-
var
|
|
3396
|
-
var ErrorBoundary = class extends
|
|
3434
|
+
var React20 = __toESM(require("react"), 1);
|
|
3435
|
+
var import_jsx_runtime25 = require("react/jsx-runtime");
|
|
3436
|
+
var ErrorBoundary = class extends React20.Component {
|
|
3397
3437
|
constructor(props) {
|
|
3398
3438
|
super(props);
|
|
3399
3439
|
__publicField(this, "reset", () => {
|
|
@@ -3414,7 +3454,7 @@ var ErrorBoundary = class extends React21.Component {
|
|
|
3414
3454
|
if (this.props.fallback) {
|
|
3415
3455
|
return this.props.fallback(this.state.error, this.reset);
|
|
3416
3456
|
}
|
|
3417
|
-
return /* @__PURE__ */ (0,
|
|
3457
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { style: {
|
|
3418
3458
|
padding: "20px",
|
|
3419
3459
|
border: "1px solid #ef4444",
|
|
3420
3460
|
borderRadius: "8px",
|
|
@@ -3422,9 +3462,9 @@ var ErrorBoundary = class extends React21.Component {
|
|
|
3422
3462
|
color: "#991b1b",
|
|
3423
3463
|
fontFamily: "system-ui, -apple-system, sans-serif"
|
|
3424
3464
|
}, children: [
|
|
3425
|
-
/* @__PURE__ */ (0,
|
|
3426
|
-
/* @__PURE__ */ (0,
|
|
3427
|
-
/* @__PURE__ */ (0,
|
|
3465
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("h3", { style: { margin: "0 0 10px 0", fontSize: "16px", fontWeight: "bold" }, children: "Payment Error" }),
|
|
3466
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("p", { style: { margin: "0 0 10px 0", fontSize: "14px" }, children: this.state.error?.message || "An unexpected error occurred while loading the payment form." }),
|
|
3467
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
3428
3468
|
"button",
|
|
3429
3469
|
{
|
|
3430
3470
|
onClick: this.reset,
|
|
@@ -3487,9 +3527,9 @@ function useConfirmCheckout(options) {
|
|
|
3487
3527
|
}
|
|
3488
3528
|
|
|
3489
3529
|
// src/components/PaymentBottomSheet/PaymentForm.tsx
|
|
3490
|
-
var
|
|
3530
|
+
var React21 = __toESM(require("react"), 1);
|
|
3491
3531
|
var import_react_stripe_js = require("@stripe/react-stripe-js");
|
|
3492
|
-
var
|
|
3532
|
+
var import_jsx_runtime26 = require("react/jsx-runtime");
|
|
3493
3533
|
function PaymentForm({
|
|
3494
3534
|
checkoutSession,
|
|
3495
3535
|
onSuccess,
|
|
@@ -3500,8 +3540,8 @@ function PaymentForm({
|
|
|
3500
3540
|
const { client } = useBillingOS();
|
|
3501
3541
|
const stripe = (0, import_react_stripe_js.useStripe)();
|
|
3502
3542
|
const elements = (0, import_react_stripe_js.useElements)();
|
|
3503
|
-
const [error, setError] =
|
|
3504
|
-
const [isExpressCheckoutReady, setIsExpressCheckoutReady] =
|
|
3543
|
+
const [error, setError] = React21.useState(null);
|
|
3544
|
+
const [isExpressCheckoutReady, setIsExpressCheckoutReady] = React21.useState(false);
|
|
3505
3545
|
const formatAmount = (cents, currency) => {
|
|
3506
3546
|
return new Intl.NumberFormat("en-US", {
|
|
3507
3547
|
style: "currency",
|
|
@@ -3588,8 +3628,8 @@ function PaymentForm({
|
|
|
3588
3628
|
setIsProcessing(false);
|
|
3589
3629
|
}
|
|
3590
3630
|
};
|
|
3591
|
-
return /* @__PURE__ */ (0,
|
|
3592
|
-
/* @__PURE__ */ (0,
|
|
3631
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("form", { onSubmit: handleSubmit, className: "space-y-6", children: [
|
|
3632
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: cn(!isExpressCheckoutReady && "hidden"), children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
3593
3633
|
import_react_stripe_js.ExpressCheckoutElement,
|
|
3594
3634
|
{
|
|
3595
3635
|
options: {
|
|
@@ -3602,11 +3642,11 @@ function PaymentForm({
|
|
|
3602
3642
|
onReady: () => setIsExpressCheckoutReady(true)
|
|
3603
3643
|
}
|
|
3604
3644
|
) }),
|
|
3605
|
-
isExpressCheckoutReady && /* @__PURE__ */ (0,
|
|
3606
|
-
/* @__PURE__ */ (0,
|
|
3607
|
-
/* @__PURE__ */ (0,
|
|
3645
|
+
isExpressCheckoutReady && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "relative", children: [
|
|
3646
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "absolute inset-0 flex items-center", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(Separator, { className: "w-full" }) }),
|
|
3647
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "relative flex justify-center text-xs uppercase", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", { className: "bg-background px-2 text-muted-foreground", children: "or pay with card" }) })
|
|
3608
3648
|
] }),
|
|
3609
|
-
/* @__PURE__ */ (0,
|
|
3649
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "space-y-4", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
3610
3650
|
import_react_stripe_js.PaymentElement,
|
|
3611
3651
|
{
|
|
3612
3652
|
options: {
|
|
@@ -3614,16 +3654,16 @@ function PaymentForm({
|
|
|
3614
3654
|
}
|
|
3615
3655
|
}
|
|
3616
3656
|
) }),
|
|
3617
|
-
error && /* @__PURE__ */ (0,
|
|
3618
|
-
/* @__PURE__ */ (0,
|
|
3657
|
+
error && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(Alert, { variant: "destructive", children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(AlertDescription, { children: error }) }),
|
|
3658
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
3619
3659
|
Button,
|
|
3620
3660
|
{
|
|
3621
3661
|
type: "submit",
|
|
3622
3662
|
className: "w-full",
|
|
3623
3663
|
size: "lg",
|
|
3624
3664
|
disabled: !stripe || isProcessing,
|
|
3625
|
-
children: isProcessing ? /* @__PURE__ */ (0,
|
|
3626
|
-
/* @__PURE__ */ (0,
|
|
3665
|
+
children: isProcessing ? /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("span", { className: "flex items-center gap-2", children: [
|
|
3666
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
|
|
3627
3667
|
"svg",
|
|
3628
3668
|
{
|
|
3629
3669
|
className: "animate-spin h-4 w-4",
|
|
@@ -3631,7 +3671,7 @@ function PaymentForm({
|
|
|
3631
3671
|
fill: "none",
|
|
3632
3672
|
viewBox: "0 0 24 24",
|
|
3633
3673
|
children: [
|
|
3634
|
-
/* @__PURE__ */ (0,
|
|
3674
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
3635
3675
|
"circle",
|
|
3636
3676
|
{
|
|
3637
3677
|
className: "opacity-25",
|
|
@@ -3642,7 +3682,7 @@ function PaymentForm({
|
|
|
3642
3682
|
strokeWidth: "4"
|
|
3643
3683
|
}
|
|
3644
3684
|
),
|
|
3645
|
-
/* @__PURE__ */ (0,
|
|
3685
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
3646
3686
|
"path",
|
|
3647
3687
|
{
|
|
3648
3688
|
className: "opacity-75",
|
|
@@ -3657,8 +3697,8 @@ function PaymentForm({
|
|
|
3657
3697
|
] }) : checkoutSession.proration ? `Upgrade Now - ${formattedAmount}` : `Subscribe - ${formattedAmount}`
|
|
3658
3698
|
}
|
|
3659
3699
|
),
|
|
3660
|
-
/* @__PURE__ */ (0,
|
|
3661
|
-
/* @__PURE__ */ (0,
|
|
3700
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "flex items-center justify-center gap-2 text-xs text-muted-foreground", children: [
|
|
3701
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
|
|
3662
3702
|
"svg",
|
|
3663
3703
|
{
|
|
3664
3704
|
xmlns: "http://www.w3.org/2000/svg",
|
|
@@ -3671,28 +3711,28 @@ function PaymentForm({
|
|
|
3671
3711
|
strokeLinecap: "round",
|
|
3672
3712
|
strokeLinejoin: "round",
|
|
3673
3713
|
children: [
|
|
3674
|
-
/* @__PURE__ */ (0,
|
|
3675
|
-
/* @__PURE__ */ (0,
|
|
3714
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("rect", { width: "18", height: "11", x: "3", y: "11", rx: "2", ry: "2" }),
|
|
3715
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("path", { d: "M7 11V7a5 5 0 0 1 10 0v4" })
|
|
3676
3716
|
]
|
|
3677
3717
|
}
|
|
3678
3718
|
),
|
|
3679
|
-
/* @__PURE__ */ (0,
|
|
3719
|
+
/* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", { children: "Secured by Stripe \u2022 Cancel anytime" })
|
|
3680
3720
|
] })
|
|
3681
3721
|
] });
|
|
3682
3722
|
}
|
|
3683
3723
|
|
|
3684
3724
|
// src/components/PaymentBottomSheet/DemoPaymentForm.tsx
|
|
3685
|
-
var
|
|
3686
|
-
var
|
|
3725
|
+
var React22 = __toESM(require("react"), 1);
|
|
3726
|
+
var import_jsx_runtime27 = require("react/jsx-runtime");
|
|
3687
3727
|
function DemoPaymentForm({
|
|
3688
3728
|
checkoutSession,
|
|
3689
3729
|
onSuccess,
|
|
3690
3730
|
isProcessing,
|
|
3691
3731
|
setIsProcessing
|
|
3692
3732
|
}) {
|
|
3693
|
-
const [cardNumber, setCardNumber] =
|
|
3694
|
-
const [expiry, setExpiry] =
|
|
3695
|
-
const [cvc, setCvc] =
|
|
3733
|
+
const [cardNumber, setCardNumber] = React22.useState("");
|
|
3734
|
+
const [expiry, setExpiry] = React22.useState("");
|
|
3735
|
+
const [cvc, setCvc] = React22.useState("");
|
|
3696
3736
|
const formatAmount = (cents, currency) => {
|
|
3697
3737
|
return new Intl.NumberFormat("en-US", {
|
|
3698
3738
|
style: "currency",
|
|
@@ -3719,9 +3759,9 @@ function DemoPaymentForm({
|
|
|
3719
3759
|
await new Promise((resolve) => setTimeout(resolve, 2e3));
|
|
3720
3760
|
onSuccess(`sub_demo_${Date.now()}`);
|
|
3721
3761
|
};
|
|
3722
|
-
return /* @__PURE__ */ (0,
|
|
3723
|
-
/* @__PURE__ */ (0,
|
|
3724
|
-
/* @__PURE__ */ (0,
|
|
3762
|
+
return /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("form", { onSubmit: handleSubmit, className: "space-y-6", children: [
|
|
3763
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "grid grid-cols-2 gap-3", children: [
|
|
3764
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(
|
|
3725
3765
|
Button,
|
|
3726
3766
|
{
|
|
3727
3767
|
type: "button",
|
|
@@ -3733,12 +3773,12 @@ function DemoPaymentForm({
|
|
|
3733
3773
|
setTimeout(() => onSuccess(`sub_demo_apple_${Date.now()}`), 2e3);
|
|
3734
3774
|
},
|
|
3735
3775
|
children: [
|
|
3736
|
-
/* @__PURE__ */ (0,
|
|
3776
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("svg", { viewBox: "0 0 24 24", className: "w-5 h-5 mr-2", fill: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("path", { d: "M17.05 20.28c-.98.95-2.05.8-3.08.35-1.09-.46-2.09-.48-3.24 0-1.44.62-2.2.44-3.06-.35C2.79 15.25 3.51 7.59 9.05 7.31c1.35.07 2.29.74 3.08.8 1.18-.24 2.31-.93 3.57-.84 1.51.12 2.65.72 3.4 1.8-3.12 1.87-2.38 5.98.48 7.13-.57 1.5-1.31 2.99-2.54 4.09l.01-.01zM12.03 7.25c-.15-2.23 1.66-4.07 3.74-4.25.29 2.58-2.34 4.5-3.74 4.25z" }) }),
|
|
3737
3777
|
"Apple Pay"
|
|
3738
3778
|
]
|
|
3739
3779
|
}
|
|
3740
3780
|
),
|
|
3741
|
-
/* @__PURE__ */ (0,
|
|
3781
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(
|
|
3742
3782
|
Button,
|
|
3743
3783
|
{
|
|
3744
3784
|
type: "button",
|
|
@@ -3750,25 +3790,25 @@ function DemoPaymentForm({
|
|
|
3750
3790
|
setTimeout(() => onSuccess(`sub_demo_google_${Date.now()}`), 2e3);
|
|
3751
3791
|
},
|
|
3752
3792
|
children: [
|
|
3753
|
-
/* @__PURE__ */ (0,
|
|
3754
|
-
/* @__PURE__ */ (0,
|
|
3755
|
-
/* @__PURE__ */ (0,
|
|
3756
|
-
/* @__PURE__ */ (0,
|
|
3757
|
-
/* @__PURE__ */ (0,
|
|
3793
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("svg", { viewBox: "0 0 24 24", className: "w-5 h-5 mr-2", children: [
|
|
3794
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("path", { fill: "#4285F4", d: "M22.56 12.25c0-.78-.07-1.53-.2-2.25H12v4.26h5.92c-.26 1.37-1.04 2.53-2.21 3.31v2.77h3.57c2.08-1.92 3.28-4.74 3.28-8.09z" }),
|
|
3795
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("path", { fill: "#34A853", d: "M12 23c2.97 0 5.46-.98 7.28-2.66l-3.57-2.77c-.98.66-2.23 1.06-3.71 1.06-2.86 0-5.29-1.93-6.16-4.53H2.18v2.84C3.99 20.53 7.7 23 12 23z" }),
|
|
3796
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("path", { fill: "#FBBC05", d: "M5.84 14.09c-.22-.66-.35-1.36-.35-2.09s.13-1.43.35-2.09V7.07H2.18C1.43 8.55 1 10.22 1 12s.43 3.45 1.18 4.93l2.85-2.22.81-.62z" }),
|
|
3797
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("path", { fill: "#EA4335", d: "M12 5.38c1.62 0 3.06.56 4.21 1.64l3.15-3.15C17.45 2.09 14.97 1 12 1 7.7 1 3.99 3.47 2.18 7.07l3.66 2.84c.87-2.6 3.3-4.53 6.16-4.53z" })
|
|
3758
3798
|
] }),
|
|
3759
3799
|
"Google Pay"
|
|
3760
3800
|
]
|
|
3761
3801
|
}
|
|
3762
3802
|
)
|
|
3763
3803
|
] }),
|
|
3764
|
-
/* @__PURE__ */ (0,
|
|
3765
|
-
/* @__PURE__ */ (0,
|
|
3766
|
-
/* @__PURE__ */ (0,
|
|
3804
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "relative", children: [
|
|
3805
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "absolute inset-0 flex items-center", children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "w-full border-t" }) }),
|
|
3806
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "relative flex justify-center text-xs uppercase", children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "bg-background px-2 text-muted-foreground", children: "or pay with card" }) })
|
|
3767
3807
|
] }),
|
|
3768
|
-
/* @__PURE__ */ (0,
|
|
3769
|
-
/* @__PURE__ */ (0,
|
|
3770
|
-
/* @__PURE__ */ (0,
|
|
3771
|
-
/* @__PURE__ */ (0,
|
|
3808
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "space-y-4", children: [
|
|
3809
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "space-y-2", children: [
|
|
3810
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(Label, { htmlFor: "card-number", children: "Card number" }),
|
|
3811
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
3772
3812
|
Input,
|
|
3773
3813
|
{
|
|
3774
3814
|
id: "card-number",
|
|
@@ -3780,10 +3820,10 @@ function DemoPaymentForm({
|
|
|
3780
3820
|
}
|
|
3781
3821
|
)
|
|
3782
3822
|
] }),
|
|
3783
|
-
/* @__PURE__ */ (0,
|
|
3784
|
-
/* @__PURE__ */ (0,
|
|
3785
|
-
/* @__PURE__ */ (0,
|
|
3786
|
-
/* @__PURE__ */ (0,
|
|
3823
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "grid grid-cols-2 gap-4", children: [
|
|
3824
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "space-y-2", children: [
|
|
3825
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(Label, { htmlFor: "expiry", children: "Expiry date" }),
|
|
3826
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
3787
3827
|
Input,
|
|
3788
3828
|
{
|
|
3789
3829
|
id: "expiry",
|
|
@@ -3795,9 +3835,9 @@ function DemoPaymentForm({
|
|
|
3795
3835
|
}
|
|
3796
3836
|
)
|
|
3797
3837
|
] }),
|
|
3798
|
-
/* @__PURE__ */ (0,
|
|
3799
|
-
/* @__PURE__ */ (0,
|
|
3800
|
-
/* @__PURE__ */ (0,
|
|
3838
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "space-y-2", children: [
|
|
3839
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(Label, { htmlFor: "cvc", children: "CVC" }),
|
|
3840
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
3801
3841
|
Input,
|
|
3802
3842
|
{
|
|
3803
3843
|
id: "cvc",
|
|
@@ -3811,15 +3851,15 @@ function DemoPaymentForm({
|
|
|
3811
3851
|
] })
|
|
3812
3852
|
] })
|
|
3813
3853
|
] }),
|
|
3814
|
-
/* @__PURE__ */ (0,
|
|
3854
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
3815
3855
|
Button,
|
|
3816
3856
|
{
|
|
3817
3857
|
type: "submit",
|
|
3818
3858
|
className: "w-full",
|
|
3819
3859
|
size: "lg",
|
|
3820
3860
|
disabled: isProcessing,
|
|
3821
|
-
children: isProcessing ? /* @__PURE__ */ (0,
|
|
3822
|
-
/* @__PURE__ */ (0,
|
|
3861
|
+
children: isProcessing ? /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("span", { className: "flex items-center gap-2", children: [
|
|
3862
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(
|
|
3823
3863
|
"svg",
|
|
3824
3864
|
{
|
|
3825
3865
|
className: "animate-spin h-4 w-4",
|
|
@@ -3827,7 +3867,7 @@ function DemoPaymentForm({
|
|
|
3827
3867
|
fill: "none",
|
|
3828
3868
|
viewBox: "0 0 24 24",
|
|
3829
3869
|
children: [
|
|
3830
|
-
/* @__PURE__ */ (0,
|
|
3870
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
3831
3871
|
"circle",
|
|
3832
3872
|
{
|
|
3833
3873
|
className: "opacity-25",
|
|
@@ -3838,7 +3878,7 @@ function DemoPaymentForm({
|
|
|
3838
3878
|
strokeWidth: "4"
|
|
3839
3879
|
}
|
|
3840
3880
|
),
|
|
3841
|
-
/* @__PURE__ */ (0,
|
|
3881
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
|
|
3842
3882
|
"path",
|
|
3843
3883
|
{
|
|
3844
3884
|
className: "opacity-75",
|
|
@@ -3853,8 +3893,8 @@ function DemoPaymentForm({
|
|
|
3853
3893
|
] }) : checkoutSession.proration ? `Upgrade Now - ${formattedAmount}` : `Subscribe - ${formattedAmount}`
|
|
3854
3894
|
}
|
|
3855
3895
|
),
|
|
3856
|
-
/* @__PURE__ */ (0,
|
|
3857
|
-
/* @__PURE__ */ (0,
|
|
3896
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: "flex items-center justify-center gap-2 text-xs text-muted-foreground", children: [
|
|
3897
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(
|
|
3858
3898
|
"svg",
|
|
3859
3899
|
{
|
|
3860
3900
|
xmlns: "http://www.w3.org/2000/svg",
|
|
@@ -3867,12 +3907,12 @@ function DemoPaymentForm({
|
|
|
3867
3907
|
strokeLinecap: "round",
|
|
3868
3908
|
strokeLinejoin: "round",
|
|
3869
3909
|
children: [
|
|
3870
|
-
/* @__PURE__ */ (0,
|
|
3871
|
-
/* @__PURE__ */ (0,
|
|
3910
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("rect", { width: "18", height: "11", x: "3", y: "11", rx: "2", ry: "2" }),
|
|
3911
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("path", { d: "M7 11V7a5 5 0 0 1 10 0v4" })
|
|
3872
3912
|
]
|
|
3873
3913
|
}
|
|
3874
3914
|
),
|
|
3875
|
-
/* @__PURE__ */ (0,
|
|
3915
|
+
/* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { children: "Secured by Stripe - Cancel anytime" })
|
|
3876
3916
|
] })
|
|
3877
3917
|
] });
|
|
3878
3918
|
}
|
|
@@ -3887,7 +3927,7 @@ function isValidClientSecret(secret) {
|
|
|
3887
3927
|
}
|
|
3888
3928
|
|
|
3889
3929
|
// src/components/PaymentBottomSheet/PaymentBottomSheet.tsx
|
|
3890
|
-
var
|
|
3930
|
+
var import_jsx_runtime28 = require("react/jsx-runtime");
|
|
3891
3931
|
function PaymentBottomSheet({
|
|
3892
3932
|
priceId,
|
|
3893
3933
|
isOpen,
|
|
@@ -3904,12 +3944,12 @@ function PaymentBottomSheet({
|
|
|
3904
3944
|
});
|
|
3905
3945
|
const { customerEmail, customerName } = useBillingOS();
|
|
3906
3946
|
const queryClient = (0, import_react_query9.useQueryClient)();
|
|
3907
|
-
const [stripePromise2, setStripePromise] =
|
|
3908
|
-
const [sheetState, setSheetState] =
|
|
3909
|
-
const [error, setError] =
|
|
3910
|
-
const [isProcessing, setIsProcessing] =
|
|
3911
|
-
const [isDemoMode, setIsDemoMode] =
|
|
3912
|
-
|
|
3947
|
+
const [stripePromise2, setStripePromise] = React23.useState(null);
|
|
3948
|
+
const [sheetState, setSheetState] = React23.useState("loading");
|
|
3949
|
+
const [error, setError] = React23.useState(null);
|
|
3950
|
+
const [isProcessing, setIsProcessing] = React23.useState(false);
|
|
3951
|
+
const [isDemoMode, setIsDemoMode] = React23.useState(false);
|
|
3952
|
+
React23.useEffect(() => {
|
|
3913
3953
|
console.log("[PaymentBottomSheet] State changed:", {
|
|
3914
3954
|
sheetState,
|
|
3915
3955
|
error,
|
|
@@ -3934,7 +3974,7 @@ function PaymentBottomSheet({
|
|
|
3934
3974
|
}
|
|
3935
3975
|
);
|
|
3936
3976
|
const checkoutSession = checkoutData;
|
|
3937
|
-
|
|
3977
|
+
React23.useEffect(() => {
|
|
3938
3978
|
console.log("[PaymentBottomSheet] Checkout session data:", {
|
|
3939
3979
|
hasCheckoutData: !!checkoutData,
|
|
3940
3980
|
checkoutSession,
|
|
@@ -3942,7 +3982,7 @@ function PaymentBottomSheet({
|
|
|
3942
3982
|
isOpen
|
|
3943
3983
|
});
|
|
3944
3984
|
}, [checkoutData, checkoutSession, checkoutError, isOpen]);
|
|
3945
|
-
|
|
3985
|
+
React23.useEffect(() => {
|
|
3946
3986
|
console.log("[PaymentBottomSheet] Stripe initialization effect triggered");
|
|
3947
3987
|
if (checkoutSession) {
|
|
3948
3988
|
const validKey = isValidStripeKey(BILLINGOS_STRIPE_PUBLISHABLE_KEY);
|
|
@@ -3968,13 +4008,13 @@ function PaymentBottomSheet({
|
|
|
3968
4008
|
setSheetState("ready");
|
|
3969
4009
|
}
|
|
3970
4010
|
}, [checkoutSession]);
|
|
3971
|
-
|
|
4011
|
+
React23.useEffect(() => {
|
|
3972
4012
|
if (checkoutError) {
|
|
3973
4013
|
setError(checkoutError.message || "Failed to create checkout session");
|
|
3974
4014
|
setSheetState("error");
|
|
3975
4015
|
}
|
|
3976
4016
|
}, [checkoutError]);
|
|
3977
|
-
|
|
4017
|
+
React23.useEffect(() => {
|
|
3978
4018
|
if (!isOpen) {
|
|
3979
4019
|
setSheetState("loading");
|
|
3980
4020
|
setError(null);
|
|
@@ -4036,29 +4076,29 @@ function PaymentBottomSheet({
|
|
|
4036
4076
|
}
|
|
4037
4077
|
};
|
|
4038
4078
|
console.log("[PaymentBottomSheet] Rendering drawer with isOpen:", isOpen, "sheetState:", sheetState);
|
|
4039
|
-
return /* @__PURE__ */ (0,
|
|
4079
|
+
return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4040
4080
|
ErrorBoundary,
|
|
4041
4081
|
{
|
|
4042
|
-
fallback: (error2, reset) => /* @__PURE__ */ (0,
|
|
4043
|
-
/* @__PURE__ */ (0,
|
|
4082
|
+
fallback: (error2, reset) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { style: { padding: "20px", maxWidth: "400px", margin: "0 auto" }, children: [
|
|
4083
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Alert, { variant: "destructive", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(AlertDescription, { children: [
|
|
4044
4084
|
"Failed to load payment form: ",
|
|
4045
4085
|
error2?.message || "Unknown error"
|
|
4046
4086
|
] }) }),
|
|
4047
|
-
/* @__PURE__ */ (0,
|
|
4048
|
-
/* @__PURE__ */ (0,
|
|
4049
|
-
/* @__PURE__ */ (0,
|
|
4087
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "mt-4 flex gap-2", children: [
|
|
4088
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Button, { variant: "outline", onClick: onClose, children: "Cancel" }),
|
|
4089
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Button, { onClick: reset, children: "Try Again" })
|
|
4050
4090
|
] })
|
|
4051
4091
|
] }),
|
|
4052
4092
|
onError: (error2, errorInfo) => {
|
|
4053
4093
|
console.error("[PaymentBottomSheet] Error caught by boundary:", error2);
|
|
4054
4094
|
console.error("[PaymentBottomSheet] Error info:", errorInfo);
|
|
4055
4095
|
},
|
|
4056
|
-
children: /* @__PURE__ */ (0,
|
|
4096
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Drawer, { open: isOpen, onOpenChange: (open) => {
|
|
4057
4097
|
console.log("[PaymentBottomSheet] Drawer.onOpenChange called with open:", open);
|
|
4058
4098
|
if (!open) {
|
|
4059
4099
|
handleClose();
|
|
4060
4100
|
}
|
|
4061
|
-
}, children: /* @__PURE__ */ (0,
|
|
4101
|
+
}, children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
|
|
4062
4102
|
DrawerContent,
|
|
4063
4103
|
{
|
|
4064
4104
|
preventClose: isProcessing,
|
|
@@ -4066,29 +4106,29 @@ function PaymentBottomSheet({
|
|
|
4066
4106
|
window.alert("Please wait while your payment is being processed.");
|
|
4067
4107
|
},
|
|
4068
4108
|
children: [
|
|
4069
|
-
/* @__PURE__ */ (0,
|
|
4070
|
-
/* @__PURE__ */ (0,
|
|
4071
|
-
sheetState !== "success" && checkoutSession && /* @__PURE__ */ (0,
|
|
4109
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(DrawerHeader, { className: "text-center sm:text-left", children: [
|
|
4110
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(DrawerTitle, { children: sheetState === "success" ? "Payment Successful!" : existingSubscriptionId ? "Complete Your Upgrade" : "Complete Payment" }),
|
|
4111
|
+
sheetState !== "success" && checkoutSession && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(DrawerDescription, { children: [
|
|
4072
4112
|
existingSubscriptionId ? "Upgrading to" : "Subscribing to",
|
|
4073
4113
|
":",
|
|
4074
4114
|
" ",
|
|
4075
|
-
/* @__PURE__ */ (0,
|
|
4115
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "font-medium", children: checkoutSession.product.name })
|
|
4076
4116
|
] })
|
|
4077
4117
|
] }),
|
|
4078
|
-
sheetState === "loading" && /* @__PURE__ */ (0,
|
|
4079
|
-
/* @__PURE__ */ (0,
|
|
4080
|
-
/* @__PURE__ */ (0,
|
|
4081
|
-
/* @__PURE__ */ (0,
|
|
4118
|
+
sheetState === "loading" && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "space-y-6 py-4", children: [
|
|
4119
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Skeleton, { className: "h-20 w-full" }),
|
|
4120
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Skeleton, { className: "h-40 w-full" }),
|
|
4121
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Skeleton, { className: "h-12 w-full" })
|
|
4082
4122
|
] }),
|
|
4083
|
-
sheetState === "error" && /* @__PURE__ */ (0,
|
|
4084
|
-
/* @__PURE__ */ (0,
|
|
4085
|
-
/* @__PURE__ */ (0,
|
|
4086
|
-
/* @__PURE__ */ (0,
|
|
4087
|
-
/* @__PURE__ */ (0,
|
|
4123
|
+
sheetState === "error" && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "space-y-4 py-4", children: [
|
|
4124
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Alert, { variant: "destructive", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(AlertDescription, { children: error || "Something went wrong. Please try again." }) }),
|
|
4125
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex gap-2", children: [
|
|
4126
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Button, { variant: "outline", onClick: onClose, className: "flex-1", children: "Cancel" }),
|
|
4127
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Button, { onClick: handleRetry, className: "flex-1", children: "Try Again" })
|
|
4088
4128
|
] })
|
|
4089
4129
|
] }),
|
|
4090
|
-
sheetState === "success" && checkoutSession && /* @__PURE__ */ (0,
|
|
4091
|
-
/* @__PURE__ */ (0,
|
|
4130
|
+
sheetState === "success" && checkoutSession && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex flex-col items-center justify-center py-8 space-y-4", children: [
|
|
4131
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "w-16 h-16 rounded-full bg-green-100 flex items-center justify-center", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4092
4132
|
"svg",
|
|
4093
4133
|
{
|
|
4094
4134
|
xmlns: "http://www.w3.org/2000/svg",
|
|
@@ -4101,20 +4141,20 @@ function PaymentBottomSheet({
|
|
|
4101
4141
|
strokeLinecap: "round",
|
|
4102
4142
|
strokeLinejoin: "round",
|
|
4103
4143
|
className: "text-green-600",
|
|
4104
|
-
children: /* @__PURE__ */ (0,
|
|
4144
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("polyline", { points: "20 6 9 17 4 12" })
|
|
4105
4145
|
}
|
|
4106
4146
|
) }),
|
|
4107
|
-
/* @__PURE__ */ (0,
|
|
4108
|
-
/* @__PURE__ */ (0,
|
|
4109
|
-
/* @__PURE__ */ (0,
|
|
4147
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "text-center", children: [
|
|
4148
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-lg font-semibold", children: "Payment Successful!" }),
|
|
4149
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("p", { className: "text-sm text-muted-foreground mt-1", children: [
|
|
4110
4150
|
"Your subscription to ",
|
|
4111
4151
|
checkoutSession.product.name,
|
|
4112
4152
|
" is now active."
|
|
4113
4153
|
] })
|
|
4114
4154
|
] })
|
|
4115
4155
|
] }),
|
|
4116
|
-
sheetState === "processing" && /* @__PURE__ */ (0,
|
|
4117
|
-
/* @__PURE__ */ (0,
|
|
4156
|
+
sheetState === "processing" && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex flex-col items-center justify-center py-8 space-y-4", children: [
|
|
4157
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "w-16 h-16 rounded-full bg-primary/10 flex items-center justify-center", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
|
|
4118
4158
|
"svg",
|
|
4119
4159
|
{
|
|
4120
4160
|
className: "animate-spin h-8 w-8 text-primary",
|
|
@@ -4122,7 +4162,7 @@ function PaymentBottomSheet({
|
|
|
4122
4162
|
fill: "none",
|
|
4123
4163
|
viewBox: "0 0 24 24",
|
|
4124
4164
|
children: [
|
|
4125
|
-
/* @__PURE__ */ (0,
|
|
4165
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4126
4166
|
"circle",
|
|
4127
4167
|
{
|
|
4128
4168
|
className: "opacity-25",
|
|
@@ -4133,7 +4173,7 @@ function PaymentBottomSheet({
|
|
|
4133
4173
|
strokeWidth: "4"
|
|
4134
4174
|
}
|
|
4135
4175
|
),
|
|
4136
|
-
/* @__PURE__ */ (0,
|
|
4176
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4137
4177
|
"path",
|
|
4138
4178
|
{
|
|
4139
4179
|
className: "opacity-75",
|
|
@@ -4144,34 +4184,34 @@ function PaymentBottomSheet({
|
|
|
4144
4184
|
]
|
|
4145
4185
|
}
|
|
4146
4186
|
) }),
|
|
4147
|
-
/* @__PURE__ */ (0,
|
|
4148
|
-
/* @__PURE__ */ (0,
|
|
4149
|
-
/* @__PURE__ */ (0,
|
|
4187
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "text-center", children: [
|
|
4188
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-lg font-semibold", children: "Processing Payment..." }),
|
|
4189
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-sm text-muted-foreground mt-1", children: "Please don't close this window." })
|
|
4150
4190
|
] })
|
|
4151
4191
|
] }),
|
|
4152
|
-
sheetState === "ready" && checkoutSession && /* @__PURE__ */ (0,
|
|
4153
|
-
isDemoMode && /* @__PURE__ */ (0,
|
|
4154
|
-
/* @__PURE__ */ (0,
|
|
4192
|
+
sheetState === "ready" && checkoutSession && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "space-y-6", children: [
|
|
4193
|
+
isDemoMode && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Alert, { children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(AlertDescription, { className: "text-sm", children: [
|
|
4194
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("strong", { children: "Demo Mode:" }),
|
|
4155
4195
|
" This is a preview with mock data. In production, a real Stripe payment form will appear here."
|
|
4156
4196
|
] }) }),
|
|
4157
|
-
/* @__PURE__ */ (0,
|
|
4158
|
-
/* @__PURE__ */ (0,
|
|
4159
|
-
/* @__PURE__ */ (0,
|
|
4160
|
-
/* @__PURE__ */ (0,
|
|
4161
|
-
/* @__PURE__ */ (0,
|
|
4197
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Card, { children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(CardContent, { className: "pt-4", children: [
|
|
4198
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex items-start justify-between", children: [
|
|
4199
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { children: [
|
|
4200
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("h3", { className: "font-semibold", children: checkoutSession.product.name }),
|
|
4201
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("p", { className: "text-2xl font-bold mt-1", children: [
|
|
4162
4202
|
formatAmount(checkoutSession.amount, checkoutSession.currency),
|
|
4163
|
-
/* @__PURE__ */ (0,
|
|
4203
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("span", { className: "text-sm font-normal text-muted-foreground", children: [
|
|
4164
4204
|
"/",
|
|
4165
4205
|
formatInterval2(checkoutSession.product.interval)
|
|
4166
4206
|
] })
|
|
4167
4207
|
] })
|
|
4168
4208
|
] }),
|
|
4169
|
-
/* @__PURE__ */ (0,
|
|
4209
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Badge, { variant: "secondary", children: existingSubscriptionId ? "Upgrade" : "New" })
|
|
4170
4210
|
] }),
|
|
4171
|
-
checkoutSession.product.features.length > 0 && /* @__PURE__ */ (0,
|
|
4172
|
-
/* @__PURE__ */ (0,
|
|
4173
|
-
/* @__PURE__ */ (0,
|
|
4174
|
-
/* @__PURE__ */ (0,
|
|
4211
|
+
checkoutSession.product.features.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "mt-4 space-y-2", children: [
|
|
4212
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-sm font-medium text-muted-foreground", children: "Features Included:" }),
|
|
4213
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("ul", { className: "space-y-1", children: checkoutSession.product.features.map((feature, index) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("li", { className: "flex items-center gap-2 text-sm", children: [
|
|
4214
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4175
4215
|
"svg",
|
|
4176
4216
|
{
|
|
4177
4217
|
xmlns: "http://www.w3.org/2000/svg",
|
|
@@ -4184,26 +4224,26 @@ function PaymentBottomSheet({
|
|
|
4184
4224
|
strokeLinecap: "round",
|
|
4185
4225
|
strokeLinejoin: "round",
|
|
4186
4226
|
className: "text-green-500",
|
|
4187
|
-
children: /* @__PURE__ */ (0,
|
|
4227
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("polyline", { points: "20 6 9 17 4 12" })
|
|
4188
4228
|
}
|
|
4189
4229
|
),
|
|
4190
4230
|
feature
|
|
4191
4231
|
] }, index)) })
|
|
4192
4232
|
] })
|
|
4193
4233
|
] }) }),
|
|
4194
|
-
checkoutSession.proration && /* @__PURE__ */ (0,
|
|
4195
|
-
/* @__PURE__ */ (0,
|
|
4196
|
-
/* @__PURE__ */ (0,
|
|
4197
|
-
/* @__PURE__ */ (0,
|
|
4198
|
-
/* @__PURE__ */ (0,
|
|
4199
|
-
/* @__PURE__ */ (0,
|
|
4234
|
+
checkoutSession.proration && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Card, { children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(CardContent, { className: "pt-4", children: [
|
|
4235
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("h4", { className: "font-medium mb-3", children: "Amount Due Today:" }),
|
|
4236
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "space-y-2 text-sm", children: [
|
|
4237
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex justify-between", children: [
|
|
4238
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: checkoutSession.product.name }),
|
|
4239
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: formatAmount(
|
|
4200
4240
|
checkoutSession.proration.charged,
|
|
4201
4241
|
checkoutSession.currency
|
|
4202
4242
|
) })
|
|
4203
4243
|
] }),
|
|
4204
|
-
/* @__PURE__ */ (0,
|
|
4205
|
-
/* @__PURE__ */ (0,
|
|
4206
|
-
/* @__PURE__ */ (0,
|
|
4244
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex justify-between text-green-600", children: [
|
|
4245
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: "Credit (unused time)" }),
|
|
4246
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("span", { children: [
|
|
4207
4247
|
"-",
|
|
4208
4248
|
formatAmount(
|
|
4209
4249
|
checkoutSession.proration.credited,
|
|
@@ -4211,17 +4251,17 @@ function PaymentBottomSheet({
|
|
|
4211
4251
|
)
|
|
4212
4252
|
] })
|
|
4213
4253
|
] }),
|
|
4214
|
-
/* @__PURE__ */ (0,
|
|
4215
|
-
/* @__PURE__ */ (0,
|
|
4216
|
-
/* @__PURE__ */ (0,
|
|
4217
|
-
/* @__PURE__ */ (0,
|
|
4254
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Separator, {}),
|
|
4255
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex justify-between font-semibold", children: [
|
|
4256
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: "Total Due Now" }),
|
|
4257
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: formatAmount(
|
|
4218
4258
|
checkoutSession.proration.total,
|
|
4219
4259
|
checkoutSession.currency
|
|
4220
4260
|
) })
|
|
4221
4261
|
] })
|
|
4222
4262
|
] }),
|
|
4223
|
-
/* @__PURE__ */ (0,
|
|
4224
|
-
/* @__PURE__ */ (0,
|
|
4263
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("p", { className: "text-xs text-muted-foreground mt-3 flex items-start gap-1", children: [
|
|
4264
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
|
|
4225
4265
|
"svg",
|
|
4226
4266
|
{
|
|
4227
4267
|
xmlns: "http://www.w3.org/2000/svg",
|
|
@@ -4235,21 +4275,21 @@ function PaymentBottomSheet({
|
|
|
4235
4275
|
strokeLinejoin: "round",
|
|
4236
4276
|
className: "mt-0.5 flex-shrink-0",
|
|
4237
4277
|
children: [
|
|
4238
|
-
/* @__PURE__ */ (0,
|
|
4239
|
-
/* @__PURE__ */ (0,
|
|
4240
|
-
/* @__PURE__ */ (0,
|
|
4278
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("circle", { cx: "12", cy: "12", r: "10" }),
|
|
4279
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("path", { d: "M12 16v-4" }),
|
|
4280
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("path", { d: "M12 8h.01" })
|
|
4241
4281
|
]
|
|
4242
4282
|
}
|
|
4243
4283
|
),
|
|
4244
4284
|
checkoutSession.proration.explanation
|
|
4245
4285
|
] })
|
|
4246
4286
|
] }) }),
|
|
4247
|
-
!checkoutSession.proration && /* @__PURE__ */ (0,
|
|
4248
|
-
/* @__PURE__ */ (0,
|
|
4249
|
-
/* @__PURE__ */ (0,
|
|
4287
|
+
!checkoutSession.proration && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Card, { children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(CardContent, { className: "pt-4", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex justify-between items-center", children: [
|
|
4288
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "font-medium", children: "Amount Due Today:" }),
|
|
4289
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "text-xl font-bold", children: formatAmount(checkoutSession.amount, checkoutSession.currency) })
|
|
4250
4290
|
] }) }) }),
|
|
4251
|
-
/* @__PURE__ */ (0,
|
|
4252
|
-
isDemoMode ? /* @__PURE__ */ (0,
|
|
4291
|
+
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Separator, {}),
|
|
4292
|
+
isDemoMode ? /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4253
4293
|
DemoPaymentForm,
|
|
4254
4294
|
{
|
|
4255
4295
|
checkoutSession,
|
|
@@ -4257,7 +4297,7 @@ function PaymentBottomSheet({
|
|
|
4257
4297
|
isProcessing,
|
|
4258
4298
|
setIsProcessing
|
|
4259
4299
|
}
|
|
4260
|
-
) : stripePromise2 ? /* @__PURE__ */ (0,
|
|
4300
|
+
) : stripePromise2 ? /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4261
4301
|
import_react_stripe_js2.Elements,
|
|
4262
4302
|
{
|
|
4263
4303
|
stripe: stripePromise2,
|
|
@@ -4265,7 +4305,7 @@ function PaymentBottomSheet({
|
|
|
4265
4305
|
clientSecret: checkoutSession.clientSecret,
|
|
4266
4306
|
appearance
|
|
4267
4307
|
},
|
|
4268
|
-
children: /* @__PURE__ */ (0,
|
|
4308
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4269
4309
|
PaymentForm,
|
|
4270
4310
|
{
|
|
4271
4311
|
checkoutSession,
|
|
@@ -4286,87 +4326,54 @@ function PaymentBottomSheet({
|
|
|
4286
4326
|
}
|
|
4287
4327
|
|
|
4288
4328
|
// src/components/PricingTable/PricingTable.tsx
|
|
4289
|
-
var
|
|
4329
|
+
var import_jsx_runtime29 = require("react/jsx-runtime");
|
|
4330
|
+
function getAllFeatures(products) {
|
|
4331
|
+
const seen = /* @__PURE__ */ new Map();
|
|
4332
|
+
products.forEach((product) => {
|
|
4333
|
+
product.features.forEach((f) => {
|
|
4334
|
+
if (!seen.has(f.name)) seen.set(f.name, { name: f.name, title: f.title, type: f.type });
|
|
4335
|
+
});
|
|
4336
|
+
});
|
|
4337
|
+
return Array.from(seen.values());
|
|
4338
|
+
}
|
|
4290
4339
|
function PricingTable({
|
|
4291
4340
|
planIds,
|
|
4292
4341
|
showIntervalToggle = true,
|
|
4293
4342
|
defaultInterval = "month",
|
|
4294
4343
|
onSelectPlan,
|
|
4295
4344
|
theme,
|
|
4296
|
-
title = "
|
|
4297
|
-
description,
|
|
4345
|
+
title = "Simple, transparent pricing",
|
|
4346
|
+
description = "Choose the perfect plan for your needs. No hidden fees, cancel anytime.",
|
|
4298
4347
|
useCheckoutModal = false,
|
|
4299
4348
|
onPlanChanged,
|
|
4300
|
-
customer: customerProp
|
|
4349
|
+
customer: customerProp,
|
|
4350
|
+
footerText = "All plans include SSL security and 99.9% uptime SLA",
|
|
4351
|
+
compact = false
|
|
4301
4352
|
}) {
|
|
4302
|
-
const [
|
|
4303
|
-
const [selectedPriceId, setSelectedPriceId] =
|
|
4304
|
-
const [isPaymentOpen, setIsPaymentOpen] =
|
|
4353
|
+
const [isYearly, setIsYearly] = React24.useState(defaultInterval === "year");
|
|
4354
|
+
const [selectedPriceId, setSelectedPriceId] = React24.useState(null);
|
|
4355
|
+
const [isPaymentOpen, setIsPaymentOpen] = React24.useState(false);
|
|
4356
|
+
const [showSuccessMessage, setShowSuccessMessage] = React24.useState(false);
|
|
4305
4357
|
const { customerEmail, customerName, debug } = useBillingOS();
|
|
4306
4358
|
const finalCustomerEmail = customerProp?.email || customerEmail;
|
|
4307
4359
|
const finalCustomerName = customerProp?.name || customerName;
|
|
4308
4360
|
const queryClient = (0, import_react_query10.useQueryClient)();
|
|
4309
|
-
const [showSuccessMessage, setShowSuccessMessage] = React25.useState(false);
|
|
4310
|
-
React25.useEffect(() => {
|
|
4311
|
-
if (debug) {
|
|
4312
|
-
console.log("[BillingOS] PricingTable customer data:", {
|
|
4313
|
-
fromProp: customerProp,
|
|
4314
|
-
fromContext: { customerEmail, customerName },
|
|
4315
|
-
final: { email: finalCustomerEmail, name: finalCustomerName }
|
|
4316
|
-
});
|
|
4317
|
-
}
|
|
4318
|
-
}, [debug, customerProp, customerEmail, customerName, finalCustomerEmail, finalCustomerName]);
|
|
4319
4361
|
const { data, isLoading, error, refetch } = useProducts2({ planIds });
|
|
4320
|
-
const
|
|
4321
|
-
const
|
|
4322
|
-
|
|
4323
|
-
|
|
4324
|
-
|
|
4325
|
-
|
|
4326
|
-
const featureMap = /* @__PURE__ */ new Map();
|
|
4327
|
-
products.forEach((product) => {
|
|
4328
|
-
product.features.forEach((feature) => {
|
|
4329
|
-
if (!featureMap.has(feature.id)) {
|
|
4330
|
-
featureMap.set(feature.id, {
|
|
4331
|
-
name: feature.title,
|
|
4332
|
-
values: Array(products.length).fill(null)
|
|
4333
|
-
});
|
|
4334
|
-
}
|
|
4335
|
-
});
|
|
4362
|
+
const currentSubscription = data?.currentSubscription ?? null;
|
|
4363
|
+
const products = React24.useMemo(() => {
|
|
4364
|
+
return [...data?.products ?? []].sort((a, b) => {
|
|
4365
|
+
const aAmt = a.prices.find((p) => p.interval === "month")?.amount ?? 0;
|
|
4366
|
+
const bAmt = b.prices.find((p) => p.interval === "month")?.amount ?? 0;
|
|
4367
|
+
return aAmt - bAmt;
|
|
4336
4368
|
});
|
|
4337
|
-
|
|
4338
|
-
|
|
4339
|
-
|
|
4340
|
-
|
|
4341
|
-
|
|
4342
|
-
|
|
4343
|
-
|
|
4344
|
-
|
|
4345
|
-
const limit = feature.properties?.limit;
|
|
4346
|
-
if (limit === -1) {
|
|
4347
|
-
featureRow.values[productIndex] = "Unlimited";
|
|
4348
|
-
} else if (typeof limit === "number") {
|
|
4349
|
-
featureRow.values[productIndex] = limit;
|
|
4350
|
-
} else {
|
|
4351
|
-
featureRow.values[productIndex] = true;
|
|
4352
|
-
}
|
|
4353
|
-
}
|
|
4354
|
-
}
|
|
4355
|
-
});
|
|
4356
|
-
});
|
|
4357
|
-
return featureRows.map(([, row]) => row);
|
|
4358
|
-
}, [products]);
|
|
4359
|
-
const formatPrice = (price) => {
|
|
4360
|
-
return new Intl.NumberFormat("en-US", {
|
|
4361
|
-
style: "currency",
|
|
4362
|
-
currency: price.currency.toUpperCase(),
|
|
4363
|
-
minimumFractionDigits: 0,
|
|
4364
|
-
maximumFractionDigits: 0
|
|
4365
|
-
}).format(price.amount / 100);
|
|
4366
|
-
};
|
|
4367
|
-
const getPriceForInterval = (product) => {
|
|
4368
|
-
return product.prices.find((p) => p.interval === selectedInterval) || product.prices[0] || null;
|
|
4369
|
-
};
|
|
4369
|
+
}, [data]);
|
|
4370
|
+
const allFeatures = React24.useMemo(() => getAllFeatures(products), [products]);
|
|
4371
|
+
const hasYearlyPricing = products.some((p) => p.prices.some((pr) => pr.interval === "year"));
|
|
4372
|
+
const selectedInterval = isYearly ? "year" : "month";
|
|
4373
|
+
const currentPlanAmount = React24.useMemo(() => {
|
|
4374
|
+
const currentProduct = products.find((p) => p.isCurrentPlan);
|
|
4375
|
+
return currentProduct?.prices.find((p) => p.interval === selectedInterval)?.amount ?? currentProduct?.prices[0]?.amount ?? 0;
|
|
4376
|
+
}, [products, selectedInterval]);
|
|
4370
4377
|
const handleSelectPlan = (priceId) => {
|
|
4371
4378
|
if (onSelectPlan) {
|
|
4372
4379
|
onSelectPlan(priceId);
|
|
@@ -4375,423 +4382,147 @@ function PricingTable({
|
|
|
4375
4382
|
setIsPaymentOpen(true);
|
|
4376
4383
|
}
|
|
4377
4384
|
};
|
|
4378
|
-
const handlePaymentSuccess =
|
|
4379
|
-
|
|
4380
|
-
|
|
4381
|
-
|
|
4382
|
-
|
|
4383
|
-
|
|
4384
|
-
|
|
4385
|
-
onPlanChanged(subscription);
|
|
4386
|
-
|
|
4387
|
-
|
|
4388
|
-
|
|
4389
|
-
|
|
4390
|
-
|
|
4391
|
-
|
|
4392
|
-
|
|
4393
|
-
|
|
4394
|
-
|
|
4395
|
-
|
|
4396
|
-
|
|
4397
|
-
|
|
4398
|
-
|
|
4399
|
-
|
|
4400
|
-
|
|
4401
|
-
|
|
4402
|
-
|
|
4403
|
-
|
|
4404
|
-
});
|
|
4405
|
-
}
|
|
4406
|
-
await refetch();
|
|
4407
|
-
}, [debug, queryClient, refetch, planIds, onPlanChanged]);
|
|
4385
|
+
const handlePaymentSuccess = React24.useCallback(
|
|
4386
|
+
async (subscription) => {
|
|
4387
|
+
if (debug) console.log("[BillingOS] Payment success:", subscription);
|
|
4388
|
+
setIsPaymentOpen(false);
|
|
4389
|
+
setSelectedPriceId(null);
|
|
4390
|
+
setShowSuccessMessage(true);
|
|
4391
|
+
setTimeout(() => setShowSuccessMessage(false), 5e3);
|
|
4392
|
+
if (onPlanChanged) onPlanChanged(subscription);
|
|
4393
|
+
await queryClient.invalidateQueries({ queryKey: ["products"], refetchType: "all" });
|
|
4394
|
+
if (subscription) {
|
|
4395
|
+
queryClient.setQueryData(["products", planIds], (oldData) => {
|
|
4396
|
+
if (!oldData) return oldData;
|
|
4397
|
+
return {
|
|
4398
|
+
...oldData,
|
|
4399
|
+
currentSubscription: subscription,
|
|
4400
|
+
products: oldData.products?.map((p) => ({
|
|
4401
|
+
...p,
|
|
4402
|
+
isCurrentPlan: p.prices?.some((pr) => pr.id === subscription.priceId) ?? false
|
|
4403
|
+
}))
|
|
4404
|
+
};
|
|
4405
|
+
});
|
|
4406
|
+
}
|
|
4407
|
+
await refetch();
|
|
4408
|
+
},
|
|
4409
|
+
[debug, queryClient, refetch, planIds, onPlanChanged]
|
|
4410
|
+
);
|
|
4408
4411
|
if (isLoading) {
|
|
4409
|
-
return /* @__PURE__ */ (0,
|
|
4410
|
-
|
|
4411
|
-
/* @__PURE__ */ (0,
|
|
4412
|
-
|
|
4412
|
+
return /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("section", { className: cn("py-20 px-4 sm:px-6 lg:px-8 bg-slate-50 min-h-screen", theme === "dark" && "dark"), children: /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "max-w-5xl mx-auto", children: [
|
|
4413
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "text-center mb-16", children: [
|
|
4414
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Skeleton, { className: "h-12 w-72 mx-auto mb-4" }),
|
|
4415
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Skeleton, { className: "h-5 w-96 mx-auto" })
|
|
4413
4416
|
] }),
|
|
4414
|
-
/* @__PURE__ */ (0,
|
|
4415
|
-
|
|
4417
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "grid grid-cols-1 md:grid-cols-2 gap-8 max-w-3xl mx-auto", children: [
|
|
4418
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Skeleton, { className: "h-[480px] rounded-2xl" }),
|
|
4419
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Skeleton, { className: "h-[480px] rounded-2xl" })
|
|
4420
|
+
] })
|
|
4421
|
+
] }) });
|
|
4416
4422
|
}
|
|
4417
4423
|
if (error) {
|
|
4418
|
-
return /* @__PURE__ */ (0,
|
|
4419
|
-
/* @__PURE__ */ (0,
|
|
4420
|
-
/* @__PURE__ */ (0,
|
|
4421
|
-
] });
|
|
4424
|
+
return /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("section", { className: cn("py-20 px-4", theme === "dark" && "dark"), children: /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "max-w-md mx-auto", children: [
|
|
4425
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Alert, { variant: "destructive", children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(AlertDescription, { children: error.message || "Failed to load pricing plans" }) }),
|
|
4426
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("div", { className: "mt-4 flex justify-center", children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Button, { onClick: () => refetch(), children: "Try Again" }) })
|
|
4427
|
+
] }) });
|
|
4422
4428
|
}
|
|
4423
4429
|
if (products.length === 0) {
|
|
4424
|
-
return /* @__PURE__ */ (0,
|
|
4430
|
+
return /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("section", { className: cn("py-20 px-4 text-center", theme === "dark" && "dark"), children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("p", { className: "text-muted-foreground", children: "No pricing plans available" }) });
|
|
4425
4431
|
}
|
|
4426
|
-
|
|
4427
|
-
|
|
4428
|
-
|
|
4429
|
-
|
|
4430
|
-
|
|
4431
|
-
|
|
4432
|
-
|
|
4433
|
-
|
|
4434
|
-
stroke: "currentColor",
|
|
4435
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4436
|
-
"path",
|
|
4437
|
-
{
|
|
4438
|
-
strokeLinecap: "round",
|
|
4439
|
-
strokeLinejoin: "round",
|
|
4440
|
-
strokeWidth: 2,
|
|
4441
|
-
d: "M5 13l4 4L19 7"
|
|
4442
|
-
}
|
|
4443
|
-
)
|
|
4444
|
-
}
|
|
4445
|
-
),
|
|
4446
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-green-800 dark:text-green-200 font-medium", children: "Payment successful! Your subscription has been updated." })
|
|
4447
|
-
] }) }),
|
|
4448
|
-
(title || description) && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "text-center mb-8", children: [
|
|
4449
|
-
title && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("h2", { className: "text-3xl font-bold tracking-tight text-foreground", children: title }),
|
|
4450
|
-
description && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-muted-foreground mt-2 max-w-2xl mx-auto", children: description }),
|
|
4451
|
-
useCheckoutModal && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "inline-flex items-center gap-2 mt-4 px-3 py-1 bg-gradient-to-r from-blue-100 to-purple-100 text-blue-800 rounded-full text-sm font-medium", children: [
|
|
4452
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("svg", { className: "w-4 h-4", fill: "currentColor", viewBox: "0 0 20 20", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("path", { fillRule: "evenodd", d: "M10 18a8 8 0 100-16 8 8 0 000 16zm3.707-9.293a1 1 0 00-1.414-1.414L9 10.586 7.707 9.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4z", clipRule: "evenodd" }) }),
|
|
4453
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: "Using Secure Iframe Checkout" })
|
|
4454
|
-
] })
|
|
4455
|
-
] }),
|
|
4456
|
-
showIntervalToggle && hasYearlyPricing && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "flex justify-center mb-8", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "inline-flex items-center rounded-lg bg-muted p-1", children: [
|
|
4457
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4458
|
-
"button",
|
|
4459
|
-
{
|
|
4460
|
-
onClick: () => setSelectedInterval("month"),
|
|
4461
|
-
className: cn(
|
|
4462
|
-
"px-4 py-2 rounded-md text-sm font-medium transition-colors",
|
|
4463
|
-
selectedInterval === "month" ? "bg-background text-foreground shadow-sm" : "text-muted-foreground hover:text-foreground"
|
|
4464
|
-
),
|
|
4465
|
-
children: "Monthly"
|
|
4432
|
+
const paymentComponent = !onSelectPlan && selectedPriceId ? /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(import_jsx_runtime29.Fragment, { children: useCheckoutModal ? /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
|
|
4433
|
+
CheckoutModal,
|
|
4434
|
+
{
|
|
4435
|
+
open: isPaymentOpen,
|
|
4436
|
+
onOpenChange: (open) => {
|
|
4437
|
+
if (!open) {
|
|
4438
|
+
setIsPaymentOpen(false);
|
|
4439
|
+
setSelectedPriceId(null);
|
|
4466
4440
|
}
|
|
4441
|
+
},
|
|
4442
|
+
priceId: selectedPriceId,
|
|
4443
|
+
customer: { email: finalCustomerEmail, name: finalCustomerName },
|
|
4444
|
+
onSuccess: handlePaymentSuccess,
|
|
4445
|
+
existingSubscriptionId: currentSubscription?.id,
|
|
4446
|
+
theme
|
|
4447
|
+
}
|
|
4448
|
+
) : /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
|
|
4449
|
+
PaymentBottomSheet,
|
|
4450
|
+
{
|
|
4451
|
+
priceId: selectedPriceId,
|
|
4452
|
+
isOpen: isPaymentOpen,
|
|
4453
|
+
onClose: () => {
|
|
4454
|
+
setIsPaymentOpen(false);
|
|
4455
|
+
setSelectedPriceId(null);
|
|
4456
|
+
},
|
|
4457
|
+
onSuccess: handlePaymentSuccess,
|
|
4458
|
+
existingSubscriptionId: currentSubscription?.id,
|
|
4459
|
+
theme
|
|
4460
|
+
}
|
|
4461
|
+
) }) : null;
|
|
4462
|
+
const cardsGrid = /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
|
|
4463
|
+
"div",
|
|
4464
|
+
{
|
|
4465
|
+
className: cn(
|
|
4466
|
+
"grid gap-8 items-start",
|
|
4467
|
+
products.length === 1 && "grid-cols-1 max-w-sm mx-auto",
|
|
4468
|
+
products.length === 2 && "grid-cols-1 md:grid-cols-2 max-w-3xl mx-auto",
|
|
4469
|
+
products.length >= 3 && "grid-cols-1 md:grid-cols-3"
|
|
4467
4470
|
),
|
|
4468
|
-
/* @__PURE__ */ (0,
|
|
4469
|
-
|
|
4471
|
+
children: products.map((product) => /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
|
|
4472
|
+
PricingCard,
|
|
4470
4473
|
{
|
|
4471
|
-
|
|
4472
|
-
|
|
4473
|
-
|
|
4474
|
-
|
|
4475
|
-
|
|
4476
|
-
|
|
4477
|
-
|
|
4478
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Badge, { variant: "secondary", className: "text-xs", children: "Save" })
|
|
4479
|
-
]
|
|
4480
|
-
}
|
|
4481
|
-
)
|
|
4482
|
-
] }) }),
|
|
4483
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "rounded-lg border bg-card overflow-hidden", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(Table, { children: [
|
|
4484
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(TableHeader, { children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(TableRow, { className: "hover:bg-transparent border-b", children: [
|
|
4485
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(TableHead, { className: "w-[200px]" }),
|
|
4486
|
-
products.map((product) => {
|
|
4487
|
-
const price = getPriceForInterval(product);
|
|
4488
|
-
const isHighlighted = product.highlighted;
|
|
4489
|
-
const isCurrentPlan = product.isCurrentPlan;
|
|
4490
|
-
return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4491
|
-
TableHead,
|
|
4492
|
-
{
|
|
4493
|
-
className: cn(
|
|
4494
|
-
"text-center relative",
|
|
4495
|
-
isHighlighted && "bg-foreground text-background"
|
|
4496
|
-
),
|
|
4497
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "py-8", children: [
|
|
4498
|
-
(isHighlighted || isCurrentPlan) && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex justify-center gap-2 mb-3", children: [
|
|
4499
|
-
isCurrentPlan && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Badge, { className: "bg-primary text-primary-foreground text-xs", children: "Current Plan" }),
|
|
4500
|
-
isHighlighted && !isCurrentPlan && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4501
|
-
Badge,
|
|
4502
|
-
{
|
|
4503
|
-
variant: "secondary",
|
|
4504
|
-
className: cn(
|
|
4505
|
-
"text-xs",
|
|
4506
|
-
isHighlighted && "bg-background text-foreground"
|
|
4507
|
-
),
|
|
4508
|
-
children: "Popular"
|
|
4509
|
-
}
|
|
4510
|
-
)
|
|
4511
|
-
] }),
|
|
4512
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: cn(
|
|
4513
|
-
"font-bold text-xl mb-3",
|
|
4514
|
-
isHighlighted ? "text-background" : "text-foreground"
|
|
4515
|
-
), children: product.name }),
|
|
4516
|
-
price && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(import_jsx_runtime28.Fragment, { children: [
|
|
4517
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: cn(
|
|
4518
|
-
"text-5xl font-bold mb-2",
|
|
4519
|
-
isHighlighted ? "text-background" : "text-foreground"
|
|
4520
|
-
), children: formatPrice(price) }),
|
|
4521
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: cn(
|
|
4522
|
-
"text-sm mt-1",
|
|
4523
|
-
isHighlighted ? "text-background/70" : "text-muted-foreground"
|
|
4524
|
-
), children: [
|
|
4525
|
-
"Per ",
|
|
4526
|
-
selectedInterval === "year" ? "year" : "month"
|
|
4527
|
-
] })
|
|
4528
|
-
] })
|
|
4529
|
-
] })
|
|
4530
|
-
},
|
|
4531
|
-
product.id
|
|
4532
|
-
);
|
|
4533
|
-
})
|
|
4534
|
-
] }) }),
|
|
4535
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(TableBody, { children: [
|
|
4536
|
-
getAllFeatures.map((featureRow, index) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(TableRow, { children: [
|
|
4537
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(TableCell, { className: "font-medium text-foreground py-4", children: featureRow.name }),
|
|
4538
|
-
featureRow.values.map((value, productIndex) => {
|
|
4539
|
-
const isHighlighted = products[productIndex]?.highlighted;
|
|
4540
|
-
return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4541
|
-
TableCell,
|
|
4542
|
-
{
|
|
4543
|
-
className: cn(
|
|
4544
|
-
"text-center py-4",
|
|
4545
|
-
isHighlighted && "bg-foreground/5"
|
|
4546
|
-
),
|
|
4547
|
-
children: value === null || value === false ? /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "text-muted-foreground", children: "-" }) : value === true ? /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
|
|
4548
|
-
"svg",
|
|
4549
|
-
{
|
|
4550
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
4551
|
-
width: "20",
|
|
4552
|
-
height: "20",
|
|
4553
|
-
viewBox: "0 0 24 24",
|
|
4554
|
-
fill: "none",
|
|
4555
|
-
stroke: "currentColor",
|
|
4556
|
-
strokeWidth: "2",
|
|
4557
|
-
strokeLinecap: "round",
|
|
4558
|
-
strokeLinejoin: "round",
|
|
4559
|
-
className: "inline-block text-foreground",
|
|
4560
|
-
children: [
|
|
4561
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("circle", { cx: "12", cy: "12", r: "10" }),
|
|
4562
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)("polyline", { points: "9 12 11 14 15 10" })
|
|
4563
|
-
]
|
|
4564
|
-
}
|
|
4565
|
-
) : /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "text-foreground font-medium", children: value })
|
|
4566
|
-
},
|
|
4567
|
-
productIndex
|
|
4568
|
-
);
|
|
4569
|
-
})
|
|
4570
|
-
] }, index)),
|
|
4571
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(TableRow, { className: "hover:bg-transparent border-t", children: [
|
|
4572
|
-
/* @__PURE__ */ (0, import_jsx_runtime28.jsx)(TableCell, { className: "font-medium text-foreground py-6", children: "Server speed" }),
|
|
4573
|
-
products.map((product) => {
|
|
4574
|
-
const price = getPriceForInterval(product);
|
|
4575
|
-
const isHighlighted = product.highlighted;
|
|
4576
|
-
const isCurrentPlan = product.isCurrentPlan;
|
|
4577
|
-
const hasSubscription = currentSubscription !== null;
|
|
4578
|
-
let buttonText = "Get Started";
|
|
4579
|
-
if (isCurrentPlan) {
|
|
4580
|
-
buttonText = "Current Plan";
|
|
4581
|
-
} else if (hasSubscription && price && currentSubscription) {
|
|
4582
|
-
const currentPrice = products.find((p) => p.isCurrentPlan);
|
|
4583
|
-
const currentPriceAmount = currentPrice ? getPriceForInterval(currentPrice)?.amount || 0 : 0;
|
|
4584
|
-
if (price.amount > currentPriceAmount) {
|
|
4585
|
-
buttonText = "Upgrade";
|
|
4586
|
-
} else if (price.amount < currentPriceAmount) {
|
|
4587
|
-
buttonText = "Downgrade";
|
|
4588
|
-
} else {
|
|
4589
|
-
buttonText = "Switch Plan";
|
|
4590
|
-
}
|
|
4591
|
-
}
|
|
4592
|
-
return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4593
|
-
TableCell,
|
|
4594
|
-
{
|
|
4595
|
-
className: cn(
|
|
4596
|
-
"text-center py-6",
|
|
4597
|
-
isHighlighted && "bg-foreground/5"
|
|
4598
|
-
),
|
|
4599
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4600
|
-
Button,
|
|
4601
|
-
{
|
|
4602
|
-
onClick: () => price && handleSelectPlan(price.id),
|
|
4603
|
-
disabled: isCurrentPlan || !price,
|
|
4604
|
-
variant: isHighlighted && !isCurrentPlan ? "default" : "outline",
|
|
4605
|
-
className: cn(
|
|
4606
|
-
"w-full max-w-[200px]",
|
|
4607
|
-
isHighlighted && !isCurrentPlan && "bg-foreground text-background hover:bg-foreground/90"
|
|
4608
|
-
),
|
|
4609
|
-
children: buttonText
|
|
4610
|
-
}
|
|
4611
|
-
)
|
|
4612
|
-
},
|
|
4613
|
-
product.id
|
|
4614
|
-
);
|
|
4615
|
-
})
|
|
4616
|
-
] })
|
|
4617
|
-
] })
|
|
4618
|
-
] }) }),
|
|
4619
|
-
!onSelectPlan && selectedPriceId && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_jsx_runtime28.Fragment, { children: useCheckoutModal ? /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4620
|
-
CheckoutModal,
|
|
4621
|
-
{
|
|
4622
|
-
open: isPaymentOpen,
|
|
4623
|
-
onOpenChange: (open) => {
|
|
4624
|
-
if (!open) {
|
|
4625
|
-
setIsPaymentOpen(false);
|
|
4626
|
-
setSelectedPriceId(null);
|
|
4627
|
-
}
|
|
4628
|
-
},
|
|
4629
|
-
priceId: selectedPriceId,
|
|
4630
|
-
customer: {
|
|
4631
|
-
email: finalCustomerEmail,
|
|
4632
|
-
name: finalCustomerName
|
|
4633
|
-
},
|
|
4634
|
-
onSuccess: (subscription) => {
|
|
4635
|
-
handlePaymentSuccess(subscription);
|
|
4636
|
-
},
|
|
4637
|
-
existingSubscriptionId: currentSubscription?.id,
|
|
4638
|
-
theme
|
|
4639
|
-
}
|
|
4640
|
-
) : /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
|
|
4641
|
-
PaymentBottomSheet,
|
|
4642
|
-
{
|
|
4643
|
-
priceId: selectedPriceId,
|
|
4644
|
-
isOpen: isPaymentOpen,
|
|
4645
|
-
onClose: () => {
|
|
4646
|
-
setIsPaymentOpen(false);
|
|
4647
|
-
setSelectedPriceId(null);
|
|
4474
|
+
product,
|
|
4475
|
+
allFeatures,
|
|
4476
|
+
isYearly,
|
|
4477
|
+
currentSubscription,
|
|
4478
|
+
currentPlanAmount,
|
|
4479
|
+
onSelectPlan: handleSelectPlan,
|
|
4480
|
+
theme
|
|
4648
4481
|
},
|
|
4649
|
-
|
|
4650
|
-
|
|
4651
|
-
theme
|
|
4652
|
-
}
|
|
4653
|
-
) })
|
|
4654
|
-
] });
|
|
4655
|
-
}
|
|
4656
|
-
|
|
4657
|
-
// src/components/PricingTable/PricingCard.tsx
|
|
4658
|
-
var import_jsx_runtime29 = require("react/jsx-runtime");
|
|
4659
|
-
function PricingCard({
|
|
4660
|
-
product,
|
|
4661
|
-
selectedInterval,
|
|
4662
|
-
currentSubscription,
|
|
4663
|
-
onSelectPlan
|
|
4664
|
-
}) {
|
|
4665
|
-
const selectedPrice = product.prices.find(
|
|
4666
|
-
(p) => p.interval === selectedInterval
|
|
4667
|
-
) || product.prices[0];
|
|
4668
|
-
const isCurrentPlan = product.isCurrentPlan;
|
|
4669
|
-
const getButtonState = () => {
|
|
4670
|
-
if (!currentSubscription) return "buy";
|
|
4671
|
-
if (isCurrentPlan) return "current";
|
|
4672
|
-
if (currentSubscription.productId === product.id) return "current";
|
|
4673
|
-
return "upgrade";
|
|
4674
|
-
};
|
|
4675
|
-
const buttonState = getButtonState();
|
|
4676
|
-
const formatPrice = (price) => {
|
|
4677
|
-
return new Intl.NumberFormat("en-US", {
|
|
4678
|
-
style: "currency",
|
|
4679
|
-
currency: price.currency.toUpperCase(),
|
|
4680
|
-
minimumFractionDigits: 0,
|
|
4681
|
-
maximumFractionDigits: 0
|
|
4682
|
-
}).format(price.amount / 100);
|
|
4683
|
-
};
|
|
4684
|
-
const calculateYearlySavings = () => {
|
|
4685
|
-
const monthlyPrice = product.prices.find((p) => p.interval === "month");
|
|
4686
|
-
const yearlyPrice = product.prices.find((p) => p.interval === "year");
|
|
4687
|
-
if (!monthlyPrice || !yearlyPrice) return null;
|
|
4688
|
-
const monthlyTotal = monthlyPrice.amount * 12;
|
|
4689
|
-
const yearlyCost = yearlyPrice.amount;
|
|
4690
|
-
const savings = (monthlyTotal - yearlyCost) / monthlyTotal * 100;
|
|
4691
|
-
return Math.round(savings);
|
|
4692
|
-
};
|
|
4693
|
-
const yearlySavings = selectedInterval === "year" ? calculateYearlySavings() : null;
|
|
4694
|
-
const formatFeature = (feature) => {
|
|
4695
|
-
if (feature.properties?.limit === -1) {
|
|
4696
|
-
return `Unlimited ${feature.properties?.unit || feature.title.toLowerCase()}`;
|
|
4697
|
-
}
|
|
4698
|
-
return feature.title;
|
|
4699
|
-
};
|
|
4700
|
-
const handleClick = () => {
|
|
4701
|
-
if (buttonState !== "current" && selectedPrice) {
|
|
4702
|
-
onSelectPlan(selectedPrice.id);
|
|
4482
|
+
product.id
|
|
4483
|
+
))
|
|
4703
4484
|
}
|
|
4704
|
-
|
|
4485
|
+
);
|
|
4486
|
+
if (compact) {
|
|
4487
|
+
return /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: cn(theme === "dark" && "dark"), children: [
|
|
4488
|
+
cardsGrid,
|
|
4489
|
+
paymentComponent
|
|
4490
|
+
] });
|
|
4491
|
+
}
|
|
4705
4492
|
return /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)(
|
|
4706
|
-
|
|
4493
|
+
"section",
|
|
4707
4494
|
{
|
|
4708
4495
|
className: cn(
|
|
4709
|
-
"
|
|
4710
|
-
|
|
4711
|
-
product.highlighted && !isCurrentPlan && "border-primary/50",
|
|
4712
|
-
"hover:shadow-lg"
|
|
4496
|
+
"py-20 px-4 sm:px-6 lg:px-8 bg-slate-50 min-h-screen",
|
|
4497
|
+
theme === "dark" && "dark"
|
|
4713
4498
|
),
|
|
4714
4499
|
children: [
|
|
4715
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "
|
|
4716
|
-
|
|
4717
|
-
|
|
4718
|
-
|
|
4719
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)(CardHeader, { className: "text-center pb-2 pt-8", children: [
|
|
4720
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(CardTitle, { className: "text-2xl font-bold", children: product.name }),
|
|
4721
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(CardDescription, { className: "text-sm mt-1", children: product.description })
|
|
4722
|
-
] }),
|
|
4723
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)(CardContent, { className: "flex-1 pt-4", children: [
|
|
4724
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "text-center mb-6", children: [
|
|
4725
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "flex items-baseline justify-center gap-1", children: [
|
|
4726
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: "text-4xl font-bold tracking-tight", children: selectedPrice ? formatPrice(selectedPrice) : "N/A" }),
|
|
4727
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("span", { className: "text-muted-foreground text-sm", children: [
|
|
4728
|
-
"/",
|
|
4729
|
-
selectedInterval === "year" ? "year" : "mo"
|
|
4730
|
-
] })
|
|
4731
|
-
] }),
|
|
4732
|
-
yearlySavings && yearlySavings > 0 && /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)(Badge, { variant: "secondary", className: "mt-2 bg-green-100 text-green-700 dark:bg-green-900 dark:text-green-300", children: [
|
|
4733
|
-
"Save ",
|
|
4734
|
-
yearlySavings,
|
|
4735
|
-
"%"
|
|
4736
|
-
] }),
|
|
4737
|
-
product.trialDays > 0 && buttonState === "buy" && /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("p", { className: "text-sm text-muted-foreground mt-2", children: [
|
|
4738
|
-
product.trialDays,
|
|
4739
|
-
"-day free trial"
|
|
4740
|
-
] })
|
|
4500
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "max-w-5xl mx-auto", children: [
|
|
4501
|
+
showSuccessMessage && /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "mb-8 p-4 bg-green-50 border border-green-200 rounded-xl flex items-center gap-3", children: [
|
|
4502
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("svg", { className: "w-5 h-5 text-green-600 flex-shrink-0", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 13l4 4L19 7" }) }),
|
|
4503
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("p", { className: "text-green-800 font-medium text-sm", children: "Payment successful! Your subscription has been updated." })
|
|
4741
4504
|
] }),
|
|
4742
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.
|
|
4505
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "text-center mb-16", children: [
|
|
4506
|
+
title && /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("h1", { className: "text-4xl md:text-5xl font-bold text-slate-900 tracking-tight mb-4", children: title }),
|
|
4507
|
+
description && /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("p", { className: "text-lg text-slate-500 max-w-2xl mx-auto", children: description })
|
|
4508
|
+
] }),
|
|
4509
|
+
showIntervalToggle && hasYearlyPricing && /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "flex items-center justify-center gap-4 mb-16", children: [
|
|
4510
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: cn("text-sm font-medium transition-colors", !isYearly ? "text-slate-900" : "text-slate-400"), children: "Monthly" }),
|
|
4743
4511
|
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
|
|
4744
|
-
|
|
4512
|
+
Switch,
|
|
4745
4513
|
{
|
|
4746
|
-
|
|
4747
|
-
|
|
4748
|
-
|
|
4749
|
-
viewBox: "0 0 24 24",
|
|
4750
|
-
fill: "none",
|
|
4751
|
-
stroke: "currentColor",
|
|
4752
|
-
strokeWidth: "2",
|
|
4753
|
-
strokeLinecap: "round",
|
|
4754
|
-
strokeLinejoin: "round",
|
|
4755
|
-
className: "text-green-500 flex-shrink-0 mt-0.5",
|
|
4756
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("polyline", { points: "20 6 9 17 4 12" })
|
|
4514
|
+
checked: isYearly,
|
|
4515
|
+
onCheckedChange: setIsYearly,
|
|
4516
|
+
"aria-label": "Billing frequency"
|
|
4757
4517
|
}
|
|
4758
4518
|
),
|
|
4759
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: "text-sm",
|
|
4760
|
-
|
|
4519
|
+
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: cn("text-sm font-medium transition-colors", isYearly ? "text-slate-900" : "text-slate-400"), children: "Yearly" }),
|
|
4520
|
+
isYearly && /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Badge, { className: "bg-emerald-100 text-emerald-700 border-0 ml-2", children: "Save up to 40%" })
|
|
4521
|
+
] }),
|
|
4522
|
+
cardsGrid,
|
|
4523
|
+
footerText && /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("div", { className: "text-center mt-16", children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("p", { className: "text-sm text-slate-400", children: footerText }) })
|
|
4761
4524
|
] }),
|
|
4762
|
-
|
|
4763
|
-
Button,
|
|
4764
|
-
{
|
|
4765
|
-
className: "w-full",
|
|
4766
|
-
size: "lg",
|
|
4767
|
-
variant: buttonState === "current" ? "outline" : "default",
|
|
4768
|
-
disabled: buttonState === "current",
|
|
4769
|
-
onClick: handleClick,
|
|
4770
|
-
children: [
|
|
4771
|
-
buttonState === "current" && /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("span", { className: "flex items-center gap-2", children: [
|
|
4772
|
-
/* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
|
|
4773
|
-
"svg",
|
|
4774
|
-
{
|
|
4775
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
4776
|
-
width: "16",
|
|
4777
|
-
height: "16",
|
|
4778
|
-
viewBox: "0 0 24 24",
|
|
4779
|
-
fill: "none",
|
|
4780
|
-
stroke: "currentColor",
|
|
4781
|
-
strokeWidth: "2",
|
|
4782
|
-
strokeLinecap: "round",
|
|
4783
|
-
strokeLinejoin: "round",
|
|
4784
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("polyline", { points: "20 6 9 17 4 12" })
|
|
4785
|
-
}
|
|
4786
|
-
),
|
|
4787
|
-
"Current Plan"
|
|
4788
|
-
] }),
|
|
4789
|
-
buttonState === "buy" && (product.trialDays > 0 ? "Start Free Trial" : "Get Started"),
|
|
4790
|
-
buttonState === "upgrade" && "Upgrade",
|
|
4791
|
-
buttonState === "downgrade" && "Downgrade"
|
|
4792
|
-
]
|
|
4793
|
-
}
|
|
4794
|
-
) })
|
|
4525
|
+
paymentComponent
|
|
4795
4526
|
]
|
|
4796
4527
|
}
|
|
4797
4528
|
);
|
|
@@ -6105,7 +5836,7 @@ function SettingsTab({
|
|
|
6105
5836
|
}
|
|
6106
5837
|
|
|
6107
5838
|
// src/components/CustomerPortal/modals/ChangePlanModal.tsx
|
|
6108
|
-
var
|
|
5839
|
+
var React25 = __toESM(require("react"), 1);
|
|
6109
5840
|
|
|
6110
5841
|
// src/components/CustomerPortal/components/ProrationPreview.tsx
|
|
6111
5842
|
var import_jsx_runtime40 = require("react/jsx-runtime");
|
|
@@ -6242,9 +5973,9 @@ function ChangePlanModal({
|
|
|
6242
5973
|
subscriptionId,
|
|
6243
5974
|
onSuccess
|
|
6244
5975
|
}) {
|
|
6245
|
-
const [selectedPlan, setSelectedPlan] =
|
|
6246
|
-
const [preview, setPreview] =
|
|
6247
|
-
const [showConfirmation, setShowConfirmation] =
|
|
5976
|
+
const [selectedPlan, setSelectedPlan] = React25.useState(null);
|
|
5977
|
+
const [preview, setPreview] = React25.useState(null);
|
|
5978
|
+
const [showConfirmation, setShowConfirmation] = React25.useState(false);
|
|
6248
5979
|
const { data: availablePlans, isLoading: isLoadingPlans, error: plansError } = useAvailablePlans(
|
|
6249
5980
|
subscriptionId,
|
|
6250
5981
|
{ enabled: open }
|
|
@@ -6256,7 +5987,7 @@ function ChangePlanModal({
|
|
|
6256
5987
|
onOpenChange(false);
|
|
6257
5988
|
}
|
|
6258
5989
|
});
|
|
6259
|
-
|
|
5990
|
+
React25.useEffect(() => {
|
|
6260
5991
|
if (!open) {
|
|
6261
5992
|
setSelectedPlan(null);
|
|
6262
5993
|
setPreview(null);
|
|
@@ -6392,7 +6123,7 @@ function ChangePlanModal({
|
|
|
6392
6123
|
}
|
|
6393
6124
|
|
|
6394
6125
|
// src/components/CustomerPortal/modals/CancelSubscriptionModal.tsx
|
|
6395
|
-
var
|
|
6126
|
+
var React26 = __toESM(require("react"), 1);
|
|
6396
6127
|
var import_jsx_runtime42 = require("react/jsx-runtime");
|
|
6397
6128
|
var CANCELLATION_REASONS = [
|
|
6398
6129
|
{ value: "too_expensive", label: "Too expensive" },
|
|
@@ -6408,10 +6139,10 @@ function CancelSubscriptionModal({
|
|
|
6408
6139
|
onConfirm,
|
|
6409
6140
|
isCanceling
|
|
6410
6141
|
}) {
|
|
6411
|
-
const [selectedReasons, setSelectedReasons] =
|
|
6412
|
-
const [feedback, setFeedback] =
|
|
6413
|
-
const [cancelTiming, setCancelTiming] =
|
|
6414
|
-
|
|
6142
|
+
const [selectedReasons, setSelectedReasons] = React26.useState([]);
|
|
6143
|
+
const [feedback, setFeedback] = React26.useState("");
|
|
6144
|
+
const [cancelTiming, setCancelTiming] = React26.useState("period_end");
|
|
6145
|
+
React26.useEffect(() => {
|
|
6415
6146
|
if (open) {
|
|
6416
6147
|
setSelectedReasons([]);
|
|
6417
6148
|
setFeedback("");
|
|
@@ -6531,7 +6262,7 @@ function CancelSubscriptionModal({
|
|
|
6531
6262
|
}
|
|
6532
6263
|
|
|
6533
6264
|
// src/components/CustomerPortal/modals/AddPaymentMethodModal.tsx
|
|
6534
|
-
var
|
|
6265
|
+
var React27 = __toESM(require("react"), 1);
|
|
6535
6266
|
var import_react_stripe_js3 = require("@stripe/react-stripe-js");
|
|
6536
6267
|
var import_stripe_js2 = require("@stripe/stripe-js");
|
|
6537
6268
|
var import_jsx_runtime43 = require("react/jsx-runtime");
|
|
@@ -6552,9 +6283,9 @@ var cardElementOptions = {
|
|
|
6552
6283
|
function PaymentForm2({ clientSecret, onSuccess, onCancel }) {
|
|
6553
6284
|
const stripe = (0, import_react_stripe_js3.useStripe)();
|
|
6554
6285
|
const elements = (0, import_react_stripe_js3.useElements)();
|
|
6555
|
-
const [isSubmitting, setIsSubmitting] =
|
|
6556
|
-
const [error, setError] =
|
|
6557
|
-
const [setAsDefault, setSetAsDefault] =
|
|
6286
|
+
const [isSubmitting, setIsSubmitting] = React27.useState(false);
|
|
6287
|
+
const [error, setError] = React27.useState(null);
|
|
6288
|
+
const [setAsDefault, setSetAsDefault] = React27.useState(true);
|
|
6558
6289
|
const handleSubmit = async (e) => {
|
|
6559
6290
|
e.preventDefault();
|
|
6560
6291
|
if (!stripe || !elements) {
|
|
@@ -6707,7 +6438,7 @@ function AddPaymentMethodModal({
|
|
|
6707
6438
|
}
|
|
6708
6439
|
|
|
6709
6440
|
// src/components/UpgradeNudge/UpgradeNudge.tsx
|
|
6710
|
-
var
|
|
6441
|
+
var React28 = __toESM(require("react"), 1);
|
|
6711
6442
|
|
|
6712
6443
|
// src/components/UpgradeNudge/BannerNudge.tsx
|
|
6713
6444
|
var import_jsx_runtime44 = require("react/jsx-runtime");
|
|
@@ -6915,7 +6646,7 @@ function ModalNudge({
|
|
|
6915
6646
|
onDismiss
|
|
6916
6647
|
}) {
|
|
6917
6648
|
const isUrgent = trigger.actual && trigger.actual >= 100;
|
|
6918
|
-
const
|
|
6649
|
+
const formatPrice2 = (amount, currency) => {
|
|
6919
6650
|
return new Intl.NumberFormat("en-US", {
|
|
6920
6651
|
style: "currency",
|
|
6921
6652
|
currency: currency.toUpperCase(),
|
|
@@ -6979,7 +6710,7 @@ function ModalNudge({
|
|
|
6979
6710
|
/* @__PURE__ */ (0, import_jsx_runtime46.jsxs)("div", { children: [
|
|
6980
6711
|
/* @__PURE__ */ (0, import_jsx_runtime46.jsx)("h3", { className: "font-semibold text-lg", children: trigger.suggestedPlan.name }),
|
|
6981
6712
|
/* @__PURE__ */ (0, import_jsx_runtime46.jsxs)("div", { className: "flex items-baseline gap-1 mt-1", children: [
|
|
6982
|
-
/* @__PURE__ */ (0, import_jsx_runtime46.jsx)("span", { className: "text-2xl font-bold", children:
|
|
6713
|
+
/* @__PURE__ */ (0, import_jsx_runtime46.jsx)("span", { className: "text-2xl font-bold", children: formatPrice2(
|
|
6983
6714
|
trigger.suggestedPlan.price.amount,
|
|
6984
6715
|
trigger.suggestedPlan.price.currency
|
|
6985
6716
|
) }),
|
|
@@ -7032,7 +6763,7 @@ function ModalNudge({
|
|
|
7032
6763
|
children: [
|
|
7033
6764
|
trigger.message.cta,
|
|
7034
6765
|
" - ",
|
|
7035
|
-
|
|
6766
|
+
formatPrice2(
|
|
7036
6767
|
trigger.suggestedPlan.price.amount,
|
|
7037
6768
|
trigger.suggestedPlan.price.currency
|
|
7038
6769
|
),
|
|
@@ -7062,11 +6793,11 @@ function UpgradeNudge({
|
|
|
7062
6793
|
onDismiss,
|
|
7063
6794
|
theme
|
|
7064
6795
|
}) {
|
|
7065
|
-
const [isVisible, setIsVisible] =
|
|
7066
|
-
|
|
6796
|
+
const [isVisible, setIsVisible] = React28.useState(true);
|
|
6797
|
+
React28.useEffect(() => {
|
|
7067
6798
|
setIsVisible(true);
|
|
7068
6799
|
}, [trigger, style]);
|
|
7069
|
-
|
|
6800
|
+
React28.useEffect(() => {
|
|
7070
6801
|
if (autoDismiss > 0 && isVisible) {
|
|
7071
6802
|
const timer = setTimeout(() => {
|
|
7072
6803
|
handleDismiss();
|
|
@@ -7074,7 +6805,7 @@ function UpgradeNudge({
|
|
|
7074
6805
|
return () => clearTimeout(timer);
|
|
7075
6806
|
}
|
|
7076
6807
|
}, [autoDismiss, isVisible]);
|
|
7077
|
-
|
|
6808
|
+
React28.useEffect(() => {
|
|
7078
6809
|
const handleKeyDown = (e) => {
|
|
7079
6810
|
if (e.key === "Escape" && isVisible) {
|
|
7080
6811
|
handleDismiss();
|
|
@@ -7654,6 +7385,7 @@ if (typeof window !== "undefined") {
|
|
|
7654
7385
|
SheetTrigger,
|
|
7655
7386
|
Skeleton,
|
|
7656
7387
|
SubscriptionTab,
|
|
7388
|
+
Switch,
|
|
7657
7389
|
Tabs,
|
|
7658
7390
|
TabsContent,
|
|
7659
7391
|
TabsList,
|