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