#if !(UNITY_WSA && ENABLE_DOTNET) using System; using System.Collections.Generic; using System.Linq; using System.Reflection; namespace Zenject { [NoReflectionBaking] public class ConventionBindInfo { readonly List> _typeFilters = new List>(); readonly List> _assemblyFilters = new List>(); #if ZEN_MULTITHREADING readonly object _locker = new object(); #endif static Dictionary _assemblyTypeCache = new Dictionary(); public void AddAssemblyFilter(Func predicate) { _assemblyFilters.Add(predicate); } public void AddTypeFilter(Func predicate) { _typeFilters.Add(predicate); } IEnumerable GetAllAssemblies() { // This seems fast enough that it's not worth caching // We also want to allow dynamically loading assemblies return AppDomain.CurrentDomain.GetAssemblies(); } bool ShouldIncludeAssembly(Assembly assembly) { return _assemblyFilters.All(predicate => predicate(assembly)); } bool ShouldIncludeType(Type type) { return _typeFilters.All(predicate => predicate(type)); } Type[] GetTypes(Assembly assembly) { Type[] types; #if ZEN_MULTITHREADING lock (_locker) #endif { // This is much faster than calling assembly.GetTypes() every time if (!_assemblyTypeCache.TryGetValue(assembly, out types)) { types = assembly.GetTypes(); _assemblyTypeCache[assembly] = types; } } return types; } public List ResolveTypes() { return GetAllAssemblies() .Where(ShouldIncludeAssembly) .SelectMany(assembly => GetTypes(assembly)) .Where(ShouldIncludeType).ToList(); } } } #endif