using Avalonia.Controls;
using MsBox.Avalonia.Dto;
using MsBox.Avalonia.Models;
using MsBox.Avalonia;
using System.Collections.Generic;
using pavesys_iRAP.ViewModels;
using Mapsui;
using BruTile.Predefined;
using Mapsui.Tiling.Fetcher;
using Mapsui.Tiling.Layers;
using Serilog;
using System;
using Mapsui.Projections;
using Mapsui.Extensions;
using pavesys_iRAP.Helper;
using Mapsui.Layers;
using System.Linq;
using Mapsui.Nts.Extensions;

namespace pavesys_iRAP.Views;

public partial class ImageSelectionPageView : UserControl
{
    
    Map SatteliteMap { get; set; }
    Map RoadMap { get; set; }
    MPoint Point { get; set; }
    ILayer lineLayer;
    ILayer pointLayer;

    public ImageSelectionPageView()
    {
        InitializeComponent();

        string bingMapsApiKey = "API_TEST";
        var bingMapsLayer = new TileLayer(KnownTileSources.Create(KnownTileSource.BingHybrid, bingMapsApiKey),
            dataFetchStrategy: new DataFetchStrategy()) // DataFetchStrategy prefetches tiles from higher levels
        {
            Name = "Bing Aerial",
        };

        SatteliteMap = new Map();
        RoadMap = new Map();

        SatteliteMap.Layers.Add(bingMapsLayer);
        RoadMap.Layers.Add(Mapsui.Tiling.OpenStreetMap.CreateTileLayer("pavesys-iRAP"));



        SatteliteMap.Home = n => n.ZoomToLevel(15);
        RoadMap.Home = n => n.ZoomToLevel(15);
        RoadMap.Refresh();
        SatteliteMap.Refresh();
        MapView.Refresh();
        //Inicia o mapview no 2d openstreetmap
        MapView.Map = RoadMap;

    }

    private async void DataGrid_DoubleTapped(object? sender, Avalonia.Input.TappedEventArgs e)
    {
        var dataCtx = this.DataContext as ImageSelectionPageViewModel;
        //WorkAround cause when we await for the messagebox we lose the selecteditem on the data grid for unknown reasons.
        dataCtx.SetTemps();
        var box = MessageBoxManager.GetMessageBoxCustom(
            new MessageBoxCustomParams
            {
                ButtonDefinitions = new List<ButtonDefinition>
                {
                    new ButtonDefinition { Name = Localizer.Localizer.Instance["FirstPhoto"], },
                    new ButtonDefinition { Name = Localizer.Localizer.Instance["LastPhoto"], },

                },
                ContentTitle = "",
                //ContentHeader = header,
                ContentMessage = Localizer.Localizer.Instance["ChoosePhoto"],
                Icon = MsBox.Avalonia.Enums.Icon.Setting,
                WindowStartupLocation = WindowStartupLocation.CenterOwner,
                CanResize = false,
                MaxWidth = 500,
                MaxHeight = 800,
                SizeToContent = SizeToContent.WidthAndHeight,
                ShowInCenter = true,
                Topmost = false
            });

        var result = await box.ShowWindowAsync();



        if (result == Localizer.Localizer.Instance["FirstPhoto"])
        {
            dataCtx.isFirstPhotoSelected = true;
            dataCtx.FirstImage = dataCtx.tempSelectedPhoto.fileName;
        }
        else if(result == Localizer.Localizer.Instance["LastPhoto"])
        {
            dataCtx.isLastPhotoSelected = true;
            dataCtx.LastImage = dataCtx.tempSelectedPhoto.fileName;
        }
        
        dataCtx.SelectedIndex = dataCtx.tempSelectedIndex;
    }

    private void SelectMapStyle(object? sender, Avalonia.Controls.SelectionChangedEventArgs e)
    {
        var lb = sender as ListBox;
        switch (lb.SelectedIndex)
        {
            case 0:
                MapView.Map = RoadMap;
                MapView.Map.Navigator.CenterOn(Point);
                MapView.Refresh();
                break;

            case 1:
                MapView.Map = SatteliteMap;
                MapView.Map.Navigator.CenterOn(Point);
                MapView.Refresh();
                break;
        }
    }

    private void UserControl_LayoutUpdated(object? sender, System.EventArgs e)
    {
        try
        {
            var dataCtx = this.DataContext as ImageSelectionPageViewModel;


            if (lineLayer is null)
            {
                var lonLatList = dataCtx.xmlLog.logs.Where(l => l.Id % 50 == 0).ToList();
                lonLatList.Add(dataCtx.xmlLog.logs.Last());
                lineLayer = MapHelper.CreateLineStringLayer(lonLatList.Select(coding =>
                SphericalMercator.FromLonLat((double)coding.LonLatGPGGA.Item1, (double)coding.LonLatGPGGA.Item2)
                .ToCoordinate())
                    .ToArray(),
                    MapHelper.CreateLineStringStyle());
                RoadMap.Layers.Add(lineLayer);
                SatteliteMap.Layers.Add(lineLayer);
            }
            if (pointLayer is null)
            {
                var LonLat = dataCtx.xmlLog.logs[0].LonLatGPGGA;

                Point = SphericalMercator.FromLonLat((double)LonLat.Item1, (double)LonLat.Item2).ToMPoint();

                pointLayer = MapHelper.CreatePointLayer(Point);
                RoadMap.Layers.Add(pointLayer);
                SatteliteMap.Layers.Add(pointLayer);
                MapView.Map.Navigator.CenterOn(Point);
                MapView.Refresh();
            }
        }
        catch (Exception ex)
        {
            Log.Error(ex, "Failed to create xml map in image selection page");
        }
        
    }

    private void DataGrid_SelectionChanged_1(object? sender, Avalonia.Controls.SelectionChangedEventArgs e)
    {
        var dataCtx = this.DataContext as ImageSelectionPageViewModel;
        var OdometroFoto= int.Parse(dataCtx.SelectedPhoto.fileName.Replace(".jpg","").Replace(".png",""));
        var LonLat = dataCtx.xmlLog.logs.Where(log => log.Odometro == OdometroFoto).First().LonLatGPGGA;
       

        Point = SphericalMercator.FromLonLat((double)LonLat.Item1, (double)LonLat.Item2).ToMPoint();

        try
        {

            RoadMap.Layers.Remove(pointLayer);
            SatteliteMap.Layers.Remove(pointLayer);
            pointLayer = MapHelper.CreatePointLayer(Point);
            RoadMap.Layers.Add(pointLayer);
            SatteliteMap.Layers.Add(pointLayer);

            RoadMap.Navigator.CenterOn(Point);
            SatteliteMap.Navigator.CenterOn(Point);
            MapView.Refresh();
        }
        catch (Exception ex) 
        {
            Log.Error(ex, "Error Loading Map on Image Selection Page");
        }
    }
}