Выпуск №12. Чудо-запросы 1С
|
|
На практике столкнулся с интересным отчетом и использовал его в своей конфигурации Транспортного Учета. Отчет красиво выводит по горизонтали информацию с данными из регистра сведений в соответствии с датами начала и окончания погрузки с определенного склада. Отчет без использования Схемы компоновки данных. Вот так он выглядит:

Что примечательного в нем, так это запрос, но прежде чем приводить код запроса вкратце опишу откуда собираются данные:
- Во первых, это справочники портов отгрузки и складов
- Во вторых это регистр сведений с Измерениями: "ДатаНачалаОтгрузки", "ДатаОкончанияОтгрузки", "Порт", "Склад" и Реквизитом "Заявка".
В запросе для каждого порта создаются временные таблицы с интервалами в полчаса от даты начала (выбранная дата + 6 часов, т.к. выгрузки с 6.30 утра до 16.30). В результате выполнения запроса получается такая таблица:

А вот и сама функция, возвращающая результат запроса:
Функция ПолучитьЗапрос() Экспорт
Запрос = Новый Запрос;
Запрос.УстановитьПараметр("НачДата", НачалоДня(Отчет.НаДату)+3600*6.5);
Запрос.УстановитьПараметр("Склад", Отчет.Склад);
Запрос.УстановитьПараметр("СкладЭтоГруппа", Отчет.Склад.ЭтоГруппа);
Запрос.УстановитьПараметр("ПустойСклад", Справочники.Склады.ПустаяСсылка());
Запрос.УстановитьПараметр("Перевозчик", Отчет.Перевозчик);
Запрос.УстановитьПараметр("ПеревозчикЭтоГруппа", Отчет.Перевозчик.ЭтоГруппа);
Запрос.УстановитьПараметр("ПустойПеревозчик", Справочники.Контрагенты.ПустаяСсылка());
Запрос.Текст = "ВЫБРАТЬ РАЗРЕШЕННЫЕ
| 0 КАК Число
|ПОМЕСТИТЬ ВТ_Разряд
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 1
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 2
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 3
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 4
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 5
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 6
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 7
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 8
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| 9
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ
| РазрядА.Число + РазрядБ.Число * 10 КАК ТекЧисло
|ПОМЕСТИТЬ ВТ_Числа
|ИЗ
| ВТ_Разряд КАК РазрядА
| ЛЕВОЕ СОЕДИНЕНИЕ ВТ_Разряд КАК РазрядБ
| ПО (ИСТИНА)
|ГДЕ
| РазрядА.Число + РазрядБ.Число * 10 МЕЖДУ 0 И 20
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| Числа_.ТекЧисло,
| ДОБАВИТЬКДАТЕ(&НачДата, МИНУТА, Числа_.ТекЧисло * 30) КАК НачалоИнтервала,
| ДОБАВИТЬКДАТЕ(ДОБАВИТЬКДАТЕ(&НачДата, МИНУТА, (Числа_.ТекЧисло + 1) * 30), СЕКУНДА, -1) КАК КонецИнтервала,
| ТУ_ПортыПогрузкиРазгрузки.Ссылка КАК Порт
|ПОМЕСТИТЬ ВТ_Интервалы
|ИЗ
| ВТ_Числа КАК Числа_
| ЛЕВОЕ СОЕДИНЕНИЕ Справочник.ТУ_ПортыПогрузкиРазгрузки КАК ТУ_ПортыПогрузкиРазгрузки
| ПО (ИСТИНА)
|ГДЕ
| Числа_.ТекЧисло <> 11
| И Числа_.ТекЧисло <> 12
| И ВЫБОР
| КОГДА &Склад = &ПустойСклад
| ТОГДА ИСТИНА
| ИНАЧЕ ВЫБОР
| КОГДА &СкладЭтоГруппа = ИСТИНА
| ТОГДА ТУ_ПортыПогрузкиРазгрузки.Склад В ИЕРАРХИИ (&Склад)
| ИНАЧЕ ТУ_ПортыПогрузкиРазгрузки.Склад = &Склад
| КОНЕЦ
| КОНЕЦ
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| ТУ_ЗанятыеПорты.ДатаВремяНачала КАК Начало,
| ДОБАВИТЬКДАТЕ(ТУ_ЗанятыеПорты.ДатаВремяОкончания, СЕКУНДА, -1) КАК Окончание,
| ТУ_ЗанятыеПорты.Порт,
| ТУ_ЗанятыеПорты.Заявка,
| ТУ_ЗанятыеПорты.Заявка.МаркаТС КАК МаркаТС,
| ТУ_ЗанятыеПорты.Заявка.Автомобиль КАК Автомобиль
|ПОМЕСТИТЬ ВТ_ЗанятыеПорты
|ИЗ
| РегистрСведений.ЗанятыеПорты КАК ТУ_ЗанятыеПорты
|ГДЕ
| НАЧАЛОПЕРИОДА(ТУ_ЗанятыеПорты.ДатаВремяНачала, ДЕНЬ) = НАЧАЛОПЕРИОДА(&НачДата, ДЕНЬ)
| И ВЫБОР
| КОГДА &Склад = &ПустойСклад
| ТОГДА ИСТИНА
| ИНАЧЕ ВЫБОР
| КОГДА &СкладЭтоГруппа = ИСТИНА
| ТОГДА ТУ_ЗанятыеПорты.Порт.Склад В ИЕРАРХИИ (&Склад)
| ИНАЧЕ ТУ_ЗанятыеПорты.Порт.Склад = &Склад
| КОНЕЦ
| КОНЕЦ
| И ВЫБОР
| КОГДА &Перевозчик = &ПустойПеревозчик
| ТОГДА ИСТИНА
| ИНАЧЕ ВЫБОР
| КОГДА &ПеревозчикЭтоГруппа = ИСТИНА
| ТОГДА ТУ_ЗанятыеПорты.Заявка.Перевозчик В ИЕРАРХИИ (&Перевозчик)
| ИНАЧЕ ТУ_ЗанятыеПорты.Заявка.Перевозчик = &Перевозчик
| КОНЕЦ
| КОНЕЦ
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| Интервалы.ТекЧисло КАК ТекЧисло,
| Интервалы.НачалоИнтервала,
| Интервалы.КонецИнтервала,
| Интервалы.Порт КАК Порт,
| ЗанятыеПорты.Заявка,
| ЕСТЬNULL(ЗанятыеПорты.МаркаТС, """") КАК МаркаТС,
| ЕСТЬNULL(ЗанятыеПорты.Автомобиль, """") КАК Автомобиль,
| ЗанятыеПорты.Начало,
| ЗанятыеПорты.Окончание,
| Интервалы.Порт.Склад КАК Склад
|ИЗ
| ВТ_Интервалы КАК Интервалы
| ЛЕВОЕ СОЕДИНЕНИЕ ВТ_ЗанятыеПорты КАК ЗанятыеПорты
| ПО (ЗанятыеПорты.Начало МЕЖДУ Интервалы.НачалоИнтервала И Интервалы.КонецИнтервала
| ИЛИ ЗанятыеПорты.Окончание МЕЖДУ Интервалы.НачалоИнтервала И Интервалы.КонецИнтервала
| ИЛИ ЗанятыеПорты.Начало < Интервалы.НачалоИнтервала
| И ЗанятыеПорты.Окончание > Интервалы.КонецИнтервала)
| И Интервалы.Порт = ЗанятыеПорты.Порт
|
|УПОРЯДОЧИТЬ ПО
| Интервалы.Порт.Склад.Наименование,
| Интервалы.Порт.Наименование,
| ТекЧисло
|ИТОГИ ПО
| Склад,
| Порт";
РезультатЗапроса = Запрос.Выполнить();
Возврат РезультатЗапроса;
КонецФункции
Ну и сама процедура вывода отчета выглядит так:
Процедура СформироватьОтчетНаСервере()
ПолеТабличногоДокумента.Очистить();
ПолеТабличногоДокумента.ОриентацияСтраницы = ОриентацияСтраницы.Ландшафт;
ПолеТабличногоДокумента.ПолеСлева = 0;
ПолеТабличногоДокумента.ПолеСправа = 0;
ПолеТабличногоДокумента.АвтоМасштаб = Истина;
Макет = Отчеты.ГрафикДвиженияАвтотранспорта.ПолучитьМакет("Макет");
ОбластьФормирование = Макет.ПолучитьОбласть("ИнформацияОФормировании");
ОбластьЗаголовок = Макет.ПолучитьОбласть("ОбластьЗаголовок");
ОбластьШапка = Макет.ПолучитьОбласть("ОбластьШапка");
ОбластьСтрока = Макет.ПолучитьОбласть("ОбластьСтрока|ОбластьСклад");
ОбластьВремя = Макет.ПолучитьОбласть("ОбластьСтрока|ОбластьВремя");
ОбластьВремяЦвет = Макет.ПолучитьОбласть("ОбластьСтрокаЦвет|ОбластьВремя");
ОбластьОтгруженЦвет = Макет.ПолучитьОбласть("ОбластьСтрокаЦветОтгружен|ОбластьВремя");
ОбластьСтрокаСклад = Макет.ПолучитьОбласть("ОбластьСтрокаСклад");
ОбластьФормирование.Параметры.ДатаФормирования = "Дата формирования: "+ТекущаяДата();
ПолеТабличногоДокумента.Вывести(ОбластьФормирование);
ОбластьЗаголовок.Параметры.Дата = Формат(Отчет.НаДату, "ДФ=dd.MM.yyyy");
ПолеТабличногоДокумента.Вывести(ОбластьЗаголовок);
ПолеТабличногоДокумента.Вывести(ОбластьШапка);
ПолеТабличногоДокумента.ФиксацияСверху = 5;
ВыборкаСклады = ПолучитьЗапрос().Выбрать(ОбходРезультатаЗапроса.ПоГруппировкам);
Пока ВыборкаСклады.Следующий() Цикл
ОбластьСтрокаСклад.Параметры.Склад = ВыборкаСклады.Склад;
ПолеТабличногоДокумента.Вывести(ОбластьСтрокаСклад);
ВыборкаПорты = ВыборкаСклады.Выбрать(ОбходРезультатаЗапроса.ПоГруппировкам);
Пока ВыборкаПорты.Следующий() Цикл
ОбластьСтрока.Параметры.СкладПорт = ВыборкаПорты.Порт;
ПолеТабличногоДокумента.Вывести(ОбластьСтрока);
Выборка = ВыборкаПорты.Выбрать();
ПредЗнач="";
Пока Выборка.Следующий() Цикл
ТекЗнач = Выборка.Заявка;
Если ТекЗнач = NULL Тогда
ТекОбласть = ОбластьВремя;
Иначе
ТекОбласть = ОбластьВремяЦвет;
КонецЕсли;
ТекОбласть.Параметры.Время = "";
Если ПредЗнач <> ТекЗнач Тогда
ТекстЗаявки = "";
Если ЗначениеЗаполнено(Выборка.Заявка) Тогда
ТЗ_Заявки = Выборка.Заявка.ЗаявкиКонтрагентов.Выгрузить();
ТЗ_Заявки.Свернуть("Контрагент");
Если Отчет.ПоказыватьМаршрут Тогда
ТекстЗаявки = "; " + СокрЛП(Выборка.Заявка.МаршрутПеревозки) + "; ";
Иначе
ТекстЗаявки = "; ";
КонецЕсли;
Для Каждого СтрЗаявки Из ТЗ_Заявки Цикл
Если ЗначениеЗаполнено(СтрЗаявки.Контрагент) Тогда
Если Отчет.ПоказыватьМаршрут Тогда
ТекстЗаявки = ТекстЗаявки + ?(Прав(СокрЛП(ТекстЗаявки), 1) = ";", "", ", ") + СокрЛП(СтрЗаявки.Контрагент);
Иначе
ТекстЗаявки = ТекстЗаявки + ?(ТекстЗаявки = "; ", "", ", ") + СокрЛП(СтрЗаявки.Контрагент);
КонецЕсли;
КонецЕсли;
КонецЦикла;
КонецЕсли;
ТекОбласть.Параметры.Время = ?(Выборка.МаркаТС="","",Выборка.МаркаТС+", "+Выборка.Автомобиль)+ТекстЗаявки;
ТекОбласть.ТекущаяОбласть.Расшифровка = Выборка.Заявка;
КонецЕсли;
ПредЗнач = ТекЗнач;
ПолеТабличногоДокумента.Присоединить(ТекОбласть);
КонецЦикла;
КонецЦикла;
КонецЦикла;
ПолеТабличногоДокумента.ФиксацияСлева = 2;
ПолеТабличногоДокумента.Автомасштаб = Истина;
КонецПроцедуры
И последнее, что осталось показать, это макет:

На этом все, кому нужна конфигурация, регистрируйтесь, и просите ниже в комментариях я вышлю Вам нам почту.

















Добавить комментарий (через VK):