예제 #1
0
 public byte[] GetImageBytesForMip(Texture2DMipInfo info, MEGame game, bool useLowerMipsIfTFCMissing, string gamePathToUse = null, List <string> additionalTFCs = null)
 {
     byte[] imageBytes = null;
     try
     {
         imageBytes = GetTextureData(info, game, gamePathToUse, true, additionalTFCs);
     }
     catch (FileNotFoundException e)
     {
         if (useLowerMipsIfTFCMissing)
         {
             //External archive not found - using built in mips (will be hideous, but better than nothing)
             info = Mips.FirstOrDefault(x => x.storageType == StorageTypes.pccUnc);
             if (info != null)
             {
                 imageBytes = GetTextureData(info, game, gamePathToUse);
             }
         }
         else
         {
             throw e; //rethrow
         }
     }
     if (imageBytes == null)
     {
         throw new Exception(GetLocalizedCouldNotFetchTextureDataMessage(info?.Export.InstancedFullPath, info?.Export.FileRef.FilePath));
     }
     return(imageBytes);
 }
예제 #2
0
 public static uint GetMipCRC(Texture2DMipInfo mip, string textureFormat, string gamePathToUse = null)
 {
     byte[] data = GetTextureData(mip, mip.Export.Game, gamePathToUse);
     if (data == null)
     {
         return(0);
     }
     if (textureFormat == "PF_NormalMap_HQ")
     {
         // only ME1 and ME2
         return((uint)~ParallelCRC.Compute(data, 0, data.Length / 2));
     }
     return((uint)~ParallelCRC.Compute(data));
 }
예제 #3
0
        public static List <Texture2DMipInfo> GetTexture2DMipInfos(ExportEntry exportEntry, string cacheName)
        {
            UTexture2D texBin = exportEntry.GetBinaryData <UTexture2D>();
            var        mips   = new List <Texture2DMipInfo>();

            for (int i = 0; i < texBin.Mips.Count; i++)
            {
                UTexture2D.Texture2DMipMap binMip = texBin.Mips[i];
                Texture2DMipInfo           mip    = new Texture2DMipInfo
                {
                    Export           = exportEntry,
                    index            = i,
                    storageType      = binMip.StorageType,
                    uncompressedSize = binMip.UncompressedSize,
                    compressedSize   = binMip.CompressedSize,
                    externalOffset   = binMip.DataOffset,
                    Mip = binMip.Mip,
                    TextureCacheName = cacheName, //If this is ME1, this will simply be ignored in the setter
                    width            = binMip.SizeX,
                    height           = binMip.SizeY
                };

                if (mip.width == 4 && mips.Exists(m => m.width == mip.width))
                {
                    mip.width = mips.Last().width / 2;
                }
                if (mip.height == 4 && mips.Exists(m => m.height == mip.height))
                {
                    mip.height = mips.Last().height / 2;
                }
                if (mip.width == 0)
                {
                    mip.width = 1;
                }
                if (mip.height == 0)
                {
                    mip.height = 1;
                }
                mips.Add(mip);
            }

            return(mips);
        }
