Order Summary
ProThe checkout and cart order read-out. One composable card that stacks line items, a promo-code band and a totals breakdown, with every price on tabular-nums so the column never jitters.
Installation#
Usage#
The preview is yours to explore. Its code comes with a Pro license, paid once and used in every project.
Have a license? Unlock it here
Anatomy#
OrderSummary is a multi-part component: one tv recipe whose slots flow to every named part through React Context. Compose only the bands you need, in any order. There are no internal dividers or boxing: the bands and the line items are simply set apart by whitespace (the house minimal style), so the summary reads clean on any surface. The card variant adds an outer border and insets the content with padding; plain sits flush.
import {
OrderSummary,
OrderSummaryHeader,
OrderSummaryTitle,
OrderSummaryItems,
OrderSummaryItem,
OrderSummaryItemThumbnail,
OrderSummaryItemContent,
OrderSummaryItemName,
OrderSummaryItemOptions,
OrderSummaryItemPrice,
OrderSummaryItemActions,
OrderSummaryItemQuantity,
OrderSummaryItemRemove,
OrderSummaryPromo,
OrderSummaryTotals,
OrderSummaryRow,
OrderSummaryTotal,
OrderSummaryFooter,
} from "@/components/ui/order-summary"
<OrderSummary>
<OrderSummaryHeader>
<OrderSummaryTitle />
</OrderSummaryHeader>
<OrderSummaryItems>
<OrderSummaryItem>
<OrderSummaryItemThumbnail />
<OrderSummaryItemContent>
<OrderSummaryItemName />
<OrderSummaryItemOptions />
</OrderSummaryItemContent>
<OrderSummaryItemPrice />
<OrderSummaryItemActions>
<OrderSummaryItemQuantity />
<OrderSummaryItemRemove />
</OrderSummaryItemActions>
</OrderSummaryItem>
</OrderSummaryItems>
<OrderSummaryPromo>…</OrderSummaryPromo>
<OrderSummaryTotals>
<OrderSummaryRow label="…">…</OrderSummaryRow>
<OrderSummaryTotal label="…">…</OrderSummaryTotal>
</OrderSummaryTotals>
<OrderSummaryFooter>…</OrderSummaryFooter>
</OrderSummary>Line items#
Each OrderSummaryItem is a <li> laying out a thumbnail, the name + options, and the line price. The thumbnail holds an <img> (auto object-cover with the DS image-outline) or a Koala glyph, and its count prop drops a quantity pill on the corner. The name truncates rather than shoving the price off the row, and the price is tabular-nums so the column stays aligned.
Shopping cart#
Compose OrderSummaryItemActions after the price to turn the read-out into a shopping cart. It holds OrderSummaryItemQuantity (the canonical NumberInput in its compact inline − value + form) and OrderSummaryItemRemove (the canonical Button in its quiet destructiveGhost trash form). Wire their onValueChange / onClick to your cart state; here the line prices and the subtotal recompute live. Removing a row sets leaving on its OrderSummaryItem so it collapses and drifts out before it's dropped from state (the rows below glide up, no jump); clearing the cart shows the empty state.
Totals & tones#
OrderSummaryTotals renders a semantic <dl>. Each OrderSummaryRow takes a label (the <dt>) and its value as children (the <dd>). The tone prop accents the value: discount greens a credit, muted softens a "Free" or "calculated later" placeholder. OrderSummaryTotal is the emphasized grand total, set apart from the rows by extra whitespace.
Promo code#
OrderSummaryPromo is a band you fill with the canonical InputGroup: a field joined to an Apply button in one seamless shell. Nothing is re-styled inline; the summary composes the real controls, so the promo row stays in lockstep with the input family.
The band imposes the big control tier on what you put in it (size="lg", 40px), the way Form does for its fields: a promo code is a real form control, not a table filter, so it matches the Checkout button under the totals instead of shrinking to the ambient density. Pass size for a different tier; a size on the control itself still wins.
The preview is yours to explore. Its code comes with a Pro license, paid once and used in every project.
Have a license? Unlock it here
Variants & density#
The default card variant is the bordered checkout sidebar. plain drops the frame so the bands sit flush on whatever surface holds them: a page column or a Drawer. Density is Koala's spacing axis: comfortable suits a checkout page; compact (the default with no DensityProvider) tightens the padding and shrinks the thumbnails for a mini-cart. Set it per instance or once on a provider.
API reference#
OrderSummary
The shell. Renders a <section> and forwards all its props. Every part accepts className, merged last.
| Prop | Type | Default | Description |
|---|---|---|---|
| variant | "card" | "plain" | "card" | card adds a ring and insets the content; plain sits flush. |
| density | "comfortable" | "compact" | - | Gaps, padding and thumbnail size. Inherits the nearest DensityProvider (compact with none) when unset. |
| asChild | boolean | false | Renders the child as the shell via Radix Slot. |
OrderSummaryHeader
The title band: a title on the left, an item-count Badge or Edit link on the right. Forwards native <div> props.
OrderSummaryTitle
The summary's title. Forwards native <div> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| asChild | boolean | false | Renders the child (an <h2>, an <h3>) as a real heading. |
OrderSummaryItems
The line items, a <ul>; rows stack on whitespace, no dividers.
OrderSummaryItem
One cart line, an <li>. Forwards all its props.
| Prop | Type | Default | Description |
|---|---|---|---|
| leaving | boolean | - | Plays the exit (collapse, fade, drift). Drop the item in onAnimationEnd, guarded to e.target === e.currentTarget. |
| Data attribute | Description |
|---|---|
| data-leaving | Present while the row plays its exit. |
OrderSummaryItemThumbnail
The product tile: an <img> (cover-fit, outlined), a Koala glyph, or nothing. Forwards native <div> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| count | React.ReactNode | - | A quantity pill on the corner. Omit for single-quantity lines. |
OrderSummaryItemContent
The name and options column; it fills so the price rides the right edge. Forwards native <div> props.
OrderSummaryItemName
The product name; truncates. Forwards native <div> props.
OrderSummaryItemOptions
The muted options line, e.g. Size M · Oat. Forwards native <div> props.
OrderSummaryItemPrice
The line total, tabular-nums, never wrapping under the name. Forwards native <div> props.
OrderSummaryItemActions
Trailing controls for an editable line: the quantity stepper and remove button. Forwards native <div> props.
OrderSummaryItemQuantity
The quantity stepper: a small inline NumberInput (minus, value, plus).
| Prop | Type | Default | Description |
|---|---|---|---|
| value | number | null | - | The quantity, controlled. |
| defaultValue | number | null | - | The initial quantity, uncontrolled. |
| onValueChange | (value: number | null) => void | - | Called on every committed change. |
| min | number | 1 | Lowest allowed quantity. |
| max | number | - | Highest allowed quantity. |
| aria-label | string | "Quantity" | The field's accessible name. |
OrderSummaryItemRemove
The remove button: a destructiveGhost icon Button with a trash glyph. Wire onClick; forwards native <button> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| aria-label | string | "Remove item" | The button's accessible name. |
OrderSummaryPromo
A band for a promo InputGroup (field plus Apply). Forwards native <div> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| size | "sm" | "md" | "lg" | "lg" | Control size imposed on the field and button, in line with the checkout CTA. |
| Data attribute | Description |
|---|---|
| data-control-size | The imposed size. |
OrderSummaryTotals
The breakdown, a <dl>.
OrderSummaryRow
One subtotal, shipping, tax or discount line: a <dt> label and a <dd> value. Forwards native <div> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| label* | React.ReactNode | - | The label, e.g. Subtotal. |
| children* | React.ReactNode | - | The value, set tabular-nums. |
| tone | "default" | "discount" | "muted" | "default" | discount greens the value; muted softens it. |
OrderSummaryTotal
The emphasized grand total. Forwards native <div> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| label* | React.ReactNode | - | The label, e.g. Total. |
| children* | React.ReactNode | - | The value. |
OrderSummaryFooter
A band for the checkout Button and a trust note. Forwards native <div> props.
| Prop | Type | Default | Description |
|---|---|---|---|
| size | "sm" | "md" | "lg" | "lg" | Control size imposed on the buttons inside. |
| Data attribute | Description |
|---|---|
| data-control-size | The imposed size. |