Как добавить внешнюю обработку заполнения табличной части в произвольное подменю формы в 1С?

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

При разработке дополнительных обработок заполнения объектов в среде 1С:Предприятие программисты часто сталкиваются с жесткими ограничениями Библиотеки стандартных подсистем (БСП). Стандартный механизм регистрации внешних обработок через функцию СведенияОВнешнейОбработке с видом ЗаполнениеОбъекта автоматически помещает созданные команды в жестко предопределенные места на форме. Обычно это общее меню «Заполнить» в командной панели самого документа.

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

Почему стандартная БСП не решает эту задачу?

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

Типичная функция регистрации в модуле внешней обработки выглядит следующим образом:


Функция СведенияОВнешнейОбработке() Экспорт
    ПараметрыРегистрации = ДополнительныеОтчетыИОбработки.СведенияОВнешнейОбработке();
    ПараметрыРегистрации.Вид = ДополнительныеОтчетыИОбработкиКлиентСервер.ВидОбработкиЗаполнениеОбъекта;
    ПараметрыРегистрации.Наименование = "Отбор с каталогами";
    ПараметрыРегистрации.Версия = "1.0";
    ПараметрыРегистрации.Назначение.Добавить("Документ.УстановкаЦенНоменклатуры");
    
    Команда = ПараметрыРегистрации.Команды.Добавить();
    Команда.Идентификатор = "ОбработатьТЧУЦН";
    Команда.Представление = "Отбор с каталогами УЦН";
    Команда.Использование = ДополнительныеОтчетыИОбработкиКлиентСервер.ТипКомандыОткрытиеФормы;
    
    Возврат ПараметрыРегистрации;
КонецФункции

Эта команда неизбежно окажется в верхней панели документа, в меню «Заполнение». Чтобы «перенаправить» кнопку в нужное нам подменю конкретной табличной части (например, ДеревоЦенКоманднаяПанельПодменюПодобрать), нам потребуется расширение конфигурации.

Решение задачи с помощью расширения конфигурации

Использование расширения — это наиболее чистый и безопасный способ кастомизации интерфейса в современных версиях платформы 1С:Предприятие 8.3 (начиная с версии 8.3.12). Мы разберем весь процесс по шагам: от заимствования формы до интеграции программного вызова нашей внешней обработки.

Шаг 1. Заимствование формы документа и элементов интерфейса

Выполним подготовительные действия в конфигураторе:

  1. Создадим новое расширение конфигурации (или откроем существующее).
  2. Найдем в дереве объектов конфигурации нужный документ (например, УстановкаЦенНоменклатуры) и добавим его в расширение.
  3. Перейдем к формам документа, найдем целевую форму и также добавим её в расширение.
  4. Откроем форму документа в расширении, перейдем на вкладку «Элементы» и найдем то самое подменю табличной части, куда необходимо поместить кнопку. Добавим это подменю в расширение (обычно это группа с видом Подменю, например, ДеревоЦенКоманднаяПанельПодменюПодобрать).

Шаг 2. Программное создание команды и кнопки

Перейдем в модуль заимствованной формы в расширении. Нам необходимо перехватить событие создания формы на сервере, чтобы программно внедрить нашу команду и кнопку в заимствованное подменю. Напишем обработчик с аннотацией &После для процедуры ПриСозданииНаСервере:


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

Важное примечание: Обратите внимание, что мы добавляем кнопку внутрь существующего элемента-родителя (подменю). В платформе 1С существует ограничение: если у командной панели включено свойство «Автозаполнение», то программно добавлять кнопки непосредственно в корень этой панели нельзя. Однако добавление кнопок в подчиненные группы (подменю) полностью решает эту проблему и обходит ограничение платформы.

Шаг 3. Реализация клиентского метода и вызов внешней обработки

Теперь нам нужно описать действие команды на клиенте. Чтобы решение оставалось гибким и нам не приходилось «хардкодить» тяжелую бизнес-логику внутри расширения, мы свяжем эту кнопку с нашей зарегистрированной внешней обработкой. Нам нужно программно получить и подключить внешнюю обработку, а затем передать ей контекст нашей формы.

Добавим в модуль формы расширения следующие процедуры:


&НаКлиенте
Процедура Префикс_ВыполнитьКомандуОтбора(Команда)
    
    // Вызываем серверный метод для подключения внешней обработки и выполнения логики
    Префикс_ВыполнитьЛогикуЗаполненияНаСервере();
    
КонецПроцедуры

&НаСервере
Процедура Префикс_ВыполнитьЛогикуЗаполненияНаСервере()
    
    // 1. Находим нашу внешнюю обработку в справочнике БСП
    СсылкаНаОбработку = Справочники.ДополнительныеОтчетыИОбработки.НайтиПоНаименованию("Отбор с каталогами");
    
    Если СсылкаНаОбработку.Пустая() Тогда
        ВызватьИсключение "Внешняя обработка 'Отбор с каталогами' не зарегистрирована в системе!";
    КонецЕсли;
    
    // 2. Подключаем обработку через стандартный механизм БСП
    ИмяОбработки = ДополнительныеОтчетыИОбработки.ПодключитьВнешнююОбработку(СсылкаНаОбработку);
    
    // 3. Создаем экземпляр обработки
    ОбъектОбработки = ВнешниеОбработки.Создать(ИмяОбработки, Истина);
    
    // 4. Вызываем экспортный метод обработки, передавая форму в качестве контекста.
    // Это позволит коду обработки напрямую манипулировать данными формы на клиенте/сервере.
    ОбъектОбработки.ВыполнитьЗаполнениеТабличнойЧасти(ЭтотОбъект);
    
КонецПроцедуры

Реализация метода в модуле внешней обработки

В самой внешней обработке (в её модуле объекта) мы должны создать экспортный метод, который примет контекст нашей формы документа и произведет все необходимые манипуляции с реквизитами формы. Поскольку мы передали всю форму целиком (ЭтотОбъект), обработка получает доступ как к реквизиту Объект (со всеми табличными частями), так и к элементам интерфейса.

Пример кода в модуле объекта внешней обработки:


Процедура ВыполнитьЗаполнениеТабличнойЧасти(ФормаДокумента) Экспорт
    
    // Извлекаем объект документа из контекста переданной формы
    ДокументОбъект = ФормаДокумента.Объект;
    
    // Пример получения Уникального Идентификатора документа, если это необходимо
    СсылкаНаДокумент = ДокументОбъект.Ссылка;
    ГУИДДокумента = СсылкаНаДокумент.УникальныйИдентификатор();
    
    // Выполняем логику заполнения дерева цен или табличной части
    Для Каждого СтрокаДерева Из ДокументОбъект.ДеревоЦен Цикл
        // Производим необходимые расчеты и заполнение реквизитов
        СтрокаДерева.Цена = СтрокаДерева.Цена * 1.1; // Пример: увеличение цен на 10%
    КонецЦикла;
    
    // Сообщаем форме, что данные были изменены, чтобы активировать кнопку "Записать"
    ФормаДокумента.Модифицированность = Истина;
    
КонецПроцедуры

Подведем итоги

Мы детально разобрали, как обойти стандартные ограничения БСП по размещению подключаемых команд. Использование расширения конфигурации позволяет нам точечно внедрить кнопку в любое, даже самое глубоко вложенное подменю формы (включая командные панели табличных частей), сохранив при этом всю основную логику внутри внешней подключаемой обработки (файла .epf). Такой подход существенно облегчает последующее обновление типовой конфигурации и делает архитектуру решения гибкой и поддерживаемой.

← На главную