Skip to content

GSAP & Scroll Motion

SaaS Pricing Table Toggle (Monthly/Annual) with GSAP Rolling Number Counter

One switch flips every plan between monthly and annual; each price rolls to its new value with tabular figures in a fixed-width slot, and screen readers hear the final price once, not every frame.

Accessible switch · Zero CLS

Works in Webflow Framer React Zero CLS

Customize before you copy

Platform
Motion timing

Showing the Webflow version

Claude prompt · production spec
You are a senior frontend engineer building a SaaS pricing section. Add a Monthly / Annual billing toggle whose prices roll to their new values.

Behaviour:
- One toggle controls every plan card. It is a real switch: role="switch" with aria-checked, a visible label ("Billed annually · save 20%"), keyboard operable with Space and Enter.
- Each price stores both values (e.g. data-monthly="49" data-annual="39"). On toggle, the number counts from the old value to the new one over 0.8s with ease "expo.out", while the digits nudge 30% vertically in the direction of change (down when the price drops, up when it rises).
- Under each price, swap the sub-label ("per month" ↔ "per month, billed yearly") and show the yearly total for annual.

Layout and performance:
- Prices use font-variant-numeric: tabular-nums inside a slot with a fixed min-width in ch, so a 2- vs 3-digit price never moves the layout (CLS 0).
- No per-frame React re-renders beyond the changing integer (re-render only when the rounded value changes), or write textContent directly.
- The server HTML shows the monthly prices, so the page is correct before JavaScript.

Accessibility:
- Don't put aria-live on the counting numbers (screen readers would read every frame). Announce once through a single polite live region: "Annual billing selected. Prices updated."
- Reduced motion: swap the numbers instantly.

Deliver the structure, styles and script, then list the three values I'd tweak to make the counter feel faster or more premium.

Target platform: Webflow.
- Build the structure as native Webflow Designer elements with Client-First class names (section_[name], [name]_component, [name]_item). No div soup from an HTML embed unless I ask for one.
- Hook every behaviour to custom attributes (data-gsap="…"), never to class names, so designers can restyle without breaking the script.
- Load GSAP through Webflow's built-in GSAP integration (Site settings) or the jsDelivr CDN tags, and put the init script in Page settings → Before </body> tag, wrapped in Webflow.push(() => { … }).
- Say which parts go in Designer styles, which in a page-head <style>, and which in the body script.
- Designer: pricing_toggle is a Button with data-billing-toggle; each plan's price is a Text Span with data-price, data-monthly and data-annual (CMS-bindable), and the sub-label a Text Span with data-price-note.
Motion timing: "Editorial". Use a base duration of 0.8s, ease "expo.out" (CSS: cubic-bezier(0.16, 1, 0.3, 1)), stagger 0.08s, scrub smoothing 0.8, and springs of stiffness 220 / damping 22, everywhere a duration, ease or spring appears.

3-step implementation guide

  1. Step 1

    DOM & attribute setup

    Give every price both values (monthly and annual) as attributes or props, render the monthly price in the HTML, and wrap the number in a fixed-width tabular-figures slot so it can't push the layout.

  2. Step 2

    Prompt Claude or drop in the snippet

    Paste the prompt for your platform or drop in the snippet. The toggle is a real switch (role and aria-checked), and a single polite live region announces the change once instead of reading every frame.

  3. Step 3

    Mobile & Core Web Vitals check

    Toggle repeatedly on a mid-range phone: no layout jump (CLS 0), no lag (INP under 200 ms in PageSpeed Insights), and with reduced motion on, the prices should swap instantly.

Building a full site like this?

Skip the manual setup — I ship complete Figma-to-Webflow & Framer builds in 5–10 business days, or can wire this exact interaction into your live site in 48 hours ($250).