internal DefineBitsLosslessTag(SwfReader r, uint curTagLen, bool hasAlpha) : base(TagType.DefineBitsLossless) { TagLen = curTagLen; HasAlpha = hasAlpha; if (hasAlpha) { tagType = TagType.DefineBitsLossless2; } CharacterId = r.GetUI16(); BitmapFormat = (BitmapFormat)r.GetByte(); this.Width = r.GetUI16(); this.Height = r.GetUI16(); if (BitmapFormat == BitmapFormat.Colormapped8Bit) // 8-bit colormapped image { this.ColorCount = (uint)r.GetByte() + 1; this.isIndexedColors = true; uint colorBytes = hasAlpha ? (uint)4 : (uint)3; uint padWidth = this.Width + (4 - (this.Width % 4)); // temp for debugging uint pos = r.Position; OrgBitmapData = r.GetBytes(curTagLen - 8); r.Position = pos; // end temp uint unzippedSize = (this.ColorCount * colorBytes) + (padWidth * this.Height); byte[] mapData = r.DecompressZLIB(curTagLen - 8, unzippedSize); uint index = 0; this.ColorTable = new RGBA[this.ColorCount]; for (int i = 0; i < this.ColorCount; i++) { if (hasAlpha) { this.ColorTable[i] = new RGBA(mapData[index], mapData[index + 1], mapData[index + 2], mapData[index + 3]); } else { this.ColorTable[i] = new RGBA(mapData[index], mapData[index + 1], mapData[index + 2]); } index += colorBytes; } this.ColorData = new uint[this.Width * this.Height]; index = 0; int offset = (int)(this.ColorCount * colorBytes); for (int i = 0; i < padWidth * this.Height; i++) { if ((i % padWidth) < this.Width) // exclude padding { this.ColorData[index++] = mapData[i + offset]; } } } else if (BitmapFormat == BitmapFormat.RGB15Bit) // RGBx555 { // todo: find a test file for rgb555 uint colorBytes = 2; uint padWidth = this.Width * colorBytes; padWidth += (4 - padWidth) % 4; // temp for debugging uint pos = r.Position; OrgBitmapData = r.GetBytes(curTagLen - 7); r.Position = pos; // end temp uint unzippedSize = (padWidth * this.Height) * colorBytes; byte[] mapData = r.DecompressZLIB(curTagLen - 7, unzippedSize); int index = 0; this.BitmapData = new RGBA[this.Width * this.Height]; for (uint i = 0; i < unzippedSize; i += colorBytes) { if ((i % padWidth) < (this.Width * colorBytes)) // exclude padding { byte b0 = mapData[i]; byte b1 = mapData[i + 1]; byte rd = (byte)((b0 & 0x7C) << 1); byte gr = (byte)(((b0 & 0x03) << 6) | ((b1 & 0xE0) >> 2)); byte bl = (byte)((b1 & 0x1F) << 3); this.BitmapData[index++] = new RGBA(rd, gr, bl); } } } else if (BitmapFormat == BitmapFormat.RGB24Bit) // RGB 24 { // temp for debugging uint pos = r.Position; OrgBitmapData = r.GetBytes(curTagLen - 7); r.Position = pos; // end temp uint colorBytes = 4; // 4 bytes will always be byte aligned uint unzippedSize = (this.Width * this.Height) * colorBytes; byte[] mapData = r.DecompressZLIB(curTagLen - 7, unzippedSize); int index = 0; this.BitmapData = new RGBA[this.Width * this.Height]; for (uint i = 0; i < unzippedSize; i += colorBytes) { if (hasAlpha) { this.BitmapData[index++] = new RGBA(mapData[i + 1], mapData[i + 2], mapData[i + 3], mapData[i]); } else { this.BitmapData[index++] = new RGBA(mapData[i + 1], mapData[i + 2], mapData[i + 3]); } } } }