Add ability to create additional empty formats to the "add empty book" command. Add a new command to add an empty format to existing books.

The code to add an empty docx should be added to oeb/polish/create.py
This commit is contained in:
Charles Haley 2015-03-28 10:11:47 +01:00
parent 407ee3ca17
commit 672f5dfd9a
3 changed files with 79 additions and 14 deletions

View File

@ -34,6 +34,8 @@ def create_toc(mi, opf, html_name, lang):
def create_book(mi, path, fmt='epub', opf_name='metadata.opf', html_name='start.xhtml', toc_name='toc.ncx'): def create_book(mi, path, fmt='epub', opf_name='metadata.opf', html_name='start.xhtml', toc_name='toc.ncx'):
''' Create an empty book in the specified format at the specified location. ''' ''' Create an empty book in the specified format at the specified location. '''
if fmt not in ['epub', 'azw3']:
return
path = os.path.abspath(path) path = os.path.abspath(path)
lang = 'und' lang = 'und'
opf = metadata_to_opf(mi, as_string=False) opf = metadata_to_opf(mi, as_string=False)

View File

@ -14,7 +14,7 @@ from PyQt5.Qt import QPixmap, QTimer
from calibre import as_unicode from calibre import as_unicode
from calibre.gui2 import (error_dialog, choose_files, choose_dir, from calibre.gui2 import (error_dialog, choose_files, choose_dir,
warning_dialog, info_dialog, gprefs) warning_dialog, info_dialog, gprefs)
from calibre.gui2.dialogs.add_empty_book import AddEmptyBookDialog from calibre.gui2.dialogs.add_empty_book import AddEmptyBookDialog, valid_empty_formats
from calibre.gui2.dialogs.confirm_delete import confirm from calibre.gui2.dialogs.confirm_delete import confirm
from calibre.gui2.dialogs.progress import ProgressDialog from calibre.gui2.dialogs.progress import ProgressDialog
from calibre.gui2.widgets import IMAGE_EXTENSIONS from calibre.gui2.widgets import IMAGE_EXTENSIONS
@ -72,13 +72,17 @@ class AddAction(InterfaceAction):
self.create_menu_action(arm, 'recursive-multiple-archive', _( self.create_menu_action(arm, 'recursive-multiple-archive', _(
'Multiple books per directory in the archive')).triggered.connect(partial(self.add_archive, False)) 'Multiple books per directory in the archive')).triggered.connect(partial(self.add_archive, False))
self.add_menu.addSeparator() self.add_menu.addSeparator()
self.add_menu.addSeparator()
ma('add-empty', _('Add Empty book. (Book entry with no formats)'), ma('add-empty', _('Add Empty book. (Book entry with no formats)'),
shortcut='Shift+Ctrl+E').triggered.connect(self.add_empty) shortcut='Shift+Ctrl+E').triggered.connect(self.add_empty)
ma('add-isbn', _('Add from ISBN')).triggered.connect(self.add_from_isbn) ma('add-isbn', _('Add from ISBN')).triggered.connect(self.add_from_isbn)
self.add_menu.addSeparator() self.add_menu.addSeparator()
ma('add-formats', _('Add files to selected book records'), ma('add-formats', _('Add files to selected book records'),
triggered=self.add_formats, shortcut='Shift+A') triggered=self.add_formats, shortcut='Shift+A')
arm = self.add_archive_menu = self.add_menu.addMenu(_('Add an empty file to selected book records'))
for fmt in valid_empty_formats:
self.create_menu_action(arm, 'add-empty-' + fmt,
_('Add empty {}').format(fmt)).triggered.connect(
partial(self.add_empty_format, fmt))
self.add_menu.addSeparator() self.add_menu.addSeparator()
ma('add-config', _('Control the adding of books'), ma('add-config', _('Control the adding of books'),
triggered=self.add_config) triggered=self.add_config)
@ -143,6 +147,52 @@ class AddAction(InterfaceAction):
if current_idx.isValid(): if current_idx.isValid():
view.model().current_changed(current_idx, current_idx) view.model().current_changed(current_idx, current_idx)
def add_empty_format(self, format_):
if self.gui.stack.currentIndex() != 0:
return
view = self.gui.library_view
rows = view.selectionModel().selectedRows()
if not rows:
return error_dialog(self.gui, _('No books selected'),
_('Cannot add files as no books are selected'), show=True)
ids = [view.model().id(r) for r in rows]
if len(ids) > 1 and not question_dialog(
self.gui,
_('Are you sure?'),
_('Are you sure you want to add the same'
' empty file to all %d books? If the format'
' already exists for a book, it will be replaced.')%len(ids)):
return
db = self.gui.library_view.model().db
if len(ids) == 1:
formats = db.formats(ids[0], index_is_id=True)
if formats:
formats = {x.lower() for x in formats.split(',')}
if format_ in formats:
title = db.title(ids[0], index_is_id=True)
msg = _('The {0} format will be replaced in the book {1}. Are you sure?').format(
format_, title)
if not confirm(msg, 'confirm_format_override_on_add', title=_('Are you sure?'),
parent=self.gui):
return
for id_ in ids:
from calibre.ebooks.oeb.polish.create import create_book
pt = PersistentTemporaryFile(suffix='.' + format_)
pt.close()
mi = db.new_api.get_metadata(id_, get_cover=False,
get_user_categories=False, cover_as_data=False)
create_book(mi, pt.name, fmt=format_)
db.add_format_with_hooks(id_, format_, pt.name, index_is_id=True, notify=True)
os.remove(pt.name)
current_idx = self.gui.library_view.currentIndex()
if current_idx.isValid():
view.model().current_changed(current_idx, current_idx)
def add_archive(self, single): def add_archive(self, single):
paths = choose_files( paths = choose_files(
self.gui, 'recursive-archive-add', _('Choose archive file'), self.gui, 'recursive-archive-add', _('Choose archive file'),
@ -209,12 +259,13 @@ class AddAction(InterfaceAction):
mi.series = series mi.series = series
mi.series_index = db.get_next_series_num_for(series) mi.series_index = db.get_next_series_num_for(series)
fmts = [] fmts = []
if gprefs.get('create_empty_epub_file', False): empty_format = gprefs.get('create_empty_format_file', '')
if empty_format:
from calibre.ebooks.oeb.polish.create import create_book from calibre.ebooks.oeb.polish.create import create_book
pt = PersistentTemporaryFile(suffix='.epub') pt = PersistentTemporaryFile(suffix='.' + empty_format)
pt.close() pt.close()
temp_files.append(pt.name) temp_files.append(pt.name)
create_book(mi, pt.name) create_book(mi, pt.name, fmt=empty_format)
fmts = [pt.name] fmts = [pt.name]
ids.append(db.import_book(mi, fmts)) ids.append(db.import_book(mi, fmts))
self.gui.library_view.model().books_added(num) self.gui.library_view.model().books_added(num)

View File

@ -6,12 +6,14 @@ __license__ = 'GPL v3'
from PyQt5.Qt import ( from PyQt5.Qt import (
QDialog, QGridLayout, QLabel, QDialogButtonBox, QApplication, QSpinBox, QDialog, QGridLayout, QLabel, QDialogButtonBox, QApplication, QSpinBox,
QToolButton, QIcon, QCheckBox, QLineEdit) QToolButton, QIcon, QCheckBox, QLineEdit, QComboBox)
from calibre.ebooks.metadata import string_to_authors from calibre.ebooks.metadata import string_to_authors
from calibre.gui2.complete2 import EditWithComplete from calibre.gui2.complete2 import EditWithComplete
from calibre.utils.config import tweaks from calibre.utils.config import tweaks
from calibre.gui2 import gprefs from calibre.gui2 import gprefs
valid_empty_formats = ['epub', 'txt', 'docx', 'azw3']
class AddEmptyBookDialog(QDialog): class AddEmptyBookDialog(QDialog):
def __init__(self, parent, db, author, series=None, title=None): def __init__(self, parent, db, author, series=None, title=None):
@ -76,21 +78,31 @@ class AddEmptyBookDialog(QDialog):
self.tclear_button.clicked.connect(self.title_edit.clear) self.tclear_button.clicked.connect(self.title_edit.clear)
self._layout.addWidget(self.tclear_button, 7, 1, 1, 1) self._layout.addWidget(self.tclear_button, 7, 1, 1, 1)
self.create_epub = c = QCheckBox(_('Create an empty EPUB file as well')) self.format_label = QLabel(_('Create an empty format as well:'))
c.setChecked(gprefs.get('create_empty_epub_file', False)) self._layout.addWidget(self.format_label, 8, 0, 1, 2)
c.setToolTip(_('Also create an empty EPUB file that you can subsequently edit')) c = self.format_value = QComboBox(self)
self._layout.addWidget(c, 8, 0, 1, -1) possible_formats = [''] + valid_empty_formats
c.addItems(possible_formats)
c.setToolTip(_('Also create an empty book format file that you can subsequently edit'))
if gprefs.get('create_empty_epub_file', False):
# Migration of the check box
gprefs.set('create_empty_format_file', 'epub')
gprefs.set('create_empty_epub_file', False)
use_format = gprefs.get('create_empty_format_file', '')
try:
c.setCurrentIndex(possible_formats.index(use_format))
except:
pass
self._layout.addWidget(c, 9, 0, 1, 1)
button_box = self.bb = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel) button_box = self.bb = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel)
button_box.accepted.connect(self.accept) button_box.accepted.connect(self.accept)
button_box.rejected.connect(self.reject) button_box.rejected.connect(self.reject)
self._layout.addWidget(button_box, 9, 0, 1, -1) self._layout.addWidget(button_box, 10, 0, 1, -1)
self.resize(self.sizeHint()) self.resize(self.sizeHint())
def accept(self): def accept(self):
oval = gprefs.get('create_empty_epub_file', False) gprefs['create_empty_format_file'] = self.format_value.currentText()
if self.create_epub.isChecked() != oval:
gprefs['create_empty_epub_file'] = self.create_epub.isChecked()
return QDialog.accept(self) return QDialog.accept(self)
def reset_author(self, *args): def reset_author(self, *args):