Order Summary

Pro

The 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.

Order summary

4 items
  • Retro Sneakers2
    Retro Sneakers
    Size 10 · Red
    $64.00
  • Chrono Watch
    Chrono Watch
    40mm · Leather
    $78.00
  • Studio Headphones
    Studio Headphones
    Black · Over-ear
    $149.00
Subtotal
$291.00
Shipping
Free
Estimated tax
$23.28
Discount (WELCOME10)
-$29.10
Total
$285.18

Taxes and shipping calculated at checkout.

Installation#

# One-time setup (tokens + lib helpers)npx koalaui-cli@latest init# Activate your Pro license (once per machine)npx koalaui-cli@latest login <key># Add this component (its dependencies come along)npx koalaui-cli@latest add order-summary

Usage#

This example is part of Koala UI Pro

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.

Your cart
4 items
  • Retro Sneakers2
    Retro Sneakers
    Size 10 · Red
    $64.00
  • Chrono Watch
    Chrono Watch
    40mm · Leather
    $78.00
  • Studio Headphones
    Studio Headphones
    Black · Over-ear
    $149.00

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.

Summary

Review your items carefully before proceeding to checkout.

  • Retro Sneakers
    Retro Sneakers
    Size 10 · Red
    $64.00
  • Chrono Watch
    Chrono Watch
    40mm · Leather
    $78.00
  • Studio Headphones
    Studio Headphones
    Black · Over-ear
    $149.00
Subtotal
$291.00
Shipping
Free
Total
$291.00

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.

Subtotal
$291.00
Shipping
Free
Estimated tax
$23.28
Store credit
-$15.00
Total due
$299.28

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.

This example is part of Koala UI Pro

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.

  • Retro Sneakers2
    Retro Sneakers
    Size 10 · Red
    $64.00
  • Chrono Watch
    Chrono Watch
    40mm · Leather
    $78.00
Subtotal
$142.00
Shipping
Free
Total
$142.00

API reference#

OrderSummary

The shell. Renders a <section> and forwards all its props. Every part accepts className, merged last.

PropTypeDefaultDescription
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.
asChildbooleanfalseRenders 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.

PropTypeDefaultDescription
asChildbooleanfalseRenders 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.

PropTypeDefaultDescription
leavingboolean-Plays the exit (collapse, fade, drift). Drop the item in onAnimationEnd, guarded to e.target === e.currentTarget.
Data attributeDescription
data-leavingPresent while the row plays its exit.

OrderSummaryItemThumbnail

The product tile: an <img> (cover-fit, outlined), a Koala glyph, or nothing. Forwards native <div> props.

PropTypeDefaultDescription
countReact.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).

PropTypeDefaultDescription
valuenumber | null-The quantity, controlled.
defaultValuenumber | null-The initial quantity, uncontrolled.
onValueChange(value: number | null) => void-Called on every committed change.
minnumber1Lowest allowed quantity.
maxnumber-Highest allowed quantity.
aria-labelstring"Quantity"The field's accessible name.

OrderSummaryItemRemove

The remove button: a destructiveGhost icon Button with a trash glyph. Wire onClick; forwards native <button> props.

PropTypeDefaultDescription
aria-labelstring"Remove item"The button's accessible name.

OrderSummaryPromo

A band for a promo InputGroup (field plus Apply). Forwards native <div> props.

PropTypeDefaultDescription
size"sm" | "md" | "lg""lg"Control size imposed on the field and button, in line with the checkout CTA.
Data attributeDescription
data-control-sizeThe 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.

PropTypeDefaultDescription
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.

PropTypeDefaultDescription
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.

PropTypeDefaultDescription
size"sm" | "md" | "lg""lg"Control size imposed on the buttons inside.
Data attributeDescription
data-control-sizeThe imposed size.

FAQ#

Because that's what they are semantically. The items are a list of products (OrderSummaryItems renders a <ul> of <li> rows), and the totals are label/value pairs (OrderSummaryTotals renders a <dl> with <dt> labels and <dd> values). Screen readers announce them correctly with no extra ARIA.