static SortedDictionary <string, bool> GetHandledExtensionsByImporter(ScriptedImporterAttribute attribute) { var handledExts = new SortedDictionary <string, bool>(); if (attribute.fileExtensions != null) { var fileExtensions = attribute.fileExtensions.Distinct(StringComparer.OrdinalIgnoreCase); foreach (var fileExtension in fileExtensions) { var cleanExt = fileExtension.Trim('.'); if (!string.IsNullOrEmpty(cleanExt)) { handledExts.Add(cleanExt, true); } } } if (attribute.overrideFileExtensions != null) { var overrideFileExtensions = attribute.overrideFileExtensions.Distinct(StringComparer.OrdinalIgnoreCase); foreach (var fileExtension in overrideFileExtensions) { var cleanExt = fileExtension.Trim('.'); if (!string.IsNullOrEmpty(cleanExt) && !handledExts.ContainsKey(cleanExt)) { handledExts.Add(cleanExt, false); } } } return(handledExts); }
internal static void RegisterScriptedImporters() { //Find the types with the 'ScriptedImporter' attribute which also derive from 'ScriptedImporter' var importers = new List <Type>(); foreach (var type in TypeCache.GetTypesWithAttribute <ScriptedImporterAttribute>()) { if (type.IsSubclassOf(typeof(ScriptedImporter))) { importers.Add(type); } else { Debug.LogError(String.Format("{0} has a 'ScriptedImporter' Attribute but is not a subclass of 'ScriptedImporter'.", type.ToString())); } } ScriptedImporterAttribute[] scriptedImporterAttributes = new ScriptedImporterAttribute[importers.Count]; SortedDictionary <string, bool>[] handledExtensions = new SortedDictionary <string, bool> [importers.Count]; Dictionary <string, List <int> > importersByExtension = new Dictionary <string, List <int> >(); // Build a dictionary of which importers are trying to register each extension that we can use to quickly find conflicts // (i.e. if an entry in the extension-keyed dictionary has a list of importers with more than one entry) for (var importerIndex = 0; importerIndex < importers.Count; importerIndex++) { Type importer = importers[importerIndex]; scriptedImporterAttributes[importerIndex] = Attribute.GetCustomAttribute(importer, typeof(ScriptedImporterAttribute)) as ScriptedImporterAttribute; handledExtensions[importerIndex] = GetHandledExtensionsByImporter(scriptedImporterAttributes[importerIndex]); if (handledExtensions[importerIndex].Count == 0) { Debug.LogError($"The ScriptedImporter {importer.FullName} does not provide any non-null file extension."); } foreach (KeyValuePair <string, bool> handledExtension in handledExtensions[importerIndex]) { // Only consider AutoSelected ones if (handledExtension.Value) { // Add this importer to the dictionary entry for this file extension, creating it if not already present if (!importersByExtension.TryGetValue(handledExtension.Key, out List <int> importerIndicesForThisExtension)) { importerIndicesForThisExtension = new List <int>(); importersByExtension.Add(handledExtension.Key, importerIndicesForThisExtension); } importerIndicesForThisExtension.Add(importerIndex); } } } // Check each AutoSelected extension we found, any of them that have more than one importer associated with them are rejected (i.e. removed from all importers that provided them) foreach (KeyValuePair <string, List <int> > importerExtension in importersByExtension) { if (importerExtension.Value.Count > 1) { string rejectedImporters = ""; foreach (int importerIndex in importerExtension.Value) { handledExtensions[importerIndex].Remove(importerExtension.Key); if (rejectedImporters.Length != 0) { rejectedImporters = $"{rejectedImporters}, "; } rejectedImporters = $"{rejectedImporters}{importers[importerIndex].FullName} (assembly: {importers[importerIndex].Module.FullyQualifiedName})"; } Debug.LogError(String.Format("Multiple scripted importers are targeting the extension '{0}' and have all been rejected: {1} ", importerExtension.Key, rejectedImporters)); } } for (var index = 0; index < importers.Count; index++) { var importer = importers[index]; var attribute = scriptedImporterAttributes[index]; var handledExts = handledExtensions[index]; if (handledExts.Count > 0) { var supportsImportDependencyHinting = (importer.GetMethod("GetHashOfImportedAssetDependencyHintsForTesting", BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static) != null) || IsStaticMethodInClassOrParent(importer, "GatherDependenciesFromSourceFile"); // Register the importer foreach (var ext in handledExts) { AssetImporter.RegisterImporter(importer, attribute.version, attribute.importQueuePriority, ext.Key, supportsImportDependencyHinting, ext.Value, attribute.AllowCaching); } } } }