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