【问题标题】:How do I use IImgCtx to get load an image with an alpha channel?如何使用 IImgCtx 加载带有 alpha 通道的图像?
【发布时间】:2010-04-16 04:55:42
【问题描述】:

我有一些使用 IImgCtx 加载图像的工作代码,但我不知道如何进入 alpha 通道。对于 .gif 和 .png 之类的图像,有透明像素,但使用 24 位位图以外的任何东西作为绘图表面都行不通。

界面参考: http://www.codeproject.com/KB/graphics/JianImgCtxDecoder.aspx

我的代码如下所示:

IImgCtx *Ctx = 0;
HRESULT hr = CoCreateInstance(CLSID_IImgCtx, NULL, CLSCTX_INPROC_SERVER, IID_IImgCtx, (LPVOID*)&Ctx);
if (SUCCEEDED(hr))
{
    GVariant Fn = Name;
    hr = Ctx->Load(Fn.WStr(), 0);
    if (SUCCEEDED(hr))
    {
        SIZE  Size = { -1, -1 };
        ULONG State = 0;

        while (true)
        {
            hr = Ctx->GetStateInfo(&State, &Size, false);
            if (SUCCEEDED(hr))
            {
                if ((State & IMGLOAD_COMPLETE) || (State & IMGLOAD_STOPPED) || (State & IMGLOAD_ERROR))
                {
                    break;
                }
                else
                {
                    Sleep(1);
                }
            }
            else break;
        }

        if (Size.cx > 0 &&
            Size.cy > 0 &&
            pDC.Reset(new GMemDC))
        {
            if (pDC->Create(Size.cx, Size.cy, 32))
            {
                HDC hDC = pDC->StartDC();
                if (hDC)
                {
                    RECT rc = { 0, 0, pDC->X(), pDC->Y() };
                    Ctx->Draw(hDC, &rc);
                    pDC->EndDC();
                }
            }
            else pDC.Reset();
        }
    }

    Ctx->Release();

“StartDC”基本上包装了 CreateCompatibleDC(NULL),“EndDC”包装了 DeleteDC,并为 HBITMAPS 等提供了适当的 SelectObjects。pDC->Create(x, y, bit_depth) 调用 CreateDIBSection(...DIB_RGB_COLORS... )。因此,如果我创建一个 24 位/像素位图但没有 alpha 可言,并且如果我传递一个 32 位/像素位图,它会填充 RGB 颜色通道并保留 alpha 通道 0x00。如果我用 0xff 或 alpha 通道将图像设置为完全不透明,那么它看起来与 24 bpp 选项相同。现在这个界面显然是被 Internet Explorer 用来加载图像的,而且显然它支持透明度,所以我相信有可能从界面中获得某种程度的 alpha。问题是如何?

(我还有调用 libpng/libjpeg/my .gif 加载器等的后备代码)

【问题讨论】:

    标签: transparency


    【解决方案1】:

    GDI 不支持 Alpha 通道。当为 PNG 和 GIF 调用 Draw 方法时,一些内部 alpha 混合方法起作用,它不会触及在 DC 中选择的位图的 alpha 通道,它只使用内部存储的 PNG\GIF 图像的 alpha 通道数据组合颜色通道。

    对于 32 位 BMP,情况完全不同,没有 alpha 混合,所有位都只是复制到 DC 中。如果在 DC 中选择的位图的位深度和要在 DC 上绘制的位图的位深度匹配,则在 DC 上绘图就像一个 memcpy 调用。这就是为什么有时会出现 GDI 支持 Alpha 通道的错觉,但实际上这只是字节的愚蠢复制,复制的 Alpha 通道不会对生成的图像产生任何影响。

    换句话说,不要使用 GDI 或任何基于它的库来处理 Alpha 通道。使用 GDI+,自发布以来已经过去了大约 10 年,几乎可以在所有 Windows 计算机上找到它。

    【讨论】:

      猜你喜欢
      • 2016-05-07
      • 1970-01-01
      • 2016-07-26
      • 1970-01-01
      • 2013-10-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多