Esempio n. 1
0
        /// <summary>
        /// Patches the scenario file with reputation data
        /// </summary>
        private static string UpdateScenarioWithTechnologyData(string scenarioData, TechNodeInfo techNode)
        {
            var document = new XmlDocument();

            document.LoadXml(scenarioData);

            var configNodeData = Encoding.UTF8.GetString(techNode.Data, 0, techNode.NumBytes);

            var newNodeDoc = new XmlDocument();

            newNodeDoc.LoadXml(ConfigNodeXmlParser.ConvertToXml(configNodeData));

            var parentNode = document.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}");

            if (parentNode != null)
            {
                var newTechXmlNode = newNodeDoc.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='Tech']");
                if (newTechXmlNode != null)
                {
                    var importNode = document.ImportNode(newTechXmlNode, true);
                    parentNode.AppendChild(importNode);
                }
            }

            return(document.ToIndentedString());
        }
        /// <summary>
        /// Raw updates a vessel in the dictionary and takes care of the locking in case we received another vessel message type
        /// </summary>
        public static void RawConfigNodeInsertOrUpdate(Guid vesselId, string vesselDataInConfigNodeFormat)
        {
            Task.Run(() =>
            {
                lock (Semaphore.GetOrAdd(vesselId, new object()))
                {
                    var vesselAsXml = ConfigNodeXmlParser.ConvertToXml(vesselDataInConfigNodeFormat);

                    if (GeneralSettings.SettingsStore.ModControl)
                    {
                        var vesselParts = GetPartNames(vesselAsXml);
                        if (vesselParts != null)
                        {
                            var bannedParts = vesselParts.Except(ModFileSystem.ModControl.AllowedParts);
                            if (bannedParts.Any())
                            {
                                LunaLog.Warning($"Received a vessel with BANNED parts! {vesselId}");
                                return;
                            }
                        }
                    }

                    VesselStoreSystem.CurrentVesselsInXmlFormat.AddOrUpdate(vesselId, vesselAsXml, (key, existingVal) => vesselAsXml);
                }
            });
        }
        /// <summary>
        /// Patches the scenario file with strategy data
        /// </summary>
        private static string UpdateScenarioWithStrategyData(string scenarioData, StrategyInfo strategy)
        {
            var document = new XmlDocument();

            document.LoadXml(scenarioData);

            var strategiesList = document.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='STRATEGIES']");

            if (strategiesList != null)
            {
                var receivedStrategy = DeserializeAndImportNode(strategy.Data, strategy.NumBytes, document);
                if (receivedStrategy != null)
                {
                    var existingStrategy = strategiesList.SelectSingleNode($"{ConfigNodeXmlParser.ParentNode}[@name='STRATEGY']/" +
                                                                           $@"{ConfigNodeXmlParser.ValueNode}[@name='name' and text()=""{strategy.Name}""]/" +
                                                                           $"parent::{ConfigNodeXmlParser.ParentNode}[@name='STRATEGY']");
                    if (existingStrategy != null)
                    {
                        //Replace the existing stragegy value with the received one
                        existingStrategy.InnerXml = receivedStrategy.InnerXml;
                    }
                    else
                    {
                        var newStrategyNode = ConfigNodeXmlParser.CreateXmlNode("STRATEGY", document);
                        newStrategyNode.InnerXml = receivedStrategy.InnerXml;
                        strategiesList.AppendChild(newStrategyNode);
                    }
                }
            }

            return(document.ToIndentedString());
        }
Esempio n. 4
0
        private static XmlNode DeserializeAndImportNode(byte[] data, int numBytes, XmlDocument docToImportTo)
        {
            var auxDoc = new XmlDocument();

            auxDoc.LoadXml(ConfigNodeXmlParser.ConvertToXml(Encoding.UTF8.GetString(data, 0, numBytes)));
            var newXmlNode = auxDoc.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}");

            return(newXmlNode == null ? null : docToImportTo.ImportNode(newXmlNode, true));
        }
Esempio n. 5
0
 /// <summary>
 /// Raw updates a scenario in the dictionary
 /// </summary>
 public static void RawConfigNodeInsertOrUpdate(string scenarioModule, string scenarioDataInConfigNodeFormat)
 {
     Task.Run(() =>
     {
         lock (Semaphore.GetOrAdd(scenarioModule, new object()))
         {
             var scenarioAsXml = ConfigNodeXmlParser.ConvertToXml(scenarioDataInConfigNodeFormat);
             ScenarioStoreSystem.CurrentScenariosInXmlFormat.AddOrUpdate(scenarioModule, scenarioAsXml, (key, existingVal) => scenarioAsXml);
         }
     });
 }
