Detail page
A page about one thing, with its main column and an aside holding its one primary action.
A detail page is about one thing, such as a customer or a price list: its title over a hairline, the main column, and an aside with the one primary action and lists of links. Use DetailPage for any page that shows and acts on a single record.
The parts
The title
titleover a hairline, with optionalbreadcrumbs, abadgeand a one-linedescription, laid out by aPageHeader.The main column
The page's
children: the record itself, such as the coffees and prices on a price list.The aside
The one primary
action, full width at its top, then lists of links:DetailPage.Linksinaside.
The aside sits beside the main column from 1100px of the page's column and drops below it under that, so the primary action is never more than a scroll away.
A price list for cafés, with its one action and a list of resources:
import type { ReactElement } from "react";
import { Text } from "@butteryui/core";
import { Button, DetailPage } from "@butteryui/react";
export function PriceList(): ReactElement {
return (
<DetailPage
title="Café price list"
description="Wholesale, by the 5 kg bag"
action={<Button variant="primary">Send to cafés</Button>}
aside={
<DetailPage.Links
title="Resources"
links={[{ label: "How prices are set", href: "/help/prices" }]}
/>
}
>
<Text variant="body">Twelve coffees, from 42 to 58 dollars a bag.</Text>
</DetailPage>
);
}DetailPage
When to use it
Use it for
- One plan, price list, product or integration, with its main facts and one thing to do about it
- A page reached from a list or a catalog, under breadcrumbs
Not for
- A record with tabs of related lists, such as a customer: use AppPage with an aside
- A page of settings: use SettingsPage
Examples
Green coffee lot
A green coffee lot: what's left in the main column, reordering it the aside's primary action.
Nyeri AA
Washed, from the Gatomboya cooperative
180 kg on hand
About nine days of roasting at this week's pace.
Plan detail
One plan's page: its price in the main column, choosing it the aside's one primary action.
Roaster plan
Billed monthly
$39 a month
For a roastery selling to cafés as well as its own customers.
Variants and states
A price list
The aside sits beside the main column from 1100px of column, and under it below that.
Café price list
Wholesale, by the 5 kg bag
$18.40 a kilo
Nyeri AA and Huila, roasted to order and shipped on Tuesdays.
Props
DetailPage
| Prop | Type | Default | Description |
|---|---|---|---|
titlerequired | string | What the page is about, its h1. | |
breadcrumbs | ReactNode | The trail of pages above it, a Breadcrumbs. | |
badge | ReactNode | A ScopeBadge after the title. | |
description | ReactNode | One line under the title, such as how it's billed. | |
actions | ReactNode | Actions at the end of the title's row: PageHeader.Actions. Most detail pages put their action in the aside. | |
action | ReactNode | The aside's one primary action, full width at its top, such as a Button variant="primary". | |
aside | ReactNode | The aside's lists: DetailPage.Links. | |
asideLabel | string | "Details" | Names the aside's landmark. Defaults to "Details". |
fill | boolean | false | Gives the page's last block the rest of the height, so a table scrolls inside it with its header
sticky while the header and filters stay put; the table's pagination then keeps floating lanes above
it. Defaults to false. |
footer | ReactNode | A small footer that ends the page under a hairline, such as a feedback link and the keyboard
shortcuts, in body-sm and text-secondary. |
It also takes Omit<ComponentPropsWithRef<"main">, "title">.
DetailPage.Links
| Prop | Type | Default | Description |
|---|---|---|---|
titlerequired | string | The list's heading, an h2 in title-sm, over a hairline. | |
linksrequired | readonly DetailPageLink[] | Its links, in the body-sm size and primary. | |
onNavigate | ((href: string, event: MouseEvent<HTMLAnchorElement>) => void) | Runs as a link is followed, where a router can take over. A click that opens the page elsewhere, in a new tab or window, is left to the browser. |
It also takes Omit<ComponentPropsWithRef<"section">, "title">.
DetailPageLink
One link in a `DetailPage.Links` list.
| Field | Type | Default | Description |
|---|---|---|---|
labelrequired | string | What it says. | |
hrefrequired | string | Where it goes. |
Accessibility
The page's main landmark, its title the h1. The aside is a complementary landmark named by asideLabel; each list of links is a region named by its h2. Each link's target is at least 24px tall.
| Keys | What they do |
|---|---|
| Enter | Follows the focused link in the aside's lists |
Motion
It doesn't move.
With reduced motion: Nothing changes.
Layout
It's an AppPage, at most 1280px wide (--bt-w-app-page), its header over a hairline. From 1100px of column the 320px aside (--bt-w-aside) sits beside the main column, 32 apart, and under it otherwise; the aside's primary action is full width, its lists sit 24 apart, and each link is at least 24px tall.
Related
Related
- Page header
The top of an app page, with its title, an optional value and the page's actions.
- DataTable
A table of records: columns with minimum widths and shares, selection, sorting, row actions, a sticky header and first column, skeleton rows and pagination.