From 020286b746241b54a09f9078203b6bab2560d30e Mon Sep 17 00:00:00 2001
From: Kovid Goyal
Date: Thu, 12 Aug 2010 18:50:57 -0600
Subject: [PATCH] Migrate delete action and location_selected code
---
src/calibre/customize/builtins.py | 6 +-
src/calibre/gui2/actions/__init__.py | 3 +
src/calibre/gui2/actions/convert.py | 3 +
src/calibre/gui2/actions/delete.py | 80 ++++++++++++++++-------
src/calibre/gui2/actions/edit_metadata.py | 4 ++
src/calibre/gui2/actions/fetch_news.py | 4 ++
src/calibre/gui2/actions/view.py | 5 ++
src/calibre/gui2/device.py | 5 +-
src/calibre/gui2/layout.py | 16 -----
src/calibre/gui2/ui.py | 13 +---
10 files changed, 84 insertions(+), 55 deletions(-)
diff --git a/src/calibre/customize/builtins.py b/src/calibre/customize/builtins.py
index 8462ae5d38..8232a163e7 100644
--- a/src/calibre/customize/builtins.py
+++ b/src/calibre/customize/builtins.py
@@ -593,5 +593,9 @@ class ActionConvert(InterfaceActionBase):
name = 'Convert Books'
actual_plugin = 'calibre.gui2.actions.convert:ConvertAction'
+class ActionDelete(InterfaceActionBase):
+ name = 'Remove Books'
+ actual_plugin = 'calibre.gui2.actions.delete:DeleteAction'
+
plugins += [ActionAdd, ActionFetchAnnotations, ActionGenerateCatalog,
- ActionConvert]
+ ActionConvert, ActionDelete]
diff --git a/src/calibre/gui2/actions/__init__.py b/src/calibre/gui2/actions/__init__.py
index 65d0078c50..b198a69214 100644
--- a/src/calibre/gui2/actions/__init__.py
+++ b/src/calibre/gui2/actions/__init__.py
@@ -52,3 +52,6 @@ class InterfaceAction(QObject):
def genesis(self):
pass
+ def location_selected(self, loc):
+ pass
+
diff --git a/src/calibre/gui2/actions/convert.py b/src/calibre/gui2/actions/convert.py
index ace877b315..0641cc6a97 100644
--- a/src/calibre/gui2/actions/convert.py
+++ b/src/calibre/gui2/actions/convert.py
@@ -35,6 +35,9 @@ class ConvertAction(InterfaceAction):
self.convert_menu = cm
self.conversion_jobs = {}
+ def location_selected(self, loc):
+ enabled = loc == 'library'
+ self.qaction.setEnabled(enabled)
def auto_convert(self, book_ids, on_card, format):
previous = self.gui.library_view.currentIndex()
diff --git a/src/calibre/gui2/actions/delete.py b/src/calibre/gui2/actions/delete.py
index de3c4d8868..e0f3ae4d65 100644
--- a/src/calibre/gui2/actions/delete.py
+++ b/src/calibre/gui2/actions/delete.py
@@ -5,16 +5,46 @@ __license__ = 'GPL v3'
__copyright__ = '2010, Kovid Goyal '
__docformat__ = 'restructuredtext en'
+from PyQt4.Qt import QMenu
+
from calibre.gui2 import error_dialog
from calibre.gui2.dialogs.delete_matching_from_device import DeleteMatchingFromDeviceDialog
from calibre.gui2.dialogs.confirm_delete import confirm
+from calibre.gui2.actions import InterfaceAction
-class DeleteAction(object):
+class DeleteAction(InterfaceAction):
+
+ name = 'Remove Books'
+ action_spec = (_('Remove books'), 'trash.svg', None, _('Del'))
+
+ def genesis(self):
+ self.qaction.triggered.connect(self.delete_books)
+ self.delete_menu = QMenu()
+ self.delete_menu.addAction(_('Remove selected books'), self.delete_books)
+ self.delete_menu.addAction(
+ _('Remove files of a specific format from selected books..'),
+ self.delete_selected_formats)
+ self.delete_menu.addAction(
+ _('Remove all formats from selected books, except...'),
+ self.delete_all_but_selected_formats)
+ self.delete_menu.addAction(
+ _('Remove covers from selected books'), self.delete_covers)
+ self.delete_menu.addSeparator()
+ self.delete_menu.addAction(
+ _('Remove matching books from device'),
+ self.remove_matching_books_from_device)
+ self.qaction.setMenu(self.delete_menu)
+ self.delete_memory = {}
+
+ def location_selected(self, loc):
+ enabled = loc == 'library'
+ for action in list(self.delete_menu.actions())[1:]:
+ action.setEnabled(enabled)
def _get_selected_formats(self, msg):
from calibre.gui2.dialogs.select_formats import SelectFormats
fmts = self.gui.library_view.model().db.all_formats()
- d = SelectFormats([x.lower() for x in fmts], msg, parent=self)
+ d = SelectFormats([x.lower() for x in fmts], msg, parent=self.gui)
if d.exec_() != d.Accepted:
return None
return d.selected_formats
@@ -22,7 +52,7 @@ class DeleteAction(object):
def _get_selected_ids(self, err_title=_('Cannot delete')):
rows = self.gui.library_view.selectionModel().selectedRows()
if not rows or len(rows) == 0:
- d = error_dialog(self, err_title, _('No book selected'))
+ d = error_dialog(self.gui, err_title, _('No book selected'))
d.exec_()
return set([])
return set(map(self.gui.library_view.model().id, rows))
@@ -43,7 +73,7 @@ class DeleteAction(object):
self.gui.library_view.model().current_changed(self.gui.library_view.currentIndex(),
self.gui.library_view.currentIndex())
if ids:
- self.tags_view.recount()
+ self.gui.tags_view.recount()
def delete_all_but_selected_formats(self, *args):
ids = self._get_selected_ids()
@@ -66,11 +96,11 @@ class DeleteAction(object):
self.gui.library_view.model().current_changed(self.gui.library_view.currentIndex(),
self.gui.library_view.currentIndex())
if ids:
- self.tags_view.recount()
+ self.gui.tags_view.recount()
def remove_matching_books_from_device(self, *args):
- if not self.device_manager.is_device_connected:
- d = error_dialog(self, _('Cannot delete books'),
+ if not self.gui.device_manager.is_device_connected:
+ d = error_dialog(self.gui, _('Cannot delete books'),
_('No device is connected'))
d.exec_()
return
@@ -81,18 +111,18 @@ class DeleteAction(object):
return
to_delete = {}
some_to_delete = False
- for model,name in ((self.memory_view.model(), _('Main memory')),
- (self.card_a_view.model(), _('Storage Card A')),
- (self.card_b_view.model(), _('Storage Card B'))):
+ for model,name in ((self.gui.memory_view.model(), _('Main memory')),
+ (self.gui.card_a_view.model(), _('Storage Card A')),
+ (self.gui.card_b_view.model(), _('Storage Card B'))):
to_delete[name] = (model, model.paths_for_db_ids(ids))
if len(to_delete[name][1]) > 0:
some_to_delete = True
if not some_to_delete:
- d = error_dialog(self, _('No books to delete'),
+ d = error_dialog(self.gui, _('No books to delete'),
_('None of the selected books are on the device'))
d.exec_()
return
- d = DeleteMatchingFromDeviceDialog(self, to_delete)
+ d = DeleteMatchingFromDeviceDialog(self.gui, to_delete)
if d.exec_():
paths = {}
ids = {}
@@ -103,10 +133,10 @@ class DeleteAction(object):
paths[model].append(path)
ids[model].append(id)
for model in paths:
- job = self.remove_paths(paths[model])
+ job = self.gui.remove_paths(paths[model])
self.delete_memory[job] = (paths[model], model)
model.mark_for_deletion(job, ids[model], rows_are_ids=True)
- self.status_bar.show_message(_('Deleting books from device.'), 1000)
+ self.gui.status_bar.show_message(_('Deleting books from device.'), 1000)
def delete_covers(self, *args):
ids = self._get_selected_ids()
@@ -126,18 +156,18 @@ class DeleteAction(object):
rows = view.selectionModel().selectedRows()
if not rows or len(rows) == 0:
return
- if self.stack.currentIndex() == 0:
+ if self.gui.stack.currentIndex() == 0:
if not confirm(''+_('The selected books will be '
'permanently deleted and the files '
'removed from your computer. Are you sure?')
- +'
', 'library_delete_books', self):
+ +'
', 'library_delete_books', self.gui):
return
ci = view.currentIndex()
row = None
if ci.isValid():
row = ci.row()
ids_deleted = view.model().delete_books(rows)
- for v in (self.memory_view, self.card_a_view, self.card_b_view):
+ for v in (self.gui.memory_view, self.gui.card_a_view, self.gui.card_b_view):
if v is None:
continue
v.model().clear_ondevice(ids_deleted)
@@ -149,17 +179,17 @@ class DeleteAction(object):
if not confirm(''+_('The selected books will be '
'permanently deleted '
'from your device. Are you sure?')
- +'
', 'device_delete_books', self):
+ +'', 'device_delete_books', self.gui):
return
- if self.stack.currentIndex() == 1:
- view = self.memory_view
- elif self.stack.currentIndex() == 2:
- view = self.card_a_view
+ if self.gui.stack.currentIndex() == 1:
+ view = self.gui.memory_view
+ elif self.gui.stack.currentIndex() == 2:
+ view = self.gui.card_a_view
else:
- view = self.card_b_view
+ view = self.gui.card_b_view
paths = view.model().paths(rows)
- job = self.remove_paths(paths)
+ job = self.gui.remove_paths(paths)
self.delete_memory[job] = (paths, view.model())
view.model().mark_for_deletion(job, rows)
- self.status_bar.show_message(_('Deleting books from device.'), 1000)
+ self.gui.status_bar.show_message(_('Deleting books from device.'), 1000)
diff --git a/src/calibre/gui2/actions/edit_metadata.py b/src/calibre/gui2/actions/edit_metadata.py
index 5c323e609d..e4b2145da0 100644
--- a/src/calibre/gui2/actions/edit_metadata.py
+++ b/src/calibre/gui2/actions/edit_metadata.py
@@ -17,6 +17,10 @@ from calibre.gui2.dialogs.tag_list_editor import TagListEditor
class EditMetadataAction(object):
+ def location_selected(self, loc):
+ enabled = loc == 'library'
+ self.qaction.setEnabled(enabled)
+
def download_metadata(self, checked, covers=True, set_metadata=True,
set_social_metadata=None):
rows = self.gui.library_view.selectionModel().selectedRows()
diff --git a/src/calibre/gui2/actions/fetch_news.py b/src/calibre/gui2/actions/fetch_news.py
index 361e3d63bd..d161877cea 100644
--- a/src/calibre/gui2/actions/fetch_news.py
+++ b/src/calibre/gui2/actions/fetch_news.py
@@ -11,6 +11,10 @@ from calibre.utils.config import dynamic
class FetchNewsAction(object):
+ def location_selected(self, loc):
+ enabled = loc == 'library'
+ self.qaction.setEnabled(enabled)
+
def genesis(self):
self.conversion_jobs = {}
diff --git a/src/calibre/gui2/actions/view.py b/src/calibre/gui2/actions/view.py
index bf445b40b2..bdad55d142 100644
--- a/src/calibre/gui2/actions/view.py
+++ b/src/calibre/gui2/actions/view.py
@@ -18,6 +18,11 @@ from calibre.ptempfile import PersistentTemporaryFile
class ViewAction(object):
+ def location_selected(self, loc):
+ enabled = loc == 'library'
+ for action in list(self.view_menu.actions())[1:]:
+ action.setEnabled(enabled)
+
def view_format(self, row, format):
fmt_path = self.gui.library_view.model().db.format_abspath(row, format)
if fmt_path:
diff --git a/src/calibre/gui2/device.py b/src/calibre/gui2/device.py
index 6cc8e47aa5..1e716a85fe 100644
--- a/src/calibre/gui2/device.py
+++ b/src/calibre/gui2/device.py
@@ -792,8 +792,9 @@ class DeviceMixin(object): # {{{
self.device_job_exception(job)
return
- if self.delete_memory.has_key(job):
- paths, model = self.delete_memory.pop(job)
+ dm = self.iactions['Remove Books'].delete_memory
+ if dm.has_key(job):
+ paths, model = dm.pop(job)
self.device_manager.remove_books_from_metadata(paths,
self.booklists())
model.paths_deleted(paths)
diff --git a/src/calibre/gui2/layout.py b/src/calibre/gui2/layout.py
index b0851c0b25..74da5f53d3 100644
--- a/src/calibre/gui2/layout.py
+++ b/src/calibre/gui2/layout.py
@@ -528,7 +528,6 @@ class MainWindowMixin(object):
md.addSeparator()
md.addAction(self.action_merge)
- self.action_del.triggered.connect(self.delete_books)
self.action_edit.triggered.connect(self.edit_metadata)
self.action_merge.triggered.connect(self.merge_books)
@@ -557,21 +556,6 @@ class MainWindowMixin(object):
self.action_view.setMenu(self.view_menu)
ac.triggered.connect(self.view_specific_format, type=Qt.QueuedConnection)
- self.delete_menu = QMenu()
- self.delete_menu.addAction(_('Remove selected books'), self.delete_books)
- self.delete_menu.addAction(
- _('Remove files of a specific format from selected books..'),
- self.delete_selected_formats)
- self.delete_menu.addAction(
- _('Remove all formats from selected books, except...'),
- self.delete_all_but_selected_formats)
- self.delete_menu.addAction(
- _('Remove covers from selected books'), self.delete_covers)
- self.delete_menu.addSeparator()
- self.delete_menu.addAction(
- _('Remove matching books from device'),
- self.remove_matching_books_from_device)
- self.action_del.setMenu(self.delete_menu)
self.action_open_containing_folder.setShortcut(Qt.Key_O)
self.addAction(self.action_open_containing_folder)
diff --git a/src/calibre/gui2/ui.py b/src/calibre/gui2/ui.py
index 79d16eeb5a..df0c9091b5 100644
--- a/src/calibre/gui2/ui.py
+++ b/src/calibre/gui2/ui.py
@@ -149,7 +149,6 @@ class Main(MainWindow, MainWindowMixin, DeviceMixin, # {{{
self.verbose = opts.verbose
self.get_metadata = GetMetadata()
self.upload_memory = {}
- self.delete_memory = {}
self.persistent_files = []
self.metadata_dialogs = []
self.default_thumbnail = None
@@ -437,26 +436,18 @@ class Main(MainWindow, MainWindowMixin, DeviceMixin, # {{{
for x in ('tb', 'cb'):
splitter = getattr(self, x+'_splitter')
splitter.button.setEnabled(location == 'library')
+ for action in self.iactions.values():
+ action.location_selected(location)
if location == 'library':
- self.action_edit.setEnabled(True)
self.action_merge.setEnabled(True)
- self.action_convert.setEnabled(True)
- self.view_menu.actions()[1].setEnabled(True)
self.action_open_containing_folder.setEnabled(True)
self.action_sync.setEnabled(True)
self.search_restriction.setEnabled(True)
- for action in list(self.delete_menu.actions())[1:]:
- action.setEnabled(True)
else:
- self.action_edit.setEnabled(False)
self.action_merge.setEnabled(False)
- self.action_convert.setEnabled(False)
- self.view_menu.actions()[1].setEnabled(False)
self.action_open_containing_folder.setEnabled(False)
self.action_sync.setEnabled(False)
self.search_restriction.setEnabled(False)
- for action in list(self.delete_menu.actions())[1:]:
- action.setEnabled(False)
# Reset the view in case something changed while it was invisible
self.current_view().reset()
self.set_number_of_books_shown()