예제 #4
0
        public static byte[] GetTextureData(Texture2DMipInfo mipToLoad, MEGame game, string gamePathToUse = null, bool decompress = true, List <string> additionalTFCs = null)
        {
            var imagebytes = new byte[decompress ? mipToLoad.uncompressedSize : mipToLoad.compressedSize];

            //Debug.WriteLine("getting texture data for " + mipToLoad.Export.FullPath);
            if (mipToLoad.storageType == StorageTypes.pccUnc)
            {
                Buffer.BlockCopy(mipToLoad.Mip, 0, imagebytes, 0, mipToLoad.uncompressedSize);
            }
            else if (mipToLoad.storageType == StorageTypes.pccLZO || mipToLoad.storageType == StorageTypes.pccZlib)
            {
                if (decompress)
                {
                    try
                    {
                        TextureCompression.DecompressTexture(imagebytes,
                                                             new MemoryStream(mipToLoad.Mip),
                                                             mipToLoad.storageType, mipToLoad.uncompressedSize, mipToLoad.compressedSize);
                    }
                    catch (Exception e)
                    {
                        throw new Exception(GetLocalizedTextureExceptionInternalMessage(e.Message, mipToLoad.storageType.ToString()));
                    }
                }
                else
                {
                    Buffer.BlockCopy(mipToLoad.Mip, 0, imagebytes, 0, mipToLoad.compressedSize);
                }
            }
            else if (mipToLoad.storageType == StorageTypes.extUnc || mipToLoad.storageType == StorageTypes.extLZO || mipToLoad.storageType == StorageTypes.extZlib || mipToLoad.storageType == StorageTypes.extLZMA)
            {
                string        filename    = null;
                List <string> loadedFiles = MELoadedFiles.GetAllGameFiles(gamePathToUse, game, false, true);
                if (mipToLoad.Export.Game == MEGame.ME1)
                {
                    var fullPath = loadedFiles.FirstOrDefault(x => Path.GetFileName(x).Equals(mipToLoad.TextureCacheName, StringComparison.InvariantCultureIgnoreCase));

                    if (fullPath != null)
                    {
                        filename = fullPath;
                    }
                    else
                    {
                        throw new FileNotFoundException(GetLocalizedCouldNotFindME1TexturePackageMessage(mipToLoad.TextureCacheName));
                    }
                }
                else
                {
                    string archive = mipToLoad.TextureCacheName + @".tfc";

                    var localDirectoryTFCPath = Path.Combine(Path.GetDirectoryName(mipToLoad.Export.FileRef.FilePath), archive);
                    if (File.Exists(localDirectoryTFCPath))
                    {
                        filename = localDirectoryTFCPath;
                    }
                    else if (additionalTFCs != null && additionalTFCs.Any(x => Path.GetFileName(x).Equals(archive, StringComparison.InvariantCultureIgnoreCase)))
                    {
                        filename = additionalTFCs.First(x => Path.GetFileName(x).Equals(archive, StringComparison.InvariantCultureIgnoreCase));
                    }
                    else
                    {
                        var tfcs = loadedFiles.Where(x => x.EndsWith(@".tfc")).ToList();

                        var fullPath = loadedFiles.FirstOrDefault(x => Path.GetFileName(x).Equals(archive, StringComparison.InvariantCultureIgnoreCase));
                        if (fullPath != null)
                        {
                            filename = fullPath;
                        }
                        else
                        {
                            throw new FileNotFoundException(GetLocalizedCouldNotFindME2ME3TextureCacheMessage(archive));
                        }
                    }
                }

                //exceptions above will prevent filename from being null here

                try
                {
                    using (FileStream fs = new FileStream(filename, FileMode.Open, FileAccess.Read))
                    {
                        try
                        {
                            fs.Seek(mipToLoad.externalOffset, SeekOrigin.Begin);
                            if (mipToLoad.storageType == StorageTypes.extLZO || mipToLoad.storageType == StorageTypes.extZlib)
                            {
                                if (decompress)
                                {
                                    using (MemoryStream tmpStream = fs.ReadToMemoryStream(mipToLoad.compressedSize))
                                    {
                                        try
                                        {
                                            TextureCompression.DecompressTexture(imagebytes, tmpStream, mipToLoad.storageType, mipToLoad.uncompressedSize, mipToLoad.compressedSize);
                                        }
                                        catch (Exception e)
                                        {
                                            throw new Exception(GetLocalizedTextureExceptionExternalMessage(e.Message, filename, mipToLoad.storageType.ToString(), mipToLoad.externalOffset.ToString()));
                                        }
                                    }
                                }
                                else
                                {
                                    fs.Read(imagebytes, 0, mipToLoad.compressedSize);
                                }
                            }
                            else
                            {
                                fs.Read(imagebytes, 0, mipToLoad.uncompressedSize);
                            }
                        }
                        catch (Exception e)
                        {
                            throw new Exception(GetLocalizedTextureExceptionExternalMessage(e.Message, filename, mipToLoad.storageType.ToString(), mipToLoad.externalOffset.ToString()));
                        }
                    }
                }
                catch (Exception e)
                {
                    throw new Exception(GetLocalizedTextureExceptionExternalMessage(e.Message, filename, mipToLoad.storageType.ToString(), mipToLoad.externalOffset.ToString()));
                }
            }
            return(imagebytes);
        }