/// <summary> /// 转换ASObject对象为.Net类型对象 /// </summary> public static object ConvertEntity(ASObject asObjeect, Type type) { try { var tempObj = Activator.CreateInstance(type); foreach (var asObj in asObjeect) { string key = asObj.Key; object value = asObj.Value; MemberInfo[] members = type.GetMember(key); if (null != value && members != null && members.Length > 0) { object newValue = null; Type asValueType = asObj.Value.GetType(); //.Net类型实体成员 MemberInfo member = members[0]; Type memberType = null; FieldInfo field = null; PropertyInfo property = null; if (member.MemberType == MemberTypes.Field) { field = type.GetField(member.Name); memberType = field.FieldType; } if (member.MemberType == MemberTypes.Property) { property = type.GetProperty(member.Name); memberType = property.PropertyType; } if (property != null || field != null) { //如果是ASObject对象 if (asValueType == typeof(ASObject)) { newValue = ConvertEntity((ASObject)value, memberType); } //如果是数组集合 else if (asValueType == typeof(Object[])) { Type subtype = Assembly.GetAssembly(memberType).GetType(memberType.FullName.Replace("[]", ""), true); object[] arrobj = (Object[])value; var objData = Array.CreateInstance(subtype, arrobj.Length); for (int nn = 0; nn < arrobj.Length; nn++) { FluorineFx.ASObject asData = (FluorineFx.ASObject)arrobj[nn]; var val = ConvertEntity(asData, subtype); objData.SetValue(val, nn); } newValue = objData; } //基本类型 else { newValue = ConvertData(memberType, null, value); } if (field != null) { field.SetValue(tempObj, Convert.ChangeType(newValue, memberType)); } else if (property != null && property.CanWrite) { property.SetValue(tempObj, Convert.ChangeType(newValue, memberType), null); } } } } return(tempObj); } catch { return(null); } }
/// <summary> /// This type supports the Fluorine infrastructure and is not intended to be used directly from your code. /// </summary> /// <param name="context">An ITypeDescriptorContext that provides a format context.</param> /// <param name="culture">A CultureInfo object. If a null reference (Nothing in Visual Basic) is passed, the current culture is assumed.</param> /// <param name="value">The Object to convert.</param> /// <param name="destinationType">The Type to convert the value parameter to.</param> /// <returns>An Object that represents the converted value.</returns> public override object ConvertTo(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value, Type destinationType) { ASObject aso = value as ASObject; if (!ReflectionUtils.IsInstantiatableType(destinationType)) { return(null); } object instance = TypeHelper.CreateInstance(destinationType); if (instance != null) { foreach (string memberName in aso.Keys) { object val = aso[memberName]; //MemberInfo mi = ReflectionUtils.GetMember(destinationType, key, MemberTypes.Field | MemberTypes.Property); //if (mi != null) // ReflectionUtils.SetMemberValue(mi, result, aso[key]); PropertyInfo propertyInfo = null; try { propertyInfo = destinationType.GetProperty(memberName); } catch (AmbiguousMatchException) { //To resolve the ambiguity, include BindingFlags.DeclaredOnly to restrict the search to members that are not inherited. propertyInfo = destinationType.GetProperty(memberName, BindingFlags.DeclaredOnly | BindingFlags.GetProperty | BindingFlags.Public | BindingFlags.Instance); } if (propertyInfo != null) { try { val = TypeHelper.ChangeType(val, propertyInfo.PropertyType); if (propertyInfo.CanWrite && propertyInfo.GetSetMethod() != null) { if (propertyInfo.GetIndexParameters() == null || propertyInfo.GetIndexParameters().Length == 0) { propertyInfo.SetValue(instance, val, null); } else { string msg = __Res.GetString(__Res.Reflection_PropertyIndexFail, string.Format("{0}.{1}", destinationType.FullName, memberName)); throw new FluorineException(msg); } } else { //string msg = __Res.GetString(__Res.Reflection_PropertyReadOnly, string.Format("{0}.{1}", type.FullName, memberName)); } } catch (Exception ex) { string msg = __Res.GetString(__Res.Reflection_PropertySetFail, string.Format("{0}.{1}", destinationType.FullName, memberName), ex.Message); throw new FluorineException(msg); } } else { FieldInfo fi = destinationType.GetField(memberName, BindingFlags.Public | BindingFlags.Instance); try { if (fi != null) { val = TypeHelper.ChangeType(val, fi.FieldType); fi.SetValue(instance, val); } else { //string msg = __Res.GetString(__Res.Reflection_MemberNotFound, string.Format("{0}.{1}", destinationType.FullName, memberName)); } } catch (Exception ex) { string msg = __Res.GetString(__Res.Reflection_FieldSetFail, string.Format("{0}.{1}", destinationType.FullName, memberName), ex.Message); throw new FluorineException(msg); } } } } return(instance); }
public virtual void FromAMF(FluorineFx.ASObject obj) { _fromObject = obj; Type objType = this.GetType(); List<FieldInfo> memberInfo = new List<FieldInfo>(); Type t = objType; if (!_fieldCache.ContainsKey(objType)) { while (t != typeof(AMFObject)) { memberInfo.AddRange(t.GetFields(BindingFlags.Instance | BindingFlags.NonPublic)); t = t.BaseType; } _fieldCache.Add(objType,memberInfo); } else memberInfo = _fieldCache[objType]; foreach (FieldInfo info in memberInfo) { object[] customAttributes; if (!_attributeCache.ContainsKey(info)) { customAttributes = info.GetCustomAttributes(true); _attributeCache.Add(info, customAttributes); } else customAttributes = _attributeCache[info]; try { foreach (object attr in customAttributes) { if (attr is AMFAttribute) { AMFAttribute attribute = attr as AMFAttribute; if (!obj.ContainsKey(attribute.Tag)) info.SetValue(this, null); else if (info.FieldType == typeof(string)) { info.SetValue(this, (string)obj[attribute.Tag]); } else if (info.FieldType == typeof(int?)) { info.SetValue(this, (int?)obj[attribute.Tag]); } else if (info.FieldType == typeof(float?)) { info.SetValue(this, (float?)obj[attribute.Tag]); } else if (info.FieldType == typeof(double?)) { if (obj[attribute.Tag] is double) info.SetValue(this, (double?)obj[attribute.Tag]); else if (obj[attribute.Tag] is int) info.SetValue(this, (double?)(int?)obj[attribute.Tag]); } else if (info.FieldType == typeof(bool?)) { info.SetValue(this, (bool?)obj[attribute.Tag]); } } else if (attr is AMFArrayAttribute) { AMFArrayAttribute attribute = attr as AMFArrayAttribute; if (attribute.ArrayType == typeof(string)) { List<string> array = new List<string>(); foreach (object aobj in (object[])obj[attribute.Tag]) array.Add((string)aobj); info.SetValue(this, array); } else if (attribute.ArrayType.IsSubclassOf(typeof(AMFObject))) { object list = info.FieldType.InvokeMember("", BindingFlags.CreateInstance, null, null, null); if (obj[attribute.Tag] != null) { foreach (object aobj in (object[])obj[attribute.Tag]) { FluorineFx.ASObject asobj = aobj as FluorineFx.ASObject; AMFObject amfobj = (AMFObject)attribute.ArrayType.InvokeMember("", BindingFlags.CreateInstance, null, null, null); amfobj.FromAMF(asobj); list.GetType().InvokeMember("Add", BindingFlags.Instance | BindingFlags.Public | BindingFlags.InvokeMethod, null, list, new object[] { amfobj }); } } info.SetValue(this, list); } } else if (attr is AMFTypedObjectArrayAttribute) { AMFTypedObjectArrayAttribute attribute = attr as AMFTypedObjectArrayAttribute; object list = info.FieldType.InvokeMember("", BindingFlags.CreateInstance, null, null, null); foreach (object aobj in (object[])obj[attribute.Tag]) { FluorineFx.ASObject asobj = aobj as FluorineFx.ASObject; System.Text.RegularExpressions.Match match = System.Text.RegularExpressions.Regex.Match(asobj.TypeName, @"var.www.releases.release-([0-9]+)-([0-9]+)-([0-9]+).([0-9]+).includes.([A-Za-z0-9\-]+).class"); AMFObject amfobj = ObjectBuilder.Instance.BuildObject(match.Groups[5].Value, asobj); //AMFObject amfobj = (AMFObject)attribute.BaseType.InvokeMember("", BindingFlags.CreateInstance, null, null, null); amfobj.FromAMF(asobj); list.GetType().InvokeMember("Add", BindingFlags.Instance | BindingFlags.Public | BindingFlags.InvokeMethod, null, list, new object[] { amfobj }); } info.SetValue(this, list); } else if (attr is AMFObjectAttribute) { AMFObjectAttribute attribute = attr as AMFObjectAttribute; AMFObject amfobj = (AMFObject)attribute.Type.InvokeMember("", BindingFlags.CreateInstance, null, null, null); amfobj.FromAMF((FluorineFx.ASObject)obj[attribute.Tag]); info.SetValue(this, amfobj); } else if (attr is AMFDictionaryAttribute) { AMFDictionaryAttribute attribute = attr as AMFDictionaryAttribute; if (attribute.ValueType == typeof(int?)) { Dictionary<string, int?> dict = new Dictionary<string, int?>(); FluorineFx.ASObject dictobj = (FluorineFx.ASObject)obj[attribute.Tag]; foreach (string key in dictobj.Keys) { object val = dictobj[key]; dict.Add(key, (int?)val); } info.SetValue(this, dict); } else if (attribute.ValueType == typeof(bool?)) { Dictionary<string, bool?> dict = new Dictionary<string, bool?>(); FluorineFx.ASObject dictobj = (FluorineFx.ASObject)obj[attribute.Tag]; foreach (string key in dictobj.Keys) { object val = dictobj[key]; dict.Add(key, (bool?)val); } info.SetValue(this, dict); } else if (attribute.ValueType == typeof(double?)) { Dictionary<string, double?> dict = new Dictionary<string, double?>(); FluorineFx.ASObject dictobj = (FluorineFx.ASObject)obj[attribute.Tag]; foreach (string key in dictobj.Keys) { object val = dictobj[key]; if (val is int) dict.Add(key, (double?)(int?)val); else dict.Add(key, (double?)val); } info.SetValue(this, dict); } } } } catch (Exception ex) { Console.WriteLine("Error setting member: " + info.Name + " " + this.GetType()); } } }