//
// WorkoutLogsView.swift
// Workouts
//
// Created by rzen on 7/13/25 at 6:52 PM.
//
// Copyright 2025 Rouslan Zenetl. All Rights Reserved.
//

import SwiftUI
import SwiftData

struct WorkoutLogsView: View {
    @Environment(SyncEngine.self) private var sync

    @Query(sort: \Workout.start, order: .reverse)
    private var workouts: [Workout]

    @State private var showingSplitPicker = false
    @State private var showingSettings = false
    @State private var itemToDelete: Workout?

    // WorkoutLogsView is the app's root screen, so it owns its NavigationStack.
    var body: some View {
        NavigationStack {
            List {
                ForEach(workouts) { workout in
                    NavigationLink {
                        WorkoutLogListView(workout: workout)
                    } label: {
                        CalendarListItem(
                            date: workout.start,
                            title: workout.splitName ?? Split.unnamed,
                            subtitle: getSubtitle(for: workout),
                            subtitle2: workout.statusName
                        )
                    }
                    .swipeActions(edge: .trailing, allowsFullSwipe: false) {
                        Button {
                            itemToDelete = workout
                        } label: {
                            Label("Delete", systemImage: "trash")
                        }
                        .tint(.red)
                    }
                }
            }
            .overlay {
                if workouts.isEmpty {
                    ContentUnavailableView(
                        "No Workouts Yet",
                        systemImage: "list.bullet.clipboard",
                        description: Text("Start a new workout from one of your splits.")
                    )
                }
            }
            .navigationTitle("Workout Logs")
            .toolbar {
                ToolbarItem(placement: .navigationBarLeading) {
                    Button {
                        showingSettings = true
                    } label: {
                        Image(systemName: "gearshape.2")
                    }
                }
                ToolbarItem(placement: .navigationBarTrailing) {
                    Button("Start New") {
                        showingSplitPicker.toggle()
                    }
                }
            }
            .sheet(isPresented: $showingSettings) {
                SettingsView()
            }
            .sheet(isPresented: $showingSplitPicker) {
                SplitPickerSheet()
            }
            .confirmationDialog(
                "Delete Workout?",
                isPresented: Binding(
                    get: { itemToDelete != nil },
                    set: { if !$0 { itemToDelete = nil } }
                ),
                titleVisibility: .visible,
                presenting: itemToDelete
            ) { workout in
                Button("Delete", role: .destructive) {
                    Task { await sync.delete(workout: workout) }
                    itemToDelete = nil
                }
                Button("Cancel", role: .cancel) {
                    itemToDelete = nil
                }
            }
        }
    }

    private func getSubtitle(for workout: Workout) -> String {
        if workout.status == .completed, let endDate = workout.end {
            return workout.start.humanTimeInterval(to: endDate)
        } else {
            return workout.start.formattedDate()
        }
    }
}

// MARK: - Split Picker Sheet

struct SplitPickerSheet: View {
    @Environment(SyncEngine.self) private var sync
    @Environment(AppServices.self) private var services
    @Environment(\.dismiss) private var dismiss

    @Query(sort: [SortDescriptor(\Split.order), SortDescriptor(\Split.name)])
    private var splits: [Split]

    var body: some View {
        NavigationStack {
            List {
                ForEach(splits) { split in
                    Button {
                        startWorkout(with: split)
                    } label: {
                        HStack {
                            Image(systemName: split.systemImage)
                                .foregroundColor(Color.color(from: split.color))
                            Text(split.name)
                            Spacer()
                            Text("\(split.exercisesArray.count) exercises")
                                .font(.caption)
                                .foregroundColor(.secondary)
                        }
                    }
                }
            }
            .navigationTitle("Select a Split")
            .toolbar {
                ToolbarItem(placement: .navigationBarLeading) {
                    Button("Cancel") {
                        dismiss()
                    }
                }
            }
        }
    }

    private func startWorkout(with split: Split) {
        let start = Date()
        let logs = split.exercisesArray.enumerated().map { index, exercise in
            WorkoutLogDocument(
                id: ULID.make(),
                exerciseName: exercise.name,
                order: index,
                sets: exercise.sets,
                reps: exercise.reps,
                weight: exercise.weight,
                loadType: exercise.loadType,
                durationSeconds: exercise.durationTotalSeconds,
                currentStateIndex: 0,
                completed: false,
                status: WorkoutStatus.notStarted.rawValue,
                notes: nil,
                date: start
            )
        }

        // A freshly started workout has no `end` — only completion stamps it.
        let doc = WorkoutDocument(
            schemaVersion: WorkoutDocument.currentSchema,
            id: ULID.make(),
            splitID: split.id,
            splitName: split.name,
            start: start,
            end: nil,
            status: WorkoutStatus.notStarted.rawValue,
            createdAt: start,
            updatedAt: start,
            logs: logs
        )

        Task { await sync.save(workout: doc) }
        // Bring the Apple Watch up into the session so the user can run it from the wrist.
        services.workoutLauncher.launchWatchWorkout()
        dismiss()
    }
}
