//
//  AchievementsListView.swift
//  SportsTime
//
//  Displays achievements gallery with earned, in-progress, and locked badges.
//

import SwiftUI
import SwiftData

struct AchievementsListView: View {
    @Environment(\.modelContext) private var modelContext
    @Environment(\.colorScheme) private var colorScheme

    @State private var achievements: [AchievementProgress] = []
    @State private var isLoading = true
    @State private var selectedCategory: AchievementCategory?
    @State private var selectedAchievement: AchievementProgress?

    var body: some View {
        ScrollView {
            VStack(spacing: Theme.Spacing.lg) {
                // Summary header
                achievementSummary
                    .staggeredAnimation(index: 0)

                // Category filter
                categoryFilter
                    .staggeredAnimation(index: 1)

                // Achievements grid
                achievementsGrid
                    .staggeredAnimation(index: 2)
            }
            .padding(Theme.Spacing.md)
        }
        .themedBackground()
        .navigationTitle("Achievements")
        .task {
            await loadAchievements()
        }
        .sheet(item: $selectedAchievement) { achievement in
            AchievementDetailSheet(achievement: achievement)
                .presentationDetents([.medium])
        }
    }

    // MARK: - Achievement Summary

    private var achievementSummary: some View {
        let earned = achievements.filter { $0.isEarned }.count
        let total = achievements.count

        return HStack(spacing: Theme.Spacing.lg) {
            // Trophy icon
            ZStack {
                Circle()
                    .fill(Theme.warmOrange.opacity(0.15))
                    .frame(width: 70, height: 70)

                Image(systemName: "trophy.fill")
                    .font(.system(size: 32))
                    .foregroundStyle(Theme.warmOrange)
            }

            VStack(alignment: .leading, spacing: Theme.Spacing.xs) {
                Text("\(earned) / \(total)")
                    .font(.system(size: Theme.FontSize.heroTitle, weight: .bold, design: .rounded))
                    .foregroundStyle(Theme.textPrimary(colorScheme))

                Text("Achievements Earned")
                    .font(.system(size: Theme.FontSize.body))
                    .foregroundStyle(Theme.textSecondary(colorScheme))

                if earned == total && total > 0 {
                    HStack(spacing: 4) {
                        Image(systemName: "star.fill")
                        Text("All achievements unlocked!")
                    }
                    .font(.system(size: Theme.FontSize.caption, weight: .semibold))
                    .foregroundStyle(Theme.warmOrange)
                }
            }

            Spacer()
        }
        .padding(Theme.Spacing.lg)
        .background(Theme.cardBackground(colorScheme))
        .clipShape(RoundedRectangle(cornerRadius: Theme.CornerRadius.large))
        .overlay {
            RoundedRectangle(cornerRadius: Theme.CornerRadius.large)
                .stroke(Theme.surfaceGlow(colorScheme), lineWidth: 1)
        }
        .shadow(color: Theme.cardShadow(colorScheme), radius: 10, y: 5)
    }

    // MARK: - Category Filter

    private var categoryFilter: some View {
        ScrollView(.horizontal, showsIndicators: false) {
            HStack(spacing: Theme.Spacing.sm) {
                CategoryFilterButton(
                    title: "All",
                    icon: "square.grid.2x2",
                    isSelected: selectedCategory == nil
                ) {
                    withAnimation(Theme.Animation.spring) {
                        selectedCategory = nil
                    }
                }

                ForEach(AchievementCategory.allCases, id: \.self) { category in
                    CategoryFilterButton(
                        title: category.displayName,
                        icon: category.iconName,
                        isSelected: selectedCategory == category
                    ) {
                        withAnimation(Theme.Animation.spring) {
                            selectedCategory = category
                        }
                    }
                }
            }
        }
    }

    // MARK: - Achievements Grid

    private var achievementsGrid: some View {
        let filtered = filteredAchievements

        return LazyVGrid(
            columns: [GridItem(.flexible()), GridItem(.flexible())],
            spacing: Theme.Spacing.md
        ) {
            ForEach(filtered) { achievement in
                AchievementCard(achievement: achievement)
                    .onTapGesture {
                        selectedAchievement = achievement
                    }
            }
        }
    }

