diff --git a/BNP Files/BOTWMultiplayer-Classic.bnp b/BNP Files/BOTWMultiplayer-Classic.bnp deleted file mode 100644 index 6b344ef..0000000 Binary files a/BNP Files/BOTWMultiplayer-Classic.bnp and /dev/null differ diff --git a/BNP Files/BreathoftheWildMultiplayer.bnp b/BNP Files/BreathoftheWildMultiplayer.bnp deleted file mode 100644 index df3572d..0000000 Binary files a/BNP Files/BreathoftheWildMultiplayer.bnp and /dev/null differ diff --git a/BNP Files/MilkBarLauncher.bnp b/BNP Files/MilkBarLauncher.bnp new file mode 100644 index 0000000..62342a0 Binary files /dev/null and b/BNP Files/MilkBarLauncher.bnp differ diff --git a/C#/BOTW.DedicatedServer/Program.cs b/C#/BOTW.DedicatedServer/Program.cs index a59893f..6d22d57 100644 --- a/C#/BOTW.DedicatedServer/Program.cs +++ b/C#/BOTW.DedicatedServer/Program.cs @@ -13,7 +13,7 @@ try #if (DEBUG) Console.WriteLine("DEV"); #else - Console.WriteLine("DEV 2.0"); + Console.WriteLine("2.0.1"); #endif Console.WriteLine(); diff --git a/C#/BOTW.Logging/Logger.cs b/C#/BOTW.Logging/Logger.cs index 2a2f68b..8394467 100644 --- a/C#/BOTW.Logging/Logger.cs +++ b/C#/BOTW.Logging/Logger.cs @@ -65,7 +65,22 @@ if (!Directory.Exists(LogsFolder)) Directory.CreateDirectory(LogsFolder); - File.Move(LogPath, $"{LogsFolder}\\{creationTime}.txt"); + string postName = ""; + + // The correct way to manage a log file already existing is by creating a differently named log file + if(File.Exists($"{LogsFolder}\\{creationTime}.txt")) + postName = $"({Directory.GetFiles(LogsFolder).Where(file => Path.GetFileNameWithoutExtension(file).StartsWith(creationTime)).Count()})"; + + if (!File.Exists($"{LogsFolder}\\{creationTime}{postName}.txt")) + { + File.Move(LogPath, $"{LogsFolder}\\{creationTime}{postName}.txt"); + } + else + { + // If for some reason, even after naming the file differently, it fails. Here we can delete it. + Console.WriteLine($"Failed to create file at: {LogsFolder}\\{creationTime}{postName}.txt. Deleting it..."); + File.Delete(LogPath); + } } File.CreateText(LogPath); @@ -83,15 +98,22 @@ logMutex.WaitOne(100); - using (StreamWriter LogFile = new StreamWriter(LogPath, true)) + try { - LogFile.Write($"[{MessageTime}] {message}"); + using (StreamWriter LogFile = new StreamWriter(LogPath, true)) + { + LogFile.Write($"[{MessageTime}] {message}"); - if (!string.IsNullOrEmpty(details)) - LogFile.Write($" - Details: {details}"); + if (!string.IsNullOrEmpty(details)) + LogFile.Write($" - Details: {details}"); - if(newLine) - LogFile.WriteLine(); + if (newLine) + LogFile.WriteLine(); + } + } + catch(Exception ex) + { + WriteToConsole(LogWriteLevelEnum.ERR, "\nCould not write to log file. Please make sure that you don't have another server process and restart your server.", MessageTime, ConsoleColor.DarkRed, true); } logMutex.ReleaseMutex(); diff --git a/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/MainViewModel.cs b/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/MainViewModel.cs index 2481ec9..af2d4c4 100644 --- a/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/MainViewModel.cs +++ b/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/MainViewModel.cs @@ -117,7 +117,6 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel this.IngameMenuVM = new IngameMenuModel(); SharedData.LoadingMessage = new LoadingModel(); this.disableBackground = false; - GameFilesModifier.CreateModifiedModel(); currentView = this.MainMenuVM; diff --git a/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/ServerBrowserModel.cs b/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/ServerBrowserModel.cs index 6c02bb9..5ea1100 100644 --- a/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/ServerBrowserModel.cs +++ b/WPF .NET 6/Breath of the Wild Multiplayer/MVVM/ViewModel/ServerBrowserModel.cs @@ -10,6 +10,7 @@ using Breath_of_the_Wild_Multiplayer.MVVM.Model.DTO; using System.Linq; using System.Threading.Tasks; using System.Text; +using System.Xml; namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel { @@ -61,10 +62,23 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel } } + public bool IsModInstalled + { + get + { + string modActorsPack = $@"{BcmlSettings.MergedDir}\Actor\Pack"; + + // If the directory for the directory doesn't even exist. That is a clear indicator that the mod is not installed + if (!Directory.Exists(modActorsPack)) + return false; + // One of the unique assets created by the mod are the actors called JugadorXX.sbactorpack. + // If we don't have any Jugador, that means the mod is not installed. + return Directory.GetFiles(modActorsPack).Any(actor => actor.Contains("Jugador") && Path.GetExtension(actor) == ".sbactorpack"); + } + } + private Dictionary ServerMapping; - private string GameDir; - private string CemuDir; public List ServerList; public RelayCommand serverButtonClick { get; set; } @@ -79,7 +93,7 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel { SharedData.ServerBrowser = this; - findCemuData(); + //findCemuData(); isMaxOffset = true; scrollState = 0; @@ -129,13 +143,13 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel foreach (var server in this.ServerList.Where(sv => sv.Favorite)) { - serversToShow.Add(new serverDataModel(!string.IsNullOrEmpty(GameDir) && !string.IsNullOrEmpty(CemuDir), name: server.Name, ip: server.IP, port: server.Port, favorite: server.Favorite, password: server.Password)); + serversToShow.Add(new serverDataModel(!string.IsNullOrEmpty(BcmlSettings.GameDir) && !string.IsNullOrEmpty(BcmlSettings.CemuDir), name: server.Name, ip: server.IP, port: server.Port, favorite: server.Favorite, password: server.Password)); ServerMapping[serverDataModel.serversAdded - 1] = server; } foreach (var server in this.ServerList.Where(sv => !sv.Favorite)) { - serversToShow.Add(new serverDataModel(!string.IsNullOrEmpty(GameDir) && !string.IsNullOrEmpty(CemuDir), name: server.Name, ip: server.IP, port: server.Port, favorite: server.Favorite, password: server.Password)); + serversToShow.Add(new serverDataModel(!string.IsNullOrEmpty(BcmlSettings.GameDir) && !string.IsNullOrEmpty(BcmlSettings.CemuDir), name: server.Name, ip: server.IP, port: server.Port, favorite: server.Favorite, password: server.Password)); ServerMapping[serverDataModel.serversAdded - 1] = server; } @@ -143,7 +157,7 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel if (_serversToShow.Count == 0) { - selectedServer.Add(new serverDataModel(!string.IsNullOrEmpty(GameDir) && !string.IsNullOrEmpty(CemuDir), name: "", ip: "", port: 0, favorite: false, password: "")); + selectedServer.Add(new serverDataModel(!string.IsNullOrEmpty(BcmlSettings.GameDir) && !string.IsNullOrEmpty(BcmlSettings.CemuDir), name: "", ip: "", port: 0, favorite: false, password: "")); } else { @@ -153,21 +167,21 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel } } - void findCemuData() - { - try - { - string CemuSettings = File.ReadAllText(Properties.Settings.Default.bcmlLocation); - Dictionary settings = JsonConvert.DeserializeObject>(CemuSettings)!; - CemuDir = settings["cemu_dir"]; - GameDir = settings["game_dir"]; - } - catch(Exception ex) - { - CemuDir = ""; - GameDir = ""; - } - } + //void findCemuData() + //{ + // try + // { + // string CemuSettings = File.ReadAllText(Properties.Settings.Default.bcmlLocation); + // Dictionary settings = JsonConvert.DeserializeObject>(CemuSettings)!; + // CemuDir = settings["cemu_dir"]; + // GameDir = settings["game_dir"]; + // } + // catch(Exception ex) + // { + // CemuDir = ""; + // GameDir = ""; + // } + //} async Task connectToServer(serverDataModel serverToJoin = null) { @@ -176,9 +190,44 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel if (serverToJoin == null) serverToJoin = _selectedServer[0]; - if (string.IsNullOrEmpty(GameDir) || string.IsNullOrEmpty(CemuDir)) + if (string.IsNullOrEmpty(BcmlSettings.GameDir) || string.IsNullOrEmpty(BcmlSettings.CemuDir)) throw new ApplicationException("Bcml not setup."); + if (!IsModInstalled) + throw new ApplicationException("Mod is not setup on BCML. Make sure to follow the instructions to install the mod."); + + string cemuSettingsPath = Path.Combine(BcmlSettings.CemuDir, "settings.xml"); + + // Does the settings file for cemu exist? + if (!File.Exists(cemuSettingsPath)) + throw new ApplicationException("Cemu settings file doesn't exist. Make sure to have open cemu and setup the graphic packs"); + + XmlDocument doc = new XmlDocument(); + doc.Load(cemuSettingsPath); + + XmlNode GraphicPacksNode = doc.DocumentElement.SelectSingleNode("/content/GraphicPack"); + + Dictionary nodesToValidate = new Dictionary() { + {" · Utilities", "bcmlPatches\\MilkBarLauncher\\rules.txt"}, + {" · Extended Memory", "BreathOfTheWild\\Mods\\ExtendedMemory\\rules.txt" } + }; + + List missingGraphicPacks = new List(); + + try + { + missingGraphicPacks = nodesToValidate + .Where(sNode => !GraphicPacksNode.ChildNodes.Cast().Any(node => node.Attributes.Cast().Any(attribute => attribute.Value.Contains(sNode.Value)))).Select(sNode => sNode.Key).ToList(); + } + catch(Exception ex) + { + // If any issue happened while reading settings xml. + throw new ApplicationException("Failed to read cemu graphic packs settings. Please make sure that your cemu is setup correctly."); + } + + if(missingGraphicPacks.Any()) + throw new ApplicationException("The following needed graphic packs are not selected on Cemu\n\n" + string.Join("\n", missingGraphicPacks) + "\n\nPlease make sure to select them before joining a server."); + if (string.IsNullOrEmpty(serverToJoin.IP) || !serverToJoin.open) return; @@ -196,6 +245,8 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel SharedData.SetLoadingMessage("Loading player data..."); + await Task.Run(() => GameFilesModifier.CreateModifiedModel()); + await Task.Run(() => GameFilesModifier.ChangeAttentionForJugadores(serverToJoin.playStyle != "Prop hunt")); await Task.Run(() => GameFilesModifier.CleanAnimations()); @@ -234,7 +285,7 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel SharedData.SetLoadingMessage("Starting Cemu..."); - await Task.Run(() => Process.Start($"{CemuDir}/cemu.exe", $"-g \"{GameDir.Replace("content", "code")}/U-King.rpx\"")); + await Task.Run(() => Process.Start($"{BcmlSettings.CemuDir}/cemu.exe", $"-g \"{BcmlSettings.GameDir.Replace("content", "code")}/U-King.rpx\"")); await Task.Delay(500); @@ -329,7 +380,7 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel this.ServerList.Add(serverToAdd); - this.serversToShow.Add(new serverDataModel(!string.IsNullOrEmpty(GameDir) && !string.IsNullOrEmpty(CemuDir), name: serverinfo.name, ip: serverinfo.ip, port: Int32.Parse(serverinfo.port), favorite: false, password: serverinfo.password)); + this.serversToShow.Add(new serverDataModel(!string.IsNullOrEmpty(BcmlSettings.GameDir) && !string.IsNullOrEmpty(BcmlSettings.CemuDir), name: serverinfo.name, ip: serverinfo.ip, port: Int32.Parse(serverinfo.port), favorite: false, password: serverinfo.password)); this.ServerMapping[serverDataModel.serversAdded - 1] = serverToAdd; changeSelected(this._serversToShow.Count - 1); @@ -337,7 +388,7 @@ namespace Breath_of_the_Wild_Multiplayer.MVVM.ViewModel } else if(serverinfo.serverIndex == -2) { - serverDataModel serverToconnect = new serverDataModel(!string.IsNullOrEmpty(GameDir) && !string.IsNullOrEmpty(CemuDir), name: serverinfo.name, ip: serverinfo.ip, port: Int32.Parse(serverinfo.port), favorite: false, password: serverinfo.password, async: false); + serverDataModel serverToconnect = new serverDataModel(!string.IsNullOrEmpty(BcmlSettings.GameDir) && !string.IsNullOrEmpty(BcmlSettings.CemuDir), name: serverinfo.name, ip: serverinfo.ip, port: Int32.Parse(serverinfo.port), favorite: false, password: serverinfo.password, async: false); if (!serverToconnect.open) throw new Exception("Could not connect to server. Check if the server is open."); diff --git a/WPF .NET 6/Breath of the Wild Multiplayer/Source files/BcmlSettings.cs b/WPF .NET 6/Breath of the Wild Multiplayer/Source files/BcmlSettings.cs new file mode 100644 index 0000000..92f0ac1 --- /dev/null +++ b/WPF .NET 6/Breath of the Wild Multiplayer/Source files/BcmlSettings.cs @@ -0,0 +1,23 @@ +using System.Collections.Generic; +using System.IO; +using Newtonsoft.Json; + +namespace Breath_of_the_Wild_Multiplayer.Source_files +{ + public static class BcmlSettings + { + public static string GameDir { get => getSetting("game_dir"); } + public static string UpdateDir { get => getSetting("update_dir"); } + public static string CemuDir { get => getSetting("cemu_dir"); } + public static string MergedDir { get => @$"{getSetting("store_dir")}\merged\content"; } + + private static string getSetting(string setting) + { + if (!File.Exists(Properties.Settings.Default.bcmlLocation)) + return null; + + string CemuSettings = File.ReadAllText(Properties.Settings.Default.bcmlLocation); + return JsonConvert.DeserializeObject>(CemuSettings)![setting]; + } + } +} diff --git a/WPF .NET 6/Breath of the Wild Multiplayer/Source files/GameFilesModifier.cs b/WPF .NET 6/Breath of the Wild Multiplayer/Source files/GameFilesModifier.cs index 525a199..a94711b 100644 --- a/WPF .NET 6/Breath of the Wild Multiplayer/Source files/GameFilesModifier.cs +++ b/WPF .NET 6/Breath of the Wild Multiplayer/Source files/GameFilesModifier.cs @@ -30,14 +30,11 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files public static void ChangeAttentionForJugadores(bool enabled) { - // Get bcml mod path to save data in that folder - string bcmlPath = Properties.Settings.Default.bcmlLocation.Replace("settings.json", @"merged\content"); - List> filesToModify = new List>(); List jugadores = new List(); - foreach (string path in Directory.GetFiles(@$"{bcmlPath}\Actor\Pack\").Where(file => Path.GetFileName(file).StartsWith("Jugador"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.MergedDir}\Actor\Pack\").Where(file => Path.GetFileName(file).StartsWith("Jugador"))) { ActorPack jugador = new ActorPack(path); ActorLink actorLinkFile = jugador.ActorLink.Files()[0]; @@ -60,15 +57,9 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files Stopwatch stopwatch = Stopwatch.StartNew(); /* Obtaining the data */ - // Get game folders so that we can extract the armors and files - string CemuSettings = File.ReadAllText(Properties.Settings.Default.bcmlLocation); - Dictionary settings = JsonConvert.DeserializeObject>(CemuSettings)!; - string GameDir = settings["game_dir"]; - string UpdateDir = settings["update_dir"]; - // Get bcml mod path to save data in that folder string bcmlPath = Properties.Settings.Default.bcmlLocation.Replace("settings.json", @"merged\content"); - string titleBGPath = @$"{UpdateDir}\Pack\TitleBG.pack"; + string titleBGPath = @$"{BcmlSettings.UpdateDir}\Pack\TitleBG.pack"; /* Instantiate objects */ // Create title bg object and load it's data @@ -78,7 +69,7 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files List totalModels = new List(); /* Get armor models */ - foreach (string path in Directory.GetFiles(@$"{UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && !file.Contains("Tex"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && !file.Contains("Tex"))) { BfresFile armorFile = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes(path)))); @@ -140,15 +131,7 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files public static void CreateModifiedModel() { /* Obtaining the data */ - // Get game folders so that we can extract the armors and files - string CemuSettings = File.ReadAllText(Properties.Settings.Default.bcmlLocation); - Dictionary settings = JsonConvert.DeserializeObject>(CemuSettings)!; - string GameDir = settings["game_dir"]; - string UpdateDir = settings["update_dir"]; - - // Get bcml mod path to save data in that folder - string bcmlPath = Properties.Settings.Default.bcmlLocation.Replace("settings.json", @"merged\content"); - string titleBGPath = @$"{UpdateDir}\Pack\TitleBG.pack"; + string titleBGPath = @$"{BcmlSettings.UpdateDir}\Pack\TitleBG.pack"; /* Instantiate objects */ // Create title bg object and load it's data @@ -158,7 +141,7 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files /************ Player model ************/ /* Modify Link models */ // Create outputModel - if(!File.Exists($@"{bcmlPath}/Model/Jugador1ModelNameLongForASpecificReason.sbfres")) + if(!File.Exists($@"{BcmlSettings.MergedDir}/Model/Jugador1ModelNameLongForASpecificReason.sbfres")) { byte[] LinkDecompressed = Yaz0.Decompress(titleBG.LoadedData["Model/Link.sbfres"].ToArray()); BfresFile outputModel = new BfresFile(new MemoryStream(LinkDecompressed)); @@ -184,7 +167,7 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files outputModel.Models[2].Shapes.Clear(); /* Get armor models */ - foreach (string path in Directory.GetFiles(@$"{UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && !file.Contains("Tex"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && !file.Contains("Tex"))) { BfresFile armorFile = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes(path)))); @@ -211,18 +194,18 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files outputModel.ToBinary(ms); } - File.WriteAllBytes($@"{bcmlPath}/Model/Jugador1ModelNameLongForASpecificReason.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); + File.WriteAllBytes($@"{BcmlSettings.MergedDir}/Model/Jugador1ModelNameLongForASpecificReason.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); } /************ Player textures ************/ /* Modify Link's tex1 file */ - if(!File.Exists($@"{bcmlPath}/Model/Jugador1ModelNameLongForASpecificReason.Tex1.sbfres")) + if(!File.Exists($@"{BcmlSettings.MergedDir}/Model/Jugador1ModelNameLongForASpecificReason.Tex1.sbfres")) { - byte[] LinkDecompressed = Yaz0.Decompress(File.ReadAllBytes($@"{GameDir}\Model\Link.Tex1.sbfres")); + byte[] LinkDecompressed = Yaz0.Decompress(File.ReadAllBytes($@"{BcmlSettings.GameDir}\Model\Link.Tex1.sbfres")); BfresFile outputTexture = new BfresFile(new MemoryStream(LinkDecompressed)); /* Get armor models from game dir*/ - foreach (string path in Directory.GetFiles(@$"{GameDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && file.Contains("Tex1"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.GameDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && file.Contains("Tex1"))) { BfresFile armorFile = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes(path)))); @@ -233,7 +216,7 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files } /* Get armor models from update dir*/ - foreach (string path in Directory.GetFiles(@$"{UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && file.Contains("Tex1"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && file.Contains("Tex1"))) { BfresFile armorFile = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes(path)))); @@ -250,17 +233,17 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files outputTexture.ToBinary(ms); } - File.WriteAllBytes($@"{bcmlPath}/Model/Jugador1ModelNameLongForASpecificReason.Tex1.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); + File.WriteAllBytes($@"{BcmlSettings.MergedDir}/Model/Jugador1ModelNameLongForASpecificReason.Tex1.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); } /* Modify Link's tex2 file */ - if (!File.Exists($@"{bcmlPath}/Model/Jugador1ModelNameLongForASpecificReason.Tex2.sbfres")) + if (!File.Exists($@"{BcmlSettings.MergedDir}/Model/Jugador1ModelNameLongForASpecificReason.Tex2.sbfres")) { byte[] LinkDecompressed = Yaz0.Decompress(titleBG.LoadedData["Model/Link.Tex2.sbfres"].ToArray()); BfresFile outputTexture = new BfresFile(new MemoryStream(LinkDecompressed)); /* Get armor models */ - foreach (string path in Directory.GetFiles(@$"{UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && file.Contains("Tex2"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.UpdateDir}\Model\").Where(file => Path.GetFileName(file).StartsWith("Armor_") && file.Contains("Tex2"))) { BfresFile armorFile = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes(path)))); @@ -285,7 +268,7 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files outputTexture.ToBinary(ms); } - File.WriteAllBytes($@"{bcmlPath}/Model/Jugador1ModelNameLongForASpecificReason.Tex2.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); + File.WriteAllBytes($@"{BcmlSettings.MergedDir}/Model/Jugador1ModelNameLongForASpecificReason.Tex2.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); } } @@ -335,17 +318,10 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files public static void CleanAnimations() { /* Obtaining the data */ - // Get game folders so that we can extract the armors and files - string CemuSettings = File.ReadAllText(Properties.Settings.Default.bcmlLocation); - Dictionary settings = JsonConvert.DeserializeObject>(CemuSettings)!; - string GameDir = settings["game_dir"]; - // Get bcml mod path to save data in that folder - string bcmlPath = Properties.Settings.Default.bcmlLocation.Replace("settings.json", @"merged\content"); - - if (!File.Exists($@"{bcmlPath}/Model/Player_Animation_NoFace.sbfres")) + if (!File.Exists($@"{BcmlSettings.MergedDir}/Model/Player_Animation_NoFace.sbfres")) { - var res = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes($@"{GameDir}\Model\Player_Animation.sbfres")))); + var res = new BfresFile(new MemoryStream(Yaz0.Decompress(File.ReadAllBytes($@"{BcmlSettings.GameDir}\Model\Player_Animation.sbfres")))); res.Name = "Player_Animation_NoFace"; List bannedBones = new List() { @@ -372,31 +348,15 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files res.ToBinary(ms); } - File.WriteAllBytes($@"{bcmlPath}/Model/Player_Animation_NoFace.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); + File.WriteAllBytes($@"{BcmlSettings.MergedDir}/Model/Player_Animation_NoFace.sbfres", Yaz0.Compress(ms.ToArray()).ToArray()); } } - public static void WrapperTests() - { - //string bcmlPath = Properties.Settings.Default.bcmlLocation.Replace("settings.json", "merged\\content"); - - //string titleBGPath = $"{bcmlPath}\\Pack\\TitleBG.pack"; - - //TitleBG titleBG = new TitleBG(titleBGPath); - //ActorPack gameRomPlayer = titleBG.Actor.Pack.Actors.File("GameROMPlayer"); - - //gameRomPlayer.ModelList.File("Player_Link").LoadedData.ModifyModel("TestNew", "Link"); - //gameRomPlayer.ASList.File("Player").LoadedData.ModifyAnimation(true); - - //titleBG.Save(true); - } - public static void ModifyGameROMPlayerModel(string folder, string model, bool isNotLink, string bumiiPath = null) { List> filesToModify = new List>(); - string bcmlPath = Properties.Settings.Default.bcmlLocation.Replace("settings.json", @"merged\content"); - string titleBGPath = @$"{bcmlPath}\Pack\TitleBG.pack"; + string titleBGPath = @$"{BcmlSettings.MergedDir}\Pack\TitleBG.pack"; TitleBG titleBG = new TitleBG(titleBGPath); ActorPack gameRomPlayer = titleBG.Actor.Pack.Actors.File("GameROMPlayer"); @@ -426,13 +386,13 @@ namespace Breath_of_the_Wild_Multiplayer.Source_files filesToModify.Add(titleBG.Actor.Pack.Actors.File("Armor_Default_Extra_00").ModelList.Files()[0].ModifyModel(armorFolder, armorModelBase.Replace("##", "00"))); filesToModify.Add(titleBG.Actor.Pack.Actors.File("Armor_Default_Extra_01").ModelList.Files()[0].ModifyModel(armorFolder, armorModelBase.Replace("##", "01"))); - ActorPack pauseMenuActor = new ActorPack(@$"{bcmlPath}\Actor\Pack\PauseMenuPlayer.sbactorpack"); + ActorPack pauseMenuActor = new ActorPack(@$"{BcmlSettings.MergedDir}\Actor\Pack\PauseMenuPlayer.sbactorpack"); filesToModify.Add(pauseMenuActor.ModelList.Files()[0].ModifyModel(folder, model)); filesToModify.Add(pauseMenuActor.ASList.Files()[0].ModifyAnimation(isNotLink)); List armors = new List(); - foreach (string path in Directory.GetFiles(@$"{bcmlPath}\Actor\Pack\").Where(file => Path.GetFileName(file).StartsWith("Armor_"))) + foreach (string path in Directory.GetFiles(@$"{BcmlSettings.MergedDir}\Actor\Pack\").Where(file => Path.GetFileName(file).StartsWith("Armor_"))) { ActorPack armorActor = new ActorPack(path); ModelList modelListFile = armorActor.ModelList.Files()[0]; diff --git a/buildWPF.py b/buildWPF.py index 6bbeb3d..b1fb5dd 100644 --- a/buildWPF.py +++ b/buildWPF.py @@ -2,6 +2,8 @@ import subprocess from shutil import copy, rmtree, copytree import os +# Make sure to have msbuild in your PATH + abovePath = "\\".join(os.getcwd().split("\\")[:-1]) WPFProject = r"WPF .NET 6\Breath of the Wild Multiplayer"