private static XmlNode GetEntryNode(XmlNodeList nodes, MetaStructureEntryInfo_s entry) { foreach (XmlNode node in nodes) { if (GetHash(node.Name) == (uint)entry.EntryNameHash) { return(node); } } return(null); }
private static void TraverseArray(XmlNode node, MetaBuilder mb, MetaStructureEntryInfo_s arrEntry, int offset, ArrayResults results) { switch (arrEntry.DataType) { case MetaStructureEntryDataType.Structure: { results.Structures[offset] = TraverseArrayStructure(node, mb, arrEntry.ReferenceKey); break; } case MetaStructureEntryDataType.StructurePointer: { results.StructurePointers[offset] = TraverseArrayStructurePointer(node, mb); break; } case MetaStructureEntryDataType.UnsignedInt: { results.UInts[offset] = TraverseRawUIntArray(node, mb); break; } case MetaStructureEntryDataType.UnsignedShort: { results.UShorts[offset] = TraverseRawUShortArray(node, mb); break; } case MetaStructureEntryDataType.UnsignedByte: { results.UBytes[offset] = TraverseRawUByteArray(node, mb); break; } case MetaStructureEntryDataType.Float: { results.Floats[offset] = TraverseRawFloatArray(node, mb); break; } case MetaStructureEntryDataType.Float_XYZ: { results.Float_XYZs[offset] = TraverseRawVector3Array(node, mb); break; } case MetaStructureEntryDataType.Hash: { results.Hashes[offset] = TraverseHashArray(node, mb); break; } case MetaStructureEntryDataType.CharPointer: { // TODO break; } case MetaStructureEntryDataType.DataBlockPointer: { // TODO break; } default: break; } }
private static byte[] Traverse(XmlNode node, MetaBuilder mb, MetaName type = 0, bool isRoot = false) { if (type == 0) { type = (MetaName)(uint)GetHash(node.Name); } var infos = MetaTypes.GetStructureInfo(type); if (infos != null) { byte[] data = new byte[infos.StructureSize]; var arrayResults = new ArrayResults(); arrayResults.Structures = new Dictionary <int, Array_Structure>(); arrayResults.StructurePointers = new Dictionary <int, Array_StructurePointer>(); arrayResults.UInts = new Dictionary <int, Array_uint>(); arrayResults.UShorts = new Dictionary <int, Array_ushort>(); arrayResults.UBytes = new Dictionary <int, Array_byte>(); arrayResults.Floats = new Dictionary <int, Array_float>(); arrayResults.Float_XYZs = new Dictionary <int, Array_Vector3>(); arrayResults.Hashes = new Dictionary <int, Array_uint>(); Array.Clear(data, 0, infos.StructureSize); MetaStructureEntryInfo_s arrEntry = new MetaStructureEntryInfo_s(); if (isRoot) { mb.EnsureBlock(type); } for (int i = 0; i < infos.Entries.Length; i++) { var entry = infos.Entries[i]; var cnode = GetEntryNode(node.ChildNodes, entry); if (entry.EntryNameHash == MetaName.ARRAYINFO) { arrEntry = entry; continue; } if (cnode == null) { continue; } switch (entry.DataType) { case MetaStructureEntryDataType.Array: { TraverseArray(cnode, mb, arrEntry, entry.DataOffset, arrayResults); break; } case MetaStructureEntryDataType.ArrayOfBytes: { GetParsedArrayOfBytes(cnode, data, entry, arrEntry); break; } case MetaStructureEntryDataType.ArrayOfChars: { int offset = entry.DataOffset; var split = Split(cnode.InnerText, 2); for (int j = 0; j < split.Length; j++) { byte val = Convert.ToByte(split[j], 16); data[offset] = val; offset += sizeof(byte); } break; } case MetaStructureEntryDataType.Boolean: { byte val = (cnode.Attributes["value"].Value == "false") ? (byte)0 : (byte)1; data[entry.DataOffset] = val; break; } case MetaStructureEntryDataType.ByteEnum: { byte val = Convert.ToByte(cnode.Attributes["value"].Value); data[entry.DataOffset] = val; break; } case MetaStructureEntryDataType.CharPointer: { if (!string.IsNullOrEmpty(cnode.InnerText)) { var ptr = mb.AddStringPtr(cnode.InnerText); var val = MetaTypes.ConvertToBytes(ptr); Buffer.BlockCopy(val, 0, data, entry.DataOffset, val.Length); } break; } case MetaStructureEntryDataType.DataBlockPointer: { // TODO break; } case MetaStructureEntryDataType.Float: { float val = FloatUtil.Parse(cnode.Attributes["value"].Value); Write(val, data, entry.DataOffset); break; } case MetaStructureEntryDataType.Float_XYZ: { float x = FloatUtil.Parse(cnode.Attributes["x"].Value); float y = FloatUtil.Parse(cnode.Attributes["y"].Value); float z = FloatUtil.Parse(cnode.Attributes["z"].Value); Write(x, data, entry.DataOffset); Write(y, data, entry.DataOffset + sizeof(float)); Write(z, data, entry.DataOffset + sizeof(float) * 2); break; } case MetaStructureEntryDataType.Float_XYZW: { float x = FloatUtil.Parse(cnode.Attributes["x"].Value); float y = FloatUtil.Parse(cnode.Attributes["y"].Value); float z = FloatUtil.Parse(cnode.Attributes["z"].Value); float w = FloatUtil.Parse(cnode.Attributes["w"].Value); Write(x, data, entry.DataOffset); Write(y, data, entry.DataOffset + sizeof(float)); Write(z, data, entry.DataOffset + sizeof(float) * 2); Write(w, data, entry.DataOffset + sizeof(float) * 3); break; } case MetaStructureEntryDataType.Hash: { var hash = GetHash(cnode.InnerText); Write(hash, data, entry.DataOffset); break; } case MetaStructureEntryDataType.IntEnum: case MetaStructureEntryDataType.IntFlags1: case MetaStructureEntryDataType.IntFlags2: { var _infos = MetaTypes.GetEnumInfo(entry.ReferenceKey); mb.AddEnumInfo(_infos.EnumNameHash); int val = GetEnumInt(entry.ReferenceKey, cnode.InnerText); Write(val, data, entry.DataOffset); break; } case MetaStructureEntryDataType.ShortFlags: { var _infos = MetaTypes.GetEnumInfo(entry.ReferenceKey); mb.AddEnumInfo(_infos.EnumNameHash); int val = GetEnumInt(entry.ReferenceKey, cnode.InnerText); Write((short)val, data, entry.DataOffset); break; } case MetaStructureEntryDataType.SignedByte: { var val = Convert.ToSByte(cnode.Attributes["value"].Value); data[entry.DataOffset] = (byte)val; break; } case MetaStructureEntryDataType.SignedInt: { var val = Convert.ToInt32(cnode.Attributes["value"].Value); Write(val, data, entry.DataOffset); break; } case MetaStructureEntryDataType.SignedShort: { var val = Convert.ToInt16(cnode.Attributes["value"].Value); Write(val, data, entry.DataOffset); break; } case MetaStructureEntryDataType.Structure: { var struc = Traverse(cnode, mb, entry.ReferenceKey); if (struc != null) { Buffer.BlockCopy(struc, 0, data, entry.DataOffset, struc.Length); } break; } case MetaStructureEntryDataType.StructurePointer: { // TODO break; } case MetaStructureEntryDataType.UnsignedByte: { var val = Convert.ToByte(cnode.Attributes["value"].Value); data[entry.DataOffset] = val; break; } case MetaStructureEntryDataType.UnsignedInt: { switch (entry.EntryNameHash) { case MetaName.color: { var val = Convert.ToUInt32(cnode.Attributes["value"].Value, 16); Write(val, data, entry.DataOffset); break; } default: { var val = Convert.ToUInt32(cnode.Attributes["value"].Value); Write(val, data, entry.DataOffset); break; } } break; } case MetaStructureEntryDataType.UnsignedShort: { var val = Convert.ToUInt16(cnode.Attributes["value"].Value); Write(val, data, entry.DataOffset); break; } default: break; } } arrayResults.WriteArrays(data); mb.AddStructureInfo(infos.StructureNameHash); if (isRoot) { mb.AddItem(type, data); } return(data); } return(null); }
private static void GetParsedArrayOfBytes(XmlNode node, byte[] data, MetaStructureEntryInfo_s entry, MetaStructureEntryInfo_s arrEntry) { int offset = entry.DataOffset; string[] split; switch (arrEntry.DataType) { default: split = Split(node.InnerText, 2); for (int j = 0; j < split.Length; j++) { byte val = Convert.ToByte(split[j], 16); data[offset] = val; offset += sizeof(byte); } break; case MetaStructureEntryDataType.SignedByte: split = node.InnerText.Split(); //split = Split(node.InnerText, 2); to read as unsplitted HEX for (int j = 0; j < split.Length; j++) { sbyte val = Convert.ToSByte(split[j], 10); data[offset] = (byte)val; offset += sizeof(sbyte); } break; case MetaStructureEntryDataType.UnsignedByte: split = node.InnerText.Split(); for (int j = 0; j < split.Length; j++) { byte val = Convert.ToByte(split[j], 10); data[offset] = val; offset += sizeof(byte); } break; case MetaStructureEntryDataType.SignedShort: split = node.InnerText.Split(); for (int j = 0; j < split.Length; j++) { short val = Convert.ToInt16(split[j], 10); Write(val, data, offset); offset += sizeof(short); } break; case MetaStructureEntryDataType.UnsignedShort: split = node.InnerText.Split(); for (int j = 0; j < split.Length; j++) { ushort val = Convert.ToUInt16(split[j], 10); Write(val, data, offset); offset += sizeof(ushort); } break; case MetaStructureEntryDataType.SignedInt: split = node.InnerText.Split(); for (int j = 0; j < split.Length; j++) { int val = Convert.ToInt32(split[j], 10); Write(val, data, offset); offset += sizeof(int); } break; case MetaStructureEntryDataType.UnsignedInt: split = node.InnerText.Split(); for (int j = 0; j < split.Length; j++) { uint val = Convert.ToUInt32(split[j], 10); Write(val, data, offset); offset += sizeof(uint); } break; case MetaStructureEntryDataType.Float: split = node.InnerText.Split(); for (int j = 0; j < split.Length; j++) { float val = FloatUtil.Parse(split[j]); Write(val, data, offset); offset += sizeof(float); } break; } }
private static void GetParsedArrayOfBytes(XmlNode node, byte[] data, MetaStructureEntryInfo_s entry, MetaStructureEntryInfo_s arrEntry) { int offset = entry.DataOffset; var ns = NumberStyles.Any; var ic = CultureInfo.InvariantCulture; var sa = new[] { ' ' }; var so = StringSplitOptions.RemoveEmptyEntries; var split = node.InnerText.Trim().Split(sa, so); //split = Split(node.InnerText, 2); to read as unsplitted HEX switch (arrEntry.DataType) { default: //expecting hex string. split = Split(node.InnerText, 2); for (int j = 0; j < split.Length; j++) { byte val = Convert.ToByte(split[j], 16); data[offset] = val; offset += sizeof(byte); } break; case MetaStructureEntryDataType.SignedByte: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { sbyte val; // = Convert.ToSByte(split[j], 10); if (sbyte.TryParse(split[j].Trim(), ns, ic, out val)) { data[offset] = (byte)val; offset += sizeof(sbyte); } } break; case MetaStructureEntryDataType.UnsignedByte: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { byte val; // = Convert.ToByte(split[j], 10); if (byte.TryParse(split[j].Trim(), ns, ic, out val)) { data[offset] = val; offset += sizeof(byte); } } break; case MetaStructureEntryDataType.SignedShort: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { short val; // = Convert.ToInt16(split[j], 10); if (short.TryParse(split[j].Trim(), ns, ic, out val)) { Write(val, data, offset); offset += sizeof(short); } } break; case MetaStructureEntryDataType.UnsignedShort: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { ushort val; // = Convert.ToUInt16(split[j], 10); if (ushort.TryParse(split[j].Trim(), ns, ic, out val)) { Write(val, data, offset); offset += sizeof(ushort); } } break; case MetaStructureEntryDataType.SignedInt: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { int val; // = Convert.ToInt32(split[j], 10); if (int.TryParse(split[j].Trim(), ns, ic, out val)) { Write(val, data, offset); offset += sizeof(int); } } break; case MetaStructureEntryDataType.UnsignedInt: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { uint val; // = Convert.ToUInt32(split[j], 10); if (uint.TryParse(split[j].Trim(), ns, ic, out val)) { Write(val, data, offset); offset += sizeof(uint); } } break; case MetaStructureEntryDataType.Float: //expecting space-separated array. for (int j = 0; j < split.Length; j++) { float val; // = FloatUtil.Parse(split[j]); if (FloatUtil.TryParse(split[j].Trim(), out val)) { Write(val, data, offset); offset += sizeof(float); } } break; } }