mirror of
https://github.com/kovidgoyal/calibre.git
synced 2025-07-09 03:04:10 -04:00
Fix a regression in 6.0 that broke rendering of first page of EPUB as cover when the EPUB has no actual cover
This commit is contained in:
parent
a41c3b775c
commit
ba8f4fb7ae
@ -89,7 +89,7 @@ def extract_calibre_cover(raw, base, log):
|
|||||||
return return_raster_image(img)
|
return return_raster_image(img)
|
||||||
|
|
||||||
|
|
||||||
def render_html_svg_workaround(path_to_html, log, width=590, height=750):
|
def render_html_svg_workaround(path_to_html, log, width=590, height=750, root=''):
|
||||||
from calibre.ebooks.oeb.base import SVG_NS
|
from calibre.ebooks.oeb.base import SVG_NS
|
||||||
with open(path_to_html, 'rb') as f:
|
with open(path_to_html, 'rb') as f:
|
||||||
raw = f.read()
|
raw = f.read()
|
||||||
@ -108,11 +108,11 @@ def render_html_svg_workaround(path_to_html, log, width=590, height=750):
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
if data is None:
|
if data is None:
|
||||||
data = render_html_data(path_to_html, width, height)
|
data = render_html_data(path_to_html, width, height, root=root)
|
||||||
return data
|
return data
|
||||||
|
|
||||||
|
|
||||||
def render_html_data(path_to_html, width, height):
|
def render_html_data(path_to_html, width, height, root=''):
|
||||||
from calibre.ptempfile import TemporaryDirectory
|
from calibre.ptempfile import TemporaryDirectory
|
||||||
from calibre.utils.ipc.simple_worker import fork_job, WorkerError
|
from calibre.utils.ipc.simple_worker import fork_job, WorkerError
|
||||||
result = {}
|
result = {}
|
||||||
@ -127,7 +127,7 @@ def render_html_data(path_to_html, width, height):
|
|||||||
|
|
||||||
with TemporaryDirectory('-render-html') as tdir:
|
with TemporaryDirectory('-render-html') as tdir:
|
||||||
try:
|
try:
|
||||||
result = fork_job('calibre.ebooks.render_html', 'main', args=(path_to_html, tdir, 'jpeg'))
|
result = fork_job('calibre.ebooks.render_html', 'main', args=(path_to_html, tdir, 'jpeg', root))
|
||||||
except WorkerError as e:
|
except WorkerError as e:
|
||||||
report_error(e.orig_tb)
|
report_error(e.orig_tb)
|
||||||
else:
|
else:
|
||||||
|
@ -218,7 +218,7 @@ class EPUBInput(InputFormatPlugin):
|
|||||||
elem[0].getparent(), OPF('item'), href=guide_elem.get('href'), id='calibre_raster_cover')
|
elem[0].getparent(), OPF('item'), href=guide_elem.get('href'), id='calibre_raster_cover')
|
||||||
t.set('media-type', 'image/jpeg')
|
t.set('media-type', 'image/jpeg')
|
||||||
if os.path.exists(guide_cover):
|
if os.path.exists(guide_cover):
|
||||||
renderer = render_html_svg_workaround(guide_cover, log)
|
renderer = render_html_svg_workaround(guide_cover, log, root=os.getcwd())
|
||||||
if renderer is not None:
|
if renderer is not None:
|
||||||
with lopen('calibre_raster_cover.jpg', 'wb') as f:
|
with lopen('calibre_raster_cover.jpg', 'wb') as f:
|
||||||
f.write(renderer)
|
f.write(renderer)
|
||||||
|
@ -146,16 +146,11 @@ class PDFOutput(OutputFormatPlugin):
|
|||||||
# Ensure Qt is setup to be used with WebEngine
|
# Ensure Qt is setup to be used with WebEngine
|
||||||
# specialize_options is called early enough in the pipeline
|
# specialize_options is called early enough in the pipeline
|
||||||
# that hopefully no Qt application has been constructed as yet
|
# that hopefully no Qt application has been constructed as yet
|
||||||
from qt.webengine import QWebEngineUrlScheme
|
|
||||||
from qt.webengine import QWebEnginePage # noqa
|
from qt.webengine import QWebEnginePage # noqa
|
||||||
from calibre.gui2 import must_use_qt
|
from calibre.gui2 import must_use_qt
|
||||||
from calibre.constants import FAKE_PROTOCOL
|
from calibre.utils.webengine import setup_fake_protocol, setup_default_profile
|
||||||
scheme = QWebEngineUrlScheme(FAKE_PROTOCOL.encode('ascii'))
|
setup_fake_protocol()
|
||||||
scheme.setSyntax(QWebEngineUrlScheme.Syntax.Host)
|
|
||||||
scheme.setFlags(QWebEngineUrlScheme.Flag.SecureScheme)
|
|
||||||
QWebEngineUrlScheme.registerScheme(scheme)
|
|
||||||
must_use_qt()
|
must_use_qt()
|
||||||
from calibre.utils.webengine import setup_default_profile
|
|
||||||
setup_default_profile()
|
setup_default_profile()
|
||||||
self.input_fmt = input_fmt
|
self.input_fmt = input_fmt
|
||||||
|
|
||||||
|
@ -193,7 +193,7 @@ def render_cover(cpage, zf, reader=None):
|
|||||||
cpage = os.path.join(tdir, cpage)
|
cpage = os.path.join(tdir, cpage)
|
||||||
if not os.path.exists(cpage):
|
if not os.path.exists(cpage):
|
||||||
return
|
return
|
||||||
return render_html_svg_workaround(cpage, default_log)
|
return render_html_svg_workaround(cpage, default_log, root=tdir)
|
||||||
|
|
||||||
|
|
||||||
def get_cover(raster_cover, first_spine_item, reader):
|
def get_cover(raster_cover, first_spine_item, reader):
|
||||||
|
@ -625,7 +625,7 @@ class OEBReader:
|
|||||||
writer = OEBWriter()
|
writer = OEBWriter()
|
||||||
writer(self.oeb, tdir)
|
writer(self.oeb, tdir)
|
||||||
path = os.path.join(tdir, unquote(hcover.href))
|
path = os.path.join(tdir, unquote(hcover.href))
|
||||||
data = render_html_svg_workaround(path, self.logger)
|
data = render_html_svg_workaround(path, self.logger, root=tdir)
|
||||||
if not data:
|
if not data:
|
||||||
data = b''
|
data = b''
|
||||||
id, href = self.oeb.manifest.generate('cover', 'cover.jpg')
|
id, href = self.oeb.manifest.generate('cover', 'cover.jpg')
|
||||||
|
@ -4,26 +4,88 @@
|
|||||||
|
|
||||||
import os
|
import os
|
||||||
import sys
|
import sys
|
||||||
|
|
||||||
from qt.core import (
|
from qt.core import (
|
||||||
QApplication, QMarginsF, QPageLayout, QPageSize, Qt, QTimer, QUrl
|
QApplication, QByteArray, QMarginsF, QPageLayout, QPageSize, Qt, QTimer, QUrl
|
||||||
|
)
|
||||||
|
from qt.webengine import (
|
||||||
|
QWebEnginePage, QWebEngineProfile, QWebEngineScript,
|
||||||
|
QWebEngineUrlRequestInterceptor, QWebEngineUrlRequestJob,
|
||||||
|
QWebEngineUrlSchemeHandler
|
||||||
)
|
)
|
||||||
from qt.webengine import QWebEnginePage, QWebEngineScript
|
|
||||||
|
|
||||||
|
from calibre.constants import FAKE_HOST, FAKE_PROTOCOL
|
||||||
from calibre.ebooks.metadata.pdf import page_images
|
from calibre.ebooks.metadata.pdf import page_images
|
||||||
|
from calibre.ebooks.oeb.polish.utils import guess_type
|
||||||
from calibre.gui2 import must_use_qt
|
from calibre.gui2 import must_use_qt
|
||||||
from calibre.utils.webengine import secure_webengine
|
from calibre.gui_launch import setup_qt_logging
|
||||||
from calibre.utils.filenames import atomic_rename
|
from calibre.utils.filenames import atomic_rename
|
||||||
|
from calibre.utils.logging import default_log
|
||||||
from calibre.utils.monotonic import monotonic
|
from calibre.utils.monotonic import monotonic
|
||||||
|
from calibre.utils.webengine import (
|
||||||
|
secure_webengine, send_reply, setup_fake_protocol, setup_profile
|
||||||
|
)
|
||||||
|
|
||||||
LOAD_TIMEOUT = 20
|
LOAD_TIMEOUT = 20
|
||||||
PRINT_TIMEOUT = 10
|
PRINT_TIMEOUT = 10
|
||||||
|
|
||||||
|
|
||||||
|
class RequestInterceptor(QWebEngineUrlRequestInterceptor):
|
||||||
|
|
||||||
|
def interceptRequest(self, request_info):
|
||||||
|
method = bytes(request_info.requestMethod())
|
||||||
|
if method not in (b'GET', b'HEAD'):
|
||||||
|
default_log.warn(f'Blocking URL request with method: {method}')
|
||||||
|
request_info.block(True)
|
||||||
|
return
|
||||||
|
qurl = request_info.requestUrl()
|
||||||
|
if qurl.scheme() not in (FAKE_PROTOCOL,):
|
||||||
|
default_log.warn(f'Blocking URL request {qurl.toString()} as it is not for a resource related to the HTML file being rendered')
|
||||||
|
request_info.block(True)
|
||||||
|
return
|
||||||
|
|
||||||
|
|
||||||
|
class UrlSchemeHandler(QWebEngineUrlSchemeHandler):
|
||||||
|
|
||||||
|
def __init__(self, root, parent=None):
|
||||||
|
self.root = root
|
||||||
|
super().__init__(parent)
|
||||||
|
self.allowed_hosts = (FAKE_HOST,)
|
||||||
|
|
||||||
|
def requestStarted(self, rq):
|
||||||
|
if bytes(rq.requestMethod()) != b'GET':
|
||||||
|
return self.fail_request(rq, QWebEngineUrlRequestJob.Error.RequestDenied)
|
||||||
|
url = rq.requestUrl()
|
||||||
|
host = url.host()
|
||||||
|
if host not in self.allowed_hosts or url.scheme() != FAKE_PROTOCOL:
|
||||||
|
return self.fail_request(rq)
|
||||||
|
path = url.path()
|
||||||
|
rp = path[1:]
|
||||||
|
if not rp:
|
||||||
|
return self.fail_request(rq, QWebEngineUrlRequestJob.Error.UrlNotFound)
|
||||||
|
resolved_path = os.path.abspath(os.path.join(self.root, rp.replace('/', os.sep)))
|
||||||
|
if not resolved_path.startswith(self.root):
|
||||||
|
return self.fail_request(rq, QWebEngineUrlRequestJob.Error.UrlNotFound)
|
||||||
|
|
||||||
|
try:
|
||||||
|
with open(resolved_path, 'rb') as f:
|
||||||
|
data = f.read()
|
||||||
|
except OSError as err:
|
||||||
|
default_log(f'Failed to read file: {rp} with error: {err}')
|
||||||
|
return self.fail_request(rq, QWebEngineUrlRequestJob.Error.RequestFailed)
|
||||||
|
|
||||||
|
send_reply(rq, guess_type(os.path.basename(resolved_path)), data)
|
||||||
|
|
||||||
|
def fail_request(self, rq, fail_code=None):
|
||||||
|
if fail_code is None:
|
||||||
|
fail_code = QWebEngineUrlRequestJob.Error.UrlNotFound
|
||||||
|
rq.fail(fail_code)
|
||||||
|
print(f"Blocking FAKE_PROTOCOL request: {rq.requestUrl().toString()} with code: {fail_code}", file=sys.stderr)
|
||||||
|
|
||||||
|
|
||||||
class Render(QWebEnginePage):
|
class Render(QWebEnginePage):
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self, profile):
|
||||||
QWebEnginePage.__init__(self)
|
QWebEnginePage.__init__(self, profile, QApplication.instance())
|
||||||
secure_webengine(self)
|
secure_webengine(self)
|
||||||
self.printing_started = False
|
self.printing_started = False
|
||||||
self.loadFinished.connect(self.load_finished, type=Qt.ConnectionType.QueuedConnection)
|
self.loadFinished.connect(self.load_finished, type=Qt.ConnectionType.QueuedConnection)
|
||||||
@ -32,6 +94,11 @@ class Render(QWebEnginePage):
|
|||||||
t.setInterval(500)
|
t.setInterval(500)
|
||||||
t.timeout.connect(self.hang_check)
|
t.timeout.connect(self.hang_check)
|
||||||
|
|
||||||
|
def break_cycles(self):
|
||||||
|
self.hang_timer.timeout.disconnect()
|
||||||
|
self.pdfPrintingFinished.disconnect()
|
||||||
|
self.setParent(None)
|
||||||
|
|
||||||
def load_finished(self, ok):
|
def load_finished(self, ok):
|
||||||
if ok:
|
if ok:
|
||||||
self.runJavaScript('''
|
self.runJavaScript('''
|
||||||
@ -52,8 +119,10 @@ class Render(QWebEnginePage):
|
|||||||
def javaScriptConsoleMessage(self, level, msg, linenumber, source_id):
|
def javaScriptConsoleMessage(self, level, msg, linenumber, source_id):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def start_load(self, path_to_html):
|
def start_load(self, path_to_html, root):
|
||||||
self.load(QUrl.fromLocalFile(path_to_html))
|
url = QUrl(f'{FAKE_PROTOCOL}://{FAKE_HOST}')
|
||||||
|
url.setPath('/' + os.path.relpath(path_to_html, root).replace(os.sep, '/'))
|
||||||
|
self.setUrl(url)
|
||||||
self.start_time = monotonic()
|
self.start_time = monotonic()
|
||||||
self.hang_timer.start()
|
self.hang_timer.start()
|
||||||
|
|
||||||
@ -79,7 +148,9 @@ class Render(QWebEnginePage):
|
|||||||
if type(getattr(QPageSize, sz, None)) is type(QPageSize.PageSizeId.A4): # noqa
|
if type(getattr(QPageSize, sz, None)) is type(QPageSize.PageSizeId.A4): # noqa
|
||||||
page_size = QPageSize(getattr(QPageSize, sz))
|
page_size = QPageSize(getattr(QPageSize, sz))
|
||||||
else:
|
else:
|
||||||
from calibre.ebooks.pdf.image_writer import parse_pdf_page_size
|
from calibre.ebooks.pdf.image_writer import (
|
||||||
|
parse_pdf_page_size
|
||||||
|
)
|
||||||
ps = parse_pdf_page_size(sz, data.get('unit', 'inch'))
|
ps = parse_pdf_page_size(sz, data.get('unit', 'inch'))
|
||||||
if ps is not None:
|
if ps is not None:
|
||||||
page_size = ps
|
page_size = ps
|
||||||
@ -95,17 +166,25 @@ class Render(QWebEnginePage):
|
|||||||
self.hang_timer.stop()
|
self.hang_timer.stop()
|
||||||
|
|
||||||
|
|
||||||
def main(path_to_html, tdir, image_format='jpeg'):
|
def main(path_to_html, tdir, image_format='jpeg', root=''):
|
||||||
if image_format not in ('jpeg', 'png'):
|
if image_format not in ('jpeg', 'png'):
|
||||||
raise ValueError('Image format must be either jpeg or png')
|
raise ValueError('Image format must be either jpeg or png')
|
||||||
must_use_qt()
|
must_use_qt()
|
||||||
from calibre.utils.webengine import setup_default_profile
|
setup_qt_logging()
|
||||||
setup_default_profile()
|
setup_fake_protocol()
|
||||||
|
profile = setup_profile(QWebEngineProfile(QApplication.instance()))
|
||||||
path_to_html = os.path.abspath(path_to_html)
|
path_to_html = os.path.abspath(path_to_html)
|
||||||
|
url_handler = UrlSchemeHandler(root or os.path.dirname(path_to_html), parent=profile)
|
||||||
|
interceptor = RequestInterceptor(profile)
|
||||||
|
profile.installUrlSchemeHandler(QByteArray(FAKE_PROTOCOL.encode('ascii')), url_handler)
|
||||||
|
profile.setUrlRequestInterceptor(interceptor)
|
||||||
|
|
||||||
os.chdir(tdir)
|
os.chdir(tdir)
|
||||||
renderer = Render()
|
renderer = Render(profile)
|
||||||
renderer.start_load(path_to_html)
|
renderer.start_load(path_to_html, url_handler.root)
|
||||||
ret = QApplication.instance().exec()
|
ret = QApplication.instance().exec()
|
||||||
|
renderer.break_cycles()
|
||||||
|
del renderer
|
||||||
if ret == 0:
|
if ret == 0:
|
||||||
page_images('rendered.pdf', image_format=image_format)
|
page_images('rendered.pdf', image_format=image_format)
|
||||||
ext = {'jpeg': 'jpg'}.get(image_format, image_format)
|
ext = {'jpeg': 'jpg'}.get(image_format, image_format)
|
||||||
|
@ -1188,8 +1188,9 @@ def main(shm_name=None):
|
|||||||
|
|
||||||
override = 'calibre-gui' if islinux else None
|
override = 'calibre-gui' if islinux else None
|
||||||
app = Application([], override_program_name=override)
|
app = Application([], override_program_name=override)
|
||||||
from calibre.utils.webengine import setup_default_profile
|
from calibre.utils.webengine import setup_default_profile, setup_fake_protocol
|
||||||
setup_default_profile()
|
setup_default_profile()
|
||||||
|
setup_fake_protocol()
|
||||||
d = TOCEditor(path, title=title, write_result_to=path + '.result')
|
d = TOCEditor(path, title=title, write_result_to=path + '.result')
|
||||||
d.start()
|
d.start()
|
||||||
ok = 0
|
ok = 0
|
||||||
|
@ -8,7 +8,7 @@ import time
|
|||||||
|
|
||||||
from qt.core import QIcon
|
from qt.core import QIcon
|
||||||
|
|
||||||
from calibre.constants import EDITOR_APP_UID, FAKE_PROTOCOL, islinux
|
from calibre.constants import EDITOR_APP_UID, islinux
|
||||||
from calibre.ebooks.oeb.polish.check.css import shutdown as shutdown_css_check_pool
|
from calibre.ebooks.oeb.polish.check.css import shutdown as shutdown_css_check_pool
|
||||||
from calibre.gui2 import (
|
from calibre.gui2 import (
|
||||||
Application, decouple, set_gui_prefs, setup_gui_option_parser
|
Application, decouple, set_gui_prefs, setup_gui_option_parser
|
||||||
@ -50,14 +50,11 @@ def gui_main(path=None, notify=None):
|
|||||||
|
|
||||||
|
|
||||||
def _run(args, notify=None):
|
def _run(args, notify=None):
|
||||||
from qt.webengine import QWebEngineUrlScheme
|
from calibre.utils.webengine import setup_fake_protocol
|
||||||
# Ensure we can continue to function if GUI is closed
|
# Ensure we can continue to function if GUI is closed
|
||||||
os.environ.pop('CALIBRE_WORKER_TEMP_DIR', None)
|
os.environ.pop('CALIBRE_WORKER_TEMP_DIR', None)
|
||||||
reset_base_dir()
|
reset_base_dir()
|
||||||
scheme = QWebEngineUrlScheme(FAKE_PROTOCOL.encode('ascii'))
|
setup_fake_protocol()
|
||||||
scheme.setSyntax(QWebEngineUrlScheme.Syntax.Host)
|
|
||||||
scheme.setFlags(QWebEngineUrlScheme.Flag.SecureScheme)
|
|
||||||
QWebEngineUrlScheme.registerScheme(scheme)
|
|
||||||
|
|
||||||
# The following two lines are needed to prevent circular imports causing
|
# The following two lines are needed to prevent circular imports causing
|
||||||
# errors during initialization of plugins that use the polish container
|
# errors during initialization of plugins that use the polish container
|
||||||
|
@ -8,7 +8,7 @@ import sys
|
|||||||
from contextlib import closing
|
from contextlib import closing
|
||||||
from qt.core import QIcon, QObject, Qt, QTimer, pyqtSignal
|
from qt.core import QIcon, QObject, Qt, QTimer, pyqtSignal
|
||||||
|
|
||||||
from calibre.constants import FAKE_PROTOCOL, VIEWER_APP_UID, islinux
|
from calibre.constants import VIEWER_APP_UID, islinux
|
||||||
from calibre.gui2 import Application, error_dialog, setup_gui_option_parser
|
from calibre.gui2 import Application, error_dialog, setup_gui_option_parser
|
||||||
from calibre.gui2.listener import send_message_in_process
|
from calibre.gui2.listener import send_message_in_process
|
||||||
from calibre.gui2.viewer.config import get_session_pref, vprefs
|
from calibre.gui2.viewer.config import get_session_pref, vprefs
|
||||||
@ -167,14 +167,11 @@ def run_gui(app, opts, args, internal_book_data, listener=None):
|
|||||||
|
|
||||||
|
|
||||||
def main(args=sys.argv):
|
def main(args=sys.argv):
|
||||||
from qt.webengine import QWebEngineUrlScheme
|
from calibre.utils.webengine import setup_fake_protocol
|
||||||
# Ensure viewer can continue to function if GUI is closed
|
# Ensure viewer can continue to function if GUI is closed
|
||||||
os.environ.pop('CALIBRE_WORKER_TEMP_DIR', None)
|
os.environ.pop('CALIBRE_WORKER_TEMP_DIR', None)
|
||||||
reset_base_dir()
|
reset_base_dir()
|
||||||
scheme = QWebEngineUrlScheme(FAKE_PROTOCOL.encode('ascii'))
|
setup_fake_protocol()
|
||||||
scheme.setSyntax(QWebEngineUrlScheme.Syntax.Host)
|
|
||||||
scheme.setFlags(QWebEngineUrlScheme.Flag.SecureScheme)
|
|
||||||
QWebEngineUrlScheme.registerScheme(scheme)
|
|
||||||
override = 'calibre-ebook-viewer' if islinux else None
|
override = 'calibre-ebook-viewer' if islinux else None
|
||||||
processed_args = []
|
processed_args = []
|
||||||
internal_book_data = internal_book_data_path = None
|
internal_book_data = internal_book_data_path = None
|
||||||
|
@ -16,11 +16,11 @@ from calibre.utils.ipc.simple_worker import start_pipe_worker
|
|||||||
|
|
||||||
|
|
||||||
def worker_main(source):
|
def worker_main(source):
|
||||||
from qt.core import QLoggingCategory, QUrl
|
from qt.core import QUrl
|
||||||
QLoggingCategory.setFilterRules('''\
|
|
||||||
qt.webenginecontext.info=false
|
|
||||||
''')
|
|
||||||
from calibre.gui2 import must_use_qt
|
from calibre.gui2 import must_use_qt
|
||||||
|
from calibre.gui_launch import setup_qt_logging
|
||||||
|
setup_qt_logging()
|
||||||
|
|
||||||
from .simple_backend import SimpleScraper
|
from .simple_backend import SimpleScraper
|
||||||
must_use_qt()
|
must_use_qt()
|
||||||
|
@ -59,7 +59,9 @@ def compiler():
|
|||||||
|
|
||||||
from calibre import walk
|
from calibre import walk
|
||||||
from calibre.gui2 import must_use_qt
|
from calibre.gui2 import must_use_qt
|
||||||
from calibre.utils.webengine import secure_webengine, setup_default_profile, setup_profile
|
from calibre.utils.webengine import (
|
||||||
|
secure_webengine, setup_default_profile, setup_profile
|
||||||
|
)
|
||||||
must_use_qt()
|
must_use_qt()
|
||||||
setup_default_profile()
|
setup_default_profile()
|
||||||
|
|
||||||
@ -335,7 +337,7 @@ def run_rapydscript_tests():
|
|||||||
from qt.core import QApplication, QByteArray, QEventLoop, QUrl
|
from qt.core import QApplication, QByteArray, QEventLoop, QUrl
|
||||||
from qt.webengine import (
|
from qt.webengine import (
|
||||||
QWebEnginePage, QWebEngineProfile, QWebEngineScript, QWebEngineUrlRequestJob,
|
QWebEnginePage, QWebEngineProfile, QWebEngineScript, QWebEngineUrlRequestJob,
|
||||||
QWebEngineUrlScheme, QWebEngineUrlSchemeHandler
|
QWebEngineUrlSchemeHandler
|
||||||
)
|
)
|
||||||
from urllib.parse import parse_qs
|
from urllib.parse import parse_qs
|
||||||
|
|
||||||
@ -343,14 +345,12 @@ def run_rapydscript_tests():
|
|||||||
from calibre.gui2 import must_use_qt
|
from calibre.gui2 import must_use_qt
|
||||||
from calibre.gui2.viewer.web_view import send_reply
|
from calibre.gui2.viewer.web_view import send_reply
|
||||||
from calibre.utils.webengine import (
|
from calibre.utils.webengine import (
|
||||||
create_script, insert_scripts, secure_webengine, setup_default_profile, setup_profile
|
create_script, insert_scripts, secure_webengine, setup_default_profile,
|
||||||
|
setup_fake_protocol, setup_profile
|
||||||
)
|
)
|
||||||
must_use_qt()
|
must_use_qt()
|
||||||
setup_default_profile()
|
setup_default_profile()
|
||||||
scheme = QWebEngineUrlScheme(FAKE_PROTOCOL.encode('ascii'))
|
setup_fake_protocol()
|
||||||
scheme.setSyntax(QWebEngineUrlScheme.Syntax.Host)
|
|
||||||
scheme.setFlags(QWebEngineUrlScheme.Flag.SecureScheme)
|
|
||||||
QWebEngineUrlScheme.registerScheme(scheme)
|
|
||||||
|
|
||||||
base = base_dir()
|
base = base_dir()
|
||||||
rapydscript_dir = os.path.join(base, 'src', 'pyj')
|
rapydscript_dir = os.path.join(base, 'src', 'pyj')
|
||||||
|
@ -3,11 +3,25 @@
|
|||||||
# License: GPL v3 Copyright: 2021, Kovid Goyal <kovid at kovidgoyal.net>
|
# License: GPL v3 Copyright: 2021, Kovid Goyal <kovid at kovidgoyal.net>
|
||||||
|
|
||||||
|
|
||||||
import json, os
|
import json
|
||||||
|
import os
|
||||||
from qt.core import QBuffer, QIODevice, QObject, pyqtSignal, sip
|
from qt.core import QBuffer, QIODevice, QObject, pyqtSignal, sip
|
||||||
from qt.webengine import QWebEngineScript, QWebEngineSettings, QWebEngineProfile
|
from qt.webengine import (
|
||||||
|
QWebEngineProfile, QWebEngineScript, QWebEngineSettings, QWebEngineUrlScheme
|
||||||
|
)
|
||||||
|
|
||||||
from calibre.constants import cache_dir, SPECIAL_TITLE_FOR_WEBENGINE_COMMS
|
from calibre.constants import (
|
||||||
|
FAKE_PROTOCOL, SPECIAL_TITLE_FOR_WEBENGINE_COMMS, cache_dir
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def setup_fake_protocol():
|
||||||
|
p = FAKE_PROTOCOL.encode('ascii')
|
||||||
|
if not QWebEngineUrlScheme.schemeByName(p).name():
|
||||||
|
scheme = QWebEngineUrlScheme(p)
|
||||||
|
scheme.setSyntax(QWebEngineUrlScheme.Syntax.Host)
|
||||||
|
scheme.setFlags(QWebEngineUrlScheme.Flag.SecureScheme)
|
||||||
|
QWebEngineUrlScheme.registerScheme(scheme)
|
||||||
|
|
||||||
|
|
||||||
def setup_profile(profile):
|
def setup_profile(profile):
|
||||||
|
Loading…
x
Reference in New Issue
Block a user