Тема возникла из обсуждения в комментариях к публикации, где рассматривался вопрос создания пустой формы объекта в расширении для добавления элементов формы программно или для изменения процедур формы объекта.
Я заявил, что форму добавлять совсем не нужно, и можно обойтись заимствованием только лишь пары общих модулей, с чем не все комментаторы согласились.
В данной публикации я опишу способ, позволяющий это сделать. Оговорюсь, что способ не универсален и не подойдет для решения любой задачи. Но в исходной публикации задачу решает на 100%. Также конфигурация должна быть основана на БСП, а форма, на которую мы хотим повлиять без ее заимствования, должна быть подключена к подсистеме "Подключаемые команды".
Итак, поехали.
1. Открываем форму документа и ищем
- В процедуре
ПриСозданииНаСервере
обращение к методу общего модуляПодключаемыеКоманды.ПриСозданииНаСервере()
- В процедуре
Подключаемый_ВыполнитьКоманду
к методу общего модуляПодключаемыеКомандыКлиент.ВыполнитьКоманду()
.
Если эти два условия соблюдены, то мы можем не заимствовать форму, а обойтись только общими модулями.
2. Заимствуем процедуру ПодключаемыеКоманды.ПриСозданииНаСервере()
с аннотацией &После и процедуру ПодключаемыеКомандыКлиент.ВыполнитьКоманду()
с аннотацией &Вместо.
В серверном модуле программно добавляем команды и кнопки (подробно описывать не буду, на сайте полно прекрасных примеров, вот один из лучших, на мой взгляд)
&После("ПриСозданииНаСервере")
Процедура прПриСозданииНаСервере(Форма, ПараметрыРазмещения)
Если Форма.ИмяФормы = "Документ.НачислениеЗарплаты.Форма.ФормаДокумента" Тогда
прНачислениеЗарплатыПриСозданииНаСервере(Форма);
КонецЕсли;
КонецПроцедуры
Функция прНачислениеЗарплатыПриСозданииНаСервере(Форма)
ИмяКоманды = "прПересчитатьВзносыСотрудника";
Команда = Форма.Команды.Добавить(ИмяКоманды);
Команда.Действие = "Подключаемый_ВыполнитьКоманду";
Команда.Заголовок = "Пересчитать взносы сотрудника";
Команда.ИзменяетСохраняемыеДанные = Истина;
Команда.ИспользованиеТекущейСтроки = ИспользованиеТекущейСтроки.Использует;
Команда.ИспользуемаяТаблица = Форма.Элементы.Взносы;
Элемент = Форма.Элементы.Добавить(ИмяКоманды, Тип("КнопкаФормы"), Форма.Элементы.Взносы.КоманднаяПанель);
Элемент.ИмяКоманды = ИмяКоманды;
КонецФункции
а в клиентском анализируем вызов команды, и если команда совпадает с нашей добавленной - обрабатываем ее, если нет - продолжаем типовой вызов.
&Вместо("ВыполнитьКоманду")
Процедура прВыполнитьКоманду(Форма, Команда, Источник)
ИмяКоманды = "прПересчитатьВзносыСотрудника";
Если Команда.Имя = ИмяКоманды Тогда
прПерезаполнитьДанныеФормыНаКлиенте(Форма);
Иначе
ПродолжитьВызов(Форма, Команда, Источник);
КонецЕсли;
КонецПроцедуры
Функция прПерезаполнитьДанныеФормыНаКлиенте(Форма)
ТекущиеДанные = Форма.Элементы.Взносы.ТекущиеДанные;
Если ТекущиеДанные = Неопределено Тогда
Возврат Ложь;
КонецЕсли;
ОчиститьСообщения();
Форма.РежимПересчетаВзносов = Истина;
Форма.ПерезаполнитьДанныеФормыНаКлиенте(ТекущиеДанные.ФизическоеЛицо);
Возврат Истина;
КонецФункции
Вот и всё - в выбранную форму добавлены нужные кнопки без заимствования самой формы документа.
В конкретном примере удачно совпало, что разработчики сделали метод формы ПерезаполнитьДанныеФормыНаКлиенте
экспортным, но даже если бы и не делали, то переносом части кода в общие модули мы бы решили эту задачу.
В чем преимущество данного подхода? На мой взгляд, не заимствуя форму, мы страхуем себя от будущих проблем, когда разработчики кардинально изменяют форму и расширение перестает работать. И просто от лишней работы в будущем, когда периодически надо обновлять форму в расширении, чтобы поддерживать актуальность типовой формы. Так же при заимствовании формы мы автоматически тащим в расширение дополнительные данные в виде реквизитов, общих картинок или элементов стиля, которые перегружают расширение (визуально и размером), но не нужны для логики его работы. Указанные общие модули уже устоялись и довольно редко подвергаются изменениям.
Если же форма не включена в подсистему "Подключаемые команды", можно рассмотреть варианты перехвата других общих модулей, в зависимости от дорабатываемой конфигурации:
УправлениеСвойствами.ПриСозданииНаСервере + УправлениеСвойствамиКлиент.ВыполнитьКоманду
СобытияФорм.ПриСозданииНаСервере + СобытияФормКлиент.ВыполнитьПереопределяемуюКоманду
РаботаСФайлами.ПриСозданииНаСервере + РаботаСФайламиКлиент.КомандаУправленияПрисоединеннымиФайлами
МодификацияКонфигурацииПереопределяемый.ПриСозданииНаСервере
ВерсионированиеОбъектов.ПриСозданииНаСервере
но они, как мне кажется, не так шикарно подходят для подобных целей.
Пример рассмотрен на конфигурации Зарплата и кадры государственного учреждения, редакция 3.1.24.310 с версией БСП 3.1.7.275, платформа 8.3.23.1437, но это совсем не принципиально. Приложенное расширение также совместимо с параллельными релизами ЗУП, КА и ERP.
Полезные ресурсы:
- Подключаемые команды на сайте ИТС
- БСП. Подключаемые команды. Команды заполнения
- Динамическое формирование интерфейса от Дмитрия Котова (rpgshnik)
Dixi.
Всем удачного кодинга!