using System;
using System.Collections.Generic;
using System.Drawing;
using System.Linq;

using BeWo.Data.Access;
using BeWo.Data.Entities;
using BeWo.Report;
using BeWo.Report.ReportObjects;
using BS.Shared;
using BS.Shared.Core;

namespace KoelnRingReports
{
    public partial class ErgaenzendeDiensteTeilnahmeJahr : DevExpress.XtraReports.UI.XtraReport, IBeWoReport<QueryRO>
    {
		public ErgaenzendeDiensteTeilnahmeJahr()
        {
            InitializeComponent();
        }

	    public void SetReportDataSource(QueryRO pRO)
	    {
		    var dateString = pRO.Rows[0].Field1;
		    var bereich = pRO.Rows[0].Field2;

		    var regions = DAOFactory.GenericDAO.GetAll<AdditionalServiceRegion>();
			regions = regions.Where(f => String.Equals(f.AdditionalService.Name, bereich.ToString(), StringComparison.CurrentCultureIgnoreCase)).ToList();
			
		    var jahr = DateTime.Parse(dateString.ToString());

			var m = new DateTime(jahr.Year, 12, 31);
		    var bookings = new List<AdditionalServiceBooking>();

		    foreach (var region in regions)
		    {
			    if (bookings.Any(a => a.AdditionalServiceRegion.Equals(region)))
				    continue;

				bookings.AddRange(DAOFactory.SearchDAO.GetAdditionalServiceBookings(region.Oid, jahr, m));
		    }

			var reportObj = ErgaenzendeDiensteTeilnahmeJahrRO.Create(bookings, jahr, bereich.ToString());

			bindingSource1.DataSource = reportObj;

			xrLabel1.Text = string.Format("Ergänzende Dienste Teilnahme im Jahr {0}", jahr.ToString("yyyy"));
	    }
    }

	public class ErgaenzendeDiensteTeilnahmeJahrRO : AbstractBeWoReportObject<ErgaenzendeDiensteTeilnahmeJahrRO>
	{
		public string Bereich { get; set; }
		public DateTime Date { get; set; }
		public List<ErgDiensteTeilnahmeJahrZeile> Zeilen { get; set; }
		public int Gesamtsumme { get; set; }

		public static ErgaenzendeDiensteTeilnahmeJahrRO Create(IEnumerable<AdditionalServiceBooking> bookings, DateTime date, string bereich)
		{
			var pRO = new ErgaenzendeDiensteTeilnahmeJahrRO { Date = date, Bereich = bereich };
			var zeilen = new List<ErgDiensteTeilnahmeJahrZeile>();
			
			foreach (var booking in bookings)
			{
				if (!booking.Datum.HasValue)
					continue;

				foreach (var customer in booking.Customer2AddServiceBookings)
				{
					if (customer.Participated)
					{
						var x = new ErgDiensteTeilnahmeJahrZeile();

						if (zeilen.Any(a => a.CustomerOid.Equals(customer.CustomerOid)))
						{
							x = zeilen.First(f => f.CustomerOid.Equals(customer.CustomerOid));
						}
						else
						{
							var c = DAOFactory.GenericDAO.GetByID<Customer>(customer.CustomerOid);
							x.CustomerOid = customer.CustomerOid;
							x.CustomerFirstname = c.Person.FirstName;
							x.CustomerLastname = c.Person.LastName;

							SetCustomerVarFields(c, x);

							zeilen.Add(x);
						}

						var index = booking.Datum.Value.Month - 1;
						x.AttendanceCounts[index]++;
					}
				}
			}
			zeilen.Sort((a, b) => String.Format("{0}_{1}", a.CustomerLastname, a.CustomerFirstname).CompareTo(String.Format("{0}_{1}", b.CustomerLastname, b.CustomerFirstname)));
			pRO.Zeilen = zeilen;
			pRO.Gesamtsumme = zeilen.Select(s => s.AttendanceCounts.Sum()).Sum();

			return pRO;
		}

