A modal dialog that interrupts the user with important content and expects a response.
1import {2 AlertDialog,3 AlertDialogCancel,4 AlertDialogAction,Installation
pnpm dlx sprawlify@latest add alert-dialognpx sprawlify@latest add alert-dialogyarn sprawlify@latest add alert-dialogbunx --bun sprawlify@latest add alert-dialog
Install the following dependencies:
pnpm add @sprawlify/primitives @sprawlify/reactnpm install @sprawlify/primitives @sprawlify/reactyarn add @sprawlify/primitives @sprawlify/reactbun add @sprawlify/primitives @sprawlify/react
Add the following files to your project:
1"use client";23import * as React from "react";4import { AlertDialog as AlertDialogPrimitive } from "@sprawlify/react/alert-dialog";5import { cn } from "@/lib/utils";6import { Button } from "@/components/ui/button";7import { Portal } from "@sprawlify/react/portal";8import { sprawlify } from "@sprawlify/react";910function AlertDialog({ ...props }: React.ComponentProps<typeof AlertDialogPrimitive.Root>) {11 return <AlertDialogPrimitive.Root data-slot="alert-dialog" {...props} />;12}1314function AlertDialogTrigger({15 ...props16}: React.ComponentProps<typeof AlertDialogPrimitive.Trigger>) {17 return <AlertDialogPrimitive.Trigger data-slot="alert-dialog-trigger" {...props} />;18}1920function AlertDialogPortal({ ...props }: React.ComponentProps<typeof Portal>) {21 return <Portal data-slot="alert-dialog-portal" {...props} />;22}2324function AlertDialogBackdrop({25 className,26 ...props27}: React.ComponentProps<typeof AlertDialogPrimitive.Backdrop>) {28 return (29 <AlertDialogPrimitive.Backdrop30 data-slot="alert-dialog-backdrop"31 className={cn(32 "data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 bg-black/10 duration-100 supports-backdrop-filter:backdrop-blur-xs fixed inset-0 z-50",33 className,34 )}35 {...props}36 />37 );38}3940function AlertDialogContent({41 className,42 size = "default",43 ...props44}: React.ComponentProps<typeof AlertDialogPrimitive.Content> & {45 size?: "default" | "sm";46}) {47 return (48 <AlertDialogPortal>49 <AlertDialogBackdrop />50 <AlertDialogPrimitive.Positioner>51 <AlertDialogPrimitive.Content52 data-slot="alert-dialog-content"53 data-size={size}54 className={cn(55 "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 bg-background ring-foreground/10 gap-4 rounded-xl p-4 ring-1 duration-100 data-[size=default]:max-w-xs data-[size=sm]:max-w-xs data-[size=default]:sm:max-w-sm group/alert-dialog-content fixed top-1/2 left-1/2 z-50 grid w-full -translate-x-1/2 -translate-y-1/2 outline-none",56 className,57 )}58 {...props}59 />60 </AlertDialogPrimitive.Positioner>61 </AlertDialogPortal>62 );63}6465function AlertDialogHeader({ className, ...props }: React.ComponentProps<"div">) {66 return (67 <sprawlify.div68 data-slot="alert-dialog-header"69 className={cn(70 "grid grid-rows-[auto_1fr] place-items-center gap-1.5 text-center has-data-[slot=alert-dialog-media]:grid-rows-[auto_auto_1fr] has-data-[slot=alert-dialog-media]:gap-x-4 sm:group-data-[size=default]/alert-dialog-content:place-items-start sm:group-data-[size=default]/alert-dialog-content:text-left sm:group-data-[size=default]/alert-dialog-content:has-data-[slot=alert-dialog-media]:grid-rows-[auto_1fr]",71 className,72 )}73 {...props}74 />75 );76}7778function AlertDialogFooter({ className, ...props }: React.ComponentProps<typeof sprawlify.div>) {79 return (80 <sprawlify.div81 data-slot="alert-dialog-footer"82 className={cn(83 "bg-muted/50 -mx-4 -mb-4 rounded-b-xl border-t p-4 flex flex-col-reverse gap-2 group-data-[size=sm]/alert-dialog-content:grid group-data-[size=sm]/alert-dialog-content:grid-cols-2 sm:flex-row sm:justify-end",84 className,85 )}86 {...props}87 />88 );89}9091function AlertDialogMedia({ className, ...props }: React.ComponentProps<typeof sprawlify.div>) {92 return (93 <sprawlify.div94 data-slot="alert-dialog-media"95 className={cn(96 "bg-muted mb-2 inline-flex size-10 items-center justify-center rounded-md sm:group-data-[size=default]/alert-dialog-content:row-span-2 *:[svg:not([class*='size-'])]:size-6",97 className,98 )}99 {...props}100 />101 );102}103104function AlertDialogTitle({105 className,106 ...props107}: React.ComponentProps<typeof AlertDialogPrimitive.Title>) {108 return (109 <AlertDialogPrimitive.Title110 data-slot="alert-dialog-title"111 className={cn(112 "text-base font-medium sm:group-data-[size=default]/alert-dialog-content:group-has-data-[slot=alert-dialog-media]/alert-dialog-content:col-start-2 cn-font-heading",113 className,114 )}115 {...props}116 />117 );118}119120function AlertDialogDescription({121 className,122 ...props123}: React.ComponentProps<typeof AlertDialogPrimitive.Description>) {124 return (125 <AlertDialogPrimitive.Description126 data-slot="alert-dialog-description"127 className={cn(128 "text-muted-foreground *:[a]:hover:text-foreground text-sm text-balance md:text-pretty *:[a]:underline *:[a]:underline-offset-3",129 className,130 )}131 {...props}132 />133 );134}135136function AlertDialogCancel({137 className,138 variant = "outline",139 size = "default",140 value = "cancel",141 ...props142}: React.ComponentProps<typeof AlertDialogPrimitive.CloseTrigger> &143 Pick<React.ComponentProps<typeof Button>, "variant" | "size">) {144 return (145 <Button variant={variant} size={size} asChild>146 <AlertDialogPrimitive.CloseTrigger147 data-slot="alert-dialog-cancel"148 value={value}149 className={cn(className)}150 {...props}151 />152 </Button>153 );154}155156function AlertDialogAction({157 className,158 variant = "default",159 size = "default",160 ...props161}: React.ComponentProps<typeof AlertDialogPrimitive.CloseTrigger> &162 Pick<React.ComponentProps<typeof Button>, "variant" | "size">) {163 return (164 <Button variant={variant} size={size} asChild>165 <AlertDialogPrimitive.CloseTrigger166 data-slot="alert-dialog-action"167 className={cn(className)}168 {...props}169 />170 </Button>171 );172}173174export {175 AlertDialog,176 AlertDialogCancel,177 AlertDialogAction,178 AlertDialogContent,179 AlertDialogDescription,180 AlertDialogFooter,181 AlertDialogHeader,182 AlertDialogMedia,183 AlertDialogBackdrop,184 AlertDialogPortal,185 AlertDialogTitle,186 AlertDialogTrigger,187};188Update the import paths to match your project setup.
Usage
1import {
2 AlertDialog,
3 AlertDialogCancel,
4 AlertDialogAction,
5 AlertDialogContent,
6 AlertDialogDescription,
7 AlertDialogFooter,
8 AlertDialogHeader,
9 AlertDialogTitle,
10 AlertDialogTrigger,
11} from "@/components/ui/alert-dialog"1<AlertDialog>
2 <AlertDialogTrigger asChild>
3 <Button variant="outline">Show Dialog</Button>
4 </AlertDialogTrigger>
5 <AlertDialogContent>
6 <AlertDialogHeader>
7 <AlertDialogTitle>Are you absolutely sure?</AlertDialogTitle>
8 <AlertDialogDescription>
9 This action cannot be undone. This will permanently delete your account
10 from our servers.
11 </AlertDialogDescription>
12 </AlertDialogHeader>
13 <AlertDialogFooter>
14 <AlertDialogCancel>Cancel</AlertDialogCancel>
15 <AlertDialogAction value="continue">Continue</AlertDialogAction>
16 </AlertDialogFooter>
17 </AlertDialogContent>
18</AlertDialog>Examples
Basic
A basic alert dialog with a title, description, and cancel and continue buttons.
1import {2 AlertDialog,3 AlertDialogCancel,4 AlertDialogAction,Destructive
Use the AlertDialogAction component to add a destructive action button to the alert dialog.
1import {2 AlertDialog,3 AlertDialogCancel,4 AlertDialogAction,Media
Use the AlertDialogMedia component to add a media element such as an icon or image to the alert dialog.
1import {2 AlertDialog,3 AlertDialogCancel,4 AlertDialogAction,Small
Use the size="sm" prop to make the alert dialog smaller.
1import {2 AlertDialog,3 AlertDialogCancel,4 AlertDialogAction,Small With Media
Use the size="sm" prop to make the alert dialog smaller and the AlertDialogMedia component to add a media element such as an icon or image to the alert dialog.
1import {2 AlertDialog,3 AlertDialogCancel,4 AlertDialogAction,Get PRO
Need premium blocks and templates? Upgrade to PRO and get access.