Estoy haciendo una aplicación en PyQt5 que implica mostrar un PDF usando QWebEngineView y PDF.js de Mozilla.
Puedo mostrar el PDF sin problemas, pero no puedo averiguar cómo:
He probado las numerosas opciones de otras publicaciones de Stackoverflow que implican el uso self.runJavaScript() para cambiarlo, pero siempre da como resultado "No se puede establecer la propiedad de indefinido" o "El objeto es NoneType".
Aquí está mi método:
def load_file(self, file, page=0) -> None: url = QtCore.QUrl().fromLocalFile(os.path.abspath("./pdfjs/web/viewer.html")) query = QtCore.QUrlQuery() query.addQueryItem("file", os.path.normpath(os.path.abspath(file))) url.setQuery(query) self.pdf_view.load(url) donde self.pdf_view es QWebEngineView.
Agradecería cualquier ayuda sobre cómo lograr esto.
EDITAR: Pude especificar la página en la carga con el símbolo # , pero en cuanto a cambiar la página sin volver a cargar todo, todavía lo desconozco.
El visor PDF.js carga algunos scripts que crean un objeto PDFViewer con todas las propiedades necesarias para navegar por las páginas mediante programación. Entonces, solo necesita ejecutar un javascript simple en la página principal del visor para obtener la funcionalidad que necesita. Para hacer que las cosas sean un poco más agradables para trabajar, también es útil proporcionar una forma de ejecutar javascript sincrónicamente para que se pueda acceder a los valores devueltos más fácilmente.
A continuación se muestra una demostración de trabajo simple que implementa eso (solo probado en Linux). Esperemos que quede claro cómo adaptarlo para que funcione con su propia aplicación:
import sys, os from PyQt5 import QtCore, QtWidgets, QtWebEngineWidgets # PDFJS = '/usr/share/pdf.js/web/viewer.html' PDFJS = './pdfjs/web/viewer.html' class Window(QtWidgets.QWidget): def __init__(self): super().__init__() self.buttonNext = QtWidgets.QPushButton('Next Page') self.buttonNext.clicked.connect(lambda: self.changePage(+1)) self.buttonPrev = QtWidgets.QPushButton('Previous Page') self.buttonPrev.clicked.connect(lambda: self.changePage(-1)) self.viewer = QtWebEngineWidgets.QWebEngineView() layout = QtWidgets.QGridLayout(self) layout.addWidget(self.viewer, 0, 0, 1, 2) layout.addWidget(self.buttonPrev, 1, 0) layout.addWidget(self.buttonNext, 1, 1) def loadFile(self, file): url = QtCore.QUrl.fromLocalFile(os.path.abspath(PDFJS)) query = QtCore.QUrlQuery() query.addQueryItem('file', os.path.abspath(file)) url.setQuery(query) self.viewer.load(url) def execJavaScript(self, script): result = None def callback(data): nonlocal result result = data loop.quit() loop = QtCore.QEventLoop() QtCore.QTimer.singleShot( 0, lambda: self.viewer.page().runJavaScript(script, callback)) loop.exec() return result def changePage(self, delta): page = self.execJavaScript( 'PDFViewerApplication.pdfViewer.currentPageNumber') self.setCurrentPage(page + int(delta)) def setCurrentPage(self, page): count = self.execJavaScript( 'PDFViewerApplication.pdfViewer.pagesCount') if 1 <= page <= count: self.execJavaScript( f'PDFViewerApplication.pdfViewer.currentPageNumber = {page}') if __name__ == '__main__': app = QtWidgets.QApplication(sys.argv) window = Window() if len(sys.argv) > 1: window.loadFile(sys.argv[1]) window.setGeometry(600, 50, 800, 600) window.show() sys.exit(app.exec_())