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