78 lines
1.8 KiB
TypeScript
78 lines
1.8 KiB
TypeScript
import { forwardRef } from "react";
|
|
|
|
import {
|
|
alertDescriptionVariants,
|
|
alertIconVariants,
|
|
alertTitleVariants,
|
|
alertVariants
|
|
} from "./alert.variants";
|
|
import { cn } from "../lib/cn";
|
|
import type { VariantProps } from "../lib/cva";
|
|
import { createDataAttributes, createSlot } from "../lib/contracts";
|
|
|
|
export type AlertProps = React.ComponentPropsWithoutRef<"div"> &
|
|
VariantProps<typeof alertVariants> & {
|
|
icon?: React.ReactNode;
|
|
};
|
|
|
|
export const Alert = forwardRef<HTMLDivElement, AlertProps>(function Alert(
|
|
{
|
|
children,
|
|
className,
|
|
icon,
|
|
variant = "default",
|
|
...props
|
|
},
|
|
ref
|
|
) {
|
|
const hasIcon = Boolean(icon);
|
|
|
|
return (
|
|
<div
|
|
{...props}
|
|
{...createSlot("root")}
|
|
{...createDataAttributes({
|
|
"has-icon": hasIcon,
|
|
variant
|
|
})}
|
|
className={cn(alertVariants({ hasIcon, variant }), className)}
|
|
ref={ref}
|
|
role={props.role ?? "alert"}
|
|
>
|
|
{hasIcon ? <span {...createSlot("icon")} className={alertIconVariants()}>{icon}</span> : null}
|
|
{children}
|
|
</div>
|
|
);
|
|
});
|
|
|
|
export type AlertTitleProps = React.ComponentPropsWithoutRef<"h4">;
|
|
|
|
export const AlertTitle = forwardRef<HTMLHeadingElement, AlertTitleProps>(function AlertTitle(
|
|
{ className, ...props },
|
|
ref
|
|
) {
|
|
return (
|
|
<h4
|
|
{...props}
|
|
{...createSlot("label")}
|
|
className={cn(alertTitleVariants(), className)}
|
|
ref={ref}
|
|
/>
|
|
);
|
|
});
|
|
|
|
export type AlertDescriptionProps = React.ComponentPropsWithoutRef<"div">;
|
|
|
|
export const AlertDescription = forwardRef<HTMLDivElement, AlertDescriptionProps>(
|
|
function AlertDescription({ className, ...props }, ref) {
|
|
return (
|
|
<div
|
|
{...props}
|
|
{...createSlot("description")}
|
|
className={cn(alertDescriptionVariants(), className)}
|
|
ref={ref}
|
|
/>
|
|
);
|
|
}
|
|
);
|