import UIKit
import VMSDK_Core

class VenueListController: UITableViewController {

    private enum Section: Int, CaseIterable {
        case builtIn = 0
        case custom = 1
    }

    private static let staticVenue = "AEGIRH"

    /// Local-dev venues live under `TestApp/venues/` in the app bundle
    /// (mounted via a single hand-managed folder reference in
    /// TestApp.xcodeproj). Devs drop `venue_map_*` directories into that
    /// path; Xcode bundles the contents at build time and we discover
    /// them at runtime here. AEGIRH ships separately at the bundle root
    /// via its own folder reference and is appended unconditionally.
    private static func discoverBuiltInVenues() -> [String] {
        var ids: Set<String> = [staticVenue]
        let fm = FileManager.default
        let prefix = "venue_map_"
        if let venuesURL = Bundle.main.url(forResource: "venues", withExtension: nil),
           let entries = try? fm.contentsOfDirectory(
                at: venuesURL,
                includingPropertiesForKeys: [.isDirectoryKey],
                options: [.skipsHiddenFiles, .skipsPackageDescendants]) {
            for url in entries {
                guard (try? url.resourceValues(forKeys: [.isDirectoryKey]).isDirectory) == true
                else { continue }
                let name = url.lastPathComponent
                guard name.hasPrefix(prefix) else { continue }
                let id = String(name.dropFirst(prefix.count))
                if !id.isEmpty { ids.insert(id) }
            }
        }
        return ids.sorted()
    }

    private let builtInVenues = VenueListController.discoverBuiltInVenues()

    private let baseURLField = UITextField()
    private let venueIdField = UITextField()

    private static let kLastBaseURL = "VenueList.lastBaseURL"
    private static let kLastVenueID = "VenueList.lastVenueID"

    override func viewDidLoad() {
        super.viewDidLoad()
        title = "VM-SDK Test"
        tableView = UITableView(frame: view.bounds, style: .grouped)
        tableView.register(UITableViewCell.self, forCellReuseIdentifier: "cell")
        tableView.register(UITableViewCell.self, forCellReuseIdentifier: "fieldCell")
        tableView.register(UITableViewCell.self, forCellReuseIdentifier: "buttonCell")
        tableView.keyboardDismissMode = .onDrag

        configureFields()
        installLogoFooter()
    }

    private func installLogoFooter() {
        let image = UIImage(named: "aegir_logo")
        let imageView = UIImageView(image: image)
        imageView.contentMode = .scaleAspectFit
        imageView.translatesAutoresizingMaskIntoConstraints = false

        let footer = UIView(frame: CGRect(x: 0, y: 0, width: tableView.bounds.width, height: 140))
        footer.addSubview(imageView)
        NSLayoutConstraint.activate([
            imageView.centerXAnchor.constraint(equalTo: footer.centerXAnchor),
            imageView.centerYAnchor.constraint(equalTo: footer.centerYAnchor),
            imageView.widthAnchor.constraint(equalToConstant: 200),
            imageView.heightAnchor.constraint(equalToConstant: 76),
        ])
        tableView.tableFooterView = footer
    }

    /// Expand the footer to occupy whatever vertical space remains below the
    /// last cell so the logo lands at the visual center of the empty area
    /// (matches Android's weight(1f) + Center alignment).
    override func viewDidLayoutSubviews() {
        super.viewDidLayoutSubviews()
        guard let footer = tableView.tableFooterView else { return }

        let visible = tableView.bounds.height
            - tableView.adjustedContentInset.top
            - tableView.adjustedContentInset.bottom
        let nonFooterContent = tableView.contentSize.height - footer.frame.height
        let desired = max(140, visible - nonFooterContent)

        if abs(footer.frame.height - desired) > 0.5 {
            var f = footer.frame
            f.size.height = desired
            footer.frame = f
            tableView.tableFooterView = footer
        }
    }

    private func configureFields() {
        baseURLField.placeholder = "https://example.com/vmd"
        baseURLField.autocapitalizationType = .none
        baseURLField.autocorrectionType = .no
        baseURLField.keyboardType = .URL
        baseURLField.clearButtonMode = .whileEditing
        baseURLField.returnKeyType = .next
        baseURLField.font = .systemFont(ofSize: 15)

        venueIdField.placeholder = "VENUE_ID"
        venueIdField.autocapitalizationType = .allCharacters
        venueIdField.autocorrectionType = .no
        venueIdField.clearButtonMode = .whileEditing
        venueIdField.returnKeyType = .done
        venueIdField.font = .systemFont(ofSize: 15)
    }

    // MARK: - UITableViewDataSource

    override func numberOfSections(in tableView: UITableView) -> Int {
        Section.allCases.count
    }

