【问题标题】:How to trim animated gif (using imagemagick)?如何修剪动画 gif(使用 imagemagick)?
【发布时间】:2017-11-17 06:08:52
【问题描述】:

给定一个纯色背景上的动画 gif

我想修剪 内边距。具体来说,我想在所有帧上将图像裁剪到前景对象的最大范围:

我似乎无法找到 -alpha-background 的正确组合来使用单个 convert 命令实现此目的。例如,如果我发出

convert -dispose 2 input.gif -trim -layers TrimBounds fail.gif

对于其单个修剪范围小于所有帧的最大范围的帧,我得到随机的“背景”颜色:

我可以用一长串命令实现正确的输出:

convert input.gif -trim -layers TrimBounds out-%03d.miff
mogrify -background "rgb(20%,30%,80%)" -layers flatten out-*.miff
convert out-*.miff output.gif
rm out-*.miff

这很慢,会写入一堆临时文件,并且需要我明确知道背景颜色 ("rgb(20%,30%,80%)")。

有没有更简单的方法来修剪动画 gif?

related question 考虑的是显式裁剪而不是自动修剪。

【问题讨论】:

    标签: image-processing imagemagick crop animated-gif imagemagick-convert


    【解决方案1】:

    您可以使用 IM 的“-distort”和定义的视口来完成这种修剪。

    convert oHBWq.gif -coalesce +repage -background none \
       \( -clone 0--1 -trim -flatten -trim \) \
       -set option:distort:viewport %[fx:u[-1].w]x%[fx:u[-1].h]+%[fx:u[-1].page.x]+%[fx:u[-1].page.y] \
       -delete -1 -distort SRT 0 +repage output.gif
    

    这会克隆输入帧,单独修剪它们,然后将它们展平以保持其原始对齐方式。然后它再次修剪扁平的一个以去除多余的透明背景。结果将是正确的尺寸,并且具有正确的页面偏移量用于完成的图像。您不必知道背景颜色。

    现在您可以轻松地将这些尺寸和偏移量添加到扭曲视口设置中并进行无操作扭曲。删除用于获取测量值的克隆展平,“+repage”其余部分,然后使用您需要的任何其他 GIF 设置完成。

    【讨论】:

      【解决方案2】:

      这是一个有趣的问题。目前,我不知道如何改进它,以便不需要额外的文件。但我会进一步考虑。但我可以稍微清理一下您的代码,让您更轻松,并使 output.gif 看起来正确。

      bgcolor=`convert oHBWq.gif[0] -format "%[pixel:u.p{0,0}]" info:`
      convert oHBWq.gif -trim -layers TrimBounds out-%03d.miff
      mogrify -background "$bgcolor" -layers flatten out-*.miff
      convert -dispose previous -delay 10 out-*.miff -loop 0 output.gif
      rm out-*.miff
      

      这与上面的操作相同,但只需要保存 1 个多帧 miff 文件。 subshel​​l 循环处理与您的 mogrify 类似。

      bgcolor=`convert oHBWq.gif[0] -format "%[pixel:u.p{0,0}]" info:`
      num=`convert oHBWq.gif -format "%n\n" info: | head -n 1`
      convert oHBWq.gif -trim -layers TrimBounds tmp.miff
      (for ((i=0; i<num; i++)); do
      convert tmp.miff[$i] -background "$bgcolor" -layers flatten miff:-
      done ) |\
      convert -dispose previous -delay 10 - -loop 0 output2.gif
      rm tmp.miff
      

      这也可以在不必保存任何临时文件的情况下工作,但必须为每次循环迭代重复 -trim -layers 修剪边界。

      bgcolor=`convert oHBWq.gif[0] -format "%[pixel:u.p{0,0}]" info:`
      num=`convert oHBWq.gif -format "%n\n" info: | head -n 1`
      echo "num=$num"
      (for ((i=0; i<num; i++)); do
      convert oHBWq.gif -trim -layers TrimBounds miff:- |\
      convert -[$i] -background "$bgcolor" -layers flatten miff:-
      done ) |\
      convert -dispose previous -delay 10 - -loop 0 output3.gif
      

      这很接近,但只有一帧:

      bgcolor=`convert oHBWq.gif[0] -format "%[pixel:u.p{0,0}]" info:`
      convert -dispose previous -delay 10 oHBWq.gif -trim -layers TrimBounds -background "$bgcolor" -layers optimize -loop 0 output5.gif
      

      【讨论】:

      • 这些肯定是朝着正确的方向发展的。使用 convert 很难做到这一点,对吧?
      • 看起来是这样。但我会继续调查。
      【解决方案3】:

      最后,这似乎可以在 ImageMagick 中使用一行来获取背景颜色和一行处理。不需要临时文件。

      bgcolor=`convert input.gif[0] -format "%[pixel:u.p{0,0}]" info:`
      convert -dispose previous -delay 10 -background "$bgcolor" input.gif -trim -layers TrimBounds -coalesce -layers optimize -loop 0 output.gif
      

      【讨论】:

        猜你喜欢
        • 2012-12-11
        • 2017-12-03
        • 1970-01-01
        • 2013-01-25
        • 1970-01-01
        • 1970-01-01
        • 2017-11-22
        • 1970-01-01
        • 2015-03-20
        相关资源
        最近更新 更多