Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- private Bitmap getIMG_ETC1(CLIM bclim)
- {
- Bitmap img = new Bitmap(Math.Max(nlpo2(bclim.Width), 16), Math.Max(nlpo2(bclim.Height), 16));
- string dllpath = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetEntryAssembly().Location).Replace('\\','/') + "/ETC1.dll";
- if (!File.Exists(dllpath)) File.WriteAllBytes(dllpath, Properties.Resources.ETC1);
- try
- {
- /*
- * Much of this code is taken/modified from Tharsis: http://jul.rustedlogic.net/thread.php?pid=436556#436556 Thank you to Tharsis's creator, xdaniel.
- */
- /* Get compressed data & handle to it */
- byte[] textureData = bclim.Data;
- //textureData = switchEndianness(textureData, 0x10);
- ushort[] input = new ushort[textureData.Length / sizeof(ushort)];
- Buffer.BlockCopy(textureData, 0, input, 0, textureData.Length);
- GCHandle pInput = GCHandle.Alloc(input, GCHandleType.Pinned);
- /* Marshal data around, invoke ETC1.dll for conversion, etc */
- UInt32 size1 = 0, size2 = 0;
- UInt16 wd = (ushort)img.Width, ht = (ushort)img.Height;
- ConvertETC1(IntPtr.Zero, ref size1, IntPtr.Zero, ref size2, wd, ht, bclim.FileFormat == 0xB); //true = etc1a4, false = etc1
- System.Diagnostics.Debug.WriteLine(size1);
- uint[] output = new uint[size1];
- GCHandle pOutput = GCHandle.Alloc(output, GCHandleType.Pinned);
- ConvertETC1(pOutput.AddrOfPinnedObject(), ref size1, pInput.AddrOfPinnedObject(), ref size2, wd, ht, bclim.FileFormat == 0xB);
- pOutput.Free();
- pInput.Free();
- /* Unscramble if needed // could probably be done in ETC1.dll, it's probably pretty damn ugly, but whatever... */
- /* Non-square code blocks could need some cleanup, verification, etc. as well... */
- uint[] finalized = new uint[output.Length];
- //Act if it's square because BCLIM swizzling is stupid
- Buffer.BlockCopy(output, 0, finalized, 0, finalized.Length);
- byte[] tmp = new byte[finalized.Length];
- Buffer.BlockCopy(finalized, 0, tmp, 0, tmp.Length);
- int h = img.Height;
- int w = img.Width;
- byte[] imgData = tmp;
- System.Diagnostics.Debug.WriteLine("COPIED IMAGE DATA AND SHIT");
- for (int i = 0; i < img.Width; i++)
- {
- for (int j = 0; j < img.Height; j++)
- {
- int k = (j + i * img.Height) * 4;
- img.SetPixel(i, j, Color.FromArgb(imgData[k + 3], imgData[k], imgData[k + 1], imgData[k + 2]));
- }
- }
- //image is 13 instead of 12
- // 24 34
- img.RotateFlip(RotateFlipType.Rotate90FlipX);
- if (wd > ht)
- {
- //image is now in appropriate order, but the swizzling done been fucked up. Let's fix that.
- Bitmap img2 = new Bitmap(Math.Max(nlpo2(bclim.Width), 16), Math.Max(nlpo2(bclim.Height), 16));
- for (int y = 0; y < Math.Max(nlpo2(bclim.Width), 16); y += 8)
- {
- for (int x = 0; x < Math.Max(nlpo2(bclim.Height), 16); x++)
- {
- for (int j = 0; j < 8; j++) //treat every 8 vertical pixels as 1 pixel for purposes of calculation, add to offset later.
- {
- int x1 = (x + ((y / 8) * h)) % img2.Width; //reshift x
- int y1 = ((x + ((y / 8) * h)) / img2.Width) * 8; //reshift y
- img2.SetPixel(x1, y1 + j, img.GetPixel(x, y + j)); //reswizzle
- }
- }
- }
- return img2;
- }
- else if (ht > wd)
- {
- //image is now in appropriate order, but the swizzling done been fucked up. Let's fix that.
- Bitmap img2 = new Bitmap(Math.Max(nlpo2(bclim.Width), 16), Math.Max(nlpo2(bclim.Height), 16));
- for (int y = 0; y < Math.Max(nlpo2(bclim.Width), 16); y += 8)
- {
- for (int x = 0; x < Math.Max(nlpo2(bclim.Height), 16); x++)
- {
- for (int j = 0; j < 8; j++) //treat every 8 vertical pixels as 1 pixel for purposes of calculation, add to offset later.
- {
- int x1 = x%img2.Width; //reshift x
- int y1 = ((x + ((y / 8) * h)) / img2.Width) * 8; //reshift y
- img2.SetPixel(x1, y1 + j, img.GetPixel(x, y + j)); //reswizzle
- }
- }
- }
- return img2;
- }
- }
- catch (System.IndexOutOfRangeException)
- {
- //
- }
- catch (System.AccessViolationException)
- {
- //
- }
- return img;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement