REFERENCE
- Gallery page: https://magpui.com/en/i/button-label-becomes-wave-loader-468f7d
- First frame (image): https://dnioievkvxejjbxgwvko.supabase.co/storage/v1/object/public/media/button-label-becomes-wave-loader-468f7d/shot.jpg
- Clip (mp4): https://dnioievkvxejjbxgwvko.supabase.co/storage/v1/object/public/media/button-label-becomes-wave-loader-468f7d/clip.mp4
- Original post: https://x.com/aviralj02/status/2114288356037398775 by @aviralj02
Before building, download the first frame and look at it. If ffmpeg is available, download the clip and extract frames (ffmpeg -i clip.mp4 -vf fps=2 frame-%02d.png), then study the motion frame by frame. Match what you see; the text below describes it, the frames are the truth.
BUILD: Build one save button whose text becomes a traveling wave of slanted strokes while saving, then a checkmark and Saved. Keep the loading state inside the label rather than adding a spinner.
DESIGN SYSTEM: Off-white #fafafa pill on #191b17; idle width approximately 180px, height 56px, radius 999px. Black #111111 medium sans-serif text around 20px. Compact success width around 136px. Center all contents with 20px horizontal padding and an 8px icon gap.
MOTION: On activation replace text with approximately 12 thin strokes, varying from vertical to diagonal and from light gray to black in a traveling wave. Target 900ms repeating cycles with 45ms per-stroke stagger, cubic-bezier(0.4,0,0.2,1). When the real async action resolves, fade strokes out in 120ms and introduce checkmark plus Saved in 180ms; animate width over 250ms cubic-bezier(0.22,1,0.36,1). Return to idle after an optional 1500ms confirmation. Durations are implementation estimates.
SECTIONS: Idle Save changes; hover; pressed; disabled-while-saving wave; successful Saved with checkmark; error with retry, using the project conventions.
IMPLEMENTATION: Motion animates width and label crossfades; SVG strokes or spans animate rotation and opacity. Avoid changing button height or surrounding layout. Use a native keyboard-operable button, visible focus ring, aria-busy and a polite status message. Reduced motion uses static Saving text and immediate width changes. Never report success before the async operation resolves.
ADAPT TO THE PROJECT: Reuse existing tokens, components and fonts; map colors to nearby project tokens. Never copy source logos, names, photos or illustrations; use placeholders.
SUCCESS CHECK:
- All states transition without layout jumps.
- Keyboard operation and reduced motion work.
- Animation stays smooth on mobile.