Esempio n. 1
0
        public static ImageData Load(Stream s)
        {
            ImageData    img;
            BinaryReader br    = new BinaryReader(s);
            var          magic = br.ReadUInt32();

            s.Position = 0;
            if (magic == 0xE0FFD8FF)
            {
                System.Drawing.Bitmap image = new System.Drawing.Bitmap(s);
                img = FromBitmap(image);
            }
            else if (magic == 0x20534444)
            {
                IImage image = Dds.Create(s);
                img = FromPfimImg(image);
            }
            //tga image
            else
            {
                IImage image = Targa.Create(s);
                img = FromPfimImg(image);
            }
            return(img);
        }
Esempio n. 2
0
 public int Pfim()
 {
     using (var image = Dds.Create(data, _pfimConfig))
     {
         return(image.BytesPerPixel);
     }
 }
Esempio n. 3
0
        public Texture2D GetTexture(string textureName)
        {
            if (string.IsNullOrEmpty(textureName))
            {
                return(null);
            }

            Texture2D texture;

            if (!Textures.TryGetValue(textureName, out texture))
            {
                Dds textureData = assetManager.LoadPackAsset <Dds>(textureName);

                if (textureData == null)
                {
                    Debug.LogErrorFormat("Could not load texture \"{0}\"", textureName);
                    Textures.Add(textureName, null);
                    return(null);
                }

                texture      = new Texture2D(textureData.Width, textureData.Height, textureData.TextureFormat, true);
                texture.name = textureName;
                texture.LoadRawTextureData(textureData.TextureData.Data);
                texture.Apply(true, true);

                assetManager.Dispose(textureData);

                Textures.Add(textureName, texture);
            }

            return(texture);
        }
Esempio n. 4
0
        static ImageSharp.Image ISImageFromDDS(Dds dds)
        {
            var isi = new ImageSharp.Image(dds.Width, dds.Height);

            isi.SetPixels(dds.Width, dds.Height, DataToColors(dds.Data, dds.BytesPerPixel));
            return(isi);
        }
Esempio n. 5
0
        /// <summary>
        /// Parses any DXT texture from raw bytes including header using Pfim.
        /// </summary>
        /// <param name="bytes"></param>
        /// <param name="mipmap">Does the texture contain mipmap data</param>
        /// <returns></returns>
        private static Texture2D LoadTexturePfim(byte[] bytes, bool mipmap)
        {
            IImage imageData = Dds.Create(bytes, new PfimConfig());

            imageData.Decompress();

            ImageFormat frmt = imageData.Format;

            TextureFormat texFrmt;

            switch (imageData.Format)
            {
            case ImageFormat.Rgb24:
                texFrmt = TextureFormat.RGB24;
                break;

            case ImageFormat.Rgba32:
                texFrmt = TextureFormat.RGBA32;
                break;

            default:
                throw new Exception($"Unknown raw image format {frmt}");
            }

            return(LoadTextureFromBytes(imageData.Data, imageData.Width, imageData.Height, texFrmt, mipmap));
        }
Esempio n. 6
0
        public DDSImage(Stream stream)
        {
            if (stream == null)
            {
                throw new Exception($"DDSImage ctor: {nameof(stream)} is null");
            }

            _ddsImageFile = Dds.Create(stream, new PfimConfig(decompress: true));
        }
Esempio n. 7
0
        public void TestDdsCompression(string path)
        {
            var data   = File.ReadAllBytes(Path.Combine("data", path));
            var image  = Dds.Create(data, new PfimConfig());
            var image2 = Dds.Create(data, new PfimConfig(decompress: false));

            Assert.False(image.Compressed);
            Assert.True(image2.Compressed);
            Assert.NotEqual(image.Data, image2.Data);
            Assert.Equal(image.Format, image2.Format);
            image2.Decompress();
            Assert.Equal(image.Data, image2.Data);
        }
Esempio n. 8
0
        public void TestMipMapProperties(string allPath, ulong hash)
        {
            var path   = Path.Combine("data", Path.Combine(allPath.Split('\\')));
            var data   = File.ReadAllBytes(path);
            var image  = Pfim.FromFile(path);
            var image2 = Dds.Create(data, new PfimConfig());

            Assert.Equal(image.MipMaps, image2.MipMaps);

            var mipMapLengths = image.MipMaps.Sum(x => x.DataLen);
            var hash1         = Hash64(image.Data, image.DataLen + mipMapLengths);

            Assert.Equal(hash1, Hash64(image2.Data, image2.DataLen + mipMapLengths));
            Assert.Equal(hash, hash1);
        }
Esempio n. 9
0
        public DDSImage(byte[] ddsImage)
        {
            if (ddsImage == null)
            {
                return;
            }

            if (ddsImage.Length == 0)
            {
                return;
            }

            _image = Dds.Create(ddsImage, new PfimConfig());
            Parse();
        }
Esempio n. 10
0
        public DDSImage(System.IO.Stream ddsImage)
        {
            if (ddsImage == null)
            {
                return;
            }

            if (!ddsImage.CanRead)
            {
                return;
            }

            _image = Dds.Create(ddsImage, new PfimConfig());
            Parse();
        }
Esempio n. 11
0
        private bool TryLoadDds(Stream s, out Texture2D result)
        {
            try
            {
                s.Seek(0, SeekOrigin.Begin);
                var img = Dds.Create(s, true);

                Texture2D tex = new Texture2D(Editor.graphics, img.Width, img.Height, false, SurfaceFormat.Color);
                if (img.Format == ImageFormat.Rgb24)
                {
                    // convert from 24bit to 32...
                    var convertedData = new byte[img.Width * img.Height * 4];
                    using (var br = new BinaryReader(new MemoryStream(img.Data)))
                        using (var bw = new BinaryWriter(new MemoryStream(convertedData)))
                        {
                            for (int i = 0; i < convertedData.Length; i += 4)
                            {
                                byte r = br.ReadByte();
                                byte g = br.ReadByte();
                                byte b = br.ReadByte();

                                bw.Write(b);
                                bw.Write(g);
                                bw.Write(r);
                                bw.Write((byte)255);
                            }
                        }

                    tex.SetData <byte>(convertedData);
                }
                else if (img.Format == ImageFormat.Rgba32)
                {
                    tex.SetData <byte>(img.Data);
                }
                else
                {
                    throw new InvalidOperationException("unsupported format: " + img.Format);
                }

                result = tex;
            }
            catch (Exception e) {
                Log.WriteLine("TryLoadDds : " + e.Message);
                result = null;
            }
            return(result != null);
        }
Esempio n. 12
0
            public DdsFrame(Stream stream)
            {
                using (var dds = Dds.Create(stream, new PfimConfig()))
                {
                    Size = new Size(dds.Width, dds.Height);
                    Data = dds.Data;
                    switch (dds.Format)
                    {
                    // SpriteFrameType refers to the channel byte order, which is reversed from the little-endian bit order
                    case ImageFormat.Rgba32: Type = SpriteFrameType.Bgra32; break;

                    case ImageFormat.Rgb24: Type = SpriteFrameType.Bgr24; break;

                    default: throw new InvalidDataException($"Unhandled ImageFormat {dds.Format}");
                    }
                }
            }
Esempio n. 13
0
        public static void LoadTextures()
        {
            dummyTextures = CreateNudDummyTextures();

            NudMatSphereDrawing.LoadMaterialSphereTextures();

            // Helpful textures.
            uvTestPattern = new Texture2D();
            uvTestPattern.LoadImageData(Properties.Resources.UVPattern);
            uvTestPattern.TextureWrapS = TextureWrapMode.Repeat;
            uvTestPattern.TextureWrapT = TextureWrapMode.Repeat;

            // TODO: Simplify this conversion.
            Dds specularSdr = new Dds(new FileData(Properties.Resources.specularSDR));

            specularPbr = NUT.CreateTextureCubeMap(specularSdr.ToNutTexture());

            Dds diffuseSdr = new Dds(new FileData(Properties.Resources.diffuseSDR));

            diffusePbr = NUT.CreateTextureCubeMap(diffuseSdr.ToNutTexture());
            // Don't use mipmaps.
            diffusePbr.MinFilter = TextureMinFilter.Linear;
            diffusePbr.MagFilter = TextureMagFilter.Linear;

            boneWeightGradient = new Texture2D();
            boneWeightGradient.LoadImageData(Properties.Resources.boneWeightGradient);

            boneWeightGradient2 = new Texture2D();
            boneWeightGradient2.LoadImageData(Properties.Resources.boneWeightGradient2);

            defaultTex = new Texture2D();
            defaultTex.LoadImageData(Resources.Resources.DefaultTexture);

            try
            {
                floorTexture = new Texture2D();
                floorTexture.LoadImageData(new Bitmap(Runtime.floorTexFilePath));

                backgroundTexture = new Texture2D();
                backgroundTexture.LoadImageData(new Bitmap(Runtime.backgroundTexFilePath));
            }
            catch (Exception)
            {
                // File paths are incorrect or never set.
            }
        }
Esempio n. 14
0
        private void button1_Click(object sender, EventArgs e)
        {
            if (CBFormat.SelectedItem == null)
            {
                CBFormat.SelectedItem = TPL_TextureFormat.CMP;
            }
            if (SelectedTexture != null)
            {
                using (OpenFileDialog ofd = new OpenFileDialog())
                {
                    if ((TPL_TextureFormat)CBFormat.SelectedItem == TPL_TextureFormat.CMP)
                    {
                        ofd.Filter = "DDS|*.dds";
                    }
                    else
                    {
                        ofd.Filter = "PNG|*.png";
                    }

                    if (ofd.ShowDialog() == DialogResult.OK)
                    {
                        Selected = SelectedTexture.Texture;
                        if ((TPL_TextureFormat)CBFormat.SelectedItem == TPL_TextureFormat.CMP)
                        {
                            Dds d = new Dds(new FileData(ofd.FileName));
                            if (d.header.ddspf.fourCc != 0x31545844)
                            {
                                MessageBox.Show("Error Importing Texture:\nOnly DXT1 Files are supported currently");
                                return;
                            }
                            Selected.SetFromDXT1(new FileData(d.bdata).GetSection(0, (int)(d.header.width * d.header.height / 2)), (int)d.header.width, (int)d.header.height);
                        }
                        else
                        {
                            Bitmap b = new Bitmap(ofd.FileName);
                            Selected.SetFromBitmap(b, (MeleeLib.TPL_TextureFormat)CBFormat.SelectedItem, (MeleeLib.TPL_PaletteFormat)CBPalette.SelectedItem);
                            b.Dispose();
                        }
                        DialogResult = DialogResult.OK;
                        CloseForm();
                        Close();
                    }
                }
            }
        }
Esempio n. 15
0
        /// <summary>
        /// Tights the data.
        /// </summary>
        /// <param name="image">The image.</param>
        /// <returns>System.Byte[].</returns>
        public byte[] TightData(Dds image)
        {
            // Code from this PR (MIT licensed): https://github.com/hguy/dds-reader/pull/1/commits/ba751f0af4fc1c725842dc86d12ecf69f0c70108
            var tightStride = image.Width * image.BitsPerPixel / 8;

            if (image.Stride == tightStride)
            {
                return(image.Data);
            }

            byte[] newData = new byte[image.Height * tightStride];
            for (int i = 0; i < image.Height; i++)
            {
                Buffer.BlockCopy(image.Data, i * image.Stride, newData, i * tightStride, tightStride);
            }

            return(newData);
        }
Esempio n. 16
0
        private void LoadImage(Stream stream)
        {
            if (Path.GetExtension(this.Filename).ToLower() == ".dds")
            {
                PixelFormat format;

                Dds image = (Dds)Pfim.Pfim.FromStream(stream);

                switch (image.Format)
                {
                case Pfim.ImageFormat.Rgb24:
                    format = PixelFormat.Format24bppRgb;
                    break;

                case Pfim.ImageFormat.Rgba32:
                    format = PixelFormat.Format32bppArgb;
                    break;

                default:
                    throw new NotImplementedException("Unsupported Pfim image format: " + image.Format.ToString());
                }

                this.DDSFormat = image.Header.PixelFormat.FourCC.ToString();

                var handle = GCHandle.Alloc(image.Data, GCHandleType.Pinned);
                try
                {
                    var data   = Marshal.UnsafeAddrOfPinnedArrayElement(image.Data, 0);
                    var bitmap = new Bitmap(image.Width, image.Height, image.Stride, format, data);
                    this.ImageSize      = new Size(bitmap.Width, bitmap.Height);
                    this.ImageBox.Image = bitmap;
                }
                finally
                {
                    handle.Free();
                }
            }
            else
            {
                var bitmap = new Bitmap(stream);
                this.ImageSize      = new Size(bitmap.Width, bitmap.Height);
                this.ImageBox.Image = bitmap;
            }
        }
