// Palette indices point to a current palette row (containing 16 indices) and are 4 bits // 2 bits: run length // 2 bits: mode: // 0: color index = 4 bits // run length = run length + 2 // 1: read new color index (4 bits) each iteration // run length = run length + 1 // 2: change paletteRow = 4 bits // // Vertical pixel order private static void DecodeRLEPaletteRowsV(byte[] buffer, int width, int height, int stripX, byte[] source, int sourcePos, bool transparent) { int x = stripX; int y = 0; int code = -1; byte color = 0; int paletteRow = 0; int runlength = 0; LEBitStream sourceStream = new LEBitStream(source, sourcePos); while (x < stripX + 8) { while (y < height) { if (runlength > 0) { if (code >> 2 == 1) { color = (byte)sourceStream.GetBits(4); } runlength--; buffer[y * width + x] = (byte)(paletteRow * 16 + color); y++; continue; } code = sourceStream.GetBits(4); switch (code >> 2) { case 0: color = (byte)sourceStream.GetBits(4); runlength = ((code & 3) + 2); break; case 1: runlength = ((code & 3) + 1); break; case 2: paletteRow = sourceStream.GetBits(4); break; } } y = 0; x++; } }
private static void DecodeMajMinH(byte[] buffer, int width, int height, int stripX, byte[] source, int sourcePos, int indexSize, bool transparent) { int runlength = 0; LEBitStream sourceStream = new LEBitStream(source, sourcePos); byte color = sourceStream.GetByte(); int x = stripX; int y = 0; while (y < height) { while (x < stripX + 8) { buffer[y * width + x] = color; x++; if (runlength > 0) { runlength--; continue; } if (sourceStream.GetBit() == 0) // 0 { } else if (sourceStream.GetBit() == 0) // 10 { color = (byte)(sourceStream.GetBits(indexSize)); } else // 11 { int code = sourceStream.GetBits(3) - 4; if (code != 0) { color = (byte)(color + code); } else { runlength = sourceStream.GetBits(8) - 1; } } } x = stripX; y++; } }
// Predecessor of ZigZag codec // Vertical pixel order private static void DecodeOldZigZagV(byte[] buffer, int width, int height, int stripX, byte[] source, int sourcePos, bool transparent) { int x = stripX; int y = 0; int sub = 1; byte color = source[sourcePos++]; LEBitStream sourceStream = new LEBitStream(source, sourcePos); while (x < stripX + 8) { while (y < height) { buffer[y * width + x] = color; y++; if (sourceStream.GetBit() == 0) // 0 { // do nothing (draw pixel, same color) } else if (sourceStream.GetBit() == 0) // 10 { sub = -sub; color = (byte)(color - sub); } else if (sourceStream.GetBit() == 0) // 110 { color = (byte)(color - sub); } else // 111 { sub = 1; color = (byte)sourceStream.GetBits(8); } } y = 0; x++; } }
private static void DecodeZigzagH(byte[] buffer, int width, int height, int stripX, byte[] source, int sourcePos, int indexSize, bool transparent) { int sub = 1; LEBitStream sourceStream = new LEBitStream(source, sourcePos); byte color = sourceStream.GetByte(); int x = stripX; int y = 0; while (y < height) { while (x < stripX + 8) { buffer[y * width + x] = color; if (sourceStream.GetBit() == 0) // 0 { // Do nothing (draw pixel, same color) } else if (sourceStream.GetBit() == 0) // 10 { color = (byte)(sourceStream.GetBits(indexSize)); sub = 1; } else if (sourceStream.GetBit() == 0) // 110 { color = (byte)(color - sub); } else // 111 { sub = -sub; color = (byte)(color - sub); } x++; } x = stripX; y++; } }