Esempio n. 6
0
 /// <summary>
 /// Raw updates a vessel in the dictionary and takes care of the locking in case we received another vessel message type
 /// </summary>
 public static void RawConfigNodeInsertOrUpdate(Guid vesselId, string vesselDataInConfigNodeFormat)
 {
     Task.Run(() =>
     {
         lock (Semaphore.GetOrAdd(vesselId, new object()))
         {
             var vesselAsXml = ConfigNodeXmlParser.ConvertToXml(vesselDataInConfigNodeFormat);
             VesselStoreSystem.CurrentVesselsInXmlFormat.AddOrUpdate(vesselId, vesselAsXml, (key, existingVal) => vesselAsXml);
         }
     });
 }
        private static void SwitchToXmlAndBack(string filePath)
        {
            if (!File.Exists(filePath))
            {
                return;
            }

            var configNode       = File.ReadAllText(filePath);
            var xml              = ConfigNodeXmlParser.ConvertToXml(configNode);
            var backToConfigNode = ConfigNodeXmlParser.ConvertToConfigNode(xml);

            Assert.IsTrue(configNode.Equals(backToConfigNode), $"Error serializing config node. File: {Path.GetFileName(filePath)}");
        }
Esempio n. 8
0
        /// <summary>
        /// Patches the scenario file with reputation data
        /// </summary>
        private static string UpdateScenarioWithTechnologyData(string scenarioData, TechNodeInfo techNode)
        {
            var document = new XmlDocument();

            document.LoadXml(scenarioData);

            var configNodeData = Encoding.UTF8.GetString(techNode.Data, 0, techNode.NumBytes);

            var newNodeDoc = new XmlDocument();

            newNodeDoc.LoadXml(ConfigNodeXmlParser.ConvertToXml(configNodeData));

            var parentNode = document.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}");

            if (parentNode != null)
            {
                var newTechXmlNode = newNodeDoc.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='Tech']");
                if (newTechXmlNode != null)
                {
                    var existingNode = parentNode.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='Tech']" +
                                                                   $@"/{ConfigNodeXmlParser.ValueNode}[@name='id' and text()=""{techNode.Id}""]" +
                                                                   $"/parent::{ConfigNodeXmlParser.ParentNode}[@name='Tech']");

                    if (existingNode != null)
                    {
                        var parts = newTechXmlNode.SelectNodes($"{ConfigNodeXmlParser.ValueNode}[@name='part']");
                        if (parts != null)
                        {
                            foreach (var part in parts.Cast <XmlNode>())
                            {
                                var existingPart = existingNode.SelectSingleNode($@"{ConfigNodeXmlParser.ValueNode}[@name='part' and text()=""{part.InnerText}""]");
                                if (existingPart == null)
                                {
                                    var importNode = document.ImportNode(part, true);
                                    existingNode.AppendChild(importNode);
                                }
                            }
                        }
                    }
                    else
                    {
                        var importNode = document.ImportNode(newTechXmlNode, true);
                        parentNode.AppendChild(importNode);
                    }
                }
            }

            return(document.ToIndentedString());
        }
        /// <summary>
        /// Patches the scenario file with part purchase data
        /// </summary>
        private static string UpdateScenarioWithPartPurchaseData(string scenarioData, string techId, string partName)
        {
            var document = new XmlDocument();

            document.LoadXml(scenarioData);

            var techNode = document.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='Tech']" +
                                                     $@"/{ConfigNodeXmlParser.ValueNode}[@name='id' and text()=""{techId}""]" +
                                                     $"/parent::{ConfigNodeXmlParser.ParentNode}[@name='Tech']");

            if (techNode != null)
            {
                var newPart = ConfigNodeXmlParser.CreateXmlParameter("part", document);
                newPart.InnerXml = partName;

                techNode.AppendChild(newPart);
            }

            return(document.ToIndentedString());
        }
