50 lines
2.2 KiB
TypeScript
50 lines
2.2 KiB
TypeScript
/*
|
|
* Main column plus a fixed support rail.
|
|
*
|
|
* The rail is what stops a page being empty and the main column is what stops
|
|
* it being thin: an account with one instance used to render a third of a row
|
|
* of summary and nothing else. The rail carries what is true regardless of how
|
|
* many instances exist, so the page has a floor.
|
|
*
|
|
* It collapses below lg in source order, which puts the main column first on a
|
|
* phone. Nothing is hidden at any width if content only fits on a desktop it
|
|
* does not belong in the rail.
|
|
*/
|
|
export function PageFrame({ children, aside }: { children: React.ReactNode; aside?: React.ReactNode }) {
|
|
if (!aside) return <div className="grid gap-5">{children}</div>;
|
|
|
|
return (
|
|
<div className="grid items-start gap-5 lg:grid-cols-[minmax(0,1fr)_320px]">
|
|
<div className="grid min-w-0 gap-4">{children}</div>
|
|
<aside className="grid gap-3.5">{aside}</aside>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
/** One card in the rail. Title is a label, not a heading you read for pleasure. */
|
|
export function RailCard({ title, count, children }: { title: string; count?: number | string; children: React.ReactNode }) {
|
|
return (
|
|
<section className="grid gap-2.5 rounded border border-rule bg-panel p-3.5">
|
|
<header className="flex items-baseline justify-between gap-2.5">
|
|
<h2 className="font-mono text-[0.66rem] font-normal uppercase tracking-[0.12em] text-ink-3">{title}</h2>
|
|
{count !== undefined && <b className="text-[0.95rem] font-extrabold tabular-nums">{count}</b>}
|
|
</header>
|
|
{children}
|
|
</section>
|
|
);
|
|
}
|
|
|
|
/** Key/value rows for the rail. Values are mono so numbers line up. */
|
|
export function RailFacts({ rows }: { rows: { label: string; value: React.ReactNode }[] }) {
|
|
return (
|
|
<dl className="grid gap-1.5">
|
|
{rows.map((r) => (
|
|
<div key={r.label} className="flex justify-between gap-2.5 text-[0.82rem]">
|
|
<dt className="text-ink-3">{r.label}</dt>
|
|
<dd className="m-0 truncate font-mono text-[0.78rem] tabular-nums text-ink">{r.value}</dd>
|
|
</div>
|
|
))}
|
|
</dl>
|
|
);
|
|
}
|