import SwiftData
import SwiftUI

/// Settings tab — skin selection, sync, about.
struct SettingsView: View {
    @EnvironmentObject private var theme: AppTheme
    @EnvironmentObject private var syncManager: SyncManager
    @EnvironmentObject private var libraryManager: LibraryManager
    @Environment(PlaylistViewModel.self) private var playlistVM
    @Environment(\.modelContext) private var modelContext

    @Query(sort: \Playlist.dateModified, order: .reverse) private var playlists: [Playlist]
    @Query private var tracks: [Track]

    @State private var showSyncImporter = false
    @State private var showSyncExportConfirm = false
    @State private var syncResult: String?
    @State private var showResetConfirm = false

    // Playback settings
    @AppStorage("trackTapAction") private var trackTapAction = "playNow"

    // Chad Music settings
    @State private var chadServerURL: String = UserDefaults.standard.string(forKey: "chadMusic.serverURL") ?? ""
    @State private var chadAPIKey: String = KeychainService.loadAPIKey() ?? ""
    @State private var chadTestResult: ChadTestState = .idle

    private enum ChadTestState {
        case idle
        case testing
        case success(ChadStats)
        case failed(String)
    }

    private static let mixColors: [Color] = [
        Color(red: 0.95, green: 0.3, blue: 0.3),
        Color(red: 0.3, green: 0.75, blue: 0.95),
        Color(red: 0.95, green: 0.75, blue: 0.2),
    ]

    var body: some View {
        NavigationStack {
            List {
                // MARK: - Mix Targets
                Section {
                    ForEach(0..<3, id: \.self) { slot in
                        Menu {
                            ForEach(playlists) { playlist in
                                Button(playlist.name) {
                                    playlistVM.setMixTarget(slot, playlist: playlist)
                                }
                            }
                            if playlistVM.mixTargets[slot] != nil {
                                Divider()
                                Button("Clear", role: .destructive) {
                                    playlistVM.setMixTarget(slot, playlist: nil)
                                }
                            }
                        } label: {
                            HStack(spacing: 12) {
                                Text("\(slot + 1)")
                                    .font(.system(size: 14, weight: .bold, design: .rounded))
                                    .frame(width: 28, height: 28)
                                    .foregroundStyle(Self.mixColors[slot])
                                    .background(Self.mixColors[slot].opacity(0.15))
                                    .clipShape(RoundedRectangle(cornerRadius: 6))

                                if let target = playlistVM.mixTargets[slot] {
                                    Text(target.name)
                                        .foregroundStyle(theme.primaryText)
                                } else {
                                    Text("Not set")
                                        .foregroundStyle(theme.tertiaryText)
                                }

                                Spacer()

                                Image(systemName: "chevron.up.chevron.down")
                                    .font(.caption)
                                    .foregroundStyle(theme.tertiaryText)
                            }
                            .contentShape(Rectangle())
                        }
                    }
                } header: {
                    Text("Mix Targets")
                } footer: {
                    Text("Assign playlists to the 3 mix buttons shown on each track. Tap a number on a track to quick-add it.")
                }

                // MARK: - App Icon Color
                Section("App Icon") {
                    let iconOptions: [(name: String, color: Color, iconName: String?)] = [
                        ("Default", .green, nil),
                        ("Green", Color(red: 0.35, green: 0.85, blue: 0.25), "AppIcon-Green"),
                        ("Lime", Color(red: 0.55, green: 0.95, blue: 0.15), "AppIcon-Lime"),
                        ("Cyan", Color(red: 0.15, green: 0.85, blue: 0.85), "AppIcon-Cyan"),
                        ("Blue", Color(red: 0.25, green: 0.45, blue: 0.95), "AppIcon-Blue"),
                        ("Purple", Color(red: 0.6, green: 0.3, blue: 0.9), "AppIcon-Purple"),
                        ("Pink", Color(red: 0.95, green: 0.3, blue: 0.6), "AppIcon-Pink"),
                        ("Red", Color(red: 0.95, green: 0.25, blue: 0.25), "AppIcon-Red"),
                        ("Orange", Color(red: 0.95, green: 0.55, blue: 0.15), "AppIcon-Orange"),
                        ("Gold", Color(red: 0.95, green: 0.8, blue: 0.15), "AppIcon-Gold"),
                        ("White", Color(red: 0.9, green: 0.9, blue: 0.92), "AppIcon-White"),
                    ]

                    ScrollView(.horizontal, showsIndicators: false) {
                        HStack(spacing: 12) {
                            ForEach(iconOptions, id: \.name) { option in
                                Button {
                                    UIApplication.shared.setAlternateIconName(option.iconName) { error in
                                        if let error { print("Icon change failed: \(error)") }
                                    }
                                } label: {
                                    VStack(spacing: 6) {
                                        RoundedRectangle(cornerRadius: 12)
                                            .fill(option.color)
                                            .frame(width: 50, height: 50)
                                            .overlay(
                                                RoundedRectangle(cornerRadius: 12)
                                                    .stroke(Color.white.opacity(0.2), lineWidth: 1)
                                            )
                                        Text(option.name)
                                            .font(.caption2)
                                            .foregroundStyle(theme.secondaryText)
                                    }
                                }
                                .buttonStyle(.plain)
                            }
                        }
                        .padding(.vertical, 8)
                    }
                    .listRowInsets(EdgeInsets(top: 0, leading: 16, bottom: 0, trailing: 16))
                }

                // MARK: - Playback
                Section("Playback") {
                    Picker("Track Tap Action", selection: $trackTapAction) {
                        Text("Play Now").tag("playNow")
                        Text("Add to Queue").tag("addToQueue")
                    }
                }

                // MARK: - Skin Selection
                Section("Skin") {
                    ForEach(AppTheme.Skin.allCases) { skin in
                        Button {
                            withAnimation(.easeInOut(duration: 0.3)) {
                                theme.currentSkin = skin
                            }
                        } label: {
                            HStack(spacing: 12) {
                                Image(systemName: skin.icon)
                                    .font(.title3)
                                    .foregroundStyle(theme.currentSkin == skin ? theme.accent : theme.secondaryText)
                                    .frame(width: 32)

                                VStack(alignment: .leading, spacing: 2) {
                                    Text(skin.rawValue)
                                        .font(.headline)
                                        .foregroundStyle(theme.primaryText)
                                    Text(skin.description)
                                        .font(.caption)
                                        .foregroundStyle(theme.secondaryText)
                                }

                                Spacer()

                                if theme.currentSkin == skin {
                                    Image(systemName: "checkmark.circle.fill")
                                        .foregroundStyle(theme.accent)
                                }
                            }
                        }
                    }
                }

                // MARK: - Chad Music
                Section {
                    HStack {
                        Text("Server URL")
                            .foregroundStyle(theme.secondaryText)
                        TextField("https://music.example.com", text: $chadServerURL)
                            .textContentType(.URL)
                            .keyboardType(.URL)
                            .autocapitalization(.none)
                            .disableAutocorrection(true)
                            .multilineTextAlignment(.trailing)
                            .onChange(of: chadServerURL) { _, newValue in
                                ChadMusicAPIClient.shared.serverURL = newValue
                            }
                    }

                    HStack {
                        Text("API Key")
                            .foregroundStyle(theme.secondaryText)
                        SecureField("Enter API key", text: $chadAPIKey)
                            .multilineTextAlignment(.trailing)
                            .onChange(of: chadAPIKey) { _, newValue in
                                if newValue.isEmpty {
                                    KeychainService.deleteAPIKey()
                                } else {
                                    try? KeychainService.saveAPIKey(newValue)
                                }
                            }
                    }

                    Button {
                        testChadConnection()
                    } label: {
                        HStack {
                            Label("Test Connection", systemImage: "antenna.radiowaves.left.and.right")
                            Spacer()
                            switch chadTestResult {
                            case .idle:
                                EmptyView()
                            case .testing:
                                ProgressView()
                            case .success:
                                Image(systemName: "checkmark.circle.fill")
                                    .foregroundStyle(.green)
                            case .failed:
                                Image(systemName: "xmark.circle.fill")
                                    .foregroundStyle(.red)
                            }
                        }
                    }
                    .disabled(chadServerURL.isEmpty || chadAPIKey.isEmpty)

                    switch chadTestResult {
                    case .success(let stats):
                        HStack(spacing: 16) {
                            if let tracks = stats.tracks {
                                VStack {
                                    Text("\(tracks)")
                                        .font(.headline)
                                    Text("Tracks")
                                        .font(.caption2)
                                        .foregroundStyle(theme.secondaryText)
                                }
                            }
                            if let albums = stats.albums {
                                VStack {
                                    Text("\(albums)")
                                        .font(.headline)
                                    Text("Albums")
                                        .font(.caption2)
                                        .foregroundStyle(theme.secondaryText)
                                }
                            }
                            if let artists = stats.artists {
                                VStack {
                                    Text("\(artists)")
                                        .font(.headline)
                                    Text("Artists")
                                        .font(.caption2)
                                        .foregroundStyle(theme.secondaryText)
                                }
                            }
                        }
                        .frame(maxWidth: .infinity)
                    case .failed(let msg):
                        Text(msg)
                            .font(.caption)
                            .foregroundStyle(.red)
                    default:
                        EmptyView()
                    }
                } header: {
                    Text("Chad Music")
                } footer: {
                    Text("Connect to your Chad Music server to stream cloud music. The server URL and API key are stored securely in the Keychain.")
                }

                // MARK: - Sync
                Section {
                    Button {
                        syncManager.exportPlaylists(playlists)
                        showSyncExportConfirm = true
                    } label: {
                        Label("Export Playlists for Mac", systemImage: "square.and.arrow.up")
                    }
                    .disabled(playlists.isEmpty)

                    Button {
                        showSyncImporter = true
                    } label: {
                        Label("Import Playlists from Mac", systemImage: "square.and.arrow.down")
                    }

                    if let date = syncManager.lastSyncDate {
                        HStack {
                            Text("Last export")
                                .foregroundStyle(theme.secondaryText)
                            Spacer()
                            Text(date.formatted(date: .abbreviated, time: .shortened))
                                .font(.caption)
                                .foregroundStyle(theme.tertiaryText)
                        }
                    }

                    if let result = syncResult {
                        Text(result)
                            .font(.caption)
                            .foregroundStyle(theme.accent)
                    }
                } header: {
                    Text("Sync")
                } footer: {
                    Text("Export creates a JSON file in Documents/Sync/ that you can share with the Mac app via AirDrop, iCloud Drive, or USB.")
                }

                // MARK: - Library Stats
                Section("Library") {
                    HStack {
                        Text("Tracks")
                        Spacer()
                        Text("\(tracks.count)")
                            .foregroundStyle(theme.secondaryText)
                    }

                    HStack {
                        Text("Playlists")
                        Spacer()
                        Text("\(playlists.count)")
                            .foregroundStyle(theme.secondaryText)
                    }

                    HStack {
                        Text("Analyzed")
                        Spacer()
                        Text("\(tracks.filter(\.isAnalyzed).count) / \(tracks.count)")
                            .foregroundStyle(theme.secondaryText)
                    }

                    Button {
                        Task { await libraryManager.rescanMetadata() }
                    } label: {
                        Label("Rescan Metadata", systemImage: "arrow.clockwise")
                    }
                    .disabled(libraryManager.isScanning)

                    Button(role: .destructive) {
                        showResetConfirm = true
                    } label: {
                        Label("Reset Library & Rescan", systemImage: "arrow.counterclockwise")
                            .foregroundStyle(.red)
                    }
                }

                // MARK: - About
                Section("About") {
                    HStack {
                        Text("MixBoard iOS")
                        Spacer()
                        Text("1.0.0")
                            .foregroundStyle(theme.tertiaryText)
                    }

                    HStack {
                        Text("Supported Formats")
                        Spacer()
                        Text("MP3, FLAC, WAV, AIFF, M4A, AAC, OGG, Opus")
                            .font(.caption)
                            .foregroundStyle(theme.tertiaryText)
                    }
                }
            }
            .navigationTitle("Settings")
            .accessibilityIdentifier("settingsView")
            .fileImporter(
                isPresented: $showSyncImporter,
                allowedContentTypes: [.json],
                allowsMultipleSelection: false
            ) { result in
                switch result {
                case .success(let urls):
                    guard let url = urls.first else { return }
                    let accessing = url.startAccessingSecurityScopedResource()
                    defer { if accessing { url.stopAccessingSecurityScopedResource() } }
                    do {
                        let imported = try syncManager.importPlaylists(from: url, context: modelContext)
                        let result = syncManager.mergeImportedPlaylists(imported, existingTracks: tracks, context: modelContext)
                        syncResult = "Imported \(result.created) playlists, \(result.matched) tracks matched, \(result.unmatched) not found"
                    } catch {
                        syncResult = "Import failed: \(error.localizedDescription)"
                    }
                case .failure(let error):
                    syncResult = "Error: \(error.localizedDescription)"
                }
            }
            .alert("Exported", isPresented: $showSyncExportConfirm) {
                Button("OK") {}
            } message: {
                Text("Playlists exported to Documents/Sync/mixboard-playlists.json\n\nShare this file with your Mac via AirDrop, iCloud Drive, or Files app.")
            }
            .alert("Reset Library?", isPresented: $showResetConfirm) {
                Button("Cancel", role: .cancel) {}
                Button("Reset & Rescan", role: .destructive) {
                    // Delete all tracks from database
                    for track in tracks {
                        modelContext.delete(track)
                    }
                    try? modelContext.save()
                    // Rescan
                    Task {
                        await libraryManager.scanMusicDirectory()
                    }
                }
            } message: {
                Text("This will remove all tracks from the database and re-scan your music folder. Your music files are NOT deleted.")
            }
        }
    }

    private func testChadConnection() {
        chadTestResult = .testing
        Task {
            let result = await ChadMusicAPIClient.shared.testConnection()
            switch result {
            case .success(let stats):
                chadTestResult = .success(stats)
            case .failure(let error):
                chadTestResult = .failed(error.localizedDescription)
            }
        }
    }
}
