简体   繁体   English

如何确定图像是否具有透明像素

[英]How to determine if an image has a transparent pixel

I just found a piece of code that was used to determine if an image has transparent pixels: 我刚刚找到了一段代码,用于确定图像是否具有透明像素:

my $alpha  = $gd->transparent;
if ($alpha < 0) {
    die("The image you uploaded has no transparent pixels. (alpha = $alpha)");
}

Obviously, this does not work. 显然,这是行不通的。 I tried it with the image user-desktop.png of the open icon library which has transparent pixels. 我使用具有透明像素的打开图标库的图像user-desktop.png进行了尝试。 The check returned -1. 支票返回-1。

I can only guess why this command was used. 我只能猜测为什么使用此命令。 GD's manpage says: GD的手册说:

If you call this method [transparent] without any parameters, it will return the current index of the transparent color, or -1 if none. 如果不带任何参数调用此方法[transparent],它将返回透明颜色的当前索引;如果没有,则返回-1。

So, as a side question: the transparent pixels can have no color index at all - right? 因此,作为一个附带问题:透明像素完全不能具有颜色索引-对吗?

Then I found the thread Perl GD check if pixel is transparent . 然后我发现线程Perl GD检查像素是否透明 But for this solution, I have to iterate over all pixels of an image (at least in the wort case, when the only transparent pixel would be the last one). 但是对于这种解决方案,我必须遍历图像的所有像素(至少在麦汁中,当唯一的透明像素是最后一个像素时)。

Isn't there an easy way of checking for this information? 是否有一种简便的方法来检查此信息? Maybe a method like $image_object->has_transparent_pixels ? 也许像$ image_object-> has_transparent_pixels这样的方法?

NB: I'm not bound to GD, so other Image modules might work as well (however, I'm on Windows - it should work there). 注意:我不限于GD,因此其他Image模块也可以正常工作(但是,我在Windows上-应该在那里工作)。

Updated Answer 更新的答案

As pointed out by @ikegami (thank you), GIFs have a designated transparent "colour" pixel in their palette rather than a alpha/transparency layer in which each pixel has its own transparency value, normally between 0-255. 正如@ikegami(谢谢您)所指出的那样,GIF在其调色板中具有指定的透明“彩色”像素,而不是alpha /透明层,其中每个像素都有其自己的透明度值,通常在0-255之间。

I have generated a 2x2 pixel GIF with one transparent pixel, one red, one green and one blue - then ran ImageMagick's identify command against it and got the following. 我生成了一个2x2像素的GIF,其中包含一个透明像素,一个红色,一个绿色和一个蓝色-然后对它运行ImageMagick的identify命令,并得到了以下内容。 I have marked the transparent pixel parts with an arrow. 我已经用箭头标记了透明像素部分。

Image: a.gif
  Format: GIF (CompuServe graphics interchange format)
  Mime type: image/gif
  Class: PseudoClass
  Geometry: 4x4+0+0
  Units: Undefined
  Type: PaletteAlpha
  Endianess: Undefined
  Colorspace: sRGB
  Depth: 8/1-bit
  Channel depth:
    red: 1-bit
    green: 1-bit
    blue: 1-bit
    alpha: 1-bit
  Channel statistics:
    Pixels: 16
    Red:
      min: 0 (0)
      max: 255 (1)
      mean: 127.5 (0.5)
      standard deviation: 127.5 (0.5)
      kurtosis: -2
      skewness: 0
    Green:
      min: 0 (0)
      max: 255 (1)
      mean: 127.5 (0.5)
      standard deviation: 127.5 (0.5)
      kurtosis: -2
      skewness: 0
    Blue:
      min: 0 (0)
      max: 255 (1)
      mean: 127.5 (0.5)
      standard deviation: 127.5 (0.5)
      kurtosis: -2
      skewness: 0
    Alpha:
      min: 0 (0)
      max: 255 (1)
      mean: 191.25 (0.75)
      standard deviation: 110.418 (0.433013)
      kurtosis: -0.666667
      skewness: 1.1547
  Image statistics:
    Overall:
      min: 0 (0)
      max: 255 (1)
      mean: 111.562 (0.4375)
      standard deviation: 123.451 (0.484123)
      kurtosis: -1.8275
      skewness: 0.271109
  Alpha: srgba(255,255,255,0)   #FFFFFF00
  Colors: 4
  Histogram:
         4: (  0,  0,255,255) #0000FF blue
         4: (  0,255,  0,255) #00FF00 lime
         4: (255,  0,  0,255) #FF0000 red
         4: (255,255,255,  0) #FFFFFF00 srgba(255,255,255,0)
  Colormap entries: 4
  Colormap:
         0: (255,  0,  0,255) #FF0000 red
         1: (  0,255,  0,255) #00FF00 lime
         2: (  0,  0,255,255) #0000FF blue
         3: (255,255,255,  0) #FFFFFF00 srgba(255,255,255,0)      <---------
  Rendering intent: Perceptual
  Gamma: 0.454545
  Chromaticity:
    red primary: (0.64,0.33)
    green primary: (0.3,0.6)
    blue primary: (0.15,0.06)
    white point: (0.3127,0.329)
  Background color: srgba(255,255,255,0)
  Border color: srgba(223,223,223,1)
  Matte color: grey74
  Transparent color: srgba(255,255,255,0)    <---------------
  Interlace: None
  Intensity: Undefined
  Compose: Over
  Page geometry: 4x4+0+0
  Dispose: Undefined
  Compression: LZW
  Orientation: Undefined
  Properties:
    date:create: 2014-10-11T10:40:09+01:00
    date:modify: 2014-10-11T10:40:08+01:00
    signature: 1c82b4c2e772fb075994516cc5661e9dec35b8142f89c651253d07fc3c4642bb
  Profiles:
    Profile-gif:xmp dataxmp: 1031 bytes
  Artifacts:
    filename: a.gif
    verbose: true
  Tainted: False
  Filesize: 1.11KB
  Number pixels: 16
  Pixels per second: 16PB
  User time: 0.000u
  Elapsed time: 0:01.000
  Version: ImageMagick 6.8.9-7 Q16 x86_64 2014-09-10 http://www.imagemagick.org

So, IM does know about the GIF transparent pixel - I will dig some more and see if it can be found sensibly in Perl - for now though, you could just run the following in Perl's backticks. 因此,IM确实了解GIF透明像素-我将进一步挖掘它,看看它是否可以在Perl中找到。-现在,您可以在Perl的反引号中运行以下内容。

my $output = `identify -verbose a.gif | grep -i transparent`;   # or maybe with FINDSTR on Windows

As an alternatvie, and less problematic across platforms, the %A escape tells you if an image has transparency enabled: 作为一种替代方法,并且在各个平台之间的问题较少, %A转义可告诉您图像是否启用了透明性:

convert a.gif -print "%A" null:
True

convert a.jpg -print "%A" null:
False

Or, in a more Perl-y way: 或者,以更Perl-y的方式:

#!/usr/bin/perl
use warnings;
use strict;
use Image::Magick;
my $image = Image::Magick->new();
$image->Read($ARGV[0]);
my $a = $image->Get('%A');
print $a;

perl ./script.pl a.gif
True

perl ./script.pl a.jpg
False

Original Answer 原始答案

I think you may be a little confused about transparency. 我认为您可能对透明度有些困惑。 Images either have transparency, which is an entire layer, or they do not. 图像要么具有透明性(即整个图层),要么没有透明性。 In general, it is not a question of a single pixel being transparent or not. 通常,这不是单个像素是否透明的问题。 From the outset, JPEG s do not support transparency, GIF and PNG can support transparency but they are not necessarily always transparent. 从一开始, JPEG不支持透明, GIFPNG 可以支持透明,但不一定总是透明的。

So, assuming you have a PNG or a GIF , it could have a transparency layer. 因此,假设您具有PNGGIF ,则可能具有透明层。 If it has, each pixel could either be totally transparent, totally opaque or somewhere in between. 如果有的话,每个像素可能完全透明,完全不透明或介于两者之间。 If you use ImageMagick, it is available at the command line or with PHP, Perl and other bindings. 如果使用ImageMagick,则可以在命令行上使用它,也可以在PHP,Perl和其他绑定中使用它。

From the command line, you can tell if an image has a transparency layer using this command: 从命令行,您可以使用以下命令判断图像是否具有透明层:

convert InputImage.png -format "%[opaque]" info:

and it will either return true or false . 它将返回truefalse

In Perl you can do this: 在Perl中,您可以执行以下操作:

#!/usr/bin/perl
use warnings;
use strict;
use Image::Magick;
my $image = Image::Magick->new();
$image->Read($ARGV[0]);
my $a = $image->Get('%[opaque]');
print $a;

then run as: 然后运行为:

perl ./script.pl ImageName.png

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM