public static void AddCustomType(Type t, CustomReadDelegate reader, CustomWriteDelegate writer) { if (reader != null) { customReadDelegateMap[t] = reader; } if (writer != null) { customWriteDelegateMap[t] = writer; } }
public static object FromLua(LuaTable table, Type t) { object result = null; if (t.GetCustomAttributes(typeof(NonSerializedAttribute), true).Length > 0) { return(null); } if (typeof(IList).IsAssignableFrom(t)) { if (t.IsArray) { Type elemT = t.GetElementType(); if (!IsNoSerializeType(elemT)) { int elemCount = table.length(); Array arr = Array.CreateInstance(elemT, elemCount); result = arr; for (int i = 1; i <= elemCount; ++i) { object elem = table[i]; if (IsBaseType(elemT)) { elem = ChangeType(elem, elemT); arr.SetValue(elem, i - 1); } else { arr.SetValue(FromLua(elem as LuaTable, elemT), i - 1); } } } } else { Type listImplementation = t.GetInterface(typeof(IList <>).Name); if (listImplementation != null) { Type elemT = listImplementation.GetGenericArguments()[0]; if (!IsNoSerializeType(elemT)) { result = result ?? Activator.CreateInstance(t); IList lst = result as IList; int elemCount = table.length(); for (int i = 1; i <= elemCount; ++i) { object elem = table[i]; if (IsBaseType(elemT)) { elem = ChangeType(elem, elemT); lst.Add(elem); } else { lst.Add(FromLua(elem as LuaTable, elemT)); } } } } } } if (typeof(IDictionary).IsAssignableFrom(t)) { Type dictImplementation = t.GetInterface(typeof(IDictionary <,>).Name); if (dictImplementation != null) { Type keyT = dictImplementation.GetGenericArguments()[0]; Type valueT = dictImplementation.GetGenericArguments()[1]; if (IsBaseType(keyT) && !IsNoSerializeType(valueT)) { result = result ?? Activator.CreateInstance(t); IDictionary dict = result as IDictionary; foreach (var pair in table) { if (pair.value == null) { continue; } object key = ChangeType(pair.key, keyT); if (IsBaseType(valueT)) { object value = ChangeType(pair.value, valueT); dict.Add(key, value); } else { dict.Add(key, FromLua(pair.value as LuaTable, valueT)); } } } } } if (!IsNoSerializeType(t)) { result = result ?? Activator.CreateInstance(t); Type curT = t; while (curT != typeof(System.Object)) { var fis = curT.GetFields(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.DeclaredOnly); for (int i = 0; i < fis.Length; ++i) { var fi = fis[i]; if (fi.GetCustomAttributes(typeof(NonSerializedAttribute), true).Length > 0) { continue; } Type elemT = fi.FieldType; object elem = table[fi.Name]; if (elem == null) { continue; } if (IsBaseType(elemT)) { elem = ChangeType(elem, elemT); fi.SetValue(result, elem); } else { fi.SetValue(result, FromLua(elem as LuaTable, elemT)); } } CustomReadDelegate reader = null; if (customReadDelegateMap.TryGetValue(curT, out reader)) { result = reader(ref result, table); } curT = curT.BaseType; } } return(result); }