private void DumpTag(NbtTag tag, int level, StreamWriter writer) { for (var index = 0; index < level; index++) writer.Write(" "); writer.Write(tag.Name); writer.Write(" ["); writer.Write(tag.GetType().Name); writer.Write("]: "); if (tag is NbtCompound) { writer.WriteLine("..."); foreach (var name in ((NbtCompound)tag).Names) { var value = tag[name]; this.DumpTag(value, level + 1, writer); } } else if (tag is NbtList) { writer.WriteLine("..."); foreach (var item in (NbtList)tag) this.DumpTag(item, level + 1, writer); } else writer.WriteLine(tag); }
public object Deserialize(NbtTag value) { if (value is NbtByte) return ((NbtByte)value).Value; else if (value is NbtByteArray) return ((NbtByteArray)value).Value; else if (value is NbtDouble) return ((NbtDouble)value).Value; else if (value is NbtFloat) return ((NbtFloat)value).Value; else if (value is NbtInt) return ((NbtInt)value).Value; else if (value is NbtIntArray) return ((NbtIntArray)value).Value; else if (value is NbtLong) return ((NbtLong)value).Value; else if (value is NbtShort) return ((NbtShort)value).Value; else if (value is NbtString) return ((NbtString)value).Value; else if(value is NbtCompound) { var compound = value as NbtCompound; var properties = Type.GetProperties().Where(p => !Attribute.GetCustomAttributes(p, typeof(NbtIgnoreAttribute)).Any()); var resultObject = Activator.CreateInstance(Type); foreach (var property in properties) { if (!property.CanWrite) continue; string name = property.Name; var nameAttributes = Attribute.GetCustomAttributes(property, typeof(TagNameAttribute)); if (nameAttributes.Length != 0) name = ((TagNameAttribute)nameAttributes[0]).Name; var node = compound.Tags.SingleOrDefault(a => a.Name == name); if (node == null) continue; var data = new NbtSerializer(property.PropertyType).Deserialize(node); if (property.PropertyType == typeof(bool) && data is byte) data = (byte)data == 1; property.SetValue(resultObject, data, null); } return resultObject; } throw new NotSupportedException("The node type '" + value.GetType() + "' is not supported."); }
public object Deserialize(NbtTag value, bool skipInterfaceCheck = false) { if (!skipInterfaceCheck && typeof(INbtSerializable).IsAssignableFrom(Type)) { var instance = (INbtSerializable)Activator.CreateInstance(Type); instance.Deserialize(value); return instance; } if (value is NbtByte) return ((NbtByte)value).Value; else if (value is NbtByteArray) return ((NbtByteArray)value).Value; else if (value is NbtDouble) return ((NbtDouble)value).Value; else if (value is NbtFloat) return ((NbtFloat)value).Value; else if (value is NbtInt) return ((NbtInt)value).Value; else if (value is NbtIntArray) return ((NbtIntArray)value).Value; else if (value is NbtLong) return ((NbtLong)value).Value; else if (value is NbtShort) return ((NbtShort)value).Value; else if (value is NbtString) return ((NbtString)value).Value; else if (value is NbtList) { var list = (NbtList)value; var type = typeof(object); if (list.ListType == NbtTagType.Byte) type = typeof(byte); else if (list.ListType == NbtTagType.ByteArray) type = typeof(byte[]); else if (list.ListType == NbtTagType.Compound) { if (Type.IsArray) type = Type.GetElementType(); else type = typeof(object); } else if (list.ListType == NbtTagType.Double) type = typeof(double); else if (list.ListType == NbtTagType.Float) type = typeof(float); else if (list.ListType == NbtTagType.Int) type = typeof(int); else if (list.ListType == NbtTagType.IntArray) type = typeof(int[]); else if (list.ListType == NbtTagType.Long) type = typeof(long); else if (list.ListType == NbtTagType.Short) type = typeof(short); else if (list.ListType == NbtTagType.String) type = typeof(string); else throw new NotSupportedException("The NBT list type '" + list.TagType + "' is not supported."); var array = Array.CreateInstance(type, list.Count); var innerSerializer = new NbtSerializer(type); for (int i = 0; i < array.Length; i++) array.SetValue(innerSerializer.Deserialize(list[i]), i); return array; } else if(value is NbtCompound) { var compound = value as NbtCompound; var properties = Type.GetProperties().Where(p => !Attribute.GetCustomAttributes(p, typeof(NbtIgnoreAttribute)).Any()); var resultObject = Activator.CreateInstance(Type); foreach (var property in properties) { if (!property.CanWrite) continue; string name = property.Name; var nameAttributes = Attribute.GetCustomAttributes(property, typeof(TagNameAttribute)); if (nameAttributes.Length != 0) name = ((TagNameAttribute)nameAttributes[0]).Name; var node = compound.Tags.SingleOrDefault(a => a.Name == name); if (node == null) continue; object data; if (typeof(INbtSerializable).IsAssignableFrom(property.PropertyType)) { data = Activator.CreateInstance(property.PropertyType); ((INbtSerializable)data).Deserialize(node); } else data = new NbtSerializer(property.PropertyType).Deserialize(node); // Some manual casting for edge cases if (property.PropertyType == typeof(bool) && data is byte) data = (byte)data == 1; if (property.PropertyType == typeof(sbyte) && data is byte) data = (sbyte)(byte)data; property.SetValue(resultObject, data, null); } return resultObject; } throw new NotSupportedException("The node type '" + value.GetType() + "' is not supported."); }