Почему форма выбора возвращает Неопределено и как получить выбранные значения в 1С

Программист 1С v8.3 (Управляемые формы) 1С:Зарплата и Управление Персоналом IT и автоматизация бизнеса
← На главную

В процессе разработки на платформе 1С:Предприятие 8.3 программисты часто сталкиваются с ситуацией, когда стандартный механизм ОписаниеОповещения при открытии формы выбора возвращает Неопределено. Особенно часто это проявляется в типовых конфигурациях, таких как Зарплата и Управление Персоналом 3.1, при работе со справочником ПодразделенияОрганизаций. Разберем подробно, почему это происходит и какими способами можно гарантированно получить результат выбора.

Анализ проблемы: почему ОписаниеОповещения не получает данные

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


&НаКлиенте
Процедура ПодборПодразделений(Команда)    
    ПараметрыОткрытия = Новый Структура; 
    ПараметрыОткрытия.Вставить("ЗакрыватьПриВыборе", Ложь); 
    ПараметрыОткрытия.Вставить("ЗакрыватьПриЗакрытииВладельца", Истина);
    ПараметрыОткрытия.Вставить("МножественныйВыбор", Истина); 
    ПараметрыОткрытия.Вставить("РежимВыбора", Истина); 
    
    ткОповещение = Новый ОписаниеОповещения("ПодборПодразделенийЗавершение", ЭтотОбъект);    
    ОткрытьФорму("Справочник.ПодразделенияОрганизаций.ФормаВыбора", ПараметрыОткрытия, ЭтотОбъект, , , , ткОповещение);
КонецПроцедуры

&НаКлиенте
Процедура ПодборПодразделенийЗавершение(РезультатВыбора, Параметры) Экспорт
    // Здесь РезультатВыбора оказывается Неопределено
КонецПроцедуры

Проанализируем ситуацию. Основная причина кроется в сочетании параметра ЗакрыватьПриВыборе = Ложь и логики самой формы выбора. Когда мы устанавливаем ЗакрыватьПриВыборе = Ложь, платформа ожидает, что форма останется открытой для выбора нескольких элементов. В этом режиме стандартное закрытие формы с передачей результата в ОписаниеОповещения часто не срабатывает автоматически, так как форма «не знает», в какой момент выбор окончательно завершен пользователем.

Способ 1: Использование события ОбработкаВыбора

Выясним важный технический нюанс: когда в форме выбора вызывается метод ОповеститьОВыборе(), данные передаются не в обратный вызов (callback) ОткрытьФорму, а в событие ОбработкаВыбора той формы, которая была указана владельцем (третий параметр в ОткрытьФорму).

Рассмотрим, как правильно реализовать получение данных через этот механизм. В вызывающей форме (владельце) необходимо создать обработчик события:


&НаКлиенте
Процедура ОбработкаВыбора(ВыбранноеЗначение, ИсточникВыбора)
    Если ТипЗнч(ВыбранноеЗначение) = Тип("Массив") Тогда
        // Обрабатываем список выбранных подразделений
        Для Каждого Элемент Из ВыбранноеЗначение Цикл
            Сообщить("Выбрано подразделение: " + Элемент);
        КонецЦикла;
    ИначеЕсли ЗначениеЗаполнено(ВыбранноеЗначение) Тогда
        Сообщить("Выбрано: " + ВыбранноеЗначение);
    КонецЕсли;
КонецПроцедуры

Важно: Чтобы этот метод сработал, при вызове ОткрытьФорму в качестве третьего параметра (Владелец) обязательно должен быть передан ЭтотОбъект или ЭтаФорма. Если владелец не указан, событие ОбработкаВыбора не будет вызвано.

Способ 2: Особенности типовых форм в ЗУП 3.1

Проанализируем специфику конфигурации ЗУП 3.1. Для справочника ПодразделенияОрганизаций часто используются специализированные формы, которые могут вести себя не так, как стандартные формы выбора. В некоторых случаях форма вообще не содержит обработчика кнопки «Выбрать», если она открыта не в режиме выбора.

Если вы обнаружили, что ОбработкаВыбора не срабатывает, стоит проверить, какая именно форма открывается. Попробуйте явно указать путь к форме:

ОткрытьФорму("Справочник.ПодразделенияОрганизаций.Форма.ФормаВыбора", ...)

Также обратите внимание на сообщение в обсуждении: в ЗУП для подразделений часто используется механизм Оповестить() вместо ОповеститьОВыборе(). Это глобальное оповещение, которое можно перехватить через ОбработкаОповещения.

Способ 3: Использование ОбработкаОповещения

Если форма выбора после нажатия кнопки «ОК» или «Выбрать» выполняет программный код Оповестить("СобытиеВыбораПодразделений", Результат), то нам нужно использовать другой механизм перехвата данных. Разберем по шагам:

  1. В вызывающей форме определим процедуру ОбработкаОповещения.
  2. Проверим имя события, которое отправляет форма выбора.
  3. Извлечем данные из параметра.

&НаКлиенте
Процедура ОбработкаОповещения(ИмяСобытия, Параметр, Источник)
    Если ИмяСобытия = "ВыборПодразделений" Тогда
        // Допустим, форма выбора отправила массив подразделений
        РезультатВыбора = Параметр;
        // Ваша логика обработки
    КонецЕсли;
КонецПроцедуры

Рекомендации по настройке параметров открытия

Чтобы минимизировать ошибки при получении Неопределено, придерживайтесь следующих правил при формировании структуры ПараметрыОткрытия:

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

← На главную