1

在 Windows 7(和新的图像编解码器:WIC)之前,我使用以下(非常快速但肮脏)的方法来创建一个 Gif 编码图像,其中白色作为透明色:

MemoryStream target = new memoryStream(4096);
image.Save(target, imageFormat.Gif);
byte[] data = target.ToArray();

// Set transparency
// Check Graphic Control Extension signature (0x21 0xF9)
if (data[0x30D] == 0x21 && data[0x30E] == 0xF9)
   data[0x313] = 0xFF; // Set palette index 255 (=white) as transparent

这种方法之所以有效,是因为 .NET 过去使用标准调色板对 Gif 进行编码,其中索引 255 是白色。

然而,在 Windows 7 中,这种方法不再有效。似乎标准调色板已更改,现在索引 251 是白色。但是我不确定。也许新的 Gif 编码器会根据使用的颜色动态生成调色板?

我的问题:是否有人对 Windows 7 的新 Gif 编码器有深入了解,以及什么是使白色透明的好且快速的方法?

4

2 回答 2

3

我找到了一种将白色设置为 gif 编码图像的透明颜色的更好方法。它似乎适用于由 GDI+ 和 WIC (Windows 7) 编码器编码的 Gif。以下代码在 Gif 的全局图像表中搜索白色的索引,并使用该索引在图形控件扩展块中设置透明色。

 byte[] data;

// Save image to byte array
using (MemoryStream target = new MemoryStream(4096))
{
    image.Save(target, imageFormat.Gif);
    data = target.ToArray();
}

// Find the index of the color white in the Global Color Table and set this index as the transparent color
byte packedFields = data[0x0A]; // <packed fields> of the logical screen descriptor
if ((packedFields & 80) != 0 && (packedFields & 0x07) == 0x07) // Global color table is present and has 3 bytes per color
{
    int whiteIndex = -1;
    // Start at last entry of Global Color Table (bigger chance to find white?)
    for (int index = 0x0D + (3 * 255); index > 0x0D; index -= 3)
    {
        if (data[index] == 0xFF && data[index + 1] == 0xFF && data[index + 2] == 0xFF)
        {
            whiteIndex = (int) ((index - 0xD) / 3);
            break;
        }
    }

    if (whiteIndex != -1)
    {
        // Set transparency
        // Check Graphic Control Extension signature (0x21 0xF9)
        if (data[0x30D] == 0x21 && data[0x30E] == 0xF9)
            data[0x313] = (byte)whiteIndex;
    }
}

// Now the byte array contains a Gif image with white as the transparent color
于 2009-11-25T14:12:32.173 回答
0

您确定这是 Windows 7 问题,而不是您的代码其他地方的问题吗?

GIF 规范建议任何索引都可以用于透明度。您可能需要检查您的图像以确保设置了启用透明度的适当位。如果不是,那么您选择的调色板索引将被忽略。

于 2009-11-25T11:52:27.150 回答