diff --git a/src/calibre/devices/interface.py b/src/calibre/devices/interface.py index 6bbb658f2c..ed51962236 100644 --- a/src/calibre/devices/interface.py +++ b/src/calibre/devices/interface.py @@ -150,10 +150,13 @@ def add_books_to_metadata(cls, locations, metadata, booklists): the device. @param locations: Result of a call to L{upload_books} @param metadata: List of dictionaries. Each dictionary must have the - keys C{title}, C{authors}, C{cover}, C{tags}. The value of the C{cover} + keys C{title}, C{authors}, C{author_sort}, C{cover}, C{tags}. + The value of the C{cover} element can be None or a three element tuple (width, height, data) where data is the image data in JPEG format as a string. C{tags} must be a possibly empty list of strings. C{authors} must be a string. + C{author_sort} may be None. It is upto the driver to decide whether to + use C{author_sort} or not. The dictionary can also have an optional key "tag order" which should be another dictionary that maps tag names to lists of book ids. The ids are ids from the book database. diff --git a/src/calibre/devices/prs505/books.py b/src/calibre/devices/prs505/books.py index 06d205fb02..38b708a312 100644 --- a/src/calibre/devices/prs505/books.py +++ b/src/calibre/devices/prs505/books.py @@ -55,7 +55,7 @@ class Book(object): title = book_metadata_field("title") authors = book_metadata_field("author", \ - formatter=lambda x: x if x and x.strip() else "Unknown") + formatter=lambda x: x if x and x.strip() else _('Unknown')) mime = book_metadata_field("mime") rpath = book_metadata_field("path") id = book_metadata_field("id", formatter=int) @@ -193,7 +193,7 @@ def add_book(self, info, name, size, ctime): attrs = { "title" : info["title"], 'titleSorter' : sortable_title(info['title']), - "author" : info["authors"] if info['authors'] else 'Unknown', \ + "author" : info["authors"] if info['authors'] else _('Unknown'), "page":"0", "part":"0", "scale":"0", \ "sourceid":sourceid, "id":str(cid), "date":"", \ "mime":mime, "path":name, "size":str(size) diff --git a/src/calibre/ebooks/metadata/opf2.py b/src/calibre/ebooks/metadata/opf2.py index 2e3b5ff047..c172d26e1a 100644 --- a/src/calibre/ebooks/metadata/opf2.py +++ b/src/calibre/ebooks/metadata/opf2.py @@ -18,7 +18,7 @@ from calibre import relpath from calibre.constants import __appname__, __version__ from calibre.ebooks.metadata.toc import TOC -from calibre.ebooks.metadata import MetaInformation +from calibre.ebooks.metadata import MetaInformation, string_to_authors class Resource(object): @@ -614,7 +614,7 @@ def authors(): def fget(self): ans = [] for elem in self.authors_path(self.metadata): - ans.extend([x.strip() for x in self.get_text(elem).split(',')]) + ans.extend(string_to_authors(self.get_text(elem))) return ans def fset(self, val): @@ -624,8 +624,8 @@ def fset(self, val): for author in val: attrib = {'{%s}role'%self.NAMESPACES['opf']: 'aut'} elem = self.create_metadata_element('creator', attrib=attrib) - self.set_text(elem, author) - + self.set_text(elem, author.strip()) + return property(fget=fget, fset=fset) @apply diff --git a/src/calibre/gui2/dialogs/config.py b/src/calibre/gui2/dialogs/config.py index bbd5475e2b..2b093a45b5 100644 --- a/src/calibre/gui2/dialogs/config.py +++ b/src/calibre/gui2/dialogs/config.py @@ -180,11 +180,12 @@ def __init__(self, window, db, server=None): self.toolbar_button_size.setCurrentIndex(0 if icons == self.ICON_SIZES[0] else 1 if icons == self.ICON_SIZES[1] else 2) self.show_toolbar_text.setChecked(config['show_text_in_toolbar']) - for ext in BOOK_EXTENSIONS: + book_exts = sorted(BOOK_EXTENSIONS) + for ext in book_exts: self.single_format.addItem(ext.upper(), QVariant(ext)) single_format = config['save_to_disk_single_format'] - self.single_format.setCurrentIndex(BOOK_EXTENSIONS.index(single_format)) + self.single_format.setCurrentIndex(book_exts.index(single_format)) self.cover_browse.setValue(config['cover_flow_queue_length']) self.systray_notifications.setChecked(not config['disable_tray_notification']) from calibre.translations.compiled import translations @@ -203,7 +204,7 @@ def __init__(self, window, db, server=None): self.pdf_metadata.setChecked(prefs['read_file_metadata']) added_html = False - for ext in BOOK_EXTENSIONS: + for ext in book_exts: ext = ext.lower() ext = re.sub(r'(x{0,1})htm(l{0,1})', 'html', ext) if ext == 'lrf' or is_supported('book.'+ext): diff --git a/src/calibre/gui2/library.py b/src/calibre/gui2/library.py index 1868623787..38652ad971 100644 --- a/src/calibre/gui2/library.py +++ b/src/calibre/gui2/library.py @@ -20,6 +20,7 @@ error_dialog from calibre.utils.search_query_parser import SearchQueryParser from calibre.ebooks.metadata.meta import set_metadata as _set_metadata +from calibre.ebooks.metadata import string_to_authors class LibraryDelegate(QItemDelegate): COLOR = QColor("blue") @@ -364,12 +365,13 @@ def get_book_info(self, index): return data - def get_metadata(self, rows, rows_are_ids=False): - metadata = [] + def get_metadata(self, rows, rows_are_ids=False, full_metadata=False): + metadata, _full_metadata = [], [] if not rows_are_ids: rows = [self.db.id(row.row()) for row in rows] for id in rows: mi = self.db.get_metadata(id, index_is_id=True) + _full_metadata.append(mi) au = authors_to_string(mi.authors if mi.authors else [_('Unknown')]) tags = mi.tags if mi.tags else [] if mi.series is not None: @@ -377,6 +379,7 @@ def get_metadata(self, rows, rows_are_ids=False): info = { 'title' : mi.title, 'authors' : au, + 'author_sort' : mi.author_sort, 'cover' : self.db.cover(id, index_is_id=True), 'tags' : tags, 'comments': mi.comments, @@ -387,7 +390,10 @@ def get_metadata(self, rows, rows_are_ids=False): } metadata.append(info) - return metadata + if full_metadata: + return metadata, _full_metadata + else: + return metadata def get_preferred_formats_from_ids(self, ids, all_formats, mode='r+b'): ans = [] @@ -928,12 +934,8 @@ def data(self, index, role): au = self.unknown if role == Qt.EditRole: return QVariant(au) - au = au.split(',') - authors = [] - for i in au: - authors += i.strip().split('&') - jau = [ a.strip() for a in authors ] - return QVariant("\n".join(jau)) + authors = string_to_authors(au) + return QVariant("\n".join(authors)) elif col == 2: size = self.db[self.map[row]].size return QVariant(BooksView.human_readable(size)) diff --git a/src/calibre/gui2/main.py b/src/calibre/gui2/main.py index b4049fc739..3972e00bdd 100644 --- a/src/calibre/gui2/main.py +++ b/src/calibre/gui2/main.py @@ -1,3 +1,4 @@ +from __future__ import with_statement __license__ = 'GPL v3' __copyright__ = '2008, Kovid Goyal ' import os, sys, textwrap, collections, traceback, time @@ -910,12 +911,13 @@ def sync_to_device(self, on_card, delete_from_library, specific_format=None): if not self.device_manager or not rows or len(rows) == 0: return ids = iter(self.library_view.model().id(r) for r in rows) - metadata = self.library_view.model().get_metadata(rows) + metadata, full_metadata = self.library_view.model().get_metadata( + rows, full_metadata=True) for mi in metadata: cdata = mi['cover'] if cdata: mi['cover'] = self.cover_to_thumbnail(cdata) - metadata = iter(metadata) + metadata, full_metadata = iter(metadata), iter(full_metadata) _files = self.library_view.model().get_preferred_formats(rows, self.device_manager.device_class.FORMATS, paths=True, set_metadata=True, @@ -923,22 +925,15 @@ def sync_to_device(self, on_card, delete_from_library, specific_format=None): files = [getattr(f, 'name', None) for f in _files] bad, good, gf, names, remove_ids = [], [], [], [], [] for f in files: - mi = metadata.next() + mi, smi = metadata.next(), full_metadata.next() id = ids.next() if f is None: bad.append(mi['title']) else: remove_ids.append(id) - aus = mi['authors'].split(',') - aus2 = [] - for a in aus: - aus2.extend(a.split('&')) try: - smi = MetaInformation(mi['title'], aus2) - smi.comments = mi.get('comments', None) - _f = open(f, 'r+b') - set_metadata(_f, smi, f.rpartition('.')[2]) - _f.close() + with open(f, 'r+b') as _f: + set_metadata(_f, smi, f.rpartition('.')[2]) except: print 'Error setting metadata in book:', mi['title'] traceback.print_exc()