Update new check for max daily dose waring and error

This commit is contained in:
2026-02-08 12:08:18 +00:00
parent 7f8503387c
commit c41db99cba
4 changed files with 89 additions and 15 deletions

View File

@@ -99,13 +99,19 @@ const DaySchedule: React.FC<DayScheduleProps> = ({
// Get template day for comparison
const templateDay = days.find(d => d.isTemplate);
// Calculate daily total
const dayTotal = day.doses.reduce((sum, dose) => sum + (parseFloat(dose.ldx) || 0), 0);
// Check for daily total warnings/errors
const isDailyTotalError = dayTotal > 200;
const isDailyTotalWarning = !isDailyTotalError && dayTotal > 70;
// Calculate differences for deviation days
let doseCountDiff = 0;
let totalMgDiff = 0;
if (!day.isTemplate && templateDay) {
doseCountDiff = day.doses.length - templateDay.doses.length;
const dayTotal = day.doses.reduce((sum, dose) => sum + (parseFloat(dose.ldx) || 0), 0);
const templateTotal = templateDay.doses.reduce((sum, dose) => sum + (parseFloat(dose.ldx) || 0), 0);
totalMgDiff = dayTotal - templateTotal;
}
@@ -153,7 +159,7 @@ const DaySchedule: React.FC<DayScheduleProps> = ({
>
<Badge
variant="outline"
className={`text-xs ${doseCountDiff > 0 ? 'bg-blue-100 dark:bg-blue-900/60 dark:text-blue-200' : 'bg-orange-100 dark:bg-orange-900/60 dark:text-orange-200'}`}
className={`text-xs ${doseCountDiff > 0 ? 'badge-trend-up' : 'badge-trend-down'}`}
>
{doseCountDiff > 0 ? <TrendingUp className="h-3 w-3 inline mr-1" /> : <TrendingDown className="h-3 w-3 inline mr-1" />}
{day.doses.length} {day.doses.length === 1 ? t('dose') : t('doses')}
@@ -180,27 +186,59 @@ const DaySchedule: React.FC<DayScheduleProps> = ({
>
<Badge
variant="outline"
className={`text-xs ${totalMgDiff > 0 ? 'bg-blue-100 dark:bg-blue-900/60 dark:text-blue-200' : 'bg-orange-100 dark:bg-orange-900/60 dark:text-orange-200'}`}
className={`text-xs ${
isDailyTotalError
? 'badge-error'
: isDailyTotalWarning
? 'badge-warning'
: totalMgDiff > 0
? 'badge-trend-up'
: 'badge-trend-down'
}`}
>
{totalMgDiff > 0 ? <TrendingUp className="h-3 w-3 inline mr-1" /> : <TrendingDown className="h-3 w-3 inline mr-1" />}
{day.doses.reduce((sum, dose) => sum + (parseFloat(dose.ldx) || 0), 0).toFixed(1)} mg
{!isDailyTotalError && !isDailyTotalWarning && (totalMgDiff > 0 ? <TrendingUp className="h-3 w-3 inline mr-1" /> : <TrendingDown className="h-3 w-3 inline mr-1" />)}
{dayTotal.toFixed(1)} mg
</Badge>
</button>
</TooltipTrigger>
<TooltipContent>
<p className="text-xs">
{totalMgDiff > 0 ? '+' : ''}{totalMgDiff.toFixed(1)} mg {t('comparedToRegularPlan')}
{isDailyTotalError
? `${t('errorDailyTotalAbove200mg').replace('{{total}}', dayTotal.toFixed(1))}`
: isDailyTotalWarning
? `${t('warningDailyTotalAbove70mg').replace('{{total}}', dayTotal.toFixed(1))}`
: `${totalMgDiff > 0 ? '+' : ''}${totalMgDiff.toFixed(1)} mg ${t('comparedToRegularPlan')}`
}
</p>
</TooltipContent>
</Tooltip>
) : (
<Badge variant="outline" className="text-xs">
{day.doses.reduce((sum, dose) => sum + (parseFloat(dose.ldx) || 0), 0).toFixed(1)} mg
<Badge
variant="outline"
className={`text-xs ${
isDailyTotalError
? 'badge-error'
: isDailyTotalWarning
? 'badge-warning'
: ''
}`}
>
{dayTotal.toFixed(1)} mg
</Badge>
)}
</CollapsibleCardHeader>
{!collapsedDays.has(day.id) && (
<CardContent className="space-y-3">
{/* Daily total warning/error box */}
{(isDailyTotalWarning || isDailyTotalError) && (
<div className={`p-3 rounded-md text-sm ${isDailyTotalError ? 'error-bg-box' : 'warning-bg-box'}`}>
{formatText(isDailyTotalError
? t('errorDailyTotalAbove200mg').replace('{{total}}', dayTotal.toFixed(1))
: t('warningDailyTotalAbove70mg').replace('{{total}}', dayTotal.toFixed(1))
)}
</div>
)}
{/* Dose table header */}
<div className="grid grid-cols-[120px_1fr_auto] sm:grid-cols-[120px_1fr_auto_auto] gap-2 text-sm font-medium text-muted-foreground">
<div className="flex items-center gap-1">
@@ -247,6 +285,23 @@ const DaySchedule: React.FC<DayScheduleProps> = ({
// Check for dose > 70 mg
const isHighDose = parseFloat(dose.ldx) > 70;
// Determine the error/warning message priority:
// 1. Daily total error (> 200mg) - ERROR
// 2. Daily total warning (> 70mg) - WARNING
// 3. Individual dose warning (zero dose or > 70mg) - WARNING
let doseErrorMessage;
let doseWarningMessage;
if (isDailyTotalError) {
doseErrorMessage = formatText(t('errorDailyTotalAbove200mg').replace('{{total}}', dayTotal.toFixed(1)));
} else if (isDailyTotalWarning) {
doseWarningMessage = formatText(t('warningDailyTotalAbove70mg').replace('{{total}}', dayTotal.toFixed(1)));
} else if (isZeroDose) {
doseWarningMessage = formatText(t('warningZeroDose'));
} else if (isHighDose) {
doseWarningMessage = formatText(t('warningDoseAbove70mg'));
}
return (
<div key={dose.id} className="space-y-2">
<div className="grid grid-cols-[120px_1fr_auto] sm:grid-cols-[120px_1fr_auto_auto] gap-2 items-center">
@@ -266,13 +321,10 @@ const DaySchedule: React.FC<DayScheduleProps> = ({
max={200}
//unit="mg"
required={true}
warning={isZeroDose || isHighDose}
errorMessage={formatText(t('errorNumberRequired'))}
warningMessage={
isZeroDose ? formatText(t('warningZeroDose'))
: isHighDose ? formatText(t('warningDoseAbove70mg'))
: undefined // should not happen since warning is false
}
error={isDailyTotalError}
warning={isDailyTotalWarning || isZeroDose || isHighDose}
errorMessage={doseErrorMessage || formatText(t('errorNumberRequired'))}
warningMessage={doseWarningMessage}
inputWidth="w-[72px]"
/>
<div className="flex gap-2 sm:contents">