【问题标题】:PNG image from imagelist来自图像列表的 PNG 图像
【发布时间】:2012-06-13 22:30:36
【问题描述】:

如何从TImageList 拍摄照片并将其放入TImage(或以TGraphic 的形式返回)?

重要的一点是TImageList 可以包含 32-bpp alpha 混合图像。目标是获取这些 alpha 混合图像之一并将其放在TImage 中。这意味着在某些时候我可能需要TGraphic。虽然严格来说,我的问题是关于将 ImageList 中的图像放入 Image。如果可以在没有中间 TGraphic 的情况下完成,那也没关系。

我们想要什么?

我们想要一个函数的胆量:

procedure GetImageListImageIntoImage(SourceImageList: TCustomImageList; 
      ImageIndex: Integer; TargetImage: TImage);
begin
   //TODO: Figure this out.
   //Neither SourceImageList.GetIcon nor SourceImageList.GetBitmap preserve the alpha channel
end;

还有另一个有用的中间辅助函数:

function ImageListGetGraphic(ImageList: TCustomImageList; ImageIndex: Integer): TGraphic;
var
//  ico: TIcon;
    bmp: TBitmap;
begin
    {Doesn't work; loses alpha channel. 
    Windows Icon format can support 32bpp alpha bitmaps. But it just doesn't work here
    ico := TIcon.Create;
    ImageList.GetIcon(ImageIndex, ico, dsTransparent, itImage);
    Result := ico;
    }

    {Doesn't work; loses alpha channel.
    Windows does support 32bpp alpha bitmaps. But it just doesn't work here
    bmp := TBitmap.Create;
    bmp.PixelFormat := pf32bit;
    Imagelist.GetBitmap(ImageIndex, bmp);
    Result := bmp;
    }
end;

让我们把原来的过程转换成:

procedure GetImageListImageIntoImage(SourceImageList: TCustomImageList; ImageIndex: Integer; TargetImage: TImage);
var
   g: TGraphic;
begin
   g := ImageListGetGraphic(SourceImageList, ImageIndex);
   TargetImage.Picture.Graphic := g; //Assignment of TGraphic does a copy
   g.Free;
end;

我也有些乱七八糟的东西:

Image1.Picture := TPicture(ImageList1.Components[0]);

但这不会编译。

附:我有德尔福 2010

【问题讨论】:

  • “我得到一个运行时错误”没有任何意义,除非你告诉我们什么错误,包括确切的错误信息和任何内存地址。
  • @Ken - 我敢打赌这是编译时错误,因为 TImage 没有“图片”属性,即使是“图片”,代码也无法编译(图片 组件)。
  • @Sertac,我同意。但是,如果问题包含信息,这将有所帮助。人们似乎忘记了我们不能从我们坐的地方看到他们的屏幕。 (至少我不能,通灵调试应该是最后的手段。

标签: windows delphi png delphi-2010 delphi-xe6


【解决方案1】:
ImageList1.GetBitmap(0, Image1.Picture.Bitmap);

【讨论】:

  • @Giacomo - 出了什么问题,透明度丢失了?
  • TImageList 仅支持 ICO 和 BMP 格式。将 PNG 放入 TImageList 会将其转换为 BMP。如果要将 PNG 保留为 PNG,则必须使用另一个支持该功能的组件,例如 TPngImageList
  • 将您的 PNG 添加到资源中...然后从资源中加载... stackoverflow.com/questions/1153394/…
  • @GiacomoKingPatermo 对于 32 位 png 图像,可以使用GetIcon 方法提取图像并保留透明度,所以尝试ImageList1.GetIcon(0, Image1.Picture.Icon);
  • @Giacomo - 除非你告诉它,否则没人知道问题所在。 “它不起作用”如何?你有错误吗?
【解决方案2】:

ImageList 中获取透明图形的例程:

function ImageListGetGraphic(ImageList: TCustomImageList; ImageIndex: Integer): TGraphic;
var
    ico: HICON;
//  png: TPngImage;
//  icon: TIcon;
//  bmp: TBitmap;
    wicbmp: IWICBitmap;
    wi: TWicImage;
begin
{   //Works. Uses our own better Wic library.
    ico := ImageList_GetIcon(ImageList.Handle, ImageIndex, ILD_NORMAL);
    Result := TWicGraphic.FromHICON(ico);
    DestroyIcon(ico);}

    //Works, uses the built-in Delphi TWicImage (careful of VCL bugs)
    ico := ImageList_GetIcon(ImageList.Handle, ImageIndex, ILD_NORMAL);
    wi := TWICImage.Create; //Due to a bug in the VCL, you must construct the TWicImage before trying to access the Wic ImagingFactory
    OleCheck(TWicImage.ImagingFactory.CreateBitmapFromHICON(ico, wicbmp));
    wi.Handle := wicbmp;
    Result := wi;

{   //Doesn't work, loses alpha channel
    icon := TIcon.Create;
    ImageList.GetIcon(ImageIndex, icon, dsTransparent, itImage);
    Result := icon;
    }

{   //Doesn't work, loses alpha channel
    bmp := TBitmap.Create;
    bmp.PixelFormat := pf32bit;
    Imagelist.GetBitmap(ImageIndex, bmp);
    Result := bmp;
    }

{   //Fails: cannot assign a TIcon to a TPngImage
    icon := TIcon.Create;
    ImageList.GetIcon(ImageIndex, icon, ImgList.dsNormal, itImage);
    png := TPngImage.Create;
    png.Assign(icon);
    Result := png;
    icon.Free;
    }

{   //Working failure; doesn't support stretched drawing (e.g. TImage.Stretch = true)
    icon := TIcon.Create;
    ImageList.GetIcon(ImageIndex, icon, ImgList.dsNormal, itImage);
    Result := ico;
    }

end;

示例用法:

g: TGraphic;

g := ImageListGetGraphic(ImageList1, 7);
Image1.Picture.Graphic := g;
g.Free;

注意:任何发布到公共领域的代码。无需注明出处。

【讨论】:

    猜你喜欢
    • 2010-10-06
    • 1970-01-01
    • 2010-09-15
    • 1970-01-01
    • 2019-05-03
    • 2019-02-14
    • 1970-01-01
    • 1970-01-01
    • 2023-04-08
    相关资源
    最近更新 更多