I need to extract the middle frame of a gif animation.
Imagemagick:
convert C:\\temp\\orig.gif -coalesce C:\\temp\\frame.jpg
generates
Ok, this script will find and save the middle frame of an animated GIF using Pillow.
It will also display the duration of the GIF by counting the milliseconds of each frame.
from PIL import Image
def iter_frames(im):
try:
i = 0
while 1:
im.seek(i)
frame = im.copy()
if i == 0:
# Save pallete of the first frame
palette = frame.getpalette()
else:
# Copy the pallete to the subsequent frames
frame.putpalette(palette)
yield frame
i += 1
except EOFError: # End of gif
pass
im = Image.open('animated.gif')
middle_frame_pos = int(im.n_frames / 2)
durations = []
for i, frame in enumerate(iter_frames(im)):
if i == middle_frame_pos:
middle_frame = frame.copy()
try:
durations.append(frame.info['duration'])
except KeyError:
pass
middle_frame.save('middle_frame.png', **frame.info)
duration = float("{:.2f}".format(sum(durations)))
print('Total duration: %d ms' % (duration))
Helpful code:
You can do it like this:
convert pour.gif -coalesce -delete 0-3,5-8 frame4.png
Basically, it generates in full, all the frames and then deletes all frames other than from 4.
You are attempting to coalesce a single input image into single output image. What you got is what you asked for.
Instead you should "flatten" frames 0-4 into a single output image:
convert C:\temp\orig.gif[0-4] -flatten C:\temp\frame.jpg
If you use "-coalesce" you'll get 5 frames of output in frame-0.jpg through frame-4.jpg, the last of them being the image you wanted.