Как вывести составные и сложные области в табличный документ 1С?

Программист 1С v8.3 (Управляемые формы)
← На главную

При разработке отчетов и обработок в 1С:Предприятие часто возникает задача формирования сложных печатных форм, таких как расписания, графики или «шахматки». Основная трудность заключается в том, что стандартная сетка табличного документа не всегда позволяет легко состыковать области разной высоты и ширины в одной логической строке. Например, когда заголовок должен объединять несколько колонок данных, а сами данные под ним имеют сложную структуру. Рассмотрим подробно, как эффективно решать такие задачи, используя встроенные механизмы 1С.

Постановка задачи и анализ структуры

Представим ситуацию: нам необходимо вывести строку расписания. Слева находится номер строки (высотой в три ячейки), затем идет общее название интервала (шириной в две ячейки, но высотой в одну), а под этим названием должны располагаться конкретные временные отрезки (интервалы), каждый из которых занимает свою ячейку. Проблема в том, что при обычном использовании метода Вывести() каждая новая область начинается с новой строки, а метод Присоединить() работает только в пределах текущей активной строки. Чтобы добиться желаемого результата, нам нужно научиться «собирать» сложные блоки и правильно позиционировать их в конечном документе.

Метод 1: Использование вспомогательного (буферного) табличного документа

Один из самых надежных и понятных способов — это создание временного табличного документа, который выступает в роли «сборочного цеха». Мы формируем в нем нужный нам сложный блок (например, шапку с подписями интервалов), а затем целиком присоединяем этот буфер к основному документу. Рассмотрим пример кода, который реализует этот подход:


// Создаем основной документ и временный буфер
ТабДок = Новый ТабличныйДокумент;
ТабДок2 = Новый ТабличныйДокумент;

// Получаем область с номером строки из макета
СтрокаТаблицы = Макет.ПолучитьОбласть("Строка|Номер");
СтрокаТаблицы.Параметры.Номер = 1;
// Выводим номер в основной документ
ТабДок.Присоединить(СтрокаТаблицы);

// Теперь собираем сложную правую часть во временном документе ТабДок2
Название = Макет.ПолучитьОбласть("Название|Интервалы");
Название.Параметры.Имя = "Рейс №101";
ТабДок2.Вывести(Название); // Название выводится сверху

// Добавляем детализацию под названием
Ин1 = Макет.ПолучитьОбласть("Времена|Интервал2");
Ин1.Параметры.Инт2 = "08:00-10:00";
ТабДок2.Вывести(Ин1); // Выводится под названием

// Присоединяем второй интервал рядом в том же временном документе
Ин2 = Макет.ПолучитьОбласть("Времена|Интервал1");
Ин2.Параметры.Инт1 = "10:00-12:00";
ТабДок2.Присоединить(Ин2); 

// Наконец, присоединяем весь собранный блок ТабДок2 к основному документу
ТабДок.Присоединить(ТабДок2);

Проанализируем этот код: использование метода Присоединить(ТабДок2) позволяет вставить сразу весь массив ячеек, при этом 1С автоматически рассчитает необходимые координаты. Это избавляет разработчика от ручного вычисления индексов строк и колонок.

Метод 2: Работа с абсолютными координатами через ВставитьОбласть

Если структура документа крайне нерегулярна, можно использовать метод ВставитьОбласть(). Этот метод позволяет буквально «вклеить» фрагмент макета в любое место итоговой таблицы по заданному адресу. Однако здесь важно учитывать производительность: при большом объеме данных (сотни и тысячи строк) этот метод работает медленнее, чем Вывести() или Присоединить(), так как системе приходится каждый раз пересчитывать структуру стилей и границ документа.

Рассмотрим, как это выглядит на практике:


// Определяем границы вставки
нВерх = пНомер.Верх;
нЛево = пНомер.Право + 1;
нПраво = нЛево + Название.ШиринаТаблицы - 1;
нНиз = нВерх + Название.ВысотаТаблицы - 1;

// Получаем область из макета и вставляем ее в основной документ
тВставка = Название.Область(1, 1, Название.ВысотаТаблицы, Название.ШиринаТаблицы);
ТабДок.ВставитьОбласть(тВставка, ТабДок.Область(нВерх, нЛево, нНиз, нПраво));

Обратите внимание, что вместо формата адресации RC (например, "R1C1"), лучше использовать числовые координаты метода Область(НомерСтроки, НомерКолонки). Это делает код более читаемым и менее подверженным ошибкам при динамическом расчете координат.

Метод 3: Построчный вывод с последующим программным объединением

В некоторых случаях проще сначала вывести данные в «плоском» виде, а затем программно объединить ячейки. Это особенно удобно для динамических расписаний, где количество колонок заранее неизвестно.

Рассмотрим алгоритм действий:

  1. Выясним минимальный «шаг» сетки по ширине и высоте.
  2. Выведем все данные обычными методами Вывести() и Присоединить(), заполняя ячейки информацией.
  3. Используем метод Область().Объединить() для создания визуальных блоков.

Пример кода для объединения ячеек:


// Объединяем ячейки в первой колонке для создания эффекта высокой ячейки номера
ОбластьНомера = ТабДок.Область(ТекущаяСтрока, 1, ТекущаяСтрока + 2, 1);
ОбластьНомера.Объединить();
ОбластьНомера.ВертикальноеПоложение = ВертикальноеПоложение.Центр;

Важные нюансы и рекомендации

При работе со сложными областями часто возникают проблемы с форматированием. Разберем основные моменты, на которые стоит обратить внимание:

  1. Заполнение параметров: Если вы планируете выводить одну и ту же область макета несколько раз (например, несколько интервалов в одной строке), заполняйте параметры ОбластьМакета.Параметры.Значение = ... до того, как область будет добавлена в основной документ. Если пытаться заполнять параметры в уже сформированном ТабличномДокументе по имени, 1С заполнит все одноименные параметры во всем документе или строке одинаковыми значениями.
  2. Ширина колонок: При использовании метода Присоединить() убедитесь, что ширина колонок в макете настроена корректно. Часто бывает полезно сначала вывести «эталонную» строку (шапку), в которой заданы ширины всех колонок, а затем выводить данные.
  3. Фиксация областей: Для удобства пользователей в больших расписаниях рекомендуется фиксировать шапку и левую колонку. Выясним, на какой строке заканчивается заголовок, и установим свойства ТабДок.ФиксацияСверху = НомерСтрокиШапки и ТабДок.ФиксацияСлева = НомерКолонкиНомера.
  4. Производительность: Если ваш отчет строится долго, проанализируйте использование ВставитьОбласть. Попробуйте заменить его на комбинацию Вывести и Присоединить с использованием буферного документа.

Таким образом, комбинируя методы работы с областями и используя вспомогательные табличные документы, мы можем создавать отчеты практически любой сложности. Главное — четко представлять структуру итоговой таблицы и выбирать метод вывода, исходя из требований к производительности и гибкости макета.

← На главную