//------------------------------------------------------------------ //本文件中的工具提供在编辑器环境下,快速整理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("策划工具/查找和移除无用的Image")] public static void CheckAndReplaceFontSwitch() { try { var allFiles = new List(); 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(assetPath); var images = prefab.GetComponentsInChildren(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 spriteroot = "Assets/ResourcesOut/UI/Sprite"; static List prefabTexts = new List(); static Dictionary processObjects = new Dictionary(); static List tasks = new List(); static int taskCount = 1; static int completedTaskCount = 0; static List configs; [MenuItem("程序/移除无用的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(); guids.AddRange(AssetDatabase.FindAssets("Win t:prefab", new string[] { uiroot1 })); guids.AddRange(AssetDatabase.FindAssets("Win t:prefab", new string[] { uiroot2 })); guids.AddRange(AssetDatabase.FindAssets("Win t:prefab", new string[] { uiroot3 })); var assetPaths = new List(); foreach (var item in guids) { assetPaths.Add(AssetDatabase.GUIDToAssetPath(item)); } prefabTexts.Clear(); foreach (var path in assetPaths) { prefabTexts.Add(File.ReadAllText(Application.dataPath + path.Substring(6, path.Length - 6))); } } static void FindSprites() { processObjects.Clear(); tasks.Clear(); var sprites = new List(); var guids = new List(); 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(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) { //AssetDatabase.DeleteAsset(AssetDatabase.GUIDToAssetPath(sprite.guid)); Debug.LogFormat("找到一张无用的图片:文件夹->{0};图片名称->{1}", sprite.folder, sprite.name); total++; } } } Debug.LogFormat("累计找到{0}张无用图片", total); } 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 sprites; public AnalyzeTask() { sprites = new List(); } public void Add(SpriteInfo info) { sprites.Add(info); } } }