175
177
self.assertEqual(output['b'], u'c')
178
def test_makeThumbnail(self):
180
def _makeThumbnailPairs(self, inputSizes, outputSize):
180
Verify that L{makeThumbnail} makes a correctly scaled thumbnail image.
182
Generate a collection of L{makeThumbnail} input/output image pairs in
183
various formats, for the given input sizes.
183
186
from PIL import Image
184
187
except ImportError:
185
188
raise unittest.SkipTest('PIL is not available')
187
# make an image to thumbnail
188
fullSizePath = self.mktemp()
189
fullSizeFormat = 'JPEG'
192
Image.new('RGB', (fullWidth, fullHeight)).save(
193
file(fullSizePath, 'w'), fullSizeFormat)
195
thumbnailPath = self.mktemp()
197
thumbnailFormat = 'TIFF'
199
fullSizePath, thumbnailPath, thumbnailSize, thumbnailFormat)
200
# open the thumbnail, make sure it's the right size and format
201
thumbnailImage = Image.open(file(thumbnailPath))
202
scaleFactor = float(thumbnailSize) / fullWidth
203
expectedHeight = int(fullHeight * scaleFactor)
205
thumbnailImage.size, (thumbnailSize, expectedHeight))
206
self.assertEqual(thumbnailImage.format, thumbnailFormat)
207
# make sure the original image is untouched
208
originalImage = Image.open(file(fullSizePath))
209
self.assertEqual(originalImage.format, fullSizeFormat)
210
self.assertEqual(originalImage.size, (fullWidth, fullHeight))
190
'JPEG': ['L', 'RGB'],
191
'PNG': ['1', 'L', 'P', 'RGB', 'RGBA'],
197
'RGB': (0xFF, 0xFF, 0xFF),
198
'RGBA': (0xFF, 0xFF, 0xFF, 0xFF),
200
for format in formatsToModes:
201
for mode in formatsToModes[format]:
202
for inputSize in inputSizes:
203
cause = ('Image.new(%r, %r) via %s'
204
% (mode, inputSize, format))
205
(inFile, outFile) = (self.mktemp(), self.mktemp())
207
image = Image.new(mode, inputSize)
208
# Plot pixels along the diagonal to provoke aliasing.
209
for i in xrange(min(inputSize)):
210
image.putpixel((i, i), modesToWhite[mode])
211
image.save(file(inFile, 'w'), format)
212
self.assertEqual(Image.open(inFile).mode, mode, cause)
213
untouchedInput = file(inFile).read()
215
makeThumbnail(file(inFile), file(outFile, 'w'),
217
self.assertEqual(file(inFile).read(), untouchedInput, cause)
218
yield (Image.open(inFile), Image.open(outFile), cause)
221
def test_makeThumbnail(self):
223
L{makeThumbnail} should scale images, preserving their aspect ratio, and
224
expanding their color space if necessary.
226
sizes = [(x, y) for x in [30, 60, 120]
227
for y in [30, 60, 120]
229
for (input, output, cause) in self._makeThumbnailPairs(sizes, 60):
230
(x1, y1) = input.size
231
(x2, y2) = output.size
232
self.assertEquals(max(x2, y2), 60, cause)
233
self.assertEquals(x2/y2, x1/y1, cause)
234
expectedMode = {'1': 'L', 'P': 'RGB'}.get(input.mode, input.mode)
235
self.assertEquals(output.mode, expectedMode, cause)
236
self.assertEquals(output.format, input.format, cause)
237
# Compare the output color distribution to Image.ANTIALIAS sampling.
238
# (Skip JPEG due to interfering noise.)
239
if output.format != 'JPEG':
240
expectedColors = (9, 13)[input.size != (120, 120)]
241
self.assertEqual(len(output.getcolors()), expectedColors, cause)
242
if 1 < len(output.getbands()): # Ugh.
243
for extrema in output.getextrema():
244
self.assertEqual(extrema, (0, 119), cause)
246
self.assertEqual(output.getextrema(), (0, 119), cause)
249
def test_makeThumbnailNoResize(self):
251
L{makeThumbnail} should leave images under thumbnail size unchanged.
253
sizes = [(x, y) for x in [30, 60]
255
for (input, output, cause) in self._makeThumbnailPairs(sizes, 60):
256
self.assertEquals(output.size, input.size, cause)
257
self.assertEquals(output.mode, input.mode, cause)
258
self.assertEquals(output.format, input.format, cause)
213
261
def test_descriptiveIdentifier(self):