Esempio n. 10
0
        /// <summary>
        /// Patches the scenario file with reputation data
        /// </summary>
        private static string UpdateScenarioWithContractData(string scenarioData, ContractInfo[] contracts)
        {
            var document = new XmlDocument();

            document.LoadXml(scenarioData);

            var contractsList = document.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='CONTRACTS']");

            if (contractsList != null)
            {
                foreach (var contract in contracts)
                {
                    var receivedContract = DeserializeAndImportNode(contract.Data, contract.NumBytes, document);
                    if (receivedContract == null)
                    {
                        continue;
                    }

                    var existingContract = contractsList.SelectSingleNode($"{ConfigNodeXmlParser.ParentNode}[@name='CONTRACT']/" +
                                                                          $@"{ConfigNodeXmlParser.ValueNode}[@name='guid' and text()=""{contract.ContractGuid}""]/" +
                                                                          $"parent::{ConfigNodeXmlParser.ParentNode}[@name='CONTRACT']");
                    if (existingContract != null)
                    {
                        //Replace the existing contract values with the received one
                        existingContract.InnerXml = receivedContract.InnerXml;
                    }
                    else
                    {
                        var newContractNode = ConfigNodeXmlParser.CreateXmlNode("CONTRACT", document);
                        newContractNode.InnerXml = receivedContract.InnerXml;
                        contractsList.AppendChild(newContractNode);
                    }
                }
            }

            return(document.ToIndentedString());
        }
        /// <summary>
        /// Patches the scenario file with achievement data
        /// </summary>
        private static string UpdateScenarioWithAchievementData(string scenarioData, AchievementInfo[] achievements)
        {
            var document = new XmlDocument();

            document.LoadXml(scenarioData);

            var progressList = document.SelectSingleNode($"/{ConfigNodeXmlParser.StartElement}/{ConfigNodeXmlParser.ParentNode}[@name='Progress']");

            if (progressList != null)
            {
                foreach (var achievement in achievements)
                {
                    var receivedAchievementXmlNode = DeserializeAndImportNode(achievement.Data, achievement.NumBytes, document);
                    if (receivedAchievementXmlNode == null)
                    {
                        continue;
                    }

                    var existingAchievement = progressList.SelectSingleNode($"{ConfigNodeXmlParser.ParentNode}[@name='{achievement.Id}']");
                    if (existingAchievement != null)
                    {
                        //Replace the existing contract values with the received one
                        existingAchievement.InnerXml = receivedAchievementXmlNode.InnerXml;
                    }
                    else
                    {
                        var newAchievement = ConfigNodeXmlParser.CreateXmlNode(achievement.Id, document);
                        newAchievement.InnerXml = receivedAchievementXmlNode.InnerXml;

                        progressList.AppendChild(newAchievement);
                    }
                }
            }

            return(document.ToIndentedString());
        }
Esempio n. 12
0
 /// <summary>
 /// Returns a XML vessel in the standard KSP format
 /// </summary>
 public static string GetVesselInConfigNodeFormat(Guid vesselId)
 {
     return(CurrentVesselsInXmlFormat.TryGetValue(vesselId, out var vesselInXmlFormat) ?
            ConfigNodeXmlParser.ConvertToConfigNode(vesselInXmlFormat) : null);
 }
