К статье
Практический материал

Разработка и Конфигурация · 12 мин

Как заполнить табличный документ 1С программно

Как заполнить табличный документ 1С программно: вывод областей из макета, заполнение параметров, циклы, итоги и оформление. Примеры кода на встроенном языке.

Табличный документ в 1С — основной инструмент формирования печатных форм, отчётов и произвольных табличных представлений данных. Заполнить его программно можно двумя принципиально разными способами: через готовый макет с именованными областями либо прямой записью значений в ячейки по координатам. Выбор зависит от задачи: типовые печатные формы почти всегда строятся на макетах, а простые служебные выгрузки допустимо собирать напрямую.

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

Ниже разобраны оба подхода с примерами кода, типовыми ошибками и способами проверки результата. Примеры приведены на встроенном языке 1С и подходят для управляемых и обычных форм — различия касаются только способа показа результата пользователю.

Создание объекта и базовые принципы работы

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

Важное свойство, которое стоит установить сразу, — ТолькоПросмотр. Если документ предназначен для печати, установите его в Истина, чтобы пользователь случайно не отредактировал ячейки. Также полезны свойства АвтоМасштаб, ОриентацияСтраницы и ИмяПараметровПечати — последнее позволяет сохранять настройки принтера для конкретной формы.

ТабДок = Новый ТабличныйДокумент;

ТабДок.ТолькоПросмотр = Истина;

ТабДок.АвтоМасштаб = Истина;

ТабДок.ОриентацияСтраницы = ОриентацияСтраницы.Портрет;

Если табличный документ размещён как реквизит управляемой формы, обращение идёт напрямую к имени реквизита, а не к локальной переменной. При этом изменения видны пользователю сразу, без дополнительных вызовов, но каждое обращение к реквизиту формы — это серверный вызов, поэтому массовое заполнение лучше выполнять в одной серверной процедуре целиком.

Заполнение через макет и области

Основной и рекомендуемый способ — использование макета табличного документа. Макет хранится в конфигурации (общий макет или макет объекта) и содержит именованные области: «Шапка», «СтрокаТовары», «Подвал» и т.п. Разработчик получает область методом ПолучитьОбласть("ИмяОбласти"), заполняет её параметры и выводит в результирующий документ.

Макет = Документы.РеализацияТоваровУслуг.ПолучитьМакет("МакетПечати");

ОбластьШапка = Макет.ПолучитьОбласть("Шапка");

ОбластьШапка.Параметры.НомерДокумента = Ссылка.Номер;

ОбластьШапка.Параметры.Контрагент = Ссылка.Контрагент;

ТабДок.Вывести(ОбластьШапка);

Параметры области — это ячейки макета, у которых свойство «Заполнение» установлено в «Параметр», а имя параметра задано в свойстве ячейки. Если обратиться к параметру, которого нет в области, возникнет ошибка времени выполнения. Поэтому имена параметров стоит сверять непосредственно в конфигураторе, открыв макет и щёлкнув по ячейке.

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

Циклический вывод строк и итоги

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

ОбластьСтрока = Макет.ПолучитьОбласть("Строка");

Для Каждого СтрокаТовары Из Ссылка.Товары Цикл

ОбластьСтрока.Параметры.Номенклатура = СтрокаТовары.Номенклатура;

ОбластьСтрока.Параметры.Количество = СтрокаТовары.Количество;

ОбластьСтрока.Параметры.Сумма = СтрокаТовары.Сумма;

ТабДок.Вывести(ОбластьСтрока);

КонецЦикла;

Для больших выборок эффективнее использовать запрос с обходом результата, чем обращение к табличной части через ссылку — каждое обращение к реквизиту объекта через точку от ссылки порождает чтение из базы. Выгрузите нужные поля запросом один раз и итерируйте выборку.

Итоги считаются двумя способами: накоплением в переменных внутри цикла либо итогами самого запроса (конструкция ИТОГИ). Второй вариант предпочтительнее при группировках: запрос сразу вернёт итоговые записи по группам, и область «ПодвалГруппы» можно выводить без ручного суммирования. Ручной подсчёт оправдан только для простых форм с одним уровнем детализации.

Порядок формирования печатной формы
  1. 1
    Создайте объект Новый ТабличныйДокумент и задайте свойства печати
  2. 2
    Получите макет через ПолучитьМакет у менеджера объекта или общего макета
  3. 3
    Выведите шапку, заполнив её параметры
  4. 4
    В цикле по данным выведите области строк
  5. 5
    Выведите подвал с итогами
  6. 6
    Покажите результат методом Показать или сохраните в файл

Прямая запись в ячейки без макета

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

ТабДок.Область(1, 1).Текст = "Номенклатура";

ТабДок.Область(1, 2).Текст = "Количество";

НомерСтроки = 2;

Для Каждого Строка Из Выборка Цикл

ТабДок.Область(НомерСтроки, 1).Текст = Строка(Строка.Номенклатура);

ТабДок.Область(НомерСтроки, 2).Текст = Строка.Количество;

НомерСтроки = НомерСтроки + 1;

КонецЦикла;

Обратиться к ячейке можно и по адресу в стиле R1C1: ТабДок.Область("R2C3"). Через область доступны не только текст, но и оформление: Шрифт, ЦветФона, Границы, ГоризонтальноеПоложение. Это позволяет программно подсвечивать строки по условию — например, отрицательные остатки красным фоном.

Ограничение подхода очевидно: вся структура зашита в код, и любое изменение формы требует правки модуля и обновления конфигурации или расширения. Поэтому прямую запись разумно применять для внутренних служебных выгрузок, а не для печатных форм, которые видят контрагенты.

Макет или прямая запись

Макет с областями

Подходит для печатных форм и отчётов. Оформление меняется в конфигураторе без правки кода. Требует создания макета.

Прямая запись в ячейки

Подходит для служебных таблиц и простых выгрузок. Быстро пишется, но структура жёстко зашита в код.

Построитель отчёта / СКД

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

Расшифровка, группировки и разрывы страниц

Расшифровка реализуется через свойство ячейки Расшифровка в макете: в параметр области записывается не только текст, но и значение расшифровки (например, ссылка на документ). При двойном щелчке по ячейке пользователь получает это значение через обработчик ОбработкаРасшифровки. Для ссылок стандартное действие — открытие объекта.

Уровни группировок задаются методом НачатьГруппуСтрок() и ЗакончитьГруппуСтрок(). Это даёт пользователю возможность сворачивать секции документа, как в типовых отчётах. Работает только при последовательном выводе областей между вызовами этих методов.

Для печати важен контроль разрывов страниц. Метод ПроверитьВывод(МассивОбластей) сообщает, поместятся ли области на текущей странице; если нет — вызывается ВывестиГоризонтальныйРазделительСтраниц(). Это стандартный приём, чтобы подписи в подвале не уходили на отдельный лист, а шапка таблицы не оставалась в одиночестве внизу страницы.

МассивОбластей = Новый Массив;

МассивОбластей.Добавить(ОбластьСтрока);

МассивОбластей.Добавить(ОбластьПодвал);

Если Не ТабДок.ПроверитьВывод(МассивОбластей) Тогда

ТабДок.ВывестиГоризонтальныйРазделительСтраниц();

КонецЕсли;

ПроверитьВывод корректно работает только если у табличного документа заданы параметры страницы (размер бумаги, поля, ориентация). Без них метод может возвращать Истина даже для заведомо не помещающихся областей.
ПЗ
Практическое замечание

Вывод результата: показать, сохранить, напечатать

Готовый документ показывается пользователю методом Показать("Заголовок") — в управляемом приложении откроется отдельное окно. Если документ является реквизитом формы, достаточно заполнить реквизит на сервере, и форма отобразит его сама.

Сохранение в файл выполняется методом Записать(ИмяФайла, ТипФайлаТабличногоДокумента). Поддерживаются форматы MXL, XLSX, PDF, HTML, ODS и другие. Для отправки печатной формы по почте типовой приём — сохранить во временный файл PDF и вложить в письмо. Прямая печать без показа выполняется методом Напечатать(РежимИспользованияДиалогаПечати.НеИспользовать).

При работе на сервере учитывайте: файловые операции выполняются в каталоге сервера 1С, а не клиента. Путь, доступный клиенту, серверу может быть недоступен, поэтому файлы для пользователя формируют во временном хранилище и передают на клиента через ПоместитьВоВременноеХранилище.

Типичные ошибки и проверка результата

Самая частая ошибка — обращение к несуществующей области или параметру. Она диагностируется сразу по тексту исключения, но если вывод областей обёрнут в попытку/исключение, ошибка может быть проглочена и документ окажется пустым. Второй частый случай — вывод области без заполнения параметров: ячейки остаются с текстом-шаблоном вида «[НомерДокумента]» либо пустыми, в зависимости от настройки макета.

Ещё одна группа проблем — типы данных. Параметр области принимает значение любого типа, но отображается оно по формату ячейки макета. Если формат не задан, дата выведется со временем, а число — с лишними разрядностями. Форматную строку лучше задавать в макете, а не преобразовывать значения в строку в коде: строка вместо числа ломает итоги при последующей обработке табличного документа.

Типичные ошибки
01
Обращение к области по имени с опечаткой — ошибка выполнения или пустой документ при подавлении исключений
02
Передача строки вместо числа в параметр — нарушается формат и невозможны итоговые вычисления
03
Вывод строк в цикле без ПроверитьВывод — подвал и подписи уезжают на отдельный лист
04
Обращение к реквизитам ссылки в цикле — каждое обращение читает базу, форма формируется неприемлемо долго
05
Забытый ТолькоПросмотр — пользователь случайно редактирует печатную форму перед печатью
Контрольные точки

Как проверить результат

Структура документа
Норма

Все области выведены в правильном порядке, шапка и подвал на месте

Тревожный признак

Пустые участки, отсутствующие строки, текст-шаблон вида [ИмяПараметра]

Числа и даты
Норма

Формат соответствует макету, итоги сходятся с данными источника

Тревожный признак

Даты со временем, числа как текст, расхождение итогов

Разбиение на страницы
Норма

Подписи не оторваны от таблицы, шапка не в одиночестве внизу листа

Тревожный признак

Подвал на отдельной странице, обрезанные строки

FAQ

Как вывести табличный документ на управляемой форме?

Добавьте в форму реквизит типа «ТабличныйДокумент» и элемент формы, связанный с ним. Заполняйте реквизит в серверной процедуре — форма отобразит содержимое автоматически. Метод Показать() для реквизита формы не нужен.

Можно ли заполнить табличный документ из запроса без цикла?

Напрямую «выгрузить» запрос в табличный документ нельзя — в отличие от таблицы значений. Но можно обойти выборку в цикле с выводом области строки, либо использовать СКД/построитель отчёта, которые сформируют табличный документ из запроса автоматически.

Почему в ячейках выводится текст вида [ИмяПараметра]?

Это отображение незаполненного параметра макета. Либо параметру области не присвоено значение перед выводом, либо имя параметра в коде не совпадает с именем в ячейке макета. Проверьте свойства ячейки в конфигураторе.

Как сохранить табличный документ в PDF?

Используйте ТабДок.Записать(ИмяФайла, ТипФайлаТабличногоДокумента.PDF). Убедитесь, что заданы параметры страницы — от них зависит разбиение PDF на листы. На сервере файл создаётся в файловой системе сервера 1С.

Чем табличный документ отличается от таблицы значений?

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

Как сделать расшифровку ячейки с открытием документа?

В макете задайте ячейке параметр расшифровки, а в коде запишите в него ссылку: Область.Параметры.РасшифровкаСтроки = Строка.Ссылка. В форме с табличным документом обработайте событие ОбработкаРасшифровки и откройте значение через ПоказатьЗначение.

Итог

Что важно запомнить

Печатные формы стройте через макет: ПолучитьОбласть, заполнение Параметры, Вывести. Данные готовьте запросом, итоги считайте в запросе или в цикле. Перед выводом подвала используйте ПроверитьВывод, а результат проверяйте на пустые параметры и формат чисел.