16 CSS Bounce Animations

16 copy-paste CSS bounce animation templates built as real-world use cases — landing-page scroll-down arrow, animate.css-style bounce-in entrance modal, Stripe payment success checkmark, Sonner/Radix toast notification, chat typing dots (wave), button hover bounce, SaaS pricing card hover lift, Shopify Add-to-Cart cart-icon shake, notification badge pop, dark-mode toggle switch elastic snap, physics ball with squash-and-stretch, weightless floating badge, bouncing letters wave, Stripe checkout form error alert shake, DVD screensaver viewport bounce, and Tailwind animate-bounce customization. Every bounce animates only transform and opacity — never margin-top, top, width, or height, which trigger the layout+paint pipeline every frame and tank INP scores on real mobile hardware. Scoped under .bn-NN for no-collision pasting, prefers-reduced-motion guarded with tier-appropriate fallback, framework-agnostic.

11 pure CSS5 light JSPublished

Related30 CSS Keyframe Animations16 CSS Pulse Animations22 CSS Transitions

Scroll Down Arrow Bounce — preview
01 / 16Pure CSS

Scroll Down Arrow Bounce

A landing-page scroll-down indicator — a chevron arrow bouncing gently downward in an infinite loop, signaling "there's more content below." Deep purple → magenta gradient surface with the arrow as the visual anchor. The canonical Apple / Vercel / Linear landing-page pattern users search for when building marketing pages. Uses translateY with a multi-stop bounce keyframe — never margin-top or padding-top which would trigger layout on every frame.

Published

Bounce-In Entrance — preview
02 / 16CSS + JS

Bounce-In Entrance

The canonical bounceIn entrance every animate.css user has copy-pasted at some point, rewritten as vanilla CSS with a modern cubic-bezier + 5-stop keyframe. A single centered card scales in from 0 with elastic overshoot then settles. Perfect drop-in replacement for the animate__bounceIn class most tutorials still teach — no 20KB library import needed. Click the trigger to replay the entrance.

Published

Success Checkmark Pop — preview
03 / 16Pure CSS

Success Checkmark Pop

A payment / form-submit success confirmation — mint circle scales up with elastic overshoot, then the checkmark draws in via stroke-dashoffset. Stripe checkout / Apple Pay / Shopify payment success aesthetic (mint #d1fae5 success surface + emerald #065f46 check). The bounce reads as "you're good." The classic two-stage cascade — circle pops, then check draws — that every well-designed confirmation UI uses.

Published

Toast Notification Bounce — preview
04 / 16CSS + JS

Toast Notification Bounce

A dev-tool toast notification that bounces up from the bottom of the frame — Sonner / Radix Toast / react-hot-toast aesthetic (deep-charcoal surface, semantic icon + copy + dismiss action, mono timestamp). The bounce reads as "new event arrived" with spring-settle physics. Dark-mode-first because dev tools live in dark IDEs. JS auto-cycles through success / info / warning states so users see the pattern in action.

Published

Bouncing Loading Dots — preview
05 / 16Pure CSS

Bouncing Loading Dots

The canonical chat-typing / loading indicator — 3 dots inside a rounded speech bubble bouncing sequentially, signaling "loading" or "the other person is typing." iMessage blue bubble (#007aff) on a soft-gray chat surface. The pattern users search for when building chat interfaces, AI streaming responses, or any loading state that needs to feel calm rather than urgent.

Published

Button Hover Bounce — preview
06 / 16Pure CSS

Button Hover Bounce

A primary CTA button with a hover-triggered bounce micro-interaction — the button lifts and settles with elastic overshoot when the pointer arrives, giving it a physical, clickable feel. Warm orange (#f97316) e-commerce CTA color, satisfying tactile feedback the moment users hover. The interaction reads as "press me" without the intrusive infinite pulse of always-on CTAs.

Published

Card Hover Lift Bounce — preview
07 / 16Pure CSS

Card Hover Lift Bounce

A single pricing / feature card that lifts and bounces on hover — the elevation change with elastic settle makes the card feel physical and interactive. Editorial off-white surface with deep-charcoal ink and gold accent. Stripe / Linear / Vercel pricing table aesthetic — the pattern users search for when building comparison surfaces where hover should reward attention without shouting.

Published

Add to Cart Cart Icon Bounce — preview
08 / 16CSS + JS

Add to Cart Cart Icon Bounce

The Shopify / Etsy Add-to-Cart pattern — clicking Add to Cart triggers a bounce on the cart icon plus a badge-count increment. Users get immediate visual confirmation the item landed in the cart. The demo shows a compact cart icon + Add to Cart button pair as the hero — the bounce reads as "item just landed."

Published

Notification Badge Pop — preview
09 / 16CSS + JS

Notification Badge Pop

A bell icon with a red count badge that pops into view when a new notification arrives — the bell shakes briefly and the badge scales up with elastic overshoot. Slack / Discord / Notion header notification pattern. The demo centers a large bell + badge as the hero — the bounce reads as "new event arrived NOW."

Published

Toggle Switch Elastic Bounce — preview
10 / 16Pure CSS

Toggle Switch Elastic Bounce

A dark mode toggle switch with elastic bounce — the knob slides across and "lands" with a spring squash at the edge, mimicking a physical switch snapping into position. iOS Settings / Figma toolbar / GitHub theme picker aesthetic. Pure CSS via <input type="checkbox"> + :checked — no JavaScript needed. The bounce reads as "switch has snapped, state is committed."

Published

Physics Ball Squash Stretch — preview
11 / 16Pure CSS

Physics Ball Squash Stretch

A bouncing ball with realistic squash-and-stretch physics — falls fast, flattens on floor contact, rebounds with elastic stretch. The classic Disney animation principle rendered as pure CSS with a multi-stop keyframe. Coral ball on a warm beige floor with a soft ground shadow that scales with the ball's height. The pattern users search for when learning "how do I bounce a ball with real physics in CSS."

Published

Floating Hovering Element — preview
12 / 16Pure CSS

Floating Hovering Element

A soft, weightless bounce that loops indefinitely to make an illustration, badge, or icon look like it's floating in mid-air. Sky-blue soft pastel palette with a rounded card element that gently rises and falls in an infinite ease-in-out cycle. Perfect for hero illustrations, achievement badges, mascots, or any element that needs to feel "alive" without demanding attention. Uses alternate iteration so the up-and-down motion never resets — smooth continuous drift.

Published

Bouncing Letters Wave — preview
13 / 16Pure CSS

Bouncing Letters Wave

Individual letters in a word bounce up in sequence, creating a wave motion — the classic 404-page / playful branding pattern. Deep pink surface with the letters of "BOUNCE" spelled out, each letter animated with staggered animation-delay. Every letter runs the SAME translateY bounce keyframe but starts at a different point in the cycle, creating the wave illusion. Users search for this when building error pages, empty states, or playful hero moments.

Published

Form Error Alert Bounce — preview
14 / 16CSS + JS

Form Error Alert Bounce

A form field that shakes horizontally when validation fails — the Stripe checkout / Google form field / login form error pattern. Sharp aggressive shake reads as "this needs your attention NOW" without being ambiguous. Muted rose surface with a card email + payment field, red border on the invalid field, and error copy below. Users search for this when building form validation, checkout flows, or any input that needs failure feedback. Pure horizontal translateX shake — never a diagonal or scale change.

Published

DVD Screensaver Viewport Bounce — preview
15 / 16Pure CSS

DVD Screensaver Viewport Bounce

The cult DVD screensaver bounce — a logo travels diagonally across the viewport and cleanly bounces off all four edges, hoping to land perfectly in a corner (the internet's favorite unsolved problem). Retro dark surface with an 80s neon-purple logo. Pure CSS with separate X and Y keyframes at coprime durations so the trajectory never visually repeats. Zero JavaScript. Every 90s kid searches for this at some point.

Published

Tailwind animate-bounce Customization — preview
16 / 16Pure CSS

Tailwind animate-bounce Customization

The 3-tier Tailwind animate-bounce customization reference — default utility, arbitrary-value tweak, and custom keyframes registered in tailwind.config.js. Three side-by-side badges bouncing at different heights and durations show how each tier controls the effect. The Stack Overflow / dev.to search intent "how do I customize Tailwind's animate-bounce" solved with a copy-paste reference. Tailwind teal palette + JetBrains Mono code snippets so users see exactly what to write.

Published

FAQ

Frequently asked questions

What is a CSS bounce animation and what's the canonical recipe?
A CSS bounce animation is a keyframe animation that mimics the elastic settling of a physical object — a ball hitting the floor, a rubber band snapping, a spring damping to rest. The canonical recipe uses only transform and opacity (never top, margin, padding, width, or height) so the animation runs on the GPU compositor thread with zero layout cost. Two implementation strategies dominate: (1) cubic-bezier overshoot — a single 2-stop keyframe (0% → 100%) with a timing function like cubic-bezier(.34, 1.56, .64, 1) where the second Y coordinate above 1 creates a peak-and-settle. Simple, works for buttons and modals. (2) Multi-stop keyframe — a 4-6 stop cascade like 0% scale(0) → 40% scale(1.15) → 70% scale(.95) → 100% scale(1). Necessary when you want asymmetric bounce (bigger up, smaller down) or squash-and-stretch physics. Both patterns keep the animation compositor-only, so 20 concurrent bounces run at 60fps even on mid-tier mobile. See Demo #1 (Scroll Down Arrow) for the multi-stop cascade and Demo #2 (Bounce-In Modal) for the 5-stop animate.css-style entrance.
Why does animating margin-top or padding kill Core Web Vitals?
Animating margin-top, padding, top, width, or height forces the browser to run its full layout + paint + composite pipeline on every animation frame — 60 times per second. The layout stage is expensive because any size or position change on any element potentially reflows its siblings, its parent, and every descendant. Paint then rebuilds pixel buffers for every affected region. Composite finally uploads to the GPU. On mid-tier mobile (mid-2020s Android, entry iPhones), this pipeline can take 15-20ms per frame — right at the edge of the 16.67ms budget for 60fps. Add one bounce animation using margin-top: 0 → 20px → 0 and you're at 22ms per frame → 45fps. Add three concurrent bounces → 33ms → 30fps → visible stutter. Now measure your INP (Interaction to Next Paint) — it will hit 200ms+ on real hardware, and Google flags this as "Poor" in Core Web Vitals. Your Search Console will show the regression within a week. The compositor-only alternative: transform: translateY and opacity skip layout and paint entirely — they run on the GPU compositor thread. So a 30-instance bounce using transform: translateY runs at consistent 60fps even on 3-year-old Android — because the CPU-side layout thread is never touched. This is the #1 mistake in CSS-bounce tutorials on Medium, dev.to, and old blog posts; every demo in this collection uses the compositor-safe pattern.
How do I replicate animate.css's bounceIn without importing the library?
The bounceIn class in animate.css is a 5-stop keyframe on transform: scale + opacity. Reproducing it as vanilla scoped CSS costs 12 lines instead of 20KB of library CSS. The recipe: @keyframes bounceIn { 0% { opacity: 0; transform: scale(.3); } 20% { transform: scale(1.1); } 40% { transform: scale(.9); } 60% { opacity: 1; transform: scale(1.03); } 80% { transform: scale(.97); } 100% { opacity: 1; transform: scale(1); } } applied with animation: bounceIn .75s cubic-bezier(.34, 1.56, .64, 1) both;. The both keyword combines forwards + backwards — it applies the 100% state after the animation ends AND the 0% state before it starts, so the element sits invisible until the animation triggers. The five stops with alternating over/undershoot (1.1 → .9 → 1.03 → .97) create the rubber-ball rest-position oscillation. A 3-stop version (0% → 50% → 100%) feels mechanical because it's a smooth curve; the extra 2 stops are what make it read as physical. For directional variants — bounceInDown / bounceInUp / bounceInLeft / bounceInRight — add translateY(-40px) or translateX(40px) to the 0% and 20% stops alongside the scale. Demo #2 in this collection ships the exact bounceIn recipe applied to a SaaS pricing modal. No animate.css package, no framework, 12 lines of scoped CSS.
How do I customize Tailwind's animate-bounce — duration, timing, height?
Tailwind ships animate-bounce as a preconfigured utility that maps to a bounce keyframe with animation: bounce 1s infinite. To customize, you have three tiers of approach depending on how much control you need. Tier 1 — arbitrary values (Tailwind v3+): animate-[bounce_1.5s_ease-in-out_infinite] uses arbitrary syntax to override duration and timing without touching tailwind.config.js. Fast for one-off tweaks. Tier 2 — extend the theme in tailwind.config.js: add theme.extend.animation.bounceSlow = 'bounce 2s ease-in-out infinite' then use animate-bounceSlow. This gives you a reusable named utility. Tier 3 — custom keyframes for full control over height and stops: register theme.extend.keyframes.customBounce = { '0%, 100%': { transform: 'translateY(0)' }, '30%': { transform: 'translateY(-20px)' }, '50%': { transform: 'translateY(-6px)' }, '70%': { transform: 'translateY(-14px)' } } paired with theme.extend.animation.customBounce = 'customBounce 2s ease-in-out infinite'. Then use animate-customBounce. The default animate-bounce peak is only -25% of the element's height (via translateY percent) which reads as subtle — for a more assertive bounce like the classic animate.css version, custom keyframes with pixel-based translateY(-20px) feel more physical. Demo #16 in this collection ships the full tailwind.config.js customization recipe alongside the equivalent scoped CSS.
How do I make a bounce animation respect prefers-reduced-motion without losing the interaction feedback?
The prefers-reduced-motion rule fires when users with vestibular disorders or motion sensitivity have set the system-level accessibility preference. The wrong response is to disable the animation entirely and lose the feedback signal — the user still needs to know their click registered. The right response depends on the animation's role. Arrivals (modals, checkmarks, toasts): skip the bounce, show the settled state instantly, add a 200ms opacity fade so the appearance isn't a jarring pop. The information ("this arrived") is preserved; only the celebration motion is disabled. Interactions (button hover bounce, add-to-cart shake): swap the bounce for an instant color state change — the button still gives feedback, just via color instead of motion. Playful/decorative (physics ball, floating badge, DVD screensaver): disable entirely. These carry no information; motion is the whole point, so removing it loses nothing meaningful. Error/alert wiggle: replace horizontal shake with a red border pulse — the "something is wrong" signal persists without the horizontal motion that triggers vestibular issues most severely. This tiered approach follows WCAG 2.3.3 (Animation from Interactions). Every demo in this collection ships its own tier-appropriate fallback in a @media (prefers-reduced-motion: reduce) block — check the demo's CSS panel to see the pattern for each intent tier.
How do I make a realistic squash-and-stretch ball bounce with gravity feel?
Realistic ball physics comes from two techniques compounded — gravity acceleration (the ball falls faster than it rises) and squash-and-stretch deformation (the ball flattens at floor contact and elongates during rebound). Both are pure CSS with a multi-stop keyframe. Gravity: instead of a symmetric 0% translateY(0) → 50% translateY(-200px) → 100% translateY(0), weight the timing curve so the fall is faster than the rise. Use animation-timing-function: cubic-bezier(.5, 0, .5, 1) on the falling half and cubic-bezier(.5, .5, .5, 1) on the rising half — or simpler, use ease-out for the rise (deceleration to peak) and ease-in for the fall (acceleration to floor). Squash-and-stretch: add scaleY and scaleX variations at the peak and floor. At the peak of the jump (100% up), the ball is at rest for a split second — apply scaleY(1.2) scaleX(.9) to elongate vertically. At the floor contact (return to translateY 0), apply scaleY(.7) scaleX(1.3) to flatten horizontally. This is the classic Disney animation principle — objects deform in the direction of motion. For the animation to loop convincingly, add a horizontal decay: translateX increments by a few pixels per cycle so the ball drifts sideways like a real bouncing ball losing energy laterally. Demo #11 in this collection ships the full recipe with all three effects combined.
What's the difference between bounce, pulse, spring, and elastic in CSS animation vocabulary?
These four terms describe distinct motion signatures, and the CSS techniques for each are different. Bounce — vertical motion with overshoot and elastic settlement. A ball hits a floor, a modal arrives with a spring landing, a checkmark pops. Signature: transform: scale or translateY with a multi-stop keyframe (0% → 40% overshoot → 70% undershoot → 100% settle) or a cubic-bezier with the second Y coordinate above 1. Direction: primarily vertical. Feels: physical, gravity-influenced. Use for: arrivals, click feedback, success confirmations. Pulse — radiating outward motion from a static center. A ring emanates from a button, a dot radiates. Signature: box-shadow outward-cast or transform: scale on a pseudo-element with opacity fading to 0. Direction: omnidirectional radial. Feels: alive, attention-signaling. Use for: CTAs, live status indicators, notifications. See our sibling CSS Pulse Animation collection for the full pulse vocabulary. Spring — sinusoidal oscillation around a rest position, damping to zero. Feels smoother than bounce (no hard "floor" contact). Signature: a multi-stop keyframe with 6-8 stops declining in amplitude, or a physics library like Framer Motion. Direction: any axis. Use for: playful UI, drag-release interactions. Elastic — snapping into position with rubber-band overshoot then quick settle. Similar to bounce but the overshoot is sharper and the settle is faster. Signature: a 3-stop cubic-bezier with negative first Y (undershoot before rise) and positive second Y (overshoot before settle). Direction: any. Feels: snappy, high-energy. Use for: modal entrances, toggle switches, tabs. The four terms overlap but the mental model helps you pick the right primitive for the job.

Related collections

20 CSS Animated Buttons preview

20 CSS Animated Buttons

20 hand-coded CSS animated buttons — neon glow, ripple, 3D press, liquid fill, jelly bounce, shine sweep, animated border, moving gradient CTA, text flip, submit success state, add-to-cart progress, download icon, hamburger-to-close, toggle switch, loading spinner inside button, next/prev arrow nav, and ghost button background reveal. Half pure CSS, half lightweight JS for production interactions.

11 CSS animation-timeline Demos preview

11 CSS animation-timeline Demos

11 pure CSS animation-timeline demos built on the W3C scroll() and view() spec — reading progress bar, view-timeline fade & reveal, shrinking sticky header, stacking cards, horizontal scroll section, parallax hero, container shadow indicators, reverse-scroll columns, text scrim reveal, cover card to sticky header, and image zoom / clip-path wipe. Zero JS, off the main thread, Core Web Vitals safe. Copy-paste ready.

25 CSS Background Animations preview

25 CSS Background Animations

25 hand-coded CSS background animations for SaaS hero sections, developer tool documentation, agency portfolios, gaming and Web3 landing pages, seasonal e-commerce campaigns, and dark-mode dashboards. Covers full-screen gradient shifts, animated mesh gradients, aurora borealis glow, cursor spotlight follow, interactive water ripples, dot grid and diagonal stripe patterns, SVG grain and noise texture overlays, topographic contour lines, layered SVG waves, plasma and lava lamp fluids, bokeh light blur, particle constellation networks, matrix digital rain, synthwave 3D perspective grids, starfield warp speed, CRT scanline overlays, fog and mist drift, morphing organic blobs, floating glassmorphism orbs, halftone dot patterns, starry night skies, floating geometric shapes, rising bubbles, and falling snow. 20 are pure CSS with zero JavaScript; the 5 that need it use vanilla canvas or pointer tracking with no dependencies. Every background animates compositor-only properties so it never blocks the main thread, is scoped under a .bga-NN prefix for no-collision pasting, guards prefers-reduced-motion, and ports unchanged to React, Vue, Svelte, Astro, Next.js and Tailwind.

Search CodeFronts

Loading…