private Image <Bgra32> DecodeFormat2(IBinaryStream reader) { var textureWidth = _alignedWidth / 4; var textureHeight = _alignedHeight / 4; var data = reader.ReadBytesExact(_alignedWidth * _alignedHeight); var decrypted = new byte[data.Length]; var src = 0; foreach (var i in Range(textureWidth * textureHeight)) { var x = GetX(i, textureWidth, 16); var y = GetY(i, textureWidth, 16); var dst = (x + y * textureWidth) * 16; foreach (var _ in Range(8)) { decrypted[dst + 1] = data[src]; decrypted[dst] = data[src + 1]; dst += 2; src += 2; } } var pixels = Dxt5Codec.Decode(decrypted, _alignedWidth, _alignedHeight); var image = Image.LoadPixelData(pixels, _alignedWidth, _alignedHeight); image.Mutate(x => x.Crop(Width, Height)); return(image); }
private static byte[] PeekBytes(IBinaryStream reader, long pos, int size) { var oldPos = reader.Position; reader.Position = pos; var bytes = reader.ReadBytesExact(size); reader.Position = oldPos; return(bytes); }
private Image <Bgr565> DecodeFormat1(IBinaryStream reader) { var data = reader.ReadBytesExact(_alignedWidth * _alignedHeight * 2); var pixels = new Bgr565[Width * Height]; foreach (var i in Range(_alignedWidth * _alignedHeight)) { var x = GetX(i, _alignedWidth, 2); var y = GetY(i, _alignedWidth, 2); if (x >= Width || y >= Height) { continue; } var src = i * 2; pixels[x + y * Width].PackedValue = checked ((ushort)(data[src] | (data[src + 1] << 8))); } return(Image.LoadPixelData(pixels, Width, Height)); }
private Image <Bgra4444> DecodeFont(IBinaryStream reader) { // from https://github.com/vn-tools/arc_unpacker/issues/54 IsFontAtlas = true; var data = reader.ReadBytesExact(_alignedWidth * _alignedHeight * 2); var encodedWidth = Width; Width *= 4; var encodedHeight = Height; var pixels = new Bgra4444[Width * Height]; foreach (var i in Range(_alignedWidth * _alignedHeight)) { var absX = GetX(i, _alignedWidth, 2); var absY = GetY(i, _alignedWidth, 2); if (absX >= encodedWidth || absY >= encodedHeight) { continue; } var src = i * 2; var blockX = (absX / BlockSize) * BlockSize; var blockY = (absY / BlockSize) * BlockSize; var x = absX % BlockSize; var y = absY % BlockSize; var targetY = blockY + y; var targetBase = blockX * 4 + x + targetY * Width; var target1 = targetBase; var target2 = targetBase + BlockSize; var target3 = targetBase + BlockSize * 2; var target4 = targetBase + BlockSize * 3; pixels[target1].PackedValue = (ushort)(0x0FFFu | ((data[src] >> 4) << 12)); pixels[target2].PackedValue = (ushort)(0x0FFFu | ((data[src] & 0xF) << 12)); pixels[target3].PackedValue = (ushort)(0x0FFFu | ((data[src + 1] >> 4) << 12)); pixels[target4].PackedValue = (ushort)(0x0FFFu | ((data[src + 1] & 0xF) << 12)); } return(Image.LoadPixelData(pixels, Width, Height)); }
private static Byte[] ReadUtfPacket(IBinaryStream reader) { var unknown = reader.ReadUInt32LE(); // 0x000000FF if (unknown != 0x00000FFU) { Console.WriteLine($"Unknown u32 {unknown} != 0x000000FF"); } var size = reader.ReadInt64LE(); if (size > int.MaxValue) { throw new InvalidDataException($"Too large UTF size {size}"); } var utf = reader.ReadBytesExact((int)size); if (!utf.Take(4).SequenceEqual(UtfTag)) { DecryptInPlace(utf); } return(utf); }
private Image <Bgra32> DecodeFormat0(IBinaryStream reader) { var data = reader.ReadBytesExact(_alignedWidth * _alignedHeight * 4); var pixels = new Bgra32[Width * Height]; foreach (var i in Range(_alignedWidth * _alignedHeight)) { var x = GetX(i, _alignedWidth, 4); var y = GetY(i, _alignedWidth, 4); if (x >= Width || y >= Height) { continue; } var src = i * 4; pixels[x + y * Width] = new Bgra32( b: data[src + 3], g: data[src + 2], r: data[src + 1], a: data[src] ); } return(Image.LoadPixelData(pixels, Width, Height)); }
protected override void ReadArgs(IBinaryStream reader) { Args = reader.ReadBytesExact(Args.Length); }