// This function is used to compress the image using the LZW algorithm public static byte[] Compress(AccessibleBitmap source) { // Add first 255 standard values to LZWDictionary in LZWCompressor.cs string[] LZWDictionary = new string[256]; for (int i = 0; i < 256; i++) { LZWDictionary[i] = ((char)i).ToString(); } List <string> dictionary = new List <string>(LZWDictionary); // Clone dictionary of all bytes Queue <byte> bytes = new Queue <byte>(source.GetRawPixelBytes()); // Get all bytes from the source image BitStreamFIFO bs = new BitStreamFIFO(); // Create bitstream for output int maxDictSize = (int)Math.Pow(2, maxBitCount); // Get maximum dictionary size string encodingString = ((char)bytes.Dequeue()).ToString(); // Create string to add encoding to while (bytes.Count > 0) { // Clear dict if full if (dictionary.Count >= maxDictSize) { dictionary = new List <string>(LZWDictionary); } char b = (char)bytes.Dequeue(); if (dictionary.Contains(encodingString + b)) { encodingString += b; } else { bs.Write(dictionary.FindIndex(x => x.StartsWith(encodingString)), maxBitCount); dictionary.Add(encodingString + b); encodingString = b.ToString(); } } // Write remaining byte to bitstream bs.Write(dictionary.FindIndex(x => x.StartsWith(encodingString)), maxBitCount); // Return the bitstream as byte array return(bs.ToByteArray()); }
public static byte[] CompressVertical(AccessibleBitmap source) { byte[] lastpixel = null; // Create variable to store the last pixel int colorCounter = 1; // Create counter for current color BitStreamFIFO bs = new BitStreamFIFO(); // Create new bitstream for all the bits int maxCount = 0; // Create variable to store the max bitcount Queue<PixelArray> output = new Queue<PixelArray>(); // Create list to store all the pixelvalues in // Write one bit to the bitstream, so the decompressor knows to decompress vertically bs.Write(true); // Iterate through every vertical row for (int x = 0; x < source.width; x++) { // Iterate through every pixel in the vertical row for (int y = 0; y < source.height; y++) { // Check if the variable lastpixel is empty if (lastpixel == null) { // If lastpixel is empty, set last pixel to the first pixel lastpixel = source.GetPixel(x, y); } else { // If lastpixel isn't empty, compare last pixel with new pixel if (lastpixel.SequenceEqual(source.GetPixel(x, y))) { // Pixels matched, so increase the counter value colorCounter++; } else { // If the pixels don't match, add the counter with the last pixel to the output queue output.Enqueue(new PixelArray(colorCounter, lastpixel)); // Check if the new countervalue is higher then the last one, if so set maxBitCount to that if (colorCounter > maxCount) maxCount = colorCounter; // Reset the colorCounter and set the last pixel to the new pixel colorCounter = 1; lastpixel = source.GetPixel(x, y); } } } } // Add the remaining pixel(s) to the bitstream output.Enqueue(new PixelArray(colorCounter, lastpixel)); // Check if the new countervalue is higher then the last one, if so set maxBitCount to that if (colorCounter > maxCount) maxCount = colorCounter; // Write the maxCount to the bitstream bs.Write((byte)Math.Ceiling(Math.Log(maxCount, 2))); // Add all the pixels from the queue to the bitstream while (output.Count > 0) { PixelArray pixel = output.Dequeue(); bs.Write(pixel.Count, (int)Math.Ceiling(Math.Log(maxCount, 2))); bs.Write(pixel.Pixel); } // Return the bitsream as a byte[] return bs.ToByteArray(); }