Поддержка печати Qt
Qt предоставляет обширную кроссплатформенную поддержку печати. Используя системы печати каждой платформы, приложения Qt могут печатать на подключенных принтерах и через сети на удаленных принтерах. Система печати Qt также поддерживает генерацию файлов PDF, предоставляя основу для базовых возможностей генерации отчетов.
Классы, поддерживающие печать
Следующие классы поддерживают выбор и настройку принтеров и выходных данных печати.
Базовая реализация диалоговых окон печати, используемых для настройки принтеров |
|
Определяет интерфейс взаимодействия QPrinter с заданной системой печати |
|
Устройство рисования, рисующее на принтере |
|
Обеспечивает доступ к информации о существующих принтерах |
|
Диалоговое окно настройки страниц для параметров принтера |
|
Диалоговое окно для указания настроек принтера |
|
Диалоговое окно для предварительного просмотра и настройки макетов страниц для вывода на принтер |
|
Виджет для предварительного просмотра макетов страниц для вывода на принтер |
Устройства рисования и печать
В Qt принтеры представляются объектом QPrinter, устройством рисования, предоставляющим функциональность, специфичную для печати, такую как поддержка нескольких страниц и двустороннего вывода. В результате, печать включает использование QPainter для рисования на серии страниц так же, как вы бы рисовали на пользовательском виджете или изображении.
Создание QPrinter
Хотя объекты QPrinter могут быть созданы и настроены без необходимости ввода пользователем, печать часто выполняется в результате запроса пользователя; например, когда пользователь выбирает пункт меню Файл|Печать... в приложении графического интерфейса. В таких случаях новый созданный объект QPrinter передается в QPrintDialog, позволяя пользователю указать используемый принтер, размер бумаги и другие свойства печати.
QPrinter printer;
QPrintDialog dialog(&printer, this);
dialog.setWindowTitle(tr("Print Document"));
if (editor->textCursor().hasSelection())
dialog.addEnabledOption(QAbstractPrintDialog::PrintSelection);
if (dialog.exec() != QDialog::Accepted) {
return;
} Также возможно установить определенные свойства по умолчанию, изменив QPrinter перед его передачей в диалоговое окно печати. Например, приложения, генерирующие партии отчетов для печати, могут настроить QPrinter на запись в локальный файл по умолчанию вместо принтера.
Рисование на странице
После создания и настройки объекта QPrinter, можно использовать QPainter для выполнения операций рисования на нем. Мы можем создать и настроить рисовальщик следующим образом:
QPrinter printer(QPrinter::HighResolution);
printer.setOutputFileName("print.ps");
QPainter painter;
painter.begin(&printer);
for (int page = 0; page < numberOfPages; ++page) {
// Use the painter to draw on the page.
if (page != lastPage)
printer.newPage();
}
painter.end(); Поскольку QPrinter начинается с пустой страницы, нам нужно вызвать функцию newPage() после рисования каждой страницы, кроме последней.
Документ отправляется на принтер или записывается в локальный файл, когда вызывается end().
Системы координат
QPrinter предоставляет функции для получения информации о размерах бумаги (прямоугольник бумаги) и размерах области печати (прямоугольник страницы). Они заданы в логических координатах устройства, которые могут отличаться от физических координат, используемых самим устройством, показывая, что принтер способен отображать текст и графику с разрешением (как правило, более высоким), чем разрешение дисплея пользователя.
Хотя нам не нужно обрабатывать преобразование между логическими и физическими координатами самостоятельно, нам все равно необходимо применять преобразования к операциям рисования, поскольку пиксельные измерения, используемые для рисования на экране, часто слишком малы для более высокого разрешения типичных принтеров.
|
Системы координат принтера и рисовальщика Функции paperRect() и pageRect() предоставляют информацию о размере бумаги, используемой для печати, и области на ней, на которой можно рисовать. Прямоугольник, возвращаемый функцией pageRect(), обычно лежит внутри прямоугольника, возвращаемого функцией paperRect(). Вам не нужно учитывать позиции и размеры этих областей при использовании QPainter с QPrinter в качестве базового устройства рисования; начало координат рисовальщика совпадёт с верхним левым углом прямоугольника страницы, а операции рисования будут обрезаться по границам напечатаемой части страницы. |
Система рисования автоматически использует правильные метрики устройства при рисовании текста, но если вам необходимо позиционировать текст, используя информацию из метрик шрифта, вам необходимо убедиться, что устройство печати указано при создании объектов QFontMetrics и QFontMetricsF, или убедитесь, что каждый используемый QFont создан с использованием формы конструктора, которая принимает аргумент QPaintDevice.
Печать виджетов
Для печати виджета можно использовать функцию QWidget::render(). Как упоминалось, разрешение принтера, как правило, выше, чем разрешение экрана, поэтому вам необходимо масштабировать рисовальщик. Вы также можете захотеть разместить виджет на странице. Следующий пример кода демонстрирует, как это может выглядеть.
QPainter painter;
painter.begin(&printer);
double xscale = printer.pageRect().width()/double(myWidget->width());
double yscale = printer.pageRect().height()/double(myWidget->height());
double scale = qMin(xscale, yscale);
painter.translate(printer.paperRect().x() + printer.pageRect().width()/2,
printer.paperRect().y() + printer.pageRect().height()/2);
painter.scale(scale, scale);
painter.translate(-width()/2, -height()/2);
myWidget->render(&painter); Это позволит центрировать виджет на странице и масштабировать его так, чтобы он поместился на странице.
Печать из сложных виджетов
Некоторые виджеты, такие как QTextEdit и QGraphicsView, отображают богатый контент, который обычно управляется экземплярами других классов, таких как QTextDocument и QGraphicsScene. В результате именно эти классы обработки контента обычно предоставляют функциональность печати, либо через функцию, которая может использоваться для выполнения всей задачи, либо через функцию, которая принимает существующий объект QPainter. Некоторые виджеты предоставляют удобные функции для экспонирования базовых функций печати, избегая необходимости получения обработчика содержимого только для вызова одной функции.
В следующей таблице показаны класс и функция, ответственные за печать из набора различных виджетов. Для виджетов, которые не предоставляют функциональности печати напрямую, классы обработки содержимого, содержащие эту функциональность, можно получить с помощью функции в API соответствующего виджета.
| Виджет | Функция печати | Принимает |
|---|---|---|
| QGraphicsView | QGraphicsView::render() | QPainter |
| QSvgWidget | QSvgRenderer::render() | QPainter |
| QTextEdit | QTextDocument::print() | QPrinter |
| QTextLayout | QTextLayout::draw() | QPainter |
| QTextLine | QTextLine::draw() | QPainter |
QTextEdit требует QPrinter, а не QPainter, поскольку использует информацию о размерах страницы для вставки разрывов страниц в наиболее подходящих местах в печатных документах.
Лицензии и товарные знаки
Модуль поддержки печати Qt доступен по коммерческим лицензиям от The Qt Company. Кроме того, он доступен по лицензиям свободного программного обеспечения. Начиная с Qt 5.4, эти лицензии свободного программного обеспечения — GNU Lesser General Public License, версия 3 или GNU General Public License, версия 2. Подробнее см. Qt Licensing.
Обратите внимание, что Adobe® вводит ограничения на использование своих товарных знаков (включая логотипы) в сочетании с PDF; например, «Adobe PDF». Сведения о рекомендациях см. на сайте www.adobe.com.
© The Qt Company Ltd
Licensed under the GNU Free Documentation License, Version 1.3.
https://doc.qt.io/qt-5.13/qtprintsupport-index.html