| //------------------------------------------------------------------ | 
| //本文件中的工具提供在编辑器环境下,快速整理UI图片相关的资源 | 
| //------------------------------------------------------------------- | 
|   | 
| using System.Collections; | 
| using System.Collections.Generic; | 
| using UnityEngine; | 
| using UnityEditor; | 
| using UnityEngine.UI; | 
| using System.IO; | 
| using System; | 
| using System.Threading; | 
| using System.Text.RegularExpressions; | 
|   | 
| public class WindowImageCheck | 
| { | 
|     static string windowRootPath = Application.dataPath + "/ResourcesOut/UI/Window"; | 
|     static string windowRootPath2 = Application.dataPath + "/ResourcesOut/UI/PriorityWindow"; | 
|     static string prefabRootPath = Application.dataPath + "/ResourcesOut/UI/Prefab"; | 
|   | 
|     [MenuItem("程序/UI Assets/查找和移除无用的Image")] | 
|     public static void CheckAndReplaceFontSwitch() | 
|     { | 
|         try | 
|         { | 
|             var allFiles = new List<FileInfo>(); | 
|             allFiles.AddRange(new DirectoryInfo(windowRootPath).GetFiles("*.prefab", SearchOption.TopDirectoryOnly)); | 
|             allFiles.AddRange(new DirectoryInfo(windowRootPath2).GetFiles("*.prefab", SearchOption.TopDirectoryOnly)); | 
|             allFiles.AddRange(new DirectoryInfo(prefabRootPath).GetFiles("*.prefab", SearchOption.TopDirectoryOnly)); | 
|   | 
|             var count = allFiles.Count; | 
|             var index = 0; | 
|   | 
|             foreach (var file in allFiles) | 
|             { | 
|                 var assetPath = file.FullName.Replace("\\", "/").Replace(Application.dataPath, "Assets"); | 
|                 var prefab = AssetDatabase.LoadAssetAtPath<GameObject>(assetPath); | 
|   | 
|                 var images = prefab.GetComponentsInChildren<Image>(true); | 
|                 foreach (var image in images) | 
|                 { | 
|                     if (image != null) | 
|                     { | 
|                         if (!image.enabled || image.color.a == 0f) | 
|                         { | 
|                             path = string.Empty; | 
|                             Debug.Log(GetComponentPath(image.transform, ref path)); | 
|                             MonoBehaviour.DestroyImmediate(image, true); | 
|                         } | 
|                     } | 
|                 } | 
|   | 
|                 index++; | 
|                 EditorUtility.SetDirty(prefab); | 
|                 EditorUtility.DisplayProgressBar("检测和移除Image", StringUtility.Contact("正在检测:", prefab.name), (float)index / count); | 
|             } | 
|   | 
|             AssetDatabase.SaveAssets(); | 
|             AssetDatabase.Refresh(); | 
|   | 
|             EditorUtility.ClearProgressBar(); | 
|         } | 
|         catch (Exception ex) | 
|         { | 
|             Debug.Log(ex); | 
|         } | 
|   | 
|     } | 
|   | 
|     static string path; | 
|     private static string GetComponentPath(Transform _transform, ref string _path) | 
|     { | 
|         path = _transform.gameObject.name + path; | 
|         if (_transform.parent != null) | 
|         { | 
|             path = "/" + path; | 
|             return GetComponentPath(_transform.parent, ref _path); | 
|         } | 
|         else | 
|         { | 
|             return path; | 
|         } | 
|     } | 
|   | 
| } | 
|   | 
| public class RemoveUnUsedSpriteQuickly | 
| { | 
|     static string uiroot1 = "Assets/ResourcesOut/UI/Window"; | 
|     static string uiroot2 = "Assets/ResourcesOut/UI/PriorityWindow"; | 
|     static string uiroot3 = "Assets/ResourcesOut/UI/Prefab"; | 
|     static string uiroot4 = "Assets/ResourcesOut/UI/Treasure/Misc"; | 
|   | 
|     static string spriteroot = "Assets/ResourcesOut/UI/Sprite"; | 
|   | 
|     static List<string> prefabTexts = new List<string>(); | 
|   | 
|     static Dictionary<string, Sprite> processObjects = new Dictionary<string, Sprite>(); | 
|     static List<AnalyzeTask> tasks = new List<AnalyzeTask>(); | 
|   | 
|     static int taskCount = 1; | 
|     static int completedTaskCount = 0; | 
|     static List<IconConfig> configs; | 
|   | 
|     [MenuItem("程序/UI Assets/移除无用的Sprite")] | 
|     public static void RemoveUnUsedSprites() | 
|     { | 
|         try | 
|         { | 
|             EditorApplication.update += OnUpdate; | 
|             IconConfig.Init(true); | 
|             configs = IconConfig.GetValues(); | 
|   | 
|             LoadPrefabTexts(); | 
|             FindSprites(); | 
|   | 
|             taskCount = 0; | 
|             completedTaskCount = 0; | 
|             foreach (var task in tasks) | 
|             { | 
|                 task.total = task.sprites.Count; | 
|                 taskCount += task.total; | 
|             } | 
|   | 
|             Analyze(); | 
|         } | 
|         catch (Exception e) | 
|         { | 
|             EditorApplication.update -= OnUpdate; | 
|             EditorUtility.ClearProgressBar(); | 
|         } | 
|     } | 
|   | 
|     static void LoadPrefabTexts() | 
|     { | 
|         var guids = new List<string>(); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot1 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot2 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot3 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot4 })); | 
|   | 
|         var assetPaths = new List<string>(); | 
|         foreach (var item in guids) | 
|         { | 
|             assetPaths.Add(AssetDatabase.GUIDToAssetPath(item)); | 
|         } | 
|   | 
|         var totalCount = assetPaths.Count; | 
|         var count = 0; | 
|         prefabTexts.Clear(); | 
|         foreach (var path in assetPaths) | 
|         { | 
|             count++; | 
|             EditorUtility.DisplayProgressBar("读取预置体文本", "正在读取预置体文本", count / (float)totalCount); | 
|             prefabTexts.Add(File.ReadAllText(Application.dataPath + path.Substring(6, path.Length - 6))); | 
|         } | 
|   | 
|         EditorUtility.ClearProgressBar(); | 
|     } | 
|   | 
|     static void FindSprites() | 
|     { | 
|         processObjects.Clear(); | 
|         tasks.Clear(); | 
|   | 
|         var sprites = new List<Sprite>(); | 
|         var guids = new List<string>(); | 
|         var subFolders = AssetDatabase.GetSubFolders(spriteroot); | 
|         foreach (var folder in subFolders) | 
|         { | 
|             guids.AddRange(AssetDatabase.FindAssets("t:sprite", new string[] { folder })); | 
|         } | 
|   | 
|         foreach (var guid in guids) | 
|         { | 
|             sprites.Add(AssetDatabase.LoadAssetAtPath<Sprite>(AssetDatabase.GUIDToAssetPath(guid))); | 
|         } | 
|   | 
|         var count = 0; | 
|         var task = new AnalyzeTask(); | 
|         tasks.Add(task); | 
|         foreach (var asset in sprites) | 
|         { | 
|             var path = AssetDatabase.GetAssetPath(asset); | 
|             var guid = AssetDatabase.AssetPathToGUID(path); | 
|             processObjects[guid] = asset; | 
|   | 
|             var folderName = Path.GetDirectoryName(path).Split('/').GetLast(); | 
|             if (folderName == "Frame") | 
|             { | 
|                 continue; | 
|             } | 
|   | 
|             task.Add(new SpriteInfo() | 
|             { | 
|                 name = asset.name, | 
|                 guid = guid, | 
|                 folder = folderName | 
|             }); | 
|   | 
|             count++; | 
|   | 
|             if (count >= 500) | 
|             { | 
|                 count = 0; | 
|                 task = new AnalyzeTask(); | 
|                 tasks.Add(task); | 
|             } | 
|         } | 
|   | 
|     } | 
|   | 
|     static void Analyze() | 
|     { | 
|         foreach (var task in tasks) | 
|         { | 
|             ThreadPool.QueueUserWorkItem(x => | 
|             { | 
|                 for (int i = 0; i < task.sprites.Count; i++) | 
|                 { | 
|                     task.completed++; | 
|                     var info = task.sprites[i]; | 
|                     if (ContainByIconTable(info)) | 
|                     { | 
|                         continue; | 
|                     } | 
|   | 
|                     if (RefrenceByPrefab(info)) | 
|                     { | 
|                         continue; | 
|                     } | 
|   | 
|                     info.unUsed = true; | 
|                     task.sprites[i] = info; | 
|                 } | 
|   | 
|                 task.done = true; | 
|             }); | 
|         } | 
|     } | 
|   | 
|     static void ProcessUnUsedSprites() | 
|     { | 
|         var total = 0; | 
|         foreach (var task in tasks) | 
|         { | 
|             foreach (var sprite in task.sprites) | 
|             { | 
|                 if (sprite.unUsed) | 
|                 { | 
|                     Debug.LogFormat("找到一张无用的图片:文件夹->{0};图片名称->{1}", sprite.folder, sprite.name); | 
|                     total++; | 
|                 } | 
|             } | 
|         } | 
|   | 
|         var count = 0; | 
|         foreach (var task in tasks) | 
|         { | 
|             foreach (var sprite in task.sprites) | 
|             { | 
|                 if (sprite.unUsed) | 
|                 { | 
|                     EditorUtility.DisplayProgressBar("删除Sprite", string.Format("正在删除第{0}张图片,共{1}张", count + 1, total), (float)count / total); | 
|                     count++; | 
|                     AssetDatabase.DeleteAsset(AssetDatabase.GUIDToAssetPath(sprite.guid)); | 
|                 } | 
|             } | 
|         } | 
|   | 
|         EditorUtility.ClearProgressBar(); | 
|     } | 
|   | 
|     static bool ContainByIconTable(SpriteInfo info) | 
|     { | 
|         return configs.FindIndex(x => { return x.folder.ToLower() == info.folder.ToLower() && x.sprite == info.name; }) != -1; | 
|     } | 
|   | 
|     static bool RefrenceByPrefab(SpriteInfo info) | 
|     { | 
|         foreach (var content in prefabTexts) | 
|         { | 
|             if (Regex.IsMatch(content, info.guid)) | 
|             { | 
|                 return true; | 
|             } | 
|         } | 
|   | 
|         return false; | 
|     } | 
|   | 
|     static void OnUpdate() | 
|     { | 
|         var done = true; | 
|         completedTaskCount = 0; | 
|         foreach (var task in tasks) | 
|         { | 
|             completedTaskCount += task.completed; | 
|             if (!task.done) | 
|             { | 
|                 done = false; | 
|             } | 
|         } | 
|   | 
|         EditorUtility.DisplayProgressBar("分析无用Sprite", | 
|             string.Format("正在分析第{0}张Sprite,共计{1}张", completedTaskCount + 1, taskCount), | 
|             (float)completedTaskCount / taskCount); | 
|   | 
|         if (done) | 
|         { | 
|             EditorUtility.ClearProgressBar(); | 
|             ProcessUnUsedSprites(); | 
|             EditorApplication.update -= OnUpdate; | 
|         } | 
|     } | 
|   | 
|     struct SpriteInfo | 
|     { | 
|         public string guid; | 
|         public string name; | 
|         public string folder; | 
|         public bool unUsed; | 
|     } | 
|   | 
|     class AnalyzeTask | 
|     { | 
|         public int total; | 
|         public int completed; | 
|         public bool done; | 
|         public List<SpriteInfo> sprites; | 
|   | 
|         public AnalyzeTask() | 
|         { | 
|             sprites = new List<SpriteInfo>(); | 
|         } | 
|   | 
|         public void Add(SpriteInfo info) | 
|         { | 
|             sprites.Add(info); | 
|         } | 
|     } | 
|   | 
| } | 
|   | 
| public class FindUnUsedPrefab | 
| { | 
|     static string uiroot1 = "Assets/ResourcesOut/UI/Window"; | 
|     static string uiroot2 = "Assets/ResourcesOut/UI/PriorityWindow"; | 
|     static string uiroot3 = "Assets/ResourcesOut/UI/Prefab"; | 
|   | 
|     [MenuItem("程序/UI Assets/找到可疑的UI Prefab对象")] | 
|     public static void FindUnnormalObjects() | 
|     { | 
|         var guids = new List<string>(); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot1 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot2 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot3 })); | 
|   | 
|         var assets = new List<GameObject>(); | 
|         foreach (var guid in guids) | 
|         { | 
|             var go = AssetDatabase.LoadAssetAtPath<GameObject>(AssetDatabase.GUIDToAssetPath(guid)); | 
|             if (go != null) | 
|             { | 
|                 assets.Add(go); | 
|             } | 
|         } | 
|   | 
|         foreach (var item in assets) | 
|         { | 
|             var so = new SerializedObject(item); | 
|             var soProperties = so.FindProperty("m_Component"); | 
|             var components = item.GetComponents<Component>(); | 
|             int propertyIndex = 0; | 
|             foreach (var c in components) | 
|             { | 
|                 if (c == null) | 
|                 { | 
|                     Debug.LogFormat("资源{0}存在可疑错误,请检查", item.name); | 
|                 } | 
|                 ++propertyIndex; | 
|             } | 
|         } | 
|   | 
|     } | 
|   | 
|   | 
| } | 
|   | 
| public class RemoveUnUsedIconKey | 
| { | 
|     static string uiroot1 = "Assets/ResourcesOut/UI/Window"; | 
|     static string uiroot2 = "Assets/ResourcesOut/UI/PriorityWindow"; | 
|     static string uiroot3 = "Assets/ResourcesOut/UI/Prefab"; | 
|     static string uiroot4 = "Assets/ResourcesOut/UI/Treasure/Misc"; | 
|   | 
|     static List<string> ignoreKeyList = new List<string>() | 
|     { | 
|         "Remark_","GemTypeMini_","AllianceBossRank_","GemTypeMini_","RealmSelectBottom_","XT_TJ_","Fb_", | 
|         "MultipleExp_Icon_","MapNPC_Colour_","LocalMapTaskState_","EquipDefaultIcon_","OpenServerActivty_","ChatIcon_" | 
|     }; | 
|   | 
|     static int taskCount = 1; | 
|     static int completedTaskCount = 0; | 
|     static Dictionary<string, List<string>> iconKeyMap = new Dictionary<string, List<string>>(); | 
|   | 
|     static List<string> prefabTexts = new List<string>(); | 
|     static List<Column> iconKeyRefrences = new List<Column>(); | 
|     static List<string> csharpFileContents = new List<string>(); | 
|     static string generalContent = string.Empty; | 
|     static List<AnalyzeTask> tasks = new List<AnalyzeTask>(); | 
|     static List<string> scriptableObjects = new List<string>(); | 
|   | 
|     [MenuItem("程序/UI Assets/移除无用的IconKey")] | 
|     public static void Remove() | 
|     { | 
|         tasks.Clear(); | 
|         var iconKeys = GetOriginalIconKeys(); | 
|   | 
|         taskCount = iconKeys.Count; | 
|         completedTaskCount = 0; | 
|   | 
|         var count = 0; | 
|         var task = new AnalyzeTask(); | 
|         tasks.Add(task); | 
|         foreach (var key in iconKeys) | 
|         { | 
|             task.Add(new IconKeyInfo() | 
|             { | 
|                 key = key, | 
|                 unused = false | 
|             }); | 
|   | 
|             if (count >= 200) | 
|             { | 
|                 count = 0; | 
|                 task = new AnalyzeTask(); | 
|                 tasks.Add(task); | 
|             } | 
|             count++; | 
|         } | 
|   | 
|         iconKeyMap = GetIconKeyMap(); | 
|         iconKeyRefrences = GetAllIconKeyRefrences(); | 
|         csharpFileContents = GetAllCSharpFileContents(); | 
|         generalContent = GetGeneralContent(); | 
|         prefabTexts = GetPrefabTexts(); | 
|         scriptableObjects = GetScriptableObjects(); | 
|   | 
|         try | 
|         { | 
|             EditorApplication.update += OnUpdate; | 
|             Analyze(); | 
|         } | 
|         catch (Exception e) | 
|         { | 
|             EditorUtility.ClearProgressBar(); | 
|             EditorApplication.update -= OnUpdate; | 
|             Debug.Log(e); | 
|         } | 
|   | 
|     } | 
|   | 
|     static void Analyze() | 
|     { | 
|         foreach (var task in tasks) | 
|         { | 
|             ThreadPool.QueueUserWorkItem(x => | 
|             { | 
|                 for (int i = task.iconKeys.Count - 1; i >= 0; i--) | 
|                 { | 
|                     task.completed++; | 
|                     var info = task.iconKeys[i]; | 
|                     if (ContainByTables(info.key, ref iconKeyRefrences)) | 
|                     { | 
|                         // Debug.LogFormat("找到一个被其他配置配件引用的 icon key:{0}", info.key); | 
|                         continue; | 
|                     } | 
|   | 
|                     if (ContainByGeneralConfig(info.key, ref generalContent)) | 
|                     { | 
|                         // Debug.LogFormat("找到一个写在功能配置表中的 icon key:{0}", info.key); | 
|                         continue; | 
|                     } | 
|   | 
|                     if (ContainBySriptableObjects(info.key, ref scriptableObjects)) | 
|                     { | 
|                         // Debug.LogFormat("找到一个配置在ScriptObject文件中的 icon key:{0}", info.key); | 
|                         continue; | 
|                     } | 
|   | 
|                     if (ContainByCSharpFile(info.key, ref csharpFileContents)) | 
|                     { | 
|                         // Debug.LogFormat("找到一个写在C#文件中的 icon key:{0}", info.key); | 
|                         continue; | 
|                     } | 
|   | 
|                     if (ContainByPrefab(info.key, ref prefabTexts)) | 
|                     { | 
|                         //Debug.LogFormat("找到一个被prefab依赖的 icon key:{0}", info.key); | 
|                         continue; | 
|                     } | 
|   | 
|                     info.unused = true; | 
|                     task.iconKeys[i] = info; | 
|                 } | 
|   | 
|                 task.done = true; | 
|             }); | 
|         } | 
|     } | 
|   | 
|     static void ProcessUnUsedIconKeys() | 
|     { | 
|         var lines = new List<string>(File.ReadAllLines(Application.dataPath + "/ResourcesOut/Refdata/Config/Icon.txt")); | 
|         var deleteLines = new List<string>(); | 
|         var unUsedIconKeys = new List<string>(); | 
|         foreach (var task in tasks) | 
|         { | 
|             foreach (var iconkey in task.iconKeys) | 
|             { | 
|                 if (iconkey.unused) | 
|                 { | 
|                     unUsedIconKeys.Add(iconkey.key); | 
|                 } | 
|             } | 
|         } | 
|   | 
|         for (int i = lines.Count - 1; i >= 3; i--) | 
|         { | 
|             var contents = lines[i].Split('\t'); | 
|             if (!contents.IsNullOrEmpty()) | 
|             { | 
|                 if (unUsedIconKeys.Contains(contents[0])) | 
|                 { | 
|                     deleteLines.Add(lines[i]); | 
|                     lines.RemoveAt(i); | 
|                 } | 
|             } | 
|         } | 
|   | 
|         File.WriteAllLines(Application.dataPath + "/删除的Icon表配置.txt", deleteLines.ToArray()); | 
|         File.WriteAllLines(Application.dataPath + "/ResourcesOut/Refdata/Config/Icon.txt", lines.ToArray()); | 
|     } | 
|   | 
|     static Dictionary<string, List<string>> GetIconKeyMap() | 
|     { | 
|         var lines = File.ReadAllLines(Application.dataPath + "/Editor/Config/TxtIconKeys.txt"); | 
|         var map = new Dictionary<string, List<string>>(); | 
|   | 
|         for (int i = 1; i < lines.Length; i++) | 
|         { | 
|             var line = lines[i]; | 
|             var contents = new List<string>(line.Split('\t')); | 
|             if (!contents.IsNullOrEmpty() && contents.Count >= 2) | 
|             { | 
|                 var fields = map[contents[0]] = new List<string>(); | 
|                 fields.AddRange(contents.GetRange(1, contents.Count - 1)); | 
|             } | 
|         } | 
|   | 
|         return map; | 
|     } | 
|   | 
|     static List<string> GetOriginalIconKeys() | 
|     { | 
|         var lines = File.ReadAllLines(Application.dataPath + "/ResourcesOut/Refdata/Config/Icon.txt"); | 
|         var iconKeys = new List<string>(); | 
|         for (int i = 3; i < lines.Length; i++) | 
|         { | 
|             var contents = lines[i].Split('\t'); | 
|             if (!contents.IsNullOrEmpty()) | 
|             { | 
|                 iconKeys.Add(contents[0]); | 
|             } | 
|         } | 
|   | 
|         return iconKeys; | 
|     } | 
|   | 
|     static List<Column> GetAllIconKeyRefrences() | 
|     { | 
|         var files = FileExtersion.GetFileInfos(Application.dataPath + "/ResourcesOut/Refdata/Config", new string[] { "*.txt", "*.TXT" }); | 
|   | 
|         var count = 0; | 
|         var columns = new List<Column>(); | 
|         foreach (var file in files) | 
|         { | 
|             count++; | 
|             EditorUtility.DisplayProgressBar("解析配置文件", "正在解析配置文件", (float)count / files.Count); | 
|   | 
|             var nameWithoutExtension = Path.GetFileNameWithoutExtension(file.FullName); | 
|             if (!iconKeyMap.ContainsKey(nameWithoutExtension)) | 
|             { | 
|                 continue; | 
|             } | 
|   | 
|             var lines = File.ReadAllLines(file.FullName); | 
|             var fields0 = new List<string>(lines[0].Split('\t')); | 
|             var fields1 = new List<string>(lines[1].Split('\t')); | 
|             var refrences = iconKeyMap[nameWithoutExtension]; | 
|             foreach (var refrence in refrences) | 
|             { | 
|                 var name = string.Empty; | 
|                 var index = fields0.IndexOf(refrence); | 
|                 if (index != -1) | 
|                 { | 
|                     name = fields0[index]; | 
|                 } | 
|                 else | 
|                 { | 
|                     index = fields1.IndexOf(refrence); | 
|                     if (index != -1) | 
|                     { | 
|                         name = fields1[index]; | 
|                     } | 
|                 } | 
|   | 
|                 if (index == -1) | 
|                 { | 
|                     continue; | 
|                 } | 
|   | 
|                 var column = new Column() | 
|                 { | 
|                     name = name, | 
|                     values = new List<string>() | 
|                 }; | 
|   | 
|                 columns.Add(column); | 
|                 for (int i = 1; i < lines.Length; i++) | 
|                 { | 
|                     var line = lines[i]; | 
|                     var contents = line.Split('\t'); | 
|                     column.values.Add(contents[index]); | 
|                 } | 
|             } | 
|   | 
|         } | 
|   | 
|         EditorUtility.ClearProgressBar(); | 
|         return columns; | 
|     } | 
|   | 
|     static List<string> GetAllCSharpFileContents() | 
|     { | 
|         var files = FileExtersion.GetFileInfos(Application.dataPath + "/Scripts", new string[] { "*.cs" }); | 
|         var contents = new List<string>(); | 
|   | 
|         var count = 0; | 
|         foreach (var file in files) | 
|         { | 
|             count++; | 
|             EditorUtility.DisplayProgressBar("读取代码文件", "正在读取代码文件", (float)count / files.Count); | 
|             contents.Add(File.ReadAllText(file.FullName)); | 
|         } | 
|   | 
|         EditorUtility.ClearProgressBar(); | 
|   | 
|         return contents; | 
|     } | 
|   | 
|     static List<string> GetPrefabTexts() | 
|     { | 
|         var guids = new List<string>(); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot1 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot2 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot3 })); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:prefab", new string[] { uiroot4 })); | 
|   | 
|         var assetPaths = new List<string>(); | 
|         foreach (var item in guids) | 
|         { | 
|             assetPaths.Add(AssetDatabase.GUIDToAssetPath(item)); | 
|         } | 
|   | 
|         var count = 0; | 
|         var prefabTexts = new List<string>(); | 
|         foreach (var path in assetPaths) | 
|         { | 
|             count++; | 
|             EditorUtility.DisplayProgressBar("读取预置体文本", "正在读取预置体文本", (float)count / assetPaths.Count); | 
|             prefabTexts.Add(File.ReadAllText(Application.dataPath + path.Substring(6, path.Length - 6))); | 
|         } | 
|   | 
|         EditorUtility.ClearProgressBar(); | 
|         return prefabTexts; | 
|     } | 
|   | 
|     static string GetGeneralContent() | 
|     { | 
|         return File.ReadAllText(Application.dataPath + "/ResourcesOut/Refdata/Config/FuncConfig.txt"); | 
|     } | 
|   | 
|     static List<string> GetScriptableObjects() | 
|     { | 
|         var guids = new List<string>(); | 
|         guids.AddRange(AssetDatabase.FindAssets("t:ScriptableObject", new string[] { "Assets/ResourcesOut/BuiltIn/ScriptableObjects" })); | 
|   | 
|         var assetPaths = new List<string>(); | 
|         foreach (var item in guids) | 
|         { | 
|             assetPaths.Add(AssetDatabase.GUIDToAssetPath(item)); | 
|         } | 
|   | 
|         var count = 0; | 
|         var scriptableObjects = new List<string>(); | 
|         foreach (var path in assetPaths) | 
|         { | 
|             count++; | 
|             EditorUtility.DisplayProgressBar("读取ScriptableObject", "正在读取ScriptableObject", (float)count / assetPaths.Count); | 
|             scriptableObjects.Add(File.ReadAllText(Application.dataPath + path.Substring(6, path.Length - 6))); | 
|         } | 
|   | 
|         EditorUtility.ClearProgressBar(); | 
|         return scriptableObjects; | 
|     } | 
|   | 
|     static bool ContainByTables(string key, ref List<Column> columns) | 
|     { | 
|         foreach (var column in columns) | 
|         { | 
|             foreach (var value in column.values) | 
|             { | 
|                 if (Regex.IsMatch(value, key)) | 
|                 { | 
|                     return true; | 
|                 } | 
|             } | 
|         } | 
|   | 
|         return false; | 
|     } | 
|   | 
|     static bool ContainByCSharpFile(string key, ref List<string> csharpContents) | 
|     { | 
|         foreach (var ignore in ignoreKeyList) | 
|         { | 
|             if (Regex.IsMatch(key, ignore)) | 
|             { | 
|                 return true; | 
|             } | 
|         } | 
|   | 
|         var pattern = string.Format(@"\.SetSprite.*{0}.*\);", key); | 
|         foreach (var content in csharpContents) | 
|         { | 
|             if (Regex.IsMatch(content, pattern)) | 
|             { | 
|                 return true; | 
|             } | 
|         } | 
|   | 
|         return false; | 
|     } | 
|   | 
|     static bool ContainByGeneralConfig(string key, ref string content) | 
|     { | 
|         return Regex.IsMatch(content, key); | 
|     } | 
|   | 
|     static bool ContainByPrefab(string key, ref List<string> prefabTexts) | 
|     { | 
|         foreach (var text in prefabTexts) | 
|         { | 
|             if (Regex.IsMatch(text, key)) | 
|             { | 
|                 return true; | 
|             } | 
|         } | 
|   | 
|         return false; | 
|     } | 
|   | 
|     static bool ContainBySriptableObjects(string key, ref List<string> scriptableObjects) | 
|     { | 
|         foreach (var text in scriptableObjects) | 
|         { | 
|             if (Regex.IsMatch(text, key)) | 
|             { | 
|                 return true; | 
|             } | 
|         } | 
|   | 
|         return false; | 
|     } | 
|   | 
|     static void OnUpdate() | 
|     { | 
|         var done = true; | 
|         completedTaskCount = 0; | 
|         foreach (var task in tasks) | 
|         { | 
|             completedTaskCount += task.completed; | 
|             if (!task.done) | 
|             { | 
|                 done = false; | 
|             } | 
|         } | 
|   | 
|         EditorUtility.DisplayProgressBar("分析无用IconKey", | 
|             string.Format("正在分析第{0}个IconKey,共计{1}个", completedTaskCount + 1, taskCount), | 
|             (float)completedTaskCount / taskCount); | 
|   | 
|         if (done) | 
|         { | 
|             EditorUtility.ClearProgressBar(); | 
|             ProcessUnUsedIconKeys(); | 
|             EditorApplication.update -= OnUpdate; | 
|         } | 
|     } | 
|   | 
|     struct Column | 
|     { | 
|         public string name; | 
|         public List<string> values; | 
|     } | 
|   | 
|     struct IconKeyInfo | 
|     { | 
|         public string key; | 
|         public bool unused; | 
|     } | 
|   | 
|     class AnalyzeTask | 
|     { | 
|         public int total; | 
|         public int completed; | 
|         public bool done; | 
|         public List<IconKeyInfo> iconKeys; | 
|   | 
|         public AnalyzeTask() | 
|         { | 
|             iconKeys = new List<IconKeyInfo>(); | 
|         } | 
|   | 
|         public void Add(IconKeyInfo key) | 
|         { | 
|             iconKeys.Add(key); | 
|         } | 
|     } | 
|   | 
| } |