【问题标题】:ImageMagick: how to minimally crop an image to a certain aspect ratio?ImageMagick:如何将图像最小程度地裁剪为特定的纵横比?
【发布时间】:2014-02-11 07:16:24
【问题描述】:

使用 imagemagick,我想以最小的方式裁剪图像,使其适合给定的纵横比。

示例:给定一张 3038 x 2014 像素的图像,我想将其裁剪为 3:2 的纵横比。生成的图像将是 3021 x 2014 像素,从原始图像的中心裁剪。

所以寻找一个类似于convert in.jpg -gravity center -crop_to_aspect_ratio 3:2 out.jpg 的命令。

【问题讨论】:

  • Fred's ImageMagick Scripts 有一个脚本。他对他如何实现效果进行了大量解释。如果您使用另一种脚本语言来驱动 IM,那么在其中进行数学计算可能会更容易。
  • 太棒了!顺便说一句,那里有很多有用的东西:)

标签: imagemagick crop aspect-ratio


【解决方案1】:

Imagemagick 7.0.7.22 及以上版本

-crop 3:2January 6th, 2018 开始工作。

JPG

magick convert in.jpg -gravity center -crop 3:2 out.jpg

警告/提醒:如果你不使用-gravity center,你会得到两个输出文件:

PNG

正如 fmw42 指出的那样,PNG 文件存储虚拟画布大小。推荐+repage

magick convert in.png -gravity center -crop 3:2 +repage out+repage.png

GIMP、IrfanView、Chrome 和 Windows Explorer 没有任何区别,但 Imagemagick 知道:

magick identify out*png
out_stndrd.png PNG 252x168 314x168+31+0 8-bit sRGB 78557B 0.000u 0:00.000
out+repage.png PNG 252x168 252x168+0+0 8-bit sRGB 78529B 0.000u 0:00.000

Imagemagick 6.9.9-34 及以上

JPG

convert in.jpg -gravity center -crop 3:2 out.jpg

PNG

convert in. -gravity center -crop 3:2 +repage out.png

Imagemagick 6.9.9-33 / 7.0.7.21 及以下

注意:对于 v7,您需要在任何 convert 之前添加 magick

1。具体目标分辨率

如果您最终的目标是获得一定的分辨率(例如 1920x1080),那么使用 -geometry、抑扬符/帽子/屋顶/房屋符号 (^) 和 -crop 很容易:

convert in.jpg -geometry 1920x1080^ -gravity center -crop 1920x1080+0+0 out.jpg

循环多个 jpg 文件:

for i in *jpg
  do convert "$i" -geometry 1920x1080^ -gravity center -crop 1920x1080+0+0 out-"$i"
done

2。仅宽高比裁剪

如果要避免缩放,则必须在 Imagemagick 之外计算裁剪边的新长度。这涉及更多:

aw=16 #desired aspect ratio width...
ah=9 #and height
in="in.jpg"
out="out.jpg"

wid=`convert "$in" -format "%[w]" info:`
hei=`convert "$in" -format "%[h]" info:`

tarar=`echo $aw/$ah | bc -l`
imgar=`convert "$in" -format "%[fx:w/h]" info:`

if (( $(bc <<< "$tarar > $imgar") ))
then
  nhei=`echo $wid/$tarar | bc`
  convert "$in" -gravity center -crop ${wid}x${nhei}+0+0 "$out"
elif (( $(bc <<< "$tarar < $imgar") ))
then
  nwid=`echo $hei*$tarar | bc`
  convert "$in" -gravity center -crop ${nwid}x${hei}+0+0 "$out"
else
  cp "$in" "$out"
fi

我在示例中使用 16:9,希望它对大多数读者来说比 3:2 更有用。更改解决方案 1 中出现的 1920x1080 或解决方案 2 中的 aw/ah 变量以获得所需的纵横比。

图片来源:Anders Krusberg / Peabody Awards

【讨论】:

    【解决方案2】:

    Imagemagick 的最新版本(自 6.9.9-34 起)具有纵横比裁剪。所以你可以这样做:

    输入:

    convert barn.jpg -gravity center -crop 3:2 +repage barn_crop_3to2.png
    

    输出为 400x267+0+0。但是注意需要+repage 去掉400x299+0+16的虚拟画布,因为PNG输出支持虚拟画布。 JPG 输出不需要 +repage,因为它不支持虚拟画布。

    【讨论】:

    • 根据change log好像是在7.0.7-22(2018-01-06)添加的?
    • 是的,在 IM 7 的那个版本中它也是新的。如果使用 IM 7,则使用 magick 而不是 convert。
    【解决方案3】:

    我需要使用 A4 (1x1.414) 纸张纵横比垂直分割很长的图像。所以我想出了以下解决方案。假设图像文件名为 ch1.jpg:

    convert -crop $(identify -format "%w" ch1.jpg)x$(printf "%.0f" $(echo $(identify -format "%w" ch1.jpg) \* 1.414|bc)) +repage ch1.jpg ch1.jpg
    

    【讨论】:

      【解决方案4】:

      随着 ImageMagick 7 的出现,您可以使用 FX 表达式在单个命令中完成给定宽高比的最大图像尺寸裁剪。

      唯一的窍门是你需要在同一个命令的四个不同位置输入所需的方面,所以我发现为那个位创建一个变量是最容易的。 aspect 可以是十进制数,也可以是 fx 表达式可以解析的字符串形式的分数。

      aspect="16/9"
      
      magick input.png -gravity center \
          -extent  "%[fx:w/h>=$aspect?h*$aspect:w]x" \
          -extent "x%[fx:w/h<=$aspect?w/$aspect:h]" \
          output.png
      

      一旦方面正确,您可以使用-resize 跟进两个-extent 操作,以使完成的图像达到您的输出大小。上面的示例使其尽可能大,因为它可以给定输入图像。

      【讨论】:

        【解决方案5】:

        您需要计算出所需的尺寸,然后进行裁剪。这是一个函数,给定图像的widthheight 加上所需的纵横比aspect_xaspect_y,将输出可用于Imagemagick 的裁剪字符串。

        def aspect(width, height, aspect_x, aspect_y)
        
          old_ratio = width.to_f / height
          new_ratio = aspect_x.to_f / aspect_y
        
          return if old_ratio == new_ratio
        
          if new_ratio > old_ratio
            height = (width / new_ratio).to_i # same width, shorter height
          else
            width = (height * new_ratio).to_i # shorter width, same height
          end
        
          "#{width}x#{height}#" # the hash mark gives centre-gravity
        
        end
        

        我在使用 Dragonfly Gem 的应用程序中使用了类似的东西。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2015-07-28
          • 2013-08-31
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多