由于 QTextDocument 仅支持 HTML4 属性的子集,因此会导致观察到的错误。
一种解决方法是使用在 Qt 6.2 中重新引入的 QtWebEngine。目前只有 windows .whl 在 pypi 中可用(请参阅 here 和 here 了解更多信息),因此我们可以安装您必须执行的 Linux 和 MacOs 包:
python -m pip install pyside6 \
--index-url=http://download.qt.io/official_releases/QtForPython
所以将my previous answer 翻译成 PySide6:
import os
from pathlib import Path
from PySide6.QtCore import (
QCoreApplication,
QEventLoop,
QObject,
QPointF,
Qt,
QUrl,
Slot,
)
from PySide6.QtGui import QKeySequence, QPainter, QShortcut
from PySide6.QtPrintSupport import QPrintDialog, QPrinter, QPrintPreviewDialog
from PySide6.QtWebEngineWidgets import QWebEngineView
from PySide6.QtWidgets import (
QApplication,
QDialog,
QProgressBar,
QProgressDialog,
)
CURRENT_DIRECTORY = Path(__file__).resolve().parent
class PrintHandler(QObject):
def __init__(self, parent=None):
super().__init__(parent)
self.m_page = None
self.m_inPrintPreview = False
def setPage(self, page):
assert not self.m_page
self.m_page = page
self.m_page.printRequested.connect(self.printPreview)
@Slot()
def print(self):
printer = QPrinter(QPrinter.HighResolution)
dialog = QPrintDialog(printer, QWebEngineView.forPage(self.m_page))
if dialog.exec_() != QDialog.Accepted:
return
self.printDocument(printer)
@Slot()
def printPreview(self):
if not self.m_page:
return
if self.m_inPrintPreview:
return
self.m_inPrintPreview = True
printer = QPrinter()
preview = QPrintPreviewDialog(printer, QWebEngineView.forPage(self.m_page))
preview.paintRequested.connect(self.printDocument)
preview.exec()
self.m_inPrintPreview = False
@Slot(QPrinter)
def printDocument(self, printer):
loop = QEventLoop()
result = False
def printPreview(success):
nonlocal result
result = success
loop.quit()
view = QWebEngineView.forPage(self.m_page)
view.printFinished.connect(printPreview)
progressbar = QProgressDialog(view)
progressbar.findChild(QProgressBar).setTextVisible(False)
progressbar.setLabelText("Wait please...")
progressbar.setRange(0, 0)
progressbar.show()
progressbar.canceled.connect(loop.quit)
view.print(printer)
loop.exec()
progressbar.close()
if not result:
painter = QPainter()
if painter.begin(printer):
font = painter.font()
font.setPixelSize(20)
painter.setFont(font)
painter.drawText(QPointF(10, 25), "Could not generate print preview.")
painter.end()
def main():
import sys
QCoreApplication.setAttribute(Qt.AA_EnableHighDpiScaling)
app = QApplication(sys.argv)
app.setApplicationName("Previewer")
filename = CURRENT_DIRECTORY / "template.html"
url = QUrl.fromLocalFile(os.fspath(filename))
view = QWebEngineView()
view.setUrl(url)
view.resize(1024, 750)
view.show()
handler = PrintHandler()
handler.setPage(view.page())
printPreviewShortCut = QShortcut(QKeySequence(Qt.CTRL + Qt.Key_P), view)
printShortCut = QShortcut(QKeySequence(Qt.CTRL + Qt.SHIFT + Qt.Key_P), view)
printPreviewShortCut.activated.connect(handler.printPreview)
printShortCut.activated.connect(handler.print)
sys.exit(app.exec())
if __name__ == "__main__":
main()
按下 Ctrl + P 后你会得到: