ToroUI

Animation

Adding smooth animations and transitions to Toro UI components.


Toro UI uses CSS-based animations powered by tw-animate-css and Tailwind CSS transitions. Animations are driven by data attributes from Base UI, so they work automatically when components open, close, or change state.

How It Works

Base UI components expose data-open and data-closed attributes that reflect their current state. Toro UI maps these to CSS animations:

<DialogPrimitive.Popup
  className="data-open:animate-in data-open:fade-in-0 data-open:zoom-in-95 data-closed:animate-out data-closed:fade-out-0 data-closed:zoom-out-95"
/>

When the dialog opens, data-open is set and the enter animation plays. When it closes, data-closed triggers the exit animation.

Animation Utilities

The tw-animate-css package provides these animation utilities:

Enter Animations

  • animate-in — Base class for enter animations
  • fade-in-{value} — Fade in from opacity (e.g., fade-in-0)
  • zoom-in-{value} — Scale up from percentage (e.g., zoom-in-95)
  • slide-in-from-top-{value} — Slide in from top
  • slide-in-from-bottom-{value} — Slide in from bottom
  • slide-in-from-left-{value} — Slide in from left
  • slide-in-from-right-{value} — Slide in from right

Exit Animations

  • animate-out — Base class for exit animations
  • fade-out-{value} — Fade out to opacity
  • zoom-out-{value} — Scale down to percentage
  • slide-out-to-top-{value} — Slide out to top
  • slide-out-to-bottom-{value} — Slide out to bottom
  • slide-out-to-left-{value} — Slide out to left
  • slide-out-to-right-{value} — Slide out to right

Common Patterns

Dialog / Alert Dialog

Fade and zoom for centered overlays:

// Overlay backdrop
className="data-open:animate-in data-open:fade-in-0 data-closed:animate-out data-closed:fade-out-0"

// Dialog content
className="data-open:animate-in data-open:fade-in-0 data-open:zoom-in-95 data-closed:animate-out data-closed:fade-out-0 data-closed:zoom-out-95"

Fade with directional slide based on placement:

className="data-open:animate-in data-open:fade-in-0 data-closed:animate-out data-closed:fade-out-0 data-side-top:slide-in-from-bottom-2 data-side-bottom:slide-in-from-top-2"

Accordion

Height animation using CSS grid:

<div className={cn(
  "grid transition-[grid-template-rows] duration-200 ease-in-out",
  open ? "grid-rows-[1fr]" : "grid-rows-[0fr]"
)}>
  <div className="overflow-hidden">
    {children}
  </div>
</div>

Transitions

For simple state changes, use Tailwind's built-in transition utilities:

<button className="transition-colors hover:bg-muted">
  Hover me
</button>

Common transition patterns in Toro UI:

  • transition-colors — Color and background changes
  • transition-all — General-purpose transitions
  • transition-transform — Scale and rotation
  • transition-[grid-template-rows] — Accordion expand/collapse
  • duration-100 / duration-200 — Animation speed

Customizing Animations

Since components live in your project, you can change any animation by editing the class names directly. To make a dialog slide in from the bottom instead of zooming:

// Before
className="data-open:animate-in data-open:zoom-in-95"

// After
className="data-open:animate-in data-open:slide-in-from-bottom-4"

Disabling Animations

Remove the animation classes from a component to disable its animations entirely, or use Tailwind's motion-reduce variant to respect user preferences:

className="motion-reduce:animate-none motion-reduce:transition-none"