Dialog with Framer Motion
Using Framer Motion to add initial and exit animations to a modal Dialog and its backdrop
element.
import * as Ariakit from "@ariakit/react";
import { AnimatePresence, motion } from "framer-motion";
import "./style.css";
export default function Example() {
const dialog = Ariakit.useDialogStore();
const mounted = dialog.useState("mounted");
return (
<>
<Ariakit.Button onClick={dialog.show} className="button">
Show modal
</Ariakit.Button>
<AnimatePresence>
{mounted && (
<Ariakit.Dialog
as={motion.div}
store={dialog}
alwaysVisible
className="dialog"
initial={{ opacity: 0, scale: 0.95 }}
animate={{ opacity: 1, scale: 1 }}
exit={{ opacity: 0, scale: 0.95 }}
backdrop={
<motion.div
className="backdrop"
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
/>
}
>
<Ariakit.DialogHeading className="heading">
Success
</Ariakit.DialogHeading>
<p className="description">
Your payment has been successfully processed. We have emailed your
receipt.
</p>
<Ariakit.DialogDismiss className="button">OK</Ariakit.DialogDismiss>
</Ariakit.Dialog>
)}
</AnimatePresence>
</>
);
}
Components
ButtonTrigger an action or event, such as submitting a Form, opening a Dialog, canceling an action, or performing a delete operation in React. This component is based on the WAI-ARIA Button Pattern.
DialogOpen a new window that can be either modal or non-modal and optionally rendered in a React portal. This component is based on the WAI-ARIA Dialog Pattern.
AnimatePresence
We use the AnimatePresence component from Framer Motion to animate the Ariakit Dialog component when it gets mounted and unmounted from the DOM.
<AnimatePresence>
{mounted && (
<Ariakit.Dialog
as={motion.div}
store={dialog}
alwaysVisible
initial={{ opacity: 0, scale: 0.95 }}
animate={{ opacity: 1, scale: 1 }}
exit={{ opacity: 0, scale: 0.95 }}
backdrop={
<motion.div
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
/>
}
/>
)}
</AnimatePresence>
To dynamically render the dialog component, you can use the mounted
state that can be retrieved from the store:
const dialog = Ariakit.useDialogStore();
const mounted = dialog.useState("mounted");
You can learn more about reading state from the store on the Component stores guide.