Разработка и Конфигурация · 14 мин
Как программно добавить табличную часть на форму в 1С
Разбираем, как программно добавить табличную часть на форму в 1С: создание реквизитов, элементов формы, примеры кода для управляемых форм и типичные ошибки.
Задача программного добавления табличной части на форму возникает, когда состав колонок или сама таблица должны формироваться динамически — по настройкам пользователя, по данным из базы или по условиям бизнес-логики. Стандартный путь через конфигуратор здесь не подходит: таблица создаётся кодом в модуле формы, обычно в обработчике ПриСозданииНаСервере.
В управляемых формах 1С процедура состоит из трёх этапов: добавление реквизита формы типа «ТаблицаЗначений», добавление колонок этого реквизита и создание элементов формы, которые будут отображать таблицу пользователю. Всё это выполняется методами ИзменитьРеквизиты() и коллекцией Элементы.
Важно понимать ограничение: программно созданная таблица — это реквизит формы, а не табличная часть объекта конфигурации. Если нужно, чтобы данные сохранялись в базе вместе с документом или справочником, табличную часть следует добавить в метаданные объекта через конфигуратор, а программно управлять только её отображением.
Когда программное добавление оправдано, а когда нет
Программное создание таблицы на форме оправдано в трёх ситуациях. Первая — динамический состав колонок: например, отчётная форма, где колонки соответствуют периодам, складам или статьям, выбранным пользователем. Вторая — универсальные обработки, которые работают с разными объектами и заранее не знают структуру данных. Третья — таблицы, зависящие от настроек: пользователь включает и отключает отображаемые показатели.
Если состав таблицы известен заранее и не меняется, правильнее добавить табличную часть в метаданные объекта или создать реквизит формы в конфигураторе. Программный подход в таком случае усложняет поддержку: колонки не видны в редакторе формы, их свойства нельзя настроить визуально, а любые изменения требуют правки кода.
Также программное создание не подходит, когда таблица должна храниться в базе данных. Реквизит формы существует только во время жизни формы: после закрытия данные теряются, если их не сохранить отдельно.
Как выбрать подход
Шаг 1. Создание реквизита формы типа «Таблица значений»
Реквизит формы — это данные, которые форма хранит и отображает. Для таблицы создаётся реквизит с типом ТаблицаЗначений, а затем для него описываются колонки. Всё это выполняется в серверном контексте, чаще всего в ПриСозданииНаСервере.
Колонки добавляются как массив объектов Новый РеквизитФормы, где указывается имя, тип значения и путь — имя родительского реквизита-таблицы. Затем вызывается метод ИзменитьРеквизиты(ДобавляемыеРеквизиты), который применяет изменения к форме.
&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
// Создаём реквизит-таблицу
ДобавляемыеРеквизиты = Новый Массив;
ДобавляемыеРеквизиты.Добавить(
Новый РеквизитФормы("ТоварыДинамические",
Новый ОписаниеТипов("ТаблицаЗначений")));
// Колонки таблицы
ДобавляемыеРеквизиты.Добавить(
Новый РеквизитФормы("Номенклатура",
Новый ОписаниеТипов("СправочникСсылка.Номенклатура"),
"ТоварыДинамические"));
ДобавляемыеРеквизиты.Добавить(
Новый РеквизитФормы("Количество",
Новый ОписаниеТипов("Число", Новый КвалификаторыЧисла(15, 3)),
"ТоварыДинамические"));
ДобавляемыеРеквизиты.Добавить(
Новый РеквизитФормы("Цена",
Новый ОписаниеТипов("Число", Новый КвалификаторыЧисла(15, 2)),
"ТоварыДинамические"));
ИзменитьРеквизиты(ДобавляемыеРеквизиты);
КонецПроцедуры
Обратите внимание на порядок: сначала в массив добавляется сама таблица, затем её колонки с указанием пути к таблице. Тип колонки задаётся через ОписаниеТипов — для ссылочных типов указывается конкретный вид объекта, для чисел — длина и точность через КвалификаторыЧисла, для строк — КвалификаторыСтроки.
Шаг 2. Добавление элементов формы для отображения таблицы
Реквизит сам по себе невидим: чтобы пользователь увидел таблицу, нужно создать элемент формы типа «ТаблицаФормы» и привязать его к реквизиту через свойство ПутьКДанным. Затем внутрь таблицы добавляются поля колонок.
// Элемент-таблица
ЭлементТаблица = Элементы.Добавить("ТоварыДинамические", Тип("ТаблицаФормы"));
ЭлементТаблица.ПутьКДанным = "ТоварыДинамические";
// Колонки
ПолеНоменклатура = Элементы.Добавить("ТоварыДинамическиеНоменклатура",
Тип("ПолеФормы"), ЭлементТаблица);
ПолеНоменклатура.ПутьКДанным = "ТоварыДинамические.Номенклатура";
ПолеНоменклатура.Вид = ВидПоляФормы.ПолеВвода;
ПолеНоменклатура.Заголовок = "Номенклатура";
ПолеКоличество = Элементы.Добавить("ТоварыДинамическиеКоличество",
Тип("ПолеФормы"), ЭлементТаблица);
ПолеКоличество.ПутьКДанным = "ТоварыДинамические.Количество";
ПолеКоличество.Вид = ВидПоляФормы.ПолеВвода;
ПолеКоличество.Заголовок = "Количество";
Третий параметр метода Элементы.Добавить — родительский элемент. Для колонок им должна быть созданная таблица, иначе поля попадут в корень формы и таблица отобразится пустой. Вид поля выбирайте по типу данных: ПолеВвода для редактируемых значений, ПолеНадписи для данных только на просмотр, ПолеФлажка для булевых колонок.
Если таблица редактируемая, полезно сразу настроить командную панель: по умолчанию у программно созданной таблицы она может отсутствовать, и пользователь не сможет добавлять строки. Установите ЭлементТаблица.КоманднаяПанель или создайте кнопки с обработчиками добавления и удаления строк.
Шаг 3. Заполнение таблицы данными
После создания структуры реквизит ведёт себя как обычная таблица значений: строки добавляются методом Добавить(), значения присваиваются по именам колонок. Заполнение можно выполнять и на сервере, и на клиенте — реквизит формы доступен в обоих контекстах.
НоваяСтрока = ТоварыДинамические.Добавить();
НоваяСтрока.Номенклатура = НайденнаяСсылка;
НоваяСтрока.Количество = 5;
НоваяСтрока.Цена = 1200;
Если данные берутся из запроса, удобно использовать ЗначениеВРеквизитФормы: выгрузите результат запроса в таблицу значений и присвойте её реквизиту. Такой подход быстрее построчного перебора при больших объёмах.
РезультатЗапроса = Запрос.Выполнить().Выгрузить();
ЗначениеВРеквизитФормы(РезультатЗапроса, "ТоварыДинамические");
При использовании ЗначениеВРеквизитФормы состав колонок выгруженной таблицы должен совпадать с колонками реквизита по именам. Лишние колонки вызовут ошибку, поэтому в запросе явно перечисляйте только нужные поля.
- 1В ПриСозданииНаСервере создайте массив реквизитов: таблица + колонки с путями
- 2Вызовите ИзменитьРеквизиты() для применения структуры
- 3Добавьте элемент ТаблицаФормы с привязкой ПутьКДанным к реквизиту
- 4Добавьте поля колонок с родителем-таблицей и путями к колонкам
- 5Настройте командную панель и видимость элементов
- 6Заполните таблицу данными построчно или через ЗначениеВРеквизитФормы
- 7Проверьте отображение и работу редактирования в режиме предприятия
Динамическое изменение состава колонок
Если колонки нужно менять после открытия формы — например, пользователь выбрал другой набор показателей — потребуется удалить старые реквизиты и элементы, затем создать новые. Удаление выполняется тем же методом ИзменитьРеквизиты, но со вторым параметром — массивом имён удаляемых реквизитов.
УдаляемыеРеквизиты = Новый Массив;
УдаляемыеРеквизиты.Добавить("ТоварыДинамические");
ИзменитьРеквизиты(Новый Массив, УдаляемыеРеквизиты);
// Удаление элементов формы
Для Каждого ИмяЭлемента Из СписокСозданныхЭлементов Цикл
Элементы.Удалить(Элементы[ИмяЭлемента]);
КонецЦикла;
Удаление реквизита-таблицы автоматически удаляет его колонки, перечислять их отдельно не нужно. Элементы формы, наоборот, удаляются по одному, поэтому имена созданных элементов удобно хранить в реквизите формы типа «СписокЗначений» или в массиве, сохранённом в параметрах формы.
Учтите, что при удалении реквизита данные в нём теряются. Если строки нужно сохранить между перестроениями, скопируйте их во временную таблицу значений, пересоздайте структуру и загрузите данные обратно с сопоставлением совпадающих колонок.
Типичные ошибки и способы их избежать
Самая частая ошибка — создание элементов формы до вызова ИзменитьРеквизиты. Элемент ссылается на путь к данным, которого ещё не существует, и форма выдаёт ошибку «Поле не найдено». Всегда соблюдайте порядок: сначала реквизиты, потом элементы.
Вторая распространённая проблема — несовпадение имён. Путь к данным элемента должен точно совпадать с именем реквизита, включая регистр не обязательно, но без опечаток. Для колонок путь строится как ИмяТаблицы.ИмяКолонки — пропуск имени таблицы приводит к тому, что колонка отображается пустой.
Третья ошибка — попытка программно добавить табличную часть в объект, которого нет в метаданных. Код не может создать табличную часть документа «на лету»: метаданные изменяются только в конфигураторе. Если требование появилось в процессе доработки, добавьте табличную часть в объект и обновите конфигурацию базы данных.
Четвёртая — повторное добавление реквизита с тем же именем при повторном входе в обработчик. Перед созданием проверяйте существование реквизита или элемента, либо удаляйте старые перед созданием новых.
Проверка результата и ограничения подхода
После внедрения кода откройте форму в режиме предприятия и проверьте: таблица отображается, все колонки заполнены, добавление и удаление строк работает, при смене настроек структура перестраивается без ошибок. Отдельно протестируйте сценарий с пустыми данными — таблица должна отображаться с заголовками колонок, а не исчезать целиком.
Проверьте поведение при повторном открытии формы и при переходе между записями, если форма списочная. Программно созданные элементы не сохраняются между сеансами формы — при каждом открытии код создания выполняется заново, что является нормальным поведением.
Из ограничений стоит помнить: программные реквизиты нельзя использовать в настройках формы в конфигураторе, их не видно в редакторе. Динамические списки программно создать сложнее — для них обычно используют готовый реквизит с произвольным запросом. Также программно созданная таблица не участвует в стандартных механизмах объекта: проведении, проверке заполнения табличных частей, обменах.
Как проверить результат
Таблица видна, колонки с заголовками, данные на месте
Ошибка «Поле не найдено» или пустая область формы
Строки добавляются, удаляются, значения сохраняются в реквизите
Нет команд добавления или ввод не сохраняется
Старые колонки удалены, новые отображаются без дублей
Дубли колонок или ошибка при повторном создании
Форма открывается без ошибок, структура создаётся заново
Ошибка дублирования реквизита
Часто задаваемые вопросы
Можно ли программно добавить табличную часть в документ или справочник?
Нет. Табличные части объектов — это метаданные, они создаются только в конфигураторе с последующим обновлением конфигурации базы данных. Программно можно добавить только реквизит формы типа «ТаблицаЗначений», который живёт, пока открыта форма. Если данные должны храниться в базе, добавьте табличную часть в объект и управляйте её отображением кодом.
Как добавить колонку с флажком в программную таблицу?
Создайте колонку реквизита с типом Новый ОписаниеТипов("Булево"), а для элемента формы установите Вид = ВидПоляФормы.ПолеФлажка. Заголовок флажка можно задать через свойство Заголовок, а положение переключателя — через ПоложениеЗаголовка.
Почему таблица отображается, но колонки пустые?
Чаще всего неверно указан путь к данным колонки: он должен иметь вид «ИмяТаблицы.ИмяКолонки» и точно совпадать с именами реквизитов. Также проверьте, что элементы созданы после вызова ИзменитьРеквизиты, и что данные действительно записаны в реквизит, а не в локальную переменную.
Как сделать, чтобы пользователь мог добавлять строки в программную таблицу?
Убедитесь, что у таблицы есть командная панель со стандартными командами: по умолчанию у программно созданной таблицы она может быть скрыта. Альтернатива — создать кнопки «Добавить» и «Удалить» с обработчиками, где строки добавляются через ТоварыДинамические.Добавить() и удаляются по текущей строке элемента таблицы.
Можно ли пересоздавать колонки без перезапуска формы?
Да. Удалите старые реквизиты через ИзменитьРеквизиты(Новый Массив, МассивУдаляемых), удалите элементы через Элементы.Удалить(), затем создайте новую структуру. Данные при этом теряются — при необходимости сохраните их во временную таблицу значений и загрузите обратно после перестроения.
Работает ли этот подход в обычных (неуправляемых) формах?
В обычных формах механика другая: там используется коллекция ЭлементыФормы и реквизиты объекта напрямую, без метода ИзменитьРеквизиты. Принцип похож — добавить таблицу значений как источник данных и элемент «ТабличноеПоле» — но синтаксис отличается. Описанный в статье код предназначен для управляемых форм.
Что важно запомнить
Программная таблица на управляемой форме создаётся в три шага: реквизит ТаблицаЗначений с колонками через ИзменитьРеквизиты, элемент ТаблицаФормы с привязкой к реквизиту, поля колонок с путями к данным. Все изменения структуры выполняются только на сервере. Данные в таком реквизите не сохраняются в базе — для хранения используйте табличную часть объекта, созданную в конфигураторе.