-
-
Notifications
You must be signed in to change notification settings - Fork 2.3k
Open
Labels
Description
We need explicit method to automatically convert image to one of the supported modes for saving formats. Affects #2609 and others. Maybe it should be part of ImagePlugins.
This is a good start point:
def fix_mode(image, new_format, fill_color='white'):
old_mode = image.mode
if old_mode in ('RGBA', 'LA') and new_format == 'GIF':
alpha = image.getchannel('A')
# Convert the image into P mode but only use 255 colors
# in the palette out of 256.
image = image.convert(old_mode[:-1]) \
.convert('P', palette=Image.ADAPTIVE, colors=255)
# Set all pixel values below 128 to 255, and the rest to 0.
mask = Image.eval(alpha, lambda px: 255 if px < 128 else 0)
# Paste the color of index 255 and use alpha as a mask.
image.paste(255, mask)
# The transparency index is 255.
image.info['transparency'] = 255
return image
if old_mode == 'CMYK' and new_format in ('PNG', 'WEBP', 'GIF'):
return image.convert('RGB')
if old_mode == 'I' and new_format in ('JPEG', 'GIF', 'WEBP'):
image = image.point([i//256 for i in range(65536)], 'L')
old_mode = image.mode
if old_mode == 'P' and new_format in ('JPEG', 'WEBP'):
# PIL loses palette attribute during crop. So we use low-level api.
alpha = 'A' in image.im.getpalettemode()
image = image.convert('RGBA' if alpha else 'RGB')
old_mode = image.mode
if old_mode in ('RGBA', 'LA') and new_format == 'JPEG':
background = Image.new(old_mode[:-1], image.size, fill_color)
background.paste(image, image.getchannel('A'))
image = background
old_mode = image.mode
# Pillow doesn't support L modes for webp for now.
if old_mode in ('L', 'LA') and new_format == 'WEBP':
image = image.convert('RGB' + old_mode[1:])
old_mode = image.mode
return imagervanlaar, kkopachev, aclark4life, LidiyaNorman and nypavanypavanypava and kra-monypava