From d67b0e1b50457bfa42c9b3f3a0078022d5d845ee Mon Sep 17 00:00:00 2001 From: Kovid Goyal Date: Sun, 5 May 2024 08:14:30 +0530 Subject: [PATCH] Spellcheck dialog: Move the checkbox to hide correctly spelled words with the rest of the checkboxes that filter the word list Fix #2064792 [[Editor][master] Problematic spell check count with "only mispelled words" option disabled](https://bugs.launchpad.net/calibre/+bug/2064792) --- src/calibre/gui2/tweak_book/spell.py | 39 ++++++++++++++-------------- 1 file changed, 19 insertions(+), 20 deletions(-) diff --git a/src/calibre/gui2/tweak_book/spell.py b/src/calibre/gui2/tweak_book/spell.py index c4629f08fbf3..2b7cd96a4bd4 100644 --- a/src/calibre/gui2/tweak_book/spell.py +++ b/src/calibre/gui2/tweak_book/spell.py @@ -723,7 +723,7 @@ class WordsModel(QAbstractTableModel): word_ignored = pyqtSignal(object, object) counts_changed = pyqtSignal() - def __init__(self, parent=None): + def __init__(self, parent=None, show_only_misspelt=True): QAbstractTableModel.__init__(self, parent) self.counts = (0, 0) self.all_caps = self.with_numbers = self.camel_case = self.snake_case = False @@ -732,7 +732,7 @@ def __init__(self, parent=None): self.sort_on = (0, False) self.items = [] # The currently displayed items self.filter_expression = None - self.show_only_misspelt = True + self.show_only_misspelt = show_only_misspelt self.headers = (_('Word'), _('Count'), _('Language'), _('Misspelled?')) self.alignments = Qt.AlignmentFlag.AlignLeft, Qt.AlignmentFlag.AlignRight, Qt.AlignmentFlag.AlignLeft, Qt.AlignmentFlag.AlignHCenter self.num_pat = regex.compile(r'\d', flags=regex.UNICODE) @@ -798,10 +798,11 @@ def sort(self, column, order=Qt.SortOrder.AscendingOrder): self.do_sort() self.endResetModel() - def filter(self, filter_text, *, all_caps=False, with_numbers=False, camel_case=False, snake_case=False): + def filter(self, filter_text, *, all_caps=False, with_numbers=False, camel_case=False, snake_case=False, show_only_misspelt=True): self.filter_expression = filter_text or None self.all_caps, self.with_numbers = all_caps, with_numbers self.camel_case, self.snake_case = camel_case, snake_case + self.show_only_misspelt = show_only_misspelt self.beginResetModel() self.do_filter() self.do_sort() @@ -1174,13 +1175,15 @@ def hw(name, title, tooltip): ac = QCheckBox(title) pref_name = f'spell-check-hide-words-{name}' ac.setObjectName(pref_name) - ac.setChecked(tprefs.get(pref_name, False)) + defval = name == 'misspelled' + ac.setChecked(tprefs.get(pref_name, defval)) if ac.isChecked(): any_hide_checked = True ac.toggled.connect(self.hide_words_toggled) ac.setToolTip(tooltip) h.addWidget(ac) return ac + self.show_only_misspelt = hw('misspelled', _('spelled correctly'), _('Hide words that are spelled correctly')) self.all_caps = hw('all-caps', _('ALL CAPS'), _('Hide words with all capital letters')) self.with_numbers = hw('with-numbers', _('with numbers'), _('Hide words that contain numbers')) self.camel_case = hw('camel-case', _('camelCase'), _('Hide words in camelCase')) @@ -1199,7 +1202,7 @@ def hw(name, title, tooltip): state = tprefs.get(self.state_name, None) hh = self.words_view.horizontalHeader() h.addWidget(w) - self.words_model = m = WordsModel(self) + self.words_model = m = WordsModel(self, show_only_misspelt=self.show_only_misspelt.isChecked()) m.counts_changed.connect(self.update_summary) w.setModel(m) m.dataChanged.connect(self.current_word_changed) @@ -1209,7 +1212,6 @@ def hw(name, title, tooltip): hh.restoreState(state) # Sort by the restored state, if any w.sortByColumn(hh.sortIndicatorSection(), hh.sortIndicatorOrder()) - m.show_only_misspelt = hh.isSectionHidden(3) self.ignore_button = b = QPushButton(_('&Ignore')) b.ign_text, b.unign_text = str(b.text()), _('Un&ignore') @@ -1255,10 +1257,7 @@ def hw(name, title, tooltip): set_no_activate_on_click(sl) l.addWidget(sl) - hh.setSectionHidden(3, m.show_only_misspelt) - self.show_only_misspelled = om = QCheckBox(_('Show &only misspelled words')) - om.setChecked(m.show_only_misspelt) - om.stateChanged.connect(self.update_show_only_misspelt) + hh.setSectionHidden(3, self.show_only_misspelt.isChecked()) self.case_sensitive_sort = cs = QCheckBox(_('Case &sensitive sort')) cs.setChecked(tprefs['spell_check_case_sensitive_sort']) cs.setToolTip(_('When sorting the list of words, be case sensitive')) @@ -1268,7 +1267,7 @@ def hw(name, title, tooltip): cs2.setChecked(tprefs['spell_check_case_sensitive_search']) cs2.stateChanged.connect(self.search_type_changed) self.hb = h = QHBoxLayout() - self.main.l.addLayout(h), h.addWidget(om), h.addWidget(cs), h.addWidget(cs2), h.addStretch(11) + self.main.l.addLayout(h), h.addWidget(cs), h.addWidget(cs2), h.addStretch(11) self.action_next_word = a = QAction(self) a.setShortcut(QKeySequence(Qt.Key.Key_Down)) a.triggered.connect(self.next_word) @@ -1294,6 +1293,8 @@ def button_action(sc, tt, button): def hide_words_toggled(self, checked): cb = self.sender() pref_name = cb.objectName() + if 'misspelled' in pref_name: + self.words_view.horizontalHeader().setSectionHidden(3, self.show_only_misspelt.isChecked()) tprefs.set(pref_name, checked) self.do_filter() @@ -1490,12 +1491,6 @@ def add_remove(self): else: self.words_model.remove_word(current.row()) - def update_show_only_misspelt(self): - m = self.words_model - m.show_only_misspelt = self.show_only_misspelled.isChecked() - self.words_view.horizontalHeader().setSectionHidden(3, m.show_only_misspelt) - self.do_filter() - def __enter__(self): idx = self.words_view.currentIndex().row() self.__current_word = self.words_model.word_for_row(idx) @@ -1511,7 +1506,8 @@ def do_filter(self): with self: self.words_model.filter( text, all_caps=self.all_caps.isChecked(), with_numbers=self.with_numbers.isChecked(), - camel_case=self.camel_case.isChecked(), snake_case=self.snake_case.isChecked()) + camel_case=self.camel_case.isChecked(), snake_case=self.snake_case.isChecked(), + show_only_misspelt=self.show_only_misspelt.isChecked()) def refresh(self, change_request=None): if not self.isVisible(): @@ -1584,8 +1580,11 @@ def work_done(self, words, spell_map, change_request): def update_summary(self): misspelled, total = self.words_model.counts visible = len(self.words_model.items) - if visible != misspelled: - self.setWindowTitle(_('Spellcheck showing: {0} of {1} misspelled and {2} total words').format(visible, misspelled, total)) + if visible not in (misspelled, total): # some filter is active + if self.show_only_misspelt.isChecked(): + self.setWindowTitle(_('Spellcheck showing: {0} of {1} misspelled with {2} total words').format(visible, misspelled, total)) + else: + self.setWindowTitle(_('Spellcheck showing: {0} of {2} total with {1} misspelled words').format(visible, misspelled, total)) else: self.setWindowTitle(_('Spellcheck showing: {0} misspelled of {1} total words').format(misspelled, total))