A more sensible API to set PNG compression levels

This commit is contained in:
Kovid Goyal 2016-05-06 21:16:20 +05:30
parent 54ac2d394a
commit 56f7d7cad4

View File

@ -7,7 +7,7 @@ from __future__ import (unicode_literals, division, absolute_import,
import os, subprocess, errno, shutil, tempfile import os, subprocess, errno, shutil, tempfile
from threading import Thread from threading import Thread
from PyQt5.Qt import QImage, QByteArray, QBuffer, Qt, QImageReader, QColor from PyQt5.Qt import QImage, QByteArray, QBuffer, Qt, QImageReader, QColor, QImageWriter
from calibre import fit_image, force_unicode from calibre import fit_image, force_unicode
from calibre.constants import iswindows, plugins from calibre.constants import iswindows, plugins
@ -84,15 +84,24 @@ def blend_image(img, bgcolor='#ffffff'):
overlay(img, nimg) overlay(img, nimg)
return nimg return nimg
def image_to_data(img, compression_quality=95, fmt='JPEG'): def image_to_data(img, compression_quality=95, fmt='JPEG', png_compression_level=9):
''' Serialize image to bytestring in the specified format.
compression_quality is for JPEG and goes from 0 to 100.
png_compression_level is for PNG and goes from 0-9 '''
ba = QByteArray() ba = QByteArray()
buf = QBuffer(ba) buf = QBuffer(ba)
buf.open(QBuffer.WriteOnly) buf.open(QBuffer.WriteOnly)
fmt = fmt.upper() fmt = fmt.upper()
w = QImageWriter(buf, fmt.encode('ascii'))
if img.hasAlphaChannel() and fmt in 'JPEG JPG'.split(): if img.hasAlphaChannel() and fmt in 'JPEG JPG'.split():
img = blend_image(img) img = blend_image(img)
if not img.save(buf, fmt, quality=compression_quality): if fmt == 'PNG':
raise ValueError('Failed to export image as ' + fmt) cl = min(9, max(0, png_compression_level))
w.setQuality(10 * (9-cl))
else:
w.setQuality(compression_quality)
if not w.write(img):
raise ValueError('Failed to export image as ' + fmt + ' with error: ' + w.errorString())
return ba.data() return ba.data()
def resize_image(img, width, height): def resize_image(img, width, height):