mirror of
https://github.com/MBombeck/HealthLog.git
synced 2026-11-08 20:42:43 +00:00
fix(medications): drop the duplicated overdue line below the streak row
The injection/GLP-1 card showed an overdue dose twice: once on the next-intake value line (the destructive escalation with the due time) and again as the open-cycle status line below the compliance bars. The cycle line's missed tier is retired; the due-today tier stays. The reserved min-h slot in the shared card body is untouched, so card heights stay symmetric across medication types.
This commit is contained in:
1 parent
53f84abfbb
commit
d323d01c93
8 files changed
+22
-39
No files matched your search
@@ -870,7 +870,6 @@
|
||||
"dayStreak": "Tage Serie",
|
||||
"dayStreakOne": "Tag Serie",
|
||||
"cycleDueToday": "Heute fällig",
|
||||
"cycleOverdue": "Überfällig",
|
||||
"cycleNoClosedCycles": "Noch keine abgeschlossenen Dosiszyklen",
|
||||
"taken": "Genommen",
|
||||
"skipped": "Übersprungen",
|
||||
|
||||
@@ -870,7 +870,6 @@
|
||||
"dayStreak": "day streak",
|
||||
"dayStreakOne": "day streak",
|
||||
"cycleDueToday": "Due today",
|
||||
"cycleOverdue": "Overdue",
|
||||
"cycleNoClosedCycles": "No closed dose cycles yet",
|
||||
"taken": "Taken",
|
||||
"skipped": "Skipped",
|
||||
|
||||
@@ -870,7 +870,6 @@
|
||||
"dayStreak": "días de racha",
|
||||
"dayStreakOne": "día de racha",
|
||||
"cycleDueToday": "Pendiente hoy",
|
||||
"cycleOverdue": "Atrasada",
|
||||
"cycleNoClosedCycles": "Aún no hay ciclos de dosis completados",
|
||||
"taken": "Tomada",
|
||||
"skipped": "Omitida",
|
||||
|
||||
@@ -870,7 +870,6 @@
|
||||
"dayStreak": "jours de série",
|
||||
"dayStreakOne": "jour de série",
|
||||
"cycleDueToday": "À prendre aujourd'hui",
|
||||
"cycleOverdue": "En retard",
|
||||
"cycleNoClosedCycles": "Aucun cycle de dose terminé pour l'instant",
|
||||
"taken": "Pris",
|
||||
"skipped": "Sauté",
|
||||
|
||||
@@ -870,7 +870,6 @@
|
||||
"dayStreak": "giorni di serie",
|
||||
"dayStreakOne": "giorno di serie",
|
||||
"cycleDueToday": "In scadenza oggi",
|
||||
"cycleOverdue": "In ritardo",
|
||||
"cycleNoClosedCycles": "Ancora nessun ciclo di dose completato",
|
||||
"taken": "Assunta",
|
||||
"skipped": "Saltata",
|
||||
|
||||
@@ -870,7 +870,6 @@
|
||||
"dayStreak": "dni serii",
|
||||
"dayStreakOne": "dzień serii",
|
||||
"cycleDueToday": "Termin dzisiaj",
|
||||
"cycleOverdue": "Zaległa",
|
||||
"cycleNoClosedCycles": "Brak zakończonych cykli dawkowania",
|
||||
"taken": "Przyjęte",
|
||||
"skipped": "Pominięte",
|
||||
|
||||
@@ -288,7 +288,10 @@ describe("medication cycle status — open-cycle line", () => {
|
||||
expect(html).toContain("lucide-calendar-clock");
|
||||
});
|
||||
|
||||
it("missed reads the destructive overdue line", () => {
|
||||
it("missed renders nothing — the overdue escalation already reads on the next-intake line", () => {
|
||||
// v1.27.5 — the card's next-intake value line carries the destructive
|
||||
// overdue escalation; a second overdue line below the streak row doubled
|
||||
// the signal and is retired.
|
||||
const html = render(
|
||||
<MedicationCycleStatus
|
||||
cycle={{
|
||||
@@ -299,9 +302,7 @@ describe("medication cycle status — open-cycle line", () => {
|
||||
}}
|
||||
/>,
|
||||
);
|
||||
expect(html).toContain("Overdue");
|
||||
expect(html).toContain("text-destructive");
|
||||
expect(html).toContain("lucide-triangle-alert");
|
||||
expect(html).toBe("");
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { AlertTriangle, CalendarClock, CircleDashed } from "lucide-react";
|
||||
import { CalendarClock, CircleDashed } from "lucide-react";
|
||||
|
||||
import type { CurrentCycle } from "@/lib/analytics/compliance";
|
||||
import { useTranslations } from "@/lib/i18n/context";
|
||||
@@ -20,13 +20,15 @@ interface MedicationCycleStatusProps {
|
||||
*
|
||||
* The calm `on_track` "next dose in N days" phrasing is intentionally NOT
|
||||
* rendered here: the upcoming-dose timing already reads on the card's
|
||||
* next-intake slot at the top, so repeating it would be a duplicate. Only the
|
||||
* actionable due / overdue tiers (and the neutral no-closed-cycles note) earn
|
||||
* this line.
|
||||
* next-intake slot at the top, so repeating it would be a duplicate. The same
|
||||
* reasoning retired the `missed` tier in v1.27.5 — an overdue dose already
|
||||
* escalates on the next-intake value line (the destructive "Überfällig" /
|
||||
* "Stark überfällig" row), so a second overdue line below the streak row
|
||||
* doubled the signal. Only the `due` tier (and the neutral no-closed-cycles
|
||||
* note) earns this line.
|
||||
*
|
||||
* Driven by `currentCycle.state` (`on_track` / `due` / `missed` / `none`) plus
|
||||
* `hasClosedCycles`. Colour follows the same semantic ramp the status pill
|
||||
* uses (warning / destructive) and pairs every tier with a Lucide glyph so
|
||||
* `hasClosedCycles`. The due tier uses the warning tone + a Lucide glyph so
|
||||
* colour-blind users can disambiguate — WCAG 1.4.1 (Use of Color). It
|
||||
* complements the compliance number; it does not replace it.
|
||||
*/
|
||||
@@ -49,31 +51,17 @@ export function MedicationCycleStatus({ cycle }: MedicationCycleStatusProps) {
|
||||
);
|
||||
}
|
||||
|
||||
// on_track — the next dose simply hasn't come round yet. The upcoming-dose
|
||||
// timing already reads on the card's next-intake slot at the top, so a second
|
||||
// "next dose in N days" line here is a duplicate. Render nothing for the
|
||||
// on-track case; only the actionable due / overdue tiers earn this line.
|
||||
if (cycle.state !== "missed" && cycle.state !== "due") return null;
|
||||
|
||||
let tone: string;
|
||||
let icon: React.ReactNode;
|
||||
let label: string;
|
||||
|
||||
if (cycle.state === "missed") {
|
||||
tone = "text-destructive";
|
||||
icon = <AlertTriangle className="size-3.5 shrink-0" aria-hidden="true" />;
|
||||
label = t("medications.cycleOverdue");
|
||||
} else {
|
||||
// due
|
||||
tone = "text-warning";
|
||||
icon = <CalendarClock className="size-3.5 shrink-0" aria-hidden="true" />;
|
||||
label = t("medications.cycleDueToday");
|
||||
}
|
||||
// on_track — the next dose simply hasn't come round yet; the upcoming-dose
|
||||
// timing already reads on the card's next-intake slot at the top. missed —
|
||||
// the overdue escalation already reads on that same next-intake value line
|
||||
// (destructive tone + glyph), so a second overdue line here doubled it.
|
||||
// Both render nothing; only the due tier earns this line.
|
||||
if (cycle.state !== "due") return null;
|
||||
|
||||
return (
|
||||
<p className={`flex items-center gap-1.5 text-xs font-medium ${tone}`}>
|
||||
{icon}
|
||||
{label}
|
||||
<p className="text-warning flex items-center gap-1.5 text-xs font-medium">
|
||||
<CalendarClock className="size-3.5 shrink-0" aria-hidden="true" />
|
||||
{t("medications.cycleDueToday")}
|
||||
</p>
|
||||
);
|
||||
}
|
||||
Reference in new issue
Block a user