1 from PIL import Image
2
3 def flat( *nums ):
4 'Build a tuple of ints from float or integer arguments. Useful because PIL crop and resize require integer points.'
5
6 return tuple( int(round(n)) for n in nums )
7
8 class Size(object):
9 def __init__(self, pair):
10 self.width = float(pair[0])
11 self.height = float(pair[1])
12
13 @property
14 def aspect_ratio(self):
15 return self.width / self.height
16
17 @property
18 def size(self):
19 return flat(self.width, self.height)
20
21 def cropped_thumbnail(img, size):
22 '''
23 Builds a thumbnail by cropping out a maximal region from the center of the original with
24 the same aspect ratio as the target size, and then resizing. The result is a thumbnail which is
25 always EXACTLY the requested size and with no aspect ratio distortion (although two edges, either
26 top/bottom or left/right depending whether the image is too tall or too wide, may be trimmed off.)
27 '''
28
29 original = Size(img.size)
30 target = Size(size)
31
32 if target.aspect_ratio > original.aspect_ratio:
33 # image is too tall: take some off the top and bottom
34 scale_factor = target.width / original.width
35 crop_size = Size( (original.width, target.height / scale_factor) )
36 top_cut_line = (original.height - crop_size.height) / 2
37 img = img.crop( flat(0, top_cut_line, crop_size.width, top_cut_line + crop_size.height) )
38 elif target.aspect_ratio < original.aspect_ratio:
39 # image is too wide: take some off the sides
40 scale_factor = target.height / original.height
41 crop_size = Size( (target.width/scale_factor, original.height) )
42 side_cut_line = (original.width - crop_size.width) / 2
43 img = img.crop( flat(side_cut_line, 0, side_cut_line + crop_size.width, crop_size.height) )
44
45 return img.resize(target.size, Image.ANTIALIAS)
1 Picture = Image.open("/path/load/file.jpg")
2 Picture = cropped_thumbnail(Picture, (500, 500))
3 Picture.save("/path/save/file.jpg", "JPEG")

Comments (0)