"use client"; import { CircleCheck, CircleX, Loader, TriangleAlert } from "lucide-react"; import { PARTICULAR_CODES, type LabelCheckResult, type LabelFinding, type LabelFindingCode, } from "@/lib/label-templates/check"; import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"; export const PARTICULAR_LABELS: Record<(typeof PARTICULAR_CODES)[number], string> = { LEGAL_NAME: "Verkehrsbezeichnung", NET_QUANTITY: "Füllmenge", BEST_BEFORE: "Mindesthaltbarkeitsdatum", LOT: "Losnummer", ORIGIN: "Herkunftsland", FOOD_BUSINESS: "Name und Anschrift des Lebensmittelunternehmers", }; function formatMm(value: number): string { return `${value.toLocaleString("de-DE", { maximumFractionDigits: 2 })} mm`; } function summaryOf(result: LabelCheckResult | null, pending: boolean): string | null { if (pending) return "Das Etikett wird geprüft …"; if (!result) return null; const missing = result.gaps.length; if (missing === 0) return "Alle Pflichtangaben sind erfüllt."; return missing === 1 ? "Es fehlt 1 Pflichtangabe." : `Es fehlen ${missing} Pflichtangaben.`; } function ParticularRow({ code, gap }: { code: LabelFindingCode; gap: LabelFinding | undefined }) { const label = PARTICULAR_LABELS[code as keyof typeof PARTICULAR_LABELS]; return (
  • {gap ? ( ) : ( )} {label}:{" "} {gap ? "Fehlt" : "Erfüllt"} {gap ? {gap.detail || gap.title} : null}
  • ); } interface LabelCompliancePanelProps { result: LabelCheckResult | null; pending: boolean; error: string | null; /** `result` answers an older draft; the current one cannot be checked. */ stale?: boolean; } /** * Shows the answer of the label check: the six particulars with symbol and * word, the warnings apart (they never block printing) and the minimums the * server used. The panel decides nothing itself. */ export function LabelCompliancePanel({ result, pending, error, stale = false, }: LabelCompliancePanelProps) { const summary = stale ? "Veraltet: Dieser Stand passt nicht mehr zu deinen Eingaben." : summaryOf(result, pending); return ( Pflichtangaben {error ? (

    {error}

    ) : null}
    {summary ? (

    {pending ? : null} {summary}

    ) : null} {result ? ( <> {result.sample ? (

    Geprüft mit Beispielwerten, nicht mit einer echten Abfüllung.

    ) : null}
      {PARTICULAR_CODES.map((code) => ( gap.code === code)} /> ))}

    Mindest-x-Höhe: {formatMm(result.requirements.minXHeightMm)} {result.requirements.netQuantityMinCapHeightMm !== null ? `. Ziffernhöhe der Füllmenge: mindestens ${formatMm(result.requirements.netQuantityMinCapHeightMm)}` : ""} .

    {result.warnings.length > 0 ? (

    Hinweise (sie sperren den Druck nicht)

      {result.warnings.map((warning, index) => (
    • Hinweis: {warning.title} {warning.detail ? ( {warning.detail} ) : null}
    • ))}
    ) : null} ) : null}
    ); }