Программное создание реквизита управляемой формы с помощью механизма расширений

Публикация № 1018735

Программирование - Практика программирования

55
В ЗУП 3 возникла задача добавить реквизит в справочник не внося изменений в конфигурацию. БСП с механизмом дополнительных реквизитов использовать было нежелательно, поэтому был использован механизм расширений. Для вывода данного реквизита на форму добавлять саму форму в расширение не хотелось по ряду причин, описанных ниже. Создание реквизита и элемента формы, соответствующего данному реквизиту было решено сделать программно в самом расширении, следуя принципу минимального воздействия на конфигурацию.

Начиная с платформы 1С версии 8.3.12 и выше появилась возможность добавлять реквизиты объектов в расширениях, чем я и воспользовался:

Но для вывода данного реквизита на форму элемента добавлять саму форму в расширение совсем не хотелось.

Во-первых добавление (заимствование) формы в расширение может привести к некоторым нежелательным эффектам, которые могут возникнуть после обновления конфигурации. Приведем немного теории.

Платформа использует сразу три формы:

  • Форму из основной конфигурации
  • Сохраненную форму
  • Форму из расширения

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

Во-вторых добавление формы в расширение привело бы к автоматическому добавлению всех реквизитов этого объекта и объектов метаданных (соответствующих ссылочным типам реквизитов объекта) в данное расширение, что загромождало бы само расширение и также не желательно.

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

В конфигурациях ERP 2 и УТ 11 для целей программного создания реквизитов и элементов формы можно использовать типовой механизм упрощенного изменения, который хорошо описан в статье: //infostart.sterx.info/public/303645/. Но у меня конфигурация ЗУП 3 и данного механизма там нет. 

Посмотрев начало процедуры ПриСозданииНаСервере() модуля формы объекта, видим что вызываются экспортные методы ПриСозданииНаСервере() общих модулей подсистем БСП:

&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
	
	Если Параметры.Свойство("АвтоТест") Тогда // Возврат при получении формы для анализа.
		Возврат;
	КонецЕсли;
	
	// СтандартныеПодсистемы.ВерсионированиеОбъектов
	ВерсионированиеОбъектов.ПриСозданииНаСервере(ЭтотОбъект);
	// Конец СтандартныеПодсистемы.ВерсионированиеОбъектов
	
	// СтандартныеПодсистемы.ПодключаемыеКоманды
	ПодключаемыеКоманды.ПриСозданииНаСервере(ЭтотОбъект);
	// Конец СтандартныеПодсистемы.ПодключаемыеКоманды
	
	// СтандартныеПодсистемы.Свойства
	ДополнительныеПараметры = Новый Структура;
	ДополнительныеПараметры.Вставить("Объект", Объект);
	ДополнительныеПараметры.Вставить("ИмяЭлементаДляРазмещения", "ГруппаДополнительныеРеквизиты");
	УправлениеСвойствами.ПриСозданииНаСервере(ЭтотОбъект, ДополнительныеПараметры);
	// Конец СтандартныеПодсистемы.Свойства
	
	// СтандартныеПодсистемы.СклонениеПредставленийОбъектов
	СклонениеПредставленийОбъектов.ПриСозданииНаСервере(ЭтотОбъект, Объект.Наименование);	
	// Конец СтандартныеПодсистемы.СклонениеПредставленийОбъектов

Было принято решение код для программного добавления реквизита формы объекта добавить в метод ПриСозданииНаСервере() общего модуля УправлениеСвойствами. Данный модуль предназначен для работы с дополнительными реквизитами и сведениями, но переопределив его в расширении он вполне сгодится и для наших целей.

Добавляем общий модуль УправлениеСвойствами в наше расширение:

и создаем обработчик события НП_ПриСозданииНаСервере(), вызываемый после типовой процедуры УправлениеСвойствами.ПриСозданииНаСервере().

Ниже приведен готовый код, код снабжен комментариями и разбит на области для лучшего понимания:

&После("ПриСозданииНаСервере")
Процедура НП_ПриСозданииНаСервере(Форма, ДополнительныеПараметры = Неопределено) Экспорт
	
	Если Форма.ИмяФормы = "Справочник.ПодразделенияОрганизаций.Форма.ФормаЭлемента" Тогда
		
		#Область ДобавлениеРеквизитовФормы
		// Массив для новых реквизитов
		ДобавляемыеРеквизиты	= Новый Массив;
		
		// Опишем ревизиты формы
		Реквизит_НаименованиеДляПечати = Новый РеквизитФормы("НаименованиеДляПечати",	Новый ОписаниеТипов("Строка", , , Новый КвалификаторыСтроки(300)),	, "Наименование для печати");
		
		// Заполним массив после описания реквизитов формы
		ДобавляемыеРеквизиты.Добавить(Реквизит_НаименованиеДляПечати);
		
		// Добавим новые реквизиты в форму
		Форма.ИзменитьРеквизиты(ДобавляемыеРеквизиты);
		#КонецОбласти
		
		#Область ДобавлениеЭлементовФормы
		// Элементы
		ИмяГруппы = "ГруппаНаименованиеКод";
		ГруппаФормы = Форма.Элементы.Найти(ИмяГруппы);
		Если ГруппаФормы <> Неопределено Тогда
			
			ИмяЭлемента = "НаименованиеДляПечати";
			Если Форма.Элементы.Найти(ИмяЭлемента) = Неопределено Тогда
				ЭлементФормы = Форма.Элементы.Добавить(ИмяЭлемента, Тип("ПолеФормы"), ГруппаФормы);        
				ЭлементФормы.Вид = ВидПоляФормы.ПолеВвода;
				ЭлементФормы.ПутьКДанным = "НаименованиеДляПечати";
				ЭлементФормы.МногострочныйРежим = Истина;
				ЭлементФормы.Высота = 3;
			КонецЕсли;   
			
		КонецЕсли;
		#КонецОбласти
		
		#Область ЗаполнениеДанных
		Форма.НаименованиеДляПечати = Форма.Объект.НаименованиеДляПечати;
		#КонецОбласти
		
	КонецЕсли;
	
КонецПроцедуры

Запускаем конфигурацию и убеждаемся, что все работает:

55

Скачать файлы

Наименование Файл Версия Размер
Расширение конфигурации для приведенного примера
.cfe 7,00Kb
13.03.19
2
.cfe 7,00Kb 2 Скачать

См. также

Специальные предложения

