From 1bef93de39bc8947b2612d40f0ca0537a429b474 Mon Sep 17 00:00:00 2001 From: Kovid Goyal Date: Sat, 5 Mar 2011 01:04:35 -0700 Subject: [PATCH] When setting covers in calibre, resize to fit within a maximum size of (1200, 1600), to prevent slowdowns due to extra large covers. This size can be controlled via Preferences->Tweaks. Fixes #9277 (Restrict max cover size to 1000x1000) --- resources/default_tweaks.py | 6 ++++++ src/calibre/library/database2.py | 3 ++- src/calibre/utils/magick/draw.py | 34 +++++++++++++++++++++++++++----- 3 files changed, 37 insertions(+), 6 deletions(-) diff --git a/resources/default_tweaks.py b/resources/default_tweaks.py index 2303c6c108..38c1685b7c 100644 --- a/resources/default_tweaks.py +++ b/resources/default_tweaks.py @@ -349,3 +349,9 @@ public_smtp_relay_delay = 301 # after a restart of calibre. draw_hidden_section_indicators = True +#: The maximum width and height for covers saved in the calibre library +# All covers in the calibre library will be resized, preserving aspect ratio, +# to fit within this size. This is to prevent slowdowns caused by extremely +# large covers +maximum_cover_size = (1200, 1600) + diff --git a/src/calibre/library/database2.py b/src/calibre/library/database2.py index 2554df93e6..e7d55da9df 100644 --- a/src/calibre/library/database2.py +++ b/src/calibre/library/database2.py @@ -37,7 +37,7 @@ from calibre.utils.config import prefs, tweaks, from_json, to_json from calibre.utils.icu import sort_key from calibre.utils.search_query_parser import saved_searches, set_saved_searches from calibre.ebooks import BOOK_EXTENSIONS, check_ebook_format -from calibre.utils.magick.draw import save_cover_data_to +from calibre.utils.magick.draw import minify_image, save_cover_data_to from calibre.utils.recycle_bin import delete_file, delete_tree from calibre.utils.formatter_functions import load_user_template_functions @@ -951,6 +951,7 @@ class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns): if callable(getattr(data, 'read', None)): data = data.read() try: + data = minify_image(data, tweaks['maximum_cover_size']) save_cover_data_to(data, path) except (IOError, OSError): time.sleep(0.2) diff --git a/src/calibre/utils/magick/draw.py b/src/calibre/utils/magick/draw.py index 04cce5efe3..615aab9bd0 100644 --- a/src/calibre/utils/magick/draw.py +++ b/src/calibre/utils/magick/draw.py @@ -12,6 +12,34 @@ from calibre.constants import __appname__, __version__ from calibre.utils.config import tweaks from calibre import fit_image +def _data_to_image(data): + if isinstance(data, Image): + img = data + else: + img = Image() + img.load(data) + return img + +def minify_image(data, minify_to=(1200, 1600), preserve_aspect_ratio=True): + ''' + Minify image to specified size if image is bigger than specified + size and return minified image, otherwise, original image is + returned. + + :param data: Image data as bytestring or Image object + :param minify_to: A tuple (width, height) to specify target size + :param preserve_aspect_ratio: whether preserve original aspect ratio + ''' + img = _data_to_image(data) + owidth, oheight = img.size + nwidth, nheight = minify_to + if owidth <= nwidth and oheight <= nheight: + return img + if preserve_aspect_ratio: + scaled, nwidth, nheight = fit_image(owidth, oheight, nwidth, nheight) + img.size = (nwidth, nheight) + return img + def normalize_format_name(fmt): fmt = fmt.lower() if fmt == 'jpeg': @@ -35,11 +63,7 @@ def save_cover_data_to(data, path, bgcolor='#ffffff', resize_to=None, ''' changed = False - if isinstance(data, Image): - img = data - else: - img = Image() - img.load(data) + img = _data_to_image(data) orig_fmt = normalize_format_name(img.format) fmt = os.path.splitext(path)[1] fmt = normalize_format_name(fmt[1:])