static BaseDrawer GetDrawerForType(Type objectType, Type[] typeCache, Type baseDrawerType) { for (int i = 0; i < typeCache.Length; i++) { var drawerType = typeCache[i]; var ignoreFor = drawerType.GetCustomAttribute <IgnoreOnTypes>(); if (ignoreFor != null) { var forTypes = ignoreFor.types; if (forTypes.Any(x => objectType.IsSubclassOfRawGeneric(x))) { continue; } } var firstGen = drawerType.GetParentGenericArguments(baseDrawerType)[0]; var drawer = ResolveDrawerFromTypes(objectType, drawerType, firstGen); if (drawer != null) { return(drawer); } } return(BaseDrawer.Create(fallbackDrawerType)); }
private BaseDrawer ResolveDrawerFromTypes(Type objectType, Type drawerType, Type drawerGenArgType) { if (objectType.IsArray) // TODO: remove concrete dependency { return(BaseDrawer.Create(typeof(ArrayDrawer <>).MakeGenericType(objectType.GetElementType()))); } if (objectType.IsA(drawerGenArgType)) { return(BaseDrawer.Create(drawerType)); } if (drawerGenArgType.IsGenericType) { if (objectType.IsSubTypeOfRawGeneric(drawerGenArgType.GetGenericTypeDefinition())) { return(BaseDrawer.Create(drawerType.MakeGenericType(objectType.IsArray ? new[] { objectType.GetElementType() } : objectType.GetGenericArguments()))); } } else if (!drawerGenArgType.IsConstructedGenType()) { var args = drawerType.GetGenericArguments(); if (args.Length == 1 && args[0].IsGenericTypeDefinition) { return(BaseDrawer.Create(drawerType.MakeGenericType(objectType))); } } return(null); }
private BaseDrawer GetDrawerForType(Type objectType, Type[] typeCache, Type baseDrawerType) { for (int i = 0; i < typeCache.Length; i++) { var drawerType = typeCache[i]; var firstGen = drawerType.GetParentGenericArguments(baseDrawerType)[0]; var drawer = ResolveDrawerFromTypes(objectType, drawerType, firstGen); if (drawer != null) { return(drawer); } } return(BaseDrawer.Create(fallbackDrawerType)); }
static BaseDrawer ResolveDrawerFromTypes(Type objectType, Type drawerType, Type drawerGenArgType) { if (objectType.IsSubTypeOfRawGeneric(typeof(IDictionary <,>))) { var args = new List <Type>(objectType.GetGenericArgsInThisOrAbove()); args.Insert(0, objectType); return(BaseDrawer.Create(typeof(DictionaryDrawer <, ,>).MakeGenericType(args.ToArray()))); } if (objectType.IsSubTypeOfRawGeneric(typeof(List <>))) { var elementType = objectType.GetGenericArgsInThisOrAbove()[0]; return(BaseDrawer.Create(typeof(ListDrawer <>).MakeGenericType(elementType))); } if (objectType.IsArray) { var elementType = objectType.GetElementType(); return(BaseDrawer.Create(typeof(ArrayDrawer <>).MakeGenericType(elementType))); } if (objectType.IsA(drawerGenArgType)) { return(BaseDrawer.Create(drawerType)); } if (drawerGenArgType.IsGenericType) { if (objectType.IsSubTypeOfRawGeneric(drawerGenArgType.GetGenericTypeDefinition())) { var args = objectType.GetGenericArgsInThisOrAbove(); return(BaseDrawer.Create(drawerType.MakeGenericType(args))); } } else if (!drawerGenArgType.IsConstructedGenType()) { var args = drawerType.GetGenericArguments(); if (args.Length == 1 && args[0].IsGenericTypeDefinition) { return(BaseDrawer.Create(drawerType.MakeGenericType(objectType))); } } return(null); }
static BaseDrawer GetDrawerForPair(Type objectType, Type attributeType, Type[] typeCache, Type baseDrawerType) { for (int i = 0; i < typeCache.Length; i++) { var drawerType = typeCache[i]; var ignoreFor = drawerType.GetCustomAttribute <IgnoreOnTypes>(); if (ignoreFor != null) { var forTypes = ignoreFor.types; if (forTypes.Any(x => objectType.IsSubclassOfRawGeneric(x))) { continue; } } var args = drawerType.GetParentGenericArguments(baseDrawerType); if (attributeType == args[1]) { var drawer = ResolveDrawerFromTypes(objectType, drawerType, args[0]); if (drawer != null) { return(drawer); } } else if (args[1].IsGenericParameter) { var constraints = args[1].GetGenericParameterConstraints(); if (constraints.Length == 1 && attributeType.IsA(constraints[0])) { return(BaseDrawer.Create(drawerType.MakeGenericType(attributeType))); } } } return(null); }