Reputation: 883
I am newbie in python world. For a project (using django) I am using PIL library to convert .gif file to .jpg file. But when the save method of the model is run it throws 'IOError at ... cannot write mode P as JPEG'
Here is my Model class. Please suggest me a solution. Thanks in advance.
class ImageArtwork(models.Model):
filepath = 'art_images/'
artwork = models.ForeignKey(Artwork, related_name='images')
artwork_image = models.ImageField(_(u"Dieses Bild hinzufügen: "), upload_to=filepath)
image_medium = models.CharField(max_length=255, blank=True)
image_thumb = models.CharField(max_length=255, blank=True)
uploaded_at = models.DateTimeField(auto_now_add=True)
def get_thumb(self):
return "/media/%s" % self.image_thumb
def get_medium(self):
return "/media/%s" % self.image_medium
def get_original(self):
return "/media/%s" % self.artwork_image
def save(self):
sizes = {'thumbnail': {'height': 50, 'width': 50}, 'medium': {'height': 300, 'width': 300}, }
# Check if the number of images for the artwork has already reached maximum limit
if ImageArtwork.objects.filter(artwork=self.artwork).count() < 6:
super(ImageArtwork, self).save()
photopath = str(self.artwork_image.path) # this returns the full system path to the original file
im = Image.open(photopath) # open the image using PIL
# pull a few variables out of that full path
extension = photopath.rsplit('.', 1)[1] # the file extension
filename = photopath.rsplit('/', 1)[1].rsplit('.', 1)[0] # the file name only (minus path or extension)
fullpath = photopath.rsplit('/', 1)[0] # the path only (minus the filename.extension)
# use the file extension to determine if the image is valid before proceeding
if extension.lower() not in ['jpg', 'jpeg', 'gif', 'png']:
return
im = ImageOps.fit(im, (sizes['medium']['width'], sizes['medium']['height']), Image.ANTIALIAS) # create medium image
medname = filename + "_" + str(sizes['medium']['width']) + "x" + str(sizes['medium']['height']) + ".jpg"
im.save(fullpath + '/' + medname)
self.image_medium = '/media/' + self.filepath + medname
im = ImageOps.fit(im, (sizes['thumbnail']['width'], sizes['thumbnail']['height']), Image.ANTIALIAS) # create thumbnail
thumbname = filename + "_" + str(sizes['thumbnail']['width']) + "x" + str(
sizes['thumbnail']['height']) + ".jpg"
im.save(fullpath + '/' + thumbname)
self.image_thumb = '/media/' + self.filepath + thumbname
super(ImageArtwork, self).save()
else:
pass
Upvotes: 1
Views: 177
Reputation: 15398
cannot write mode P as JPEG
That's not a django problem, it's an imaging library constraint.
P
stands for paletted
. PIL tries to preserve the colour mode from the original image when writing the JPEG. Since JPEG only supports "TrueColor" (i.e. RGB
) images, you get this error when converting a (paletted) GIF file.
Always convert the image to RGB when saving to JPEG:
im.convert('RGB').save(fullpath + '/' + medname)
Upvotes: 4