Esempio n. 17
0
        public void TestDdsMipMap1()
        {
            var image        = Pfim.FromFile(Path.Combine("data", "wose_BC1_UNORM.DDS"));
            var expectedMips = new[]
            {
                new MipMapOffset(36, 36, 144, 20736, 5184),
                new MipMapOffset(18, 18, 80, 25920, 1600),
                new MipMapOffset(9, 9, 48, 27520, 576),
                new MipMapOffset(4, 4, 16, 28096, 64),
                new MipMapOffset(2, 2, 16, 28160, 64),
                new MipMapOffset(1, 1, 16, 28224, 64)
            };

            Assert.Equal(expectedMips, image.MipMaps);
            Assert.Equal(28224 + 64, image.Data.Length);

            image = Dds.Create(File.ReadAllBytes(Path.Combine("data", "wose_BC1_UNORM.DDS")), new PfimConfig());
            Assert.Equal(expectedMips, image.MipMaps);
            Assert.Equal(28224 + 64, image.Data.Length);
        }
Esempio n. 18
0
        public void TestDdsMipMap1()
        {
            var image        = Pfim.FromFile(Path.Combine("data", "wose_BC1_UNORM.DDS"));
            var expectedMips = new[]
            {
                new MipMapOffset(36, 36, 108, 15552, 3888),
                new MipMapOffset(18, 18, 60, 19440, 1200),
                new MipMapOffset(9, 9, 36, 20640, 432),
                new MipMapOffset(4, 4, 12, 21072, 48),
                new MipMapOffset(2, 2, 12, 21120, 48),
                new MipMapOffset(1, 1, 12, 21168, 48)
            };

            Assert.Equal(expectedMips, image.MipMaps);
            Assert.Equal(21168 + 48, image.Data.Length);

            image = Dds.Create(File.ReadAllBytes(Path.Combine("data", "wose_BC1_UNORM.DDS")), new PfimConfig());
            Assert.Equal(expectedMips, image.MipMaps);
            Assert.Equal(21168 + 48, image.Data.Length);
        }
        public Material GetMaterial(CnkLOD chunkData)
        {
            Texture2D[] diffuseTextures = new Texture2D[chunkData.Textures.Count];
            Texture2D[] specTextures    = new Texture2D[chunkData.Textures.Count];

            for (int i = 0; i < chunkData.Textures.Count; i++)
            {
                CnkLOD.Texture texture = chunkData.Textures[i];

                Dds diffuse = texture.ColorNXMap;
                Dds spec    = texture.SpecNyMap;

                Texture2D diffuseTex = new Texture2D(diffuse.Width, diffuse.Height, diffuse.TextureFormat, false);
                Texture2D specTex    = new Texture2D(spec.Width, spec.Height, spec.TextureFormat, false);

                diffuseTex.LoadRawTextureData(diffuse.TextureData.Data);
                specTex.LoadRawTextureData(spec.TextureData.Data);

                diffuseTextures[i] = diffuseTex;
                specTextures[i]    = specTex;
            }

            Texture2D materialDiffuse = new Texture2D(1024, 1024);

            materialDiffuse.PackTextures(diffuseTextures, 0, 2048, true);
            materialDiffuse.name = chunkData.Name + " Diffuse";

            Texture2D materialSpec = new Texture2D(1024, 1024);

            materialSpec.PackTextures(specTextures, 0, 2048, true);
            materialSpec.name = chunkData.Name + " Specular";

            Material material = new Material(source);

            material.SetTexture("_MainTex", materialDiffuse);
            material.SetTextureScale("_MainTex", new Vector2(1, -1));
            material.SetTexture("_PackedSpecular", materialSpec);
            material.SetTextureScale("_PackedSpecular", new Vector2(1, -1));

            return(material);
        }
Esempio n. 20
0
        public unsafe static byte[] MakeMipsImage(byte[] data)
        {
            var dds   = Dds.Create(new MemoryStream(data));
            var tlen  = dds.Width * dds.Height * 2 * 4;
            var mips  = SiliconStudio.Xenko.Graphics.Image.CountMips(dds.Width, dds.Height);
            var adata = Marshal.AllocHGlobal(tlen);

            var isi = ISImageFromDDS(dds);

            var off = 0;

            for (var i = 0; i < mips; ++i)
            {
                off += MakeMipLevel(isi, (uint *)adata, i, off, dds.BytesPerPixel == 4);
            }

            using (var ms = new MemoryStream()) {
                SiliconStudio.Xenko.Graphics.Image.New2D(dds.Width, dds.Height, mips, PixelFormat.R8G8B8A8_UNorm, 1, adata).Save(ms, ImageFileType.Xenko);
                ms.Flush();
                return(ms.GetBuffer());
            }
        }
Esempio n. 21
0
                static async Task <MemoryStream> getDDS(Stream stream)
                {
                    MemoryStream ms = null;

                    using var pfimImage = Dds.Create(stream, new PfimConfig());
                    if (pfimImage.Compressed)
                    {
                        pfimImage.Decompress();
                    }
                    if (pfimImage.Format == ImageFormat.Rgba32)
                    {
                        ms = new MemoryStream();
                        using var image = Image.LoadPixelData <Bgra32>(tightData(pfimImage), pfimImage.Width, pfimImage.Height);
                        await image.SaveAsPngAsync(ms);
                    }
                    else if (pfimImage.Format == ImageFormat.Rgb24)
                    {
                        ms = new MemoryStream();
                        using var image = Image.LoadPixelData <Bgr24>(tightData(pfimImage), pfimImage.Width, pfimImage.Height);
                        await image.SaveAsPngAsync(ms);
                    }
                    return(ms);
                }
Esempio n. 22
0
                static async Task <MemoryStream> getDDS(Stream stream)
                {
                    if (stream.CanSeek)
                    {
                        stream.Seek(0, SeekOrigin.Begin);
                    }
                    var          exceptions = new List <Exception>();
                    MemoryStream ms         = null;

                    try
                    {
                        ms = new MemoryStream();
                        var file    = DdsFile.Load(stream);
                        var decoder = new BcDecoder();
                        var image   = decoder.Decode(file);
                        await image.SaveAsPngAsync(ms);
                    }
                    catch (Exception ex)
                    {
                        if (ms != null)
                        {
                            ms.Close();
                            await ms.DisposeAsync();
                        }
                        ms = null;
                        exceptions.Add(ex);
                    }
                    // fallback
                    if (ms == null)
                    {
                        if (stream.CanSeek)
                        {
                            stream.Seek(0, SeekOrigin.Begin);
                        }
                        try
                        {
                            using var pfimImage = Dds.Create(stream, new PfimConfig());
                            if (pfimImage.Compressed)
                            {
                                pfimImage.Decompress();
                            }
                            if (pfimImage.Format == ImageFormat.Rgba32)
                            {
                                ms = new MemoryStream();
                                using var image = Image.LoadPixelData <Bgra32>(tightData(pfimImage), pfimImage.Width, pfimImage.Height);
                                await image.SaveAsPngAsync(ms);
                            }
                            else if (pfimImage.Format == ImageFormat.Rgb24)
                            {
                                ms = new MemoryStream();
                                using var image = Image.LoadPixelData <Bgr24>(tightData(pfimImage), pfimImage.Width, pfimImage.Height);
                                await image.SaveAsPngAsync(ms);
                            }
                        }
                        catch (Exception ex)
                        {
                            if (ms != null)
                            {
                                ms.Close();
                                await ms.DisposeAsync();
                            }
                            ms = null;
                            exceptions.Add(ex);
                        }
                    }
                    // Fallback can result in memory stream being empty so throw aggregate exception only if both attempts failed
                    if (ms == null && exceptions.Count == 2)
                    {
                        throw new AggregateException(exceptions);
                    }
                    return(ms);
                }
Esempio n. 23
0
        /// <summary>
        /// Creates valid DDS Header for entry's texture.
        /// </summary>
        /// <param name="entry">Valid BA2TextureFileEntry instance.</param>
        /// <returns>
        /// Valid DDS Header.
        /// </returns>
        /// <exception cref="System.NotSupportedException">Entry DDS format is not supported.</exception>
        private DdsHeader CreateDdsHeaderForEntry(BA2TextureFileEntry entry)
        {
            var        header = new DdsHeader();
            DxgiFormat format = (DxgiFormat)entry.Format;

            header.dwSize        = 124; // sizeof(DDS_HEADER)
            header.dwHeaderFlags = Dds.DDS_HEADER_FLAGS_TEXTURE |
                                   Dds.DDS_HEADER_FLAGS_LINEARSIZE | Dds.DDS_HEADER_FLAGS_MIPMAP;
            header.dwHeight       = (uint)entry.TextureHeight;
            header.dwWidth        = (uint)entry.TextureWidth;
            header.dwMipMapCount  = (uint)entry.NumberOfMipmaps;
            header.ddspf.dwSize   = 32; // sizeof(DDS_PIXELFORMAT);
            header.dwSurfaceFlags = Dds.DDS_SURFACE_FLAGS_TEXTURE | Dds.DDS_SURFACE_FLAGS_MIPMAP;

            switch (format)
            {
            case DxgiFormat.BC1_UNORM:
                header.ddspf.dwFlags       = Dds.DDS_FOURCC;
                header.ddspf.dwFourCC      = (uint)Dds.MakeFourCC('D', 'X', 'T', '1');
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight / 2u;
                break;

            case DxgiFormat.BC2_UNORM:
                header.ddspf.dwFlags       = Dds.DDS_FOURCC;
                header.ddspf.dwFourCC      = (uint)Dds.MakeFourCC('D', 'X', 'T', '3');
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight;
                break;

            case DxgiFormat.BC3_UNORM:
                header.ddspf.dwFlags       = Dds.DDS_FOURCC;
                header.ddspf.dwFourCC      = (uint)Dds.MakeFourCC('D', 'X', 'T', '5');
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight;
                break;

            case DxgiFormat.BC5_UNORM:
                header.ddspf.dwFlags = Dds.DDS_FOURCC;
                // ATI2
                header.ddspf.dwFourCC      = (uint)Dds.MakeFourCC('D', 'X', 'T', '5');
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight;
                break;

            case DxgiFormat.BC7_UNORM:
                header.ddspf.dwFlags       = Dds.DDS_FOURCC;
                header.ddspf.dwFourCC      = (uint)Dds.MakeFourCC('B', 'C', '7', '\0');
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight;
                break;

            case DxgiFormat.B8G8R8A8_UNORM:
                header.ddspf.dwFlags       = Dds.DDS_RGBA;
                header.ddspf.dwRGBBitCount = 32;
                header.ddspf.dwRBitMask    = 0x00FF0000;
                header.ddspf.dwGBitMask    = 0x0000FF00;
                header.ddspf.dwBBitMask    = 0x000000FF;
                header.ddspf.dwABitMask    = 0xFF000000;
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight * 4u;
                break;

            case DxgiFormat.R8_UNORM:
                header.ddspf.dwFlags       = Dds.DDS_RGB;
                header.ddspf.dwRGBBitCount = 8;
                header.ddspf.dwRBitMask    = 0xFF;
                header.dwPitchOrLinearSize = (uint)entry.TextureWidth * (uint)entry.TextureHeight;
                break;

            default:
                throw new NotSupportedException($"DDS format \"{format.ToString()}\" is not supported.");
            }

            return(header);
        }
Esempio n. 24
0
        /// <summary>
        /// Gets the DDS.
        /// </summary>
        /// <param name="stream">The stream.</param>
        /// <returns>MemoryStream.</returns>
        /// <exception cref="System.AggregateException"></exception>
        private async Task <MemoryStream> GetDDS(Stream stream)
        {
            if (stream.CanSeek)
            {
                stream.Seek(0, SeekOrigin.Begin);
            }
            var          exceptions = new List <Exception>();
            MemoryStream ms         = null;

            // Default provider (SixLabors.Textures)
            try
            {
                var image = await ddsDecoder.DecodeStreamToImageAsync(stream);

                ms = new MemoryStream();
                await image.SaveAsPngAsync(ms);
            }
            catch (Exception ex)
            {
                if (ms != null)
                {
                    ms.Close();
                    await ms.DisposeAsync();
                }
                ms = null;
                exceptions.Add(ex);
            }
            // fallback #1 (BCnEncoder.NET)
            if (ms == null)
            {
                if (stream.CanSeek)
                {
                    stream.Seek(0, SeekOrigin.Begin);
                }
                try
                {
                    var file  = DdsFile.Load(stream);
                    var image = await ddsDecoder.DecodeToImageAsync(file);

                    ms = new MemoryStream();
                    await image.SaveAsPngAsync(ms);
                }
                catch (Exception ex)
                {
                    if (ms != null)
                    {
                        ms.Close();
                        await ms.DisposeAsync();
                    }
                    ms = null;
                    exceptions.Add(ex);
                }
            }
            // fallback #2 (pfim)
            if (ms == null)
            {
                if (stream.CanSeek)
                {
                    stream.Seek(0, SeekOrigin.Begin);
                }
                try
                {
                    using var pfimImage = Dds.Create(stream, new PfimConfig());
                    if (pfimImage.Compressed)
                    {
                        pfimImage.Decompress();
                    }
                    if (pfimImage.Format == ImageFormat.Rgba32)
                    {
                        ms = new MemoryStream();
                        using var image = Image.LoadPixelData <Bgra32>(ddsDecoder.TightData(pfimImage), pfimImage.Width, pfimImage.Height);
                        await image.SaveAsPngAsync(ms);
                    }
                    else if (pfimImage.Format == ImageFormat.Rgb24)
                    {
                        ms = new MemoryStream();
                        using var image = Image.LoadPixelData <Bgr24>(ddsDecoder.TightData(pfimImage), pfimImage.Width, pfimImage.Height);
                        await image.SaveAsPngAsync(ms);
                    }
                }
                catch (Exception ex)
                {
                    if (ms != null)
                    {
                        ms.Close();
                        await ms.DisposeAsync();
                    }
                    ms = null;
                    exceptions.Add(ex);
                }
            }
            // Fallback can result in memory stream being empty so throw aggregate exception only if all attempts failed
            if (ms == null && exceptions.Count == 3)
            {
                throw new AggregateException(exceptions);
            }
            return(ms);
        }
Esempio n. 25
0
        public override void Read(BinaryReader br)
        {
            long offset = br.BaseStream.Position;

            br.BaseStream.Seek(4, SeekOrigin.Current); //"GBIX"
            GBIXSize    = br.ReadUInt32();
            GBIXContent = br.ReadBytes((int)GBIXSize);
            br.BaseStream.Seek(4, SeekOrigin.Current); //"PVRT"

            Size   = br.ReadUInt32();
            Type   = (PVRType)br.ReadByte();
            Format = (PVRFormat)br.ReadByte();
            br.BaseStream.Seek(2, SeekOrigin.Current);
            Width  = br.ReadUInt16();
            Height = br.ReadUInt16();

            if (Format == PVRFormat.VQ)
            {
                var palette = new Color4[1024];
                for (int i = 0; i < palette.Length; i++)
                {
                    palette[i] = ReadColor(br);
                }
                var bytes = new byte[Width * Height / 4];
                for (int i = 0; i < Width * Height / 4; i++)
                {
                    bytes[i] = br.ReadByte();
                }
                DecodeVQ(bytes, palette);
            }
            else if (Type == PVRType.RGB565 || Type == PVRType.ARGB1555 || Type == PVRType.ARGB4444)
            {
                Pixels = new Color4[Width * Height];
                for (int i = 0; i < Width * Height; i++)
                {
                    Pixels[i] = ReadColor(br);
                }
                Unswizzle();
            }
            else if (Type == PVRType.DDS_RGB24 || Type == PVRType.DDS_RGBA32)
            {
                Dds image = Dds.Create(br.BaseStream, new PfimConfig());

                byte[] pixels = image.Data;
                Pixels = new Color4[image.Width * image.Height];
                for (int i = 0; i < image.Width * image.Height; i++)
                {
                    int index = i * image.BytesPerPixel;
                    if (image.BytesPerPixel > 3)
                    {
                        if (pixels[index + 3] < 0.8)
                        {
                            HasTransparency = true;
                        }
                        Pixels[i] = new Color4(pixels[index + 2], pixels[index + 1], pixels[index], pixels[index + 3]);
                    }
                    else
                    {
                        HasTransparency = false;
                        Pixels[i]       = new Color4(pixels[index + 2], pixels[index + 1], pixels[index], 255);
                    }
                }
            }
            else
            {
                throw new NotImplementedException();
            }
        }