caliper uidocs

Billing screen

Pro

Plan, usage and money: the next invoice itemised before it is charged, usage with its cost at this pace, and failed invoices with a pay action.

Installs components/ui/billing-screen.tsxDepends on @radix-ui/react-slot, lucide-reactMotion none in component source
pnpm dlx shadcn@latest add @caliper/billing-screen
Billing

Billing

Team plan · billed monthly · renews 1 November

Usage this period

Seats

14 / 20

Within limit

Build minutes

3,120 / 5,000

About $57 extra at this pace.

Within limit

Storage

41 / 50 GB

Within limit

Next invoice

$666.71

Charged 1 November

Team plan · 14 seats × $32
$448.00
Build minutes overage (projected)
$57.00
2 seats added mid-period
$46.00
VAT 21%
$115.71
Visa ending 4242Expires 10/26, before this invoice

Invoices

  • INV-2041September · Paid$672.00
  • INV-1987August · Retrying 12 Oct$624.00
  • INV-1932July · Paid$624.00

When to use #

Use it for

  • Self-serve plans with seats or metered usage.
  • Customers ask what next month will cost.

Skip it when

  • Invoice-only enterprise billing; a list of invoices is enough.

Installation #

terminal
pnpm dlx shadcn@latest add @caliper/billing-screen

Adds its 8 files to components/ui/, each with its own stylesheet, and installs their packages. Pro installs with your access token, set up once per project. See Pro access. The first part also adds Caliper UI’s tokens; import them once as in Installation.

Usage #

Import it from your copy of the source. The example behind the preview comes with the source.

example.tsx
import { BillingScreen } from "@/components/ui/billing-screen"

The worked example comes with Pro

The 59-line example behind the preview opens here with a Pro or Team licence.

Checking your licence…

API reference #

BillingScreen

component
PropTypeDefault
titlestring"Billing"
plan *{ name: string; detail: string; }—
actionsReactNode—
usage *readonly BillingUsage[]—
nextInvoice *{ date: string; lines: readonly { label: string; amount: number; projected?: boolean | undefined; }[]; }—
card{ label: string; expires: string; expiresFirst?: boolean | undefined; onUpdate?: (() => void) | undefined; }—
invoices *readonly BillingInvoice[]—
currencystring"USD"
classNamestring—

Accessibility #

It is built on native elements and keeps aria-hidden, aria-labelledby and aria-label in step with state.

No custom key handling; Tab and the native activation keys do the work.

Motion #

It declares no animation in its component source. Any transition comes from its stylesheet, which uses the duration tokens that collapse to instant under prefers-reduced-motion.