using System;
using System.Collections.Generic;
using Avalonia.Data.Converters;
using MarketData.MarketDataModel;
using MarketData.Utils;

namespace PortfolioManager.UIUtils
{

  /// <summary>
  /// If the OS is not Window then multiply the first parameter.
  /// For example:  "30|.5" would multiply 30 * .5 if the OS is not Windows and return 15 as the result.  Otherwise (if Windows) it will return 30
  /// I am doing this because I need to adjust image sizes across Windows and Unix platforms where Unix images appear quite larger than Windows
  /// </summary>
  public class OSValueConverter : IValueConverter
  {
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      String[] parameters = parameter.ToString().Split('|');
      double valueItem = double.Parse(parameters[0]);
      double multiplier = double.Parse(parameters[1]);

      if (Utility.IsOSWindows())
      {
        return (int)valueItem;
      }
      else
      {
        return (int)(valueItem * multiplier);
      }
    }

    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }

  public class RMultipleValueConverter : IValueConverter
  {
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      double doubleValue = (double)value;
      if (double.IsNaN(doubleValue) || double.IsInfinity(doubleValue)) return Constants.CONST_DASHES;
      return Utility.FormatNumber(doubleValue, 2) + "R";
    }
    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }

  public class DoubleValueConverter : IValueConverter
  {
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      double doubleValue = (double)value;
      if (double.IsNaN(doubleValue) || double.IsInfinity(doubleValue)) return Constants.CONST_DASHES;
      if (null != parameter) return Utility.FormatNumber(doubleValue, int.Parse(parameter.ToString()));
      return Utility.FormatNumber(doubleValue, 4);
    }
    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }

  public class CurrencyValueConverter : IValueConverter
  {
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      double doubleValue = (double)value;
      if (double.IsNaN(doubleValue) || double.IsInfinity(doubleValue)) return Constants.CONST_DASHES;
      if (null != parameter) return Utility.FormatCurrency(doubleValue, int.Parse(parameter.ToString()));
      return Utility.FormatCurrency(doubleValue, 4);
    }
    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }

  public class IntValueConverter : IValueConverter
  {
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      int intValue = (int)value;
      if (int.MinValue.Equals(intValue)) return Constants.CONST_DASHES;
      if (null != parameter) return Utility.FormatNumber(intValue, int.Parse(parameter.ToString()), true);
      return Utility.FormatNumber(intValue, 2, true);
    }
    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }

  public class BoolValueConverter:IValueConverter
  {
    public object Convert(object value,Type targetType,object parameter,System.Globalization.CultureInfo culture)
    {
      bool boolValue=(bool)value;
      if(null!=parameter)
      {
        if("0".Equals(parameter.ToString())) return boolValue?"T":"F";
        if("1".Equals(parameter.ToString())) return boolValue?"Y":"N";
        if("2".Equals(parameter.ToString())) return boolValue?"Yes":"No";
        if("3".Equals(parameter.ToString())) return boolValue?"True":"False";
      }
      return boolValue.ToString();
    }
    public object ConvertBack(object value,Type targetType,object parameter,System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }

  public class DateValueConverter:IValueConverter
  {
    public object Convert(object value,Type targetType,object parameter,System.Globalization.CultureInfo culture)
    {
      DateTime dateValue=(DateTime)value;
      if(Utility.IsEpoch(dateValue))return Constants.CONST_DASHES;
      return Utility.DateTimeToStringMMSDDSYYYY(dateValue);
    }
    public object ConvertBack(object value,Type targetType,object parameter,System.Globalization.CultureInfo culture)
    {
      return null;
    }
  }
// ********************************************************************
  public class SubStringConverter : IValueConverter
  {
      /// <summary> the zero-based starting character position </summary>
      public int StartIndex { get; set; }

      /// <summary> The number of characters in the substring </summary>
      public int Length { get; set; }

      /// <summary> shows "..." if value was truncated after StartIndex</summary>
      public bool ShowEllipse { get; set; }

      public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
      {
          string valueString = value as string;
          if (string.IsNullOrWhiteSpace(valueString) == false)
          {
              if (Length > 0 && Length < (valueString.Length + StartIndex))
              {
                  if (ShowEllipse)
                      return valueString.Substring(StartIndex, Length - 3) + "...";
                  else
                      return valueString.Substring(StartIndex, Length);
              }
              else if (StartIndex < valueString.Length)
                  return valueString.Substring(StartIndex);
              else
                  return ""; //because startIndex must be past the length of the string
          }
          else
          {
              return value;
          }
      }

      public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
      {
          throw new NotImplementedException();
      }
  }
  public class TextMarkerOffsets
  {
    private static int MAX_HITS=12;
    private Dictionary<String,double> tradesBySymbolAndDate=new Dictionary<String,double>();
    private double defaultOffset=0.00;
    private double increment=-18;
    private int hits;

    public TextMarkerOffsets()
    {
      hits=0;
    }
    public TextMarkerOffsets(double defaultOffset)
    {
      this.defaultOffset=defaultOffset;
      hits=0;
    }
    public TextMarkerOffsets(double defaultOffset,double increment)
    {
      this.defaultOffset=defaultOffset;
      this.increment=increment;
      this.hits=0;
    }
    public double GetOffset(PortfolioTrade portfolioTrade)
    {
      String key;
      double offset=defaultOffset;

      if (portfolioTrade.IsOpen)
      {
        key = portfolioTrade.Symbol + portfolioTrade.TradeDate.ToShortDateString();
      } 
      else
      {
        key = portfolioTrade.Symbol + portfolioTrade.SellDate.ToShortDateString();
      }
      if (tradesBySymbolAndDate.ContainsKey(key))
      {
        if(hits>MAX_HITS)increment=5;
        offset=tradesBySymbolAndDate[key]+increment;
        tradesBySymbolAndDate[key]=offset;
        hits++;
      }
      else
      {
        offset=defaultOffset;
        tradesBySymbolAndDate.Add(key,defaultOffset);
      }
      return offset;
    }
  }
  // public class MenuItemSorter : IComparer<System.Windows.Controls.MenuItem>
  // {
  //   public int Compare(System.Windows.Controls.MenuItem v1,System.Windows.Controls.MenuItem v2)      
  //   {
  //     return v1.Header.ToString().CompareTo(v2.Header.ToString());
  //   }
  // }
  // public static class UIServices
  // {
  //   /// <summary>
  //   ///   A value indicating whether the UI is currently busy
  //   /// </summary>
  //   //private static bool isBusy;

  //   /// <summary>
  //   /// Sets the busystate as busy.
  //   /// </summary>
  //   public static void ClearProperty(int fromSeconds, EventHandler dispatchEventHandler)
  //   {
  //     new DispatcherTimer(TimeSpan.FromSeconds(fromSeconds), DispatcherPriority.ApplicationIdle, dispatchEventHandler, Application.Current.Dispatcher);
  //   }
  //   public static void SortMenuItems(ObservableCollection<System.Windows.Controls.MenuItem> menuCollection)
  //   {
  //     List<System.Windows.Controls.MenuItem> items=new List<System.Windows.Controls.MenuItem>();
  //     foreach(System.Windows.Controls.MenuItem item in menuCollection)items.Add(item);
  //     items.Sort(new MenuItemSorter());
  //     menuCollection.Clear();
  //     foreach(System.Windows.Controls.MenuItem item in items)menuCollection.Add(item);
  //   }
  // }
}
