summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorSzabolcs David <davidsz@inf.u-szeged.hu>2021-06-03 01:37:37 +0200
committerSzabolcs David <davidsz@inf.u-szeged.hu>2021-06-03 14:05:22 +0200
commit4943d9801ccad59aef073374644fc991e49987e3 (patch)
tree4a4495c6a3391aa1bc4ad42d1548ff2f1bc9e46e /src
parent57140466f277a074b288a515b2bdfd26c8a3cbe3 (diff)
Drop printsupport dependency from core
Prevent linkage of core to widgets by moving printing API from QWebEnginePage to View and using QPagedPaintDevice (the QtGui ancestor of QPrinter) where it's needed. Change-Id: I6ea96edb495b0dcaaa584bbe72632fda025c18d3 Reviewed-by: Allan Sandfeld Jensen <allan.jensen@qt.io>
Diffstat (limited to 'src')
-rw-r--r--src/core/api/CMakeLists.txt6
-rw-r--r--src/core/api/qwebenginepage.cpp186
-rw-r--r--src/core/api/qwebenginepage.h8
-rw-r--r--src/core/api/qwebenginepage_p.h6
-rw-r--r--src/core/printing/printer_worker.cpp52
-rw-r--r--src/core/printing/printer_worker.h13
-rw-r--r--src/webenginewidgets/CMakeLists.txt5
-rw-r--r--src/webenginewidgets/api/qwebengineview.cpp126
-rw-r--r--src/webenginewidgets/api/qwebengineview.h7
-rw-r--r--src/webenginewidgets/api/qwebengineview_p.h8
10 files changed, 185 insertions, 232 deletions
diff --git a/src/core/api/CMakeLists.txt b/src/core/api/CMakeLists.txt
index bf2008ebd..4074bdb51 100644
--- a/src/core/api/CMakeLists.txt
+++ b/src/core/api/CMakeLists.txt
@@ -2,7 +2,7 @@ if(NOT DEFINED WEBENGINE_ROOT_SOURCE_DIR)
get_filename_component(WEBENGINE_ROOT_SOURCE_DIR "${CMAKE_CURRENT_LIST_DIR}/../../.." REALPATH)
endif()
find_package(Qt6 ${PROJECT_VERSION} REQUIRED COMPONENTS Gui Network OpenGL Quick)
-find_package(Qt6 ${PROJECT_VERSION} QUIET OPTIONAL_COMPONENTS PrintSupport WebChannel Positioning)
+find_package(Qt6 ${PROJECT_VERSION} QUIET OPTIONAL_COMPONENTS WebChannel Positioning)
include(${WEBENGINE_ROOT_SOURCE_DIR}/cmake/Functions.cmake)
get_configure_mode(configureMode)
@@ -65,10 +65,6 @@ qt_skip_warnings_are_errors(WebEngineCore)
make_install_only(WebEngineCore)
make_config_for_gn(WebEngineCore gn_config)
-qt_internal_extend_target(WebEngineCore CONDITION QT_FEATURE_webengine_printing_and_pdf
- PUBLIC_LIBRARIES
- Qt::PrintSupport
-)
qt_internal_extend_target(WebEngineCore CONDITION QT_FEATURE_webengine_webchannel
PUBLIC_LIBRARIES
Qt::WebChannel
diff --git a/src/core/api/qwebenginepage.cpp b/src/core/api/qwebenginepage.cpp
index 548457349..f04a0943c 100644
--- a/src/core/api/qwebenginepage.cpp
+++ b/src/core/api/qwebenginepage.cpp
@@ -48,9 +48,6 @@
#include "find_text_helper.h"
#include "file_picker_controller.h"
#include "javascript_dialog_controller.h"
-#if QT_CONFIG(webengine_printing_and_pdf)
-#include "printing/printer_worker.h"
-#endif
#include "qwebenginecertificateerror.h"
#include "qwebenginefindtextresult.h"
#include "qwebenginefullscreenrequest.h"
@@ -79,13 +76,10 @@
#include <QIcon>
#include <QLoggingCategory>
#include <QMimeData>
-#if QT_CONFIG(webengine_printing_and_pdf)
-#include <QPrinter>
-#include <QThread>
-#endif
#include <QTimer>
#include <QUrl>
+
QT_BEGIN_NAMESPACE
using namespace QtWebEngineCore;
@@ -182,9 +176,6 @@ QWebEnginePagePrivate::QWebEnginePagePrivate(QWebEngineProfile *_profile)
, webChannelWorldId(QWebEngineScript::MainWorld)
, defaultAudioMuted(false)
, defaultZoomFactor(1.0)
-#if QT_CONFIG(webengine_printing_and_pdf)
- , currentPrinter(nullptr)
-#endif
{
memset(actions, 0, sizeof(actions));
@@ -340,8 +331,8 @@ void QWebEnginePagePrivate::loadFinished(bool success, const QUrl &url, bool isE
void QWebEnginePagePrivate::didPrintPageToPdf(const QString &filePath, bool success)
{
- Q_Q(QWebEnginePage);
- Q_EMIT q->pdfPrintingFinished(filePath, success);
+ if (view)
+ view->didPrintPageToPdf(filePath, success);
}
void QWebEnginePagePrivate::focusContainer()
@@ -486,38 +477,8 @@ void QWebEnginePagePrivate::didFetchDocumentInnerText(quint64 requestId, const Q
void QWebEnginePagePrivate::didPrintPage(quint64 requestId, QSharedPointer<QByteArray> result)
{
-#if QT_CONFIG(webengine_printing_and_pdf)
- Q_Q(QWebEnginePage);
-
- // If no currentPrinter is set that means that were printing to PDF only.
- if (!currentPrinter) {
- if (!result.data())
- return;
- m_callbacks.invoke(requestId, *(result.data()));
- return;
- }
-
- QThread *printerThread = new QThread;
- QObject::connect(printerThread, &QThread::finished, printerThread, &QThread::deleteLater);
- printerThread->start();
-
- PrinterWorker *printerWorker = new PrinterWorker(result, currentPrinter);
- QObject::connect(printerWorker, &PrinterWorker::resultReady, q, [requestId, this](bool success) {
- currentPrinter = nullptr;
- m_callbacks.invoke(requestId, success);
- });
-
- QObject::connect(printerWorker, &PrinterWorker::resultReady, printerThread, &QThread::quit);
- QObject::connect(printerThread, &QThread::finished, printerWorker, &PrinterWorker::deleteLater);
-
- printerWorker->moveToThread(printerThread);
- QMetaObject::invokeMethod(printerWorker, "print");
-
-#else
- // we should never enter this branch, but just for safe-keeping...
- Q_UNUSED(result);
- m_callbacks.invoke(requestId, QByteArray());
-#endif
+ if (view)
+ view->didPrintPage(requestId, result);
}
bool QWebEnginePagePrivate::passOnFocus(bool reverse)
@@ -780,15 +741,6 @@ QWebEnginePage::QWebEnginePage(QObject* parent)
\sa findText()
*/
-/*!
- \fn void QWebEnginePage::printRequested()
- \since 5.12
-
- This signal is emitted when the JavaScript \c{window.print()} method is called.
- Typically, the signal handler can simply call printToPdf().
-
- \sa printToPdf()
-*/
/*!
\enum QWebEnginePage::RenderProcessTerminationStatus
@@ -854,19 +806,6 @@ QWebEnginePage::QWebEnginePage(QObject* parent)
*/
/*!
- \fn void QWebEnginePage::pdfPrintingFinished(const QString &filePath, bool success)
- \since 5.9
-
- This signal is emitted when printing the web page into a PDF file has
- finished.
- \a filePath will contain the path the file was requested to be created
- at, and \a success will be \c true if the file was successfully created and
- \c false otherwise.
-
- \sa printToPdf()
-*/
-
-/*!
\property QWebEnginePage::scrollPosition
\since 5.7
@@ -1752,10 +1691,8 @@ void QWebEnginePagePrivate::setToolTip(const QString &toolTipText)
void QWebEnginePagePrivate::printRequested()
{
- Q_Q(QWebEnginePage);
- QTimer::singleShot(0, q, [q](){
- Q_EMIT q->printRequested();
- });
+ if (view)
+ view->printRequested();
}
void QWebEnginePagePrivate::lifecycleStateChanged(LifecycleState state)
@@ -2268,115 +2205,6 @@ QSizeF QWebEnginePage::contentsSize() const
}
/*!
- Renders the current content of the page into a PDF document and saves it
- in the location specified in \a filePath.
- The page size and orientation of the produced PDF document are taken from
- the values specified in \a pageLayout.
-
- This method issues an asynchronous request for printing the web page into
- a PDF and returns immediately.
- To be informed about the result of the request, connect to the signal
- pdfPrintingFinished().
-
- If a file already exists at the provided file path, it will be overwritten.
- \since 5.7
- \sa pdfPrintingFinished()
-*/
-void QWebEnginePage::printToPdf(const QString &filePath, const QPageLayout &pageLayout)
-{
-#if QT_CONFIG(webengine_printing_and_pdf)
- Q_D(const QWebEnginePage);
- if (d->currentPrinter) {
- qWarning("Cannot print to PDF while at the same time printing on printer %ls", qUtf16Printable(d->currentPrinter->printerName()));
- return;
- }
- d->ensureInitialized();
- d->adapter->printToPDF(pageLayout, filePath);
-#else
- Q_UNUSED(filePath);
- Q_UNUSED(pageLayout);
-#endif
-}
-
-
-/*!
- Renders the current content of the page into a PDF document and returns a byte array containing the PDF data
- as parameter to \a resultCallback.
- The page size and orientation of the produced PDF document are taken from the values specified in \a pageLayout.
-
- The \a resultCallback must take a const reference to a QByteArray as parameter. If printing was successful, this byte array
- will contain the PDF data, otherwise, the byte array will be empty.
-
- \warning We guarantee that the callback (\a resultCallback) is always called, but it might be done
- during page destruction. When QWebEnginePage is deleted, the callback is triggered with an invalid
- value and it is not safe to use the corresponding QWebEnginePage or QWebEngineView instance inside it.
-
- \since 5.7
-*/
-void QWebEnginePage::printToPdf(const QWebEngineCallback<const QByteArray&> &resultCallback, const QPageLayout &pageLayout)
-{
- Q_D(QWebEnginePage);
-#if QT_CONFIG(webengine_printing_and_pdf)
- if (d->currentPrinter) {
- qWarning("Cannot print to PDF while at the same time printing on printer %ls", qUtf16Printable(d->currentPrinter->printerName()));
- d->m_callbacks.invokeEmpty(resultCallback);
- return;
- }
- d->ensureInitialized();
- quint64 requestId = d->adapter->printToPDFCallbackResult(pageLayout);
- d->m_callbacks.registerCallback(requestId, resultCallback);
-#else
- Q_UNUSED(pageLayout);
- d->m_callbacks.invokeEmpty(resultCallback);
-#endif
-}
-
-/*!
- Renders the current content of the page into a temporary PDF document, then prints it using \a printer.
-
- The settings for creating and printing the PDF document will be retrieved from the \a printer
- object.
- It is the users responsibility to ensure the \a printer remains valid until \a resultCallback
- has been called.
-
- \note Printing runs on the browser process, which is by default not sandboxed.
-
- The \a resultCallback must take a boolean as parameter. If printing was successful, this
- boolean will have the value \c true, otherwise, its value will be \c false.
-
- \warning We guarantee that the callback (\a resultCallback) is always called, but it might be done
- during page destruction. When QWebEnginePage is deleted, the callback is triggered with an invalid
- value and it is not safe to use the corresponding QWebEnginePage or QWebEngineView instance inside it.
-
- \note This function rasterizes the result when rendering onto \a printer. Please consider raising
- the default resolution of \a printer to at least 300 DPI or using printToPdf() to produce
- PDF file output more effectively.
-
- \since 5.8
-*/
-void QWebEnginePage::print(QPrinter *printer, const QWebEngineCallback<bool> &resultCallback)
-{
- Q_D(QWebEnginePage);
-#if QT_CONFIG(webengine_printing_and_pdf)
- if (d->currentPrinter) {
- qWarning("Cannot print page on printer %ls: Already printing on %ls.", qUtf16Printable(printer->printerName()), qUtf16Printable(d->currentPrinter->printerName()));
- d->m_callbacks.invokeDirectly(resultCallback, false);
- return;
- }
- d->currentPrinter = printer;
- d->ensureInitialized();
- quint64 requestId = d->adapter->printToPDFCallbackResult(printer->pageLayout(),
- printer->colorMode() == QPrinter::Color,
- false);
- d->m_callbacks.registerCallback(requestId, resultCallback);
-#else
- Q_UNUSED(printer);
- d->m_callbacks.invokeDirectly(resultCallback, false);
-#endif
-}
-
-
-/*!
\fn void QWebEnginePage::newWindowRequested(WebEngineNewViewRequest &request)
\since 6.2
diff --git a/src/core/api/qwebenginepage.h b/src/core/api/qwebenginepage.h
index c0c970207..94a78aa67 100644
--- a/src/core/api/qwebenginepage.h
+++ b/src/core/api/qwebenginepage.h
@@ -55,7 +55,6 @@
QT_BEGIN_NAMESPACE
class QMenu;
-class QPrinter;
class QContextMenuBuilder;
class QWebChannel;
@@ -302,10 +301,6 @@ public:
bool recentlyAudible() const;
qint64 renderProcessPid() const;
- void printToPdf(const QString &filePath, const QPageLayout &layout = QPageLayout(QPageSize(QPageSize::A4), QPageLayout::Portrait, QMarginsF()));
- void printToPdf(const QWebEngineCallback<const QByteArray&> &resultCallback, const QPageLayout &layout = QPageLayout(QPageSize(QPageSize::A4), QPageLayout::Portrait, QMarginsF()));
- void print(QPrinter *printer, const QWebEngineCallback<bool> &resultCallback);
-
void setInspectedPage(QWebEnginePage *page);
QWebEnginePage *inspectedPage() const;
void setDevToolsPage(QWebEnginePage *page);
@@ -360,9 +355,6 @@ Q_SIGNALS:
void recentlyAudibleChanged(bool recentlyAudible);
void renderProcessPidChanged(qint64 pid);
- void pdfPrintingFinished(const QString &filePath, bool success);
- void printRequested();
-
void visibleChanged(bool visible);
void lifecycleStateChanged(LifecycleState state);
diff --git a/src/core/api/qwebenginepage_p.h b/src/core/api/qwebenginepage_p.h
index d2c246397..a830028f8 100644
--- a/src/core/api/qwebenginepage_p.h
+++ b/src/core/api/qwebenginepage_p.h
@@ -104,6 +104,9 @@ public:
virtual void unhandledKeyEvent(QKeyEvent *event) = 0;
virtual bool passOnFocus(bool reverse) = 0;
virtual QObject *accessibilityParentObject() = 0;
+ virtual void didPrintPage(quint64 requestId, QSharedPointer<QByteArray> result) = 0;
+ virtual void didPrintPageToPdf(const QString &filePath, bool success) = 0;
+ virtual void printRequested() = 0;
};
class Q_WEBENGINECORE_PRIVATE_EXPORT QWebEnginePagePrivate : public QtWebEngineCore::WebContentsAdapterClient
@@ -225,9 +228,6 @@ public:
mutable QtWebEngineCore::CallbackDirectory m_callbacks;
mutable QAction *actions[QWebEnginePage::WebActionCount];
-#if QT_CONFIG(webengine_printing_and_pdf)
- QPrinter *currentPrinter;
-#endif
};
QT_END_NAMESPACE
diff --git a/src/core/printing/printer_worker.cpp b/src/core/printing/printer_worker.cpp
index cbd6b8da3..411e326c3 100644
--- a/src/core/printing/printer_worker.cpp
+++ b/src/core/printing/printer_worker.cpp
@@ -42,12 +42,12 @@
#include "printing/pdfium_document_wrapper_qt.h"
#include <QPainter>
-#include <QPrinter>
+#include <QPagedPaintDevice>
namespace QtWebEngineCore {
-PrinterWorker::PrinterWorker(QSharedPointer<QByteArray> data, QPrinter *printer)
- : m_data(data), m_printer(printer)
+PrinterWorker::PrinterWorker(QSharedPointer<QByteArray> data, QPagedPaintDevice *device)
+ : m_data(data), m_device(device)
{
}
@@ -56,16 +56,16 @@ PrinterWorker::~PrinterWorker() { }
void PrinterWorker::print()
{
if (!m_data->size()) {
- qWarning("Failure to print on printer %ls: Print result data is empty.",
- qUtf16Printable(m_printer->printerName()));
+ qWarning("Failed to print: Print result data is empty.");
Q_EMIT resultReady(false);
return;
}
PdfiumDocumentWrapperQt pdfiumWrapper(m_data->constData(), m_data->size());
- int toPage = m_printer->toPage();
- int fromPage = m_printer->fromPage();
+ const QPageRanges ranges = m_device->pageRanges();
+ int toPage = ranges.firstPage();
+ int fromPage = ranges.lastPage();
bool ascendingOrder = true;
if (fromPage == 0 && toPage == 0) {
@@ -75,62 +75,50 @@ void PrinterWorker::print()
fromPage = qMax(1, fromPage);
toPage = qMin(pdfiumWrapper.pageCount(), toPage);
- if (m_printer->pageOrder() == QPrinter::LastPageFirst) {
+ if (!m_firstPageFirst) {
qSwap(fromPage, toPage);
ascendingOrder = false;
}
int pageCopies = 1;
- int documentCopies = 1;
-
- if (!m_printer->supportsMultipleCopies())
- documentCopies = m_printer->copyCount();
-
- if (m_printer->collateCopies()) {
- pageCopies = documentCopies;
- documentCopies = 1;
+ if (m_collateCopies) {
+ pageCopies = m_documentCopies;
+ m_documentCopies = 1;
}
- qreal resolution = m_printer->resolution() / 72.0; // pdfium uses points so 1/72 inch
+ qreal resolution = m_deviceResolution / 72.0; // pdfium uses points so 1/72 inch
QPainter painter;
- for (int printedDocuments = 0; printedDocuments < documentCopies; printedDocuments++) {
+ for (int printedDocuments = 0; printedDocuments < m_documentCopies; printedDocuments++) {
if (printedDocuments > 0)
- m_printer->newPage();
+ m_device->newPage();
int currentPageIndex = fromPage;
for (int i = 0; true; i++) {
QSizeF documentSize = (pdfiumWrapper.pageSize(currentPageIndex - 1) * resolution);
bool isLandscape = documentSize.width() > documentSize.height();
- m_printer->setPageOrientation(isLandscape ? QPageLayout::Landscape
+ m_device->setPageOrientation(isLandscape ? QPageLayout::Landscape
: QPageLayout::Portrait);
- QRectF pageRect = m_printer->pageRect(QPrinter::DevicePixel);
+ QRectF pageRect = m_device->pageLayout().pageSize().rectPixels(m_deviceResolution);
documentSize = documentSize.scaled(pageRect.size(), Qt::KeepAspectRatio);
// setPageOrientation has to be called before qpainter.begin() or before
// qprinter.newPage() so correct metrics is used, therefore call begin now for only
// first page
- if (!painter.isActive() && !painter.begin(m_printer)) {
- qWarning("Failure to print on printer %ls: Could not open printer for painting.",
- qUtf16Printable(m_printer->printerName()));
+ if (!painter.isActive() && !painter.begin(m_device)) {
+ qWarning("Failure to print on device: Could not open printer for painting.");
Q_EMIT resultReady(false);
return;
}
if (i > 0)
- m_printer->newPage();
+ m_device->newPage();
for (int printedPages = 0; printedPages < pageCopies; printedPages++) {
- if (m_printer->printerState() == QPrinter::Aborted
- || m_printer->printerState() == QPrinter::Error) {
- Q_EMIT resultReady(false);
- return;
- }
-
if (printedPages > 0)
- m_printer->newPage();
+ m_device->newPage();
QImage currentImage = pdfiumWrapper.pageAsQImage(
currentPageIndex - 1, documentSize.width(), documentSize.height());
diff --git a/src/core/printing/printer_worker.h b/src/core/printing/printer_worker.h
index 9d1192bd2..3681312a9 100644
--- a/src/core/printing/printer_worker.h
+++ b/src/core/printing/printer_worker.h
@@ -51,12 +51,12 @@
#ifndef PRINTER_WORKER_H
#define PRINTER_WORKER_H
-#include "qtwebenginecoreglobal_p.h"
+#include <QtWebEngineCore/private/qtwebenginecoreglobal_p.h>
#include <QSharedPointer>
QT_BEGIN_NAMESPACE
-class QPrinter;
+class QPagedPaintDevice;
QT_END_NAMESPACE
namespace QtWebEngineCore {
@@ -65,9 +65,14 @@ class Q_WEBENGINECORE_PRIVATE_EXPORT PrinterWorker : public QObject
{
Q_OBJECT
public:
- PrinterWorker(QSharedPointer<QByteArray> data, QPrinter *printer);
+ PrinterWorker(QSharedPointer<QByteArray> data, QPagedPaintDevice *device);
virtual ~PrinterWorker();
+ int m_deviceResolution;
+ bool m_firstPageFirst;
+ int m_documentCopies;
+ bool m_collateCopies;
+
public Q_SLOTS:
void print();
@@ -78,7 +83,7 @@ private:
Q_DISABLE_COPY(PrinterWorker)
QSharedPointer<QByteArray> m_data;
- QPrinter *m_printer;
+ QPagedPaintDevice *m_device;
};
} // namespace QtWebEngineCore
diff --git a/src/webenginewidgets/CMakeLists.txt b/src/webenginewidgets/CMakeLists.txt
index f37948c8c..425eb1d73 100644
--- a/src/webenginewidgets/CMakeLists.txt
+++ b/src/webenginewidgets/CMakeLists.txt
@@ -29,3 +29,8 @@ qt_internal_add_module(WebEngineWidgets
Qt::WebEngineCore
)
make_install_only(WebEngineWidgets)
+
+qt_internal_extend_target(WebEngineWidgets CONDITION QT_FEATURE_webengine_printing_and_pdf
+ PUBLIC_LIBRARIES
+ Qt::PrintSupport
+)
diff --git a/src/webenginewidgets/api/qwebengineview.cpp b/src/webenginewidgets/api/qwebengineview.cpp
index 9ce954e06..a34c841e3 100644
--- a/src/webenginewidgets/api/qwebengineview.cpp
+++ b/src/webenginewidgets/api/qwebengineview.cpp
@@ -80,6 +80,13 @@
#include <QStyle>
#include <QGuiApplication>
+#if QT_CONFIG(webengine_printing_and_pdf)
+#include "printing/printer_worker.h"
+
+#include <QPrinter>
+#include <QThread>
+#endif
+
QT_BEGIN_NAMESPACE
void QWebEngineViewPrivate::pageChanged(QWebEnginePage *oldPage, QWebEnginePage *newPage)
@@ -344,7 +351,13 @@ static QAccessibleInterface *webAccessibleFactory(const QString &, QObject *obje
#endif // QT_NO_ACCESSIBILITY
QWebEngineViewPrivate::QWebEngineViewPrivate()
- : page(0), m_dragEntered(false), m_ownsPage(false), m_contextRequest(nullptr)
+ : page(0)
+ , m_dragEntered(false)
+ , m_ownsPage(false)
+ , m_contextRequest(nullptr)
+#if QT_CONFIG(webengine_printing_and_pdf)
+ , currentPrinter(nullptr)
+#endif
{
#ifndef QT_NO_ACCESSIBILITY
QAccessible::installFactory(&webAccessibleFactory);
@@ -495,6 +508,61 @@ QObject *QWebEngineViewPrivate::accessibilityParentObject()
return q;
}
+void QWebEngineViewPrivate::didPrintPage(quint64 requestId, QSharedPointer<QByteArray> result)
+{
+#if QT_CONFIG(webengine_printing_and_pdf)
+ Q_Q(QWebEngineView);
+
+ // If no currentPrinter is set that means that were printing to PDF only.
+ if (!currentPrinter) {
+ if (!result.data())
+ return;
+ page->d_ptr->m_callbacks.invoke(requestId, *(result.data()));
+ return;
+ }
+
+ QThread *printerThread = new QThread;
+ QObject::connect(printerThread, &QThread::finished, printerThread, &QThread::deleteLater);
+ printerThread->start();
+
+ QtWebEngineCore::PrinterWorker *printerWorker = new QtWebEngineCore::PrinterWorker(result, currentPrinter);
+ printerWorker->m_deviceResolution = currentPrinter->resolution();
+ printerWorker->m_firstPageFirst = currentPrinter->pageOrder() == QPrinter::FirstPageFirst;
+ printerWorker->m_documentCopies = currentPrinter->copyCount();
+ printerWorker->m_collateCopies = currentPrinter->collateCopies();
+
+ QObject::connect(printerWorker, &QtWebEngineCore::PrinterWorker::resultReady, q, [requestId, this](bool success) {
+ currentPrinter = nullptr;
+ page->d_ptr->m_callbacks.invoke(requestId, success);
+ });
+
+ QObject::connect(printerWorker, &QtWebEngineCore::PrinterWorker::resultReady, printerThread, &QThread::quit);
+ QObject::connect(printerThread, &QThread::finished, printerWorker, &QtWebEngineCore::PrinterWorker::deleteLater);
+
+ printerWorker->moveToThread(printerThread);
+ QMetaObject::invokeMethod(printerWorker, "print");
+
+#else
+ // we should never enter this branch, but just for safe-keeping...
+ Q_UNUSED(result);
+ page->d_ptr->m_callbacks.invoke(requestId, QByteArray());
+#endif
+}
+
+void QWebEngineViewPrivate::didPrintPageToPdf(const QString &filePath, bool success)
+{
+ Q_Q(QWebEngineView);
+ Q_EMIT q->pdfPrintingFinished(filePath, success);
+}
+
+void QWebEngineViewPrivate::printRequested()
+{
+ Q_Q(QWebEngineView);
+ QTimer::singleShot(0, q, [q]() {
+ Q_EMIT q->printRequested();
+ });
+}
+
bool QWebEngineViewPrivate::isVisible() const
{
Q_Q(const QWebEngineView);
@@ -878,6 +946,62 @@ QWebEngineContextMenuRequest *QWebEngineView::lastContextMenuRequest() const
return d->m_contextRequest;
}
+void QWebEngineView::printToPdf(const QString &filePath, const QPageLayout &layout)
+{
+#if QT_CONFIG(webengine_printing_and_pdf)
+ Q_D(QWebEngineView);
+ if (d->currentPrinter) {
+ qWarning("Cannot print to PDF while printing at the same time.");
+ return;
+ }
+ page()->d_ptr->ensureInitialized();
+ page()->d_ptr->adapter->printToPDF(layout, filePath);
+#else
+ Q_UNUSED(filePath);
+ Q_UNUSED(layout);
+#endif
+}
+
+void QWebEngineView::printToPdf(const QWebEngineCallback<const QByteArray&> &resultCallback, const QPageLayout &layout)
+{
+#if QT_CONFIG(webengine_printing_and_pdf)
+ Q_D(QWebEngineView);
+ if (d->currentPrinter) {
+ qWarning("Cannot print to PDF while printing at the same time.");
+ page()->d_ptr->m_callbacks.invokeEmpty(resultCallback);
+ return;
+ }
+ page()->d_ptr->ensureInitialized();
+ quint64 requestId = page()->d_ptr->adapter->printToPDFCallbackResult(layout);
+ page()->d_ptr->m_callbacks.registerCallback(requestId, resultCallback);
+#else
+ Q_UNUSED(layout);
+ page()->d_ptr->m_callbacks.invokeEmpty(resultCallback);
+#endif
+}
+
+void QWebEngineView::print(QPrinter *printer, const QWebEngineCallback<bool> &resultCallback)
+{
+#if QT_CONFIG(webengine_printing_and_pdf)
+ Q_D(QWebEngineView);
+ if (d->currentPrinter) {
+ qWarning("Cannot print page on printer %ls: Already printing on a device.", qUtf16Printable(printer->printerName()));
+ page()->d_ptr->m_callbacks.invokeDirectly(resultCallback, false);
+ return;
+ }
+
+ d->currentPrinter = printer;
+ page()->d_ptr->ensureInitialized();
+ quint64 requestId = page()->d_ptr->adapter->printToPDFCallbackResult(printer->pageLayout(),
+ printer->colorMode() == QPrinter::Color,
+ false);
+ page()->d_ptr->m_callbacks.registerCallback(requestId, resultCallback);
+#else
+ Q_UNUSED(printer);
+ page()->d_ptr->m_callbacks.invokeDirectly(resultCallback, false);
+#endif
+}
+
#ifndef QT_NO_ACCESSIBILITY
bool QWebEngineViewAccessible::isValid() const
{
diff --git a/src/webenginewidgets/api/qwebengineview.h b/src/webenginewidgets/api/qwebengineview.h
index d7f9d6a45..136df0b93 100644
--- a/src/webenginewidgets/api/qwebengineview.h
+++ b/src/webenginewidgets/api/qwebengineview.h
@@ -51,6 +51,7 @@
QT_BEGIN_NAMESPACE
class QContextMenuEvent;
+class QPrinter;
class QUrl;
class QWebEnginePage;
class QWebEngineSettings;
@@ -107,6 +108,10 @@ public:
#endif
QWebEngineContextMenuRequest *lastContextMenuRequest() const;
+ void printToPdf(const QString &filePath, const QPageLayout &layout = QPageLayout(QPageSize(QPageSize::A4), QPageLayout::Portrait, QMarginsF()));
+ void printToPdf(const QWebEngineCallback<const QByteArray&> &resultCallback, const QPageLayout &layout = QPageLayout(QPageSize(QPageSize::A4), QPageLayout::Portrait, QMarginsF()));
+ void print(QPrinter *printer, const QWebEngineCallback<bool> &resultCallback);
+
public Q_SLOTS:
void stop();
void back();
@@ -124,6 +129,8 @@ Q_SIGNALS:
void iconChanged(const QIcon&);
void renderProcessTerminated(QWebEnginePage::RenderProcessTerminationStatus terminationStatus,
int exitCode);
+ void pdfPrintingFinished(const QString &filePath, bool success);
+ void printRequested();
protected:
virtual QWebEngineView *createWindow(QWebEnginePage::WebWindowType type);
diff --git a/src/webenginewidgets/api/qwebengineview_p.h b/src/webenginewidgets/api/qwebengineview_p.h
index 40f195522..71e7d04f7 100644
--- a/src/webenginewidgets/api/qwebengineview_p.h
+++ b/src/webenginewidgets/api/qwebengineview_p.h
@@ -58,6 +58,7 @@
#include <QtWidgets/qaccessiblewidget.h>
namespace QtWebEngineCore {
+class QPrinter;
class RenderWidgetHostViewQtDelegateWidget;
class RenderWidgetHostViewQtDelegate;
}
@@ -92,6 +93,10 @@ public:
QWebEngineContextMenuRequest *lastContextMenuRequest() const override;
QWebEnginePage *createPageForWindow(QWebEnginePage::WebWindowType type) override;
QObject *accessibilityParentObject() override;
+ void didPrintPage(quint64 requestId, QSharedPointer<QByteArray> result) override;
+ void didPrintPageToPdf(const QString &filePath, bool success) override;
+ void printRequested() override;
+
QWebEngineViewPrivate();
virtual ~QWebEngineViewPrivate();
static void bindPageAndView(QWebEnginePage *page, QWebEngineView *view);
@@ -108,6 +113,9 @@ public:
bool m_dragEntered;
mutable bool m_ownsPage;
QWebEngineContextMenuRequest *m_contextRequest;
+#if QT_CONFIG(webengine_printing_and_pdf)
+ QPrinter *currentPrinter;
+#endif
};
#ifndef QT_NO_ACCESSIBILITY