© 2007 Ирина Цыбульникова
Создание программных комплексов для бухучета всегда предполагает большое количество отчетных форм. Я опишу некоторые аспекты своей работы, позволяющие оптимизировать процесс создания и управления отчетами на примере программного комплекса расчета с покупателями в системе ЖКХ.
В процессе разработки отчетов нередко возникает задача представления одних и тех же данных в разных видах. Примером такой задачи может служить реестр полученных оплат за выполненные услуги ЖКХ. Упрощенный вид таблицы:
По условиям задачи эти данные надо представлять в виде нескольких отчетов: "платежи по видам оплат за период", "платежи по услугам за период", "сумма оплат по дням за период", "расшифровка каждого вида оплаты по типам платежных документов" и несколько других.
Заказчик в техническом задании указал только, в каком разрезе должна быть представлена информация, не указав точно как должен выглядеть каждый отчет. Но сама таблица с данными уже определяет вид каждого отчета. Первые два, представляют собой списки плательщиков, сгруппированные по разным полям таблицы. Очевидно, шаблоны этих отчетов должны будут иметь одинаковые заголовки и примерно одинаковые списки. В третьем отчете вместо списка плательщиков будет список дней. В четвертом ограничение по виду оплат и группировка по типу документа. И все отчеты имеют ограничение по периоду.
Самым простым решением задачи явилось бы создание отдельных шаблонов для каждого отчета. Но в этом случае значительная часть информации повторялась бы в каждом из шаблонов. К счастью в FastReport 4 есть возможность оптимизировать работу по созданию и управлению подобными однотипными отчетами. При использовании наследования шаблонов решение задачи значительно упрощается и код получается более простой и наглядный.
Итак, приступим. В первую очередь создаем базовый отчет, на котором располагаем заголовок отчета, описание параметров заказанных пользователем, одну группу и одну детализацию. Отчет имеет следующий вид:

Сохраняем отчет с именем BaseReport.fr3. Теперь на его основе будем создавать первый отчет "Платежи по видам оплат за период". Для этого нажимаем меню "файл"-"новый…", в качестве базового выбираем BaseReport и устанавливаем флажок "Наследовать отчет".

Далее создание наследованного отчета требует три обязательных действия: определить, по какому полю будет выполняться группировка, добавить заголовки столбцов и изменить детализацию. Как видно, работы по созданию нового отчета стало заметно меньше. Готовый отчет имеет следующий вид:

Создание второго отчета "Платежи по услугам за период" аналогично созданию первого отчета, и отличается только тем, что группировка происходит по другим полям, детализация имеет другое количество столбцов. При этом не приходится задумываться о шапке отчета и подвале страницы - они остаются неизменными. Отчет имеет следующий вид:

Третий отчет "Сумма оплат по дням за период" имеет такую же шапку и подвал страницы, как и первые два, но группировка не нужна, поэтому grMainHeader и grMainFooter делаем невидимыми (Visible = False). Отчет имеет следующий вид:

Другие отчеты будут наследоваться по аналогии, используя изменение свойств бендов предка и текста SQL запроса.
Но при наследовании не обошлось без проблем. Как же без них.
Решаемая задача является небольшой частью большого программного комплекса, состоящего из нескольких десятков динамических библиотек, исполняемых модулей, шаблонов отчетов и других ресурсов. Очевидно, что предлагаемый в документации UserManual (гл.12) способ хранения базового и наследованных шаблонов в одном каталоге с исполняемыми модулями в нашем случае не самый удобный. Простая попытка переместить базовый и наследованные шаблоны в другой каталог приведет к тому, что отчет не будет формироваться. На экране появится пустая страница, которая говорит о том, что предок шаблона отчета "Платежи по видам оплат за период" не был найден в одном каталоге с исполняемыми модулями.

Решение подсказал документ ProgrammerManual (гл.1.21), в котором описан обработчик события OnLoadTemplate. После создание такого обработчика:
procedure TfmAnUniAsk.frxMainReportLoadTemplate(Report: TfrxReport; const TemplateName: string);наш отчет прекрасно находит базовый отчет в требуемом каталоге.
begin
Report.LoadFromFile(MyReportPath + TemplateName);
end;
В реальной программе может возникнуть необходимость создания и другого вида отчетов для представления данных реестра оплат. В этом случае грамотно построенный базовый шаблон позволит решить задачу с минимальными усилиями.
Использование наследования от базового отчета в проекте с большим количеством отчетов имеет несколько плюсов:
Copyright© 2007 Ирина Цыбульникова Специально для Delphi Plus