ImageMagick-如何获得最大的图层并进行压缩?

时间:2019-04-22 15:13:47

标签: imagemagick

请帮助。是否有一种简单的方法来提取tiff的最大层并用imagemagick或类似的方法再次将其压缩回压缩为单层tiff?

3 个答案:

答案 0 :(得分:3)

只是弗雷德答案的简单一点。您可以在TIF中生成每个图层的区域列表(以像素为单位),然后是图层/场景编号,如下所示:

magick identify -format "%[fx:w*h] %s\n" image.tif

示例输出

240000 0
560000 1
200000 2

因此,如果再次执行此操作,请对其进行数字反转并取第一个结果的第二个字段,我们将获得面积最大的图层编号:

layer=$(magick identify -format "%[fx:w*h] %s\n" image.tif | sort -rn | awk 'NR==1{print $2}')

因此,完整的解决方案如下:

#!/bin/bash

# Get layer number of layer with largest area
layer=$(magick identify -format "%[fx:w*h] %s\n" image.tif | sort -rn | awk 'NR==1{print $2}')

# Extract that layer and recompress as single layer
magick image.tif[$layer] -compress lzw result.tif

如果您使用的是 ImageMagick v6或更低版本:

  • magick identify ...成为identify ...
  • magick image.tif ...成为convert image.tif ...

答案 1 :(得分:3)

从概念上讲,使用ImageMagick可以在单个命令中完成。这是一个例子...

magick input.tif -background none -virtual-pixel none ^
   ( -clone 0--1 +repage -layers merge ) ^
   -distort affine "0,0 0,%[fx:s.w==u[-1].w&&s.h==u[-1].h?0:h]" ^
   -delete -1 -layers merge output.tif

首先读取原始TIF,然后将背景和虚拟像素设置设置为“无”。

然后在括号内克隆TIF的所有层,对其进行重新分页,然后将它们合并为具有最大层尺寸的单个图像。这将成为衡量的标准。

接下来,它使用“扭曲仿射”将每个图像滑出视口,并保持透明。除非图像与该量规的宽度和高度匹配。因此,在扭曲之后,最大的图像将保持不变,所有其他图像将保持透明。

通过删除该量规图像并将其合并来完成。除了最大的一层以外,所有层都是透明的,因此合并它们只会将可见的一层作为单个层。

该命令是使用IM7的Windows语法。如果您使用的是ImageMagick v6,请使用“转换”而不是“ magick”。要使其在* nix中工作,请将连续的行插入符号“ ^”更改为反斜杠“ \”,并使用反斜杠“ \(... \)”对括号进行转义。我可能还忽略了其他问题。

很明显,如果有两层或更多层匹配最大尺寸,则输出结果将只是原始TIF中的第一层。

编辑后添加:仅当最大宽度和最大高度都在同一图像上时,此方法才有效。

答案 2 :(得分:1)

您如何定义最大?宽度,高度,文件大小?如果使用了宽度和高度的最大尺寸,则在Unix中,您可以在3层tif文件中执行以下操作。获取每个图层的最大尺寸。然后找到最大的层。然后在读写文件时仅使用该层。

Arr=(`identify -format "%[fx:max(w,h)]\n" img.tif`)
echo "${Arr[*]}"
500 1024 770

num=${#Arr[*]}
dim=0
for ((i=0; i<num; i++)); do
if [ ${Arr[$i]} > $dim ]; then
dim=${Arr[$i]}
index=$i
fi
done
echo "$index"
2

convert img.tif[$index] -compress zip newimg.tif
identify newimg.tif
newimg.tif[2] TIFF 770x768 770x768+0+0 8-bit sRGB 3662B 0.000u 0:00.000

我想不出任何直接简单的方法来找到最大的图层并将其提取到同一命令行中。