При разработке на платформе 1С:Предприятие 8.3 программисты часто сталкиваются с необходимостью динамического изменения интерфейса. Одной из самых популярных задач является программное добавление колонок в табличные части (ТЧ) управляемой формы. На первый взгляд задача кажется простой, но при попытке добавить однотипные колонки в разные таблицы можно столкнуться с ошибкой «Недопустимое значение параметров». В этой статье мы подробно разберем, почему возникает эта ошибка, как правильно организовать программное создание элементов и какие нюансы платформы стоит учитывать для стабильной работы кода.
Проанализируем ситуацию, представленную в вопросе. Разработчик пытается добавить две колонки (Ставка НДС и Сумма НДС) в две разные таблицы на одной форме: ТаблицаДебиторскаяЗадолженностьВспомогательная и ТаблицаКредиторскаяЗадолженность. При выполнении кода для одной таблицы все работает корректно, но при включении кода для второй таблицы система выдает ошибку.
Выясним причину такого поведения. В управляемом приложении 1С все визуальные элементы формы (кнопки, поля, группы, таблицы и их колонки) хранятся в одной «плоской» коллекции — ЭтаФорма.Элементы. Несмотря на то, что визуально колонки принадлежат разным таблицам, их имена в рамках всей коллекции Элементы должны быть уникальными. Если вы уже создали элемент с именем СДС_СтавкаНДС в первой таблице, вы не можете создать элемент с таким же именем во второй.
Посмотрим, как выглядит правильное решение задачи. Для устранения ошибки необходимо добавить уникальные префиксы или постфиксы к именам создаваемых элементов. Рассмотрим пример исправленного кода:
// Добавление колонок для Дебиторской задолженности
ДнЭлемент = Элементы.Добавить("Дебет_СДС_СтавкаНДС", Тип("ПолеФормы"), Элементы.ТаблицаДебиторскаяЗадолженностьВспомогательная);
ДнЭлемент.Вид = ВидПоляФормы.ПолеВвода;
ДнЭлемент.ПутьКДанным = "Объект.ДебиторскаяЗадолженность.СДС_СтавкаНДС";
ДнЭлемент = Элементы.Добавить("Дебет_СДС_СуммаНДС", Тип("ПолеФормы"), Элементы.ТаблицаДебиторскаяЗадолженностьВспомогательная);
ДнЭлемент.Вид = ВидПоляФормы.ПолеВвода;
ДнЭлемент.ПутьКДанным = "Объект.ДебиторскаяЗадолженность.СДС_СуммаНДС";
// Добавление колонок для Кредиторской задолженности
КнЭлемент = Элементы.Добавить("Кредит_СДС_СтавкаНДС", Тип("ПолеФормы"), Элементы.ТаблицаКредиторскаяЗадолженность);
КнЭлемент.Вид = ВидПоляФормы.ПолеВвода;
КнЭлемент.ПутьКДанным = "Объект.КредиторскаяЗадолженность.СДС_СтавкаНДС";
КнЭлемент = Элементы.Добавить("Кредит_СДС_СуммаНДС", Тип("ПолеФормы"), Элементы.ТаблицаКредиторскаяЗадолженность);
КнЭлемент.Вид = ВидПоляФормы.ПолеВвода;
КнЭлемент.ПутьКДанным = "Объект.КредиторскаяЗадолженность.СДС_СуммаНДС";
Важно четко понимать разницу между данными (реквизитами) и их визуальным отображением (элементами). Рассмотрим два сценария работы:
Элементы.Добавить() и правильно указать ПутьКДанным.РеквизитФормы и метод ИзменитьРеквизиты(). Только после этого можно создавать визуальное поле.Проанализируем пример динамического создания реквизита и элемента вместе:
// 1. Создаем массив новых реквизитов
ДобавляемыеРеквизиты = Новый Массив;
ДобавляемыеРеквизиты.Добавить(Новый РеквизитФормы("ДинамическаяКолонка", Новый ОписаниеТипов("Число"), "Объект.Товары", "Новая колонка", Истина));
// 2. Добавляем реквизиты на форму
ЭтаФорма.ИзменитьРеквизиты(ДобавляемыеРеквизиты);
// 3. Создаем визуальный элемент (колонку в таблице)
НоваяКолонка = Элементы.Добавить("ТоварыДинамическаяКолонка", Тип("ПолеФормы"), Элементы.Товары);
НоваяКолонка.Вид = ВидПоляФормы.ПолеВвода;
НоваяКолонка.ПутьКДанным = "Объект.Товары.ДинамическаяКолонка";
По умолчанию метод Добавить() помещает новую колонку в самый конец таблицы. Однако часто требуется вставить поле в конкретное место, например, перед стандартным полем «Сумма». Разберем, как это сделать, используя четвертый параметр метода Добавить.
Синтаксис метода: Добавить(Имя, Тип, Родитель, ПоместитьПеред). В качестве последнего аргумента мы передаем существующий элемент таблицы, перед которым хотим видеть нашу новую колонку.
Также рассмотрим ситуацию, когда колонки нужно логически объединить. В управляемых формах для этого используются группы колонок. Разберем порядок действий:
ГруппаФормы и видом ГруппаКолонок.
// Создаем группу для налогов
ГруппаНалоги = Элементы.Добавить("ГруппаНалоги", Тип("ГруппаФормы"), Элементы.ДебиторскаяЗадолженность);
ГруппаНалоги.Вид = ВидГруппыФормы.ГруппаКолонок;
ГруппаНалоги.Заголовок = "Налоговые показатели";
// Добавляем ставку НДС в эту группу
КолонкаСтавка = Элементы.Добавить("Дебет_Ставка", Тип("ПолеФормы"), ГруппаНалоги);
КолонкаСтавка.Вид = ВидПоляФормы.ПолеВвода;
КолонкаСтавка.ПутьКДанным = "Объект.ДебиторскаяЗадолженность.СтавкаНДС";
Просто отобразить данные недостаточно — часто нужно реагировать на их изменение. Поскольку элементы создаются программно, мы не можем просто дважды кликнуть по полю в дизайнере. Нам необходимо использовать метод УстановитьДействие.
Рассмотрим по шагам, как подключить обработчик события ПриИзменении:
&НаКлиенте.
// В процедуре ПриСозданииНаСервере
НовыйЭлемент.УстановитьДействие("ПриИзменении", "Подключаемый_ПриИзмененииКолонки");
// В модуле формы на клиенте
&НаКлиенте
Процедура Подключаемый_ПриИзмененииКолонки(Элемент)
// Ваша логика пересчета
Сообщить("Значение в колонке изменено!");
КонецПроцедуры
Одной из самых частых причин отсутствия данных в программно созданной колонке является ошибка в строке ПутьКДанным. Проанализируем правила формирования этой строки:
Важно: Любая опечатка или лишний пробел в этой строке приведут к тому, что колонка отобразится «пустой» и не будет доступна для редактирования, так как платформа не сможет связать визуальное поле с буфером данных.
Выясним, как массовое добавление колонок влияет на производительность. Каждый вызов метода ИзменитьРеквизиты() заставляет платформу полностью перестраивать структуру формы в памяти. Если вам нужно добавить 10 колонок, крайне не рекомендуется вызывать этот метод 10 раз.
Правильный подход заключается в следующем: сформируйте один массив всех добавляемых реквизитов и вызовите метод ИзменитьРеквизиты() один раз в конце. Что касается визуальных элементов (метод Элементы.Добавить()), их можно добавлять последовательно, это не так критично для производительности, но группировка кода по логическим блокам сделает ваш код чище и понятнее для коллег.
Также не забывайте про функциональные опции. Если ваше решение предназначено для тиражной конфигурации (например, БП 3.0), проверьте, включен ли соответствующий учет (например, учет НДС) перед тем, как программно выводить колонки на экран. Если опция выключена, лучше установить свойство Видимость = Ложь для созданных элементов.