Как реализовать выбор значения в поле шапки из колонки табличной части?

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

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

Постановка задачи и базовый алгоритм решения

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

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

  1. Получить данные из нужной колонки табличной части.
  2. Преобразовать эти данные в формат, пригодный для списка выбора.
  3. Очистить старые значения в элементе формы.
  4. Загрузить актуальные данные в выпадающий список.

Разбор типичных ошибок и выбор правильного метода

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


// Ошибочный или неточный вариант
Элементы.ВыбранныйКонтрагент.СписокЗначений.Загрузить(ТабличнаяЧасть.Выгрузить.ВыгрузитьКолонку("Контрагент"));

Проанализируем, почему этот код может не работать или работать некорректно:

  1. Неправильное имя свойства: У элемента формы (поля ввода) нет свойства СписокЗначений. Для управления выпадающим списком используется коллекция СписокВыбора.
  2. Неправильный метод: Метод Загрузить() предназначен для других типов коллекций. Для объекта типа СписокЗначений (которым является СписокВыбора) правильно использовать метод ЗагрузитьЗначения().
  3. Избыточность: Конструкция ТабличнаяЧасть.Выгрузить.ВыгрузитьКолонку() создает промежуточную таблицу значений в памяти. Если мы работаем в контексте формы, лучше обращаться к данным напрямую.

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


// Исправленный вариант
МассивДанных = Объект.СоставНоменклатуры.ВыгрузитьКолонку("Склад");
Элементы.ОсновнойСклад.СписокВыбора.ЗагрузитьЗначения(МассивДанных);

Оптимизация: Удаление дублей и пустых значений

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

Для удаления дублей лучше всего использовать вспомогательный объект ТаблицаЗначений и её метод Свернуть(). Рассмотрим этот алгоритм по шагам:


// Создаем временную таблицу на основе колонки ТЧ
ТЗ = Объект.СоставНоменклатуры.Выгрузить( , "Склад");

// Сворачиваем таблицу, оставляя только уникальные значения
ТЗ.Свернуть("Склад");

// Теперь удалим пустые ссылки, чтобы они не мешали пользователю
Индекс = 0;
Пока Индекс < ТЗ.Количество() Цикл
    Если Не ЗначениеЗаполнено(ТЗ[Индекс].Склад) Тогда
        ТЗ.Удалить(Индекс);
    Иначе
        Индекс = Индекс + 1;
    КонецЕсли;
КонецЦикла;

// Получаем массив уникальных заполненных значений
МассивУникальныхЗначений = ТЗ.ВыгрузитьКолонку("Склад");

// Очищаем и заполняем список выбора в элементе формы
Элементы.ОсновнойСклад.СписокВыбора.ЗагрузитьЗначения(МассивУникальныхЗначений);

Выбор подходящего события для обновления списка

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

Разберем реализацию через событие НачалоВыбора элемента формы:

  1. В свойствах поля ввода в конфигураторе найдите событие НачалоВыбора и создайте обработчик на клиенте.
  2. Установите параметр СтандартнаяОбработка = Ложь. Это отключит открытие стандартного окна справочника.
  3. Вызовите серверную функцию для получения актуального массива данных.
  4. Используйте метод ВыбратьИзСписка.

Пример реализации в модуле управляемой формы:


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

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

Настройка свойств элемента формы

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

Заключение

Мы рассмотрели эффективный способ организации выбора данных в 1С, который значительно повышает качество интерфейса. Подведем итог: для реализации этой задачи важно не только знать правильные методы ВыгрузитьКолонку и ЗагрузитьЗначения, но и помнить о необходимости очистки данных от дублей и пустых ссылок. Использование событийной модели НачалоВыбора позволяет гарантировать актуальность списка в любой момент времени без лишней нагрузки на систему.

← На главную