Slow GIF Generation

The MagickWand interface is a new high-level C API interface to ImageMagick core methods. We discourage the use of the core methods and encourage the use of this API instead. Post MagickWand questions, bug reports, and suggestions to this forum.
Post Reply
orthogonal
Posts: 2
Joined: 2016-04-09T08:09:56-07:00
Authentication code: 1151

Slow GIF Generation

Post by orthogonal »

It appears this topic has come up before, so I apologize if I've missed the answer.

I have some code that decodes frames from an ffmpeg steam, loads them into a magickwand via ConstituteImage, calls OptimizeImageLayers, then OptimizeImageTransparency, and finally gets the bytes via GetImagesBlob. Some pseudocode:

Code: Select all

mw = NewMagickWand()
for(i=0;i < frameCount;i++) {
    MagickConstituteImage(mw, cols, rows, cspmap, stype, ptr)
    MagickSetImageFuzz(mw, fuzz)
    MagickSetImageDelay(mw, delay)
}
mw = MagickOptimizeImageLayers(mw)
MagickOptimizeImageTransparency(mw)
MagickSetImageFormat(mw, "gif")
data = MagickGetImagesBlob(mw, &clen)
Obviously most of the variable declarations are removed there, but the gist is hopefully clear. In the preceding case adding 100 frames takes about 400ms (this includes some decode time and memory copying so I'm not worried about that), optimizing layers ~250ms, optimizing transparency ~350ms, and getting the bytes via MagickGetImagesBlob ~2s. These numbers can vary quite a bit depending on what 100 frames are provided. I've seen the final step take > 3s.

Is there any way to speed this up without compromising quality (or at least not compromising it significantly)? I believe much of the time is spent quantizing the images, but it's unclear to me if there's a better way to do this.

As an aside, does anyone know if this code generates a global color palette or one per frame?

Thanks!

Edit: I forgot to mention I'm using the latest imagemagick compiled from source (6.9.3-7) Q16 no HDRI with OpenMP enabled. The numbers are from a 10 core Xeon server I'm using for testing.
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Slow GIF Generation

Post by fmw42 »

I believe that each frame gets its own color table. To have a common colortable, you would have to process each frame with a common color table image using -remap.

Quantization in the conversion to gif can be slow. I am told that using -treedepth may help speed that up.

See
http://www.imagemagick.org/script/comma ... #treedepth
http://www.imagemagick.org/script/quantize.php
http://www.imagemagick.org/Usage/quantize/#remap
http://www.imagemagick.org/Usage/anim_opt/#colortables
orthogonal
Posts: 2
Joined: 2016-04-09T08:09:56-07:00
Authentication code: 1151

Re: Slow GIF Generation

Post by orthogonal »

Thanks for the quick response. Two questions:

* Is there any reasonable way to generate a shared colortable from a wand full of images? It looks like I can use MagickRemapImage on each image as I add them to the wand, but it doesn't look like there's any way to generate the color table?
* MagickQuantizeImages has a treedepth argument but calling that doesn't affect the speed of MagickGetImagesBlob. Is it re-quantizing and ignoring what MagickQuantizeImages does?
User avatar
fmw42
Posts: 25562
Joined: 2007-07-02T17:14:51-07:00
Authentication code: 1152
Location: Sunnyvale, California, USA

Re: Slow GIF Generation

Post by fmw42 »

I do not know the workings of Imagemagick quantization code.

You can generate the color table image by selecting the colors your want and making one pixel images of each color, then append them.

Code: Select all

convert -size 1x1 xc:"color1" xc:"color2" .... xc:"color256" +append colortable.gif
Or you can just use one gif image (256 colors or less), export the -unique-colors to a new image.\

Code: Select all

convert frame1.gif -unique-colors colortable.gif
See http://www.imagemagick.org/Usage/quantize/#extract
Post Reply