В типовых конфигурациях на платформе 8.1, таких как «Управление торговлей 10.3», механизм подбора номенклатуры является одним из самых сложных и в то же время гибких узлов. Часто возникают задачи, когда стандартного функционала недостаточно: например, нужно ограничить список товаров только теми, что присутствуют в специфическом регистре сведений или остатками на конкретном складе, а также вывести в форму подбора дополнительные данные (колонки).
В этой статье мы разберем, как кастомизировать обработку ПодборНоменклатуры, научимся включать отладку на сервере для поиска нужных процедур и программно управлять отборами в иерархических списках.
Прежде чем приступать к коду, необходимо убедиться, что мы можем отследить выполнение процедур, которые срабатывают на стороне сервера. В версии 8.1 отладка на сервере по умолчанию часто выключена. Без этого вы не сможете «провалиться» в процедуры заполнения табличных частей, если они вызываются в серверном контексте.
Проанализируем последовательность действий для включения отладки:
regedit.HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\1C:Enterprise 8.1 Server Agent.ImagePath. Нам нужно добавить флаг -debug в строку запуска.Например, если исходная строка выглядит так:
"C:\Program Files\1cv81\bin\ragent.exe" -srvc -agent -regport 1541 -port 1540 -range 1560:1591 -d "C:\Program Files\1cv81\server"
То после редактирования она должна принять вид:
"C:\Program Files\1cv81\bin\ragent.exe" -srvc -agent -regport 1541 -port 1540 -range 1560:1591 -debug -d "C:\Program Files\1cv81\server"
После этого запустим службу заново. Теперь отладчик будет останавливаться на точках останова в модулях объектов и серверных общих модулях.
Чтобы форма подбора «понимала», что ее открыли из вашего специфического документа с определенным складом, данные нужно передать в момент открытия. В УТ 10.3 подбор обычно вызывается через общую процедуру в модуле РаботаСНоменклатурой.
Рассмотрим пример формирования структуры параметров в модуле вашего документа:
СтруктураПараметров = Новый Структура;
СтруктураПараметров.Вставить("Склад", ЭтотОбъект.Склад);
СтруктураПараметров.Вставить("СвойРежимПодбора", Истина);
СтруктураПараметров.Вставить("Заголовок", "Подбор номенклатуры по спец. регистру");
РаботаСНоменклатурой.ОткрытьФормуПодбораНоменклатуры(ЭтаФорма, Истина, СтруктураПараметров);
Эти параметры попадут в форму подбора, где их можно будет обработать в процедуре ПриОткрытии или ИнициализироватьФорму.
Если нам нужно оставить в подборе только ту номенклатуру, которая есть в нашем специфическом регистре, самым надежным способом будет наложение отбора ВСписке на основной список номенклатуры. Выясним, как это реализовать.
Для начала получим массив нужных ссылок. Это лучше сделать одним запросом:
Запрос = Новый Запрос;
Запрос.Текст =
"ВЫБРАТЬ РАЗЛИЧНЫЕ
| МойРегистр.Номенклатура
|ИЗ
| РегистрСведений.МойРегистр КАК МойРегистр
|ГДЕ
| МойРегистр.Склад = &Склад";
Запрос.УстановитьПараметр("Склад", ПараметрСклад);
СписокРазрешеннойНоменклатуры = Запрос.Выполнить().Выгрузить().ВыгрузитьКолонку("Номенклатура");
Теперь применим этот список к элементу формы СправочникСписок (который обычно отображает товары справа в форме подбора):
ОтборСсылка = ЭлементыФормы.СправочникСписок.Значение.Отбор.Ссылка;
ОтборСсылка.ВидСравнения = ВидСравнения.ВСписке;
ОтборСсылка.Значение.ЗагрузитьЗначения(СписокРазрешеннойНоменклатуры);
ОтборСсылка.Использовать = Истина;
Важный момент: типовой механизм подбора часто перестраивает отборы при переключении режимов (по справочнику, по остаткам и т.д.). Рассмотрим процедуру ПерезаполнитьТаблицуНоменклатуры — именно здесь в типовых решениях часто происходит сброс или установка новых фильтров. Вам может потребоваться вклиниться в эту логику, чтобы ваш отбор не «слетал».
Пользователи часто жалуются, что после установки фильтра в правой части (список товаров) в левой части (дерево групп) остаются все группы справочника, даже пустые. В 1С 8.1 динамически управлять видимостью веток дерева сложнее, чем в управляемых формах.
Проанализируем варианты решения:
СправочникСписок иерархический просмотр.ДеревоЗначений, его придется перебирать и удалять узлы, для которых в подчиненных элементах нет товаров из нашего «разрешенного» списка.Если вам нужно вывести, например, «Остаток по спец. регистру» прямо в список подбора, разберем два пути:
Путь А: Динамическое заполнение через событие
Используем событие ПриВыводеСтроки табличного поля СправочникСписок. Это позволяет не менять сложные запросы обработки подбора.
Процедура СправочникСписокПриВыводеСтроки(Элемент, ОформлениеСтроки, ДанныеСтроки)
Если ДанныеСтроки.ЭтоГруппа Тогда
Возврат;
КонецЕсли;
// Получаем данные из регистра (в реальности лучше использовать кэширование)
ОформлениеСтроки.Ячейки.МояКолонка.УстановитьТекст(ПолучитьЗначениеИзРегистра(ДанныеСтроки.Ссылка));
КонецПроцедуры
Путь Б: Модификация запроса
В модуле обработки ПодборНоменклатуры найдем функцию, формирующую текст запроса (обычно СформироватьЗапрос). Нам нужно добавить ЛЕВОЕ СОЕДИНЕНИЕ с нашим регистром. Это более производительный метод для больших списков, так как данные будут получены одним пакетом с основными данными справочника.
После того как пользователь выбрал товар, срабатывает процедура ОформитьЗаказ или ОбработкаВыбора. Если вы добавили новые колонки в форму подбора и хотите передать эти значения в документ, убедитесь, что они попадают в структуру, возвращаемую методом ОповеститьОВыборе().
Выясним, где это происходит в коде. В типовой УТ 10.3 за это отвечает процедура ВыбратьЭлемент() или логика кнопки «ОК» в корзине подбора. Проверьте, чтобы ваша новая колонка была добавлена в список полей, которые копируются из формы подбора в табличную часть документа.
Используя эти методы, вы сможете превратить стандартный подбор в мощный инструмент, адаптированный под бизнес-логику вашей компании, сохраняя при этом удобство типового интерфейса 1С 8.1.