Комментарии
Избранное Подписка Сортировка: Древо
1. alexpvs 53 12.03.19 11:20 Сейчас в теме
(4) "Во-первых добавление формы в расширение привело бы к её "заморозке", то есть если форма будет меняться разработчиками в последующих релизах, то эти изменения не будут больше отображаться, пользователи будут видеть как бы "снимок" формы, который был при её добавлении в расширение" - это не так.
2. ni_cola 131 12.03.19 12:33 Сейчас в теме
(1) При заимствовании формы в расширение платформа использует сразу 3 формы: Форму из основной конфигурации, Сохраненную форму (я назвал её "замороженной") и Форму из расширения. Они взаимодействуют между собой и в результате мы получаем Результирующую форму. В результате такого взаимодействия может быть, например, такая ситуация: мы доработали форму в расширении, потом в новом релизе добавили реквизиты, но они на форме не отображаются.
Более подробно тут: https://xn----1-bedvffifm4g.xn--p1ai/news/2017-11-24-forms-customization-by-using-extensions/
7. alexpvs 53 13.03.19 07:45 Сейчас в теме
(2) Смотря как поменяли форму в расширении.
Вот простейший пример: у поставщика документ с 2 реквизитами, в первом релизе выглядит так (см шаг1).
Заимствуем эту форму в расширение, добавляем свой реквизит на форму, выводим в конец формы его. (см. шаг2).
После этого поставщик делает 2 релиз, в котором у одного реквизита меняет синоним, у второго реквизита меняет имя и синоним. И на форме свои два реквизита помещает в горизонтальную группу. После этих изменений, расширение продолжает работать, и изменения поставщика присутствуют в результирующей форме (см. шаг3)
Прикрепленные файлы:
11. ids79 1469 13.03.19 09:37 Сейчас в теме
(2)По приведенной Вами ссылке совсем другая ситуация описана.
Если перенести доработанную форму в расширение, а потом удалить доработки в основной,
эти доработки не будут на результирующей форме.
Там объясняется почему так происходит.
Но в описанной Вами ситуации, новые реквизиты будут отображыены, если конечно их наименования не совпадут с наименованиям новых реквизитов в расширенной форме.
А лишние метаданные, добавленные в расширение вместе с формой можно без проблем удалить.
3. DoctorRoza 12.03.19 13:18 Сейчас в теме
(1) тут изначальный посыл смущает. Добавление каких - либо реквизитов потребует доработку, например, отчетов. печатныйх форм. Значит, придется дописывать алгоритм. В свою очередь, появятся еще внешние и т.п. подключамые объекты. Что выливается еще в лишнюю 100-ню строк кода! А сделать через доп. реквизит, чтобы вообще кода не было - отказались, по своим причинам.
4. Ioryk30 12.03.19 16:37 Сейчас в теме
(1) А как ? Пока вижу на практике именно " заморозку". Имена объектов (Документов и справочников) при обновлении в расширение не попадают.
5. unichkin 1131 12.03.19 18:47 Сейчас в теме
Я стараюсь не использовать изменение метаданных в расширении. Был прецедент когда клиент удалил расширение, и у него исчезли добавленные во время работы с ним договоры (в договоры был добавлен реквизит, расширением). После включения договоры восстановились - повезло, что не было реструктуризации.
Можно добавить свойство, и вывести его поле на форму, программно. В запросах не так удобно им пользоваться, но все же риска меньше.
EVKash; Sanya1984; +2 Ответить
6. insurgut 195 13.03.19 06:31 Сейчас в теме
Разница данного метода от дополнительных реквизитов по сути в том, что мы нужный реквизит поместим куда захотим? Но в дальнейшем разработчикам типовой конфигурации ничего не мешает изменить/переименовать групп реквизитов и решение станет не рабочим, в отличие от дополнительных реквизитов.
rpgshnik; +1 Ответить
8. papami 22 13.03.19 08:47 Сейчас в теме
Вот так программно из разных мест надобавляют реквизитов разработчики и, когда приспичит, сидишь и ищешь код по всей конфе, вспоминая разработчиков добрым словом. В Медицину кто заглядывал?
rpgshnik; +1 Ответить
9. myxins1989 47 13.03.19 09:08 Сейчас в теме
(8) А вы попробуйте обновить формы, когда на них через конструктор добавляют элементы. И попробуйте ничего не пропустить, а не как обычно - "ой, не работает, сейчас подключимся и посмотрим" - и так в течение недели после обновления.
10. user633533_encantado 4 13.03.19 09:31 Сейчас в теме
Не понимаю, почему разработчики ЗУП не хотят добавить модули модификации конфигурации и их вызовы во все формы, как это сделано в УТ и прочих.
12. koln 13.03.19 11:38 Сейчас в теме
Попробовал, но получил ошибку в месте
Форма.НаименованиеДляПечати = Форма.Объект.НаименованиеДляПечати;
Ругается на то, что не найден реквизит. На мой взгляд, это и логично, ведь добавляется реквизит формы, а не Объекта.
При чем пробовал даже не через расширение, а в модуле формы, в обработчике "ПриСозданииНаСервере". Может я что-то не так понял, но даже в отладчике, после добавления реквизита, он не появляется.
13. ni_cola 131 13.03.19 12:21 Сейчас в теме
(12) Проверьте порядок действий:
1. Заимствовать объект в расширение, например Справочник.ПодразделенияОрганизаций.
2. Добавить реквизит НаименованиеДляПечати в заимствованный объект в расширении.
3. Заимствовать в расширение общий модуль УправлениеСвойствами.
4. Добавить в него метод, выполняющийся после УправлениеСвойствами.ПриСозданииНаСервере() для программного создания реквизита.
14. koln 13.03.19 14:06 Сейчас в теме
(13) 1. У меня даже в модуле самой формы в основной конфигурации такую ошибку выдает, не то, что через расширение;
2. Откуда у Вас берутся данные для заполнения вновь созданного программного реквизита, которые выводятся на форму?
15. ni_cola 131 13.03.19 15:05 Сейчас в теме
(14) Приложил к статье расширение с рассматриваемым примером для скачивания
16. Eremkin 14.03.19 09:21 Сейчас в теме
В Бухгалтерии немного дорабатывал форму Инвентаризация товаров на складе. Добавил команду на форму + дополнительная форма выбора счета. Выполнил заимствование формы документа. При этом автоматически подтянулись реквизиты объекта, табличная часть. Поместил свою команду в нужное подменю на форме и удалил реквизиты с табличной частью. И все отлично отлично работает. Ранее еще добавлял новый реквизит на форму (позже удалил с формы за ненадобностью, т.к. реализовал отдельную форму выбора счета с отборами). На то и оно и расширение, чтобы не городить писанину с программным созданием различных элементов формы.
Прикрепленные файлы:
17. Terve!R 18.03.19 08:01 Сейчас в теме
Мотивация автора изобретать велосипед вызывает недоумение.
Да, в расширении что-то добавлять чуть сложнее, чем просто в конфигурации править, но удобства перекрывают некоторые минусы. А автор из-за нюансов работы с расширениями вовсе отказывается от расширений, еще и других такому учит.

Если Вы не знали, то у окошка расширения есть кнопочка, которая показывает только вручную добавленные объекты в расширение, скрывая автоматически заимствованные.
А в последних версиях платформы появился инструмент обновления заимствованной формы из формы поставщика.

Если уж ссылаетесь на теорию, то следите за изменениями механизма. Разработчики понимают о некоторых неудобствах, и стараются упростить жизнь с расширениями, но кто-то уже обозвал расширения злом и избегает их, это же глупо.
19. ni_cola 131 18.03.19 10:01 Сейчас в теме
(17)
А в последних версиях платформы появился инструмент обновления заимствованной формы из формы поставщика.


Не знал об этом, можно поподробнее? Даже если это уже реализовано, то мне не нравится, что при заимствовании формы в расширение автоматически заимствуются объекты метаданных всех ссылочных типов, выводящихся на форму, что загромождает расширение "не нужными" объектами и в свою очередь усложняет сопровождение данного расширения.
18. Andrefan 18.03.19 09:38 Сейчас в теме
Не знал что за такую очевидность можно столько плюсов собрать)
Оставьте свое сообщение