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