Allow easily editing notes in the highlights panel

This commit is contained in:
Kovid Goyal 2020-07-13 15:56:45 +05:30
parent 90f664e645
commit cf7a40a960
No known key found for this signature in database
GPG Key ID: 06BC317B515ACE7C
6 changed files with 99 additions and 8 deletions

View File

@ -6,13 +6,16 @@ from itertools import chain
from PyQt5.Qt import (
QHBoxLayout, QIcon, QItemSelectionModel, QKeySequence, QLabel, QListWidget,
QListWidgetItem, QPushButton, Qt, QTextBrowser, QVBoxLayout, QWidget, pyqtSignal
QListWidgetItem, QPushButton, Qt, QTextEdit, QToolButton, QVBoxLayout, QWidget,
pyqtSignal
)
from calibre.constants import plugins
from calibre.gui2 import error_dialog, question_dialog
from calibre.gui2.library.annotations import Details
from calibre.gui2.viewer.search import SearchInput
from calibre.gui2.viewer.shortcuts import index_to_key_sequence
from calibre.gui2.widgets2 import Dialog
from polyglot.builtins import range
@ -83,10 +86,63 @@ class Highlights(QListWidget):
return i.data(Qt.UserRole)
class NotesEditDialog(Dialog):
def __init__(self, notes, parent=None):
self.initial_notes = notes
Dialog.__init__(self, name='edit-notes-highlight', title=_('Edit notes'), parent=parent)
def setup_ui(self):
l = QVBoxLayout(self)
self.qte = qte = QTextEdit(self)
qte.setMinimumHeight(400)
qte.setMinimumWidth(600)
if self.initial_notes:
qte.setPlainText(self.initial_notes)
l.addWidget(qte)
l.addWidget(self.bb)
@property
def notes(self):
return self.qte.toPlainText().rstrip()
class NotesDisplay(QWidget):
notes_edited = pyqtSignal(object)
def __init__(self, parent=None):
QWidget.__init__(self, parent)
h = QHBoxLayout(self)
h.setContentsMargins(0, 0, 0, 0)
self.browser = nd = Details(self)
h.addWidget(nd)
self.edit_button = eb = QToolButton(self)
eb.setIcon(QIcon(I('modified.png')))
eb.setToolTip(_('Edit the notes for this highlight'))
h.addWidget(eb)
eb.clicked.connect(self.edit_notes)
def show_notes(self, text=''):
text = (text or '').strip()
self.setVisible(bool(text))
self.browser.setPlainText(text)
h = self.browser.document().size().height() + 8
self.browser.setMaximumHeight(h)
self.setMaximumHeight(max(self.edit_button.sizeHint().height() + 4, h))
def edit_notes(self):
current_text = self.browser.toPlainText()
d = NotesEditDialog(current_text, self)
if d.exec_() == d.Accepted and d.notes != current_text:
self.notes_edited.emit(d.notes)
class HighlightsPanel(QWidget):
jump_to_cfi = pyqtSignal(object)
request_highlight_action = pyqtSignal(object, object)
web_action = pyqtSignal(object, object)
def __init__(self, parent=None):
QWidget.__init__(self, parent)
@ -123,10 +179,17 @@ class HighlightsPanel(QWidget):
self.remove_button = button('trash.png', _('Remove'), _('Remove the selected highlight'), self.remove_highlight)
h.addWidget(self.add_button), h.addWidget(self.edit_button), h.addWidget(self.remove_button)
self.notes_display = nd = QTextBrowser(self)
self.notes_display = nd = NotesDisplay(self)
nd.notes_edited.connect(self.notes_edited)
l.addWidget(nd)
nd.setVisible(False)
def notes_edited(self, text):
h = self.highlights.current_highlight
if h is not None:
h['notes'] = text
self.web_action.emit('set-notes-in-highlight', h)
def set_tooltips(self, rmap):
a = rmap.get('create_annotation')
if a:
@ -153,13 +216,9 @@ class HighlightsPanel(QWidget):
def current_highlight_changed(self, highlight):
nd = self.notes_display
if highlight is None or not highlight.get('notes'):
nd.setVisible(False)
nd.setPlainText('')
nd.show_notes()
else:
nd.setVisible(True)
nd.setPlainText(highlight['notes'])
h = nd.document().size().height()
nd.setMaximumHeight(h + 8)
nd.show_notes(highlight['notes'])
def no_selected_highlight(self):
error_dialog(self, _('No selected highlight'), _(

View File

@ -193,6 +193,7 @@ class EbookViewer(MainWindow):
self.actions_toolbar.update_visibility()
self.dock_visibility_changed()
self.highlights_widget.request_highlight_action.connect(self.web_view.highlight_action)
self.highlights_widget.web_action.connect(self.web_view.generic_action)
if continue_reading:
self.continue_reading()

View File

@ -281,6 +281,7 @@ class ViewerBridge(Bridge):
trigger_shortcut = to_js()
set_system_palette = to_js()
highlight_action = to_js()
generic_action = to_js()
show_search_result = to_js()
prepare_for_close = to_js()
viewer_font_size_changed = to_js()
@ -688,6 +689,9 @@ class WebView(RestartingWebEngineView):
self.execute_when_ready('highlight_action', uuid, which)
self.setFocus(Qt.OtherFocusReason)
def generic_action(self, which, data):
self.execute_when_ready('generic_action', which, data)
def contextMenuEvent(self, ev):
ev.accept()
self.trigger_shortcut('show_chrome')

View File

@ -60,6 +60,18 @@ class AnnotationsManager:
if h:
return h.notes
def set_notes_for_highlight(self, uuid, notes):
h = self.highlights[uuid]
if h:
if notes:
h.notes = notes
else:
v'delete h.notes'
if ui_operations.highlights_changed:
ui_operations.highlights_changed(Object.values(self.highlights))
return True
return False
def style_for_highlight(self, uuid):
h = self.highlights[uuid]
if h:
@ -811,6 +823,10 @@ class ViewAnnotation:
self.container.style.display = 'none'
self.showing_uuid = None
@property
def is_visible(self):
return self.container.style.display is not 'none'
def edit_current(self):
if self.showing_uuid:
self.view.create_annotation.edit_highlight(self.showing_uuid)

View File

@ -999,6 +999,11 @@ class View:
if reading_pos_cfi:
self.goto_cfi(reading_pos_cfi)
def set_notes_for_highlight(self, uuid, notes):
if self.annotations_manager.set_notes_for_highlight(uuid, notes):
if self.view_annotation.is_visible and self.view_annotation.showing_uuid is uuid:
self.view_annotation.show(uuid)
def on_next_spine_item(self, data):
spine = self.book.manifest.spine
idx = spine.indexOf(self.currently_showing.name)

View File

@ -197,6 +197,12 @@ def highlight_action(uuid, which):
view.highlight_action(uuid, which)
@from_python
def generic_action(which, data):
if which is 'set-notes-in-highlight':
view.set_notes_for_highlight(data.uuid, data.notes or '')
@from_python
def show_home_page():
view.overlay.open_book(False)