onstage 1.0.0

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.js ADDED
@@ -0,0 +1,568 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ // If the importer is in node compatibility mode or this is not an ESM
22
+ // file that has been converted to a CommonJS file using a Babel-
23
+ // compatible transform (i.e. "__esModule" has not been set), then set
24
+ // "default" to the CommonJS "module.exports" for node compatibility.
25
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
+ mod
27
+ ));
28
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
+
30
+ // src/index.ts
31
+ var index_exports = {};
32
+ __export(index_exports, {
33
+ OnboardingModal: () => OnboardingModal,
34
+ OnboardingProvider: () => OnboardingProvider,
35
+ useOnboarding: () => useOnboarding
36
+ });
37
+ module.exports = __toCommonJS(index_exports);
38
+
39
+ // src/context/OnboardingContext.tsx
40
+ var import_react = require("react");
41
+ var import_jsx_runtime = require("react/jsx-runtime");
42
+ var OnboardingContext = (0, import_react.createContext)(
43
+ void 0
44
+ );
45
+ function OnboardingProvider({
46
+ children,
47
+ steps,
48
+ defaultOpen = false,
49
+ onFinish,
50
+ onSkip
51
+ }) {
52
+ const [isOpen, setIsOpen] = (0, import_react.useState)(defaultOpen);
53
+ const [currentStepIndex, setCurrentStepIndex] = (0, import_react.useState)(0);
54
+ const nextStep = (0, import_react.useCallback)(() => {
55
+ if (currentStepIndex < steps.length - 1) {
56
+ setCurrentStepIndex((prev) => prev + 1);
57
+ }
58
+ }, [currentStepIndex, steps.length]);
59
+ const prevStep = (0, import_react.useCallback)(() => {
60
+ if (currentStepIndex > 0) {
61
+ setCurrentStepIndex((prev) => prev - 1);
62
+ }
63
+ }, [currentStepIndex]);
64
+ const finishOnboarding = (0, import_react.useCallback)(() => {
65
+ setIsOpen(false);
66
+ onFinish?.();
67
+ }, [onFinish]);
68
+ const skipOnboarding = (0, import_react.useCallback)(() => {
69
+ setIsOpen(false);
70
+ onSkip?.();
71
+ }, [onSkip]);
72
+ const resetOnboarding = (0, import_react.useCallback)(() => {
73
+ setCurrentStepIndex(0);
74
+ setIsOpen(true);
75
+ }, []);
76
+ const value = (0, import_react.useMemo)(
77
+ () => ({
78
+ isOpen,
79
+ currentStepIndex,
80
+ steps,
81
+ nextStep,
82
+ prevStep,
83
+ skipOnboarding,
84
+ finishOnboarding,
85
+ resetOnboarding,
86
+ setIsOpen
87
+ }),
88
+ [
89
+ isOpen,
90
+ currentStepIndex,
91
+ steps,
92
+ nextStep,
93
+ prevStep,
94
+ skipOnboarding,
95
+ finishOnboarding,
96
+ resetOnboarding,
97
+ setIsOpen
98
+ ]
99
+ );
100
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(OnboardingContext.Provider, { value, children });
101
+ }
102
+ function useOnboarding() {
103
+ const context = (0, import_react.useContext)(OnboardingContext);
104
+ if (!context) {
105
+ throw new Error("useOnboarding must be used within an OnboardingProvider");
106
+ }
107
+ return context;
108
+ }
109
+
110
+ // src/components/OnboardingModal.tsx
111
+ var import_react2 = require("react");
112
+
113
+ // src/components/ui/dialog.tsx
114
+ var React = __toESM(require("react"));
115
+ var DialogPrimitive = __toESM(require("@radix-ui/react-dialog"));
116
+
117
+ // src/lib/utils.ts
118
+ var import_clsx = require("clsx");
119
+ var import_tailwind_merge = require("tailwind-merge");
120
+ function cn(...inputs) {
121
+ return (0, import_tailwind_merge.twMerge)((0, import_clsx.clsx)(inputs));
122
+ }
123
+
124
+ // src/components/ui/dialog.tsx
125
+ var import_jsx_runtime2 = require("react/jsx-runtime");
126
+ var Dialog = DialogPrimitive.Root;
127
+ var DialogPortal = DialogPrimitive.Portal;
128
+ var DialogOverlay = React.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
129
+ DialogPrimitive.Overlay,
130
+ {
131
+ ref,
132
+ className: cn(
133
+ "fixed inset-0 z-50 bg-black/80 data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0",
134
+ className
135
+ ),
136
+ ...props
137
+ }
138
+ ));
139
+ DialogOverlay.displayName = DialogPrimitive.Overlay.displayName;
140
+ var DialogContent = React.forwardRef(({ className, children, overlayClassName, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime2.jsxs)(DialogPortal, { children: [
141
+ /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(DialogOverlay, { className: overlayClassName }),
142
+ /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
143
+ DialogPrimitive.Content,
144
+ {
145
+ ref,
146
+ className: cn(
147
+ "fixed left-[50%] top-[50%] z-50 grid w-full max-w-lg max-h-[90vh] translate-x-[-50%] translate-y-[-50%] gap-4 border bg-background p-6 shadow-lg duration-200 overflow-y-auto data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[state=closed]:slide-out-to-left-1/2 data-[state=closed]:slide-out-to-top-[48%] data-[state=open]:slide-in-from-left-1/2 data-[state=open]:slide-in-from-top-[48%] sm:rounded-lg",
148
+ className
149
+ ),
150
+ ...props,
151
+ children
152
+ }
153
+ )
154
+ ] }));
155
+ DialogContent.displayName = DialogPrimitive.Content.displayName;
156
+ var DialogHeader = ({
157
+ className,
158
+ ...props
159
+ }) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
160
+ "div",
161
+ {
162
+ className: cn(
163
+ "flex flex-col space-y-1.5 text-center sm:text-left",
164
+ className
165
+ ),
166
+ ...props
167
+ }
168
+ );
169
+ DialogHeader.displayName = "DialogHeader";
170
+ var DialogFooter = ({
171
+ className,
172
+ ...props
173
+ }) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
174
+ "div",
175
+ {
176
+ className: cn(
177
+ "flex flex-col-reverse sm:flex-row sm:justify-end sm:space-x-2",
178
+ className
179
+ ),
180
+ ...props
181
+ }
182
+ );
183
+ DialogFooter.displayName = "DialogFooter";
184
+ var DialogTitle = React.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
185
+ DialogPrimitive.Title,
186
+ {
187
+ ref,
188
+ className: cn(
189
+ "text-lg font-semibold leading-none tracking-tight",
190
+ className
191
+ ),
192
+ ...props
193
+ }
194
+ ));
195
+ DialogTitle.displayName = DialogPrimitive.Title.displayName;
196
+ var DialogDescription = React.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(
197
+ DialogPrimitive.Description,
198
+ {
199
+ ref,
200
+ className: cn("text-sm text-muted-foreground", className),
201
+ ...props
202
+ }
203
+ ));
204
+ DialogDescription.displayName = DialogPrimitive.Description.displayName;
205
+
206
+ // src/components/ui/button.tsx
207
+ var React2 = __toESM(require("react"));
208
+ var import_react_slot = require("@radix-ui/react-slot");
209
+ var import_class_variance_authority = require("class-variance-authority");
210
+ var import_jsx_runtime3 = require("react/jsx-runtime");
211
+ var buttonVariants = (0, import_class_variance_authority.cva)(
212
+ "inline-flex items-center justify-center gap-2 whitespace-nowrap rounded-lg text-sm font-medium transition-all duration-200 focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg]:size-4 [&_svg]:shrink-0",
213
+ {
214
+ variants: {
215
+ variant: {
216
+ default: "bg-primary text-primary-foreground hover:bg-primary/90",
217
+ destructive: "bg-destructive text-destructive-foreground hover:bg-destructive/90",
218
+ outline: "border border-border bg-background hover:bg-accent hover:text-accent-foreground",
219
+ secondary: "bg-secondary text-secondary-foreground hover:bg-secondary/80",
220
+ ghost: "hover:bg-accent hover:text-accent-foreground",
221
+ link: "text-primary underline-offset-4 hover:underline"
222
+ },
223
+ size: {
224
+ default: "h-9 px-4 py-2",
225
+ sm: "h-8 rounded-md px-3 text-xs",
226
+ lg: "h-10 rounded-md px-6",
227
+ icon: "h-9 w-9"
228
+ }
229
+ },
230
+ defaultVariants: {
231
+ variant: "default",
232
+ size: "default"
233
+ }
234
+ }
235
+ );
236
+ var Button = React2.forwardRef(
237
+ ({ className, variant, size, asChild = false, ...props }, ref) => {
238
+ const Comp = asChild ? import_react_slot.Slot : "button";
239
+ return /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
240
+ Comp,
241
+ {
242
+ className: cn(buttonVariants({ variant, size, className })),
243
+ ref,
244
+ ...props
245
+ }
246
+ );
247
+ }
248
+ );
249
+ Button.displayName = "Button";
250
+
251
+ // src/components/OnboardingModal.tsx
252
+ var import_jsx_runtime4 = require("react/jsx-runtime");
253
+ var THEMES = {
254
+ light: {
255
+ mode: "light",
256
+ gradient: "animated"
257
+ },
258
+ dark: {
259
+ mode: "dark",
260
+ gradient: "animated"
261
+ },
262
+ minimal: {
263
+ mode: "light",
264
+ gradient: "none",
265
+ className: "border-2 border-black shadow-none rounded-none sm:rounded-none",
266
+ style: {
267
+ "--radius": "0px",
268
+ "--primary": "0 0% 0%",
269
+ "--primary-foreground": "0 0% 100%"
270
+ },
271
+ classNames: {
272
+ nextButton: "rounded-none border-2 border-black hover:bg-black hover:text-white transition-none",
273
+ prevButton: "rounded-none border-2 border-black hover:bg-black hover:text-white transition-none",
274
+ skipButton: "hover:bg-transparent underline decoration-black underline-offset-4",
275
+ stepIndicators: "rounded-none",
276
+ imageContainer: "border-b-2 border-black",
277
+ content: "rounded-none"
278
+ }
279
+ },
280
+ glass: {
281
+ mode: "dark",
282
+ gradient: "animated",
283
+ className: "bg-black/40 backdrop-blur-xl border-white/10 shadow-2xl",
284
+ style: {
285
+ "--primary": "0 0% 100%",
286
+ "--primary-foreground": "0 0% 0%",
287
+ "--muted-foreground": "0 0% 80%"
288
+ },
289
+ classNames: {
290
+ overlay: "bg-black/60 backdrop-blur-sm",
291
+ nextButton: "bg-white/90 text-black hover:bg-white",
292
+ prevButton: "border-white/20 hover:bg-white/10 text-white",
293
+ skipButton: "text-white/60 hover:text-white",
294
+ title: "text-white drop-shadow-md",
295
+ description: "text-white/90 drop-shadow-sm"
296
+ }
297
+ },
298
+ midnight: {
299
+ mode: "dark",
300
+ gradient: "animated",
301
+ style: {
302
+ "--background": "222 47% 11%",
303
+ "--foreground": "210 40% 98%",
304
+ "--primary": "263 70% 50%",
305
+ "--primary-foreground": "210 40% 98%"
306
+ },
307
+ className: "border-indigo-500/30"
308
+ },
309
+ ocean: {
310
+ mode: "light",
311
+ gradient: "animated",
312
+ style: {
313
+ "--primary": "199 89% 48%",
314
+ "--primary-foreground": "0 0% 100%"
315
+ },
316
+ className: "border-cyan-200"
317
+ },
318
+ sunset: {
319
+ mode: "light",
320
+ gradient: "animated",
321
+ style: {
322
+ "--primary": "24 90% 60%",
323
+ "--primary-foreground": "0 0% 100%"
324
+ },
325
+ className: "border-orange-200"
326
+ }
327
+ };
328
+ function OnboardingModal({
329
+ theme = "light",
330
+ gradient,
331
+ backdrop = "default",
332
+ customGradientClass,
333
+ style,
334
+ className,
335
+ allowClickOutside = true,
336
+ classNames = {},
337
+ styles = {}
338
+ }) {
339
+ const {
340
+ isOpen,
341
+ currentStepIndex,
342
+ steps,
343
+ nextStep,
344
+ prevStep,
345
+ skipOnboarding,
346
+ finishOnboarding,
347
+ setIsOpen
348
+ } = useOnboarding();
349
+ if (!steps || steps.length === 0) return null;
350
+ const currentStep = steps[currentStepIndex] || steps[0];
351
+ const isLastStep = currentStepIndex === steps.length - 1;
352
+ const isFirstStep = currentStepIndex === 0;
353
+ const activeTheme = THEMES[theme] || THEMES.light;
354
+ const finalGradient = gradient || activeTheme.gradient;
355
+ const isDarkMode = activeTheme.mode === "dark";
356
+ const mergedRootStyle = { ...activeTheme.style, ...style };
357
+ let backdropClass = "";
358
+ if (backdrop === "blur") backdropClass = "backdrop-blur-md bg-black/10";
359
+ else if (backdrop === "transparent") backdropClass = "bg-transparent";
360
+ const mergedClassNames = (0, import_react2.useMemo)(() => {
361
+ const themeClasses = activeTheme.classNames || {};
362
+ return {
363
+ overlay: cn(
364
+ // If backdrop prop is set to anything other than default, we override theme overlay
365
+ backdrop !== "default" ? backdropClass : themeClasses.overlay,
366
+ classNames.overlay
367
+ ),
368
+ content: cn(themeClasses.content, classNames.content),
369
+ imageContainer: cn(themeClasses.imageContainer, classNames.imageContainer),
370
+ image: cn(themeClasses.image, classNames.image),
371
+ header: cn(themeClasses.header, classNames.header),
372
+ title: cn(themeClasses.title, classNames.title),
373
+ description: cn(themeClasses.description, classNames.description),
374
+ footer: cn(themeClasses.footer, classNames.footer),
375
+ stepIndicators: cn(themeClasses.stepIndicators, classNames.stepIndicators),
376
+ nextButton: cn(themeClasses.nextButton, classNames.nextButton),
377
+ prevButton: cn(themeClasses.prevButton, classNames.prevButton),
378
+ skipButton: cn(themeClasses.skipButton, classNames.skipButton),
379
+ finishButton: cn(themeClasses.finishButton, classNames.finishButton)
380
+ };
381
+ }, [activeTheme, classNames, backdrop, backdropClass]);
382
+ if (!isOpen) return null;
383
+ const showGradient = finalGradient !== "none";
384
+ const defaultGradientClass = finalGradient === "animated" ? "bg-gradient-to-br from-primary/30 via-background to-primary/30 animate-gradient-flow" : "bg-gradient-to-br from-primary/20 to-background";
385
+ const finalGradientClass = customGradientClass || defaultGradientClass;
386
+ return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
387
+ Dialog,
388
+ {
389
+ open: isOpen,
390
+ onOpenChange: (open) => {
391
+ if (!open) {
392
+ if (allowClickOutside) {
393
+ skipOnboarding();
394
+ } else {
395
+ setIsOpen(true);
396
+ }
397
+ }
398
+ },
399
+ children: /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)(
400
+ DialogContent,
401
+ {
402
+ overlayClassName: mergedClassNames.overlay,
403
+ style: { ...mergedRootStyle, ...styles.content },
404
+ className: cn(
405
+ isDarkMode && "dark",
406
+ "max-w-[95vw] sm:max-w-[1000px] p-0 overflow-hidden gap-0 z-[50001] rounded-xl sm:rounded-lg",
407
+ "bg-background text-foreground",
408
+ activeTheme.className,
409
+ className,
410
+ mergedClassNames.content
411
+ ),
412
+ onPointerDownOutside: (e) => {
413
+ if (!allowClickOutside) e.preventDefault();
414
+ },
415
+ onEscapeKeyDown: (e) => {
416
+ if (!allowClickOutside) e.preventDefault();
417
+ },
418
+ children: [
419
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)(
420
+ "div",
421
+ {
422
+ className: cn(
423
+ "w-full relative flex items-center justify-center overflow-hidden bg-background transition-all duration-300",
424
+ "aspect-[4/5] sm:aspect-[4/3] lg:aspect-[16/9]",
425
+ mergedClassNames.imageContainer
426
+ ),
427
+ style: styles.imageContainer,
428
+ children: [
429
+ showGradient && /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: cn("absolute inset-0 z-0", finalGradientClass) }),
430
+ showGradient && finalGradient === "animated" && /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "absolute inset-0 z-0 bg-[radial-gradient(circle_at_50%_50%,rgba(var(--primary),0.15),transparent_50%)] animate-pulse" }),
431
+ typeof currentStep.image === "string" ? /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
432
+ "img",
433
+ {
434
+ src: currentStep.image,
435
+ alt: currentStep.title,
436
+ className: cn("object-contain w-full h-full relative z-10 drop-shadow-2xl", mergedClassNames.image),
437
+ style: styles.image,
438
+ onError: (e) => {
439
+ e.currentTarget.style.display = "none";
440
+ }
441
+ }
442
+ ) : /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)("picture", { className: cn("w-full h-full relative z-10 flex items-center justify-center", mergedClassNames.image), style: styles.image, children: [
443
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("source", { media: "(min-width: 1024px)", srcSet: currentStep.image.desktop }),
444
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("source", { media: "(min-width: 640px)", srcSet: currentStep.image.tablet || currentStep.image.desktop }),
445
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
446
+ "img",
447
+ {
448
+ src: currentStep.image.mobile,
449
+ alt: currentStep.title,
450
+ className: "object-contain w-full h-full drop-shadow-2xl",
451
+ onError: (e) => {
452
+ e.currentTarget.style.display = "none";
453
+ }
454
+ }
455
+ )
456
+ ] })
457
+ ]
458
+ }
459
+ ),
460
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)("div", { className: cn("p-5 sm:p-8", isDarkMode && "dark text-foreground"), children: [
461
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { className: "min-h-[100px] sm:min-h-[140px] flex flex-col justify-center", children: /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)(DialogHeader, { className: cn("mb-0", mergedClassNames.header), style: styles.header, children: [
462
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
463
+ DialogTitle,
464
+ {
465
+ className: cn("text-2xl sm:text-3xl text-center mb-3 sm:mb-4", mergedClassNames.title),
466
+ style: styles.title,
467
+ children: currentStep.title
468
+ }
469
+ ),
470
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
471
+ DialogDescription,
472
+ {
473
+ className: cn("text-center text-base sm:text-lg max-w-[95%] sm:max-w-[80%] mx-auto", mergedClassNames.description),
474
+ style: styles.description,
475
+ children: currentStep.description.split("**").map((part, index) => index % 2 === 1 ? /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("span", { className: "text-primary font-bold", children: part }, index) : /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("span", { children: part }, index))
476
+ }
477
+ )
478
+ ] }) }),
479
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)(
480
+ DialogFooter,
481
+ {
482
+ className: cn("relative flex flex-col gap-4 sm:block mt-4 sm:mt-6", mergedClassNames.footer),
483
+ style: styles.footer,
484
+ children: [
485
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
486
+ "div",
487
+ {
488
+ className: cn("w-full flex justify-center sm:absolute sm:left-1/2 sm:top-1/2 sm:-translate-x-1/2 sm:-translate-y-1/2 sm:w-auto", mergedClassNames.stepIndicators),
489
+ style: styles.stepIndicators,
490
+ children: steps.map((_, index) => /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
491
+ "div",
492
+ {
493
+ className: cn(
494
+ "h-2 w-2 sm:h-2.5 sm:w-2.5 rounded-full transition-colors duration-300 mx-1",
495
+ index === currentStepIndex ? "bg-primary" : "bg-muted-foreground/30"
496
+ )
497
+ },
498
+ index
499
+ ))
500
+ }
501
+ ),
502
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)("div", { className: "flex w-full justify-between items-center relative z-10 box-border", children: [
503
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
504
+ Button,
505
+ {
506
+ variant: "ghost",
507
+ size: "lg",
508
+ onClick: skipOnboarding,
509
+ className: cn("text-muted-foreground hover:text-foreground text-sm sm:text-base px-2 sm:px-4", mergedClassNames.skipButton),
510
+ style: styles.skipButton,
511
+ children: "Skip"
512
+ }
513
+ ),
514
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsxs)("div", { className: "flex gap-2", children: [
515
+ /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
516
+ Button,
517
+ {
518
+ variant: "outline",
519
+ size: "lg",
520
+ onClick: prevStep,
521
+ disabled: isFirstStep,
522
+ className: cn(
523
+ isFirstStep && "invisible",
524
+ "text-sm sm:text-base px-3 sm:px-6",
525
+ mergedClassNames.prevButton
526
+ ),
527
+ style: styles.prevButton,
528
+ children: "Back"
529
+ }
530
+ ),
531
+ isLastStep ? /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
532
+ Button,
533
+ {
534
+ onClick: finishOnboarding,
535
+ size: "lg",
536
+ className: cn("bg-primary text-primary-foreground hover:bg-primary/90 text-sm sm:text-base px-4 sm:px-8", mergedClassNames.finishButton),
537
+ style: styles.finishButton,
538
+ children: "Get Started"
539
+ }
540
+ ) : /* @__PURE__ */ (0, import_jsx_runtime4.jsx)(
541
+ Button,
542
+ {
543
+ onClick: nextStep,
544
+ size: "lg",
545
+ className: cn("text-sm sm:text-base px-4 sm:px-8", mergedClassNames.nextButton),
546
+ style: styles.nextButton,
547
+ children: "Next"
548
+ }
549
+ )
550
+ ] })
551
+ ] })
552
+ ]
553
+ }
554
+ )
555
+ ] })
556
+ ]
557
+ }
558
+ )
559
+ }
560
+ );
561
+ }
562
+ // Annotate the CommonJS export names for ESM import in node:
563
+ 0 && (module.exports = {
564
+ OnboardingModal,
565
+ OnboardingProvider,
566
+ useOnboarding
567
+ });
568
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/index.ts","../src/context/OnboardingContext.tsx","../src/components/OnboardingModal.tsx","../src/components/ui/dialog.tsx","../src/lib/utils.ts","../src/components/ui/button.tsx"],"sourcesContent":["export * from \"./context/OnboardingContext\";\nexport * from \"./components/OnboardingModal\";\n// Explicitly export the props interface for documentation/usage\nexport type { OnboardingModalProps } from \"./components/OnboardingModal\";","import {\n createContext,\n useContext,\n useState,\n useMemo,\n useCallback,\n type ReactNode,\n} from \"react\";\n\nexport interface OnboardingStep {\n title: string;\n description: string;\n image: string | { mobile: string; tablet?: string; desktop: string };\n}\n\ninterface OnboardingContextValue {\n isOpen: boolean;\n currentStepIndex: number;\n steps: OnboardingStep[];\n nextStep: () => void;\n prevStep: () => void;\n skipOnboarding: () => void;\n finishOnboarding: () => void;\n resetOnboarding: () => void;\n setIsOpen: (isOpen: boolean) => void;\n}\n\nconst OnboardingContext = createContext<OnboardingContextValue | undefined>(\n undefined\n);\n\ninterface OnboardingProviderProps {\n children: ReactNode;\n steps: OnboardingStep[];\n defaultOpen?: boolean;\n onFinish?: () => void;\n onSkip?: () => void;\n}\n\nexport function OnboardingProvider({\n children,\n steps,\n defaultOpen = false,\n onFinish,\n onSkip,\n}: OnboardingProviderProps) {\n const [isOpen, setIsOpen] = useState(defaultOpen);\n const [currentStepIndex, setCurrentStepIndex] = useState(0);\n\n const nextStep = useCallback(() => {\n if (currentStepIndex < steps.length - 1) {\n setCurrentStepIndex((prev) => prev + 1);\n }\n }, [currentStepIndex, steps.length]);\n\n const prevStep = useCallback(() => {\n if (currentStepIndex > 0) {\n setCurrentStepIndex((prev) => prev - 1);\n }\n }, [currentStepIndex]);\n\n const finishOnboarding = useCallback(() => {\n setIsOpen(false);\n onFinish?.();\n }, [onFinish]);\n\n const skipOnboarding = useCallback(() => {\n setIsOpen(false);\n onSkip?.();\n }, [onSkip]);\n\n const resetOnboarding = useCallback(() => {\n setCurrentStepIndex(0);\n setIsOpen(true);\n }, []);\n\n const value = useMemo(\n () => ({\n isOpen,\n currentStepIndex,\n steps,\n nextStep,\n prevStep,\n skipOnboarding,\n finishOnboarding,\n resetOnboarding,\n setIsOpen,\n }),\n [\n isOpen,\n currentStepIndex,\n steps,\n nextStep,\n prevStep,\n skipOnboarding,\n finishOnboarding,\n resetOnboarding,\n setIsOpen,\n ]\n );\n\n return (\n <OnboardingContext.Provider value={value}>\n {children}\n </OnboardingContext.Provider>\n );\n}\n\nexport function useOnboarding() {\n const context = useContext(OnboardingContext);\n if (!context) {\n throw new Error(\"useOnboarding must be used within an OnboardingProvider\");\n }\n return context;\n}","import { CSSProperties, useMemo } from \"react\";\nimport {\n Dialog,\n DialogContent,\n DialogHeader,\n DialogTitle,\n DialogDescription,\n DialogFooter,\n} from \"./ui/dialog\";\nimport { Button } from \"./ui/button\";\nimport { useOnboarding } from \"../context/OnboardingContext\";\nimport { cn } from \"../lib/utils\";\n\n// --- Types ---\n\nexport type OnboardingTheme = \n | \"light\" \n | \"dark\" \n | \"minimal\" \n | \"glass\" \n | \"midnight\" \n | \"ocean\" \n | \"sunset\";\n\nexport interface OnboardingModalProps {\n /**\n * The aesthetic theme of the modal.\n */\n theme?: OnboardingTheme;\n \n /**\n * Controls the background gradient style.\n */\n gradient?: \"animated\" | \"static\" | \"none\";\n\n /**\n * Controls the visual style of the backdrop overlay.\n * - `default`: Standard dark dimming.\n * - `blur`: Clean frosted glass effect (blur only).\n * - `transparent`: Invisible overlay.\n * @default \"default\"\n */\n backdrop?: \"default\" | \"blur\" | \"transparent\";\n\n /**\n * Pass a custom Tailwind class for the gradient background.\n */\n customGradientClass?: string;\n\n /**\n * Inline styles to apply to the modal content.\n */\n style?: CSSProperties;\n\n /**\n * Additional class names for the modal container.\n */\n className?: string;\n\n /**\n * Whether to allow closing the modal by clicking the overlay or pressing Escape.\n * @default true\n */\n allowClickOutside?: boolean;\n\n /**\n * Target specific internal elements for styling.\n */\n classNames?: {\n overlay?: string;\n content?: string;\n imageContainer?: string;\n image?: string;\n header?: string;\n title?: string;\n description?: string;\n footer?: string;\n stepIndicators?: string;\n nextButton?: string;\n prevButton?: string;\n skipButton?: string;\n finishButton?: string;\n };\n\n /**\n * Target specific internal elements with inline styles.\n */\n styles?: {\n overlay?: CSSProperties;\n content?: CSSProperties;\n imageContainer?: CSSProperties;\n image?: CSSProperties;\n header?: CSSProperties;\n title?: CSSProperties;\n description?: CSSProperties;\n footer?: CSSProperties;\n stepIndicators?: CSSProperties;\n nextButton?: CSSProperties;\n prevButton?: CSSProperties;\n skipButton?: CSSProperties;\n finishButton?: CSSProperties;\n };\n}\n\n// --- Theme Configurations ---\n\ntype ThemeConfig = {\n mode: \"light\" | \"dark\"; \n gradient: \"animated\" | \"static\" | \"none\";\n className?: string; \n style?: CSSProperties; \n classNames?: OnboardingModalProps['classNames']; \n};\n\nconst THEMES: Record<OnboardingTheme, ThemeConfig> = {\n light: {\n mode: \"light\",\n gradient: \"animated\",\n },\n dark: {\n mode: \"dark\",\n gradient: \"animated\",\n },\n minimal: {\n mode: \"light\",\n gradient: \"none\",\n className: \"border-2 border-black shadow-none rounded-none sm:rounded-none\",\n style: {\n \"--radius\": \"0px\",\n \"--primary\": \"0 0% 0%\", \n \"--primary-foreground\": \"0 0% 100%\",\n } as CSSProperties,\n classNames: {\n nextButton: \"rounded-none border-2 border-black hover:bg-black hover:text-white transition-none\",\n prevButton: \"rounded-none border-2 border-black hover:bg-black hover:text-white transition-none\",\n skipButton: \"hover:bg-transparent underline decoration-black underline-offset-4\",\n stepIndicators: \"rounded-none\",\n imageContainer: \"border-b-2 border-black\",\n content: \"rounded-none\"\n }\n },\n glass: {\n mode: \"dark\",\n gradient: \"animated\",\n className: \"bg-black/40 backdrop-blur-xl border-white/10 shadow-2xl\",\n style: {\n \"--primary\": \"0 0% 100%\",\n \"--primary-foreground\": \"0 0% 0%\",\n \"--muted-foreground\": \"0 0% 80%\",\n } as CSSProperties,\n classNames: {\n overlay: \"bg-black/60 backdrop-blur-sm\",\n nextButton: \"bg-white/90 text-black hover:bg-white\",\n prevButton: \"border-white/20 hover:bg-white/10 text-white\",\n skipButton: \"text-white/60 hover:text-white\",\n title: \"text-white drop-shadow-md\",\n description: \"text-white/90 drop-shadow-sm\"\n }\n },\n midnight: {\n mode: \"dark\",\n gradient: \"animated\",\n style: {\n \"--background\": \"222 47% 11%\", \n \"--foreground\": \"210 40% 98%\",\n \"--primary\": \"263 70% 50%\", \n \"--primary-foreground\": \"210 40% 98%\",\n } as CSSProperties,\n className: \"border-indigo-500/30\"\n },\n ocean: {\n mode: \"light\",\n gradient: \"animated\",\n style: {\n \"--primary\": \"199 89% 48%\", \n \"--primary-foreground\": \"0 0% 100%\",\n } as CSSProperties,\n className: \"border-cyan-200\"\n },\n sunset: {\n mode: \"light\",\n gradient: \"animated\",\n style: {\n \"--primary\": \"24 90% 60%\", \n \"--primary-foreground\": \"0 0% 100%\",\n } as CSSProperties,\n className: \"border-orange-200\"\n }\n};\n\nexport function OnboardingModal({\n theme = \"light\",\n gradient, \n backdrop = \"default\",\n customGradientClass,\n style,\n className,\n allowClickOutside = true, \n classNames = {},\n styles = {},\n}: OnboardingModalProps) {\n const {\n isOpen,\n currentStepIndex,\n steps,\n nextStep,\n prevStep,\n skipOnboarding,\n finishOnboarding,\n setIsOpen,\n } = useOnboarding();\n\n if (!steps || steps.length === 0) return null;\n const currentStep = steps[currentStepIndex] || steps[0];\n \n const isLastStep = currentStepIndex === steps.length - 1;\n const isFirstStep = currentStepIndex === 0;\n\n // --- Theme Merging Logic ---\n const activeTheme = THEMES[theme] || THEMES.light;\n const finalGradient = gradient || activeTheme.gradient;\n const isDarkMode = activeTheme.mode === \"dark\";\n const mergedRootStyle = { ...activeTheme.style, ...style };\n\n // Resolve Backdrop Class (Strictly Blur or Transparent if selected)\n let backdropClass = \"\";\n if (backdrop === \"blur\") backdropClass = \"backdrop-blur-md bg-black/10\"; \n else if (backdrop === \"transparent\") backdropClass = \"bg-transparent\";\n\n const mergedClassNames = useMemo(() => {\n const themeClasses = activeTheme.classNames || {};\n return {\n overlay: cn(\n // If backdrop prop is set to anything other than default, we override theme overlay\n backdrop !== \"default\" ? backdropClass : themeClasses.overlay,\n classNames.overlay\n ),\n content: cn(themeClasses.content, classNames.content),\n imageContainer: cn(themeClasses.imageContainer, classNames.imageContainer),\n image: cn(themeClasses.image, classNames.image),\n header: cn(themeClasses.header, classNames.header),\n title: cn(themeClasses.title, classNames.title),\n description: cn(themeClasses.description, classNames.description),\n footer: cn(themeClasses.footer, classNames.footer),\n stepIndicators: cn(themeClasses.stepIndicators, classNames.stepIndicators),\n nextButton: cn(themeClasses.nextButton, classNames.nextButton),\n prevButton: cn(themeClasses.prevButton, classNames.prevButton),\n skipButton: cn(themeClasses.skipButton, classNames.skipButton),\n finishButton: cn(themeClasses.finishButton, classNames.finishButton),\n };\n }, [activeTheme, classNames, backdrop, backdropClass]);\n\n if (!isOpen) return null;\n\n const showGradient = finalGradient !== \"none\";\n const defaultGradientClass = finalGradient === \"animated\" \n ? \"bg-gradient-to-br from-primary/30 via-background to-primary/30 animate-gradient-flow\"\n : \"bg-gradient-to-br from-primary/20 to-background\"; \n\n const finalGradientClass = customGradientClass || defaultGradientClass;\n\n return (\n <Dialog \n open={isOpen} \n onOpenChange={(open) => {\n if (!open) {\n if (allowClickOutside) {\n skipOnboarding();\n } else {\n setIsOpen(true);\n }\n }\n }}\n >\n <DialogContent \n overlayClassName={mergedClassNames.overlay}\n style={{ ...mergedRootStyle, ...styles.content }}\n className={cn(\n isDarkMode && \"dark\",\n \"max-w-[95vw] sm:max-w-[1000px] p-0 overflow-hidden gap-0 z-[50001] rounded-xl sm:rounded-lg\",\n \"bg-background text-foreground\",\n activeTheme.className,\n className,\n mergedClassNames.content\n )}\n onPointerDownOutside={(e) => {\n if (!allowClickOutside) e.preventDefault();\n }}\n onEscapeKeyDown={(e) => {\n if (!allowClickOutside) e.preventDefault();\n }}\n >\n {/* Step Image Area */}\n <div \n className={cn(\n \"w-full relative flex items-center justify-center overflow-hidden bg-background transition-all duration-300\",\n \"aspect-[4/5] sm:aspect-[4/3] lg:aspect-[16/9]\",\n mergedClassNames.imageContainer\n )}\n style={styles.imageContainer}\n >\n {showGradient && (\n <div className={cn(\"absolute inset-0 z-0\", finalGradientClass)} />\n )}\n \n {showGradient && finalGradient === \"animated\" && (\n <div className=\"absolute inset-0 z-0 bg-[radial-gradient(circle_at_50%_50%,rgba(var(--primary),0.15),transparent_50%)] animate-pulse\" />\n )}\n\n {typeof currentStep.image === 'string' ? (\n <img \n src={currentStep.image} \n alt={currentStep.title}\n className={cn(\"object-contain w-full h-full relative z-10 drop-shadow-2xl\", mergedClassNames.image)}\n style={styles.image}\n onError={(e) => {\n e.currentTarget.style.display = 'none';\n }}\n />\n ) : (\n <picture className={cn(\"w-full h-full relative z-10 flex items-center justify-center\", mergedClassNames.image)} style={styles.image}>\n <source media=\"(min-width: 1024px)\" srcSet={currentStep.image.desktop} />\n <source media=\"(min-width: 640px)\" srcSet={currentStep.image.tablet || currentStep.image.desktop} />\n <img \n src={currentStep.image.mobile} \n alt={currentStep.title}\n className=\"object-contain w-full h-full drop-shadow-2xl\"\n onError={(e) => {\n e.currentTarget.style.display = 'none';\n }}\n />\n </picture>\n )}\n </div>\n\n <div className={cn(\"p-5 sm:p-8\", isDarkMode && \"dark text-foreground\")}>\n <div className=\"min-h-[100px] sm:min-h-[140px] flex flex-col justify-center\">\n <DialogHeader className={cn(\"mb-0\", mergedClassNames.header)} style={styles.header}>\n <DialogTitle \n className={cn(\"text-2xl sm:text-3xl text-center mb-3 sm:mb-4\", mergedClassNames.title)}\n style={styles.title}\n >\n {currentStep.title}\n </DialogTitle>\n <DialogDescription \n className={cn(\"text-center text-base sm:text-lg max-w-[95%] sm:max-w-[80%] mx-auto\", mergedClassNames.description)}\n style={styles.description}\n >\n {currentStep.description.split(\"**\").map((part, index) => (\n index % 2 === 1 ? (\n <span key={index} className=\"text-primary font-bold\">{part}</span>\n ) : (\n <span key={index}>{part}</span>\n )\n ))}\n </DialogDescription>\n </DialogHeader>\n </div>\n\n <DialogFooter \n className={cn(\"relative flex flex-col gap-4 sm:block mt-4 sm:mt-6\", mergedClassNames.footer)}\n style={styles.footer}\n >\n <div \n className={cn(\"w-full flex justify-center sm:absolute sm:left-1/2 sm:top-1/2 sm:-translate-x-1/2 sm:-translate-y-1/2 sm:w-auto\", mergedClassNames.stepIndicators)}\n style={styles.stepIndicators}\n >\n {steps.map((_, index) => (\n <div\n key={index}\n className={cn(\n \"h-2 w-2 sm:h-2.5 sm:w-2.5 rounded-full transition-colors duration-300 mx-1\",\n index === currentStepIndex\n ? \"bg-primary\"\n : \"bg-muted-foreground/30\"\n )}\n />\n ))}\n </div>\n \n <div className=\"flex w-full justify-between items-center relative z-10 box-border\">\n <Button\n variant=\"ghost\"\n size=\"lg\"\n onClick={skipOnboarding}\n className={cn(\"text-muted-foreground hover:text-foreground text-sm sm:text-base px-2 sm:px-4\", mergedClassNames.skipButton)}\n style={styles.skipButton}\n >\n Skip\n </Button>\n\n <div className=\"flex gap-2\">\n <Button\n variant=\"outline\"\n size=\"lg\"\n onClick={prevStep}\n disabled={isFirstStep}\n className={cn(\n isFirstStep && \"invisible\", \n \"text-sm sm:text-base px-3 sm:px-6\",\n mergedClassNames.prevButton\n )}\n style={styles.prevButton}\n >\n Back\n </Button>\n \n {isLastStep ? (\n <Button \n onClick={finishOnboarding} \n size=\"lg\" \n className={cn(\"bg-primary text-primary-foreground hover:bg-primary/90 text-sm sm:text-base px-4 sm:px-8\", mergedClassNames.finishButton)}\n style={styles.finishButton}\n >\n Get Started\n </Button>\n ) : (\n <Button \n onClick={nextStep} \n size=\"lg\" \n className={cn(\"text-sm sm:text-base px-4 sm:px-8\", mergedClassNames.nextButton)}\n style={styles.nextButton}\n >\n Next\n </Button>\n )}\n </div>\n </div>\n </DialogFooter>\n </div>\n </DialogContent>\n </Dialog>\n );\n}\n","import * as React from \"react\";\nimport * as DialogPrimitive from \"@radix-ui/react-dialog\";\n\nimport { cn } from \"../../lib/utils\";\n\nconst Dialog = DialogPrimitive.Root;\n\nconst DialogTrigger = DialogPrimitive.Trigger;\n\nconst DialogPortal = DialogPrimitive.Portal;\n\nconst DialogClose = DialogPrimitive.Close;\n\nconst DialogOverlay = React.forwardRef<\n React.ElementRef<typeof DialogPrimitive.Overlay>,\n React.ComponentPropsWithoutRef<typeof DialogPrimitive.Overlay>\n>(({ className, ...props }, ref) => (\n <DialogPrimitive.Overlay\n ref={ref}\n className={cn(\n \"fixed inset-0 z-50 bg-black/80 data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0\",\n className\n )}\n {...props}\n />\n));\nDialogOverlay.displayName = DialogPrimitive.Overlay.displayName;\n\ninterface DialogContentProps extends React.ComponentPropsWithoutRef<typeof DialogPrimitive.Content> {\n overlayClassName?: string;\n}\n\nconst DialogContent = React.forwardRef<\n React.ElementRef<typeof DialogPrimitive.Content>,\n DialogContentProps\n>(({ className, children, overlayClassName, ...props }, ref) => (\n <DialogPortal>\n <DialogOverlay className={overlayClassName} />\n <DialogPrimitive.Content\n ref={ref}\n className={cn(\n \"fixed left-[50%] top-[50%] z-50 grid w-full max-w-lg max-h-[90vh] translate-x-[-50%] translate-y-[-50%] gap-4 border bg-background p-6 shadow-lg duration-200 overflow-y-auto data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[state=closed]:slide-out-to-left-1/2 data-[state=closed]:slide-out-to-top-[48%] data-[state=open]:slide-in-from-left-1/2 data-[state=open]:slide-in-from-top-[48%] sm:rounded-lg\",\n className\n )}\n {...props}\n >\n {children}\n </DialogPrimitive.Content>\n </DialogPortal>\n));\nDialogContent.displayName = DialogPrimitive.Content.displayName;\n\nconst DialogHeader = ({\n className,\n ...props\n}: React.HTMLAttributes<HTMLDivElement>) => (\n <div\n className={cn(\n \"flex flex-col space-y-1.5 text-center sm:text-left\",\n className\n )}\n {...props}\n />\n);\nDialogHeader.displayName = \"DialogHeader\";\n\nconst DialogFooter = ({\n className,\n ...props\n}: React.HTMLAttributes<HTMLDivElement>) => (\n <div\n className={cn(\n \"flex flex-col-reverse sm:flex-row sm:justify-end sm:space-x-2\",\n className\n )}\n {...props}\n />\n);\nDialogFooter.displayName = \"DialogFooter\";\n\nconst DialogTitle = React.forwardRef<\n React.ElementRef<typeof DialogPrimitive.Title>,\n React.ComponentPropsWithoutRef<typeof DialogPrimitive.Title>\n>(({ className, ...props }, ref) => (\n <DialogPrimitive.Title\n ref={ref}\n className={cn(\n \"text-lg font-semibold leading-none tracking-tight\",\n className\n )}\n {...props}\n />\n));\nDialogTitle.displayName = DialogPrimitive.Title.displayName;\n\nconst DialogDescription = React.forwardRef<\n React.ElementRef<typeof DialogPrimitive.Description>,\n React.ComponentPropsWithoutRef<typeof DialogPrimitive.Description>\n>(({ className, ...props }, ref) => (\n <DialogPrimitive.Description\n ref={ref}\n className={cn(\"text-sm text-muted-foreground\", className)}\n {...props}\n />\n));\nDialogDescription.displayName = DialogPrimitive.Description.displayName;\n\nexport {\n Dialog,\n DialogPortal,\n DialogOverlay,\n DialogClose,\n DialogTrigger,\n DialogContent,\n DialogHeader,\n DialogFooter,\n DialogTitle,\n DialogDescription,\n};\n","import { type ClassValue, clsx } from \"clsx\";\nimport { twMerge } from \"tailwind-merge\";\n\nexport function cn(...inputs: ClassValue[]) {\n return twMerge(clsx(inputs));\n}\n","import * as React from \"react\";\nimport { Slot } from \"@radix-ui/react-slot\";\nimport { cva, type VariantProps } from \"class-variance-authority\";\n\nimport { cn } from \"../../lib/utils\";\n\nconst buttonVariants = cva(\n \"inline-flex items-center justify-center gap-2 whitespace-nowrap rounded-lg text-sm font-medium transition-all duration-200 focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg]:size-4 [&_svg]:shrink-0\",\n {\n variants: {\n variant: {\n default:\n \"bg-primary text-primary-foreground hover:bg-primary/90\",\n destructive:\n \"bg-destructive text-destructive-foreground hover:bg-destructive/90\",\n outline:\n \"border border-border bg-background hover:bg-accent hover:text-accent-foreground\",\n secondary:\n \"bg-secondary text-secondary-foreground hover:bg-secondary/80\",\n ghost: \"hover:bg-accent hover:text-accent-foreground\",\n link: \"text-primary underline-offset-4 hover:underline\",\n },\n size: {\n default: \"h-9 px-4 py-2\",\n sm: \"h-8 rounded-md px-3 text-xs\",\n lg: \"h-10 rounded-md px-6\",\n icon: \"h-9 w-9\",\n },\n },\n defaultVariants: {\n variant: \"default\",\n size: \"default\",\n },\n }\n);\n\nexport interface ButtonProps\n extends React.ButtonHTMLAttributes<HTMLButtonElement>,\n VariantProps<typeof buttonVariants> {\n asChild?: boolean;\n}\n\nconst Button = React.forwardRef<HTMLButtonElement, ButtonProps>(\n ({ className, variant, size, asChild = false, ...props }, ref) => {\n const Comp = asChild ? Slot : \"button\";\n return (\n <Comp\n className={cn(buttonVariants({ variant, size, className }))}\n ref={ref}\n {...props}\n />\n );\n }\n);\nButton.displayName = \"Button\";\n\nexport { Button, buttonVariants };\n"],"mappings":"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","names":["import_react","import_jsx_runtime","React","import_jsx_runtime","import_jsx_runtime"]}