    private var filteredAchievements: [AchievementProgress] {
        guard let category = selectedCategory else {
            return achievements.sorted { first, second in
                // Earned first, then by progress
                if first.isEarned != second.isEarned {
                    return first.isEarned
                }
                return first.progressPercentage > second.progressPercentage
            }
        }
        return achievements.filter { $0.definition.category == category }
            .sorted { first, second in
                if first.isEarned != second.isEarned {
                    return first.isEarned
                }
                return first.progressPercentage > second.progressPercentage
            }
    }

    // MARK: - Data Loading

    private func loadAchievements() async {
        isLoading = true
        do {
            let engine = AchievementEngine(modelContext: modelContext)
            achievements = try await engine.getProgress()
        } catch {
            // Handle error silently, show empty state
            achievements = []
        }
        isLoading = false
    }
}

// MARK: - Category Filter Button

struct CategoryFilterButton: View {
    let title: String
    let icon: String
    let isSelected: Bool
    let action: () -> Void

    @Environment(\.colorScheme) private var colorScheme

    var body: some View {
        Button(action: action) {
            HStack(spacing: Theme.Spacing.xs) {
                Image(systemName: icon)
                    .font(.system(size: 14))
                Text(title)
                    .font(.system(size: Theme.FontSize.caption, weight: .medium))
            }
            .padding(.horizontal, Theme.Spacing.md)
            .padding(.vertical, Theme.Spacing.sm)
            .background(isSelected ? Theme.warmOrange : Theme.cardBackground(colorScheme))
            .foregroundStyle(isSelected ? .white : Theme.textPrimary(colorScheme))
            .clipShape(Capsule())
            .overlay {
                Capsule()
                    .stroke(isSelected ? Color.clear : Theme.surfaceGlow(colorScheme), lineWidth: 1)
            }
        }
        .buttonStyle(.plain)
    }
}

// MARK: - Achievement Card

struct AchievementCard: View {
    let achievement: AchievementProgress

    @Environment(\.colorScheme) private var colorScheme

    var body: some View {
        VStack(spacing: Theme.Spacing.sm) {
            // Badge icon
            ZStack {
                Circle()
                    .fill(badgeBackgroundColor)
                    .frame(width: 60, height: 60)

                Image(systemName: achievement.definition.iconName)
                    .font(.system(size: 28))
                    .foregroundStyle(badgeIconColor)

                if !achievement.isEarned {
                    Circle()
                        .fill(.black.opacity(0.3))
                        .frame(width: 60, height: 60)

                    Image(systemName: "lock.fill")
                        .font(.system(size: 14))
                        .foregroundStyle(.white)
                }
            }

            // Title
            Text(achievement.definition.name)
                .font(.system(size: Theme.FontSize.caption, weight: .semibold))
                .foregroundStyle(achievement.isEarned ? Theme.textPrimary(colorScheme) : Theme.textMuted(colorScheme))
                .multilineTextAlignment(.center)
                .lineLimit(2)
                .fixedSize(horizontal: false, vertical: true)

            // Progress or earned date
            if achievement.isEarned {
                if let earnedAt = achievement.earnedAt {
                    Text(earnedAt.formatted(date: .abbreviated, time: .omitted))
                        .font(.system(size: Theme.FontSize.micro))
                        .foregroundStyle(Theme.warmOrange)
                }
            } else {
                // Progress bar
                VStack(spacing: 4) {
                    ProgressView(value: achievement.progressPercentage)
                        .progressViewStyle(AchievementProgressStyle())

                    Text(achievement.progressText)
                        .font(.system(size: Theme.FontSize.micro))
                        .foregroundStyle(Theme.textMuted(colorScheme))
                }
            }
        }
        .padding(Theme.Spacing.md)
        .frame(maxWidth: .infinity, minHeight: 170)
        .background(Theme.cardBackground(colorScheme))
        .clipShape(RoundedRectangle(cornerRadius: Theme.CornerRadius.medium))
        .overlay {
            RoundedRectangle(cornerRadius: Theme.CornerRadius.medium)
                .stroke(achievement.isEarned ? Theme.warmOrange.opacity(0.5) : Theme.surfaceGlow(colorScheme), lineWidth: achievement.isEarned ? 2 : 1)
        }
        .shadow(color: Theme.cardShadow(colorScheme), radius: 5, y: 2)
        .opacity(achievement.isEarned ? 1.0 : 0.7)
    }