Esempio n. 13
0
        public static void GenerateUniverse(string saveName)
        {
            var universeFolder = CommonUtil.CombinePaths(MainSystem.KspPath, "Universe");

            if (Directory.Exists(universeFolder))
            {
                Directory.Delete(universeFolder, true);
            }

            var saveFolder = CommonUtil.CombinePaths(SavesFolder, saveName);

            if (!Directory.Exists(saveFolder))
            {
                LunaLog.Log($"[LMP]: Failed to generate a LMP universe for '{saveName}', Save directory doesn't exist");
                LunaScreenMsg.PostScreenMessage($"Failed to generate a LMP universe for '{saveName}', Save directory doesn't exist", 5f,
                                                ScreenMessageStyle.UPPER_CENTER);
                return;
            }

            var persistentFile = CommonUtil.CombinePaths(saveFolder, "persistent.sfs");

            if (!File.Exists(persistentFile))
            {
                LunaLog.Log($"[LMP]: Failed to generate a LMP universe for '{saveName}', persistent.sfs doesn't exist");
                LunaScreenMsg.PostScreenMessage($"Failed to generate a LMP universe for '{saveName}', persistent.sfs doesn't exist", 5f,
                                                ScreenMessageStyle.UPPER_CENTER);
                return;
            }

            Directory.CreateDirectory(universeFolder);
            var vesselFolder = CommonUtil.CombinePaths(universeFolder, "Vessels");

            Directory.CreateDirectory(vesselFolder);
            var scenarioFolder = CommonUtil.CombinePaths(universeFolder, "Scenarios");

            Directory.CreateDirectory(scenarioFolder);
            var kerbalFolder = CommonUtil.CombinePaths(universeFolder, "Kerbals");

            Directory.CreateDirectory(kerbalFolder);

            //Load game data
            var persistentData = ConfigNode.Load(persistentFile);

            if (persistentData == null)
            {
                LunaLog.Log($"[LMP]: Failed to generate a LMP universe for '{saveName}', failed to load persistent data");
                LunaScreenMsg.PostScreenMessage($"Failed to generate a LMP universe for '{saveName}', failed to load persistent data", 5f, ScreenMessageStyle.UPPER_CENTER);
                return;
            }

            var gameData = persistentData.GetNode("GAME");

            if (gameData == null)
            {
                LunaLog.Log($"[LMP]: Failed to generate a LMP universe for '{saveName}', failed to load game data");
                LunaScreenMsg.PostScreenMessage($"Failed to generate a LMP universe for '{saveName}', failed to load game data", 5f,
                                                ScreenMessageStyle.UPPER_CENTER);
                return;
            }

            //Save vessels
            var flightState = gameData.GetNode("FLIGHTSTATE");

            if (flightState == null)
            {
                LunaLog.Log($"[LMP]: Failed to generate a LMP universe for '{saveName}', failed to load flight state data");
                LunaScreenMsg.PostScreenMessage($"Failed to generate a LMP universe for '{saveName}', failed to load flight state data", 5f,
                                                ScreenMessageStyle.UPPER_CENTER);
                return;
            }

            var vesselNodes = flightState.GetNodes("VESSEL");

            if (vesselNodes != null)
            {
                foreach (var cn in vesselNodes)
                {
                    var vesselId = Common.ConvertConfigStringToGuidString(cn.GetValue("pid"));
                    LunaLog.Log($"[LMP]: Saving vessel {vesselId}, Name: {cn.GetValue("name")}");

                    var xmlData = ConfigNodeXmlParser.ConvertToXml(Encoding.UTF8.GetString(ConfigNodeSerializer.Serialize(cn)));
                    File.WriteAllText(CommonUtil.CombinePaths(vesselFolder, $"{vesselId}.xml"), xmlData);
                }
            }

            //Save scenario data
            var scenarioNodes = gameData.GetNodes("SCENARIO");

            if (scenarioNodes != null)
            {
                foreach (var cn in scenarioNodes)
                {
                    var scenarioName = cn.GetValue("name");
                    if (string.IsNullOrEmpty(scenarioName))
                    {
                        continue;
                    }

                    LunaLog.Log($"[LMP]: Saving scenario: {scenarioName}");

                    var xmlData = ConfigNodeXmlParser.ConvertToXml(Encoding.UTF8.GetString(ConfigNodeSerializer.Serialize(cn)));
                    File.WriteAllText(CommonUtil.CombinePaths(scenarioFolder, $"{scenarioName}.xml"), xmlData);
                }
            }

            //Save kerbal data
            var kerbalNodes = gameData.GetNode("ROSTER").GetNodes("KERBAL");

            if (kerbalNodes != null)
            {
                foreach (var cn in kerbalNodes)
                {
                    var kerbalName = cn.GetValue("name");
                    LunaLog.Log($"[LMP]: Saving kerbal: {kerbalName}");

                    cn.Save(CommonUtil.CombinePaths(kerbalFolder, $"{kerbalName}.txt"));
                }
            }

            LunaLog.Log($"[LMP]: Generated KSP_folder/Universe from {saveName}");
            LunaScreenMsg.PostScreenMessage($"Generated KSP_folder/Universe from {saveName}", 5f, ScreenMessageStyle.UPPER_CENTER);
        }
 /// <summary>
 /// Returns a XML scenario in the standard KSP format
 /// </summary>
 public static string GetScenarioInConfigNodeFormat(string scenarioName)
 {
     return(CurrentScenariosInXmlFormat.TryGetValue(scenarioName, out var scenarioInXmlFormat) ?
            ConfigNodeXmlParser.ConvertToConfigNode(scenarioInXmlFormat) : null);
 }