import SwiftUI

// MARK: - EncryptionKeyView

/// Displays the group encryption key as a pixel grid + hex bytes.
/// Desktop parity: pixel visualization (5 discrete Mantine blue colors) + XOR-encoded hex + secure message.
struct EncryptionKeyView: View {
    let groupDialogKey: String

    @Environment(\.dismiss) private var dismiss

    private var keyHex: String {
        let account = SessionManager.shared.currentPublicKey
        guard let privateKey = SessionManager.shared.privateKeyHex else { return "" }
        return GroupRepository.shared.groupKey(
            account: account,
            privateKeyHex: privateKey,
            groupDialogKey: groupDialogKey
        ) ?? ""
    }

    var body: some View {
        ZStack {
            RosettaColors.Adaptive.background.ignoresSafeArea()

            ScrollView {
                VStack(spacing: 24) {
                    Spacer(minLength: 32)

                    // Pixel grid visualization (desktop parity: 8×8, no spacing, no radius)
                    EncryptionKeyPixelGrid(keyString: keyHex, size: 180)
                        .frame(width: 180, height: 180)

                    // Hex bytes formatted in rows (desktop parity: XOR 27)
                    hexBytesView
                        .padding(.horizontal, 24)

                    // Secure message
                    HStack(spacing: 6) {
                        Text("Your messages is secure")
                            .font(.system(size: 17, weight: .medium))
                            .foregroundStyle(RosettaColors.Adaptive.text)

                        Image(systemName: "lock.fill")
                            .font(.system(size: 14))
                            .foregroundStyle(Color(hex: 0x34C759))
                    }
                    .padding(.top, 8)

                    // Description
                    Text("This key is used to encrypt and decrypt messages. Your messages is secure and not stored on our servers.")
                        .font(.system(size: 15))
                        .foregroundStyle(RosettaColors.Adaptive.textSecondary)
                        .multilineTextAlignment(.center)
                        .padding(.horizontal, 40)

                    Spacer(minLength: 40)
                }
                .frame(maxWidth: .infinity)
            }
        }
        .navigationBarTitleDisplayMode(.inline)
        .navigationBarBackButtonHidden(true)
        .enableSwipeBack()
        .toolbar {
            ToolbarItem(placement: .navigationBarLeading) {
                Button { dismiss() } label: {
                    TelegramVectorIcon(
                        pathData: TelegramIconPath.backChevron,
                        viewBox: CGSize(width: 11, height: 20),
                        color: RosettaColors.Adaptive.text
                    )
                    .frame(width: 11, height: 20)
                    .frame(width: 44, height: 44)
                    .contentShape(Rectangle())
                    .background { TelegramGlassCapsule() }
                }
                .buttonStyle(.plain)
            }
        }
        .toolbarBackground(.hidden, for: .navigationBar)
    }

    // MARK: - Hex Bytes (Desktop Parity)

    /// Desktop algorithm: (charCode ^ 27).toString(16), padded to 2 chars.
    /// 4 rows, each fitting within iPhone screen width.
    private var hexBytesView: some View {
        let key = keyHex
        let charsPerRow = 12
        let totalChars = min(key.count, charsPerRow * 4)

        let rows: [String] = stride(from: 0, to: totalChars, by: charsPerRow).map { start in
            let end = min(start + charsPerRow, totalChars)
            guard start < key.count else { return "" }

            let startIdx = key.index(key.startIndex, offsetBy: start)
            let endIdx = key.index(key.startIndex, offsetBy: min(end, key.count))
            let substring = key[startIdx..<endIdx]

            let hexPairs: [String] = substring.map { char in
                let charCode = Int(char.asciiValue ?? 0)
                let xored = charCode ^ 27
                return String(format: "%02x", xored)
            }
            return hexPairs.joined(separator: "  ")
        }

        return VStack(spacing: 6) {
            ForEach(Array(rows.enumerated()), id: \.offset) { _, row in
                if !row.isEmpty {
                    Text(row)
                        .font(.system(size: 13, weight: .medium, design: .monospaced))
                        .foregroundStyle(RosettaColors.Adaptive.textSecondary)
                }
            }
        }
    }
}

// MARK: - Reusable Pixel Grid

/// Desktop-parity pixel grid: 5 discrete Mantine blue colors, charCode % 5 mapping.
/// Reusable for both full-size detail page and thumbnail in card.
struct EncryptionKeyPixelGrid: View {
    let keyString: String
    let size: CGFloat

    // Mantine blue palette: blue[1]–blue[5]
    private static let mantineBlues: [Color] = [
        Color(red: 0.906, green: 0.961, blue: 1.0),   // #E7F5FF blue[1]
        Color(red: 0.816, green: 0.922, blue: 1.0),   // #D0EBFF blue[2]
        Color(red: 0.647, green: 0.847, blue: 1.0),   // #A5D8FF blue[3]
        Color(red: 0.455, green: 0.753, blue: 0.988),  // #74C0FC blue[4]
        Color(red: 0.302, green: 0.671, blue: 0.969),  // #4DABF7 blue[5]
    ]

    var body: some View {
        let gridSize = 8
        let totalChars = keyString.count

        let charColors: [Color] = (0..<(gridSize * gridSize)).map { i in
            guard totalChars > 0 else { return Self.mantineBlues[0] }
            let charIndex = keyString.index(keyString.startIndex, offsetBy: i % totalChars)
            let charCode = Int(keyString[charIndex].asciiValue ?? 0)
            let colorIndex = charCode % Self.mantineBlues.count
            return Self.mantineBlues[colorIndex]
        }

        VStack(spacing: 0) {
            ForEach(0..<gridSize, id: \.self) { row in
                HStack(spacing: 0) {
                    ForEach(0..<gridSize, id: \.self) { col in
                        let index = row * gridSize + col
                        Rectangle()
                            .fill(charColors[index])
                    }
                }
            }
        }
        .frame(width: size, height: size)
    }
}
