-
Notifications
You must be signed in to change notification settings - Fork 4
Description
Original Issue Body
To improve the visual density, accessibility, and professional polish of the HRM experimental analytics components, we need to address several "AI slop" indicators: unformatted raw data (long floats), poor spatial utilization, and missing semantic color coding for workout states and heart rate zones.
Below are the high-level technical recommendations and refactored code snippets to align with the repository's specified stack and Material-UI theme.
1. Refactor WorkoutSummary.tsx
The current implementation uses a generic layout. We should utilize the custom palette defined in theme.ts to color-code the workout status and improve typography weight for data readability.
// app/client/experimental/components/WorkoutSummary.tsx
'use client'
import { Card, CardContent, Typography, Grid, Box, Chip } from '@mui/material'
import { useTheme } from '@mui/material/styles'
import { formatDuration } from '@/lib/utils'
interface WorkoutSummaryProps {
duration: number
calories: number
status: 'idle' | 'running' | 'paused' | 'finished'
}
const WorkoutSummary = ({ duration, calories, status }: WorkoutSummaryProps) => {
const theme = useTheme();
// Map status to theme colors defined in theme.ts
const statusColor = theme.palette.custom[status === 'running' ? 'running' : 'idle'];
return (
<Card elevation={2}>
<CardContent>
<Box display="flex" justifyContent="space-between" alignItems="center" mb={2}>
<Typography variant="h6" fontWeight="bold">Workout Summary</Typography>
<Chip
label={status.toUpperCase()}
sx={{ backgroundColor: statusColor, color: '#fff', fontWeight: 'bold' }}
/>
</Box>
<Grid container spacing={2}>
<Grid item xs={6}>
<Typography variant="caption" color="textSecondary">Duration</Typography>
<Typography variant="h5" sx={{ fontFamily: 'Monospace' }}>
{formatDuration(duration, { unit: 'seconds', format: 'HH:MM:SS' })}
</Typography>
</Grid>
<Grid item xs={6}>
<Typography variant="caption" color="textSecondary">Calories</Typography>
<Typography variant="h5">{calories.toFixed(0)} <small>kcal</small></Typography>
</Grid>
</Grid>
</CardContent>
</Card>
)
}2. Refactor ZoneDistribution.tsx
The HTML output showed raw floating-point seconds (e.g., 0:27.713000...). We must truncate these for the UI and use a horizontal bar representation to communicate "Time in Zone" effectively.
// app/client/experimental/components/ZoneDistribution.tsx
'use client'
import { Card, CardContent, Typography, Box, LinearProgress } from '@mui/material'
import { HrZoneName } from '@/lib/workout-session-storage'
// ... existing props interface
const ZoneDistribution = ({ timeInZones, totalDuration }: ZoneDistributionProps) => {
return (
<Card elevation={2}>
<CardContent>
<Typography variant="h6" fontWeight="bold" gutterBottom>Time in Zones</Typography>
{Object.entries(timeInZones)
.filter(([zone]) => ![HrZoneName.NoData, HrZoneName.Unknown].includes(zone as HrZoneName))
.map(([zone, time]) => {
const percentage = totalDuration > 0 ? (time / totalDuration) * 100 : 0;
if (percentage < 1) return null; // Hide negligible data
return (
<Box key={zone} mb={2}>
<Box display="flex" justifyContent="space-between" mb={0.5}>
<Typography variant="body2" fontWeight="medium">{zone}</Typography>
<Typography variant="body2" color="textSecondary">
{Math.floor(time / 60)}m {Math.floor(time % 60)}s ({percentage.toFixed(1)}%)
</Typography>
</Box>
<LinearProgress
variant="determinate"
value={percentage}
sx={{ height: 8, borderRadius: 4 }}
/>
</Box>
);
})}
</CardContent>
</Card>
);
}3. Improve HeartRateTimeSeries.tsx
The chart is currently using a default purple stroke. For an HRM app, the line color should ideally reflect the current intensity or use a more energetic color.
- Tip: Use a
ResponsiveContainerwith a fixedminHeightto prevent layout shift. - Grid: Lighten the
CartesianGridstroke for better contrast.
Key Improvements Summary:
- Precision Control: Implemented
toFixed(0)for calories and removed long float decimals in duration to reduce visual noise. - Semantic Color: Integrated the
custompalette fromtheme.tsto provide immediate visual feedback on workout state. - Accessibility: Switched to a
Gridlayout with explicitcaptionlabels, ensuring screen readers clearly associate labels with values.
To improve the visual density, accessibility, and professional polish of the HRM experimental analytics components, we need to address several "AI slop" indicators: unformatted raw data (long floats), poor spatial utilization, and missing semantic color coding for workout states and heart rate zones.
Below are the high-level technical recommendations and refactored code snippets to align with the repository's specified stack and Material-UI theme.
1. Refactor WorkoutSummary.tsx
The current implementation uses a generic layout. We should utilize the custom palette defined in theme.ts to color-code the workout status and improve typography weight for data readability.
// app/client/experimental/components/WorkoutSummary.tsx
'use client'
import { Card, CardContent, Typography, Grid, Box, Chip } from '@mui/material'
import { useTheme } from '@mui/material/styles'
import { formatDuration } from '@/lib/utils'
interface WorkoutSummaryProps {
duration: number
calories: number
status: 'idle' | 'running' | 'paused' | 'finished'
}
const WorkoutSummary = ({ duration, calories, status }: WorkoutSummaryProps) => {
const theme = useTheme();
// Map status to theme colors defined in theme.ts
const statusColor = theme.palette.custom[status === 'running' ? 'running' : 'idle'];
return (
<Card elevation={2}>
<CardContent>
<Box display="flex" justifyContent="space-between" alignItems="center" mb={2}>
<Typography variant="h6" fontWeight="bold">Workout Summary</Typography>
<Chip
label={status.toUpperCase()}
sx={{ backgroundColor: statusColor, color: '#fff', fontWeight: 'bold' }}
/>
</Box>
<Grid container spacing={2}>
<Grid item xs={6}>
<Typography variant="caption" color="textSecondary">Duration</Typography>
<Typography variant="h5" sx={{ fontFamily: 'Monospace' }}>
{formatDuration(duration, { unit: 'seconds', format: 'HH:MM:SS' })}
</Typography>
</Grid>
<Grid item xs={6}>
<Typography variant="caption" color="textSecondary">Calories</Typography>
<Typography variant="h5">{calories.toFixed(0)} <small>kcal</small></Typography>
</Grid>
</Grid>
</CardContent>
</Card>
)
}2. Refactor ZoneDistribution.tsx
The HTML output showed raw floating-point seconds (e.g., 0:27.713000...). We must truncate these for the UI and use a horizontal bar representation to communicate "Time in Zone" effectively.
// app/client/experimental/components/ZoneDistribution.tsx
'use client'
import { Card, CardContent, Typography, Box, LinearProgress } from '@mui/material'
import { HrZoneName } from '@/lib/workout-session-storage'
// ... existing props interface
const ZoneDistribution = ({ timeInZones, totalDuration }: ZoneDistributionProps) => {
return (
<Card elevation={2}>
<CardContent>
<Typography variant="h6" fontWeight="bold" gutterBottom>Time in Zones</Typography>
{Object.entries(timeInZones)
.filter(([zone]) => ![HrZoneName.NoData, HrZoneName.Unknown].includes(zone as HrZoneName))
.map(([zone, time]) => {
const percentage = totalDuration > 0 ? (time / totalDuration) * 100 : 0;
if (percentage < 1) return null; // Hide negligible data
return (
<Box key={zone} mb={2}>
<Box display="flex" justifyContent="space-between" mb={0.5}>
<Typography variant="body2" fontWeight="medium">{zone}</Typography>
<Typography variant="body2" color="textSecondary">
{Math.floor(time / 60)}m {Math.floor(time % 60)}s ({percentage.toFixed(1)}%)
</Typography>
</Box>
<LinearProgress
variant="determinate"
value={percentage}
sx={{ height: 8, borderRadius: 4 }}
/>
</Box>
);
})}
</CardContent>
</Card>
);
}3. Improve HeartRateTimeSeries.tsx
The chart is currently using a default purple stroke. For an HRM app, the line color should ideally reflect the current intensity or use a more energetic color.
- Tip: Use a
ResponsiveContainerwith a fixedminHeightto prevent layout shift. - Grid: Lighten the
CartesianGridstroke for better contrast.
Key Improvements Summary:
- Precision Control: Implemented
toFixed(0)for calories and removed long float decimals in duration to reduce visual noise. - Semantic Color: Integrated the
custompalette fromtheme.tsto provide immediate visual feedback on workout state. - Accessibility: Switched to a
Gridlayout with explicitcaptionlabels, ensuring screen readers clearly associate labels with values.
Metadata
Metadata
Assignees
Labels
Projects
Status