using System;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using System.Linq;
using Decal.Adapter;
using Microsoft.Win32;

namespace MosswartMassacre
{
    public class NavVisualization : IDisposable
    {
        private bool disposed = false;
        private NavRoute currentRoute = null;
        private string vtankProfilesDirectory = "";
        private List<string> availableNavFiles = new List<string>();
        
        // Default comparison route color (red)
        private readonly Color comparisonRouteColor = Color.FromArgb(255, 255, 100, 100);

        public bool IsEnabled { get; private set; } = false;
        public bool HasRouteLoaded => currentRoute != null && currentRoute.WaypointCount > 0;
        public string CurrentRouteFile => currentRoute?.FileName ?? "None";
        public List<string> AvailableNavFiles => availableNavFiles.ToList();

        public event EventHandler RouteChanged;

        public NavVisualization()
        {
            InitializeVTankDirectory();
            RefreshNavFileList();
        }

        private void InitializeVTankDirectory()
        {
            try
            {
                // First, check if user has configured a custom path
                if (!string.IsNullOrEmpty(PluginSettings.Instance?.VTankProfilesPath))
                {
                    vtankProfilesDirectory = PluginSettings.Instance.VTankProfilesPath;
                    return;
                }

                // Try to get VTank directory from Windows Registry (same method as UtilityBelt)
                var defaultPath = @"C:\Games\VirindiPlugins\VirindiTank\";
                try
                {
                    var regKey = Registry.LocalMachine.OpenSubKey("Software\\Decal\\Plugins\\{642F1F48-16BE-48BF-B1D4-286652C4533E}");
                    if (regKey != null)
                    {
                        var profilePath = regKey.GetValue("ProfilePath")?.ToString();
                        if (!string.IsNullOrEmpty(profilePath))
                        {
                            vtankProfilesDirectory = profilePath;
                            return;
                        }
                    }
                }
                catch
                {
                }

                // Fall back to default path
                vtankProfilesDirectory = defaultPath;
                // Using default path - user can configure in Settings if needed
            }
            catch (Exception ex)
            {
                PluginCore.WriteToChat($"[NavViz] Error finding VTank directory: {ex.Message}");
                vtankProfilesDirectory = "";
            }
        }

        /// <summary>
        /// Scan VTank directory for .nav files and populate available routes list
        /// Filters out follow files and temporary files, sorts alphabetically
        /// </summary>
        public void RefreshNavFileList()
        {
            // Re-initialize directory in case settings changed
            InitializeVTankDirectory();
            
            availableNavFiles.Clear();
            
            
            if (string.IsNullOrEmpty(vtankProfilesDirectory))
            {
                PluginCore.WriteToChat("VTank directory not configured. Set path in Settings tab.");
                return;
            }
            
            if (!Directory.Exists(vtankProfilesDirectory))
            {
                PluginCore.WriteToChat($"VTank directory not found: {vtankProfilesDirectory}");
                return;
            }

            try
            {
                // Get all files and filter for .nav files only, excluding follow/temporary files
                var allFiles = Directory.GetFiles(vtankProfilesDirectory);
                var navFiles = allFiles
                    .Where(file => Path.GetExtension(file).Equals(".nav", StringComparison.OrdinalIgnoreCase))
                    .Select(file => Path.GetFileNameWithoutExtension(file))
                    .Where(name => !string.IsNullOrEmpty(name) && 
                                   !name.StartsWith("follow", StringComparison.OrdinalIgnoreCase) &&
                                   !name.StartsWith("--", StringComparison.OrdinalIgnoreCase))
                    .OrderBy(name => name)
                    .ToList();

                availableNavFiles.AddRange(navFiles);
                
                // Only report summary - no need to spam chat with every file
                if (navFiles.Count > 0)
                {
                    PluginCore.WriteToChat($"Navigation: Found {navFiles.Count} route files");
                }
            }
            catch (Exception ex)
            {
                PluginCore.WriteToChat($"Navigation: Error scanning files - {ex.Message}");
            }
        }

        /// <summary>
        /// Load a specific navigation route file for visualization
        /// Clears current route if "None" specified, otherwise loads .nav file
        /// </summary>
        /// <param name="navFileName">Name of .nav file (without extension) or "None"</param>
        /// <returns>True if route loaded successfully, false otherwise</returns>
        public bool LoadRoute(string navFileName)
        {
            try
            {
                // Clear current route
                if (currentRoute != null)
                {
                    currentRoute.Dispose();
                    currentRoute = null;
                }

                if (string.IsNullOrEmpty(navFileName) || navFileName == "None")
                {
                    RouteChanged?.Invoke(this, EventArgs.Empty);
                    return true;
                }

                string fullPath = Path.Combine(vtankProfilesDirectory, navFileName + ".nav");
                
                if (!File.Exists(fullPath))
                {
                    PluginCore.WriteToChat($"Navigation file '{navFileName}' not found");
                    return false;
                }

                currentRoute = new NavRoute(fullPath, comparisonRouteColor);
                
                if (!currentRoute.LoadFromFile())
                {
                    currentRoute.Dispose();
                    currentRoute = null;
                    return false;
                }

                // Show route if visualization is enabled
                if (IsEnabled)
                {
                    currentRoute.Show();
                }

                RouteChanged?.Invoke(this, EventArgs.Empty);
                return true;
            }
            catch (Exception ex)
            {
                PluginCore.WriteToChat($"Navigation: Failed to load '{navFileName}' - {ex.Message}");
                return false;
            }
        }

        /// <summary>
        /// Enable or disable navigation route visualization in 3D world
        /// Shows/hides the currently loaded route based on enabled state
        /// </summary>
        /// <param name="enabled">True to show route lines, false to hide</param>
        public void SetEnabled(bool enabled)
        {
            // No change needed if already in desired state
            if (IsEnabled == enabled) return;

            IsEnabled = enabled;

            if (currentRoute != null)
            {
                if (enabled)
                {
                    currentRoute.Show();
                }
                else
                {
                    currentRoute.Hide();
                }
            }
            else
            {
            }

            PluginCore.WriteToChat($"Navigation visualization {(enabled ? "enabled" : "disabled")}");
        }

        public void ToggleEnabled()
        {
            SetEnabled(!IsEnabled);
        }

        public string GetStatus()
        {
            if (currentRoute == null)
                return "No route loaded";

            string status = $"{currentRoute.FileName} ({currentRoute.WaypointCount} points)";
            if (IsEnabled && currentRoute.IsVisible)
                status += " - Visible";
            else if (IsEnabled)
                status += " - Hidden";
            else
                status += " - Disabled";

            return status;
        }

        public void Dispose()
        {
            if (!disposed)
            {
                if (currentRoute != null)
                {
                    currentRoute.Dispose();
                    currentRoute = null;
                }
                disposed = true;
            }
        }
    }
}