Toggle Price Counter React component
A monthly / yearly billing switch whose price rolls to the new amount digit by digit like an odometer, with a saving badge that pops when yearly is picked and a line that spells out what's billed and saved.
When to use the Toggle Price Counter component
Use Toggle Price Counter at the top of a pricing page or inside a plan card to let people compare monthly and yearly billing. The rolling digits make the difference feel concrete.
Control period from the page and use RollingNumber on every plan card so all prices roll together.
Installation
Add the Toggle Price Counter component to your project with the shadcn CLI. It lands in components/toggle-price-counter.tsx as plain React + Tailwind CSS source you own and can edit.
npx shadcn@latest add https://reactframe.com/r/toggle-price-counter.jsonOr copy the source by hand and install its dependencies:
npm install motion clsx tailwind-mergeProps
<TogglePriceCounter /> accepts 10 props, all optional.
| Prop | Type | Default |
|---|---|---|
| monthly Price per month on monthly billing. | number | 24 |
| yearly Price per month on yearly billing. | number | 19 |
| currency | string | "USD" |
| locale | string | "en-US" |
| defaultPeriod | "monthly" | "yearly" | "monthly" |
| period | "monthly" | "yearly" | — |
| onPeriodChange | (period: "monthly" | "yearly") => void | — |
| discountLabel Badge next to Yearly. Leave out to show the computed saving. | string | — |
| theme | "dark" | "light" | "dark" |
| className | string | — |
- monthly
Price per month on monthly billing.
numberDefault: 24 - yearly
Price per month on yearly billing.
numberDefault: 19 - currencystringDefault: "USD"
- localestringDefault: "en-US"
- defaultPeriod"monthly" | "yearly"Default: "monthly"
- period"monthly" | "yearly"
- onPeriodChange(period: "monthly" | "yearly") => void
- discountLabel
Badge next to Yearly. Leave out to show the computed saving.
string - theme"dark" | "light"Default: "dark"
- classNamestring
FAQ
- How is the saving calculated?
- From the two per-month prices: 1 − yearly ÷ monthly, rounded. Pass discountLabel to show your own text, like '2 months free'.
- Can I animate several prices at once?
- Yes. Keep period in your state, pass it to the toggle, and render RollingNumber for each plan's price.
- Do screen readers hear the digits?
- They hear the whole price once; the rolling digit columns are hidden from them.