Search code examples
pythonpyqtpyqt5qtwebengineqprinter

how to print html page with image in Qprinter pyqt5


i have generated a report for my program using html code but it doesn't show image in Qprinter.

def run(self):
    view = QtWebEngineWidgets.QWebEngineView()
    view.setHtml("""<img src="header.jpeg" alt="logo" width="280" height="100">""")
    printer = QPrinter()
    printer.setPaperSize(QtCore.QSizeF(80 ,297), QPrinter.Millimeter)
    try :
        r = QPrintDialog(printer)
        if r.exec_() == QPrintDialog.Accepted:
            view.page().print(printer, self.print_completed)
    except Exception as e :
        print(e)

html code that i want to print . the header.jpeg in same directory .


Solution

  • Qt Webengine executes the tasks asynchronously as printing, and since view and printer are local variables they will be eliminated when the synchro function is finished. The solution is to keep those objects even when you finish running.

    Not necessary to use QWebEngineView since you will not show anything, just QWebEnginePage.

    On the other hand the docs states that external resources such as images are loaded based on the URL that is passed second parameter. So the solution is to pass a url using the current directory as a basis.

    import os
    # ...
    def run(self):
        current_dir = os.path.dirname(os.path.abspath(__file__))
        self._page = QtWebEngineWidgets.QWebEnginePage()
        self._page.setHtml('''
        ... <img src="header.jpeg" alt="logo" width="280" height="100"> ...
        ''', QtCore.QUrl.fromLocalFile(os.path.join(current_dir, "index.html")))
        self._printer = QtPrintSupport.QPrinter()
        self._printer.setPaperSize(QtCore.QSizeF(80 ,297), QtPrintSupport.QPrinter.Millimeter)
        r = QtPrintSupport.QPrintDialog(self._printer)
        if r.exec_() == QtPrintSupport.QPrintDialog.Accepted:
            self._page.print(self._printer, self.print_completed)