using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using StockPortfolio.localhost;
using System.ServiceModel;
using C1.Silverlight.Data;

namespace StockPortfolio
{
    public partial class Main : UserControl
    {
        StockInfoServiceClient _stockInfoService;

        public Main()
        {
            InitializeComponent();
            SizeChanged += new SizeChangedEventHandler(Main_SizeChanged);

            PortfolioSet.Portfolio.ServiceStarted += (s, e) => 
            {
                SpinnerStory.Begin();
                //gridArea.gridMain.IsLoading = true;
                //gridArea.ShowDisableGrid.Begin();
            };
            PortfolioSet.Portfolio.ServiceEnded += (s, e) =>
            {
                SpinnerStory.Stop();
                //gridArea.gridMain.IsLoading = false;
                //gridArea.HideDisableGrid.Begin();
            };

            // load (or create) portfolio
            PortfolioSet.Portfolio.ActivePortfolioChanged += (s, e) => UpdateStatus();
            PortfolioSet.Portfolio.CurrentStockInfoUpdated += (s, e) => UpdateStatus();
            PortfolioSet.Portfolio.SummaryUpdated += (s, e) => UpdateStatus();
            
            PortfolioSet.Portfolio.Initialize();

            HideGridStory.Completed += new EventHandler(HideGridStory_Completed);
        }

        void Main_SizeChanged(object sender, SizeChangedEventArgs e)
        {
            mainContainer.Clip = new RectangleGeometry() { Rect = new Rect(0, 0, mainContainer.ActualWidth, mainContainer.ActualHeight) };
            gridArea.Width = mainContainer.ActualWidth;
            gridArea.Height = mainContainer.ActualHeight;
            chartArea.Width = mainContainer.ActualWidth;
            chartArea.Height = mainContainer.ActualHeight;
            if (gridvisible)
            {
                chartArea.SetValue(Canvas.LeftProperty, mainContainer.ActualWidth);
            }
            else
            {
                chartArea.SetValue(Canvas.LeftProperty, (double)0);
            }
            ((DoubleAnimationUsingKeyFrames)(HideGridStory.Children[1])).KeyFrames[1].Value = -1 * mainContainer.ActualWidth;
            ((DoubleAnimationUsingKeyFrames)(HideGridStory.Children[2])).KeyFrames[0].Value = mainContainer.ActualWidth;
            ((DoubleAnimationUsingKeyFrames)(ShowGridStory.Children[1])).KeyFrames[0].Value = -1 * mainContainer.ActualWidth;
            ((DoubleAnimationUsingKeyFrames)(ShowGridStory.Children[2])).KeyFrames[1].Value = mainContainer.ActualWidth;
        }

        private bool gridvisible = true;
        private void btnPageBar_Click(object sender, RoutedEventArgs e)
        {
            ShowGrid();
        }

        private void ShowGrid()
        {
            gridvisible = true;
            chartArea.RemoveSymHolders();
            ShowGridStory.Begin();
        }
        private void ShowChart()
        {
            gridvisible = false;
            HideGridStory.Begin();
        }

        void HideGridStory_Completed(object sender, EventArgs e)
        {
            if (_selectedStockInfo != null)
            {
                this.chartArea.AddSymbol(_selectedStockInfo);
            }
        }

        #region Chart stuff

        CurrentStockInfo _selectedStockInfo;
        string _showSym = string.Empty;

        // toggle grid/chart views
        public void ShowChart(string symbol)
        {
            if (_stockInfoService == null)
            {
                BasicHttpBinding binding = new BasicHttpBinding();
                binding.MaxReceivedMessageSize = 2147483647; // int.MaxValue
                binding.MaxBufferSize = 2147483647; // int.MaxValue
                string url = GetAbsoluteUri("StockInfoService.svc");
                EndpointAddress address = new EndpointAddress(url);
                _stockInfoService = new StockInfoServiceClient(binding, address);

                // the async callback is where we'll transition to the chart page
                _stockInfoService.GetCurrentStockInfoCompleted += _stockInfoService_GetCurrentStockInfoCompleted;
            }

            // get the current info for the selected stock
            _stockInfoService.GetCurrentStockInfoAsync(symbol);
        }
        void _stockInfoService_GetCurrentStockInfoCompleted(object sender, GetCurrentStockInfoCompletedEventArgs e)
        {
            if (!e.Cancelled && e.Error == null)
            {
                _selectedStockInfo = e.Result;
            }
            ShowChart();
        }

        // convert relative url into absolute
        public static string GetAbsoluteUri(string relativeUri)
        {
            // get current absolute Uri; this depends on where/how the app is deployed
            // e.g. "http://labs.componentone.com/silverlight/stockportfolio/foo.aspx"
            //      "http://localhost:1337/mysamples/stockportfolio/foo.aspx"
            Uri uri = System.Windows.Browser.HtmlPage.Document.DocumentUri;
            string uriString = uri.AbsoluteUri;

            // replace page name with relative service Uri
            int ls = uriString.LastIndexOf('/');
            return uriString.Substring(0, ls + 1) + relativeUri;
        }

        // update status line
        private void UpdateStatus()
        {
            PortfolioSet.Portfolio.Save();

            DataRow pf = PortfolioSet.Portfolio.Portfolios.Rows.Find(PortfolioSet.Portfolio.ActivePortfolio);
            if (pf != null)
            {
                double value = (double)pf["Market Value"];
                double cost = (double)pf["Cost Basis"];
                double gain = (double)pf["Gain"];

                gridArea.lblStatus.Text = string.Format("Current portfolio value {0:$#,###}, gain {1:$#,###} ({2:p2}), last updated at {3}.",
                    value,
                    gain,
                    cost != 0 ? gain / cost : 0,
                    PortfolioSet.Portfolio.LastUpdate.ToShortTimeString());

                gridArea.lblStatus.Visibility = value != 0 ? Visibility.Visible : Visibility.Collapsed;
            }
        }
        #endregion
    }
}
