mirror of
https://github.com/kovidgoyal/calibre.git
synced 2025-07-09 03:04:10 -04:00
Add a new function booksize() to the template language to get the value of the size column in calibre. Fix ratings in templates being multiplied by 2
This commit is contained in:
commit
cd93a31066
@ -592,7 +592,7 @@ class Metadata(object):
|
||||
elif datatype == 'bool':
|
||||
res = _('Yes') if res else _('No')
|
||||
elif datatype == 'rating':
|
||||
res = res/2
|
||||
res = res/2.0
|
||||
return (name, unicode(res), orig_res, cmeta)
|
||||
|
||||
# convert top-level ids into their value
|
||||
@ -625,6 +625,8 @@ class Metadata(object):
|
||||
res = res + ' [%s]'%self.format_series_index()
|
||||
elif datatype == 'datetime':
|
||||
res = format_date(res, fmeta['display'].get('date_format','dd MMM yyyy'))
|
||||
elif datatype == 'rating':
|
||||
res = res/2.0
|
||||
return (name, unicode(res), orig_res, fmeta)
|
||||
|
||||
return (None, None, None, None)
|
||||
|
@ -7,7 +7,7 @@ import os, traceback, Queue, time, cStringIO, re, sys
|
||||
from threading import Thread
|
||||
|
||||
from PyQt4.Qt import QMenu, QAction, QActionGroup, QIcon, SIGNAL, \
|
||||
Qt, pyqtSignal, QDialog
|
||||
Qt, pyqtSignal, QDialog, QObject
|
||||
|
||||
from calibre.customize.ui import available_input_formats, available_output_formats, \
|
||||
device_plugins
|
||||
@ -587,18 +587,26 @@ class DeviceMenu(QMenu): # {{{
|
||||
|
||||
# }}}
|
||||
|
||||
class DeviceMixin(object): # {{{
|
||||
|
||||
class DeviceSignals(QObject):
|
||||
#: This signal is emitted once, after metadata is downloaded from the
|
||||
#: connected device.
|
||||
#: The sequence: gui.device_manager.is_device_connected will become True,
|
||||
#: and the device_connection_changed signal will be emitted,
|
||||
#: then sometime later gui.device_metadata_available will be signaled.
|
||||
#: This does not mean that there are no more jobs running. Automatic metadata
|
||||
#: management might have kicked off a sync_booklists to write new metadata onto
|
||||
#: the device, and that job might still be running when the signal is emitted.
|
||||
device_metadata_available = pyqtSignal()
|
||||
|
||||
#: This signal is emitted once when the device is detected and once when
|
||||
#: it is disconnected. If the parameter is True, then it is a connection,
|
||||
#: otherwise a disconnection.
|
||||
device_connection_changed = pyqtSignal(object)
|
||||
|
||||
device_signals = DeviceSignals()
|
||||
|
||||
class DeviceMixin(object): # {{{
|
||||
|
||||
def __init__(self):
|
||||
self.device_error_dialog = error_dialog(self, _('Error'),
|
||||
_('Error communicating with device'), ' ')
|
||||
@ -745,7 +753,7 @@ class DeviceMixin(object): # {{{
|
||||
self.location_manager.update_devices()
|
||||
self.library_view.set_device_connected(self.device_connected)
|
||||
self.refresh_ondevice()
|
||||
self.device_connection_changed.emit(connected)
|
||||
device_signals.device_connection_changed.emit(connected)
|
||||
|
||||
def info_read(self, job):
|
||||
'''
|
||||
@ -784,7 +792,7 @@ class DeviceMixin(object): # {{{
|
||||
self.sync_news()
|
||||
self.sync_catalogs()
|
||||
self.refresh_ondevice()
|
||||
self.device_metadata_available.emit()
|
||||
device_signals.device_metadata_available.emit()
|
||||
|
||||
def refresh_ondevice(self, reset_only = False):
|
||||
'''
|
||||
|
@ -156,8 +156,6 @@ class SearchBar(QWidget): # {{{
|
||||
x = ComboBoxWithHelp(self)
|
||||
x.setMaximumSize(QSize(150, 16777215))
|
||||
x.setObjectName("search_restriction")
|
||||
x.setToolTip(_('Books display will be restricted to those matching the '
|
||||
'selected saved search'))
|
||||
l.addWidget(x)
|
||||
parent.search_restriction = x
|
||||
|
||||
|
@ -17,6 +17,10 @@ class SearchRestrictionMixin(object):
|
||||
self.search_restriction.setMinimumContentsLength(10)
|
||||
self.search_restriction.setStatusTip(self.search_restriction.toolTip())
|
||||
self.search_count.setText(_("(all books)"))
|
||||
self.search_restriction_tooltip = \
|
||||
_('Books display will be restricted to those matching a '
|
||||
'selected saved search')
|
||||
self.search_restriction.setToolTip(self.search_restriction_tooltip)
|
||||
|
||||
def apply_named_search_restriction(self, name):
|
||||
if not name:
|
||||
@ -30,22 +34,31 @@ class SearchRestrictionMixin(object):
|
||||
self.apply_search_restriction(r)
|
||||
|
||||
def apply_text_search_restriction(self, search):
|
||||
search = unicode(search)
|
||||
if not search:
|
||||
self.search_restriction.setItemText(1, _('*Current search'))
|
||||
self.search_restriction.setCurrentIndex(0)
|
||||
else:
|
||||
self.search_restriction.setCurrentIndex(1)
|
||||
self.search_restriction.setItemText(1, search)
|
||||
s = '*' + search
|
||||
if self.search_restriction.count() > 1:
|
||||
txt = unicode(self.search_restriction.itemText(2))
|
||||
if txt.startswith('*'):
|
||||
self.search_restriction.setItemText(2, s)
|
||||
else:
|
||||
self.search_restriction.insertItem(2, s)
|
||||
else:
|
||||
self.search_restriction.insertItem(2, s)
|
||||
self.search_restriction.setCurrentIndex(2)
|
||||
self.search_restriction.setToolTip('<p>' +
|
||||
self.search_restriction_tooltip +
|
||||
_(' or the search ') + "'" + search + "'</p>")
|
||||
self._apply_search_restriction(search)
|
||||
|
||||
def apply_search_restriction(self, i):
|
||||
self.search_restriction.setItemText(1, _('*Current search'))
|
||||
if i == 1:
|
||||
restriction = unicode(self.search.currentText())
|
||||
if not restriction:
|
||||
self.search_restriction.setCurrentIndex(0)
|
||||
else:
|
||||
self.search_restriction.setItemText(1, restriction)
|
||||
self.apply_text_search_restriction(unicode(self.search.currentText()))
|
||||
elif i == 2 and unicode(self.search_restriction.currentText()).startswith('*'):
|
||||
self.apply_text_search_restriction(
|
||||
unicode(self.search_restriction.currentText())[1:])
|
||||
else:
|
||||
r = unicode(self.search_restriction.currentText())
|
||||
if r is not None and r != '':
|
||||
|
@ -853,6 +853,7 @@ class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns):
|
||||
mi.pubdate = row[fm['pubdate']]
|
||||
mi.uuid = row[fm['uuid']]
|
||||
mi.title_sort = row[fm['sort']]
|
||||
mi.book_size = row[fm['size']]
|
||||
mi.last_modified = row[fm['last_modified']]
|
||||
formats = row[fm['formats']]
|
||||
if not formats:
|
||||
@ -1378,13 +1379,15 @@ class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns):
|
||||
for (cat, dex, mult, is_comp) in md:
|
||||
if not book[dex]:
|
||||
continue
|
||||
tid_cat = tids[cat]
|
||||
tcats_cat = tcategories[cat]
|
||||
if not mult:
|
||||
val = book[dex]
|
||||
if is_comp:
|
||||
item = tcategories[cat].get(val, None)
|
||||
item = tcats_cat.get(val, None)
|
||||
if not item:
|
||||
item = tag_class(val, val)
|
||||
tcategories[cat][val] = item
|
||||
tcats_cat[val] = item
|
||||
item.c += 1
|
||||
item.id = val
|
||||
if rating > 0:
|
||||
@ -1392,11 +1395,11 @@ class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns):
|
||||
item.rc += 1
|
||||
continue
|
||||
try:
|
||||
(item_id, sort_val) = tids[cat][val] # let exceptions fly
|
||||
item = tcategories[cat].get(val, None)
|
||||
(item_id, sort_val) = tid_cat[val] # let exceptions fly
|
||||
item = tcats_cat.get(val, None)
|
||||
if not item:
|
||||
item = tag_class(val, sort_val)
|
||||
tcategories[cat][val] = item
|
||||
tcats_cat[val] = item
|
||||
item.c += 1
|
||||
item.id_set.add(book[0])
|
||||
item.id = item_id
|
||||
@ -1410,21 +1413,15 @@ class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns):
|
||||
if is_comp:
|
||||
vals = [v.strip() for v in vals if v.strip()]
|
||||
for val in vals:
|
||||
if val not in tids:
|
||||
tids[cat][val] = (val, val)
|
||||
item = tcategories[cat].get(val, None)
|
||||
if not item:
|
||||
item = tag_class(val, val)
|
||||
tcategories[cat][val] = item
|
||||
item.c += 1
|
||||
item.id = val
|
||||
if val not in tid_cat:
|
||||
tid_cat[val] = (val, val)
|
||||
for val in vals:
|
||||
try:
|
||||
(item_id, sort_val) = tids[cat][val] # let exceptions fly
|
||||
item = tcategories[cat].get(val, None)
|
||||
(item_id, sort_val) = tid_cat[val] # let exceptions fly
|
||||
item = tcats_cat.get(val, None)
|
||||
if not item:
|
||||
item = tag_class(val, sort_val)
|
||||
tcategories[cat][val] = item
|
||||
tcats_cat[val] = item
|
||||
item.c += 1
|
||||
item.id_set.add(book[0])
|
||||
item.id = item_id
|
||||
|
@ -198,7 +198,6 @@ def get_components(template, mi, id, timefmt='%b %Y', length=250,
|
||||
for key in custom_metadata:
|
||||
if key in format_args:
|
||||
cm = custom_metadata[key]
|
||||
## TODO: NEWMETA: should ratings be divided by 2? The standard rating isn't...
|
||||
if cm['datatype'] == 'series':
|
||||
format_args[key] = title_sort(format_args[key], order=tsorder)
|
||||
if key+'_index' in format_args:
|
||||
|
@ -230,6 +230,7 @@ The following functions are available in addition to those described in single-f
|
||||
|
||||
* ``add(x, y)`` -- returns x + y. Throws an exception if either x or y are not numbers.
|
||||
* ``assign(id, val)`` -- assigns val to id, then returns val. id must be an identifier, not an expression
|
||||
* ``booksize()`` -- returns the value of the |app| 'size' field. Returns '' if there are no formats.
|
||||
* ``cmp(x, y, lt, eq, gt)`` -- compares x and y after converting both to numbers. Returns ``lt`` if x < y. Returns ``eq`` if x == y. Otherwise returns ``gt``.
|
||||
* ``divide(x, y)`` -- returns x / y. Throws an exception if either x or y are not numbers.
|
||||
* ``field(name)`` -- returns the metadata field named by ``name``.
|
||||
|
@ -549,8 +549,22 @@ class BuiltinCapitalize(BuiltinFormatterFunction):
|
||||
def evaluate(self, formatter, kwargs, mi, locals, val):
|
||||
return capitalize(val)
|
||||
|
||||
class BuiltinBooksize(BuiltinFormatterFunction):
|
||||
name = 'booksize'
|
||||
arg_count = 0
|
||||
doc = _('booksize() -- return value of the field capitalized')
|
||||
|
||||
def evaluate(self, formatter, kwargs, mi, locals):
|
||||
if mi.book_size is not None:
|
||||
try:
|
||||
return str(mi.book_size)
|
||||
except:
|
||||
pass
|
||||
return ''
|
||||
|
||||
builtin_add = BuiltinAdd()
|
||||
builtin_assign = BuiltinAssign()
|
||||
builtin_booksize = BuiltinBooksize()
|
||||
builtin_capitalize = BuiltinCapitalize()
|
||||
builtin_cmp = BuiltinCmp()
|
||||
builtin_contains = BuiltinContains()
|
||||
|
Loading…
x
Reference in New Issue
Block a user