/// <summary> /// Loads stringID set definitions from an XML container. /// </summary> /// <param name="container">The XML container to load set definitions from.</param> /// <param name="resolver">The StringIDSetResolver to store sets to.</param> public static void LoadAllStringIDSets(XContainer container, StringIDSetResolver resolver) { // Make sure there is a root <layouts> tag XContainer stringIDContainer = container.Element("stringIDs"); if (stringIDContainer == null) throw new ArgumentException("Invalid stringID definition document"); // Process <set> elements foreach (XElement element in stringIDContainer.Elements("set")) ProcessSetElement(element, resolver); }
private static void ProcessSetElement(XElement element, StringIDSetResolver resolver) { // Get the set's ID from the "id" attribute XAttribute idAttribute = element.Attribute("id"); if (idAttribute == null) throw new ArgumentException("StringID set tags must have an \"id\" attribute"); short id = (short)ParseNumber(idAttribute.Value); // Get the set's min index from the "min" attribute (optional, defaults to 0) ushort min = 0; XAttribute minAttribute = element.Attribute("min"); if (minAttribute != null) min = (ushort)ParseNumber(minAttribute.Value); // Get the set's global index from the "startIndex" attribute XAttribute startIndexAttribute = element.Attribute("startIndex"); if (startIndexAttribute == null) throw new ArgumentException("String id set tags must have a \"startIndex\" attribute"); int globalIndex = ParseNumber(startIndexAttribute.Value); // Register the set resolver.RegisterSet(id, min, globalIndex); }
/// <summary> /// Loads all of the structure layouts defined for a specified build. /// </summary> /// <param name="buildName">The build version to load structure layouts for.</param> /// <returns>The build's information.</returns> public BuildInformation LoadBuild(string buildName) { // Build tags have the format: // <build name="(name of this build of the engine)" // version="(build version string)" // localeKey="(key used to decrypt the locales)" // Optional // requiresTaglist="bool indication if the build requires a taglist)" // Optional // headerSize="(size of the header, in hex)" // filename="(filename containing layouts)" /> // // Just find the first build tag whose version matches and load its file. XElement buildElement = _builds.Elements("build").FirstOrDefault(e => e.Attribute("version") != null && e.Attribute("version").Value == buildName); if (buildElement == null) return null; XAttribute gameNameAttrib = buildElement.Attribute("name"); XAttribute localeKeyAttrib = buildElement.Attribute("localeKey"); XAttribute stringidKeyAttrib = buildElement.Attribute("stringidKey"); XAttribute stringidModifiersAttrib = buildElement.Attribute("stringidModifiers"); // NOTE: Deprecated - use stringidDefinitions instead! XAttribute stringidDefinitionsAttrib = buildElement.Attribute("stringidDefinitions"); XAttribute filenameKeyAttrib = buildElement.Attribute("filenameKey"); XAttribute headerSizeAttrib = buildElement.Attribute("headerSize"); XAttribute loadStringsAttrib = buildElement.Attribute("loadStrings"); XAttribute shortNameAttrib = buildElement.Attribute("shortName"); XAttribute filenameAttrib = buildElement.Attribute("filename"); XAttribute localeSymbolsAttrib = buildElement.Attribute("localeSymbols"); XAttribute pluginFolderAttrib = buildElement.Attribute("pluginFolder"); XAttribute scriptDefinitionsAttrib = buildElement.Attribute("scriptDefinitions"); XAttribute localeAlignmentAttrib = buildElement.Attribute("localeAlignment"); if (gameNameAttrib == null || filenameAttrib == null || headerSizeAttrib == null || shortNameAttrib == null || pluginFolderAttrib == null) return null; bool loadStrings = true; string localeKey = null; string stringidKey = null; string filenameKey = null; string localeSymbols = null; string scriptOpcodes = null; int localeAlignment = 0x1000; int headerSize = ParseNumber(headerSizeAttrib.Value); if (filenameKeyAttrib != null) filenameKey = filenameKeyAttrib.Value; if (localeSymbolsAttrib != null) localeSymbols = localeSymbolsAttrib.Value; if (stringidKeyAttrib != null) stringidKey = stringidKeyAttrib.Value; if (localeKeyAttrib != null) localeKey = localeKeyAttrib.Value; if (loadStringsAttrib != null) loadStrings = Convert.ToBoolean(loadStringsAttrib.Value); if (scriptDefinitionsAttrib != null) scriptOpcodes = _basePath + @"Scripting\" + scriptDefinitionsAttrib.Value; if (localeAlignmentAttrib != null) localeAlignment = ParseNumber(localeAlignmentAttrib.Value); // StringID Modifers, this is a bitch IStringIDResolver stringIdResolver = null; if (stringidModifiersAttrib != null) { StringIDModifierResolver modifierResolver = new StringIDModifierResolver(); stringIdResolver = modifierResolver; string[] sets = stringidModifiersAttrib.Value.Split('|'); foreach (string set in sets) { string[] parts = set.Split(','); /* Format: * Identifier * Modifier * MathSymbol (+/-) * Direction (>/<) */ int identifier = int.Parse(parts[0].Replace("0x", ""), NumberStyles.AllowHexSpecifier); int modifier = int.Parse(parts[1].Replace("0x", ""), NumberStyles.AllowHexSpecifier); bool isAddition = parts[2] == "+"; bool isGreaterThan = parts[3] == ">"; modifierResolver.AddModifier(identifier, modifier, isGreaterThan, isAddition); } } else if (stringidDefinitionsAttrib != null) { StringIDSetResolver setResolver = new StringIDSetResolver(); stringIdResolver = setResolver; XDocument stringIdDocument = XDocument.Load(_basePath + @"StringIDs\" + stringidDefinitionsAttrib.Value); StringIDSetLoader.LoadAllStringIDSets(stringIdDocument, setResolver); } else { // Use a blank modifier stringIdResolver = new StringIDModifierResolver(); } BuildInformation info = new BuildInformation(gameNameAttrib.Value, localeKey, stringidKey, stringIdResolver, filenameKey, headerSize, loadStrings, filenameAttrib.Value, shortNameAttrib.Value, pluginFolderAttrib.Value, scriptOpcodes, localeAlignment); XDocument layoutDocument = XDocument.Load(_basePath + filenameAttrib.Value); LoadAllLayouts(layoutDocument, info); if (localeSymbols != null) { XDocument localeSymbolDocument = XDocument.Load(_basePath + @"LocaleSymbols\" + localeSymbols); LoadAllLocaleSymbols(localeSymbolDocument, info); } return info; }