From 19db50ae44db6d7fef85f09eef3a411bd458bbf2 Mon Sep 17 00:00:00 2001 From: Kovid Goyal Date: Mon, 3 Jan 2011 18:17:21 -0700 Subject: [PATCH] Fix #8161 (Ability to send updated thumbnails to newer Sony readers) --- src/calibre/devices/prs505/driver.py | 28 +++++++++--- src/calibre/devices/usbms/deviceconfig.py | 38 ++++++++++++++-- .../gui2/device_drivers/configwidget.py | 43 ++++++++++++++++--- .../gui2/device_drivers/configwidget.ui | 15 +------ src/calibre/library/catalog.py | 2 +- 5 files changed, 94 insertions(+), 32 deletions(-) diff --git a/src/calibre/devices/prs505/driver.py b/src/calibre/devices/prs505/driver.py index 6652d581d4..98a7241a36 100644 --- a/src/calibre/devices/prs505/driver.py +++ b/src/calibre/devices/prs505/driver.py @@ -61,14 +61,26 @@ class PRS505(USBMS): ALL_BY_TITLE = _('All by title') ALL_BY_AUTHOR = _('All by author') - EXTRA_CUSTOMIZATION_MESSAGE = _('Comma separated list of metadata fields ' + EXTRA_CUSTOMIZATION_MESSAGE = [ + _('Comma separated list of metadata fields ' 'to turn into collections on the device. Possibilities include: ')+\ 'series, tags, authors' +\ _('. Two special collections are available: %s:%s and %s:%s. Add ' 'these values to the list to enable them. The collections will be ' 'given the name provided after the ":" character.')%( - 'abt', ALL_BY_TITLE, 'aba', ALL_BY_AUTHOR) - EXTRA_CUSTOMIZATION_DEFAULT = ', '.join(['series', 'tags']) + 'abt', ALL_BY_TITLE, 'aba', ALL_BY_AUTHOR), + _('Upload separate cover thumbnails for books (newer readers)') + + ':::'+_('Normally, the SONY readers get the cover image from the' + ' ebook file itself. With this option, calibre will send a ' + 'separate cover image to the reader, useful if you are ' + 'sending DRMed books in which you cannot change the cover.' + ' WARNING: This option should only be used with newer ' + 'SONY readers: 350, 650, 950 and newer.'), + ] + EXTRA_CUSTOMIZATION_DEFAULT = [ + ', '.join(['series', 'tags']), + False + ] plugboard = None plugboard_func = None @@ -159,7 +171,7 @@ class PRS505(USBMS): opts = self.settings() if opts.extra_customization: collections = [x.strip() for x in - opts.extra_customization.split(',')] + opts.extra_customization[0].split(',')] else: collections = [] debug_print('PRS505: collection fields:', collections) @@ -186,8 +198,12 @@ class PRS505(USBMS): self.plugboard_func = pb_func def upload_cover(self, path, filename, metadata, filepath): - return # Disabled as the SONY's don't need this thumbnail anyway and - # older models don't auto delete it + opts = self.settings() + if not opts.extra_customization[1]: + # Building thumbnails disabled + debug_print('PRS505: not uploading covers') + return + debug_print('PRS505: uploading covers') if metadata.thumbnail and metadata.thumbnail[-1]: path = path.replace('/', os.sep) is_main = path.startswith(self._main_prefix) diff --git a/src/calibre/devices/usbms/deviceconfig.py b/src/calibre/devices/usbms/deviceconfig.py index e074387175..769543f7cc 100644 --- a/src/calibre/devices/usbms/deviceconfig.py +++ b/src/calibre/devices/usbms/deviceconfig.py @@ -10,7 +10,21 @@ from calibre.utils.config import Config, ConfigProxy class DeviceConfig(object): HELP_MESSAGE = _('Configure Device') + + #: Can be None, a string or a list of strings. When it is a string + #: that string is used for the help text and the actual customization value + #: can be read from ``dev.settings().extra_customization``. + #: If it a list of strings, then dev.settings().extra_customization will + #: also be a list. In this case, you *must* ensure that + #: EXTRA_CUSTOMIZATION_DEFAULT is also a list. The list can contain either + #: boolean values or strings, in which case a checkbox or line edit will be + #: used for them in the config widget, automatically. + #: If a string contains ::: then the text after it is interpreted as the + #: tooltip EXTRA_CUSTOMIZATION_MESSAGE = None + + #: The default value for extra customization. If you set + #: EXTRA_CUSTOMIZATION_MESSAGE you *must* set this as well. EXTRA_CUSTOMIZATION_DEFAULT = None SUPPORTS_SUB_DIRS = False @@ -73,16 +87,32 @@ class DeviceConfig(object): if cls.SUPPORTS_USE_AUTHOR_SORT: proxy['use_author_sort'] = config_widget.use_author_sort() if cls.EXTRA_CUSTOMIZATION_MESSAGE: - ec = unicode(config_widget.opt_extra_customization.text()).strip() - if not ec: - ec = None + if isinstance(cls.EXTRA_CUSTOMIZATION_MESSAGE, list): + ec = [] + for i in range(0, len(cls.EXTRA_CUSTOMIZATION_MESSAGE)): + if hasattr(config_widget.opt_extra_customization[i], 'isChecked'): + ec.append(config_widget.opt_extra_customization[i].isChecked()) + else: + ec.append(unicode(config_widget.opt_extra_customization[i].text()).strip()) + else: + ec = unicode(config_widget.opt_extra_customization.text()).strip() + if not ec: + ec = None proxy['extra_customization'] = ec st = unicode(config_widget.opt_save_template.text()) proxy['save_template'] = st @classmethod def settings(cls): - return cls._config().parse() + opts = cls._config().parse() + if isinstance(cls.EXTRA_CUSTOMIZATION_DEFAULT, list): + if not isinstance(opts.extra_customization, list): + opts.extra_customization = [opts.extra_customization] + else: + for i,d in enumerate(cls.EXTRA_CUSTOMIZATION_DEFAULT): + if i >= len(opts.extra_customization): + opts.extra_customization.append(d) + return opts @classmethod def save_template(cls): diff --git a/src/calibre/gui2/device_drivers/configwidget.py b/src/calibre/gui2/device_drivers/configwidget.py index 64321e1a46..7b440db7fc 100644 --- a/src/calibre/gui2/device_drivers/configwidget.py +++ b/src/calibre/gui2/device_drivers/configwidget.py @@ -4,7 +4,10 @@ __license__ = 'GPL 3' __copyright__ = '2009, John Schember ' __docformat__ = 'restructuredtext en' -from PyQt4.Qt import QWidget, QListWidgetItem, Qt, QVariant, SIGNAL +import textwrap + +from PyQt4.Qt import QWidget, QListWidgetItem, Qt, QVariant, SIGNAL, \ + QLabel, QLineEdit, QCheckBox from calibre.gui2 import error_dialog from calibre.gui2.device_drivers.configwidget_ui import Ui_ConfigWidget @@ -46,12 +49,38 @@ class ConfigWidget(QWidget, Ui_ConfigWidget): else: self.opt_use_author_sort.hide() if extra_customization_message: - self.extra_customization_label.setText(extra_customization_message) - if settings.extra_customization: - self.opt_extra_customization.setText(settings.extra_customization) - else: - self.extra_customization_label.setVisible(False) - self.opt_extra_customization.setVisible(False) + def parse_msg(m): + msg, _, tt = m.partition(':::') if m else ('', '', '') + return msg.strip(), textwrap.fill(tt.strip(), 100) + + if isinstance(extra_customization_message, list): + self.opt_extra_customization = [] + for i, m in enumerate(extra_customization_message): + label_text, tt = parse_msg(m) + if isinstance(settings.extra_customization[i], bool): + self.opt_extra_customization.append(QCheckBox(label_text)) + self.opt_extra_customization[-1].setToolTip(tt) + self.opt_extra_customization[i].setChecked(bool(settings.extra_customization[i])) + else: + self.opt_extra_customization.append(QLineEdit(self)) + l = QLabel(label_text) + l.setToolTip(tt) + l.setBuddy(self.opt_extra_customization[i]) + l.setWordWrap(True) + self.opt_extra_customization[i].setText(settings.extra_customization[i]) + self.extra_layout.addWidget(l) + self.extra_layout.addWidget(self.opt_extra_customization[i]) + else: + self.opt_extra_customization = QLineEdit() + label_text, tt = parse_msg(extra_customization_message) + l = QLabel(label_text) + l.setToolTip(tt) + l.setBuddy(self.opt_extra_customization) + l.setWordWrap(True) + if settings.extra_customization: + self.opt_extra_customization.setText(settings.extra_customization) + self.extra_layout.addWidget(l) + self.extra_layout.addWidget(self.opt_extra_customization) self.opt_save_template.setText(settings.save_template) diff --git a/src/calibre/gui2/device_drivers/configwidget.ui b/src/calibre/gui2/device_drivers/configwidget.ui index 1e8ee75852..f4902a7387 100644 --- a/src/calibre/gui2/device_drivers/configwidget.ui +++ b/src/calibre/gui2/device_drivers/configwidget.ui @@ -98,20 +98,7 @@ - - - Extra customization - - - true - - - opt_extra_customization - - - - - + diff --git a/src/calibre/library/catalog.py b/src/calibre/library/catalog.py index ae61d7cf52..0a5d5284e2 100644 --- a/src/calibre/library/catalog.py +++ b/src/calibre/library/catalog.py @@ -15,7 +15,7 @@ from calibre.customize import CatalogPlugin from calibre.customize.conversion import OptionRecommendation, DummyReporter from calibre.ebooks.BeautifulSoup import BeautifulSoup, BeautifulStoneSoup, Tag, NavigableString from calibre.ebooks.chardet import substitute_entites -from calibre.ebooks.oeb.base import RECOVER_PARSER, XHTML_NS +from calibre.ebooks.oeb.base import XHTML_NS from calibre.ptempfile import PersistentTemporaryDirectory from calibre.utils.config import config_dir from calibre.utils.date import format_date, isoformat, now as nowf