import WidgetKit
import SwiftUI
import SharedModels

struct WeekProgressEntry: TimelineEntry {
    let date: Date
    let data: WidgetData
}

struct WeekProgressProvider: TimelineProvider {
    func placeholder(in context: Context) -> WeekProgressEntry {
        WeekProgressEntry(date: Date(), data: .placeholder)
    }

    func getSnapshot(in context: Context, completion: @escaping (WeekProgressEntry) -> Void) {
        if context.isPreview {
            completion(WeekProgressEntry(date: Date(), data: .placeholder))
            return
        }
        completion(WeekProgressEntry(date: Date(), data: WidgetDataReader.read()))
    }

    func getTimeline(in context: Context, completion: @escaping (Timeline<WeekProgressEntry>) -> Void) {
        let data = WidgetDataReader.read()
        var entries: [WeekProgressEntry] = []
        let now = Date()
        for offset in 0..<8 {
            let date = Calendar.current.date(byAdding: .minute, value: offset * 15, to: now)!
            entries.append(WeekProgressEntry(date: date, data: data))
        }
        completion(Timeline(entries: entries, policy: .atEnd))
    }
}

struct WeekProgressWidget: Widget {
    let kind = "WeekProgressWidget"

    var body: some WidgetConfiguration {
        StaticConfiguration(kind: kind, provider: WeekProgressProvider()) { entry in
            WeekProgressWidgetView(entry: entry)
                .containerBackground(.fill.tertiary, for: .widget)
        }
        .configurationDisplayName("Week Progress")
        .description("See your current week and latest test score.")
        .supportedFamilies([.systemMedium])
    }
}

struct WeekProgressWidgetView: View {
    let entry: WeekProgressEntry

    var body: some View {
        HStack(spacing: 16) {
            // Left: Week + Streak
            VStack(spacing: 10) {
                VStack(spacing: 2) {
                    Text("WEEK")
                        .font(.caption2.weight(.semibold))
                        .foregroundStyle(.secondary)
                    Text("\(entry.data.currentWeek)")
                        .font(.system(size: 40, weight: .bold, design: .rounded))
                }

                if entry.data.currentStreak > 0 {
                    HStack(spacing: 3) {
                        Image(systemName: "flame.fill")
                            .foregroundStyle(.orange)
                        Text("\(entry.data.currentStreak)")
                            .fontWeight(.bold)
                    }
                    .font(.caption)
                }
            }
            .frame(maxWidth: .infinity)

            Divider()

            // Right: Stats
            VStack(alignment: .leading, spacing: 10) {
                // Latest test score
                if let score = entry.data.latestTestScore,
                   let week = entry.data.latestTestWeek {
                    HStack(spacing: 8) {
                        Image(systemName: scoreIcon(score))
                            .foregroundStyle(scoreColor(score))
                            .font(.title3)

                        VStack(alignment: .leading, spacing: 1) {
                            Text("Week \(week) Test")
                                .font(.caption2)
                                .foregroundStyle(.secondary)
                            Text("\(score)%")
                                .font(.headline.bold())
                                .foregroundStyle(scoreColor(score))
                        }
                    }
                }

                // Today's progress
                HStack(spacing: 8) {
                    Image(systemName: "checkmark.circle")
                        .foregroundStyle(.blue)
                        .font(.title3)

                    VStack(alignment: .leading, spacing: 1) {
                        Text("Today")
                            .font(.caption2)
                            .foregroundStyle(.secondary)
                        Text("\(entry.data.todayCount) / \(entry.data.dailyGoal)")
                            .font(.subheadline.weight(.medium))
                    }
                }

                // Due cards
                if entry.data.dueCardCount > 0 {
                    HStack(spacing: 8) {
                        Image(systemName: "clock.badge.exclamationmark")
                            .foregroundStyle(.orange)
                            .font(.title3)

                        VStack(alignment: .leading, spacing: 1) {
                            Text("Due")
                                .font(.caption2)
                                .foregroundStyle(.secondary)
                            Text("\(entry.data.dueCardCount) cards")
                                .font(.subheadline.weight(.medium))
                        }
                    }
                }
            }
            .frame(maxWidth: .infinity, alignment: .leading)
        }
        .padding(.horizontal, 4)
    }

    private func scoreColor(_ score: Int) -> Color {
        if score >= 90 { return .green }
        if score >= 70 { return .orange }
        return .red
    }

    private func scoreIcon(_ score: Int) -> String {
        if score >= 90 { return "star.fill" }
        if score >= 70 { return "hand.thumbsup.fill" }
        return "arrow.clockwise"
    }
}

#Preview(as: .systemMedium) {
    WeekProgressWidget()
} timeline: {
    WeekProgressEntry(date: Date(), data: .placeholder)
}
