public static void CreateJob(Album album)
        {
            if (ChangePanels.Count == 0) return;

            List<FacadeMounting> facades = album.LibLoadService.Facades;

            // Показать список панелей с изменившейся маркой.
            // Исключение ошибочныйх панелей.
            ChangePanels.Sort();
            FormChangePanel formChange = new FormChangePanel();
            if (Application.ShowModalDialog(formChange) != System.Windows.Forms.DialogResult.OK)
            {
                // Прервать
                formChange.SetModaless();
                Application.ShowModelessDialog(formChange);
                throw new Exception(AcadLib.General.CanceledByUser);
            }
            else
            {
                var doc = Application.DocumentManager.MdiActiveDocument;
                Database db = doc.Database;
                Editor ed = doc.Editor;

                IdTextStylePik = db.GetTextStylePIK();
                ColorChange = Color.FromRgb(205, 77, 4);

                // все монтажные планы сгруппированные по секциям по возрастания
                var mountPlansSecGroups = facades.SelectMany(s => s.Floors).GroupBy(g => g).Select(s => s.First())
                                                    .GroupBy(g => g.Section).OrderBy(o => o.Key);

                var mountPlansFloorGroups = mountPlansSecGroups.SelectMany(s => s).GroupBy(g=>g.Storey);

                double totalLen = 0;// SecCols.Sum(s => s.LengthMax) + (SecCols.Count-1) * OffsetMountPlansX;
                double tableHeight = ChangePanels.Count * 800 + 2500;
                double totalHeight = 0;// FloorRows.Sum(f => f.HeightMax) + (FloorRows.Count-1) * OffsetMountPlansY +tableHeight;

                // определение максимальной длины плана в каждой секции
                foreach (var item in mountPlansSecGroups)
                {
                    var maxLen = item.Max(m => m.PlanExtentsLength);
                    totalLen += maxLen;
                    var secCol = new SectionColumn(item.Key, maxLen);
                    SecCols.Add(secCol);
                }
                totalLen += (mountPlansSecGroups.Count() - 1) * OffsetMountPlansX;

                // определение максимальной высоты плана в каждом этаже
                foreach (var item in mountPlansFloorGroups)
                {
                    var maxH = item.Max(m => m.PlanExtentsHeight);
                    totalHeight += maxH;
                    var fr = new FloorRow(item.Key, maxH);
                    FloorRows.Add(fr);
                }
                totalHeight += (mountPlansFloorGroups.Count() - 1) * OffsetMountPlansY + tableHeight;

                // Запрос точки вставки изменений
                // Общая высота планов изменений
                var ptRes = ed.GetRectanglePoint(totalLen, totalHeight);// ed.GetPointWCS("Точка вставки планов задания на изменение марок покраски.");
                var ptStart = new Point3d(ptRes.X, ptRes.Y + totalHeight, 0);
                //AcadLib.Jigs.RectangleJig

                // Положение столбцов секций
                double xPrev = ptStart.X;
                foreach (var item in SecCols)
                {
                    item.X = xPrev;
                    xPrev += item.LengthMax + OffsetMountPlansX;
                }

                double yPrev = ptStart.Y;
                foreach (var item in FloorRows)
                {
                    item.Y = yPrev;
                    yPrev -= item.HeightMax + OffsetMountPlansY;
                }

                //SecCols.Sort();
                //FloorRows.Sort();

                //// Определение X для столбцов секций
                //double xPrev = ptStart.X;
                //SecCols.First().X = xPrev;
                //foreach (var secCol in SecCols.Skip(1))
                //{
                //    secCol.X = xPrev + OffsetMountPlansX + secCol.LengthMax;
                //    xPrev = secCol.X;
                //}
                //// Определение Y для этажей
                //double yPrev = ptStart.Y;
                //FloorRows.First().Y = yPrev;
                //foreach (var fr in FloorRows.Skip(1))
                //{
                //    fr.Y = yPrev - fr.HeightMax - OffsetMountPlansY;
                //    yPrev = fr.Y;
                //}

                //// группировка измененных панелей по секциям и этажам
                //var groupChPanels = ChangePanels.OrderBy(o=>o.FloorRow.Storey).ThenBy(o=>o.SecCol.Section)
                //                                .GroupBy(g => new { g.FloorRow, g.SecCol });

                // Формирование паланов изменений и общей таблицы изменений.
                using (var t = db.TransactionManager.StartTransaction())
                {
                    var ptPlan = ptStart;
                    var ms = db.CurrentSpaceId.GetObject(OpenMode.ForWrite) as BlockTableRecord;

                    // подпись секций
                    var heightFirstFloor = FloorRows.First().HeightMax;
                    double yTextSection = ptStart.Y + heightFirstFloor + 2500;
                    foreach (var secCol in SecCols)
                    {
                        var ptText = new Point3d(secCol.X + secCol.LengthMax * 0.5, yTextSection, 0);
                        string text = "Секция " + secCol.Section.ToString();
                        addText(ms, t, ptText, text, 1500, TextHorizontalMode.TextCenter);
                    }

                    var ptTextData = new Point3d(ptStart.X + totalLen*0.5,yTextSection+3500, 0);
                    string textData = "Изменения марок покраски от " + album.Date;
                    addText(ms, t, ptTextData, textData, 1500, TextHorizontalMode.TextCenter);

                    var xFloorTexts = ptStart.X;
                    foreach (var groupSec in mountPlansSecGroups)
                    {
                        var secCol = SecCols.First(s => s.Section == groupSec.Key);
                        foreach (var item in groupSec)
                        {
                            var fr = FloorRows.First(f => f.Storey == item.Storey);
                            ptPlan = new Point3d(secCol.X, fr.Y, 0);
                            // изменения для этого монтажного плана
                            var chPanels = ChangePanels.Where(p => p.PanelMount.Floor == item);
                            var extPlan = createChangePlan(chPanels.ToList(), ptPlan, item.IdBtrMounting, ms, t);
                            if (extPlan.MinPoint.X < xFloorTexts) xFloorTexts = extPlan.MinPoint.X;
                        }
                    }

                    // подпись этажа
                    foreach (var fr in FloorRows)
                    {
                        var ptText = new Point3d(xFloorTexts-5000, fr.Y + fr.HeightMax * 0.5, 0);
                        string text = fr.Storey.ToString() + "-этаж";
                        addText(ms, t, ptText, text, 1500, TextHorizontalMode.TextCenter);
                    }

                    // Таблица изменений
                    ptPlan = new Point3d(ptPlan.X, ptPlan.Y - 10000, 0);
                    ChangeJobTable chTable = new ChangeJobTable(ChangePanels, db, ptPlan);
                    chTable.Create(ms, t);

                    t.Commit();
                }
            }
        }
        public static void CreateJob(Album album)
        {
            if (ChangePanels.Count == 0)
            {
                return;
            }

            List <FacadeMounting> facades = album.LibLoadService.Facades;

            // Показать список панелей с изменившейся маркой.
            // Исключение ошибочныйх панелей.
            ChangePanels.Sort();
            FormChangePanel formChange = new FormChangePanel();

            if (Application.ShowModalDialog(formChange) != System.Windows.Forms.DialogResult.OK)
            {
                // Прервать
                formChange.SetModaless();
                Application.ShowModelessDialog(formChange);
                throw new Exception(AcadLib.General.CanceledByUser);
            }
            else
            {
                var      doc = Application.DocumentManager.MdiActiveDocument;
                Database db  = doc.Database;
                Editor   ed  = doc.Editor;

                IdTextStylePik = db.GetTextStylePIK();
                ColorChange    = Color.FromRgb(205, 77, 4);

                // все монтажные планы сгруппированные по секциям по возрастания
                var mountPlansSecGroups = facades.SelectMany(s => s.Floors).GroupBy(g => g).Select(s => s.First())
                                          .GroupBy(g => g.Section).OrderBy(o => o.Key);

                var mountPlansFloorGroups = mountPlansSecGroups.SelectMany(s => s).GroupBy(g => g.Storey);

                double totalLen    = 0; // SecCols.Sum(s => s.LengthMax) + (SecCols.Count-1) * OffsetMountPlansX;
                double tableHeight = ChangePanels.Count * 800 + 2500;
                double totalHeight = 0; // FloorRows.Sum(f => f.HeightMax) + (FloorRows.Count-1) * OffsetMountPlansY +tableHeight;

                // определение максимальной длины плана в каждой секции
                foreach (var item in mountPlansSecGroups)
                {
                    var maxLen = item.Max(m => m.PlanExtentsLength);
                    totalLen += maxLen;
                    var secCol = new SectionColumn(item.Key, maxLen);
                    SecCols.Add(secCol);
                }
                totalLen += (mountPlansSecGroups.Count() - 1) * OffsetMountPlansX;

                // определение максимальной высоты плана в каждом этаже
                foreach (var item in mountPlansFloorGroups)
                {
                    var maxH = item.Max(m => m.PlanExtentsHeight);
                    totalHeight += maxH;
                    var fr = new FloorRow(item.Key, maxH);
                    FloorRows.Add(fr);
                }
                totalHeight += (mountPlansFloorGroups.Count() - 1) * OffsetMountPlansY + tableHeight;

                // Запрос точки вставки изменений
                // Общая высота планов изменений
                var ptRes   = ed.GetRectanglePoint(totalLen, totalHeight);// ed.GetPointWCS("Точка вставки планов задания на изменение марок покраски.");
                var ptStart = new Point3d(ptRes.X, ptRes.Y + totalHeight, 0);
                //AcadLib.Jigs.RectangleJig

                // Положение столбцов секций
                double xPrev = ptStart.X;
                foreach (var item in SecCols)
                {
                    item.X = xPrev;
                    xPrev += item.LengthMax + OffsetMountPlansX;
                }

                double yPrev = ptStart.Y;
                foreach (var item in FloorRows)
                {
                    item.Y = yPrev;
                    yPrev -= item.HeightMax + OffsetMountPlansY;
                }

                //SecCols.Sort();
                //FloorRows.Sort();

                //// Определение X для столбцов секций
                //double xPrev = ptStart.X;
                //SecCols.First().X = xPrev;
                //foreach (var secCol in SecCols.Skip(1))
                //{
                //    secCol.X = xPrev + OffsetMountPlansX + secCol.LengthMax;
                //    xPrev = secCol.X;
                //}
                //// Определение Y для этажей
                //double yPrev = ptStart.Y;
                //FloorRows.First().Y = yPrev;
                //foreach (var fr in FloorRows.Skip(1))
                //{
                //    fr.Y = yPrev - fr.HeightMax - OffsetMountPlansY;
                //    yPrev = fr.Y;
                //}

                //// группировка измененных панелей по секциям и этажам
                //var groupChPanels = ChangePanels.OrderBy(o=>o.FloorRow.Storey).ThenBy(o=>o.SecCol.Section)
                //                                .GroupBy(g => new { g.FloorRow, g.SecCol });

                // Формирование паланов изменений и общей таблицы изменений.
                using (var t = db.TransactionManager.StartTransaction())
                {
                    var ptPlan = ptStart;
                    var ms     = db.CurrentSpaceId.GetObject(OpenMode.ForWrite) as BlockTableRecord;

                    // подпись секций
                    var    heightFirstFloor = FloorRows.First().HeightMax;
                    double yTextSection     = ptStart.Y + heightFirstFloor + 2500;
                    foreach (var secCol in SecCols)
                    {
                        var    ptText = new Point3d(secCol.X + secCol.LengthMax * 0.5, yTextSection, 0);
                        string text   = "Секция " + secCol.Section.ToString();
                        addText(ms, t, ptText, text, 1500, TextHorizontalMode.TextCenter);
                    }

                    var    ptTextData = new Point3d(ptStart.X + totalLen * 0.5, yTextSection + 3500, 0);
                    string textData   = "Изменения марок покраски от " + album.Date;
                    addText(ms, t, ptTextData, textData, 1500, TextHorizontalMode.TextCenter);

                    var xFloorTexts = ptStart.X;
                    foreach (var groupSec in mountPlansSecGroups)
                    {
                        var secCol = SecCols.First(s => s.Section == groupSec.Key);
                        foreach (var item in groupSec)
                        {
                            var fr = FloorRows.First(f => f.Storey == item.Storey);
                            ptPlan = new Point3d(secCol.X, fr.Y, 0);
                            // изменения для этого монтажного плана
                            var chPanels = ChangePanels.Where(p => p.PanelMount.Floor == item);
                            var extPlan  = createChangePlan(chPanels.ToList(), ptPlan, item.IdBtrMounting, ms, t);
                            if (extPlan.MinPoint.X < xFloorTexts)
                            {
                                xFloorTexts = extPlan.MinPoint.X;
                            }
                        }
                    }

                    // подпись этажа
                    foreach (var fr in FloorRows)
                    {
                        var    ptText = new Point3d(xFloorTexts - 5000, fr.Y + fr.HeightMax * 0.5, 0);
                        string text   = fr.Storey.ToString() + "-этаж";
                        addText(ms, t, ptText, text, 1500, TextHorizontalMode.TextCenter);
                    }

                    // Таблица изменений
                    ptPlan = new Point3d(ptPlan.X, ptPlan.Y - 10000, 0);
                    ChangeJobTable chTable = new ChangeJobTable(ChangePanels, db, ptPlan);
                    chTable.Create(ms, t);

                    t.Commit();
                }
            }
        }