~ubuntu-branches/ubuntu/trusty/monodevelop/trusty-proposed

« back to all changes in this revision

Viewing changes to external/ikvm/awt/IconFactory.cs

  • Committer: Package Import Robot
  • Author(s): Jo Shields
  • Date: 2013-05-12 09:46:03 UTC
  • mto: This revision was merged to the branch mainline in revision 29.
  • Revision ID: package-import@ubuntu.com-20130512094603-mad323bzcxvmcam0
Tags: upstream-4.0.5+dfsg
ImportĀ upstreamĀ versionĀ 4.0.5+dfsg

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
  Copyright (C) 2012 Volker Berlin (i-net software)
 
3
 
 
4
  This software is provided 'as-is', without any express or implied
 
5
  warranty.  In no event will the authors be held liable for any damages
 
6
  arising from the use of this software.
 
7
 
 
8
  Permission is granted to anyone to use this software for any purpose,
 
9
  including commercial applications, and to alter it and redistribute it
 
10
  freely, subject to the following restrictions:
 
11
 
 
12
  1. The origin of this software must not be misrepresented; you must not
 
13
     claim that you wrote the original software. If you use this software
 
14
     in a product, an acknowledgment in the product documentation would be
 
15
     appreciated but is not required.
 
16
  2. Altered source versions must be plainly marked as such, and must not be
 
17
     misrepresented as being the original software.
 
18
  3. This notice may not be removed or altered from any source distribution.
 
19
 
 
20
  Jeroen Frijters
 
21
  jeroen@frijters.net 
 
22
 
 
23
*/
 
24
 
 
25
namespace ikvm.awt
 
26
{
 
27
 
 
28
    using java.awt.image;
 
29
    using System.IO;
 
30
    using System.Drawing;
 
31
 
 
32
    /// <summary>
 
33
    /// Encodes images in ICO format.
 
34
    /// </summary>
 
35
    internal class IconFactory
 
36
    {
 
37
 
 
38
        /// <summary>
 
39
        /// Indicates that ICO data represents an icon (.ICO).
 
40
        /// </summary>
 
41
        private const int TYPE_ICON = 1;
 
42
 
 
43
        private BinaryWriter writer;
 
44
 
 
45
        /// <summary>
 
46
        /// Creates a new instance of IconFactory </summary>
 
47
        internal IconFactory()
 
48
        {
 
49
        }
 
50
 
 
51
        /// <summary>
 
52
        /// Create a Icon from the given list of images
 
53
        /// </summary>
 
54
        /// <param name="images">list of images</param>
 
55
        /// <returns></returns>
 
56
        internal Icon CreateIcon(java.util.List images, Size size)
 
57
        {
 
58
            MemoryStream stream = new MemoryStream();
 
59
            Write(images, stream);
 
60
            stream.Position = 0;
 
61
            return new Icon(stream, size);
 
62
        }
 
63
 
 
64
        /// <summary>
 
65
        /// Encodes and writes multiple images without colour depth conversion.
 
66
        /// </summary>
 
67
        /// <param name="images">
 
68
        ///            the list of source images to be encoded </param>
 
69
        /// <param name="stream">
 
70
        ///            the output to which the encoded image will be written </param>
 
71
        internal void Write(java.util.List images, System.IO.Stream stream)
 
72
        {
 
73
            writer = new BinaryWriter(stream);
 
74
 
 
75
            int count = images.size();
 
76
 
 
77
            // file header 6
 
78
            WriteFileHeader(count, TYPE_ICON);
 
79
 
 
80
            // file offset where images start
 
81
            int fileOffset = 6 + count * 16;
 
82
 
 
83
            // icon entries 16 * count
 
84
            for (int i = 0; i < count; i++)
 
85
            {
 
86
                BufferedImage imgc = (BufferedImage)images.get(i);
 
87
                fileOffset += WriteIconEntry(imgc, fileOffset);
 
88
            }
 
89
 
 
90
            // images
 
91
            for (int i = 0; i < count; i++)
 
92
            {
 
93
                BufferedImage imgc = (BufferedImage)images.get(i);
 
94
 
 
95
                // info header
 
96
                WriteInfoHeader(imgc);
 
97
                // color map
 
98
                if (imgc.getColorModel().getPixelSize() <= 8)
 
99
                {
 
100
                    IndexColorModel icm = (IndexColorModel)imgc.getColorModel();
 
101
                    WriteColorMap(icm);
 
102
                }
 
103
                // xor bitmap
 
104
                WriteXorBitmap(imgc);
 
105
                // and bitmap
 
106
                WriteAndBitmap(imgc);
 
107
 
 
108
            }
 
109
        }
 
110
 
 
111
        /// <summary>
 
112
        /// Writes the ICO file header for an ICO containing the given number of
 
113
        /// images.
 
114
        /// </summary>
 
115
        /// <param name="count">
 
116
        ///            the number of images in the ICO </param>
 
117
        /// <param name="type">
 
118
        ///            TYPE_ICON
 
119
        private void WriteFileHeader(int count, int type)
 
120
        {
 
121
            // reserved 2
 
122
            writer.Write((short)0);
 
123
            // type 2
 
124
            writer.Write((short)type);
 
125
            // count 2
 
126
            writer.Write((short)count);
 
127
        }
 
128
 
 
129
        /// <summary>
 
130
        /// Encodes the <em>AND</em> bitmap for the given image according the its
 
131
        /// alpha channel (transparency) and writes it to the given output.
 
132
        /// </summary>
 
133
        /// <param name="img">
 
134
        ///            the image to encode as the <em>AND</em> bitmap. </param>
 
135
        private void WriteAndBitmap(BufferedImage img)
 
136
        {
 
137
            WritableRaster alpha = img.getAlphaRaster();
 
138
 
 
139
            // indexed transparency (eg. GIF files)
 
140
            if (img.getColorModel() is IndexColorModel && img.getColorModel().hasAlpha())
 
141
            {
 
142
                int w = img.getWidth();
 
143
                int h = img.getHeight();
 
144
 
 
145
                int bytesPerLine = GetBytesPerLine1(w);
 
146
 
 
147
                byte[] line = new byte[bytesPerLine];
 
148
 
 
149
                IndexColorModel icm = (IndexColorModel)img.getColorModel();
 
150
                Raster raster = img.getRaster();
 
151
 
 
152
                for (int y = h - 1; y >= 0; y--)
 
153
                {
 
154
                    for (int x = 0; x < w; x++)
 
155
                    {
 
156
                        int bi = x / 8;
 
157
                        int i = x % 8;
 
158
                        // int a = alpha.getSample(x, y, 0);
 
159
                        int p = raster.getSample(x, y, 0);
 
160
                        int a = icm.getAlpha(p);
 
161
                        // invert bit since and mask is applied to xor mask
 
162
                        int b = ~a & 1;
 
163
                        line[bi] = SetBit(line[bi], i, b);
 
164
                    }
 
165
 
 
166
                    writer.Write(line);
 
167
                }
 
168
            }
 
169
            // no transparency
 
170
            else if (alpha == null)
 
171
            {
 
172
                int h = img.getHeight();
 
173
                int w = img.getWidth();
 
174
                // calculate number of bytes per line, including 32-bit padding
 
175
                int bytesPerLine = GetBytesPerLine1(w);
 
176
 
 
177
                byte[] line = new byte[bytesPerLine];
 
178
                for (int i = 0; i < bytesPerLine; i++)
 
179
                {
 
180
                    line[i] = (byte)0;
 
181
                }
 
182
 
 
183
                for (int y = h - 1; y >= 0; y--)
 
184
                {
 
185
                    writer.Write(line);
 
186
                }
 
187
            }
 
188
            // transparency (ARGB, etc. eg. PNG)
 
189
            else
 
190
            {
 
191
                int w = img.getWidth();
 
192
                int h = img.getHeight();
 
193
 
 
194
                int bytesPerLine = GetBytesPerLine1(w);
 
195
 
 
196
                byte[] line = new byte[bytesPerLine];
 
197
 
 
198
                for (int y = h - 1; y >= 0; y--)
 
199
                {
 
200
                    for (int x = 0; x < w; x++)
 
201
                    {
 
202
                        int bi = x / 8;
 
203
                        int i = x % 8;
 
204
                        int a = alpha.getSample(x, y, 0);
 
205
                        // invert bit since and mask is applied to xor mask
 
206
                        int b = ~a & 1;
 
207
                        line[bi] = SetBit(line[bi], i, b);
 
208
                    }
 
209
 
 
210
                    writer.Write(line);
 
211
                }
 
212
            }
 
213
        }
 
214
 
 
215
        private void WriteXorBitmap(BufferedImage img)
 
216
        {
 
217
            Raster raster = img.getRaster();
 
218
            switch (img.getColorModel().getPixelSize())
 
219
            {
 
220
                case 1:
 
221
                    Write1(raster);
 
222
                    break;
 
223
                case 4:
 
224
                    Write4(raster);
 
225
                    break;
 
226
                case 8:
 
227
                    Write8(raster);
 
228
                    break;
 
229
                case 24:
 
230
                    Write24(raster);
 
231
                    break;
 
232
                case 32:
 
233
                    Raster alpha = img.getAlphaRaster();
 
234
                    Write32(raster, alpha);
 
235
                    break;
 
236
            }
 
237
        }
 
238
 
 
239
        /// <summary>
 
240
        /// Writes the <tt>InfoHeader</tt> structure to output
 
241
        /// 
 
242
        /// </summary>
 
243
        private void WriteInfoHeader(BufferedImage img)
 
244
        {
 
245
            // Size of InfoHeader structure = 40
 
246
            writer.Write(40);
 
247
            // Width
 
248
            writer.Write(img.getWidth());
 
249
            // Height
 
250
            writer.Write(img.getHeight() * 2);
 
251
            // Planes (=1)
 
252
            writer.Write((short)1);
 
253
            // Bit count
 
254
            writer.Write((short)img.getColorModel().getPixelSize());
 
255
            // Compression
 
256
            writer.Write(0);
 
257
            // Image size - compressed size of image or 0 if Compression = 0
 
258
            writer.Write(0);
 
259
            // horizontal resolution pixels/meter
 
260
            writer.Write(0);
 
261
            // vertical resolution pixels/meter
 
262
            writer.Write(0);
 
263
            // Colors used - number of colors actually used
 
264
            writer.Write(0);
 
265
            // Colors important - number of important colors 0 = all
 
266
            writer.Write(0);
 
267
        }
 
268
 
 
269
        /// <summary>
 
270
        /// Writes the <tt>IconEntry</tt> structure to output
 
271
        /// </summary>
 
272
        private int WriteIconEntry(BufferedImage img, int fileOffset)
 
273
        {
 
274
            // Width 1 byte Cursor Width (16, 32 or 64)
 
275
            int width = img.getWidth();
 
276
            writer.Write((byte)(width == 256 ? 0 : width));
 
277
            // Height 1 byte Cursor Height (16, 32 or 64 , most commonly = Width)
 
278
            int height = img.getHeight();
 
279
            writer.Write((byte)(height == 256 ? 0 : height));
 
280
            // ColorCount 1 byte Number of Colors (2,16, 0=256)
 
281
            short BitCount = (short)img.getColorModel().getPixelSize();
 
282
            int NumColors = 1 << (BitCount == 32 ? 24 : (int)BitCount);
 
283
            byte ColorCount = (byte)(NumColors >= 256 ? 0 : NumColors);
 
284
            writer.Write((byte)ColorCount);
 
285
            // Reserved 1 byte =0
 
286
            writer.Write((byte)0);
 
287
            // Planes 2 byte =1
 
288
            writer.Write((short)1);
 
289
            // BitCount 2 byte bits per pixel (1, 4, 8)
 
290
            writer.Write((short)BitCount);
 
291
            // SizeInBytes 4 byte Size of (InfoHeader + ANDbitmap + XORbitmap)
 
292
            int cmapSize = GetColorMapSize(BitCount);
 
293
            int xorSize = GetBitmapSize(width, height, BitCount);
 
294
            int andSize = GetBitmapSize(width, height, 1);
 
295
            int size = 40 + cmapSize + xorSize + andSize;
 
296
            writer.Write(size);
 
297
            // FileOffset 4 byte FilePos, where InfoHeader starts
 
298
            writer.Write(fileOffset);
 
299
            return size;
 
300
        }
 
301
 
 
302
        /// <summary>
 
303
        /// Writes the colour map resulting from the source <tt>IndexColorModel</tt>.
 
304
        /// </summary>
 
305
        /// <param name="icm">
 
306
        ///            the source <tt>IndexColorModel</tt> </param>
 
307
        private void WriteColorMap(IndexColorModel icm)
 
308
        {
 
309
            int mapSize = icm.getMapSize();
 
310
            for (int i = 0; i < mapSize; i++)
 
311
            {
 
312
                int rgb = icm.getRGB(i);
 
313
                byte r = (byte)(rgb >> 16);
 
314
                byte g = (byte)(rgb >> 8);
 
315
                byte b = (byte)(rgb);
 
316
                writer.Write(b);
 
317
                writer.Write(g);
 
318
                writer.Write(r);
 
319
                writer.Write((byte)0);
 
320
            }
 
321
        }
 
322
 
 
323
        /// <summary>
 
324
        /// Calculates the number of bytes per line required for the given width in
 
325
        /// pixels, for a 1-bit bitmap. Lines are always padded to the next 4-byte
 
326
        /// boundary.
 
327
        /// </summary>
 
328
        /// <param name="width">
 
329
        ///            the width in pixels </param>
 
330
        /// <returns> the number of bytes per line </returns>
 
331
        private int GetBytesPerLine1(int width)
 
332
        {
 
333
            int ret = (int)width / 8;
 
334
            if (ret % 4 != 0)
 
335
            {
 
336
                ret = (ret / 4 + 1) * 4;
 
337
            }
 
338
            return ret;
 
339
        }
 
340
 
 
341
        /// <summary>
 
342
        /// Calculates the number of bytes per line required for the given with in
 
343
        /// pixels, for a 4-bit bitmap. Lines are always padded to the next 4-byte
 
344
        /// boundary.
 
345
        /// </summary>
 
346
        /// <param name="width">
 
347
        ///            the width in pixels </param>
 
348
        /// <returns> the number of bytes per line </returns>
 
349
        private int GetBytesPerLine4(int width)
 
350
        {
 
351
            int ret = (int)width / 2;
 
352
            if (ret % 4 != 0)
 
353
            {
 
354
                ret = (ret / 4 + 1) * 4;
 
355
            }
 
356
            return ret;
 
357
        }
 
358
 
 
359
        /// <summary>
 
360
        /// Calculates the number of bytes per line required for the given with in
 
361
        /// pixels, for a 8-bit bitmap. Lines are always padded to the next 4-byte
 
362
        /// boundary.
 
363
        /// </summary>
 
364
        /// <param name="width">
 
365
        ///            the width in pixels </param>
 
366
        /// <returns> the number of bytes per line </returns>
 
367
        private int GetBytesPerLine8(int width)
 
368
        {
 
369
            int ret = width;
 
370
            if (ret % 4 != 0)
 
371
            {
 
372
                ret = (ret / 4 + 1) * 4;
 
373
            }
 
374
            return ret;
 
375
        }
 
376
 
 
377
        /// <summary>
 
378
        /// Calculates the number of bytes per line required for the given with in
 
379
        /// pixels, for a 24-bit bitmap. Lines are always padded to the next 4-byte
 
380
        /// boundary.
 
381
        /// </summary>
 
382
        /// <param name="width">
 
383
        ///            the width in pixels </param>
 
384
        /// <returns> the number of bytes per line </returns>
 
385
        private int GetBytesPerLine24(int width)
 
386
        {
 
387
            int ret = width * 3;
 
388
            if (ret % 4 != 0)
 
389
            {
 
390
                ret = (ret / 4 + 1) * 4;
 
391
            }
 
392
            return ret;
 
393
        }
 
394
 
 
395
        /// <summary>
 
396
        /// Calculates the size in bytes of a bitmap with the specified size and
 
397
        /// colour depth.
 
398
        /// </summary>
 
399
        /// <param name="w">
 
400
        ///            the width in pixels </param>
 
401
        /// <param name="h">
 
402
        ///            the height in pixels </param>
 
403
        /// <param name="bpp">
 
404
        ///            the colour depth (bits per pixel) </param>
 
405
        /// <returns> the size of the bitmap in bytes </returns>
 
406
        private int GetBitmapSize(int w, int h, int bpp)
 
407
        {
 
408
            int bytesPerLine = 0;
 
409
            switch (bpp)
 
410
            {
 
411
                case 1:
 
412
                    bytesPerLine = GetBytesPerLine1(w);
 
413
                    break;
 
414
                case 4:
 
415
                    bytesPerLine = GetBytesPerLine4(w);
 
416
                    break;
 
417
                case 8:
 
418
                    bytesPerLine = GetBytesPerLine8(w);
 
419
                    break;
 
420
                case 24:
 
421
                    bytesPerLine = GetBytesPerLine24(w);
 
422
                    break;
 
423
                case 32:
 
424
                    bytesPerLine = w * 4;
 
425
                    break;
 
426
            }
 
427
            int ret = bytesPerLine * h;
 
428
            return ret;
 
429
        }
 
430
 
 
431
        /// <summary>
 
432
        /// Encodes and writes raster data as a 1-bit bitmap.
 
433
        /// </summary>
 
434
        /// <param name="raster">
 
435
        ///            the source raster data </param>
 
436
        private void Write1(Raster raster)
 
437
        {
 
438
            int bytesPerLine = GetBytesPerLine1(raster.getWidth());
 
439
 
 
440
            byte[] line = new byte[bytesPerLine];
 
441
 
 
442
            for (int y = raster.getHeight() - 1; y >= 0; y--)
 
443
            {
 
444
                for (int i = 0; i < bytesPerLine; i++)
 
445
                {
 
446
                    line[i] = 0;
 
447
                }
 
448
 
 
449
                for (int x = 0; x < raster.getWidth(); x++)
 
450
                {
 
451
                    int bi = x / 8;
 
452
                    int i = x % 8;
 
453
                    int index = raster.getSample(x, y, 0);
 
454
                    line[bi] = SetBit(line[bi], i, index);
 
455
                }
 
456
 
 
457
                writer.Write(line);
 
458
            }
 
459
        }
 
460
 
 
461
        /// <summary>
 
462
        /// Encodes and writes raster data as a 4-bit bitmap.
 
463
        /// </summary>
 
464
        /// <param name="raster">
 
465
        ///            the source raster data </param>
 
466
        private void Write4(Raster raster)
 
467
        {
 
468
            int width = raster.getWidth();
 
469
            int height = raster.getHeight();
 
470
 
 
471
            // calculate bytes per line
 
472
            int bytesPerLine = GetBytesPerLine4(width);
 
473
 
 
474
            // line buffer
 
475
            byte[] line = new byte[bytesPerLine];
 
476
 
 
477
            // encode and write lines
 
478
            for (int y = height - 1; y >= 0; y--)
 
479
            {
 
480
 
 
481
                // clear line buffer
 
482
                for (int i = 0; i < bytesPerLine; i++)
 
483
                {
 
484
                    line[i] = 0;
 
485
                }
 
486
 
 
487
                // encode raster data for line
 
488
                for (int x = 0; x < width; x++)
 
489
                {
 
490
 
 
491
                    // calculate buffer index
 
492
                    int bi = x / 2;
 
493
 
 
494
                    // calculate nibble index (high order or low order)
 
495
                    int i = x % 2;
 
496
 
 
497
                    // get color index
 
498
                    int index = raster.getSample(x, y, 0);
 
499
                    // set color index in buffer
 
500
                    line[bi] = SetNibble(line[bi], i, index);
 
501
                }
 
502
 
 
503
                // write line data (padding bytes included)
 
504
                writer.Write(line);
 
505
            }
 
506
        }
 
507
 
 
508
        /// <summary>
 
509
        /// Encodes and writes raster data as an 8-bit bitmap.
 
510
        /// </summary>
 
511
        /// <param name="raster">
 
512
        ///            the source raster data </param>
 
513
        private void Write8(Raster raster)
 
514
        {
 
515
            int width = raster.getWidth();
 
516
            int height = raster.getHeight();
 
517
 
 
518
            // calculate bytes per line
 
519
            int bytesPerLine = GetBytesPerLine8(width);
 
520
 
 
521
            // write lines
 
522
            for (int y = height - 1; y >= 0; y--)
 
523
            {
 
524
 
 
525
                // write raster data for each line
 
526
                for (int x = 0; x < width; x++)
 
527
                {
 
528
 
 
529
                    // get color index for pixel
 
530
                    byte index = (byte)raster.getSample(x, y, 0);
 
531
 
 
532
                    // write color index
 
533
                    writer.Write(index);
 
534
                }
 
535
 
 
536
                // write padding bytes at end of line
 
537
                for (int i = width; i < bytesPerLine; i++)
 
538
                {
 
539
                    writer.Write((byte)0);
 
540
                }
 
541
 
 
542
            }
 
543
        }
 
544
 
 
545
        /// <summary>
 
546
        /// Encodes and writes raster data as a 24-bit bitmap.
 
547
        /// </summary>
 
548
        /// <param name="raster">
 
549
        ///            the source raster data </param>
 
550
        private void Write24(Raster raster)
 
551
        {
 
552
            int width = raster.getWidth();
 
553
            int height = raster.getHeight();
 
554
 
 
555
            // calculate bytes per line
 
556
            int bytesPerLine = GetBytesPerLine24(width);
 
557
 
 
558
            // write lines
 
559
            for (int y = height - 1; y >= 0; y--)
 
560
            {
 
561
 
 
562
                // write pixel data for each line
 
563
                for (int x = 0; x < width; x++)
 
564
                {
 
565
 
 
566
                    // get RGB values for pixel
 
567
                    byte r = (byte)raster.getSample(x, y, 0);
 
568
                    byte g = (byte)raster.getSample(x, y, 1);
 
569
                    byte b = (byte)raster.getSample(x, y, 2);
 
570
 
 
571
                    // write RGB values
 
572
                    writer.Write(b);
 
573
                    writer.Write(g);
 
574
                    writer.Write(r);
 
575
                }
 
576
 
 
577
                // write padding bytes at end of line
 
578
                for (int i = width * 3; i < bytesPerLine; i++)
 
579
                {
 
580
                    writer.Write((byte)0);
 
581
                }
 
582
            }
 
583
        }
 
584
 
 
585
        /// <summary>
 
586
        /// Encodes and writes raster data, together with alpha (transparency) data,
 
587
        /// as a 32-bit bitmap.
 
588
        /// </summary>
 
589
        /// <param name="raster">
 
590
        ///            the source raster data </param>
 
591
        /// <param name="alpha">
 
592
        ///            the source alpha data </param>
 
593
        private void Write32(Raster raster, Raster alpha)
 
594
        {
 
595
            int width = raster.getWidth();
 
596
            int height = raster.getHeight();
 
597
 
 
598
            // write lines
 
599
            for (int y = height - 1; y >= 0; y--)
 
600
            {
 
601
 
 
602
                // write pixel data for each line
 
603
                for (int x = 0; x < width; x++)
 
604
                {
 
605
 
 
606
                    // get RGBA values
 
607
                    byte r = (byte)raster.getSample(x, y, 0);
 
608
                    byte g = (byte)raster.getSample(x, y, 1);
 
609
                    byte b = (byte)raster.getSample(x, y, 2);
 
610
                    byte a = (byte)alpha.getSample(x, y, 0);
 
611
 
 
612
                    // write RGBA values
 
613
                    writer.Write(b);
 
614
                    writer.Write(g);
 
615
                    writer.Write(r);
 
616
                    writer.Write(a);
 
617
                }
 
618
            }
 
619
        }
 
620
 
 
621
        /// <summary>
 
622
        /// Sets a particular bit in a byte.
 
623
        /// </summary>
 
624
        /// <param name="bits">
 
625
        ///            the source byte </param>
 
626
        /// <param name="index">
 
627
        ///            the index of the bit to set </param>
 
628
        /// <param name="bit">
 
629
        ///            the value for the bit, which should be either <tt>0</tt> or
 
630
        ///            <tt>1</tt>. </param>
 
631
        /// <param name="the">
 
632
        ///            resultant byte </param>
 
633
        private byte SetBit(byte bits, int index, int bit)
 
634
        {
 
635
            if (bit == 0)
 
636
            {
 
637
                bits &= (byte)~(1 << (7 - index));
 
638
            }
 
639
            else
 
640
            {
 
641
                bits |= (byte)(1 << (7 - index));
 
642
            }
 
643
            return bits;
 
644
        }
 
645
 
 
646
        /// <summary>
 
647
        /// Sets a particular nibble (4 bits) in a byte.
 
648
        /// </summary>
 
649
        /// <param name="nibbles">
 
650
        ///            the source byte </param>
 
651
        /// <param name="index">
 
652
        ///            the index of the nibble to set </param>
 
653
        /// <param name="the">
 
654
        ///            value for the nibble, which should be in the range
 
655
        ///            <tt>0x0..0xF</tt>. </param>
 
656
        private byte SetNibble(byte nibbles, int index, int nibble)
 
657
        {
 
658
            nibbles |= (byte)(nibble << ((1 - index) * 4));
 
659
 
 
660
            return nibbles;
 
661
        }
 
662
 
 
663
        /// <summary>
 
664
        /// Calculates the size in bytes for a colour map with the specified bit
 
665
        /// count.
 
666
        /// </summary>
 
667
        /// <param name="sBitCount">
 
668
        ///            the bit count, which represents the colour depth </param>
 
669
        /// <returns> the size of the colour map, in bytes if <tt>sBitCount</tt> is
 
670
        ///         less than or equal to 8, otherwise <tt>0</tt> as colour maps are
 
671
        ///         only used for bitmaps with a colour depth of 8 bits or less. </returns>
 
672
        private int GetColorMapSize(short sBitCount)
 
673
        {
 
674
            int ret = 0;
 
675
            if (sBitCount <= 8)
 
676
            {
 
677
                ret = (1 << sBitCount) * 4;
 
678
            }
 
679
            return ret;
 
680
        }
 
681
 
 
682
    }
 
683
}