Delphi World - это проект, являющийся сборником статей и малодокументированных возможностей  по программированию в среде Delphi. Здесь вы найдёте работы по следующим категориям: delphi, delfi, borland, bds, дельфи, делфи, дэльфи, дэлфи, programming, example, программирование, исходные коды, code, исходники, source, sources, сорцы, сорсы, soft, programs, программы, and, how, delphiworld, базы данных, графика, игры, интернет, сети, компоненты, классы, мультимедиа, ос, железо, программа, интерфейс, рабочий стол, синтаксис, технологии, файловая система...
Проблемы со шрифтами у QuickReport

Я использую Delphi 2.0 и QuickReports 1.1.

Я создал ОЧЕНЬ сложный (графически, во всяком случае) отчет и только что обнаружил, что это не выводится как положено на экране и на принтере во время выполнения программы (хотя это и корректно отображается в окне предварительного просмотра в режиме проектирования). Ошибка возникает только в том случае, если в Windows 95 установлены большие (LARGE) системные шрифты! Ну и что мне теперь прикажете делать?

У меня тоже была такая же серьезная проблема, но только при печати под Win 95 на офисный HP 4M и при просмотре отчета под NT 4.0. Но то же самое приложение у меня прекрасно работало под NT 3.51 SP5.

Я видел дискуссию по поводу этой ошибки, возникающей в GDI коде под NT 4.0, поэтому я не удивился, обнаружив ее у себя. Мне пришлось засучить рукава и очень тесно познакомиться с кодом QuickReports, особенно с процедурой первичного вывода текста, когда программа изменяет шрифт в каждой выводимой области. Вот этот злосчастный сегмент кода в методе TQRCustomControl.Print:


QRPrinter.Canvas.Font:=Font;
QRPrinter.Canvas.Font.size:=trunc(abs(parentreport.xpos(font.size)));
QRPrinter.Canvas.brush.Color:=Color;

Теперь те из нас, которые истратили слишком много времени на изучение исходного кода VCL узнали, что VCL поддерживает кэш ресурса через менеджера дескрипторов в Graphics.pas и что попытки уменьшения количества используемых ресурсов Windows сводятся к методу подсчета ссылок на дескрипторы многократно испольуемых ресурсов. Коду, приведенному выше, отлично удалось это обойти! Каждый раз холст принтера устанавливает шрифты полей, таким образом уменьшая счетчик используемых ресурсов в ноль с дальнейшим его освобождением и затем масштабирует размер шрифта для соответствия его метрике принтера, таким образом требуя размещения нового шрифтового ресурса.

Всдедствие этого _каждое_ поле отчета использует для вывода собственный шрифт, тратя для этого каждый раз системные ресурсы и вгоняя в штопор систему (регистратор метафайлов), пытающуюся уследить за бешенным ритмом смены шрифтов и массовым съеданием ресурсов.

В качестве эксперимента я создал непечатаемую этикетку с тем же самым размером шрифта, что и у масштабируемого шрифта принтера, тем самым заставляя ресурс кэшироваться - ошибка исчезла как страшный сон! Это доказывает идентичность проблемы в NT 4.0 - те же действующие лица: регистратор расширенных метафайлов и огромное количество изменений шрифтов.

Лучшее решение я увидел в следующем:


// При установке нового шрифта сохраняем шрифт принтера
SaveFont := TFont.Create;
SaveFont.Assign(QRPrinter.Canvas.Font);

QRPrinter.Canvas.Font:=Font;
QRPrinter.Canvas.Font.size:=trunc(abs(parentreport.xpos(font.size)));
QRPrinter.Canvas.brush.Color:=Color;

// Освобождаем сохраненный шрифт принтера. Теперь работа сделана.
SaveFont.Free;
SaveFont := nil;

Дополнительными строками нам удается проверить тот факт, что шрифт принтера уже используется или же для холста принтера выбирается тот же самый шрифт. Это работает уже вполне корректно и позволяет печатать правильные отчеты под NT 4.0. Некоторым странным совпадением можно считать устранение зашитых жирных шрифтов, изменившее шрифты, печатаемые под Win95.

Так, если у вас есть зарегистрированная версия QuickReports, вы можете сделать коррекцию исходных файлов, и вы увидите, что ваши отчеты будут генериться быстрее, выглядеть "мягче" и не будет ошибок и издержек шрифтовых ресурсов из-за ограничения кода расширенных метафайлов и GDI.

Проект Delphi World © Выпуск 2002 - 2004
Автор проекта: ___Nikolay