    private var badgeBackgroundColor: Color {
        if achievement.isEarned {
            return categoryColor.opacity(0.2)
        }
        return Theme.cardBackgroundElevated(colorScheme)
    }

    private var badgeIconColor: Color {
        if achievement.isEarned {
            return categoryColor
        }
        return Theme.textMuted(colorScheme)
    }

    private var categoryColor: Color {
        switch achievement.definition.category {
        case .count:
            return Theme.warmOrange
        case .division:
            return Theme.routeGold
        case .conference:
            return Theme.routeAmber
        case .league:
            return Color(hex: "FFD700") // Gold
        case .journey:
            return Color(hex: "9B59B6") // Purple
        case .special:
            return Color(hex: "E74C3C") // Red
        }
    }
}

// MARK: - Achievement Progress Style

struct AchievementProgressStyle: ProgressViewStyle {
    @Environment(\.colorScheme) private var colorScheme

    func makeBody(configuration: Configuration) -> some View {
        GeometryReader { geometry in
            ZStack(alignment: .leading) {
                RoundedRectangle(cornerRadius: 2)
                    .fill(Theme.cardBackgroundElevated(colorScheme))
                    .frame(height: 4)

                RoundedRectangle(cornerRadius: 2)
                    .fill(Theme.warmOrange)
                    .frame(width: geometry.size.width * CGFloat(configuration.fractionCompleted ?? 0), height: 4)
            }
        }
        .frame(height: 4)
    }
}

// MARK: - Achievement Detail Sheet

struct AchievementDetailSheet: View {
    let achievement: AchievementProgress

    @Environment(\.colorScheme) private var colorScheme
    @Environment(\.dismiss) private var dismiss

    var body: some View {
        NavigationStack {
            VStack(spacing: Theme.Spacing.xl) {
                // Large badge
                ZStack {
                    Circle()
                        .fill(badgeBackgroundColor)
                        .frame(width: 120, height: 120)

                    if achievement.isEarned {
                        Circle()
                            .stroke(Theme.warmOrange, lineWidth: 4)
                            .frame(width: 130, height: 130)
                    }

                    Image(systemName: achievement.definition.iconName)
                        .font(.system(size: 56))
                        .foregroundStyle(badgeIconColor)

                    if !achievement.isEarned {
                        Circle()
                            .fill(.black.opacity(0.3))
                            .frame(width: 120, height: 120)

                        Image(systemName: "lock.fill")
                            .font(.system(size: 24))
                            .foregroundStyle(.white)
                    }
                }

                // Title and description
                VStack(spacing: Theme.Spacing.sm) {
                    Text(achievement.definition.name)
                        .font(.system(size: Theme.FontSize.sectionTitle, weight: .bold, design: .rounded))
                        .foregroundStyle(Theme.textPrimary(colorScheme))

                    Text(achievement.definition.description)
                        .font(.system(size: Theme.FontSize.body))
                        .foregroundStyle(Theme.textSecondary(colorScheme))
                        .multilineTextAlignment(.center)

                    // Category badge
                    HStack(spacing: 4) {
                        Image(systemName: achievement.definition.category.iconName)
                        Text(achievement.definition.category.displayName)
                    }
                    .font(.system(size: Theme.FontSize.caption))
                    .foregroundStyle(categoryColor)
                    .padding(.horizontal, Theme.Spacing.sm)
                    .padding(.vertical, Theme.Spacing.xs)
                    .background(categoryColor.opacity(0.15))
                    .clipShape(Capsule())
                }

                // Status section
                if achievement.isEarned {
                    if let earnedAt = achievement.earnedAt {
                        VStack(spacing: 4) {
                            Image(systemName: "checkmark.seal.fill")
                                .font(.system(size: 24))
                                .foregroundStyle(.green)

                            Text("Earned on \(earnedAt.formatted(date: .long, time: .omitted))")
                                .font(.system(size: Theme.FontSize.body, weight: .medium))
                                .foregroundStyle(Theme.textPrimary(colorScheme))
                        }
                    }
                } else {
                    // Progress section
                    VStack(spacing: Theme.Spacing.sm) {
                        Text("Progress")
                            .font(.system(size: Theme.FontSize.caption, weight: .medium))
                            .foregroundStyle(Theme.textMuted(colorScheme))

                        ProgressView(value: achievement.progressPercentage)
                            .progressViewStyle(LargeProgressStyle())
                            .frame(width: 200)

                        Text("\(achievement.currentProgress) / \(achievement.totalRequired)")
                            .font(.system(size: Theme.FontSize.cardTitle, weight: .bold))
                            .foregroundStyle(Theme.textPrimary(colorScheme))
                    }
                }

                // Sport badge if applicable
                if let sport = achievement.definition.sport {
                    HStack(spacing: Theme.Spacing.xs) {
                        Image(systemName: sport.iconName)
                        Text(sport.displayName)
                    }
                    .font(.system(size: Theme.FontSize.caption, weight: .medium))
                    .foregroundStyle(sport.themeColor)
                    .padding(.horizontal, Theme.Spacing.md)
                    .padding(.vertical, Theme.Spacing.sm)
                    .background(sport.themeColor.opacity(0.15))
                    .clipShape(Capsule())
                }

                Spacer()
            }
            .padding(Theme.Spacing.lg)
            .navigationBarTitleDisplayMode(.inline)
            .toolbar {
                ToolbarItem(placement: .cancellationAction) {
                    Button("Done") { dismiss() }
                }
            }
        }
    }

    private var badgeBackgroundColor: Color {
        if achievement.isEarned {
            return categoryColor.opacity(0.2)
        }
        return Theme.cardBackgroundElevated(colorScheme)
    }

    private var badgeIconColor: Color {
        if achievement.isEarned {
            return categoryColor
        }
        return Theme.textMuted(colorScheme)
    }

    private var categoryColor: Color {
        switch achievement.definition.category {
        case .count:
            return Theme.warmOrange
        case .division:
            return Theme.routeGold
        case .conference:
            return Theme.routeAmber
        case .league:
            return Color(hex: "FFD700")
        case .journey:
            return Color(hex: "9B59B6")
        case .special:
            return Color(hex: "E74C3C")
        }
    }
}

// MARK: - Large Progress Style

struct LargeProgressStyle: ProgressViewStyle {
    @Environment(\.colorScheme) private var colorScheme

    func makeBody(configuration: Configuration) -> some View {
        GeometryReader { geometry in
            ZStack(alignment: .leading) {
                RoundedRectangle(cornerRadius: 4)
                    .fill(Theme.cardBackgroundElevated(colorScheme))
                    .frame(height: 8)

                RoundedRectangle(cornerRadius: 4)
                    .fill(Theme.warmOrange)
                    .frame(width: geometry.size.width * CGFloat(configuration.fractionCompleted ?? 0), height: 8)
            }
        }
        .frame(height: 8)
    }
}

// MARK: - Category Extensions

extension AchievementCategory {
    var iconName: String {
        switch self {
        case .count: return "number.circle"
        case .division: return "map"
        case .conference: return "building.2"
        case .league: return "crown"
        case .journey: return "car.fill"
        case .special: return "star.circle"
        }
    }
}

// MARK: - Preview

#Preview {
    NavigationStack {
        AchievementsListView()
    }
    .modelContainer(for: StadiumVisit.self, inMemory: true)
}
