using CaseAccountingBusinessLogic.OfficePackage;
using CaseAccountingBusinessLogic.OfficePackage.HelperEnums;
using CaseAccountingBusinessLogic.OfficePackage.HelperModels;
using CaseAccountingContracts.ViewModels;
using MigraDoc.DocumentObjectModel;
using MigraDoc.DocumentObjectModel.Tables;
using MigraDoc.Rendering;
using PdfSharp.Pdf;
using System.Text;

namespace CaseAccountingBusinessLogic.BusinessLogic.OfficePackage
{
    public class PdfBuilderProvider
    {
        private readonly string tempFileName = "temp.pdf";
        private Document? document;
        private Section? section;
        private Table? table;

        private static ParagraphAlignment GetParagraphAlignment(PdfParagraphAlignmentType type)
        {
            return type switch
            {
                PdfParagraphAlignmentType.Center => ParagraphAlignment.Center,
                PdfParagraphAlignmentType.Left => ParagraphAlignment.Left,
                _ => ParagraphAlignment.Justify,
            };
        }

        private void DefineStyles(Document document)
        {
            var style = document.Styles["Normal"];
            style.Font.Name = "Times New Roman";
            style.Font.Size = 14;

            style = document.Styles.AddStyle("NormalTitle", "Normal");
            style.Font.Bold = true;
        }

        public void CreateDocument()
        {
            document = new Document();
            DefineStyles(document);
            section = document.AddSection();
        }

        public void CreateParagraph(PdfParagraph pdfParagraph)
        {
            if (section == null)
            {
                return;
            }
            var paragraph = section.AddParagraph(pdfParagraph.Text);
            paragraph.Format.SpaceAfter = "1cm";
            paragraph.Format.Alignment = GetParagraphAlignment(pdfParagraph.ParagraphAlignment);
            paragraph.Style = pdfParagraph.Style;
        }

        public void CreateTable(List<string> columns)
        {
            if (document == null)
            {
                return;
            }
            table = document.LastSection.AddTable();
            foreach (var elem in columns)
            {
                table.AddColumn(elem);
            }
        }

        public void CreateRow(PdfRowParameters rowParameters)
        {
            if (table == null)
            {
                return;
            }
            var row = table.AddRow();
            for (int i = 0; i < rowParameters.Texts.Count; ++i)
            {
                row.Cells[i].AddParagraph(rowParameters.Texts[i]);
                if (!string.IsNullOrEmpty(rowParameters.Style))
                {
                    row.Cells[i].Style = rowParameters.Style;
                }
                Unit borderWidth = 0.5;
                row.Cells[i].Borders.Left.Width = borderWidth;
                row.Cells[i].Borders.Right.Width = borderWidth;
                row.Cells[i].Borders.Top.Width = borderWidth;
                row.Cells[i].Borders.Bottom.Width = borderWidth;
                row.Cells[i].Format.Alignment = GetParagraphAlignment(rowParameters.ParagraphAlignment);
                row.Cells[i].VerticalAlignment = VerticalAlignment.Center;
            }
        }

        private void Save()
        {

            // Регистрация провайдера кодировки для кодировки 1252, без этого ошибОчка была
            Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);

            var renderer = new PdfDocumentRenderer(true)
            {
                Document = document
            };
            renderer.RenderDocument();
            renderer.PdfDocument.Save(tempFileName);
        }

        public byte[] GetFile()
        {
            Save();
            byte[] file = File.ReadAllBytes(tempFileName);
            File.Delete(tempFileName);
            return file;
        }

        public byte[] GetHearingLawyerReportFile(PdfData<ReportHearingLawyerViewModel> data)
        {
            CreateDocument();

            CreateParagraph(new PdfParagraph
            {
                Text = data.Title,
                Style = "NormalTitle",
                ParagraphAlignment = PdfParagraphAlignmentType.Center
            });

            CreateParagraph(new PdfParagraph
            {
                Text = $"за период с {data.DateFrom.ToShortDateString()} " +
                    $"по {data.DateTo.ToShortDateString()}",
                Style = "Normal",
                ParagraphAlignment = PdfParagraphAlignmentType.Center
            });

            CreateTable(new List<string> { "4cm","5cm", "3cm", "3cm" });

            CreateRow(new PdfRowParameters
            {
                Texts = new List<string> { "Номер слушания", "Дело", "Дата проведения", "Юрист" },
                Style = "NormalTitle",
                ParagraphAlignment = PdfParagraphAlignmentType.Center
            });

            foreach (var record in data.Records)
            {
                List<CaseLawyerViewModel> casesAndLawyes = record.CaseLawyers;
                int recordHeight = casesAndLawyes.Count + 1;
                for (int i = 0; i < recordHeight; i++)
                {
                    List<string> cellsData = new() { "", "", "", "" };
                    if (i == 0)
                    {
                        cellsData[0] = record.Hearing;
                        CreateRow(new PdfRowParameters
                        {
                            Texts = cellsData,
                            Style = "Normal",
                            ParagraphAlignment = PdfParagraphAlignmentType.Left
                        });
                        continue;
                    }
                    int k = i - 1;
                    if (k < casesAndLawyes.Count)
                    {
                        cellsData[1] = casesAndLawyes[k].Case;
                        cellsData[2] = casesAndLawyes[k].Date.ToString("yyyy-MM-dd");
                        cellsData[3] = casesAndLawyes[k].Lawyer;
                    }
                    CreateRow(new PdfRowParameters
                    {
                        Texts = cellsData,
                        Style = "Normal",
                        ParagraphAlignment = PdfParagraphAlignmentType.Left
                    });
                }
            }

            return GetFile();
        }
    }
}
