-
-
Notifications
You must be signed in to change notification settings - Fork 2.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Inconsistent GIF result after resizing #6085
Comments
This is actually unrelated to doing a resize or the save call. Instead, it happens during the loading of the GIF. The lack of crisp-ness, aka, the graininess of each frame is a typical dithering artifact, in this case Floyd–Steinberg dithering. It currently happens under the hood once you seek beyond the first frame of a GIF: Pillow/src/PIL/GifImagePlugin.py Lines 169 to 177 in 4638c4f
I don't think there is much you can do in pillow 9.0.1 considering that the value was hard-coded. It might be possible to expose the dithering method as a kwarg instead of hardcoding it (which could then be set to |
Hi. Unfortunately, I need to disagree with @FirefoxMetzger. Dithering during loading is not causing a problem here. from PIL import Image
image = Image.open("test.gif")
image.save("firstframe.png")
image.seek(1)
image.save("secondframe.png")
It's hard to tell visually on this page, but if I zoom in on macOS Preview, both display similarly. from PIL import Image
image = Image.open("test.gif")
print(image.mode) # P
image.resize((512, 512), resample=Image.BICUBIC).save("firstframe_resized.png")
image.seek(1)
print(image.mode) # RGB
image.resize((512, 512), resample=Image.BICUBIC).save("secondframe_resized.png")
The difference is only apparent once you try and resize the images. This would be because the first frame is P, and the second frame is RGB.
So your request is that all frames be blurred? If so, this can be achieved by just converting the first frame to RGB. from PIL import Image
image = Image.open("test.gif")
frames = []
for i in range(image.n_frames):
image.seek(i)
frame = image
if i == 0:
frame = frame.convert("RGB")
frames.append(frame.resize((512, 512), resample=Image.BICUBIC))
frames[0].save("result.gif", save_all=True, append_images=frames[1:], duration=100, loop=0) |
Okay, I understand that the issue comes from the conversion of the first frame being different. I can modify my program as suggested to fix the issue. But why is it that the first frame is not converted as RGB automatically when the others are ? Is it because of the |
Before Pillow 9, P mode was used for all frames in a non-grayscale GIF. While this worked fine for your image, some images were broken because of this.
Why was the first frame not changed to RGB as well? I presume there is a contingent of Pillow users who just read the first frame of images, and don't bother seeking past that. This change in Pillow 9 (#5857) had no effect on those users, and so did not disrupt their experience at all. I think the first image is a P mode image - it has only up to 256 colors. It is represented by a palette in the original GIF. |
@Kusefiru did that answer your question? Is there anything else we can do for you? |
Yes I think it's fine for me, thanks. |
I am trying to resize a
.gif
file. For that, I open my file with Pillow, then for each frame, resize that frame, and save the resulting frames as a new .gif file.Here is the sample code:
Here is the used
test.gif
file:As the resize is done using the
Image.BICUBIC
resampling method, I expect the resulting file to have a blurred appearance.On Pillow 9.0.1, the first frame appears pixel crisp:
On my previous install, Pillow 8.4.0, all the frames are pixel crisp:
What could explain such behaviour (is there a missing option in my
save
call)?The text was updated successfully, but these errors were encountered: