Pull from trunk

This commit is contained in:
Kovid Goyal 2010-09-11 16:17:22 -06:00
commit a4fe814d52
8 changed files with 70 additions and 48 deletions

View File

@ -166,6 +166,17 @@ class HTMLPreProcessor(object):
(re.compile(u'`\s*(<br.*?>)*\s*O', re.UNICODE), lambda match: u'Ò'), (re.compile(u'`\s*(<br.*?>)*\s*O', re.UNICODE), lambda match: u'Ò'),
(re.compile(u'`\s*(<br.*?>)*\s*u', re.UNICODE), lambda match: u'ù'), (re.compile(u'`\s*(<br.*?>)*\s*u', re.UNICODE), lambda match: u'ù'),
(re.compile(u'`\s*(<br.*?>)*\s*U', re.UNICODE), lambda match: u'Ù'), (re.compile(u'`\s*(<br.*?>)*\s*U', re.UNICODE), lambda match: u'Ù'),
# ` with letter before
(re.compile(u'a\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'à'),
(re.compile(u'A\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'À'),
(re.compile(u'e\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'è'),
(re.compile(u'E\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'È'),
(re.compile(u'i\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'ì'),
(re.compile(u'I\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'Ì'),
(re.compile(u'o\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'ò'),
(re.compile(u'O\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'Ò'),
(re.compile(u'u\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'ù'),
(re.compile(u'U\s*(<br.*?>)*\s*`', re.UNICODE), lambda match: u'Ù'),
# ´ # ´
(re.compile(u'´\s*(<br.*?>)*\s*a', re.UNICODE), lambda match: u'á'), (re.compile(u'´\s*(<br.*?>)*\s*a', re.UNICODE), lambda match: u'á'),

View File

@ -207,6 +207,7 @@ class PML_HTMLizer(object):
while html != old: while html != old:
old = html old = html
html = self.cleanup_html_remove_redundant(html) html = self.cleanup_html_remove_redundant(html)
html = re.sub(r'(?imu)^\s*', '', html)
return html return html
def cleanup_html_remove_redundant(self, html): def cleanup_html_remove_redundant(self, html):
@ -216,7 +217,7 @@ class PML_HTMLizer(object):
html = re.sub(r'(?u)%s\s*%s' % (open % '.*?', close), '', html) html = re.sub(r'(?u)%s\s*%s' % (open % '.*?', close), '', html)
else: else:
html = re.sub(r'(?u)%s\s*%s' % (open, close), '', html) html = re.sub(r'(?u)%s\s*%s' % (open, close), '', html)
html = re.sub(r'<p>\s*</p>', '', html) html = re.sub(r'(?imu)<p>\s*</p>', '', html)
return html return html
def start_line(self): def start_line(self):
@ -556,7 +557,7 @@ class PML_HTMLizer(object):
text = t text = t
else: else:
self.toc.add_item(os.path.basename(self.file_name), id, value) self.toc.add_item(os.path.basename(self.file_name), id, value)
text = '<span id="%s"></span>%s' % (id, t) text = '%s<span id="%s"></span>' % (t, id)
elif c == 'm': elif c == 'm':
empty = False empty = False
src = self.code_value(line) src = self.code_value(line)

View File

@ -77,7 +77,7 @@ def separate_paragraphs_print_formatted(txt):
def preserve_spaces(txt): def preserve_spaces(txt):
txt = txt.replace(' ', '&nbsp;') txt = txt.replace(' ', '&nbsp;')
txt = txt.replace('\t', '&#09;') txt = txt.replace('\t', '&nbsp;&nbsp;&nbsp;&nbsp;')
return txt return txt
def opf_writer(path, opf_name, manifest, spine, mi): def opf_writer(path, opf_name, manifest, spine, mi):

View File

@ -121,10 +121,8 @@ class BooksModel(QAbstractTableModel): # {{{
def set_device_connected(self, is_connected): def set_device_connected(self, is_connected):
self.device_connected = is_connected self.device_connected = is_connected
self.db.refresh_ondevice() self.db.refresh_ondevice()
self.refresh() self.refresh() # does a resort()
self.research() self.research()
if is_connected and self.sorted_on[0] == 'ondevice':
self.resort()
def set_book_on_device_func(self, func): def set_book_on_device_func(self, func):
self.book_on_device = func self.book_on_device = func
@ -249,7 +247,7 @@ class BooksModel(QAbstractTableModel): # {{{
# the search and count records for restrictions # the search and count records for restrictions
self.searched.emit(True) self.searched.emit(True)
def sort(self, col, order, reset=True): def sort(self, col, order, reset=True, update_history=True):
if not self.db: if not self.db:
return return
self.about_to_be_sorted.emit(self.db.id) self.about_to_be_sorted.emit(self.db.id)
@ -260,23 +258,23 @@ class BooksModel(QAbstractTableModel): # {{{
self.clear_caches() self.clear_caches()
self.reset() self.reset()
self.sorted_on = (label, order) self.sorted_on = (label, order)
if update_history:
self.sort_history.insert(0, self.sorted_on) self.sort_history.insert(0, self.sorted_on)
self.sorting_done.emit(self.db.index) self.sorting_done.emit(self.db.index)
def refresh(self, reset=True): def refresh(self, reset=True):
try:
col = self.column_map.index(self.sorted_on[0])
except:
col = 0
self.db.refresh(field=None) self.db.refresh(field=None)
self.sort(col, self.sorted_on[1], reset=reset) self.resort(reset=reset)
def resort(self, reset=True): def resort(self, reset=True, history=5): # Bug report needed history=4 :)
for col,ord in reversed(self.sort_history[:history]):
try: try:
col = self.column_map.index(self.sorted_on[0]) col = self.column_map.index(col)
except ValueError: except ValueError:
col = 0 col = 0
self.sort(col, self.sorted_on[1], reset=reset) self.sort(col, ord, reset=False, update_history=False)
if reset:
self.reset()
def research(self, reset=True): def research(self, reset=True):
self.search(self.last_search, reset=reset) self.search(self.last_search, reset=reset)

View File

@ -512,7 +512,8 @@ class TagsModel(QAbstractItemModel): # {{{
_('The saved search name %s is already used.')%val).exec_() _('The saved search name %s is already used.')%val).exec_()
return False return False
saved_searches().rename(unicode(item.data(role).toString()), val) saved_searches().rename(unicode(item.data(role).toString()), val)
self.tags_view.search_item_renamed.emit() item.tag.name = val
self.tags_view.search_item_renamed.emit() # Does a refresh
else: else:
if key == 'series': if key == 'series':
self.db.rename_series(item.tag.id, val) self.db.rename_series(item.tag.id, val)
@ -669,7 +670,7 @@ class TagBrowserMixin(object): # {{{
self.tags_view.saved_search_edit.connect(self.do_saved_search_edit) self.tags_view.saved_search_edit.connect(self.do_saved_search_edit)
self.tags_view.author_sort_edit.connect(self.do_author_sort_edit) self.tags_view.author_sort_edit.connect(self.do_author_sort_edit)
self.tags_view.tag_item_renamed.connect(self.do_tag_item_renamed) self.tags_view.tag_item_renamed.connect(self.do_tag_item_renamed)
self.tags_view.search_item_renamed.connect(self.saved_search.clear_to_help) self.tags_view.search_item_renamed.connect(self.saved_searches_changed)
self.edit_categories.clicked.connect(lambda x: self.edit_categories.clicked.connect(lambda x:
self.do_user_categories_edit()) self.do_user_categories_edit())

View File

@ -141,6 +141,8 @@ class ResultCache(SearchQueryParser):
for x in self.iterall(): for x in self.iterall():
yield x[idx] yield x[idx]
# Search functions {{{
def universal_set(self): def universal_set(self):
return set([i[0] for i in self._data if i is not None]) return set([i[0] for i in self._data if i is not None])
@ -462,6 +464,30 @@ class ResultCache(SearchQueryParser):
continue continue
return matches return matches
def search(self, query, return_matches=False):
ans = self.search_getting_ids(query, self.search_restriction)
if return_matches:
return ans
self._map_filtered = ans
def search_getting_ids(self, query, search_restriction):
q = ''
if not query or not query.strip():
q = search_restriction
else:
q = query
if search_restriction:
q = u'%s (%s)' % (search_restriction, query)
if not q:
return list(self._map)
matches = sorted(self.parse(q))
return [id for id in self._map if id in matches]
def set_search_restriction(self, s):
self.search_restriction = s
# }}}
def remove(self, id): def remove(self, id):
self._data[id] = None self._data[id] = None
if id in self._map: if id in self._map:
@ -549,7 +575,9 @@ class ResultCache(SearchQueryParser):
self.sort(field, ascending) self.sort(field, ascending)
self._map_filtered = list(self._map) self._map_filtered = list(self._map)
if self.search_restriction: if self.search_restriction:
self.search('', return_matches=False, ignore_search_restriction=False) self.search('', return_matches=False)
# Sorting functions {{{
def seriescmp(self, sidx, siidx, x, y, library_order=None): def seriescmp(self, sidx, siidx, x, y, library_order=None):
try: try:
@ -615,24 +643,6 @@ class ResultCache(SearchQueryParser):
self._map.sort(cmp=fcmp, reverse=not ascending) self._map.sort(cmp=fcmp, reverse=not ascending)
self._map_filtered = [id for id in self._map if id in self._map_filtered] self._map_filtered = [id for id in self._map if id in self._map_filtered]
def search(self, query, return_matches=False): # }}}
ans = self.search_getting_ids(query, self.search_restriction)
if return_matches:
return ans
self._map_filtered = ans
def search_getting_ids(self, query, search_restriction):
q = ''
if not query or not query.strip():
q = search_restriction
else:
q = query
if search_restriction:
q = u'%s (%s)' % (search_restriction, query)
if not q:
return list(self._map)
matches = sorted(self.parse(q))
return [id for id in self._map if id in matches]
def set_search_restriction(self, s):
self.search_restriction = s

View File

@ -69,6 +69,8 @@ class FieldMetadata(dict):
VALID_DATA_TYPES = frozenset([None, 'rating', 'text', 'comments', 'datetime', VALID_DATA_TYPES = frozenset([None, 'rating', 'text', 'comments', 'datetime',
'int', 'float', 'bool', 'series']) 'int', 'float', 'bool', 'series'])
# Builtin metadata {{{
_field_metadata = [ _field_metadata = [
('authors', {'table':'authors', ('authors', {'table':'authors',
'column':'name', 'column':'name',
@ -288,6 +290,7 @@ class FieldMetadata(dict):
'is_custom':False, 'is_custom':False,
'is_category':False}), 'is_category':False}),
] ]
# }}}
# search labels that are not db columns # search labels that are not db columns
search_items = [ 'all', search_items = [ 'all',

View File

@ -54,10 +54,8 @@ def shorten_components_to(length, components):
r = x[0] if x is components[-1] else '' r = x[0] if x is components[-1] else ''
else: else:
if x is components[-1]: if x is components[-1]:
b, _, e = x.rpartition('.') b, e = os.path.splitext(x)
if not b and e: if e == '.': e = ''
b = e
e = ''
r = b[:-delta]+e r = b[:-delta]+e
if r.startswith('.'): r = x[0]+r if r.startswith('.'): r = x[0]+r
else: else: