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