import pandas as pd import numpy as np import random import gradio as gr from sklearn.preprocessing import StandardScaler from sklearn.neighbors import NearestNeighbors import requests from bs4 import BeautifulSoup # Sample exercise database exercises_df = pd.DataFrame({ 'name': [ # Strength - Upper Body 'Push-ups', 'Bench Press', 'Shoulder Press', 'Pull-ups', 'Lat Pulldowns', 'Dumbbell Rows', 'Bicep Curls', 'Tricep Extensions', 'Chest Flyes', # Strength - Lower Body 'Squats', 'Deadlifts', 'Lunges', 'Leg Press', 'Leg Extensions', 'Hamstring Curls', 'Calf Raises', 'Glute Bridges', 'Box Jumps', # Cardio 'Running', 'Cycling', 'Elliptical', 'Jumping Rope', 'Swimming', 'Rowing', 'Stair Climbing', 'HIIT', 'Walking', # Flexibility/Recovery 'Yoga', 'Stretching', 'Foam Rolling', 'Pilates', 'Tai Chi' ], 'category': [ # Strength - Upper Body 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', # Strength - Lower Body 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', 'strength', # Cardio 'cardio', 'cardio', 'cardio', 'cardio', 'cardio', 'cardio', 'cardio', 'cardio', 'cardio', # Flexibility/Recovery 'flexibility', 'flexibility', 'flexibility', 'flexibility', 'flexibility' ], 'muscle_group': [ # Strength - Upper Body 'chest', 'chest', 'shoulders', 'back', 'back', 'back', 'arms', 'arms', 'chest', # Strength - Lower Body 'legs', 'legs', 'legs', 'legs', 'legs', 'legs', 'legs', 'legs', 'legs', # Cardio 'full_body', 'lower_body', 'full_body', 'full_body', 'full_body', 'full_body', 'lower_body', 'full_body', 'lower_body', # Flexibility/Recovery 'full_body', 'full_body', 'full_body', 'full_body', 'full_body' ], 'difficulty': [ # Strength - Upper Body 2, 3, 3, 4, 3, 2, 2, 2, 3, # Strength - Lower Body 3, 4, 3, 3, 2, 2, 1, 2, 4, # Cardio 3, 2, 2, 3, 4, 3, 3, 4, 1, # Flexibility/Recovery 2, 1, 1, 3, 2 ], 'equipment_needed': [ # Strength - Upper Body 'none', 'barbell', 'dumbbell', 'pull-up_bar', 'machine', 'dumbbell', 'dumbbell', 'dumbbell', 'dumbbell', # Strength - Lower Body 'none', 'barbell', 'none', 'machine', 'machine', 'machine', 'machine', 'none', 'box', # Cardio 'none', 'machine', 'machine', 'jump_rope', 'pool', 'machine', 'machine', 'none', 'none', # Flexibility/Recovery 'mat', 'none', 'foam_roller', 'mat', 'none' ], 'calorie_burn_factor': [ # Strength - Upper Body 2, 3, 2, 3, 2, 2, 1, 1, 2, # Strength - Lower Body 4, 5, 3, 4, 2, 2, 1, 2, 4, # Cardio 5, 4, 4, 4, 5, 4, 4, 5, 2, # Flexibility/Recovery 2, 1, 1, 2, 1 ], 'muscle_building_factor': [ # Strength - Upper Body 3, 5, 4, 4, 4, 3, 3, 3, 3, # Strength - Lower Body 5, 5, 4, 4, 3, 3, 2, 3, 3, # Cardio 1, 1, 1, 1, 1, 1, 1, 2, 1, # Flexibility/Recovery 1, 0, 0, 1, 0 ], 'endurance_factor': [ # Strength - Upper Body 2, 1, 1, 2, 1, 1, 1, 1, 1, # Strength - Lower Body 2, 1, 2, 1, 1, 1, 1, 1, 2, # Cardio 5, 5, 5, 4, 5, 5, 4, 4, 3, # Flexibility/Recovery 1, 0, 0, 1, 1 ], 'flexibility_factor': [ # Strength - Upper Body 1, 0, 0, 1, 0, 0, 0, 0, 1, # Strength - Lower Body 2, 1, 2, 0, 0, 1, 1, 1, 0, # Cardio 1, 1, 1, 1, 2, 1, 1, 1, 1, # Flexibility/Recovery 5, 5, 3, 4, 4 ], 'injury_risk': [ # Strength - Upper Body 1, 3, 2, 3, 1, 2, 1, 1, 1, # Strength - Lower Body 2, 4, 2, 2, 1, 1, 1, 1, 3, # Cardio 3, 1, 1, 2, 1, 1, 2, 3, 1, # Flexibility/Recovery 1, 1, 1, 1, 1 ] }) # Body type recommendations body_type_recommendations = { 'ectomorph': { 'strength_focus': 0.6, 'cardio_focus': 0.2, 'flexibility_focus': 0.2, 'sets': 4, 'reps': '8-12', 'rest': '60-90 seconds', 'nutrition': 'High calorie, protein-rich diet. Focus on strength training with compound movements. Add extra calories for muscle building.' }, 'mesomorph': { 'strength_focus': 0.5, 'cardio_focus': 0.3, 'flexibility_focus': 0.2, 'sets': 3, 'reps': '8-15', 'rest': '45-60 seconds', 'nutrition': 'Balanced macronutrients with moderate protein. Mix of strength and cardio works well. Adjust calories based on specific goals.' }, 'endomorph': { 'strength_focus': 0.4, 'cardio_focus': 0.4, 'flexibility_focus': 0.2, 'sets': 3, 'reps': '12-15', 'rest': '30-45 seconds', 'nutrition': 'Calorie-controlled diet with higher protein. Include more cardio and circuit training. Focus on reducing processed carbs.' } } # Goal-based recommendations goal_recommendations = { 'weight_loss': { 'strength_focus': 0.3, 'cardio_focus': 0.5, 'flexibility_focus': 0.2, 'training_frequency': '4-5 days/week', 'nutrition': 'Calorie deficit of 500-750 per day. Higher protein intake (1.6-2g per kg). Focus on whole foods and fiber.' }, 'muscle_gain': { 'strength_focus': 0.7, 'cardio_focus': 0.1, 'flexibility_focus': 0.2, 'training_frequency': '4 days/week', 'nutrition': 'Calorie surplus of 250-500 per day. High protein intake (1.8-2.2g per kg). Carbs around workouts.' }, 'endurance': { 'strength_focus': 0.2, 'cardio_focus': 0.6, 'flexibility_focus': 0.2, 'training_frequency': '5-6 days/week', 'nutrition': 'Balanced calories. Higher carbohydrate intake (5-7g per kg). Timing nutrition around longer training sessions.' }, 'flexibility': { 'strength_focus': 0.3, 'cardio_focus': 0.2, 'flexibility_focus': 0.5, 'training_frequency': '3-4 days/week', 'nutrition': 'Balanced diet with anti-inflammatory foods. Adequate protein (1.4-1.6g per kg). Hydration is essential.' }, 'general_fitness': { 'strength_focus': 0.4, 'cardio_focus': 0.4, 'flexibility_focus': 0.2, 'training_frequency': '3-4 days/week', 'nutrition': 'Balanced diet with proper macronutrients. Focus on whole foods. Moderate protein (1.4-1.6g per kg).' } } # Activity level calorie multipliers activity_multipliers = { 'sedentary': 1.2, 'lightly_active': 1.375, 'moderately_active': 1.55, 'very_active': 1.725, 'extra_active': 1.9 } # Health condition adjustments health_condition_adjustments = { 'none': {}, 'back_pain': { 'avoid': ['Deadlifts', 'Squats', 'Bench Press'], 'recommended': ['Swimming', 'Walking', 'Yoga', 'Pilates'], 'advice': 'Focus on core strengthening exercises. Avoid high-impact activities and heavy weights.' }, 'knee_pain': { 'avoid': ['Squats', 'Lunges', 'Running', 'Box Jumps'], 'recommended': ['Swimming', 'Cycling', 'Rowing', 'Upper Body Training'], 'advice': 'Low-impact cardio and avoid deep knee bending. Strengthen muscles around the knee with controlled movements.' }, 'shoulder_pain': { 'avoid': ['Shoulder Press', 'Push-ups', 'Pull-ups', 'Bench Press'], 'recommended': ['Leg Training', 'Core Work', 'Controlled Mobility', 'Walking'], 'advice': 'Avoid overhead movements and heavy pushing/pulling. Focus on rotator cuff strengthening and mobility.' }, 'hypertension': { 'avoid': ['HIIT', 'Heavy weight lifting', 'Exercises with head below heart'], 'recommended': ['Walking', 'Swimming', 'Cycling', 'Light weight training'], 'advice': 'Focus on moderate-intensity, steady-state cardio. Avoid holding breath during exercise.' }, 'diabetes': { 'avoid': [], 'recommended': ['Walking', 'Swimming', 'Cycling', 'Resistance Training'], 'advice': 'Regular moderate exercise helps control blood sugar. Monitor glucose levels before and after exercise.' } } # Add diet recommendations diet_recommendations = { 'weight_loss': { 'calorie_deficit': 500, 'protein_factor': 2.0, # g per kg of bodyweight 'carb_factor': 2.0, # g per kg of bodyweight 'fat_factor': 0.8, # g per kg of bodyweight 'meal_count': 4, 'sample_foods': { 'proteins': ['Chicken breast', 'Turkey', 'Fish', 'Tofu', 'Greek yogurt', 'Cottage cheese', 'Egg whites', 'Lean beef', 'Protein powder'], 'carbs': ['Brown rice', 'Quinoa', 'Sweet potato', 'Oatmeal', 'Whole grain bread', 'Beans', 'Lentils', 'Fruits'], 'fats': ['Avocado', 'Olive oil', 'Nuts', 'Seeds', 'Nut butters', 'Fatty fish'], 'vegetables': ['Broccoli', 'Spinach', 'Kale', 'Cauliflower', 'Peppers', 'Cucumbers', 'Asparagus', 'Zucchini'], 'snacks': ['Greek yogurt', 'Protein bar', 'Apple with peanut butter', 'Cottage cheese with berries', 'Veggie sticks with hummus'] }, 'avoid': ['Sugary drinks', 'Processed foods', 'Refined carbs', 'Alcohol', 'Fried foods', 'High-sugar desserts'], 'tips': [ 'Drink water before meals to increase fullness', 'Use smaller plates to control portion sizes', 'Fill half your plate with vegetables', 'Track your food intake with a journal or app', 'Allow yourself one treat meal per week to stay motivated' ] }, 'muscle_gain': { 'calorie_surplus': 300, 'protein_factor': 2.2, # g per kg of bodyweight 'carb_factor': 4.0, # g per kg of bodyweight 'fat_factor': 1.0, # g per kg of bodyweight 'meal_count': 5, 'sample_foods': { 'proteins': ['Chicken breast', 'Turkey', 'Fish', 'Lean beef', 'Eggs', 'Greek yogurt', 'Cottage cheese', 'Whey protein', 'Tofu'], 'carbs': ['Rice', 'Pasta', 'Potatoes', 'Oats', 'Bread', 'Quinoa', 'Bananas', 'Honey'], 'fats': ['Avocado', 'Olive oil', 'Nuts', 'Nut butters', 'Seeds', 'Whole eggs'], 'vegetables': ['Broccoli', 'Spinach', 'Kale', 'Peppers', 'Carrots', 'Peas', 'Green beans'], 'snacks': ['Protein shake with banana', 'Trail mix', 'Tuna on crackers', 'PB&J sandwich', 'Greek yogurt with granola'] }, 'avoid': ['Alcohol', 'Low-nutrient processed foods', 'Excessive fiber before workouts'], 'tips': [ 'Eat a protein and carb-rich meal within 30-60 minutes after training', 'Aim to gain 0.2-0.5kg per week to minimize fat gain', 'Focus on progressive overload in your training to stimulate muscle growth', 'Get 7-9 hours of quality sleep for maximum recovery and growth', 'Consider creatine monohydrate as a supplement (5g daily)' ] }, 'endurance': { 'calorie_balance': 0, 'protein_factor': 1.6, # g per kg of bodyweight 'carb_factor': 6.0, # g per kg of bodyweight 'fat_factor': 1.0, # g per kg of bodyweight 'meal_count': 5, 'sample_foods': { 'proteins': ['Chicken', 'Fish', 'Tofu', 'Beans', 'Lentils', 'Greek yogurt', 'Eggs', 'Lean meat'], 'carbs': ['Oats', 'Rice', 'Quinoa', 'Sweet potatoes', 'Pasta', 'Bananas', 'Dates', 'Whole grains'], 'fats': ['Avocado', 'Olive oil', 'Nuts', 'Seeds', 'Fatty fish'], 'vegetables': ['Leafy greens', 'Peppers', 'Carrots', 'Beets', 'Sweet potatoes', 'Tomatoes'], 'snacks': ['Banana with honey', 'Energy bars', 'Dried fruit and nuts', 'Rice cakes with nut butter', 'Smoothies'] }, 'avoid': ['High-fiber foods before races/long training', 'New foods before competition', 'Heavy meals before workouts'], 'tips': [ 'Carb-load 24-48 hours before long endurance events', 'Consume easily digestible carbs during sessions lasting over 60 minutes', 'Stay well-hydrated and consider electrolyte replacement during long sessions', 'Practice your race-day nutrition plan during training', 'Consume 30-60g of carbs per hour during endurance exercise lasting more than 90 minutes' ] }, 'flexibility': { 'calorie_balance': 0, 'protein_factor': 1.4, # g per kg of bodyweight 'carb_factor': 3.0, # g per kg of bodyweight 'fat_factor': 1.0, # g per kg of bodyweight 'meal_count': 3, 'sample_foods': { 'proteins': ['Fish', 'Chicken', 'Tofu', 'Beans', 'Lentils', 'Eggs', 'Greek yogurt'], 'carbs': ['Sweet potatoes', 'Brown rice', 'Quinoa', 'Fruits', 'Oats', 'Whole grains'], 'fats': ['Avocado', 'Olive oil', 'Nuts', 'Seeds', 'Coconut oil'], 'vegetables': ['Leafy greens', 'Peppers', 'Carrots', 'Cucumbers', 'Tomatoes'], 'snacks': ['Fruit with nut butter', 'Hummus with vegetables', 'Trail mix', 'Smoothies'] }, 'avoid': ['Highly processed foods', 'Excessive alcohol', 'Sugar-sweetened beverages'], 'tips': [ 'Stay well-hydrated to maintain joint and tissue health', 'Include foods rich in omega-3 fatty acids for their anti-inflammatory properties', 'Consider collagen supplements to support joint and connective tissue health', 'Include foods high in vitamin C to support collagen production', 'Maintain consistent meal timing to support recovery' ] }, 'general_fitness': { 'calorie_balance': 0, 'protein_factor': 1.6, # g per kg of bodyweight 'carb_factor': 3.0, # g per kg of bodyweight 'fat_factor': 0.9, # g per kg of bodyweight 'meal_count': 4, 'sample_foods': { 'proteins': ['Chicken', 'Fish', 'Eggs', 'Greek yogurt', 'Cottage cheese', 'Tofu', 'Lean beef', 'Turkey', 'Legumes'], 'carbs': ['Brown rice', 'Quinoa', 'Sweet potatoes', 'Oats', 'Whole grain bread', 'Fruits', 'Whole grain pasta'], 'fats': ['Avocado', 'Olive oil', 'Nuts', 'Seeds', 'Nut butters', 'Fatty fish'], 'vegetables': ['Broccoli', 'Spinach', 'Kale', 'Bell peppers', 'Carrots', 'Tomatoes', 'Cucumber', 'Zucchini'], 'snacks': ['Greek yogurt with berries', 'Apple with almond butter', 'Hummus with veggies', 'Hard-boiled eggs', 'Trail mix'] }, 'avoid': ['Processed foods', 'Excessive sugar', 'Trans fats', 'Excessive alcohol'], 'tips': [ 'Focus on whole, minimally processed foods', 'Stay hydrated throughout the day', 'Plan and prep meals ahead of time', 'Listen to your body\'s hunger and fullness cues', 'Aim for a colorful variety of fruits and vegetables' ] } } # Add health condition dietary adjustments health_condition_diet_adjustments = { 'none': {}, 'back_pain': { 'beneficial_foods': ['Fatty fish (omega-3s)', 'Turmeric', 'Ginger', 'Berries', 'Green leafy vegetables', 'Nuts and seeds'], 'avoid_foods': ['Processed foods', 'Sugary foods', 'Alcohol', 'Excessive red meat'], 'advice': 'Focus on anti-inflammatory foods to reduce pain and inflammation. Stay well-hydrated and maintain a healthy weight to reduce strain on your back.' }, 'knee_pain': { 'beneficial_foods': ['Fatty fish', 'Olive oil', 'Nuts', 'Fruits', 'Vegetables', 'Whole grains', 'Ginger', 'Turmeric'], 'avoid_foods': ['Processed foods', 'Sugar', 'Refined carbohydrates', 'Alcohol', 'Saturated fats'], 'advice': 'Focus on anti-inflammatory foods and maintain a healthy weight to reduce stress on knee joints. Consider vitamin D and calcium supplements for joint health.' }, 'shoulder_pain': { 'beneficial_foods': ['Fatty fish', 'Berries', 'Olive oil', 'Nuts', 'Seeds', 'Dark leafy greens', 'Colorful vegetables'], 'avoid_foods': ['Processed foods', 'Sugar', 'Refined carbohydrates', 'Excessive alcohol'], 'advice': 'Anti-inflammatory diet can help reduce shoulder pain and inflammation. Consider protein timing around workouts to support tissue repair.' }, 'hypertension': { 'beneficial_foods': ['Bananas', 'Leafy greens', 'Berries', 'Beets', 'Oats', 'Garlic', 'Olive oil', 'Low-fat dairy', 'Seeds'], 'avoid_foods': ['Salt', 'Processed foods', 'Alcohol', 'Caffeine', 'Red meat', 'Sugar'], 'advice': 'Follow a DASH-style diet (Dietary Approaches to Stop Hypertension). Limit sodium to 1,500-2,300mg per day. Monitor caffeine intake and avoid excessive alcohol.' }, 'diabetes': { 'beneficial_foods': ['Leafy greens', 'Fatty fish', 'Nuts', 'Seeds', 'Beans', 'Whole grains', 'Berries', 'Avocados', 'Eggs'], 'avoid_foods': ['Sugar', 'Refined carbs', 'Sugary drinks', 'Fruit juices', 'Trans fats', 'Processed meats', 'Alcohol'], 'advice': 'Focus on low glycemic index foods and consistent carbohydrate intake throughout the day. Monitor blood glucose response to different foods and meal timing.' } } def calculate_bmr(weight, height, age, gender): """Calculate Basal Metabolic Rate using the Mifflin-St Jeor Equation""" if gender == 'male': return 10 * weight + 6.25 * height - 5 * age + 5 else: return 10 * weight + 6.25 * height - 5 * age - 161 def calculate_daily_calories(bmr, activity_level, goal): """Calculate daily calorie needs based on activity level and goal""" activity_multiplier = activity_multipliers[activity_level] tdee = bmr * activity_multiplier if goal == 'weight_loss': return int(tdee - 500) elif goal == 'muscle_gain': return int(tdee + 300) else: return int(tdee) def filter_exercises_by_health_condition(exercises, health_condition): """Filter out exercises that should be avoided based on health condition""" if health_condition == 'none': return exercises avoid_list = health_condition_adjustments[health_condition]['avoid'] return [ex for ex in exercises if ex['name'] not in avoid_list] def get_exercise_recommendations(user_profile, available_equipment=None): """Generate exercise recommendations based on user profile""" body_type = user_profile['body_type'] goal = user_profile['goal'] health_condition = user_profile['health_condition'] # Combine recommendations from body type and goal body_rec = body_type_recommendations[body_type] goal_rec = goal_recommendations[goal] # Calculate focus distribution (weighted average) strength_focus = 0.5 * body_rec['strength_focus'] + 0.5 * goal_rec['strength_focus'] cardio_focus = 0.5 * body_rec['cardio_focus'] + 0.5 * goal_rec['cardio_focus'] flexibility_focus = 0.5 * body_rec['flexibility_focus'] + 0.5 * goal_rec['flexibility_focus'] # Filter exercises by available equipment if specified filtered_exercises = exercises_df if available_equipment and 'any' not in available_equipment: filtered_exercises = filtered_exercises[filtered_exercises['equipment_needed'].isin(['none'] + available_equipment)] # Convert to list of dictionaries for easier manipulation exercises_list = filtered_exercises.to_dict('records') # Filter out exercises to avoid based on health condition exercises_list = filter_exercises_by_health_condition(exercises_list, health_condition) # Select exercises based on focus distribution num_exercises = 12 # Total exercises in the plan num_strength = max(1, int(num_exercises * strength_focus)) num_cardio = max(1, int(num_exercises * cardio_focus)) num_flexibility = max(1, num_exercises - num_strength - num_cardio) # Further divide strength exercises by muscle group strength_exercises = [ex for ex in exercises_list if ex['category'] == 'strength'] upper_body = [ex for ex in strength_exercises if ex['muscle_group'] in ['chest', 'back', 'shoulders', 'arms']] lower_body = [ex for ex in strength_exercises if ex['muscle_group'] == 'legs'] num_upper = max(1, int(num_strength * 0.6)) num_lower = max(1, num_strength - num_upper) # Select exercises selected_upper = random.sample(upper_body, min(num_upper, len(upper_body))) selected_lower = random.sample(lower_body, min(num_lower, len(lower_body))) cardio_exercises = [ex for ex in exercises_list if ex['category'] == 'cardio'] selected_cardio = random.sample(cardio_exercises, min(num_cardio, len(cardio_exercises))) flexibility_exercises = [ex for ex in exercises_list if ex['category'] == 'flexibility'] selected_flexibility = random.sample(flexibility_exercises, min(num_flexibility, len(flexibility_exercises))) # Combine all selected exercises selected_exercises = selected_upper + selected_lower + selected_cardio + selected_flexibility # Create workout plan workout_plan = { 'schedule': create_weekly_schedule(selected_exercises, goal_rec['training_frequency']), 'sets': body_rec['sets'], 'reps': body_rec['reps'], 'rest': body_rec['rest'], 'nutrition': combine_nutrition_advice(body_rec['nutrition'], goal_rec['nutrition']), 'health_advice': health_condition_adjustments[health_condition].get('advice', ''), } if health_condition != 'none': workout_plan['recommended_exercises'] = health_condition_adjustments[health_condition]['recommended'] return workout_plan def create_weekly_schedule(exercises, training_frequency): """Create a weekly workout schedule based on exercises and training frequency""" # Parse training frequency to number of days days_per_week = int(training_frequency.split('-')[0]) # Create empty schedule schedule = {} # Define workout days based on frequency if days_per_week <= 3: workout_days = ['Monday', 'Wednesday', 'Friday'][:days_per_week] elif days_per_week <= 4: workout_days = ['Monday', 'Tuesday', 'Thursday', 'Friday'] elif days_per_week <= 5: workout_days = ['Monday', 'Tuesday', 'Wednesday', 'Friday', 'Saturday'] else: workout_days = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'] # Group exercises by category strength_exercises = [ex for ex in exercises if ex['category'] == 'strength'] upper_body = [ex for ex in strength_exercises if ex['muscle_group'] in ['chest', 'back', 'shoulders', 'arms']] lower_body = [ex for ex in strength_exercises if ex['muscle_group'] == 'legs'] cardio_exercises = [ex for ex in exercises if ex['category'] == 'cardio'] flexibility_exercises = [ex for ex in exercises if ex['category'] == 'flexibility'] # Distribute exercises based on number of days if days_per_week <= 3: # Full body workouts for day in workout_days: day_exercises = [] day_exercises.extend(random.sample(upper_body, min(2, len(upper_body)))) day_exercises.extend(random.sample(lower_body, min(2, len(lower_body)))) day_exercises.extend(random.sample(cardio_exercises, min(1, len(cardio_exercises)))) day_exercises.extend(random.sample(flexibility_exercises, min(1, len(flexibility_exercises)))) schedule[day] = day_exercises elif days_per_week == 4: # Upper/Lower split upper_days = [workout_days[0], workout_days[2]] lower_days = [workout_days[1], workout_days[3]] for day in upper_days: day_exercises = [] day_exercises.extend(random.sample(upper_body, min(4, len(upper_body)))) day_exercises.extend(random.sample(cardio_exercises, min(1, len(cardio_exercises)))) day_exercises.extend(random.sample(flexibility_exercises, min(1, len(flexibility_exercises)))) schedule[day] = day_exercises for day in lower_days: day_exercises = [] day_exercises.extend(random.sample(lower_body, min(3, len(lower_body)))) day_exercises.extend(random.sample(cardio_exercises, min(1, len(cardio_exercises)))) day_exercises.extend(random.sample(flexibility_exercises, min(1, len(flexibility_exercises)))) schedule[day] = day_exercises else: # Push/Pull/Legs or other specialized split random.shuffle(strength_exercises) split_size = len(strength_exercises) // (days_per_week - 1) for i, day in enumerate(workout_days[:-1]): start_idx = i * split_size end_idx = (i + 1) * split_size if i < days_per_week - 2 else len(strength_exercises) day_exercises = strength_exercises[start_idx:end_idx] # Add some cardio to each day day_exercises.extend(random.sample(cardio_exercises, min(1, len(cardio_exercises)))) schedule[day] = day_exercises # Last day is cardio and flexibility schedule[workout_days[-1]] = random.sample(cardio_exercises, min(2, len(cardio_exercises))) + flexibility_exercises return schedule def combine_nutrition_advice(body_type_advice, goal_advice): """Combine nutrition advice from body type and goal""" return f"Body Type Recommendation: {body_type_advice}\n\nGoal-Based Recommendation: {goal_advice}" def format_workout_plan(plan, user_profile): """Format the workout plan into a readable string""" result = "" # Add header with user stats result += f"## PERSONALIZED WORKOUT PLAN\n\n" result += f"### USER PROFILE\n" result += f"- Age: {user_profile['age']}\n" result += f"- Height: {user_profile['height']} cm\n" result += f"- Weight: {user_profile['weight']} kg\n" result += f"- Gender: {user_profile['gender'].capitalize()}\n" result += f"- Body Type: {user_profile['body_type'].capitalize()}\n" result += f"- Activity Level: {user_profile['activity_level'].replace('_', ' ').capitalize()}\n" result += f"- Fitness Goal: {user_profile['goal'].replace('_', ' ').capitalize()}\n" # Add BMI and calorie calculations bmi = round(user_profile['weight'] / ((user_profile['height'] / 100) ** 2), 1) bmr = calculate_bmr(user_profile['weight'], user_profile['height'], user_profile['age'], user_profile['gender']) daily_calories = calculate_daily_calories(bmr, user_profile['activity_level'], user_profile['goal']) result += f"- BMI: {bmi} " if bmi < 18.5: result += "(Underweight)" elif bmi < 25: result += "(Normal weight)" elif bmi < 30: result += "(Overweight)" else: result += "(Obese)" result += f"\n- Recommended Daily Calories: {daily_calories} kcal\n\n" # Add health condition advice if applicable if user_profile['health_condition'] != 'none': result += f"### HEALTH CONSIDERATIONS\n" result += f"Based on your {user_profile['health_condition'].replace('_', ' ')}, please note:\n\n" result += f"{plan['health_advice']}\n\n" result += f"Recommended exercises for your condition:\n" for ex in plan['recommended_exercises']: result += f"- {ex}\n" result += "\n" # Add weekly schedule result += f"### WEEKLY WORKOUT SCHEDULE\n\n" for day, exercises in plan['schedule'].items(): result += f"#### {day}\n" if exercises: for i, ex in enumerate(exercises, 1): result += f"{i}. {ex['name']} " if ex['category'] == 'strength': result += f"({plan['sets']} sets of {plan['reps']} reps, {plan['rest']} rest)" elif ex['category'] == 'cardio': if ex['name'] in ['HIIT', 'Circuit Training']: result += "(20-30 minutes, including work/rest intervals)" else: result += "(30-45 minutes, moderate intensity)" else: # flexibility result += "(15-20 minutes)" result += "\n" else: result += "Rest Day\n" result += "\n" # Add nutrition advice result += f"### NUTRITION RECOMMENDATIONS\n\n" result += f"{plan['nutrition']}\n\n" # Add progression tips result += f"### PROGRESSION TIPS\n\n" result += "1. Increase weight by 5-10% when you can complete all sets and reps with good form\n" result += "2. For cardio, gradually increase duration by 5 minutes or intensity by 5-10%\n" result += "3. Track your workouts to ensure progressive overload\n" result += "4. Aim for 7-9 hours of quality sleep per night for recovery\n" result += "5. Stay hydrated with at least 3 liters of water daily\n\n" result += "### NOTES\n" result += "- Always warm up for 5-10 minutes before each workout\n" result += "- Cool down with 5-10 minutes of light activity and stretching\n" result += "- Listen to your body and adjust intensity as needed\n" result += "- Consistency is more important than perfection\n" return result def generate_meal_plan(user_profile): """Generate a personalized meal plan based on user profile""" weight = user_profile['weight'] goal = user_profile['goal'] health_condition = user_profile['health_condition'] body_type = user_profile['body_type'] # Get diet recommendations based on goal diet_rec = diet_recommendations[goal] # Calculate daily calorie needs bmr = calculate_bmr(weight, user_profile['height'], user_profile['age'], user_profile['gender']) activity_multiplier = activity_multipliers[user_profile['activity_level']] tdee = bmr * activity_multiplier # Adjust calories based on goal if goal == 'weight_loss': daily_calories = int(tdee - diet_rec['calorie_deficit']) elif goal == 'muscle_gain': daily_calories = int(tdee + diet_rec['calorie_surplus']) else: daily_calories = int(tdee) # Adjust based on body type if body_type == 'ectomorph' and goal == 'muscle_gain': daily_calories += 200 elif body_type == 'endomorph' and goal == 'weight_loss': daily_calories -= 100 # Calculate macronutrients protein_grams = round(weight * diet_rec['protein_factor']) carb_grams = round(weight * diet_rec['carb_factor']) fat_grams = round(weight * diet_rec['fat_factor']) # Adjust based on health condition if needed health_adjustments = health_condition_diet_adjustments.get(health_condition, {}) # Calculate calories from each macro protein_cals = protein_grams * 4 carb_cals = carb_grams * 4 fat_cals = fat_grams * 9 # Generate sample meals meal_count = diet_rec['meal_count'] sample_meals = generate_sample_meals(diet_rec, meal_count, protein_grams, carb_grams, fat_grams, health_adjustments) # Create the meal plan dictionary meal_plan = { 'daily_calories': daily_calories, 'macros': { 'protein': { 'grams': protein_grams, 'calories': protein_cals, 'percentage': round((protein_cals / daily_calories) * 100) }, 'carbs': { 'grams': carb_grams, 'calories': carb_cals, 'percentage': round((carb_cals / daily_calories) * 100) }, 'fats': { 'grams': fat_grams, 'calories': fat_cals, 'percentage': round((fat_cals / daily_calories) * 100) } }, 'meal_schedule': sample_meals, 'foods_to_include': diet_rec['sample_foods'], 'foods_to_avoid': diet_rec['avoid'], 'tips': diet_rec['tips'], } # Add health condition specific recommendations if applicable if health_condition != 'none': meal_plan['health_recommendations'] = { 'beneficial_foods': health_adjustments.get('beneficial_foods', []), 'avoid_foods': health_adjustments.get('avoid_foods', []), 'advice': health_adjustments.get('advice', '') } return meal_plan def generate_sample_meals(diet_rec, meal_count, daily_protein, daily_carbs, daily_fats, health_adjustments=None): """Generate sample meals based on diet recommendations and macros""" meals = {} meal_names = ["Breakfast", "Morning Snack", "Lunch", "Afternoon Snack", "Dinner", "Evening Snack"] # Adjust meal names based on meal count if meal_count == 3: selected_meals = ["Breakfast", "Lunch", "Dinner"] elif meal_count == 4: selected_meals = ["Breakfast", "Lunch", "Afternoon Snack", "Dinner"] elif meal_count == 5: selected_meals = ["Breakfast", "Morning Snack", "Lunch", "Afternoon Snack", "Dinner"] else: # 6 meals selected_meals = meal_names # Get sample foods, considering health adjustments proteins = diet_rec['sample_foods']['proteins'] carbs = diet_rec['sample_foods']['carbs'] fats = diet_rec['sample_foods']['fats'] vegetables = diet_rec['sample_foods']['vegetables'] snacks = diet_rec['sample_foods']['snacks'] # Filter out foods to avoid if health condition exists if health_adjustments and 'avoid_foods' in health_adjustments: avoid_foods = health_adjustments['avoid_foods'] proteins = [p for p in proteins if p not in avoid_foods] carbs = [c for c in carbs if c not in avoid_foods] fats = [f for f in fats if f not in avoid_foods] vegetables = [v for v in vegetables if v not in avoid_foods] snacks = [s for s in snacks if s not in avoid_foods and not any(avoid in s for avoid in avoid_foods)] # Create basic meal templates based on meal type for meal in selected_meals: if "Snack" in meal: # Snacks are simpler meals[meal] = { 'description': random.choice(snacks), 'protein': round(daily_protein / meal_count / 2, 1), 'carbs': round(daily_carbs / meal_count / 2, 1), 'fats': round(daily_fats / meal_count / 2, 1) } elif meal == "Breakfast": protein_choice = random.choice(proteins) carb_choice = random.choice(carbs) fat_choice = random.choice(fats) meals[meal] = { 'description': f"{carb_choice} with {protein_choice} and {fat_choice}", 'protein': round(daily_protein * 0.25, 1), 'carbs': round(daily_carbs * 0.25, 1), 'fats': round(daily_fats * 0.2, 1) } elif meal == "Lunch" or meal == "Dinner": protein_choice = random.choice(proteins) carb_choice = random.choice(carbs) fat_choice = random.choice(fats) veg_choice = random.choice(vegetables) meals[meal] = { 'description': f"{protein_choice} with {carb_choice}, {veg_choice}, and {fat_choice}", 'protein': round(daily_protein * 0.3, 1), 'carbs': round(daily_carbs * 0.3, 1), 'fats': round(daily_fats * 0.3, 1) } return meals def format_meal_plan(meal_plan, user_profile): """Format the meal plan into a readable string""" result = "" # Add header result += "## PERSONALIZED NUTRITION PLAN\n\n" # Add summary of calories and macros result += "### DAILY NUTRITIONAL TARGETS\n" result += f"- Daily Calories: {meal_plan['daily_calories']} kcal\n" result += f"- Protein: {meal_plan['macros']['protein']['grams']}g ({meal_plan['macros']['protein']['percentage']}% of calories)\n" result += f"- Carbohydrates: {meal_plan['macros']['carbs']['grams']}g ({meal_plan['macros']['carbs']['percentage']}% of calories)\n" result += f"- Fats: {meal_plan['macros']['fats']['grams']}g ({meal_plan['macros']['fats']['percentage']}% of calories)\n\n" # Add health-specific recommendations if applicable if user_profile['health_condition'] != 'none': result += "### HEALTH-SPECIFIC RECOMMENDATIONS\n" result += f"Based on your {user_profile['health_condition'].replace('_', ' ')}, please consider:\n\n" result += f"{meal_plan['health_recommendations']['advice']}\n\n" result += "Beneficial foods to include:\n" for food in meal_plan['health_recommendations']['beneficial_foods']: result += f"- {food}\n" result += "\nFoods to limit or avoid:\n" for food in meal_plan['health_recommendations']['avoid_foods']: result += f"- {food}\n" result += "\n" # Add sample meal plan result += "### SAMPLE MEAL PLAN\n\n" for meal_name, meal_info in meal_plan['meal_schedule'].items(): result += f"#### {meal_name}\n" result += f"{meal_info['description']}\n" result += f"- Protein: {meal_info['protein']}g\n" result += f"- Carbs: {meal_info['carbs']}g\n" result += f"- Fats: {meal_info['fats']}g\n\n" # Add recommended foods list result += "### RECOMMENDED FOODS\n\n" result += "#### Protein Sources\n" for food in meal_plan['foods_to_include']['proteins']: result += f"- {food}\n" result += "\n#### Carbohydrate Sources\n" for food in meal_plan['foods_to_include']['carbs']: result += f"- {food}\n" result += "\n#### Healthy Fat Sources\n" for food in meal_plan['foods_to_include']['fats']: result += f"- {food}\n" result += "\n#### Vegetables\n" for food in meal_plan['foods_to_include']['vegetables']: result += f"- {food}\n" # Add foods to avoid result += "\n### FOODS TO LIMIT OR AVOID\n" for food in meal_plan['foods_to_avoid']: result += f"- {food}\n" # Add nutrition tips result += "\n### NUTRITION TIPS\n" for i, tip in enumerate(meal_plan['tips'], 1): result += f"{i}. {tip}\n" return result # Update the generate_workout_plan function to include diet plan def generate_workout_plan(age, weight, height, gender, body_type, activity_level, goal, health_condition): """Main function to generate a workout and diet plan based on user inputs""" user_profile = { 'age': age, 'weight': weight, 'height': height, 'gender': gender, 'body_type': body_type, 'activity_level': activity_level, 'goal': goal, 'health_condition': health_condition } # Get workout recommendations workout_plan = get_exercise_recommendations(user_profile) # Get diet recommendations diet_plan = generate_meal_plan(user_profile) # Format the plans into readable strings formatted_workout_plan = format_workout_plan(workout_plan, user_profile) formatted_diet_plan = format_meal_plan(diet_plan, user_profile) # Combine the two plans combined_plan = formatted_workout_plan + "\n\n" + formatted_diet_plan return combined_plan # Update the Gradio interface to include diet plan options def create_gradio_interface(): with gr.Blocks(title="AI Fitness & Nutrition Plan Generator") as app: gr.Markdown("# AI Fitness & Nutrition Plan Generator") gr.Markdown("Enter your details below to get a personalized workout and diet plan") with gr.Row(): with gr.Column(): age = gr.Slider(label="Age", minimum=16, maximum=80, value=30, step=1) weight = gr.Slider(label="Weight (kg)", minimum=40, maximum=150, value=70, step=1) height = gr.Slider(label="Height (cm)", minimum=140, maximum=220, value=175, step=1) gender = gr.Radio(label="Gender", choices=["male", "female"], value="male") body_type = gr.Radio( label="Body Type", choices=["ectomorph", "mesomorph", "endomorph"], value="mesomorph", info="Ectomorph (slim), Mesomorph (athletic), Endomorph (broader)" ) activity_level = gr.Radio( label="Activity Level", choices=["sedentary", "lightly_active", "moderately_active", "very_active", "extra_active"], value="moderately_active", info="Daily activity level excluding planned workouts" ) goal = gr.Radio( label="Primary Fitness Goal", choices=["weight_loss", "muscle_gain", "endurance", "flexibility", "general_fitness"], value="general_fitness" ) health_condition = gr.Radio( label="Health Condition", choices=["none", "back_pain", "knee_pain", "shoulder_pain", "hypertension", "diabetes"], value="none", info="Select any condition that might affect your exercise selection" ) # Add dietary preference options dietary_preference = gr.Radio( label="Dietary Preference", choices=["standard", "vegetarian", "vegan", "pescatarian", "keto", "paleo"], value="standard", info="Select your dietary preference for meal planning" ) food_allergies = gr.CheckboxGroup( label="Food Allergies/Intolerances", choices=["none", "gluten", "dairy", "nuts", "shellfish", "eggs", "soy"], value=["none"], info="Select any food allergies or intolerances" ) generate_button = gr.Button("Generate Fitness & Nutrition Plan") # Exercise data search exercise_name = gr.Textbox(label="Exercise Name to Search on MyFitnessPal") get_exercise_data_button = gr.Button("Get Exercise Data from MyFitnessPal") with gr.Column(): output = gr.Markdown(label="Your Personalized Fitness & Nutrition Plan") mfp_output = gr.JSON(label="MyFitnessPal Exercise Data") # Update the function call to include the new parameters generate_button.click( generate_workout_plan, inputs=[age, weight, height, gender, body_type, activity_level, goal, health_condition], outputs=output ) get_exercise_data_button.click( scrape_myfitnesspal_exercise_data, inputs=exercise_name, outputs=mfp_output ) return app # Launch the app if __name__ == "__main__": app = create_gradio_interface() app.launch()