Example #1
0
        public static void BuildResourceSingle(string outputFolder, string collectionName)
        {
            Utils.EnsureKeys();

            using (RageArchiveWrapper7 rpf = RageArchiveWrapper7.Create(outputFolder + @"\dlc.rpf"))
            {
                rpf.archive_.Encryption = RageArchiveEncryption7.NG;

                var dir = rpf.Root.CreateDirectory();
                dir.Name = "common";

                var dataDir = dir.CreateDirectory();
                dataDir.Name = "data";

                dir      = rpf.Root.CreateDirectory();
                dir.Name = "x64";

                dir      = dir.CreateDirectory();
                dir.Name = "models";

                var cdimagesDir = dir.CreateDirectory();
                cdimagesDir.Name = "cdimages";

                RageArchiveWrapper7 currComponentRpf = null;
                IArchiveDirectory   currComponentDir = null;

                RageArchiveWrapper7 currPropRpf = null;
                IArchiveDirectory   currPropDir = null;

                bool hasMale        = false;
                bool hasFemale      = false;
                bool hasMaleProps   = false;
                bool hasFemaleProps = false;

                for (int sexNr = 0; sexNr < 2; ++sexNr)
                {
                    //Male YMT generating
                    YmtPedDefinitionFile ymt = new YmtPedDefinitionFile();

                    ymt.metaYmtName           = prefixes[sexNr] + collectionName;
                    ymt.Unk_376833625.DlcName = RageLib.Hash.Jenkins.Hash(prefixes[sexNr] + collectionName);

                    MUnk_3538495220[] componentTextureBindings = { null, null, null, null, null, null, null, null, null, null, null, null };
                    int[]             componentIndexes         = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
                    int[]             propIndexes = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };

                    //ymt.Unk_376833625.Unk_1235281004 = 0;
                    //ymt.Unk_376833625.Unk_4086467184 = 0;
                    //ymt.Unk_376833625.Unk_911147899 = 0;
                    //ymt.Unk_376833625.Unk_315291935 = 0;
                    //ymt.Unk_376833625.Unk_2996560424 = ;

                    bool isAnyClothAdded = false;
                    bool isAnyPropAdded  = false;

                    foreach (ClothData cd in MainWindow.clothes)
                    {
                        if (cd.IsComponent())
                        {
                            byte componentTypeID = cd.GetComponentTypeID();

                            if (cd.textures.Count > 0 && (int)cd.targetSex == sexNr)
                            {
                                YmtPedDefinitionFile targetYmt = ymt;

                                if (componentTextureBindings[componentTypeID] == null)
                                {
                                    componentTextureBindings[componentTypeID] = new MUnk_3538495220();
                                }

                                MUnk_1535046754 textureDescription = new MUnk_1535046754();

                                byte nextPropMask = 17;

                                switch (componentTypeID)
                                {
                                case 2:
                                case 7:
                                    nextPropMask = 11; break;

                                case 5:
                                case 8:
                                    nextPropMask = 65; break;

                                case 9:
                                    nextPropMask = 1; break;

                                case 10:
                                    nextPropMask = 5; break;

                                case 11:
                                    nextPropMask = 1; break;

                                default:
                                    break;
                                }

                                textureDescription.PropMask       = nextPropMask;
                                textureDescription.Unk_2806194106 = (byte)(cd.fpModelPath != "" ? 1 : 0);

                                byte   texId      = (byte)(cd.mainPath.EndsWith("_u.ydd") ? 0 : 1);
                                string postfix    = cd.mainPath.EndsWith("_u.ydd") ? "u" : "r";
                                string ytdPostfix = cd.mainPath.EndsWith("_u.ydd") ? "uni" : "whi";

                                foreach (string texPath in cd.textures)
                                {
                                    MUnk_1036962405 texInfo = new MUnk_1036962405();
                                    texInfo.Distribution = 255;
                                    texInfo.TexId        = texId;
                                    textureDescription.ATexData.Add(texInfo);
                                }

                                textureDescription.ClothData.Unk_2828247905 = 0;

                                componentTextureBindings[componentTypeID].Unk_1756136273.Add(textureDescription);

                                byte componentTextureLocalId = (byte)(componentTextureBindings[componentTypeID].Unk_1756136273.Count - 1);

                                MCComponentInfo componentInfo = new MCComponentInfo();
                                componentInfo.Unk_802196719    = 0;
                                componentInfo.Unk_4233133352   = 0;
                                componentInfo.Unk_128864925.b0 = (byte)(cd.componentFlags.unkFlag1 ? 1 : 0);
                                componentInfo.Unk_128864925.b1 = (byte)(cd.componentFlags.unkFlag2 ? 1 : 0);
                                componentInfo.Unk_128864925.b2 = (byte)(cd.componentFlags.unkFlag3 ? 1 : 0);
                                componentInfo.Unk_128864925.b3 = (byte)(cd.componentFlags.unkFlag4 ? 1 : 0);
                                componentInfo.Unk_128864925.b4 = (byte)(cd.componentFlags.isHighHeels ? 1 : 0);
                                componentInfo.Flags            = 0;
                                componentInfo.Inclusions       = 0;
                                componentInfo.Exclusions       = 0;
                                componentInfo.Unk_1613922652   = 0;
                                componentInfo.Unk_2114993291   = 0;
                                componentInfo.Unk_3509540765   = componentTypeID;
                                componentInfo.Unk_4196345791   = componentTextureLocalId;

                                targetYmt.Unk_376833625.CompInfos.Add(componentInfo);

                                if (!isAnyClothAdded)
                                {
                                    isAnyClothAdded = true;

                                    var ms = new MemoryStream();

                                    currComponentRpf = RageArchiveWrapper7.Create(ms, folderNames[sexNr].Replace("ped_", collectionName + "_") + ".rpf");
                                    currComponentRpf.archive_.Encryption = RageArchiveEncryption7.NG;
                                    currComponentDir      = currComponentRpf.Root.CreateDirectory();
                                    currComponentDir.Name = prefixes[sexNr] + "freemode_01_" + prefixes[sexNr] + collectionName;
                                }

                                int currentComponentIndex = componentIndexes[componentTypeID]++;

                                string componentNumerics = currentComponentIndex.ToString().PadLeft(3, '0');
                                string prefix            = cd.GetPrefix();

                                var resource = currComponentDir.CreateResourceFile();
                                resource.Name = prefix + "_" + componentNumerics + "_" + postfix + ".ydd";
                                resource.Import(cd.mainPath);

                                char offsetLetter = 'a';

                                for (int i = 0; i < cd.textures.Count; ++i)
                                {
                                    resource      = currComponentDir.CreateResourceFile();
                                    resource.Name = prefix + "_diff_" + componentNumerics + "_" + (char)(offsetLetter + i) + "_" + ytdPostfix + ".ytd";
                                    resource.Import(cd.textures[i]);
                                }

                                if (cd.fpModelPath != "")
                                {
                                    resource      = currComponentDir.CreateResourceFile();
                                    resource.Name = prefix + "_" + componentNumerics + "_" + postfix + "_1.ydd";
                                    resource.Import(cd.fpModelPath);
                                }
                            }
                        }
                        else
                        {
                            Unk_2834549053 anchor = (Unk_2834549053)cd.GetPedPropTypeID();

                            if (cd.textures.Count > 0 && (int)cd.targetSex == sexNr)
                            {
                                YmtPedDefinitionFile targetYmt = ymt;

                                var defs = ymt.Unk_376833625.PropInfo.Props[anchor] ?? new List <MUnk_94549140>();
                                var item = new MUnk_94549140(ymt.Unk_376833625.PropInfo);

                                item.AnchorId = (byte)anchor;

                                for (int i = 0; i < cd.textures.Count; i++)
                                {
                                    var texture = new MUnk_254518642();
                                    texture.TexId = (byte)i;
                                    item.TexData.Add(texture);
                                }

                                // Get or create linked anchor
                                var aanchor = ymt.Unk_376833625.PropInfo.AAnchors.Find(e => e.Anchor == anchor);

                                if (aanchor == null)
                                {
                                    aanchor = new MCAnchorProps(ymt.Unk_376833625.PropInfo)
                                    {
                                        Anchor = anchor
                                    };

                                    aanchor.PropsMap[item] = (byte)item.TexData.Count;

                                    ymt.Unk_376833625.PropInfo.AAnchors.Add(aanchor);
                                }
                                else
                                {
                                    aanchor.PropsMap[item] = (byte)item.TexData.Count;
                                }

                                defs.Add(item);

                                if (!isAnyPropAdded)
                                {
                                    isAnyPropAdded = true;

                                    var ms = new MemoryStream();

                                    currPropRpf = RageArchiveWrapper7.Create(ms, folderNames[sexNr].Replace("ped_", collectionName + "_") + "_p.rpf");
                                    currPropRpf.archive_.Encryption = RageArchiveEncryption7.NG;
                                    currPropDir      = currPropRpf.Root.CreateDirectory();
                                    currPropDir.Name = prefixes[sexNr] + "freemode_01_p_" + prefixes[sexNr] + collectionName;
                                }

                                int currentPropIndex = propIndexes[(byte)anchor]++;

                                string componentNumerics = currentPropIndex.ToString().PadLeft(3, '0');
                                string prefix            = cd.GetPrefix();

                                var resource = currPropDir.CreateResourceFile();
                                resource.Name = prefix + "_" + componentNumerics + ".ydd";
                                resource.Import(cd.mainPath);

                                char offsetLetter = 'a';
                                for (int i = 0; i < cd.textures.Count; ++i)
                                {
                                    resource      = currPropDir.CreateResourceFile();
                                    resource.Name = prefix + "_diff_" + componentNumerics + "_" + (char)(offsetLetter + i) + ".ytd";
                                    resource.Import(cd.textures[i]);
                                }
                            }
                        }
                    }

                    if (isAnyClothAdded)
                    {
                        if (sexNr == 0)
                        {
                            hasMale = true;
                        }
                        else if (sexNr == 1)
                        {
                            hasFemale = true;
                        }

                        int arrIndex = 0;
                        for (int i = 0; i < componentTextureBindings.Length; ++i)
                        {
                            if (componentTextureBindings[i] != null)
                            {
                                byte id = (byte)(arrIndex++);
                                ymt.Unk_376833625.Unk_2996560424.SetByte(i, id);
                            }

                            ymt.Unk_376833625.Components[(Unk_884254308)i] = componentTextureBindings[i];
                        }
                    }

                    if (isAnyClothAdded || isAnyPropAdded)
                    {
                        using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(GenerateShopMeta((Sex)sexNr, collectionName))))
                        {
                            var binFile = dataDir.CreateBinaryFile();
                            binFile.Name = prefixes[sexNr] + "freemode_01_" + prefixes[sexNr] + collectionName + ".meta";
                            binFile.Import(stream);
                        }
                        currComponentRpf.Flush();

                        var binRpfFile = cdimagesDir.CreateBinaryFile();
                        binRpfFile.Name = folderNames[sexNr].Replace("ped_", collectionName + "_") + ".rpf";
                        binRpfFile.Import(currComponentRpf.archive_.BaseStream);

                        currComponentRpf.Dispose();
                    }

                    if (isAnyPropAdded)
                    {
                        if (sexNr == 0)
                        {
                            hasMaleProps = true;
                        }
                        else if (sexNr == 1)
                        {
                            hasFemaleProps = true;
                        }

                        currPropRpf.Flush();

                        var binRpfFile = cdimagesDir.CreateBinaryFile();
                        binRpfFile.Name = folderNames[sexNr].Replace("ped_", collectionName + "_") + "_p.rpf";
                        binRpfFile.Import(currPropRpf.archive_.BaseStream);

                        currPropRpf.Dispose();
                    }
                }

                using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(GenerateContentXML(collectionName, hasMale, hasFemale, hasMaleProps, hasFemaleProps))))
                {
                    var binFile = rpf.Root.CreateBinaryFile();
                    binFile.Name = "content.xml";
                    binFile.Import(stream);
                }

                using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(GenerateSetup2XML(collectionName))))
                {
                    var binFile = rpf.Root.CreateBinaryFile();
                    binFile.Name = "setup2.xml";
                    binFile.Import(stream);
                }

                rpf.Flush();
                rpf.Dispose();

                MessageBox.Show("Resource built!");
            }
        }
        public static void BuildResourceSingle(string outputFolder, string collectionName)
        {
            Utils.EnsureKeys();

            using (RageArchiveWrapper7 rpf = RageArchiveWrapper7.Create(outputFolder + @"\dlc.rpf"))
            {
                rpf.archive_.Encryption = RageArchiveEncryption7.NG;

                var dir = rpf.Root.CreateDirectory();
                dir.Name = "common";

                var dataDir = dir.CreateDirectory();
                dataDir.Name = "data";

                dir      = rpf.Root.CreateDirectory();
                dir.Name = "x64";

                dir      = dir.CreateDirectory();
                dir.Name = "models";

                var cdimagesDir = dir.CreateDirectory();
                cdimagesDir.Name = "cdimages";

                RageArchiveWrapper7 currComponentRpf = null;
                IArchiveDirectory   currComponentDir = null;

                RageArchiveWrapper7 currPropRpf = null;
                IArchiveDirectory   currPropDir = null;

                bool hasMale        = false;
                bool hasFemale      = false;
                bool hasMaleProps   = false;
                bool hasFemaleProps = false;

                for (int sexNr = 0; sexNr < 2; ++sexNr)
                {
                    //Male YMT generating
                    YmtPedDefinitionFile ymt = new YmtPedDefinitionFile
                    {
                        metaYmtName   = Prefixes[sexNr] + collectionName,
                        Unk_376833625 = { DlcName = RageLib.Hash.Jenkins.Hash(Prefixes[sexNr] + collectionName) }
                    };

                    MUnk_3538495220[] componentTextureBindings = { null, null, null, null, null, null, null, null, null, null, null, null };
                    int[]             componentIndexes         = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
                    int[]             propIndexes = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };

                    //ymt.Unk_376833625.Unk_1235281004 = 0;
                    //ymt.Unk_376833625.Unk_4086467184 = 0;
                    //ymt.Unk_376833625.Unk_911147899 = 0;
                    //ymt.Unk_376833625.Unk_315291935 = 0;
                    //ymt.Unk_376833625.Unk_2996560424 = ;

                    bool isAnyClothAdded = false;
                    bool isAnyPropAdded  = false;

                    foreach (ClothData clothData in MainWindow.Clothes)
                    {
                        if (clothData.IsComponent())
                        {
                            if (clothData.Textures.Count <= 0 || (int)clothData.TargetSex != sexNr)
                            {
                                continue;
                            }

                            var componentItemInfo = GenerateYmtPedComponentItem(clothData, ref componentTextureBindings);
                            ymt.Unk_376833625.CompInfos.Add(componentItemInfo);

                            var componentTypeId = componentItemInfo.Unk_3509540765;
                            GetClothPostfixes(clothData, out var ytdPostfix, out var yddPostfix);

                            if (!isAnyClothAdded)
                            {
                                isAnyClothAdded = true;

                                var ms = new MemoryStream();

                                currComponentRpf = RageArchiveWrapper7.Create(ms, FolderNames[sexNr].Replace("ped_", collectionName + "_") + ".rpf");
                                currComponentRpf.archive_.Encryption = RageArchiveEncryption7.NG;
                                currComponentDir      = currComponentRpf.Root.CreateDirectory();
                                currComponentDir.Name = Prefixes[sexNr] + "freemode_01_" + Prefixes[sexNr] + collectionName;
                            }

                            int currentComponentIndex = componentIndexes[componentTypeId]++;

                            string componentNumerics = currentComponentIndex.ToString().PadLeft(3, '0');
                            string prefix            = clothData.GetPrefix();

                            clothData.SetComponentNumerics(componentNumerics, currentComponentIndex);

                            var resource = currComponentDir.CreateResourceFile();
                            resource.Name = prefix + "_" + componentNumerics + "_" + yddPostfix + ".ydd";
                            resource.Import(clothData.MainPath);

                            char offsetLetter = 'a';

                            for (int i = 0; i < clothData.Textures.Count; ++i)
                            {
                                resource      = currComponentDir.CreateResourceFile();
                                resource.Name = prefix + "_diff_" + componentNumerics + "_" + (char)(offsetLetter + i) + "_" + ytdPostfix + ".ytd";
                                resource.Import(clothData.Textures[i]);
                            }

                            if (clothData.FirstPersonModelPath != "")
                            {
                                resource      = currComponentDir.CreateResourceFile();
                                resource.Name = prefix + "_" + componentNumerics + "_" + yddPostfix + "_1.ydd";
                                resource.Import(clothData.FirstPersonModelPath);
                            }
                        }
                        else
                        {
                            if (clothData.Textures.Count <= 0 || (int)clothData.TargetSex != sexNr)
                            {
                                continue;
                            }

                            Unk_2834549053 anchor = (Unk_2834549053)clothData.GetPedPropTypeId();
                            var            defs   = ymt.Unk_376833625.PropInfo.Props[anchor] ?? new List <MUnk_94549140>();
                            var            item   = GenerateYmtPedPropItem(ymt, anchor, clothData);
                            defs.Add(item);

                            if (!isAnyPropAdded)
                            {
                                isAnyPropAdded = true;

                                var ms = new MemoryStream();

                                currPropRpf = RageArchiveWrapper7.Create(ms, FolderNames[sexNr].Replace("ped_", collectionName + "_") + "_p.rpf");
                                currPropRpf.archive_.Encryption = RageArchiveEncryption7.NG;
                                currPropDir      = currPropRpf.Root.CreateDirectory();
                                currPropDir.Name = Prefixes[sexNr] + "freemode_01_p_" + Prefixes[sexNr] + collectionName;
                            }

                            int currentPropIndex = propIndexes[(byte)anchor]++;

                            string componentNumerics = currentPropIndex.ToString().PadLeft(3, '0');
                            string prefix            = clothData.GetPrefix();

                            clothData.SetComponentNumerics(componentNumerics, currentPropIndex);

                            var resource = currPropDir.CreateResourceFile();
                            resource.Name = prefix + "_" + componentNumerics + ".ydd";
                            resource.Import(clothData.MainPath);

                            char offsetLetter = 'a';
                            for (int i = 0; i < clothData.Textures.Count; ++i)
                            {
                                resource      = currPropDir.CreateResourceFile();
                                resource.Name = prefix + "_diff_" + componentNumerics + "_" + (char)(offsetLetter + i) + ".ytd";
                                resource.Import(clothData.Textures[i]);
                            }
                        }
                    }

                    if (isAnyClothAdded)
                    {
                        if (sexNr == 0)
                        {
                            hasMale = true;
                        }
                        else if (sexNr == 1)
                        {
                            hasFemale = true;
                        }

                        UpdateYmtComponentTextureBindings(componentTextureBindings, ymt);
                    }

                    if (isAnyClothAdded || isAnyPropAdded)
                    {
                        using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(GenerateShopMeta((Sex)sexNr, collectionName))))
                        {
                            var binFile = dataDir.CreateBinaryFile();
                            binFile.Name = Prefixes[sexNr] + "freemode_01_" + Prefixes[sexNr] + collectionName + ".meta";
                            binFile.Import(stream);
                        }
                        currComponentRpf.Flush();

                        var binRpfFile = cdimagesDir.CreateBinaryFile();
                        binRpfFile.Name = FolderNames[sexNr].Replace("ped_", collectionName + "_") + ".rpf";
                        binRpfFile.Import(currComponentRpf.archive_.BaseStream);

                        currComponentRpf.Dispose();
                    }

                    if (isAnyPropAdded)
                    {
                        if (sexNr == 0)
                        {
                            hasMaleProps = true;
                        }
                        else if (sexNr == 1)
                        {
                            hasFemaleProps = true;
                        }

                        currPropRpf.Flush();

                        var binRpfFile = cdimagesDir.CreateBinaryFile();
                        binRpfFile.Name = FolderNames[sexNr].Replace("ped_", collectionName + "_") + "_p.rpf";
                        binRpfFile.Import(currPropRpf.archive_.BaseStream);

                        currPropRpf.Dispose();
                    }
                }

                using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(GenerateSingleplayerContentXml(collectionName, hasMale, hasFemale, hasMaleProps, hasFemaleProps))))
                {
                    var binFile = rpf.Root.CreateBinaryFile();
                    binFile.Name = "content.xml";
                    binFile.Import(stream);
                }

                using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(GenerateSingleplayerSetup2Xml(collectionName))))
                {
                    var binFile = rpf.Root.CreateBinaryFile();
                    binFile.Name = "setup2.xml";
                    binFile.Import(stream);
                }

                rpf.Flush();
                rpf.Dispose();
            }
        }
Example #3
0
        static void HandleFixArchiveOptions(string[] args)
        {
            CommandLine.Parse <FixArchiveOptions>(args, (opts, gOpts) =>
            {
                EnsurePath();
                EnsureKeys();

                if (opts.InputFiles != null)
                {
                    var inputFiles = Utils.Expand(opts.InputFiles);

                    for (int i = 0; i < inputFiles.Length; i++)
                    {
                        var fileInfo = inputFiles[i];

                        Console.WriteLine(fileInfo.FullName);

                        using (RageArchiveWrapper7 inputArchive = RageArchiveWrapper7.Open(fileInfo.FullName))
                        {
                            var rpfs = new List <Tuple <string, RageArchiveWrapper7> >();

                            if (opts.Recursive)
                            {
                                ArchiveUtilities.ForEachFile(fileInfo.FullName.Replace(Settings.Default.GTAFolder, ""), inputArchive.Root, inputArchive.archive_.Encryption, (string fullFileName, IArchiveFile file, RageArchiveEncryption7 encryption) =>
                                {
                                    if (fullFileName.EndsWith(".rpf", StringComparison.OrdinalIgnoreCase))
                                    {
                                        try
                                        {
                                            var binFile   = (RageArchiveBinaryFileWrapper7)file;
                                            var tmpStream = new FileStream(Path.GetTempFileName(), FileMode.Open);

                                            binFile.Export(tmpStream);
                                            RageArchiveWrapper7 archive = RageArchiveWrapper7.Open(tmpStream, file.Name);

                                            var wrapper = RageArchiveWrapper7.Open(tmpStream, binFile.Name);

                                            rpfs.Add(new Tuple <string, RageArchiveWrapper7>(fullFileName, wrapper));
                                        }
                                        catch (Exception e)
                                        {
                                            Console.Error.WriteLine(e.Message);
                                        }
                                    }
                                });

                                rpfs.Sort((a, b) =>
                                {
                                    return(b.Item1.Replace('\\', '/').Split('/').Length - a.Item1.Replace('\\', '/').Split('/').Length);
                                });
                            }

                            bool found = false;

                            if (opts.Recursive)
                            {
                                for (int j = 0; j < rpfs.Count; j++)
                                {
                                    var fullName = rpfs[j].Item1;
                                    var wrapper  = rpfs[j].Item2;

                                    if (wrapper.archive_.Encryption != RageArchiveEncryption7.None)
                                    {
                                        Console.WriteLine("SKIP " + fullName);
                                        continue;
                                    }

                                    found = true;

                                    wrapper.archive_.Encryption = RageArchiveEncryption7.NG;
                                    wrapper.Flush();
                                    wrapper.Dispose();

                                    Console.WriteLine("ENCRYPT " + fullName);
                                }
                            }

                            if (inputArchive.archive_.Encryption != RageArchiveEncryption7.None && !found)
                            {
                                Console.WriteLine("SKIP " + fileInfo.Name);
                                continue;
                            }

                            inputArchive.archive_.Encryption = RageArchiveEncryption7.NG;
                            inputArchive.Flush();
                            inputArchive.Dispose();

                            Console.WriteLine("ENCRYPT " + fileInfo.Name);

                            rpfs.Reverse();

                            for (int j = 0; j < rpfs.Count; j++)
                            {
                                rpfs[j].Item2.Dispose();
                            }
                        }
                    }
                }
            });
        }