如何检查加载到FMX.TBitmap的PNG图像是否有alpha通道?

时间:2011-12-28 08:26:16

标签: delphi png delphi-xe2 firemonkey tbitmap

我在Delphi-XE2 Update3 FireMonkey HD应用程序中将PNG图像加载到FMX.Type.TBitmap。如何检查加载的PNG图像是否具有Alpha通道?

目前,如果我加载带有Alpha通道的图像,则它在Bitmap.Scanline[Y]^[X]中以$ AABBGGRR的形式包含alpha信息。但是,如果我加载没有alpha的PNG图像,则所述记录只有$ 00BBGGRR条目(AA = 0),就像具有清晰alpha的图像一样。因此问题 - 如何确定它是否是具有完全透明的alpha的RGBA图像,或者它是RGB图像(在这种情况下,我将处理它以使alpha完全不透明)。注意:无法检查所有像素。

FMX TBitmap没有PixelFormat属性,也找不到HasAlpha标志。

2 个答案:

答案 0 :(得分:2)

你可能不会喜欢这个。

FMX中的所有位图都是32位,它们是使用OS中的代码加载和保存的,这些代码都是32位。

所以,真正的答案是所有位图都有一个alpha通道。

但是,你真正想知道的是位图是否使用了alpha通道,而告诉它的唯一方法就是迭代每个像素并查看是否有任何alpha通道是<> 255。

我建议如下(未经测试):

function TBitmap.IsAlpha(Bitmap: TBitmap): Boolean;
var
  I, j: Integer;
  Bits: PAlphaColorRecArray;
begin
  Bits := PAlphaColorRecArray(StartLine);
  for j := 0 to Height - 1 do
    for I := 0 to Width - 1 do
    begin
      if Bits[I + (j * Width)].A <> 255 then
      begin
        Result := True;
        EXIT;
      end;
    end;
  Result := False;
end;

答案 1 :(得分:2)

以下功能检查PNG文件是否具有透明通道。这很容易,因为主PNG标头具有固定长度,并且数据信息块IHDR必须是第一个出现的块。

function PngHasAlphaLayer(f: String): Boolean;
var
  fs: TFileStream;
  colorType: Byte;
begin
  fs := TFileStream.Create(f, fmOpenRead);
  fs.Position := 25;
  fs.Read(colorType, 1);
  fs.Free;
  Result := colorType and (1 shl 2) <> 0;
end;

因此它存储在第26个字节(或0x19为十六进制),第3位。

但是,出于简化原因,此函数不检查有效的文件结构。因此,应该在将PNG图像加载到TBitmap之后使用它,然后可以存储其透明度支持的布尔值。 G。在TImage的Tag属性中(或任何您想要的地方)。