Loader

Eighteen loading animations with accessible labels, adjustable speed, and reduced motion support.

Loading example…

Installation

bunx --bun shadcn@latest add @sui/loader

Install with the shadcn CLI or use the shared @workspace/ui package. Follow the installation guide to configure the registry, load styles, and choose import aliases.

import { Loader } from "@workspace/ui/components/loader";

Usage

<Loader variant="dots" label="Loading messages" />

Loader provides eighteen distinct loading animations, all using the current text color. The root exposes role="status" and a loading label while decorative visuals remain hidden from assistive technology. Reduced motion changes stop CSS animations and character timers immediately, leaving a static indicator. Timers and media listeners are cleaned up on unmount. Server rendering uses static character frames to avoid hydration differences.

Variants

VariantAnimation
spinnerRotating arc over a circular track
dash-ringStretching arc that travels smoothly around a rotating ring
dotsThree staggered bouncing dots
barsFour staggered scaling bars
dot-matrixA rippling 3 × 3 dot matrix
ditherA patterned 4 × 4 blinking square matrix
asciiRotating character frames
ascii-lineRotating line character frames
ascii-brailleBraille ring character frames
ascii-blocksRising and falling block characters
ascii-bounceBouncing dot character frames
morphRotating circle, square, triangle, and hexagon morphs
cometRotating comet with a fading trail
scrambleScrambled characters resolving to LOADING
metaballsTwo merging circular blobs
newtonAlternating end swings of a Newton cradle
helixOpposing strands of oscillating dots
percentDecorative looping percentage and short bar

percent is a looping loading motif, not measured task progress. Use Progress for actual progress.

Sizes and colors

Use sm (16px), default (20px), lg (28px), or a numeric pixel size. Numeric sizes are clamped to 8–4096px; non-finite values use 20px. Set className="text-primary" to use the active theme color.

Loading example…

Animation speed

speed controls the base cycle in seconds and defaults to 1. Smaller values are faster; values are clamped to 0.1–86400 and non-finite values fall back to 1. Character timers have a minimum interval of 10 milliseconds. Complex animations use fixed multiples of the base cycle.

<Loader variant="dots" speed={0.6} label="Loading" />
<Loader variant="metaballs" speed={2} label="Loading" />

Button loading state

Render the loader only while work is in progress and disable repeated submissions. This example simulates a local save and cleans up its timer on unmount.

Loading example…

API

PropTypeDefault
variantLoaderVariant, see all eighteen variants above"spinner"
size"sm" | "default" | "lg" | number"default"
speednumber, base cycle in seconds1
labelstring"Loading"
renderReact element or render functionspan

Standard span props, refs, styles, and className are supported. The root exposes data-slot="loader" and data-variant. Labels describe actual activity; the percentage motif is decorative and does not expose progress values to assistive technology. See Base UI composition for render and ref behavior.