Как настроить отбор по справочнику в плане видов характеристик (ПВХ) на обычных формах 1С?

Программист 1С v8.3 (Обычные формы) 1С:Управление торговлей Управленческий учет Торговля и дистрибуция
← На главную

При разработке внешних отчетов и обработок в конфигурациях на обычных формах (таких как 1С:Управление торговлей 10.3, Управление производственным предприятием 1.3 или Комплексная автоматизация 1.1) часто возникает задача ограничить выбор свойств объектов. Например, нам требуется предоставить пользователю возможность выбирать свойства (элементы плана видов характеристик) исключительно для справочника Номенклатура, скрыв все остальные свойства (контрагентов, договоров и т.д.).

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

В чем сложность решения задачи на обычных формах?

В управляемом интерфейсе (начиная с платформы 8.2 и 8.3) большинство задач фильтрации данных решается простой настройкой свойств пути к данным, связей параметров выбора или параметров выбора непосредственно в конфигураторе. Однако в обычных формах этот функционал ограничен.

Если мы попытаемся настроить отбор стандартными методами, мы столкнемся со следующими проблемами:

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

Давайте пошагово разберем, как правильно реализовать программное ограничение списка выбора.

Решение 1. Простой отбор по назначению свойства

Рассмотрим базовый сценарий: нам нужно открыть форму выбора плана видов характеристик СвойстваОбъектов и показать там только те свойства, у которых реквизит НазначениеСвойства равен значению Справочник_Номенклатура.

Для реализации этого решения нам понадобится перехватить событие начала выбора у поля ввода. Выполним следующие шаги:

Шаг 1. Откроем форму нашего отчета или обработки в конфигураторе, выберем нужное поле ввода (в котором выбирается свойство) и перейдем в его свойства.

Шаг 2. Найдем событие НачалоВыбора и создадим для него процедуру-обработчик на клиенте.

Шаг 3. Пропишем внутри обработчика следующий программный код:


Процедура СвойстваНоменклатурыНачалоВыбора(Элемент, СтандартнаяОбработка)
    
    // Отменяем стандартное открытие формы выбора платформой
    СтандартнаяОбработка = Ложь;
    
    // Получаем форму выбора плана видов характеристик программно
    ФормаВыбора = ПланыВидовХарактеристик.СвойстваОбъектов.ПолучитьФормуВыбора("ФормаВыбора", Элемент);
    
    // Обращаемся к отбору табличного поля (списка) на форме выбора
    // Название списка по умолчанию в ПВХ — "ПланВидовХарактеристикСписок"
    ЭлементОтбора = ФормаВыбора.ПланВидовХарактеристикСписок.Отбор.НазначениеСвойства;
    
    // Настраиваем параметры отбора
    ЭлементОтбора.Значение      = ПланыВидовХарактеристик.НазначенияСвойствКатегорийОбъектов.Справочник_Номенклатура;
    ЭлементОтбора.ВидСравнения  = ВидСравнения.Равно;
    
    // КРИТИЧЕСКИ ВАЖНО: Включаем использование отбора, иначе он не применится!
    ЭлементОтбора.Использование = Истина;
    
    // По желанию: запрещаем пользователю отключать или изменять этот отбор в форме выбора
    ФормаВыбора.ЭлементыФормы.ПланВидовХарактеристикСписок.НастройкаОтбора.НазначениеСвойства.Доступность = Ложь;
    
    // Открываем форму выбора
    ФормаВыбора.Открыть();
    
КонецПроцедуры

В этом коде ключевым моментом является установка свойства Использование = Истина. Без этой строки платформа проигнорирует переданное значение отбора и выведет весь список свойств объектов, включая свойства контрагентов, складов и документов.

Решение 2. Продвинутый отбор с учетом иерархии групп номенклатуры

В реальных бизнес-задачах конфигурации УТ 10.3 свойства редко назначаются сразу всей номенклатуре. Чаще всего свойства привязываются к конкретным папкам (группам) номенклатуры. Например, свойство «Размер обуви» актуально только для группы «Обувь», а «Объем памяти» — для группы «Электроника».

Связь свойств с группами номенклатуры хранится не в самом плане видов характеристик, а в регистре сведений НазначенияСвойствОбъектов. Если мы применим простое решение №1, то пользователь не увидит специфические свойства, закрепленные за конкретными папками.

Давайте разберем более сложный алгоритм, который определяет выбранную в отчете группу номенклатуры, собирает все родительские группы (так как свойства наследуются по иерархии вниз) и выводит только актуальные свойства.

Предположим, что на форме нашего внешнего отчета есть реквизит ГруппаНоменклатуры. Тогда код обработчика начала выбора будет выглядеть следующим образом:


Процедура СвойстваНоменклатурыНачалоВыбора(Элемент, СтандартнаяОбработка)
    
    СтандартнаяОбработка = Ложь;
    
    // 1. Формируем список групп для поиска (с учетом иерархии родителей)
    СписокНазначений = Новый СписокЗначений;
    Если ЗначениеЗаполнено(ГруппаНоменклатуры) Тогда
        СписокНазначений.Добавить(ГруппаНоменклатуры);
        
        // Рекурсивно поднимаемся вверх по дереву групп номенклатуры
        ТекущийРодитель = ГруппаНоменклатуры.Родитель;
        Пока ЗначениеЗаполнено(ТекущийРодитель) Цикл
            СписокНазначений.Добавить(ТекущийРодитель);
            ТекущийРодитель = ТекущийРодитель.Родитель;
        КонецЦикла;
    КонецЕсли;
    
    // 2. Выбираем свойства запросом из регистра сведений "НазначенияСвойствОбъектов"
    Запрос = Новый Запрос;
    Запрос.Текст = 
    "ВЫБРАТЬ РАЗЛИЧНЫЕ
    |	СвойстваОбъектов.Ссылка КАК Ссылка
    |ИЗ
    |	ПланВидовХарактеристик.СвойстваОбъектов КАК СвойстваОбъектов
    |	ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.НазначенияСвойствОбъектов КАК НазначенияСвойствОбъектов
    |		ПО НазначенияСвойствОбъектов.Свойство = СвойстваОбъектов.Ссылка
    |ГДЕ
    |	СвойстваОбъектов.НазначениеСвойства = &НазначениеНоменклатура
    |	И (НазначенияСвойствОбъектов.Объект ЕСТЬ NULL 
    |		ИЛИ НазначенияСвойствОбъектов.Объект В (&СписокНазначений))";
    
    Запрос.УстановитьПараметр("НазначениеНоменклатура", ПланыВидовХарактеристик.НазначенияСвойствКатегорийОбъектов.Справочник_Номенклатура);
    Запрос.УстановитьПараметр("СписокНазначений", СписокНазначений);
    
    Выгрузка = Запрос.Выполнить().Выгрузить();
    МассивРазрешенныхСвойств = Выгрузка.ВыгрузитьКолонку("Ссылка");
    
    СписокРазрешенныхСвойств = Новый СписокЗначений;
    СписокРазрешенныхСвойств.ЗагрузитьЗначения(МассивРазрешенныхСвойств);
    
    // 3. Открываем форму выбора и накладываем отбор "В списке" по ссылкам ПВХ
    ФормаВыбора = ПланыВидовХарактеристик.СвойстваОбъектов.ПолучитьФормуВыбора("ФормаВыбора", Элемент);
    
    ОтборСсылка = ФормаВыбора.ПланВидовХарактеристикСписок.Отбор.Ссылка;
    ОтборСсылка.ВидСравнения = ВидСравнения.ВСписке;
    ОтборСсылка.Значение     = СписокРазрешенныхСвойств;
    ОтборСсылка.Использование = Истина;
    
    ФормаВыбора.Открыть();
    
КонецПроцедуры

Этот способ является наиболее профессиональным и юзабильным для конечного пользователя, так как он динамически сужает список доступных свойств до тех, которые действительно имеют смысл для выбранного сегмента номенклатуры.

Резюме и частые ошибки

При работе с планами видов характеристик на обычных формах всегда помните следующие правила:

Используя предложенные варианты программного кода, вы сможете легко и безошибочно настроить любые сложные отборы в своих внешних отчетах и обработках.

← На главную