For column icons and grid view emblems, support icons for both light and dark themes.

This commit is contained in:
Charles Haley 2024-09-25 12:26:26 +01:00
parent 31be5f3708
commit 1f5e9d0ac5
3 changed files with 47 additions and 6 deletions

View File

@ -60,7 +60,7 @@ from qt.core import (
from calibre import fit_image, human_readable, prepare_string_for_xml
from calibre.constants import DEBUG, config_dir, islinux
from calibre.ebooks.metadata import fmt_sidx, rating_to_stars
from calibre.gui2 import clip_border_radius, config, empty_index, gprefs, rating_font
from calibre.gui2 import clip_border_radius, config, empty_index, gprefs, rating_font, is_dark_theme
from calibre.gui2.dnd import path_from_qurl
from calibre.gui2.gestures import GestureManager
from calibre.gui2.library.caches import CoverCache, ThumbnailCache
@ -554,6 +554,13 @@ class CoverDelegate(QStyledItemDelegate):
elif name == ':ondevice':
ans = QIcon.ic('ok.png').pixmap(sz, sz)
elif name:
pmap = None
if is_dark_theme():
n,ext = os.path.splitext(name)
d = os.path.join(config_dir, 'cc_icons', n + '-dark' + ext)
if os.path.exists(d):
pmap = QIcon(d).pixmap(sz, sz)
if pmap is None:
pmap = QIcon(os.path.join(config_dir, 'cc_icons', name)).pixmap(sz, sz)
if not pmap.isNull():
ans = pmap

View File

@ -23,7 +23,7 @@ from calibre.db.search import CONTAINS_MATCH, EQUALS_MATCH, REGEXP_MATCH, _match
from calibre.db.utils import force_to_bool
from calibre.ebooks.metadata import authors_to_string, fmt_sidx, string_to_authors
from calibre.ebooks.metadata.book.formatter import SafeFormat
from calibre.gui2 import error_dialog, simple_excepthook
from calibre.gui2 import error_dialog, simple_excepthook, is_dark_theme
from calibre.gui2.library import DEFAULT_SORT
from calibre.library.coloring import color_row_key
from calibre.library.save_to_disk import find_plugboard
@ -132,8 +132,15 @@ class ColumnIcon: # {{{
total_width = 0
rh = max(2, self.model.row_height - 4)
dim = int(self.dpr * rh)
icon_dir = os.path.join(config_dir, 'cc_icons')
for icon in icons:
d = os.path.join(config_dir, 'cc_icons', icon)
d = None
if is_dark_theme():
root,ext = os.path.splitext(icon)
d = os.path.join(icon_dir, root + '-dark' + ext)
d = d if os.path.exists(d) else None
if d is None:
d = os.path.join(icon_dir, icon)
if (os.path.exists(d)):
bm = QPixmap(d)
scaled, nw, nh = fit_image(bm.width(), bm.height(), bm.width(), dim)

View File

@ -21,6 +21,7 @@ from qt.core import (
QDoubleValidator,
QFrame,
QGridLayout,
QHBoxLayout,
QIcon,
QIntValidator,
QItemSelection,
@ -47,7 +48,8 @@ from qt.core import (
from calibre import as_unicode, prepare_string_for_xml, sanitize_file_name
from calibre.constants import config_dir
from calibre.gui2 import choose_files, choose_save_file, error_dialog, gprefs, open_local_file, pixmap_to_data, question_dialog
from calibre.gui2 import (choose_files, choose_save_file, error_dialog, gprefs, info_dialog,
open_local_file, pixmap_to_data, question_dialog)
from calibre.gui2.dialogs.template_dialog import TemplateDialog
from calibre.gui2.metadata.single_download import RichTextDelegate
from calibre.gui2.preferences import ListViewWithMoveByKeyPress
@ -512,11 +514,19 @@ class RuleEditor(QDialog): # {{{
' blanking all of its boxes'))
l.addWidget(l6, 8, 0, 1, 8)
bbl = QHBoxLayout()
self.bb = bb = QDialogButtonBox(
QDialogButtonBox.StandardButton.Ok|QDialogButtonBox.StandardButton.Cancel)
bb.accepted.connect(self.accept)
bb.rejected.connect(self.reject)
l.addWidget(bb, 9, 0, 1, 8)
if self.rule_kind in ('emblem', 'icon'):
theme_button = QPushButton(_('Using icons in light/dark themes'))
theme_button.setIcon(QIcon.ic('help.png'))
theme_button.clicked.connect(self.show_theme_help)
bbl.addWidget(theme_button)
bbl.addStretch(10)
bbl.addWidget(bb)
l.addLayout(bbl, 9, 0, 1, 8)
if self.rule_kind != 'color':
self.remove_button = b = bb.addButton(_('&Remove icons'), QDialogButtonBox.ButtonRole.ActionRole)
b.setIcon(QIcon.ic('minus.png'))
@ -555,6 +565,23 @@ class RuleEditor(QDialog): # {{{
self.resize(self.sizeHint())
def show_theme_help(self):
msg = '<p>'+ _(
'You can use different icons in light and dark themes. To do this, '
'add two icons to the icon list. The light theme icon will have '
'the "normal" name, for example "ok.png". The dark theme icon must '
'have the same name with "-dark" appended. For example, if the light '
'theme icon is named "ok.png" then the dark theme icon must be named '
'"ok-dark.png".'
'</p><p>'
'When defining a rule, always use the "normal" name. The -dark icon will be '
'automatically substituted for the normal icon when a dark theme is '
'being used.'
'</p><p>'
'Remember to add both the light and dark theme icons to the list of icons.'
) + '</p>'
info_dialog(self, _('Using icons in light/dark themes'), msg, show=True)
def multiple_box_clicked(self):
self.update_filename_box()
self.update_icon_filenames_in_box()