import ActivityKit
import SwiftUI
import UIKit
import WidgetKit

@main
struct BaoLifeLiveActivityExtension: WidgetBundle {
    var body: some Widget {
        CharacterLiveActivityWidget()
    }
}

struct CharacterLiveActivityWidget: Widget {
    var body: some WidgetConfiguration {
        ActivityConfiguration(for: CharacterLiveActivityAttributes.self) { context in
            LiveActivityLockScreenView(context: context)
                .activityBackgroundTint(Color(red: 0.08, green: 0.09, blue: 0.12))
                .activitySystemActionForegroundColor(.white)
                .widgetURL(LiveActivitySharedConfiguration.appURL)
        } dynamicIsland: { context in
            DynamicIsland {
                DynamicIslandExpandedRegion(.leading) {
                    VStack(alignment: .leading, spacing: 6) {
                        AvatarView(
                            characterName: context.attributes.characterName,
                            avatarCacheKey: context.attributes.avatarCacheKey,
                            size: 44
                        )

                        Text(context.attributes.characterName)
                            .font(.caption2.weight(.semibold))
                            .lineLimit(1)
                    }
                }

                DynamicIslandExpandedRegion(.trailing) {
                    VStack(alignment: .trailing, spacing: 4) {
                        Text(context.state.gameTime)
                            .font(.headline.weight(.semibold))
                            .monospacedDigit()

                        Text(context.state.gameDate)
                            .font(.caption2)
                            .foregroundStyle(.secondary)

                        Text(context.state.speedLabel)
                            .font(.caption2.weight(.medium))
                            .foregroundStyle(context.state.isRunning ? .green : .secondary)
                    }
                }

                DynamicIslandExpandedRegion(.bottom) {
                    VStack(alignment: .leading, spacing: 8) {
                        Text(context.state.statusMessage)
                            .font(.subheadline.weight(.semibold))
                            .lineLimit(1)

                        Text(context.state.location)
                            .font(.caption)
                            .foregroundStyle(.secondary)
                            .lineLimit(1)

                        StatStrip(state: context.state)
                    }
                }
            } compactLeading: {
                AvatarView(
                    characterName: context.attributes.characterName,
                    avatarCacheKey: context.attributes.avatarCacheKey,
                    size: 24
                )
            } compactTrailing: {
                Text(context.state.gameTime)
                    .font(.caption2.weight(.semibold))
                    .monospacedDigit()
            } minimal: {
                Text(LiveActivityAvatarFallback.initials(for: context.attributes.characterName))
                    .font(.caption2.weight(.bold))
            }
            .widgetURL(LiveActivitySharedConfiguration.appURL)
            .keylineTint(.teal)
        }
    }
}

private struct LiveActivityLockScreenView: View {
    let context: ActivityViewContext<CharacterLiveActivityAttributes>

    var body: some View {
        HStack(spacing: 12) {
            AvatarView(
                characterName: context.attributes.characterName,
                avatarCacheKey: context.attributes.avatarCacheKey,
                size: 56
            )

            VStack(alignment: .leading, spacing: 5) {
                HStack(alignment: .firstTextBaseline) {
                    Text(context.attributes.characterName)
                        .font(.headline.weight(.semibold))
                        .lineLimit(1)

                    Spacer(minLength: 8)

                    Text(context.state.gameTime)
                        .font(.subheadline.weight(.semibold))
                        .monospacedDigit()
                }

                Text(context.state.statusMessage)
                    .font(.subheadline)
                    .foregroundStyle(.primary)
                    .lineLimit(1)

                HStack(spacing: 8) {
                    Text(context.state.location)
                        .font(.caption)
                        .foregroundStyle(.secondary)
                        .lineLimit(1)

                    Text("Age \(context.state.age)")
                        .font(.caption)
                        .foregroundStyle(.secondary)
                        .lineLimit(1)
                }

                StatStrip(state: context.state)
            }
        }
        .padding(.vertical, 4)
    }
}

private struct AvatarView: View {
    let characterName: String
    let avatarCacheKey: String
    let size: CGFloat

    var body: some View {
        Group {
            if let image = cachedImage {
                Image(uiImage: image)
                    .resizable()
                    .scaledToFill()
            } else {
                ZStack {
                    Circle()
                        .fill(Color.teal.opacity(0.22))

                    Text(LiveActivityAvatarFallback.initials(for: characterName))
                        .font(.system(size: size * 0.36, weight: .bold, design: .rounded))
                        .foregroundStyle(.teal)
                }
            }
        }
        .frame(width: size, height: size)
        .clipShape(Circle())
        .overlay(
            Circle()
                .strokeBorder(Color.white.opacity(0.16), lineWidth: 1)
        )
    }

    private var cachedImage: UIImage? {
        guard let url = LiveActivitySharedConfiguration.avatarURL(for: avatarCacheKey) else {
            return nil
        }
        return UIImage(contentsOfFile: url.path)
    }
}

private struct StatStrip: View {
    let state: CharacterLiveActivityAttributes.ContentState

    var body: some View {
        HStack(spacing: 8) {
            StatPill(label: "Energy", value: state.energy, color: .yellow)
            StatPill(label: "Health", value: state.health, color: .green)
            StatPill(label: "Mood", value: state.happiness, color: .pink)
        }
    }
}

private struct StatPill: View {
    let label: String
    let value: Int
    let color: Color

    var body: some View {
        VStack(alignment: .leading, spacing: 3) {
            HStack(spacing: 3) {
                Circle()
                    .fill(color)
                    .frame(width: 5, height: 5)

                Text(label)
                    .font(.caption2)
                    .foregroundStyle(.secondary)
                    .lineLimit(1)
            }

            ProgressView(value: Double(clampedValue), total: 100)
                .tint(color)
                .frame(maxWidth: .infinity)
        }
    }

    private var clampedValue: Int {
        max(0, min(100, value))
    }
}
