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