"use client";
import { Toast } from "@base-ui/react/toast";
import {
CircleAlertIcon,
CircleCheckIcon,
InfoIcon,
LoaderCircleIcon,
TriangleAlertIcon,
} from "lucide-react";
import { cn } from "~/lib/utils";
import { buttonVariants } from "~/components/ui/button";
const toastManager = Toast.createToastManager();
const anchoredToastManager = Toast.createToastManager();
const TOAST_ICONS = {
error: CircleAlertIcon,
info: InfoIcon,
loading: LoaderCircleIcon,
success: CircleCheckIcon,
warning: TriangleAlertIcon,
} as const;
type ToastPosition =
| "top-left"
| "top-center"
| "top-right"
| "bottom-left"
| "bottom-center"
| "bottom-right";
interface ToastProviderProps extends Toast.Provider.Props {
position?: ToastPosition;
}
function ToastProvider({ children, position = "top-right", ...props }: ToastProviderProps) {
return (
{children}
);
}
function Toasts({ position = "top-right" }: { position: ToastPosition }) {
const { toasts } = Toast.useToastManager();
const isTop = position.startsWith("top");
return (
{toasts.map((toast) => {
const Icon = toast.type ? TOAST_ICONS[toast.type as keyof typeof TOAST_ICONS] : null;
return (
{toast.actionProps && (
{toast.actionProps.children}
)}
);
})}
);
}
function AnchoredToastProvider({ children, ...props }: Toast.Provider.Props) {
return (
{children}
);
}
function AnchoredToasts() {
const { toasts } = Toast.useToastManager();
return (
{toasts.map((toast) => {
const Icon = toast.type ? TOAST_ICONS[toast.type as keyof typeof TOAST_ICONS] : null;
const tooltipStyle = (toast.data as { tooltipStyle?: boolean })?.tooltipStyle ?? false;
const positionerProps = toast.positionerProps;
if (!positionerProps?.anchor) {
return null;
}
return (
{tooltipStyle ? (
) : (
{toast.actionProps && (
{toast.actionProps.children}
)}
)}
);
})}
);
}
export {
ToastProvider,
type ToastPosition,
toastManager,
AnchoredToastProvider,
anchoredToastManager,
};