"use client"
import { useState, useEffect, useCallback } from "react"
import { Dumbbell, Plus, Zap } from "lucide-react"
import { Button } from "@/components/ui/button"
import { Progress } from "@/components/ui/progress"
import { cn } from "@/lib/utils"
import { useFitnessData } from "@/hooks/useFitnessData"
import { PlannedWorkout } from "@/lib/api"
interface Exercise {
id: string
name: string
sets: string
reps: string
weight?: string
duration?: string
completed: boolean
type: "strength" | "cardio"
}
interface WorkoutTrackerProps {
loggedWorkouts?: Array<{
id: string
name: string
type: string
completed: boolean
timestamp: string
duration?: number
}>
currentPlan?: PlannedWorkout[]
}
export function WorkoutTracker({ loggedWorkouts = [], currentPlan }: WorkoutTrackerProps) {
console.log('π WorkoutTracker received logged workouts:', loggedWorkouts)
console.log('π WorkoutTracker received current plan:', currentPlan)
const { logNewEntry, refreshContext } = useFitnessData()
// Helper function to check if an exercise is completed based on logged workouts
const isExerciseCompleted = useCallback((exerciseName: string) => {
const result = loggedWorkouts.some(workout => {
const workoutName = workout.name.toLowerCase().trim()
const exerciseName_lower = exerciseName.toLowerCase().trim()
// Simplified matching logic
let matches = false
// Direct case-insensitive match
if (workoutName === exerciseName_lower) {
matches = true
}
// Handle push-ups variations
else if (exerciseName_lower === 'push-ups') {
matches = ['push-ups', 'pushups', 'push ups'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Handle squats variations
else if (exerciseName_lower === 'squats') {
matches = ['squats', 'squat'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Handle plank variations
else if (exerciseName_lower === 'plank') {
matches = ['plank', 'planks'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Handle lunges variations
else if (exerciseName_lower === 'lunges') {
matches = ['lunges', 'lunge'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Default substring matching
else {
matches = workoutName.includes(exerciseName_lower) || exerciseName_lower.includes(workoutName)
}
if (matches) {
console.log(`β
${exerciseName} matches workout: ${workout.name}`)
}
return matches
})
console.log(`π ${exerciseName} completed status: ${result} (from ${loggedWorkouts.length} total workouts)`)
return result
}, [loggedWorkouts])
// Helper function to get actual duration from logged workouts (sum all matching sessions)
const getActualDuration = useCallback((exerciseName: string) => {
const matchingWorkouts = loggedWorkouts.filter(workout => {
const workoutName = workout.name.toLowerCase().trim()
const exerciseName_lower = exerciseName.toLowerCase().trim()
// Use the same simplified matching logic
let matches = false
// Direct case-insensitive match
if (workoutName === exerciseName_lower) {
matches = true
}
// Handle push-ups variations
else if (exerciseName_lower === 'push-ups') {
matches = ['push-ups', 'pushups', 'push ups'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Handle squats variations
else if (exerciseName_lower === 'squats') {
matches = ['squats', 'squat'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Handle plank variations
else if (exerciseName_lower === 'plank') {
matches = ['plank', 'planks'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Handle lunges variations
else if (exerciseName_lower === 'lunges') {
matches = ['lunges', 'lunge'].some(pattern =>
workoutName === pattern || workoutName.includes(pattern) || pattern.includes(workoutName)
)
}
// Default substring matching
else {
matches = workoutName.includes(exerciseName_lower) || exerciseName_lower.includes(workoutName)
}
return matches
})
// Sum all durations for this exercise type
const totalDuration = matchingWorkouts.reduce((total, workout) => total + (workout.duration || 0), 0)
console.log(`ποΈ ${exerciseName}: Found ${matchingWorkouts.length} sessions, total duration: ${totalDuration} min`)
return totalDuration
}, [loggedWorkouts])
// Helper function to convert PlannedWorkout to Exercise format
const convertPlanToExercises = useCallback((plan: PlannedWorkout[]): Exercise[] => {
return plan.map(plannedWorkout => ({
id: plannedWorkout.id,
name: plannedWorkout.name,
sets: plannedWorkout.sets.toString(),
reps: plannedWorkout.reps.toString(),
weight: plannedWorkout.weight,
duration: plannedWorkout.duration ? `${plannedWorkout.duration}${plannedWorkout.duration < 60 ? 's' : 'min'}` : undefined,
completed: isExerciseCompleted(plannedWorkout.name),
type: plannedWorkout.type
}))
}, [isExerciseCompleted])
// Helper function to determine if we're showing tomorrow's plan
const isTomorrowsPlan = useCallback(() => {
console.log('π Title detection - Checking if tomorrow\'s plan...')
console.log('π LoggedWorkouts length:', loggedWorkouts.length)
console.log('π CurrentPlan length:', currentPlan?.length || 0)
// If we have no current plan, it's definitely today's workout (not tomorrow's)
if (!currentPlan || currentPlan.length === 0) {
console.log('β No current plan - showing today\'s workout')
return false
}
// If we have logged workouts AND a current plan, check if plan is different
if (loggedWorkouts.length > 0 && currentPlan.length > 0) {
const loggedExerciseNames = loggedWorkouts.map(w => w.name.toLowerCase().trim())
const planExerciseNames = currentPlan.map(p => p.name.toLowerCase().trim())
console.log('π
Logged exercises:', loggedExerciseNames)
console.log('π
Plan exercises:', planExerciseNames)
// If plan has exercises NOT in logged workouts, it's tomorrow's plan
const hasNewExercises = planExerciseNames.some(planEx =>
!loggedExerciseNames.some(loggedEx =>
planEx.includes(loggedEx) || loggedEx.includes(planEx)
)
)
console.log('π Has new exercises?', hasNewExercises)
if (hasNewExercises) {
console.log('β
Detected tomorrow\'s plan!')
return true
} else {
console.log('β Plan has same exercises as logged - showing today\'s workout')
return false
}
}
// If we have a plan but NO logged workouts, it could be either:
// - Today's plan (before doing any workouts)
// - Tomorrow's plan (generated for tomorrow)
// Default to today's workout unless explicitly generated as tomorrow's plan
if (currentPlan.length > 0 && loggedWorkouts.length === 0) {
console.log('β Plan exists but no logged workouts - defaulting to today\'s workout')
return false
}
console.log('β Default to today\'s workout')
return false
}, [loggedWorkouts, currentPlan])
// Determine the title and description
const isTomorrow = isTomorrowsPlan()
const workoutTitle = isTomorrow ? "Tomorrow's Workout" : "Today's Workout"
const titleEmoji = isTomorrow ? "π
" : "ποΈ"
console.log('π Final workout title:', workoutTitle, titleEmoji)
// Helper function to create exercises that preserve today's completed workouts
const createMixedExercises = useCallback((): Exercise[] => {
let exercisesToShow: Exercise[] = []
console.log('ποΈ Creating exercises list')
console.log('π Current plan provided:', !!currentPlan, currentPlan?.length || 0, 'exercises')
console.log('πͺ Logged workouts:', loggedWorkouts.length, loggedWorkouts.map(w => w.name))
// Strategy: Only show exercises that have been logged OR are in the current plan
// Don't show any fallback exercises by default
if (currentPlan && currentPlan.length > 0) {
// If there's a plan, show plan exercises
console.log('π Using current plan exercises')
exercisesToShow = currentPlan.map(planned => ({
id: planned.id,
name: planned.name,
sets: planned.sets.toString(),
reps: planned.reps?.toString() || "",
weight: planned.weight,
duration: planned.duration ? `${planned.duration}s` : undefined,
completed: isExerciseCompleted(planned.name),
type: planned.type
}))
}
// Add any logged exercises that aren't in the plan
const loggedExerciseNames = new Set(exercisesToShow.map(e => e.name.toLowerCase()))
loggedWorkouts.forEach((workout, index) => {
if (!loggedExerciseNames.has(workout.name.toLowerCase())) {
console.log('β Adding logged exercise not in plan:', workout.name)
exercisesToShow.push({
id: `logged-${workout.id || index}`,
name: workout.name,
sets: "3", // Default values for logged exercises
reps: "10",
weight: undefined,
duration: workout.duration ? `${workout.duration}min` : undefined,
completed: true, // Logged exercises are always completed
type: workout.type as "strength" | "cardio" || "strength"
})
}
})
// If no plan and no logged workouts, show empty list
if (exercisesToShow.length === 0) {
console.log('π No plan and no logged workouts - showing empty list')
return []
}
console.log('β
Final exercises to show:', exercisesToShow.map(e => `${e.name}(${e.completed ? 'completed' : 'pending'})`))
return exercisesToShow
}, [loggedWorkouts, currentPlan, isExerciseCompleted])
// Initialize exercises with mixed approach that preserves today's progress
const [exercises, setExercises] = useState<Exercise[]>(() => {
console.log('π Initializing exercises')
return createMixedExercises()
})
// Update exercises when currentPlan or loggedWorkouts change
useEffect(() => {
console.log('π Updating exercises due to plan/workout changes')
setExercises(createMixedExercises())
}, [createMixedExercises])
const [showAddForm, setShowAddForm] = useState(false)
const [newExercise, setNewExercise] = useState({
name: "",
sets: "",
reps: "",
weight: "",
duration: "",
type: "strength" as "strength" | "cardio",
})
const toggleExercise = async (id: string) => {
const exercise = exercises.find(ex => ex.id === id)
if (!exercise) return
const newCompletedState = !exercise.completed
// Check if this exercise is already logged via + button
const isAlreadyLogged = isExerciseCompleted(exercise.name)
if (isAlreadyLogged && !newCompletedState) {
// If trying to uncheck a logged exercise, just update local state but keep it completed
// (since it was logged via + button, we don't want to fully uncheck it)
return
}
// Update local state immediately for UI responsiveness
setExercises(
exercises.map((ex) => (ex.id === id ? { ...ex, completed: newCompletedState } : ex)),
)
// If completing the exercise and it's not already logged, log it to the API
if (newCompletedState && !isAlreadyLogged) {
try {
// Calculate duration based on exercise type and estimates
let estimatedDuration = 5 // Default 5 minutes per exercise
if (exercise.type === 'cardio' && exercise.duration) {
// Extract duration from string like "30s" or "30min"
const durationMatch = exercise.duration.match(/(\d+)/)
if (durationMatch) {
const number = parseInt(durationMatch[1])
if (exercise.duration.includes('min')) {
estimatedDuration = number
} else if (exercise.duration.includes('s')) {
estimatedDuration = Math.max(1, Math.round(number / 60)) // Convert seconds to minutes
}
}
} else if (exercise.sets && exercise.reps) {
// Estimate time for strength exercises: sets * reps * 3 seconds + rest time
const sets = parseInt(exercise.sets) || 3
const reps = parseInt(exercise.reps) || 10
estimatedDuration = Math.max(1, Math.round((sets * reps * 3 + sets * 60) / 60)) // 3 sec per rep + 60 sec rest per set
} else if (exercise.duration) {
// Use plan duration
const durationMatch = exercise.duration.match(/(\d+)/)
if (durationMatch) {
const number = parseInt(durationMatch[1])
if (exercise.duration.includes('min')) {
estimatedDuration = number
} else if (exercise.duration.includes('s')) {
estimatedDuration = Math.max(1, Math.round(number / 60))
}
}
}
const result = await logNewEntry('workout', {
workout: {
type: exercise.type,
name: exercise.name,
duration: estimatedDuration,
sets: parseInt(exercise.sets) || undefined,
reps: parseInt(exercise.reps) || undefined,
weight: exercise.weight || undefined,
}
})
if (result.success) {
console.log(`β
Logged completed exercise: ${exercise.name} (${estimatedDuration} min)`)
console.log('β
Progress should update automatically via logNewEntry')
} else {
console.error('β Failed to log exercise:', result.error)
}
} catch (error) {
console.error('Failed to log exercise completion:', error)
// Revert the state if API call failed
setExercises(
exercises.map((ex) => (ex.id === id ? { ...ex, completed: !newCompletedState } : ex)),
)
}
}
}
const handleAddExercise = () => {
if (!newExercise.name || !newExercise.sets) return
const exercise: Exercise = {
id: Date.now().toString(),
name: newExercise.name,
sets: newExercise.sets,
reps: newExercise.reps,
weight: newExercise.weight || undefined,
duration: newExercise.duration || undefined,
completed: false,
type: newExercise.type,
}
setExercises([...exercises, exercise])
setNewExercise({
name: "",
sets: "",
reps: "",
weight: "",
duration: "",
type: "strength",
})
setShowAddForm(false)
}
const completedExercises = exercises.filter((exercise) => exercise.completed)
const progress = (completedExercises.length / exercises.length) * 100
// Calculate total time based on completed exercises and estimates for remaining
let actualTime = 0
let estimatedTime = 0
exercises.forEach(exercise => {
if (exercise.completed) {
// Use actual logged duration for completed exercises if available
const loggedDuration = getActualDuration(exercise.name)
if (loggedDuration > 0) {
actualTime += loggedDuration
} else {
// Fallback to plan duration if manually completed but not logged
if (exercise.duration) {
const durationMatch = exercise.duration.match(/(\d+)/)
if (durationMatch) {
const number = parseInt(durationMatch[1])
if (exercise.duration.includes('min')) {
actualTime += number
} else if (exercise.duration.includes('s')) {
actualTime += Math.max(1, Math.round(number / 60))
}
}
} else {
actualTime += 5 // Default 5 minutes
}
}
} else {
// Estimates for uncompleted exercises
if (exercise.duration) {
const durationMatch = exercise.duration.match(/(\d+)/)
if (durationMatch) {
const number = parseInt(durationMatch[1])
if (exercise.duration.includes('min')) {
estimatedTime += number
} else if (exercise.duration.includes('s')) {
estimatedTime += Math.max(1, Math.round(number / 60))
}
}
} else {
estimatedTime += 5 // Default 5 minutes per exercise
}
}
})
const timeData = {
actualTime,
estimatedTime,
totalTime: actualTime + estimatedTime
}
return (
<div className="bg-white/80 backdrop-blur-sm rounded-3xl shadow-lg border border-white/20 p-6">
{/* Header */}
<div className="flex items-center justify-between mb-6">
<div className="flex items-center gap-3">
<div className="w-12 h-12 bg-gradient-to-br from-orange-400 to-red-500 rounded-2xl flex items-center justify-center">
<Dumbbell className="w-6 h-6 text-white" />
</div>
<div>
<h3 className="text-lg font-bold text-slate-800">{workoutTitle}</h3>
<div className="flex items-center gap-2 mt-1">
<Progress value={progress} className="w-20 h-2" />
<span className="text-sm text-slate-600">{Math.round(progress)}%</span>
</div>
</div>
</div>
<Button
size="sm"
className="rounded-full bg-gradient-to-r from-orange-400 to-red-500 hover:from-orange-500 hover:to-red-600"
onClick={() => setShowAddForm(!showAddForm)}
>
<Plus className="w-4 h-4" />
</Button>
</div>
{/* Add Exercise Form */}
{showAddForm && (
<div className="mb-6 p-4 bg-gradient-to-r from-orange-50 to-red-50 rounded-2xl border border-orange-200/50 animate-in slide-in-from-top-2 duration-300">
<h4 className="font-semibold text-orange-800 mb-3 text-sm">Add New Exercise</h4>
<div className="space-y-3">
<div className="grid grid-cols-2 gap-3">
<input
type="text"
placeholder="Exercise name"
value={newExercise.name}
onChange={(e) => setNewExercise({ ...newExercise, name: e.target.value })}
className="px-3 py-2 rounded-xl border border-coral-200 bg-white/80 text-sm focus:outline-none focus:ring-2 focus:ring-coral-400"
/>
<select
value={newExercise.type}
onChange={(e) => setNewExercise({ ...newExercise, type: e.target.value as "strength" | "cardio" })}
className="px-3 py-2 rounded-xl border border-coral-200 bg-white/80 text-sm focus:outline-none focus:ring-2 focus:ring-coral-400"
>
<option value="strength">Strength</option>
<option value="cardio">Cardio</option>
</select>
</div>
<div className="grid grid-cols-3 gap-3">
<input
type="text"
placeholder="Sets"
value={newExercise.sets}
onChange={(e) => setNewExercise({ ...newExercise, sets: e.target.value })}
className="px-3 py-2 rounded-xl border border-coral-200 bg-white/80 text-sm focus:outline-none focus:ring-2 focus:ring-coral-400"
/>
<input
type="text"
placeholder="Reps"
value={newExercise.reps}
onChange={(e) => setNewExercise({ ...newExercise, reps: e.target.value })}
className="px-3 py-2 rounded-xl border border-coral-200 bg-white/80 text-sm focus:outline-none focus:ring-2 focus:ring-coral-400"
/>
<input
type="text"
placeholder="Weight (optional)"
value={newExercise.weight}
onChange={(e) => setNewExercise({ ...newExercise, weight: e.target.value })}
className="px-3 py-2 rounded-xl border border-coral-200 bg-white/80 text-sm focus:outline-none focus:ring-2 focus:ring-coral-400"
/>
</div>
{newExercise.type === "cardio" && (
<input
type="text"
placeholder="Duration (e.g., 30min)"
value={newExercise.duration}
onChange={(e) => setNewExercise({ ...newExercise, duration: e.target.value })}
className="w-full px-3 py-2 rounded-xl border border-coral-200 bg-white/80 text-sm focus:outline-none focus:ring-2 focus:ring-coral-400"
/>
)}
<div className="flex gap-2">
<Button
size="sm"
onClick={handleAddExercise}
className="flex-1 rounded-xl bg-gradient-to-r from-coral-400 to-red-500 hover:from-coral-500 hover:to-red-600"
>
Add Exercise
</Button>
<Button
size="sm"
variant="outline"
onClick={() => setShowAddForm(false)}
className="rounded-xl border-coral-200 text-coral-600 hover:bg-coral-50"
>
Cancel
</Button>
</div>
</div>
</div>
)}
{/* Exercises List */}
{exercises.length === 0 ? (
// Empty state
<div className="text-center py-8">
<div className="w-16 h-16 mx-auto mb-4 bg-orange-100 rounded-full flex items-center justify-center">
<Dumbbell className="w-8 h-8 text-orange-500" />
</div>
<h4 className="text-lg font-semibold text-slate-700 mb-2">Ready to Start?</h4>
<p className="text-sm text-slate-500 mb-4">
Log your first workout using the + button or chat interface
</p>
<div className="text-xs text-slate-400">
Try saying: "I did 20 push-ups for 10 minutes"
</div>
</div>
) : (
<>
<div className="space-y-3 mb-6">
{exercises.map((exercise) => (
<button
key={exercise.id}
onClick={() => toggleExercise(exercise.id)}
className={cn(
"w-full p-4 rounded-2xl border-2 transition-all duration-200 text-left group",
exercise.completed
? "bg-gradient-to-r from-green-50 to-emerald-50 border-green-200 shadow-sm"
: "bg-gradient-to-r from-slate-50 to-gray-50 border-slate-200 hover:border-coral-300 hover:shadow-md hover:scale-[1.01]",
)}
>
<div className="flex items-start justify-between">
<div className="flex items-start gap-3 flex-1">
<div
className={cn(
"w-4 h-4 rounded-full mt-0.5 transition-all duration-200 flex items-center justify-center",
exercise.completed
? "bg-green-500 shadow-lg shadow-green-200"
: "bg-slate-300 group-hover:bg-coral-400",
)}
>
{exercise.completed && (
<svg className="w-2.5 h-2.5 text-white" fill="currentColor" viewBox="0 0 20 20">
<path
fillRule="evenodd"
d="M16.707 5.293a1 1 0 010 1.414l-8 8a1 1 0 01-1.414 0l-4-4a1 1 0 011.414-1.414L8 12.586l7.293-7.293a1 1 0 011.414 0z"
clipRule="evenodd"
/>
</svg>
)}
</div>
<div className="flex-1 min-w-0">
<div className="flex items-center gap-2 mb-1">
<span
className={cn(
"text-xs font-semibold px-2 py-1 rounded-full",
exercise.completed
? "bg-green-100 text-green-700"
: exercise.type === "strength"
? "bg-coral-100 text-coral-700 group-hover:bg-coral-200"
: "bg-blue-100 text-blue-700 group-hover:bg-blue-200",
)}
>
{exercise.type === "strength" ? "STRENGTH" : "CARDIO"}
</span>
{exercise.type === "strength" && (
<div className="flex items-center gap-1 text-xs text-slate-500">
<Dumbbell className="w-3 h-3" />
</div>
)}
{exercise.type === "cardio" && (
<div className="flex items-center gap-1 text-xs text-slate-500">
<Zap className="w-3 h-3" />
</div>
)}
</div>
<p
className={cn(
"font-medium text-sm leading-relaxed mb-2",
exercise.completed ? "text-green-800" : "text-slate-700",
)}
>
{exercise.name}
</p>
<div className="flex items-center gap-4 text-xs">
<span className={exercise.completed ? "text-green-600" : "text-slate-500"}>
{exercise.sets} sets
</span>
{exercise.reps && (
<span className={exercise.completed ? "text-green-600" : "text-slate-500"}>
{exercise.reps} reps
</span>
)}
{exercise.weight && (
<span className={exercise.completed ? "text-green-600" : "text-slate-500"}>
{exercise.weight}
</span>
)}
{exercise.duration && (
<span className={exercise.completed ? "text-green-600" : "text-slate-500"}>
{exercise.duration}
</span>
)}
</div>
</div>
</div>
</div>
</button>
))}
</div>
{showAddForm && (
<div className="border-t border-slate-200 pt-4">
<div className="space-y-3">
<div className="flex gap-2">
<input
type="text"
placeholder="Exercise name"
value={newExercise.name}
onChange={(e) => setNewExercise(prev => ({ ...prev, name: e.target.value }))}
className="flex-1 px-3 py-2 border border-slate-300 rounded-lg text-sm"
/>
<select
value={newExercise.type}
onChange={(e) => setNewExercise(prev => ({ ...prev, type: e.target.value as "strength" | "cardio" }))}
className="px-3 py-2 border border-slate-300 rounded-lg text-sm"
>
<option value="strength">Strength</option>
<option value="cardio">Cardio</option>
</select>
</div>
<div className="flex gap-2">
<input
type="text"
placeholder="Sets"
value={newExercise.sets}
onChange={(e) => setNewExercise(prev => ({ ...prev, sets: e.target.value }))}
className="w-16 px-3 py-2 border border-slate-300 rounded-lg text-sm"
/>
<input
type="text"
placeholder="Reps"
value={newExercise.reps}
onChange={(e) => setNewExercise(prev => ({ ...prev, reps: e.target.value }))}
className="w-16 px-3 py-2 border border-slate-300 rounded-lg text-sm"
/>
<input
type="text"
placeholder="Weight"
value={newExercise.weight}
onChange={(e) => setNewExercise(prev => ({ ...prev, weight: e.target.value }))}
className="flex-1 px-3 py-2 border border-slate-300 rounded-lg text-sm"
/>
<input
type="text"
placeholder="Duration"
value={newExercise.duration}
onChange={(e) => setNewExercise(prev => ({ ...prev, duration: e.target.value }))}
className="flex-1 px-3 py-2 border border-slate-300 rounded-lg text-sm"
/>
</div>
<div className="flex gap-2 justify-end">
<button
onClick={() => setShowAddForm(false)}
className="px-4 py-2 text-sm text-slate-600 hover:text-slate-800"
>
Cancel
</button>
<button
onClick={handleAddExercise}
className="px-4 py-2 bg-orange-500 text-white text-sm rounded-lg hover:bg-orange-600"
>
Add Exercise
</button>
</div>
</div>
</div>
)}
<div className="border-t border-slate-200 pt-4">
<div className="flex items-center justify-between text-sm">
<span className="text-slate-600">
Time: {timeData.actualTime > 0 && timeData.estimatedTime > 0
? `${timeData.actualTime} + ${timeData.estimatedTime} min`
: timeData.actualTime > 0
? `${timeData.actualTime} min actual`
: timeData.estimatedTime > 0
? `${timeData.estimatedTime} min estimated`
: '0 min'
}
</span>
<button
onClick={() => setShowAddForm(!showAddForm)}
className="flex items-center gap-1 text-orange-500 hover:text-orange-600"
>
<Plus className="w-4 h-4" />
Add Exercise
</button>
</div>
</div>
</>
)}
{/* Workout Summary */}
<div className="bg-gradient-to-r from-orange-50 to-red-50 rounded-2xl p-4 border border-orange-200/50">
<h4 className="font-semibold text-orange-800 mb-3 text-sm flex items-center gap-2">
<Zap className="w-4 h-4" />
Workout Progress
</h4>
<div className="grid grid-cols-2 gap-4">
<div>
<div className="flex items-center justify-between mb-1">
<span className="text-xs text-orange-600">Exercises</span>
<span className="text-xs text-orange-600">
{completedExercises.length}/{exercises.length}
</span>
</div>
<div className="w-full bg-orange-200 rounded-full h-2">
<div
className="bg-gradient-to-r from-orange-400 to-red-500 h-2 rounded-full transition-all duration-300"
style={{ width: `${progress}%` }}
></div>
</div>
</div>
<div>
<div className="flex items-center justify-between mb-1">
<span className="text-xs text-orange-600">Time</span>
<span className="text-xs text-orange-600">
{timeData.actualTime > 0 ? `${timeData.actualTime}` : '0'}
{timeData.estimatedTime > 0 ? ` + ${timeData.estimatedTime}` : ''} min
</span>
</div>
<div className="w-full bg-orange-200 rounded-full h-2">
<div
className="bg-gradient-to-r from-orange-400 to-red-500 h-2 rounded-full transition-all duration-300"
style={{
width: timeData.totalTime > 0
? `${(timeData.actualTime / timeData.totalTime) * 100}%`
: '0%'
}}
></div>
</div>
</div>
</div>
</div>
</div>
)
}