Edit book: Fix initial sync of preview panel to cursor position sometimes not working when a new HTML file is opened for editing

This commit is contained in:
Kovid Goyal 2020-07-07 21:49:44 +05:30
parent 685ac9e5cb
commit 195ff72d44
No known key found for this signature in database
GPG Key ID: 06BC317B515ACE7C
4 changed files with 25 additions and 8 deletions

View File

@ -12,7 +12,7 @@ from functools import partial, wraps
from PyQt5.Qt import ( from PyQt5.Qt import (
QApplication, QCheckBox, QDialog, QDialogButtonBox, QGridLayout, QIcon, QApplication, QCheckBox, QDialog, QDialogButtonBox, QGridLayout, QIcon,
QInputDialog, QLabel, QMimeData, QObject, QSize, Qt, QUrl, QVBoxLayout, QInputDialog, QLabel, QMimeData, QObject, QSize, Qt, QTimer, QUrl, QVBoxLayout,
pyqtSignal pyqtSignal
) )
@ -1497,7 +1497,11 @@ class Boss(QObject):
if ed is not None: if ed is not None:
name = editor_name(ed) name = editor_name(ed)
if name is not None and getattr(ed, 'syntax', None) == 'html': if name is not None and getattr(ed, 'syntax', None) == 'html':
self.gui.preview.sync_to_editor(name, ed.current_tag()) ct = ed.current_tag()
self.gui.preview.sync_to_editor(name, ct)
hl = getattr(ed, 'highlighter', None)
if hl is not None and hl.is_working:
QTimer.singleShot(75, self.sync_preview_to_editor)
def show_partial_cfi_in_editor(self, name, cfi): def show_partial_cfi_in_editor(self, name, cfi):
editor = self.edit_file(name, 'html') editor = self.edit_file(name, 'html')

View File

@ -201,6 +201,10 @@ class SyntaxHighlighter(object):
finally: finally:
self.ignore_requests = False self.ignore_requests = False
@property
def is_working(self):
return bool(self.requests)
def parse_single_block(self, block): def parse_single_block(self, block):
ud, is_new_ud = self.get_user_data(block) ud, is_new_ud = self.get_user_data(block)
orig_state = ud.state orig_state = ud.state

View File

@ -182,6 +182,10 @@ class Editor(QMainWindow):
def current_tag(self, for_position_sync=True): def current_tag(self, for_position_sync=True):
return self.editor.current_tag(for_position_sync=for_position_sync) return self.editor.current_tag(for_position_sync=for_position_sync)
@property
def highlighter(self):
return self.editor.highlighter
@property @property
def number_of_lines(self): def number_of_lines(self):
return self.editor.blockCount() return self.editor.blockCount()

View File

@ -438,6 +438,7 @@ class Preview(QWidget):
self.l = l = QVBoxLayout() self.l = l = QVBoxLayout()
self.setLayout(l) self.setLayout(l)
l.setContentsMargins(0, 0, 0, 0) l.setContentsMargins(0, 0, 0, 0)
self.current_sync_retry_count = 0
self.view = WebView(self) self.view = WebView(self)
self.view._page.bridge.request_sync.connect(self.request_sync) self.view._page.bridge.request_sync.connect(self.request_sync)
self.view._page.bridge.request_split.connect(self.request_split) self.view._page.bridge.request_split.connect(self.request_split)
@ -533,20 +534,24 @@ class Preview(QWidget):
if self.current_name: if self.current_name:
self.split_requested.emit(self.current_name, loc, totals) self.split_requested.emit(self.current_name, loc, totals)
@property
def bridge_ready(self):
return self.view._page.bridge.ready
def sync_to_editor(self, name, sourceline_address): def sync_to_editor(self, name, sourceline_address):
self.current_sync_request = (name, sourceline_address) self.current_sync_request = (name, sourceline_address)
self.current_sync_retry_count = 0
QTimer.singleShot(100, self._sync_to_editor) QTimer.singleShot(100, self._sync_to_editor)
def _sync_to_editor(self): def _sync_to_editor(self):
if not actions['sync-preview-to-editor'].isChecked(): if not actions['sync-preview-to-editor'].isChecked() or self.current_sync_retry_count >= 3000 or self.current_sync_request is None:
return return
try: if self.refresh_timer.isActive() or not self.bridge_ready or self.current_sync_request[0] != self.current_name:
if self.refresh_timer.isActive() or self.current_sync_request[0] != self.current_name: self.current_sync_retry_count += 1
return QTimer.singleShot(100, self._sync_to_editor) return QTimer.singleShot(100, self._sync_to_editor)
except TypeError:
return # Happens if current_sync_request is None
sourceline_address = self.current_sync_request[1] sourceline_address = self.current_sync_request[1]
self.current_sync_request = None self.current_sync_request = None
self.current_sync_retry_count = 0
self.view._page.go_to_sourceline_address(sourceline_address) self.view._page.go_to_sourceline_address(sourceline_address)
def report_worker_launch_error(self): def report_worker_launch_error(self):