示例#1
0
        private SerializedClass DeserializeClass(BinaryReader reader)
        {
            var value = new SerializedClass(DeserializeDefaults(reader));
            var count = reader.ReadInt32();

            for (int i = 0; i < count; i++)
            {
                var name = reader.ReadString();
                var mode = (ESerializableMode)reader.ReadInt32();
                switch (mode)
                {
                case ESerializableMode.Primitive:
                    value.Add(name, DeserializePrimitive(reader));
                    break;

                case ESerializableMode.Enum:
                    value.Add(name, DeserializeEnum(reader));
                    break;

                case ESerializableMode.List:
                    value.Add(name, DeserializeList(reader));
                    break;

                case ESerializableMode.Class:
                    value.Add(name, DeserializeClass(reader));
                    break;

                default:
                    break;
                }
            }

            return(value);
        }
        private SerializedClass SerializeClass(object value, Type valueType)
        {
            if (value == null)
            {
                return(new SerializedClass(GetNextID(), valueType.AssemblyQualifiedName)
                {
                    IsNull = true
                });
            }

            if (value is UnityEngine.Object)
            {
                var result = false;
                var fa     = new FakeAsset((UnityEngine.Object)value, out result);
                if (result)
                {
                    return(SerializeClass(fa, typeof(FakeAsset)));
                }
                else
                {
                    return(new SerializedClass(GetNextID(), valueType.AssemblyQualifiedName)
                    {
                        IsNull = true
                    });
                }
            }

            var obj = new SerializedClass(GetNextID(), valueType.AssemblyQualifiedName);

            if (Compare(value, valueType, ref obj.ID))
            {
                obj.IsReference = true;
                return(obj);
            }
            else
            {
                AddToComparables(obj, value, valueType);
            }

            var fields = SerializationHelper.GetFields(valueType, BindingFlags.Instance | BindingFlags.FlattenHierarchy | BindingFlags.Public | BindingFlags.NonPublic)
                         .Where(f =>
                                (f.IsPublic && f.GetCustomAttributes(typeof(IgnoreSerializationAttribute), false).Length == 0) ||
                                (f.IsPrivate && f.GetCustomAttributes(typeof(RequireSerializationAttribute), false).Length == 1))
                         .OrderBy(f => f.Name).ToList();

            var properties = SerializationHelper.GetProperties(valueType, BindingFlags.Instance | BindingFlags.FlattenHierarchy | BindingFlags.Public | BindingFlags.NonPublic)
                             .Where(p => p.CanRead && p.CanWrite)
                             .Where(p => p.GetCustomAttributes(typeof(IgnoreSerializationAttribute), false).Length == 0)
                             .OrderBy(p => p.Name).ToList();

            try {
                for (int i = 0; i < fields.Count; i++)
                {
                    var field  = fields[i];
                    var type   = field.FieldType;
                    var tValue = field.GetValue(value);
                    var fname  = string.Format("{0}|{1}", field.Name, i);

                    if (type == typeof(object) && tValue != null)
                    {
                        type = tValue.GetType();
                    }

                    if ((type.ToString() == "System.MonoType" && tValue != null) || type == typeof(Type))
                    {
                        var t = (Type)tValue;
                        var v = "";
                        try {
                            v = t.AssemblyQualifiedName;
                        } catch (Exception) { }
                        obj.Add(fname, SerializeClass(new FakeType(v), typeof(FakeType)));
                    }
                    else if (type.IsArray())
                    {
                        obj.Add(fname, SerializeList(tValue, type));
                    }
                    else if (type.IsEnum)
                    {
                        obj.Add(fname, SerializeEnum(tValue, type));
                    }
                    else if (type.IsValueType && !type.IsPrimitive)
                    {
                        if (type == typeof(decimal))
                        {
                            obj.Add(fname, SerializePrimitive(tValue, type));
                        }
                        else
                        {
                            obj.Add(fname, SerializeClass(tValue, type));
                        }
                    }
                    else if (type.IsValueType)
                    {
                        obj.Add(fname, SerializePrimitive(tValue, type));
                    }
                    else if (type.IsClass)
                    {
                        if (type == typeof(string))
                        {
                            obj.Add(fname, SerializePrimitive(tValue, type));
                        }
                        else if (type.IsList())
                        {
                            obj.Add(fname, SerializeList(tValue, type));
                        }
                        else
                        {
                            obj.Add(fname, SerializeClass(tValue, type));
                        }
                    }
                }

                for (int i = 0; i < properties.Count; i++)
                {
                    var property = properties[i];
                    var type     = property.PropertyType;
                    if (property.GetIndexParameters().Length > 0)
                    {
                        continue;
                    }
                    var tValue = property.GetValue(value, null);
                    var pname  = string.Format("{0}|{1}", property.Name, i);

                    if (type == typeof(object) && tValue != null)
                    {
                        type = tValue.GetType();
                    }

                    if (type.ToString() == "System.MonoType" && tValue != null)
                    {
                        var t = (Type)tValue;
                        var v = "";
                        try {
                            v = t.AssemblyQualifiedName;
                        } catch (Exception) { }
                        obj.Add(pname, SerializeClass(new FakeType(v), typeof(FakeType)));
                    }
                    else if (type.IsArray())
                    {
                        obj.Add(pname, SerializeList(tValue, type));
                    }
                    else if (type.IsEnum)
                    {
                        obj.Add(pname, SerializeEnum(tValue, type));
                    }
                    else if (type.IsValueType && !type.IsPrimitive)
                    {
                        if (type == typeof(double))
                        {
                            obj.Add(pname, SerializePrimitive(tValue, type));
                        }
                        else
                        {
                            obj.Add(pname, SerializeClass(tValue, type));
                        }
                    }
                    else if (type.IsValueType)
                    {
                        obj.Add(pname, SerializePrimitive(tValue, type));
                    }
                    else if (type.IsClass)
                    {
                        if (type == typeof(string))
                        {
                            obj.Add(pname, SerializePrimitive(tValue, type));
                        }
                        else if (type.IsList())
                        {
                            obj.Add(pname, SerializeList(tValue, type));
                        }
                        else
                        {
                            obj.Add(pname, SerializeClass(tValue, type));
                        }
                    }
                }
            } catch (Exception) {
                // pretty ugly but doing this to prevent MissingReferenceExcpetion which apparently isn't catchable
                obj.IsNull = true;
                return(obj);
            }

            return(obj);
        }