import { Fragment } from "react";
import type { ReactNode } from "react";
import type { CheckRun, PatientDetail } from "../../api/types";
import { formatDate } from "../../flow";
import { headerLine, statCells } from "../../logic/patient-detail";
import { patientStatePill } from "../../logic/pills";
import { cn } from "../kit";
import { Pill } from "../Pill";
import { CopyButton } from "./bits";
import { PatientActions } from "./PatientActions";
const Sep = () => (
<span aria-hidden="true" className="text-line-strong max-sm:hidden">
•
</span>
);
/** The name large, a quiet contact line with copy buttons under it, and how the clinician has the patient on the right. */
export function PatientHeader({ patient, clinicName }: { patient: PatientDetail; clinicName: string }) {
const born = patient.dateOfBirth ? formatDate(patient.dateOfBirth) : null;
const items: ReactNode[] = [];
if (patient.phone)
items.push(
<span className="inline-flex items-center gap-1">
<a href={`tel:${patient.phone.replace(/[^\d+]/g, "")}`} className="text-body tabular-nums no-underline hover:text-ink hover:underline hover:decoration-line hover:underline-offset-4">
{patient.phone}
</a>
<CopyButton value={patient.phone} label="Copy phone number" />
</span>,
);
for (const part of headerLine(patient, clinicName))
items.push(
born && part === `Born ${born}` ? (
<span className="inline-flex items-center gap-1">
{part}
<CopyButton value={born} label="Copy date of birth" />
</span>
) : (
<span>{part}</span>
),
);
return (
<header className="flex flex-wrap items-end justify-between gap-x-5 gap-y-3 pb-[22px] shadow-[inset_0_-1px_0_var(--color-hairline)]">
<div className="flex min-w-0 flex-col gap-2">
<h1 className="m-0 text-[28px] leading-[34px] font-semibold tracking-[-0.02em] text-ink max-sm:text-[24px] max-sm:leading-[30px]">
{patient.name}
{patient.age !== null && <span className="font-normal text-muted">, {patient.age}</span>}
</h1>
<p className="m-0 flex min-h-6 flex-wrap items-center gap-x-2.5 gap-y-1 text-[14px] text-muted max-sm:gap-x-4">
{items.map((item, i) => (
<Fragment key={i}>
{i > 0 && <Sep />}
{item}
</Fragment>
))}
</p>
</div>
<Pill pill={patientStatePill(patient)} />
</header>
);
}
/** Four label and value pairs from what the page already loaded, no boxes, and the actions beside them. */
export function StatRow({ patient, check, checkLoading }: { patient: PatientDetail; check: CheckRun | null; checkLoading: boolean }) {
const cells = statCells(patient, check, checkLoading);
return (
<section aria-label="At a glance" className="flex flex-wrap items-end justify-between gap-x-6 gap-y-5">
<dl className="m-0 grid min-w-0 grid-cols-2 gap-x-6 gap-y-4 sm:flex sm:flex-wrap sm:gap-x-11">
{cells.map((c) => {
const quiet = c.value === "Not shared";
return (
<div key={c.label} className="flex min-w-0 flex-col gap-1.5">
<dt className="text-[13px] leading-[18px] text-muted">{c.label}</dt>
<dd className="m-0 flex min-w-0 flex-col gap-0.5">
<span className={cn("text-[17px] leading-6 font-medium tabular-nums sm:text-[19px]", quiet ? "text-subtle" : "text-ink")}>{c.value}</span>
<span className="text-[12.5px] leading-[18px] text-subtle">{c.note}</span>
</dd>
</div>
);
})}
</dl>
<PatientActions patient={patient} />
</section>
);
}