chadtmiller.com/pds.js
An atproto PDS in JavaScript, for Cloudflare Workers and Node
0
0
import { ChevronLeftIcon } from 'lucide-react';
import { Link } from '#/components/atoms/link.jsx';
import { MEASURE } from '#/lib/layout.js';
import { cn } from '#/lib/utils.js';
/**
* What a detail screen is about, fixed above its body: the title, one line
* of facts under it, and the one action on the right. A
* pull request, a commit, an issue and a run all open on this, so a reader
* meets one heading at one size wherever they land.
*
* The heading sits in the reading column unless `wide`, for a screen whose
* body takes the window. `rule` closes it with a rule, drawn to the column
* or, wide, to the window. `back` names where the reader came from, on a line
* above the title, for a page whose parent is not the section tab: a commit
* reached from a pull request, a form. `meta` is the line under the title:
* who, when, which sha. `children` is anything else the head carries, such
* as the tabs a pull request opens on.
* @param {{title: import('react').ReactNode, back?: {href: string, label: string}, meta?: import('react').ReactNode, actions?: import('react').ReactNode, wide?: boolean, rule?: boolean, className?: string, children?: import('react').ReactNode}} props
*/
export function PageHead({
title,
back,
meta,
actions,
wide = false,
rule = false,
className,
children,
}) {
return (
<div
className={cn(
'shrink-0 px-(--gutter) pt-4',
wide && 'pb-3.5',
wide && rule && 'border-border border-b',
className,
)}
>
<div
className={cn(
!wide && `${MEASURE} pb-3.5`,
!wide && rule && 'border-border border-b',
)}
>
{back && (
<Link
href={back.href}
className="mb-1.5 flex max-w-full items-center gap-1 text-[12.5px] text-muted-foreground no-underline hover:text-foreground hover:no-underline"
>
<ChevronLeftIcon className="size-3.5 shrink-0" />
<span className="truncate">{back.label}</span>
</Link>
)}
<div className="flex flex-wrap items-start justify-between gap-x-4 gap-y-2">
<h2 className="min-w-0 flex-1 break-words font-semibold text-[18px] leading-snug tracking-[-0.01em]">
{title}
</h2>
{actions && (
<div className="flex min-w-0 shrink-0 items-center gap-2">
{actions}
</div>
)}
</div>
{meta && (
<div className="mt-2 flex flex-wrap items-center gap-x-2.5 gap-y-1.5 text-[12.5px] text-faint">
{meta}
</div>
)}
{children}
</div>
</div>
);
}