    override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
        switch Section(rawValue: section)! {
        case .builtIn: return "Built-in Venues"
        case .custom: return "Custom Venue (HTTPS)"
        }
    }

    override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        switch Section(rawValue: section)! {
        case .builtIn: return 1
        case .custom: return 3
        }
    }

    override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        switch Section(rawValue: indexPath.section)! {
        case .builtIn:
            let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
            cell.textLabel?.text = "Select Venue..."
            cell.textLabel?.textColor = .systemBlue
            cell.accessoryType = .disclosureIndicator
            return cell

        case .custom:
            if indexPath.row == 0 {
                let cell = tableView.dequeueReusableCell(withIdentifier: "fieldCell", for: indexPath)
                cell.selectionStyle = .none
                cell.contentView.subviews.forEach { $0.removeFromSuperview() }
                embedField(baseURLField, in: cell, label: "Base URL")
                return cell
            } else if indexPath.row == 1 {
                let cell = tableView.dequeueReusableCell(withIdentifier: "fieldCell", for: indexPath)
                cell.selectionStyle = .none
                cell.contentView.subviews.forEach { $0.removeFromSuperview() }
                embedField(venueIdField, in: cell, label: "Venue ID")
                return cell
            } else {
                let cell = tableView.dequeueReusableCell(withIdentifier: "buttonCell", for: indexPath)
                cell.textLabel?.text = "Load Custom Venue"
                cell.textLabel?.textColor = .systemBlue
                cell.textLabel?.textAlignment = .center
                return cell
            }
        }
    }

    private func embedField(_ field: UITextField, in cell: UITableViewCell, label: String) {
        let lbl = UILabel()
        lbl.text = label
        lbl.font = .systemFont(ofSize: 13, weight: .medium)
        lbl.textColor = .secondaryLabel
        lbl.setContentHuggingPriority(.required, for: .horizontal)

        let stack = UIStackView(arrangedSubviews: [lbl, field])
        stack.axis = .horizontal
        stack.spacing = 12
        stack.alignment = .center
        stack.translatesAutoresizingMaskIntoConstraints = false
        cell.contentView.addSubview(stack)
        NSLayoutConstraint.activate([
            stack.leadingAnchor.constraint(equalTo: cell.contentView.layoutMarginsGuide.leadingAnchor),
            stack.trailingAnchor.constraint(equalTo: cell.contentView.layoutMarginsGuide.trailingAnchor),
            stack.topAnchor.constraint(equalTo: cell.contentView.topAnchor, constant: 8),
            stack.bottomAnchor.constraint(equalTo: cell.contentView.bottomAnchor, constant: -8),
            lbl.widthAnchor.constraint(equalToConstant: 70),
        ])
    }

    // MARK: - UITableViewDelegate

    override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
        tableView.deselectRow(at: indexPath, animated: true)

        switch Section(rawValue: indexPath.section)! {
        case .builtIn:
            showBuiltInVenuePicker()
        case .custom:
            guard indexPath.row == 2 else { return }
            loadCustomVenue()
        }
    }

    // MARK: - Navigation

    private func showBuiltInVenuePicker() {
        let picker = VenuePickerController(venues: builtInVenues) { [weak self] venue in
            guard let self else { return }
            self.dismiss(animated: true) {
                self.pushMap(venueId: venue, isRemote: false)
            }
        }
        let nav = UINavigationController(rootViewController: picker)
        nav.modalPresentationStyle = .pageSheet
        if let sheet = nav.sheetPresentationController {
            sheet.detents = [.medium(), .large()]
        }
        present(nav, animated: true)
    }

    private func loadCustomVenue() {
        guard let baseURL = baseURLField.text?.trimmingCharacters(in: .whitespacesAndNewlines),
              !baseURL.isEmpty,
              let venueId = venueIdField.text?.trimmingCharacters(in: .whitespacesAndNewlines),
              !venueId.isEmpty else {
            let alert = UIAlertController(title: "Missing Fields", message: "Provide both a Base URL and Venue ID.", preferredStyle: .alert)
            alert.addAction(UIAlertAction(title: "OK", style: .default))
            present(alert, animated: true)
            return
        }
        UserDefaults.standard.set(baseURL, forKey: Self.kLastBaseURL)
        UserDefaults.standard.set(venueId, forKey: Self.kLastVenueID)
        pushMap(venueId: venueId, isRemote: true)
    }

    private func pushMap(venueId: String, isRemote: Bool) {
        let basePath: String
        if isRemote {
            var url = baseURLField.text?.trimmingCharacters(in: .whitespacesAndNewlines) ?? ""
            if !url.hasSuffix("/") { url += "/" }
            basePath = "\(url)\(venueId)/venue_map_\(venueId)"
        } else {
            // AEGIRH lives at the bundle root via its own folder reference.
            // Other built-in venues are dropped into `TestApp/venues/` and
            // bundled via the `venues` folder reference. Resolve in that
            // order so AEGIRH continues to work alongside dev-side drops.
            let venueDir = "venue_map_\(venueId)"
            if let url = Bundle.main.url(forResource: venueDir, withExtension: nil) {
                basePath = url.path
            } else if let venuesRoot = Bundle.main.url(forResource: "venues", withExtension: nil),
                      FileManager.default.fileExists(atPath: venuesRoot.appendingPathComponent(venueDir).path) {
                basePath = venuesRoot.appendingPathComponent(venueDir).path
            } else {
                guard let bundlePath = Bundle.main.resourcePath else { return }
                basePath = "\(bundlePath)/\(venueDir)"
            }
        }

        let config = VenueConfig(
            venueId: venueId,
            basePath: basePath,
            isRemote: isRemote
        )

        let apple = AppleVenueMapController()
        apple.venueConfig = config
        navigationController?.pushViewController(apple, animated: true)
    }
}
