import SwiftUI

/// Theme system for MixBoard iOS.
/// Multiple skins from retro to modern aesthetics.
final class AppTheme: ObservableObject {

    // MARK: - Available Skins

    enum Skin: String, CaseIterable, Identifiable, Codable {
        case winamp       = "Winamp"
        case foobarLight  = "foobar Light"
        case foobarDark   = "foobar Dark"
        case wmp          = "Windows Media"
        case obsidian     = "Obsidian"
        case vinyl        = "Vinyl"
        case tidal        = "Tidal"

        var id: String { rawValue }

        var icon: String {
            switch self {
            case .winamp:      return "bolt.fill"
            case .foobarLight: return "list.bullet"
            case .foobarDark:  return "list.bullet.rectangle"
            case .wmp:         return "play.rectangle.fill"
            case .obsidian:    return "diamond.fill"
            case .vinyl:       return "record.circle"
            case .tidal:       return "waveform"
            }
        }

        var description: String {
            switch self {
            case .winamp:      return "Neon retro vibes"
            case .foobarLight: return "Clean & minimal, light"
            case .foobarDark:  return "Clean & minimal, dark"
            case .wmp:         return "Glossy blue media player"
            case .obsidian:    return "Deep purple, elegant"
            case .vinyl:       return "Warm analog warmth"
            case .tidal:       return "Dark with teal glow"
            }
        }
    }

    // MARK: - Published

    @Published var currentSkin: Skin {
        didSet {
            applySkin(currentSkin)
            UserDefaults.standard.set(currentSkin.rawValue, forKey: "appThemeSkin")
        }
    }

    // MARK: - Colors

    @Published var accent: Color = .green
    @Published var background: Color = .black
    @Published var secondaryBackground: Color = Color(white: 0.1)
    @Published var seekbarBackground: Color = Color.gray.opacity(0.3)
    @Published var seekbarForeground: Color = .green
    @Published var playerBarBackground: Color = Color(white: 0.08)
    @Published var cardBackground: Color = Color(white: 0.12)
    @Published var primaryText: Color = .white
    @Published var secondaryText: Color = .gray
    @Published var tertiaryText: Color = Color.gray.opacity(0.5)
    @Published var playingHighlight: Color = .green
    @Published var groupHeaderText: Color = .white
    @Published var tabBarBackground: Color = Color(white: 0.06)
    @Published var separatorColor: Color = Color.white.opacity(0.1)

    // MARK: - Sizes

    @Published var seekbarHeight: CGFloat = 6
    @Published var rowHeight: CGFloat = 56
    @Published var dataFontSize: CGFloat = 15
    @Published var smallFontSize: CGFloat = 12
    @Published var cornerRadius: CGFloat = 8

    // MARK: - Style flags

    @Published var useDarkMode: Bool = true
    @Published var preferredColorScheme: ColorScheme? = .dark

    // MARK: - Init

    init() {
        let savedSkin = UserDefaults.standard.string(forKey: "appThemeSkin")
            .flatMap { Skin(rawValue: $0) } ?? .winamp
        self.currentSkin = savedSkin
        applySkin(savedSkin)
    }

    // MARK: - Apply Skin

