原文出处
http://blog.csdn.net/ncjmc/archive/2006/08/28/1132879.aspx
以前在用C#做网站保存缩略图的程序中发现,当保存为GIF文件类型时,原来的透明背景变成了黑色,当时由于赶时间,就统一用白色代替了背景,并用Jpeg格式存储,并没有深究。
近来在网上查阅了许多资料,看到了两种解决方法:一种是在显示时设置透明背景色,GIF文件本身并不改变,另一种是不推荐使用的调用API的方法。将后一种I的VB源码用C#重写后,发现其中的调色板设置太少,转换效果不理想。
重新到网上搜索关于调色板的资料,发现MSDN上的一篇《对 ASP.NET 图像的颜色量化(Quantization)进行优化》的文章。
http://www.microsoft.com/china/MSDN/library/archives/library/DNAspp/html/colorquant.asp
将其中基于调色板量化的代码分离出来,透明背景色的图片保存成功。
完整代码如下:
1
public class GifPalette
2![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedBlockStart.gif)
{
3
private static ArrayList _cardPalette;
4
private Color[] _colors;
5
private Hashtable _colorMap;
6![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
7
public GifPalette(ArrayList palette)
8![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
9
_colorMap = new Hashtable();
10
_colors = new Color[palette.Count];
11
palette.CopyTo(_colors);
12
}
13![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
14
public GifPalette()
15![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
16
ArrayList palette = SetPalette();
17
_colorMap = new Hashtable();
18
_colors = new Color[palette.Count];
19
palette.CopyTo(_colors);
20
}
21![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
22
public Bitmap Quantize(Image source)
23![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
24
int height = source.Height;
25
int width = source.Width;
26![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
27
Rectangle bounds = new Rectangle(0, 0, width, height);
28![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
29
Bitmap copy = new Bitmap(width, height, PixelFormat.Format32bppArgb);
30
Bitmap output = new Bitmap(width, height, PixelFormat.Format8bppIndexed);
31![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
32
using (Graphics g = Graphics.FromImage(copy))
33![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
34
g.PageUnit = GraphicsUnit.Pixel;
35![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
36
g.DrawImageUnscaled(source, bounds);
37
}
38![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
39
BitmapData sourceData = null;
40![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
41
try
42![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
43
sourceData = copy.LockBits(bounds, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb);
44![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
45
output.Palette = this.GetPalette(output.Palette);
46![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
47
SecondPass(sourceData, output, width, height, bounds);
48
}
49
finally
50![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
51
copy.UnlockBits(sourceData);
52
}
53![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
54
return output;
55
}
56![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
57
private ColorPalette GetPalette(ColorPalette palette)
58![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
59
for (int index = 0; index < _colors.Length; index++)
60
palette.Entries[index] = _colors[index];
61
return palette;
62
}
63![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
64
private unsafe void SecondPass(BitmapData sourceData, Bitmap output, int width, int height, Rectangle bounds)
65![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
66
BitmapData outputData = null;
67![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
68
try
69![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
70
outputData = output.LockBits(bounds, ImageLockMode.WriteOnly, PixelFormat.Format8bppIndexed);
71![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
72
byte* pSourceRow = (byte*)sourceData.Scan0.ToPointer();
73
Int32* pSourcePixel = (Int32*)pSourceRow;
74
Int32* pPreviousPixel = pSourcePixel;
75![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
76
byte* pDestinationRow = (byte*)outputData.Scan0.ToPointer();
77
byte* pDestinationPixel = pDestinationRow;
78![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
79
byte pixelValue = QuantizePixel((Color32*)pSourcePixel);
80![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
81
*pDestinationPixel = pixelValue;
82![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
83
for (int row = 0; row < height; row++)
84![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
85
pSourcePixel = (Int32*)pSourceRow;
86![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
87
pDestinationPixel = pDestinationRow;
88![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
89
for (int col = 0; col < width; col++, pSourcePixel++, pDestinationPixel++)
90![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
91
if (*pPreviousPixel != *pSourcePixel)
92![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
93
pixelValue = QuantizePixel((Color32*)pSourcePixel);
94![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
95
pPreviousPixel = pSourcePixel;
96
}
97![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
98
*pDestinationPixel = pixelValue;
99
}
100![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
101
pSourceRow += sourceData.Stride;
102![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
103
pDestinationRow += outputData.Stride;
104
}
105
}
106
finally
107![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
108
output.UnlockBits(outputData);
109
}
110
}
111![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
112
private unsafe byte QuantizePixel(Color32* pixel)
113![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
114
byte colorIndex = 0;
115
int colorHash = pixel->ARGB;
116![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
117
if (_colorMap.ContainsKey(colorHash))
118
colorIndex = (byte)_colorMap[colorHash];
119
else
120![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
121
if (0 == pixel->Alpha)
122![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
123
for (int index = 0; index < _colors.Length; index++)
124![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
125
if (0 == _colors[index].A)
126![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
127
colorIndex = (byte)index;
128
break;
129
}
130
}
131
}
132
else
133![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
134
int leastDistance = int.MaxValue;
135
int red = pixel->Red;
136
int green = pixel->Green;
137
int blue = pixel->Blue;
138![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
139
for (int index = 0; index < _colors.Length; index++)
140![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
141
Color paletteColor = _colors[index];
142![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
143
int redDistance = paletteColor.R - red;
144
int greenDistance = paletteColor.G - green;
145
int blueDistance = paletteColor.B - blue;
146![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
147
int distance = (redDistance * redDistance) +
148
(greenDistance * greenDistance) +
149
(blueDistance * blueDistance);
150![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
151
if (distance < leastDistance)
152![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
153
colorIndex = (byte)index;
154
leastDistance = distance;
155![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
156
if (0 == distance)
157
break;
158
}
159
}
160
}
161![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
162
_colorMap.Add(colorHash, colorIndex);
163
}
164![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
165
return colorIndex;
166
}
167![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
168
[StructLayout(LayoutKind.Explicit)]
169
public struct Color32
170![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
171
[FieldOffset(0)]
172
public byte Blue;
173![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
174
[FieldOffset(1)]
175
public byte Green;
176![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
177
[FieldOffset(2)]
178
public byte Red;
179![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
180
[FieldOffset(3)]
181
public byte Alpha;
182![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
183
[FieldOffset(0)]
184
public int ARGB;
185![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
186
public Color Color
187![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
188![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
get
{ return Color.FromArgb(Alpha, Red, Green, Blue); }
189
}
190
}
191![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
192
public static ArrayList SetPalette()
193![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
194
if (null == _cardPalette)
195![](https://www.cnblogs.com/Images/OutliningIndicators/ExpandedSubBlockStart.gif)
{
196
_cardPalette = new ArrayList();
197![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
198
//Insert the colors into the arraylist
199![](https://www.cnblogs.com/Images/OutliningIndicators/ContractedSubBlock.gif)
Insert the colors into the arraylist#region Insert the colors into the arraylist
200
_cardPalette.Add(Color.FromArgb(255, 0, 0, 0));
201
_cardPalette.Add(Color.FromArgb(255, 128, 0, 0));
202
_cardPalette.Add(Color.FromArgb(255, 0, 128, 0));
203
_cardPalette.Add(Color.FromArgb(255, 128, 128, 0));
204
_cardPalette.Add(Color.FromArgb(255, 0, 0, 128));
205
_cardPalette.Add(Color.FromArgb(255, 128, 0, 128));
206
_cardPalette.Add(Color.FromArgb(255, 0, 128, 128));
207
_cardPalette.Add(Color.FromArgb(255, 192, 192, 192));
208
_cardPalette.Add(Color.FromArgb(255, 192, 220, 192));
209
_cardPalette.Add(Color.FromArgb(255, 166, 202, 240));
210
_cardPalette.Add(Color.FromArgb(255, 1, 25, 83));
211
_cardPalette.Add(Color.FromArgb(255, 1, 37, 92));
212
_cardPalette.Add(Color.FromArgb(255, 2, 51, 103));
213
_cardPalette.Add(Color.FromArgb(255, 18, 66, 114));
214
_cardPalette.Add(Color.FromArgb(255, 39, 78, 123));
215
_cardPalette.Add(Color.FromArgb(255, 101, 63, 107));
216
_cardPalette.Add(Color.FromArgb(255, 72, 92, 119));
217
_cardPalette.Add(Color.FromArgb(255, 89, 74, 121));
218
_cardPalette.Add(Color.FromArgb(255, 85, 101, 122));
219
_cardPalette.Add(Color.FromArgb(255, 122, 89, 127));
220
_cardPalette.Add(Color.FromArgb(255, 101, 108, 106));
221
_cardPalette.Add(Color.FromArgb(255, 111, 116, 111));
222
_cardPalette.Add(Color.FromArgb(255, 109, 118, 122));
223
_cardPalette.Add(Color.FromArgb(255, 120, 119, 97));
224
_cardPalette.Add(Color.FromArgb(255, 121, 124, 114));
225
_cardPalette.Add(Color.FromArgb(255, 1, 52, 154));
226
_cardPalette.Add(Color.FromArgb(255, 16, 61, 156));
227
_cardPalette.Add(Color.FromArgb(255, 15, 63, 160));
228
_cardPalette.Add(Color.FromArgb(255, 37, 55, 131));
229
_cardPalette.Add(Color.FromArgb(255, 24, 69, 158));
230
_cardPalette.Add(Color.FromArgb(255, 21, 68, 162));
231
_cardPalette.Add(Color.FromArgb(255, 35, 71, 137));
232
_cardPalette.Add(Color.FromArgb(255, 33, 71, 152));
233
_cardPalette.Add(Color.FromArgb(255, 43, 93, 130));
234
_cardPalette.Add(Color.FromArgb(255, 51, 68, 139));
235
_cardPalette.Add(Color.FromArgb(255, 48, 79, 159));
236
_cardPalette.Add(Color.FromArgb(255, 53, 85, 131));
237
_cardPalette.Add(Color.FromArgb(255, 49, 81, 151));
238
_cardPalette.Add(Color.FromArgb(255, 34, 78, 167));
239
_cardPalette.Add(Color.FromArgb(255, 41, 84, 170));
240
_cardPalette.Add(Color.FromArgb(255, 50, 91, 173));
241
_cardPalette.Add(Color.FromArgb(255, 54, 94, 176));
242
_cardPalette.Add(Color.FromArgb(255, 53, 101, 136));
243
_cardPalette.Add(Color.FromArgb(255, 60, 97, 168));
244
_cardPalette.Add(Color.FromArgb(255, 59, 99, 177));
245
_cardPalette.Add(Color.FromArgb(255, 68, 93, 134));
246
_cardPalette.Add(Color.FromArgb(255, 67, 91, 150));
247
_cardPalette.Add(Color.FromArgb(255, 86, 93, 151));
248
_cardPalette.Add(Color.FromArgb(255, 64, 102, 142));
249
_cardPalette.Add(Color.FromArgb(255, 76, 105, 153));
250
_cardPalette.Add(Color.FromArgb(255, 75, 116, 150));
251
_cardPalette.Add(Color.FromArgb(255, 81, 103, 140));
252
_cardPalette.Add(Color.FromArgb(255, 84, 106, 147));
253
_cardPalette.Add(Color.FromArgb(255, 91, 113, 146));
254
_cardPalette.Add(Color.FromArgb(255, 75, 107, 172));
255
_cardPalette.Add(Color.FromArgb(255, 65, 103, 180));
256
_cardPalette.Add(Color.FromArgb(255, 77, 113, 184));
257
_cardPalette.Add(Color.FromArgb(255, 90, 104, 162));
258
_cardPalette.Add(Color.FromArgb(255, 90, 115, 160));
259
_cardPalette.Add(Color.FromArgb(255, 90, 123, 189));
260
_cardPalette.Add(Color.FromArgb(255, 101, 87, 130));
261
_cardPalette.Add(Color.FromArgb(255, 106, 108, 158));
262
_cardPalette.Add(Color.FromArgb(255, 101, 115, 130));
263
_cardPalette.Add(Color.FromArgb(255, 103, 121, 149));
264
_cardPalette.Add(Color.FromArgb(255, 112, 99, 139));
265
_cardPalette.Add(Color.FromArgb(255, 122, 110, 148));
266
_cardPalette.Add(Color.FromArgb(255, 101, 122, 165));
267
_cardPalette.Add(Color.FromArgb(255, 116, 124, 172));
268
_cardPalette.Add(Color.FromArgb(255, 93, 126, 192));
269
_cardPalette.Add(Color.FromArgb(255, 96, 127, 192));
270
_cardPalette.Add(Color.FromArgb(0, 72, 254, 42));
271
_cardPalette.Add(Color.FromArgb(255, 90, 128, 160));
272
_cardPalette.Add(Color.FromArgb(255, 97, 130, 159));
273
_cardPalette.Add(Color.FromArgb(255, 119, 129, 138));
274
_cardPalette.Add(Color.FromArgb(255, 118, 133, 154));
275
_cardPalette.Add(Color.FromArgb(255, 107, 131, 169));
276
_cardPalette.Add(Color.FromArgb(255, 105, 132, 186));
277
_cardPalette.Add(Color.FromArgb(255, 118, 138, 170));
278
_cardPalette.Add(Color.FromArgb(255, 117, 137, 180));
279
_cardPalette.Add(Color.FromArgb(255, 118, 145, 173));
280
_cardPalette.Add(Color.FromArgb(255, 124, 152, 183));
281
_cardPalette.Add(Color.FromArgb(255, 95, 128, 192));
282
_cardPalette.Add(Color.FromArgb(255, 102, 133, 195));
283
_cardPalette.Add(Color.FromArgb(255, 112, 141, 199));
284
_cardPalette.Add(Color.FromArgb(255, 120, 147, 202));
285
_cardPalette.Add(Color.FromArgb(255, 154, 53, 53));
286
_cardPalette.Add(Color.FromArgb(255, 131, 72, 91));
287
_cardPalette.Add(Color.FromArgb(255, 143, 87, 104));
288
_cardPalette.Add(Color.FromArgb(255, 129, 123, 92));
289
_cardPalette.Add(Color.FromArgb(255, 156, 124, 68));
290
_cardPalette.Add(Color.FromArgb(255, 129, 126, 101));
291
_cardPalette.Add(Color.FromArgb(255, 154, 105, 120));
292
_cardPalette.Add(Color.FromArgb(255, 169, 83, 82));
293
_cardPalette.Add(Color.FromArgb(255, 165, 125, 70));
294
_cardPalette.Add(Color.FromArgb(255, 160, 125, 80));
295
_cardPalette.Add(Color.FromArgb(255, 176, 109, 114));
296
_cardPalette.Add(Color.FromArgb(255, 205, 53, 2));
297
_cardPalette.Add(Color.FromArgb(255, 209, 67, 19));
298
_cardPalette.Add(Color.FromArgb(255, 210, 85, 47));
299
_cardPalette.Add(Color.FromArgb(255, 230, 67, 21));
300
_cardPalette.Add(Color.FromArgb(255, 243, 88, 46));
301
_cardPalette.Add(Color.FromArgb(255, 255, 97, 53));
302
_cardPalette.Add(Color.FromArgb(255, 201, 92, 71));
303
_cardPalette.Add(Color.FromArgb(255, 214, 107, 79));
304
_cardPalette.Add(Color.FromArgb(255, 205, 117, 105));
305
_cardPalette.Add(Color.FromArgb(255, 245, 112, 74));
306
_cardPalette.Add(Color.FromArgb(255, 131, 101, 136));
307
_cardPalette.Add(Color.FromArgb(255, 139, 110, 144));
308
_cardPalette.Add(Color.FromArgb(255, 130, 120, 156));
309
_cardPalette.Add(Color.FromArgb(255, 146, 124, 155));
310
_cardPalette.Add(Color.FromArgb(255, 162, 117, 131));
311
_cardPalette.Add(Color.FromArgb(255, 141, 133, 94));
312
_cardPalette.Add(Color.FromArgb(255, 156, 131, 72));
313
_cardPalette.Add(Color.FromArgb(255, 151, 133, 83));
314
_cardPalette.Add(Color.FromArgb(255, 157, 144, 92));
315
_cardPalette.Add(Color.FromArgb(255, 137, 132, 102));
316
_cardPalette.Add(Color.FromArgb(255, 135, 136, 120));
317
_cardPalette.Add(Color.FromArgb(255, 147, 139, 102));
318
_cardPalette.Add(Color.FromArgb(255, 148, 143, 115));
319
_cardPalette.Add(Color.FromArgb(255, 156, 146, 106));
320
_cardPalette.Add(Color.FromArgb(255, 148, 145, 122));
321
_cardPalette.Add(Color.FromArgb(255, 168, 136, 73));
322
_cardPalette.Add(Color.FromArgb(255, 168, 138, 88));
323
_cardPalette.Add(Color.FromArgb(255, 172, 147, 90));
324
_cardPalette.Add(Color.FromArgb(255, 178, 138, 82));
325
_cardPalette.Add(Color.FromArgb(255, 186, 153, 69));
326
_cardPalette.Add(Color.FromArgb(255, 179, 150, 91));
327
_cardPalette.Add(Color.FromArgb(255, 174, 139, 100));
328
_cardPalette.Add(Color.FromArgb(255, 166, 154, 107));
329
_cardPalette.Add(Color.FromArgb(255, 161, 151, 114));
330
_cardPalette.Add(Color.FromArgb(255, 182, 154, 101));
331
_cardPalette.Add(Color.FromArgb(255, 190, 162, 81));
332
_cardPalette.Add(Color.FromArgb(255, 172, 160, 117));
333
_cardPalette.Add(Color.FromArgb(255, 183, 161, 103));
334
_cardPalette.Add(Color.FromArgb(255, 182, 163, 119));
335
_cardPalette.Add(Color.FromArgb(255, 205, 168, 63));
336
_cardPalette.Add(Color.FromArgb(255, 218, 174, 52));
337
_cardPalette.Add(Color.FromArgb(255, 221, 177, 53));
338
_cardPalette.Add(Color.FromArgb(255, 255, 154, 1));
339
_cardPalette.Add(Color.FromArgb(255, 255, 161, 18));
340
_cardPalette.Add(Color.FromArgb(255, 235, 184, 44));
341
_cardPalette.Add(Color.FromArgb(255, 228, 182, 52));
342
_cardPalette.Add(Color.FromArgb(255, 247, 190, 36));
343
_cardPalette.Add(Color.FromArgb(255, 200, 155, 94));
344
_cardPalette.Add(Color.FromArgb(255, 192, 153, 104));
345
_cardPalette.Add(Color.FromArgb(255, 223, 130, 103));
346
_cardPalette.Add(Color.FromArgb(255, 215, 132, 118));
347
_cardPalette.Add(Color.FromArgb(255, 201, 167, 68));
348
_cardPalette.Add(Color.FromArgb(255, 196, 167, 87));
349
_cardPalette.Add(Color.FromArgb(255, 209, 173, 70));
350
_cardPalette.Add(Color.FromArgb(255, 212, 169, 91));
351
_cardPalette.Add(Color.FromArgb(255, 213, 177, 73));
352
_cardPalette.Add(Color.FromArgb(255, 198, 166, 102));
353
_cardPalette.Add(Color.FromArgb(255, 196, 168, 123));
354
_cardPalette.Add(Color.FromArgb(255, 219, 172, 112));
355
_cardPalette.Add(Color.FromArgb(255, 219, 183, 106));
356
_cardPalette.Add(Color.FromArgb(255, 217, 185, 115));
357
_cardPalette.Add(Color.FromArgb(255, 255, 131, 91));
358
_cardPalette.Add(Color.FromArgb(255, 249, 143, 109));
359
_cardPalette.Add(Color.FromArgb(255, 227, 186, 108));
360
_cardPalette.Add(Color.FromArgb(255, 229, 186, 112));
361
_cardPalette.Add(Color.FromArgb(255, 255, 164, 123));
362
_cardPalette.Add(Color.FromArgb(255, 207, 195, 127));
363
_cardPalette.Add(Color.FromArgb(255, 253, 204, 94));
364
_cardPalette.Add(Color.FromArgb(255, 235, 194, 108));
365
_cardPalette.Add(Color.FromArgb(255, 233, 197, 117));
366
_cardPalette.Add(Color.FromArgb(255, 252, 204, 104));
367
_cardPalette.Add(Color.FromArgb(255, 249, 204, 115));
368
_cardPalette.Add(Color.FromArgb(255, 251, 208, 106));
369
_cardPalette.Add(Color.FromArgb(255, 253, 209, 117));
370
_cardPalette.Add(Color.FromArgb(255, 128, 137, 140));
371
_cardPalette.Add(Color.FromArgb(255, 136, 144, 145));
372
_cardPalette.Add(Color.FromArgb(255, 151, 150, 130));
373
_cardPalette.Add(Color.FromArgb(255, 144, 149, 148));
374
_cardPalette.Add(Color.FromArgb(255, 137, 131, 165));
375
_cardPalette.Add(Color.FromArgb(255, 137, 140, 180));
376
_cardPalette.Add(Color.FromArgb(255, 140, 154, 168));
377
_cardPalette.Add(Color.FromArgb(255, 133, 151, 180));
378
_cardPalette.Add(Color.FromArgb(255, 149, 137, 167));
379
_cardPalette.Add(Color.FromArgb(255, 149, 152, 188));
380
_cardPalette.Add(Color.FromArgb(255, 138, 168, 188));
381
_cardPalette.Add(Color.FromArgb(255, 175, 135, 148));
382
_cardPalette.Add(Color.FromArgb(255, 169, 154, 129));
383
_cardPalette.Add(Color.FromArgb(255, 187, 135, 134));
384
_cardPalette.Add(Color.FromArgb(255, 178, 138, 148));
385
_cardPalette.Add(Color.FromArgb(255, 184, 146, 156));
386
_cardPalette.Add(Color.FromArgb(255, 168, 149, 173));
387
_cardPalette.Add(Color.FromArgb(255, 170, 163, 131));
388
_cardPalette.Add(Color.FromArgb(255, 184, 165, 128));
389
_cardPalette.Add(Color.FromArgb(255, 181, 166, 157));
390
_cardPalette.Add(Color.FromArgb(255, 162, 175, 186));
391
_cardPalette.Add(Color.FromArgb(255, 189, 185, 170));
392
_cardPalette.Add(Color.FromArgb(255, 130, 155, 206));
393
_cardPalette.Add(Color.FromArgb(255, 134, 158, 208));
394
_cardPalette.Add(Color.FromArgb(255, 146, 155, 196));
395
_cardPalette.Add(Color.FromArgb(255, 142, 169, 193));
396
_cardPalette.Add(Color.FromArgb(255, 140, 163, 209));
397
_cardPalette.Add(Color.FromArgb(255, 153, 168, 199));
398
_cardPalette.Add(Color.FromArgb(255, 148, 170, 213));
399
_cardPalette.Add(Color.FromArgb(255, 157, 177, 216));
400
_cardPalette.Add(Color.FromArgb(255, 164, 166, 193));
401
_cardPalette.Add(Color.FromArgb(255, 171, 179, 198));
402
_cardPalette.Add(Color.FromArgb(255, 167, 185, 220));
403
_cardPalette.Add(Color.FromArgb(255, 181, 179, 205));
404
_cardPalette.Add(Color.FromArgb(255, 181, 188, 211));
405
_cardPalette.Add(Color.FromArgb(255, 173, 190, 224));
406
_cardPalette.Add(Color.FromArgb(255, 178, 196, 217));
407
_cardPalette.Add(Color.FromArgb(255, 174, 192, 224));
408
_cardPalette.Add(Color.FromArgb(255, 174, 212, 224));
409
_cardPalette.Add(Color.FromArgb(255, 184, 198, 227));
410
_cardPalette.Add(Color.FromArgb(255, 185, 218, 229));
411
_cardPalette.Add(Color.FromArgb(255, 202, 145, 142));
412
_cardPalette.Add(Color.FromArgb(255, 196, 172, 134));
413
_cardPalette.Add(Color.FromArgb(255, 203, 161, 158));
414
_cardPalette.Add(Color.FromArgb(255, 203, 177, 134));
415
_cardPalette.Add(Color.FromArgb(255, 207, 185, 151));
416
_cardPalette.Add(Color.FromArgb(255, 210, 186, 132));
417
_cardPalette.Add(Color.FromArgb(255, 215, 189, 148));
418
_cardPalette.Add(Color.FromArgb(255, 213, 168, 167));
419
_cardPalette.Add(Color.FromArgb(255, 234, 155, 132));
420
_cardPalette.Add(Color.FromArgb(255, 253, 172, 140));
421
_cardPalette.Add(Color.FromArgb(255, 193, 191, 193));
422
_cardPalette.Add(Color.FromArgb(255, 206, 194, 135));
423
_cardPalette.Add(Color.FromArgb(255, 214, 198, 136));
424
_cardPalette.Add(Color.FromArgb(255, 219, 204, 145));
425
_cardPalette.Add(Color.FromArgb(255, 218, 209, 141));
426
_cardPalette.Add(Color.FromArgb(255, 215, 209, 154));
427
_cardPalette.Add(Color.FromArgb(255, 231, 196, 135));
428
_cardPalette.Add(Color.FromArgb(255, 225, 213, 143));
429
_cardPalette.Add(Color.FromArgb(255, 231, 217, 148));
430
_cardPalette.Add(Color.FromArgb(255, 251, 212, 129));
431
_cardPalette.Add(Color.FromArgb(255, 255, 199, 172));
432
_cardPalette.Add(Color.FromArgb(255, 202, 205, 219));
433
_cardPalette.Add(Color.FromArgb(255, 193, 205, 230));
434
_cardPalette.Add(Color.FromArgb(255, 200, 211, 233));
435
_cardPalette.Add(Color.FromArgb(255, 211, 220, 237));
436
_cardPalette.Add(Color.FromArgb(255, 213, 222, 240));
437
_cardPalette.Add(Color.FromArgb(255, 201, 226, 228));
438
_cardPalette.Add(Color.FromArgb(255, 201, 231, 242));
439
_cardPalette.Add(Color.FromArgb(255, 216, 227, 232));
440
_cardPalette.Add(Color.FromArgb(255, 219, 227, 241));
441
_cardPalette.Add(Color.FromArgb(255, 228, 233, 237));
442
_cardPalette.Add(Color.FromArgb(255, 229, 234, 244));
443
_cardPalette.Add(Color.FromArgb(255, 236, 241, 248));
444
_cardPalette.Add(Color.FromArgb(255, 240, 239, 243));
445
_cardPalette.Add(Color.FromArgb(255, 253, 253, 254));
446
_cardPalette.Add(Color.FromArgb(255, 255, 251, 240));
447
_cardPalette.Add(Color.FromArgb(255, 160, 160, 164));
448
_cardPalette.Add(Color.FromArgb(255, 128, 128, 128));
449
_cardPalette.Add(Color.FromArgb(255, 255, 0, 0));
450
_cardPalette.Add(Color.FromArgb(255, 0, 255, 0));
451
_cardPalette.Add(Color.FromArgb(255, 255, 255, 0));
452
_cardPalette.Add(Color.FromArgb(255, 0, 0, 255));
453
_cardPalette.Add(Color.FromArgb(255, 255, 0, 255));
454
_cardPalette.Add(Color.FromArgb(255, 0, 255, 255));
455
_cardPalette.Add(Color.FromArgb(255, 255, 255, 255));
456
#endregion
457
}
458
return _cardPalette;
459
}
460![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
461![](https://www.cnblogs.com/Images/OutliningIndicators/InBlock.gif)
462
}
调用方法:
先将该类添加到项目中,再在合适的地方调用。例:
Bitmap bitmap = new System.Drawing.Bitmap(width, height); // Image类也可
// ......(图形操作代码)
WindwoodGif.GifPalette gifPalette = new WindwoodGif.GifPalette();
bitmap = gifPalette.Quantize(bitmap);
bitmap.Save(SaveFileName, ImageFormat.Gif);
经测试,这种方法能够实现GIF文件的透明背景存储,在WinForm、WebForm均能使用。由于使用了标准256色调色板,内存开销可能较大,转换时间相对较慢,图像质量也有一定影响。此外,代码中使用了非安全代码(指针),在编译时项目属性中要设置允许不安全代码。