		private static void SetCustomerVarFields(Customer c, ErgDiensteTeilnahmeJahrZeile x)
		{
			foreach (var vv in c.VarFieldValueList)
			{
				var varFieldValue = Utils.XMLDeserializeFromString(vv.SerializedValue, Type.GetType(vv.TypeName));
				if (varFieldValue != null)
				{
					if (vv.VarFieldDefOid.Value == 1)
					{
						x.Klient = varFieldValue.ToString();
					}
					else if (vv.VarFieldDefOid.Value == 2)
					{
						x.Abteilung = varFieldValue.ToString();
					}
					else if (vv.VarFieldDefOid.Value == 3)
					{
						x.Wohnort = varFieldValue.ToString();
					}
					else if (vv.VarFieldDefOid.Value == 4)
					{
						x.Status = varFieldValue.ToString();
					}
					else if (vv.VarFieldDefOid.Value == 5)
					{
						x.KT = varFieldValue.ToString();
					}
				}
			}
			List<String> betreuungsarten = new List<String>();
			foreach (var v2o in c.ValueList)
			{
				if (v2o.Entry.Type == ValueListEntryType.CustomerCareType)
				{
					betreuungsarten.Add(v2o.Entry.Value);
				}
			}

			betreuungsarten.Sort((a, b) => a.CompareTo(b));

			foreach (var ba in betreuungsarten)
			{
				if (String.IsNullOrEmpty(x.Betreuungsart))
				{
					x.Betreuungsart = ba;
				}
				else
				{
					x.Betreuungsart += ", " + ba;
				}
			}
		}
	}

	public class ErgDiensteTeilnahmeJahrZeile
	{
		public long CustomerOid { get; set; }

		public string CustomerFirstname { get; set; }

		public string CustomerLastname { get; set; }

		public string AttendanceCountJanuary { get { return AttendanceCounts[0] == 0 ? string.Empty : AttendanceCounts[0].ToString(); } }

		public string AttendanceCountFebuary { get { return AttendanceCounts[1] == 0 ? string.Empty : AttendanceCounts[1].ToString(); } }

		public string AttendanceCountMarch { get { return AttendanceCounts[2] == 0 ? string.Empty : AttendanceCounts[2].ToString(); } }

		public string AttendanceCountApril { get { return AttendanceCounts[3] == 0 ? string.Empty : AttendanceCounts[3].ToString(); } }

		public string AttendanceCountMay { get { return AttendanceCounts[4] == 0 ? string.Empty : AttendanceCounts[4].ToString(); } }

		public string AttendanceCountJune { get { return AttendanceCounts[5] == 0 ? string.Empty : AttendanceCounts[5].ToString(); } }

		public string AttendanceCountJuly { get { return AttendanceCounts[6] == 0 ? string.Empty : AttendanceCounts[6].ToString(); } }

		public string AttendanceCountAugust { get { return AttendanceCounts[7] == 0 ? string.Empty : AttendanceCounts[7].ToString(); } }

		public string AttendanceCountSeptember { get { return AttendanceCounts[8] == 0 ? string.Empty : AttendanceCounts[8].ToString(); } }

		public string AttendanceCountOctober { get { return AttendanceCounts[9] == 0 ? string.Empty : AttendanceCounts[9].ToString(); } }

		public string AttendanceCountNovember { get { return AttendanceCounts[10] == 0 ? string.Empty : AttendanceCounts[10].ToString(); } }

		public string AttendanceCountDecember { get { return AttendanceCounts[11] == 0 ? string.Empty : AttendanceCounts[11].ToString(); } }
		
		public readonly int[] AttendanceCounts = new int[12];

		public string Betreuungsart { get; set; }

		public int Summe { get { return AttendanceCounts.Sum(); } }

		public string Klient { get; set; }

		public string Abteilung { get; set; }

		public string Wohnort { get; set; }

		public string Status { get; set; }

		public string KT { get; set; }
	}
}