    private func applySkin(_ skin: Skin) {
        switch skin {

        // ── Winamp Classic ──────────────────────────────
        // Dark background, neon green text, retro aesthetic
        case .winamp:
            accent = Color(red: 0.0, green: 1.0, blue: 0.0)
            background = Color(red: 0.06, green: 0.06, blue: 0.08)
            secondaryBackground = Color(red: 0.1, green: 0.1, blue: 0.12)
            seekbarBackground = Color(red: 0.15, green: 0.15, blue: 0.15)
            seekbarForeground = Color(red: 0.0, green: 1.0, blue: 0.0)
            playerBarBackground = Color(red: 0.08, green: 0.08, blue: 0.1)
            cardBackground = Color(red: 0.1, green: 0.1, blue: 0.12)
            primaryText = Color(red: 0.0, green: 0.9, blue: 0.0)
            secondaryText = Color(red: 0.0, green: 0.65, blue: 0.0)
            tertiaryText = Color(red: 0.0, green: 0.35, blue: 0.0)
            playingHighlight = Color(red: 0.0, green: 1.0, blue: 0.0)
            groupHeaderText = Color(red: 0.0, green: 1.0, blue: 0.0)
            tabBarBackground = Color(red: 0.05, green: 0.05, blue: 0.07)
            separatorColor = Color(red: 0.0, green: 0.3, blue: 0.0)
            seekbarHeight = 6; rowHeight = 52; dataFontSize = 14; smallFontSize = 11; cornerRadius = 4
            useDarkMode = true; preferredColorScheme = .dark

        // ── foobar2000 Light ────────────────────────────
        // Clean white, minimal, data-focused — default foobar aesthetic
        case .foobarLight:
            accent = Color(red: 0.0, green: 0.0, blue: 0.55)
            background = Color(uiColor: .systemBackground)
            secondaryBackground = Color(uiColor: .secondarySystemBackground)
            seekbarBackground = Color(uiColor: .systemGray5)
            seekbarForeground = Color(red: 0.0, green: 0.0, blue: 0.55)
            playerBarBackground = Color(uiColor: .secondarySystemBackground)
            cardBackground = Color(uiColor: .secondarySystemGroupedBackground)
            primaryText = Color(uiColor: .label)
            secondaryText = Color(uiColor: .secondaryLabel)
            tertiaryText = Color(uiColor: .tertiaryLabel)
            playingHighlight = Color(red: 0.0, green: 0.0, blue: 0.55)
            groupHeaderText = Color(uiColor: .label)
            tabBarBackground = Color(uiColor: .secondarySystemBackground)
            separatorColor = Color(uiColor: .separator)
            seekbarHeight = 4; rowHeight = 44; dataFontSize = 14; smallFontSize = 11; cornerRadius = 6
            useDarkMode = false; preferredColorScheme = .light

        // ── foobar2000 Dark ─────────────────────────────
        // Dark mode foobar — charcoal gray, muted blue accent
        case .foobarDark:
            accent = Color(red: 0.45, green: 0.55, blue: 0.75)
            background = Color(red: 0.11, green: 0.11, blue: 0.12)
            secondaryBackground = Color(red: 0.15, green: 0.15, blue: 0.16)
            seekbarBackground = Color(red: 0.2, green: 0.2, blue: 0.22)
            seekbarForeground = Color(red: 0.45, green: 0.55, blue: 0.75)
            playerBarBackground = Color(red: 0.13, green: 0.13, blue: 0.14)
            cardBackground = Color(red: 0.16, green: 0.16, blue: 0.17)
            primaryText = Color(red: 0.88, green: 0.88, blue: 0.9)
            secondaryText = Color(red: 0.55, green: 0.55, blue: 0.58)
            tertiaryText = Color(red: 0.38, green: 0.38, blue: 0.4)
            playingHighlight = Color(red: 0.45, green: 0.55, blue: 0.75)
            groupHeaderText = Color(red: 0.65, green: 0.65, blue: 0.7)
            tabBarBackground = Color(red: 0.09, green: 0.09, blue: 0.1)
            separatorColor = Color(red: 0.22, green: 0.22, blue: 0.24)
            seekbarHeight = 4; rowHeight = 44; dataFontSize = 14; smallFontSize = 11; cornerRadius = 6
            useDarkMode = true; preferredColorScheme = .dark

        // ── Windows Media Player ────────────────────────
        // Glossy dark blue, silver chrome, WMP 11 aesthetic
        case .wmp:
            accent = Color(red: 0.2, green: 0.5, blue: 0.95)
            background = Color(red: 0.05, green: 0.08, blue: 0.15)
            secondaryBackground = Color(red: 0.08, green: 0.12, blue: 0.2)
            seekbarBackground = Color(red: 0.12, green: 0.16, blue: 0.25)
            seekbarForeground = Color(red: 0.3, green: 0.6, blue: 1.0)
            playerBarBackground = Color(red: 0.06, green: 0.1, blue: 0.18)
            cardBackground = Color(red: 0.1, green: 0.14, blue: 0.22)
            primaryText = Color(red: 0.9, green: 0.92, blue: 0.96)
            secondaryText = Color(red: 0.55, green: 0.62, blue: 0.75)
            tertiaryText = Color(red: 0.35, green: 0.4, blue: 0.52)
            playingHighlight = Color(red: 0.3, green: 0.65, blue: 1.0)
            groupHeaderText = Color(red: 0.6, green: 0.7, blue: 0.9)
            tabBarBackground = Color(red: 0.04, green: 0.06, blue: 0.12)
            separatorColor = Color(red: 0.15, green: 0.2, blue: 0.3)
            seekbarHeight = 6; rowHeight = 50; dataFontSize = 14; smallFontSize = 11; cornerRadius = 8
            useDarkMode = true; preferredColorScheme = .dark

        // ── Obsidian ────────────────────────────────────
        // Deep dark with purple/violet accent, elegant and modern
        case .obsidian:
            accent = Color(red: 0.6, green: 0.4, blue: 0.9)
            background = Color(red: 0.07, green: 0.06, blue: 0.1)
            secondaryBackground = Color(red: 0.1, green: 0.09, blue: 0.14)
            seekbarBackground = Color(red: 0.15, green: 0.13, blue: 0.2)
            seekbarForeground = Color(red: 0.6, green: 0.4, blue: 0.9)
            playerBarBackground = Color(red: 0.08, green: 0.07, blue: 0.12)
            cardBackground = Color(red: 0.12, green: 0.1, blue: 0.16)
            primaryText = Color(red: 0.9, green: 0.88, blue: 0.95)
            secondaryText = Color(red: 0.55, green: 0.5, blue: 0.65)
            tertiaryText = Color(red: 0.35, green: 0.32, blue: 0.45)
            playingHighlight = Color(red: 0.65, green: 0.45, blue: 0.95)
            groupHeaderText = Color(red: 0.7, green: 0.6, blue: 0.85)
            tabBarBackground = Color(red: 0.05, green: 0.04, blue: 0.08)
            separatorColor = Color(red: 0.2, green: 0.17, blue: 0.28)
            seekbarHeight = 5; rowHeight = 52; dataFontSize = 15; smallFontSize = 12; cornerRadius = 12
            useDarkMode = true; preferredColorScheme = .dark

        // ── Vinyl ───────────────────────────────────────
        // Warm browns, cream text, analog feel — like vintage hi-fi equipment
        case .vinyl:
            accent = Color(red: 0.85, green: 0.55, blue: 0.2)              // warm amber/orange
            background = Color(red: 0.12, green: 0.1, blue: 0.08)          // dark walnut
            secondaryBackground = Color(red: 0.16, green: 0.13, blue: 0.1)
            seekbarBackground = Color(red: 0.22, green: 0.18, blue: 0.14)
            seekbarForeground = Color(red: 0.85, green: 0.55, blue: 0.2)
            playerBarBackground = Color(red: 0.14, green: 0.11, blue: 0.09)
            cardBackground = Color(red: 0.18, green: 0.15, blue: 0.11)
            primaryText = Color(red: 0.92, green: 0.88, blue: 0.78)        // warm cream
            secondaryText = Color(red: 0.65, green: 0.58, blue: 0.48)
            tertiaryText = Color(red: 0.45, green: 0.4, blue: 0.32)
            playingHighlight = Color(red: 0.9, green: 0.6, blue: 0.2)
            groupHeaderText = Color(red: 0.8, green: 0.65, blue: 0.4)
            tabBarBackground = Color(red: 0.1, green: 0.08, blue: 0.06)
            separatorColor = Color(red: 0.25, green: 0.2, blue: 0.15)
            seekbarHeight = 5; rowHeight = 54; dataFontSize = 15; smallFontSize = 12; cornerRadius = 8
            useDarkMode = true; preferredColorScheme = .dark

        // ── Tidal ───────────────────────────────────────
        // Dark warm background, teal/cyan accent, like screenshot
        case .tidal:
            accent = Color(red: 0.2, green: 0.85, blue: 0.75)              // teal/cyan
            background = Color(red: 0.08, green: 0.07, blue: 0.06)         // warm near-black
            secondaryBackground = Color(red: 0.12, green: 0.11, blue: 0.09)
            seekbarBackground = Color(red: 0.25, green: 0.24, blue: 0.22)
            seekbarForeground = Color.white
            playerBarBackground = Color(red: 0.1, green: 0.09, blue: 0.07)
            cardBackground = Color(red: 0.14, green: 0.13, blue: 0.11)
            primaryText = Color.white
            secondaryText = Color(red: 0.65, green: 0.63, blue: 0.58)
            tertiaryText = Color(red: 0.4, green: 0.38, blue: 0.35)
            playingHighlight = Color(red: 0.2, green: 0.85, blue: 0.75)
            groupHeaderText = Color(red: 0.75, green: 0.73, blue: 0.68)
            tabBarBackground = Color(red: 0.06, green: 0.05, blue: 0.04)
            separatorColor = Color(red: 0.2, green: 0.19, blue: 0.17)
            seekbarHeight = 4; rowHeight = 56; dataFontSize = 15; smallFontSize = 12; cornerRadius = 10
            useDarkMode = true; preferredColorScheme = .dark
        }
    }
}

// MARK: - Color hex helper

extension Color {
    init?(hex: String) {
        var hexSanitized = hex.trimmingCharacters(in: .whitespacesAndNewlines)
        hexSanitized = hexSanitized.replacingOccurrences(of: "#", with: "")
        guard hexSanitized.count == 6,
              let rgb = UInt64(hexSanitized, radix: 16) else { return nil }
        self.init(
            red: Double((rgb >> 16) & 0xFF) / 255.0,
            green: Double((rgb >> 8) & 0xFF) / 255.0,
            blue: Double(rgb & 0xFF) / 255.0
        )
    }
}
