using System;
using System.Collections.Generic;
using System.Linq;
using Consulenza.ReportWriter.Business;
using Consulenza.ReportWriter.Business.OBJ_PDF;
using System.Data;
using Consulenza.ReportWriter.Business.Entity;
using Consulenza.ReportCommon;

namespace Consulenza.ReportWriter.Manager.Section.Immobiliare.MappaturaPreliminare
{
    /// <summary>
    /// Mappatura strategica degli immobili (id 135)
    /// La scheda è costituita da due tabelle, nelle quali sono riportati gli immobili del cliente.
    /// Nella prima sono elencate le abitazioni per le quali non si è scelto di  stampare la “Scheda di dettaglio dell’abitazione” e le abitazioni censite manualmente su Sei.
    /// Qualora il PB abbia scelto di stampare la “Scheda di dettaglio dell’abitazione” per tutte le abitazioni del cliente e non siano state censite manualmente abitazioni su Sei, la tabella in questione non sarà rappresentata.
    /// </summary>
    public class S8 : Entity.Section
    {
        public S8(EnvironmentFacade environmentFacade, int idSection)
            : base(environmentFacade, idSection)
        {
            try
            {
                Draw();
            }
            catch (Exception ex)
            {
                SectionLogger.Write("S8", ex.Message, SectionLoggerMessageLevel.E, EnvironmentFacade.ReportEnvironment);
            }
        }

      
        protected override sealed void Draw()
        {
            var dati = GetDataSet();
            if (dati.Tables[0].Rows.Count == 0) return;
            var testi = GetText();

            var titolo = new FormattedTextAreaPDF(testi.Rows[0]["testo1"].ToString(), EnvironmentFacade.RendererFacade.XLeftLimit, 600) { FontSize = 10, FontColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
            AddElement(new SpacePDF(40));
            AddElement(titolo);

            #region Oggetti da ripetere al salto pagina della tabella

            var listaOggettiDaRipetere = new List<ObjectPDF> { new SpacePDF(40), titolo, new SpacePDF(20) };
            AddElement(new RepeaterPDF(listaOggettiDaRipetere));

            #endregion

            AddElement(new SpacePDF(20));
            #region ABITAZIONI
            //escludo idimmobili stampati nella S7 se presenti, altrimenti prendo tutti quelli del dataset e li divido tra abitazioni e altri
            DataTable dtab = new DataTable();
            DataTable dtal = new DataTable();
            //escludo idimmobili richiesti e tutti gli immobili che non siano Abitazioni
            //var queryAbitazioni = from x in dati.Tables[0].AsEnumerable()
            //            where (!EnvironmentFacade.ReportEnvironment.MappaturaPreliminare.IdImmobileCatasto.Any(b => x.Field<string>("idImmobileCatasto").Contains(b))) && x.Field<string>("tipologia").Trim() == "Abitazioni"
            //               select x;
            //var queryAltri = from x in dati.Tables[0].AsEnumerable()
            //            where (!EnvironmentFacade.ReportEnvironment.MappaturaPreliminare.IdImmobileCatasto.Any(b => x.Field<string>("idImmobileCatasto").Contains(b))) && x.Field<string>("tipologia").Trim() != "Abitazioni"
            //            select x;

            var queryAbitazioni = from x in dati.Tables[0].AsEnumerable()
                                  where (!EnvironmentFacade.ReportEnvironment.MappaturaPreliminare.IdImmobileCatasto.Any(b => x.Field<string>("idImmobileCatasto").Contains(b))) && x.Field<string>("TipoImmobile").Trim() == "F"
                                  select x;
            var queryAltri = from x in dati.Tables[0].AsEnumerable()
                             where (!EnvironmentFacade.ReportEnvironment.MappaturaPreliminare.IdImmobileCatasto.Any(b => x.Field<string>("idImmobileCatasto").Contains(b))) && x.Field<string>("TipoImmobile").Trim() == "T"
                             select x;

           
            if (queryAbitazioni.Count() > 0)
            {
                var dtAbitazioni = new DataTable();
                dtab = queryAbitazioni.CopyToDataTable();
                
                dtAbitazioni.Columns.Add(new DataColumn("Fabricati", typeof(string)));
                dtAbitazioni.Columns.Add(new DataColumn("Superficie", typeof(string)));
                dtAbitazioni.Columns.Add(new DataColumn("Usoabitativo", typeof(string)));
                dtAbitazioni.Columns.Add(new DataColumn("Usostrumentale", typeof(string)));
                dtAbitazioni.Columns.Add(new DataColumn("Usoinvestimento", typeof(string)));
                dtAbitazioni.Columns.Add(new DataColumn("Libero", typeof(string)));
                dtAbitazioni.Columns.Add(new DataColumn("Affittato", typeof(string)));
                foreach (DataRow ro in dtab.Rows)
                {

                    dtAbitazioni.Rows.Add(ro["descrizione"].ToString(), Convert.ToInt32(ro["Superficie"]) == 0 ? "n.d." : Helper.FormatInteger(ro["Superficie"].ToString()) + " mq", "", "", "", "", "");

                }


                var tabella = new TablePDF(EnvironmentFacade.RendererFacade.XLeftLimit, dtAbitazioni)
                {
                   
                    Style = Style.Immobiliare,
                    Footer = false,
                    ShowBorderLastLine = true,
                    ShowSeparationLines = false,
                    RowHeight = 15
                };


                tabella.Columns.Add(new ColumnPDF("Fabricati", 305, HorizontalAlignmentType.Sinistra, false, false, 8, ColumnType.Testo, "Fabricati", "Fabricati") {HeaderBackgroundColor=ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 8 });
                tabella.Columns.Add(new ColumnPDF("superficie", 105, HorizontalAlignmentType.Centrato, false, false, 8, ColumnType.Testo, "Superficie", "Superficie stimata") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 8 });

                tabella.Columns.Add(new ColumnPDF("usoabitativo", 70, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Usoabitativo", "<i>Uso abitativo<i>")
                {
                    HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella,
                    HeaderFontSize = 7,
                    HeaderGroupText = new List<string> { string.Format("{0}Finalità", string.Concat(Enumerable.Repeat("&nbsp;", 27))) },
                    HeaderGroupWidth = 210,
                    HeaderGroupTextDeltaX = 13,
                    HeaderGroupTextDeltaY = -15,
                    HeaderVerticalAlignment = VerticalAlignmentType.Basso
                });
                tabella.Columns.Add(new ColumnPDF("strumentale", 70, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Usostrumentale", "<i>Strumentale<i>") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 7, HeaderVerticalAlignment = VerticalAlignmentType.Basso }); //Separatore
                tabella.Columns.Add(new ColumnPDF("investimento", 70, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Usoinvestimento", "<i>Investimento<i>") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 7, HeaderVerticalAlignment = VerticalAlignmentType.Basso });
                tabella.Columns.Add(new ColumnPDF("libero", 50, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Libero", "Libero")
                {
                    HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella,
                    HeaderFontSize = 7,
                    HeaderGroupText = new List<string> { string.Format("{0}Stato*", string.Concat(Enumerable.Repeat("&nbsp;", 10))) },
                    HeaderGroupWidth = 100,
                    HeaderGroupTextDeltaX = 13,
                    HeaderGroupTextDeltaY = -15,
                    HeaderVerticalAlignment = VerticalAlignmentType.Basso
                }
                );
                tabella.Columns.Add(new ColumnPDF("affittato", 50, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Affittato", "Affittato") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderVerticalAlignment = VerticalAlignmentType.Basso, HeaderFontSize = 7 });

                int i = 0;
                foreach (DataRow r in dtAbitazioni.Rows)
                {

                    tabella.Cells[2, i].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                    tabella.Cells[3, i].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                    tabella.Cells[4, i].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                    tabella.Cells[5, i].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                    tabella.Cells[6, i].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                    i++;
                }
                AddElement(tabella);

            }
           
            #endregion
            
            #region ALTRI FABBRICATI E TERRENI
            if(dtab.Rows.Count > 0)
                AddElement(new SpacePDF(15));

            if (queryAltri.Count() > 0)
            {
                var dtAltri = new DataTable();
                dtal = queryAltri.OrderBy(o => o.Field<string>("TipoImmobile")).CopyToDataTable();
            dtAltri.Columns.Add(new DataColumn("Terreni", typeof(string)));
            dtAltri.Columns.Add(new DataColumn("Superficie", typeof(string)));
            dtAltri.Columns.Add(new DataColumn("Usoabitativo", typeof(string)));
            dtAltri.Columns.Add(new DataColumn("Usostrumentale", typeof(string)));
            dtAltri.Columns.Add(new DataColumn("Usoinvestimento", typeof(string)));
            dtAltri.Columns.Add(new DataColumn("Libero", typeof(string)));
            dtAltri.Columns.Add(new DataColumn("Affittato", typeof(string)));


            foreach (DataRow ro in dtal.Rows)
            {
                dtAltri.Rows.Add(ro["descrizione"].ToString(), Convert.ToDecimal(ro["Superficie"]) == 0 ? "n.d." : (ro["TipoImmobile"].ToString() == "T" ? Helper.FormatDecimal(ro["Superficie"].ToString(),3) + " ha" : Helper.FormatInteger(ro["Superficie"].ToString()) + " mq"), "", "", "", "", "");
                
            }


            var tabellaAltri = new TablePDF(EnvironmentFacade.RendererFacade.XLeftLimit, dtAltri)
            {
                
                Style = Style.Immobiliare,

                Footer = false,
                ShowBorderLastLine = true,
                ShowSeparationLines = false,
                RowHeight = 15
            };

            tabellaAltri.Columns.Add(new ColumnPDF("altri2", 305, HorizontalAlignmentType.Sinistra, false, false, 8, ColumnType.Testo, "Terreni", "Terreni") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 8 });
            tabellaAltri.Columns.Add(new ColumnPDF("superficie2", 105, HorizontalAlignmentType.Centrato, false, false, 8, ColumnType.Testo, "Superficie", "Superficie stimata") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 8 });

            tabellaAltri.Columns.Add(new ColumnPDF("usoabitativo2", 70, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Usoabitativo", "<i>Uso abitativo<i>")
            {
                HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella,
                HeaderFontSize = 7,
                HeaderGroupText = new List<string> { string.Format("{0}Finalità", string.Concat(Enumerable.Repeat("&nbsp;", 27))) },
                HeaderGroupWidth = 210,
                HeaderGroupTextDeltaX = 13,
                HeaderGroupTextDeltaY = -15,
                HeaderVerticalAlignment = VerticalAlignmentType.Basso
            });
            tabellaAltri.Columns.Add(new ColumnPDF("strumentale2", 70, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Usostrumentale", "<i>Strumentale<i>") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 7, HeaderVerticalAlignment = VerticalAlignmentType.Basso }); //Separatore
            tabellaAltri.Columns.Add(new ColumnPDF("investimento2", 70, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Usoinvestimento", "<i>Investimento<i>") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderFontSize = 7, HeaderVerticalAlignment = VerticalAlignmentType.Basso });
            tabellaAltri.Columns.Add(new ColumnPDF("libero2", 50, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Libero", "Libero")
            {
                HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella,
                HeaderFontSize = 7,
                HeaderGroupText = new List<string> { string.Format("{0}Stato*", string.Concat(Enumerable.Repeat("&nbsp;", 10))) },
                HeaderGroupWidth = 100,
                HeaderGroupTextDeltaX = 13,
                HeaderGroupTextDeltaY = -15,
                HeaderVerticalAlignment = VerticalAlignmentType.Basso
            }
            );
            tabellaAltri.Columns.Add(new ColumnPDF("affittato2", 50, HorizontalAlignmentType.Centrato, false, false, 7, ColumnType.Objectpdf, "Affittato", "Affittato") { HeaderBackgroundColor = ColorPDF.Standard_Grigio_SfondoColonnaTabella, HeaderVerticalAlignment = VerticalAlignmentType.Basso, HeaderFontSize = 7 });

            int e = 0;
            foreach (DataRow r in dtAltri.Rows)
            {

                tabellaAltri.Cells[2, e].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                tabellaAltri.Cells[3, e].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                tabellaAltri.Cells[4, e].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                tabellaAltri.Cells[5, e].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                tabellaAltri.Cells[6, e].ValueObject = new RectanglePDF(11, 11, ColorPDF.Bianco) { DeltaY = 3, BorderWidth = 1, BorderColor = ColorPDF.Immobiliare_Grigio_TestoStandard };
                e++;
            }
           // AddElement(new SpacePDF(7));
            AddElement(tabellaAltri);
            }
            if (dtab.Rows.Count > 0 || dtal.Rows.Count > 0)
            {
                AddElement(new SpacePDF(5));
                AddElement(new FormattedTextAreaPDF("(*) Compilare se la finalità dell'immobile è “Investimento”", EnvironmentFacade.RendererFacade.XLeftLimit) { FontSize = 7 });
            }
            #endregion
        }

        /// <summary>
        /// Recupera i dati necessari alla Section restituendo un DataTable.
        /// </summary>
        /// <returns></returns>
        protected override DataTable GetDataTable()
        {
            return null;
        }

        /// <summary>
        /// Recupera i dati necessari alla Section restituendo un DataSet.
        /// </summary>
        /// <returns></returns>
        protected sealed override DataSet GetDataSet()
        {
            #region Definizione dei parametri
            var ds = new DataSet();
            var parametri = new List<Parametro>
            {
                new Parametro
                {
                    Direction = ParameterDirection.Input,
                    DbType = DbType.Int64,
                    ParameterName = "ChiaveClientePB",
                    Value = EnvironmentFacade.ReportEnvironment.Cliente.Chiave
                }
            };

            #endregion

            ds = EnvironmentFacade.ReportEnvironment.MappaturaPreliminare.ImmobiliareCEUnica ? DataAccess.ExecuteDataSetStoredProcedure(DBProvider.SqlServerConsulenzaUnica, "REP_MappaturaPreliminare_S8_MappStrategicaImmobili", parametri)
                : DataAccess.ExecuteDataSetStoredProcedure(DBProvider.SqlServerConsulenzaEvoluta, "REP_MappaturaPreliminare_S8_MappStrategicaImmobili", parametri);
            #region Ordinamento

            //L’odinamento dei fabbricati elencati nella tabella è costruito con le seguenti regole:
            // 1.	Immobile di residenza (se indicato)
            // 2.	Pertinenza dell’immobile di residenza (se indicata)
            // 3.	Fabbricati del comune di residenza:
            //      	Abitazioni (per indirizzo);
            //      	Box/posti auto (per indirizzo);
            //      	Altre categorie fabbricati (per indirizzo).
            // 4.	Fabbricati di altri comuni (per indirizzo):
            //      	Abitazioni (per indirizzo);
            //      	Box/posti auto (per indirizzo);
            //      	Altre categorie fabbricati (per indirizzo).

            var codiceComuneResidenza = ds.Tables[0].Rows[0]["codComuneResidenza"] != DBNull.Value ? ds.Tables[0].Rows[0]["codComuneResidenza"].ToString() : string.Empty;
            DataTable dtOrdinamentoStep1;
            DataTable dtOrdinamentoStep2;

            if (string.IsNullOrEmpty(codiceComuneResidenza))
            {
                dtOrdinamentoStep1 = ds.Tables[0].AsEnumerable()
                .OrderByDescending(o => o.Field<int>("ordResidenza"))
                .ThenByDescending(o => o.Field<int>("ordPertinenza"))
                .ThenByDescending(o => o.Field<int>("ordindirizzo"))
                .ThenByDescending(o => o.Field<decimal>("controvaloreComune"))
                .ThenBy(o => o.Field<string>("indirizzo"))
                .ThenByDescending(o => o.Field<int>("ordFabbricati"))
                .ThenByDescending(o => o.Field<decimal>("Totale"))
                .CopyToDataTable();

                dtOrdinamentoStep2 = dtOrdinamentoStep1;
            }
            else
            {
                dtOrdinamentoStep1 = ds.Tables[0].AsEnumerable().CopyToDataTable();

                // prima recupero i CodComune = codiceComuneResidenza
                // - verifico che siano presenti prima di ordinare
                if (dtOrdinamentoStep1.AsEnumerable().Any(o => o.Field<string>("CodComune").Equals(codiceComuneResidenza)))
                {
                    dtOrdinamentoStep2 = dtOrdinamentoStep1.AsEnumerable().Where(o => o.Field<string>("CodComune").Equals(codiceComuneResidenza))
                         .OrderByDescending(o => o.Field<int>("ordResidenza"))
                        .ThenByDescending(o => o.Field<int>("ordPertinenza"))
                        .ThenByDescending(o => o.Field<int>("ordindirizzo"))
                        .ThenByDescending(o => o.Field<decimal>("controvaloreComune"))
                         .ThenBy(o => o.Field<string>("indirizzo"))
                        .ThenByDescending(o => o.Field<int>("ordFabbricati"))
                        .ThenByDescending(o => o.Field<decimal>("Totale"))
                        .CopyToDataTable();
                }
                else
                    dtOrdinamentoStep2 = dtOrdinamentoStep1;

                // poi recupero tutti gli altri
                // - verifico che siano presenti prima di ordinare
                if (dtOrdinamentoStep1.AsEnumerable().Any(o => o.Field<string>("CodComune") != codiceComuneResidenza))
                {
                    dtOrdinamentoStep2.Merge(dtOrdinamentoStep1.AsEnumerable().Where(o => o.Field<string>("CodComune") != codiceComuneResidenza)
                         .OrderBy(o => o.Field<string>("indirizzo"))
                        .ThenByDescending(o => o.Field<decimal>("controvaloreComune"))
                         .ThenByDescending(o => o.Field<int>("ordFabbricati"))
                         .ThenByDescending(o => o.Field<decimal>("Totale"))
                         .CopyToDataTable());
                }
            }

            //Rinomino dt di output
            dtOrdinamentoStep2.TableName = "Dati";

            #endregion

            // Dataset di ritorno
            var dsResult = new DataSet();
            dsResult.Tables.Add(dtOrdinamentoStep2.Copy());
            return dsResult;
        }
    }
}
