Unity/기능구현

[Unity] Prefab의 Missing Script 자동으로 삭제하기

민트초밥 2024. 7. 19. 17:02

 

스크립트 파일을 삭제했을 때 해당 스크립트 파일을 사용하고 있는 오브젝트나 프리팹이 있으면 오류가 발생한다.

 

 

 

 

 

 

이런 상황을 방지하기 위해 모든 프리팹을 검사해서 Missing Script를 삭제하는 기능을 만들었다.

using System.Collections.Generic;
using System.Linq;
using UnityEditor;
using UnityEngine;

public class DeleteMissingScripts : MonoBehaviour
{
#if UNITY_EDITOR

    [MenuItem("Custom/Delete Missing Scripts")]
    public static void DeleteMissingScriptInPrefabs()
    {
        string[] allPrefabs = AssetDatabase.FindAssets("t:Prefab");

        List<GameObject> list = new List<GameObject>();

        foreach (string prefabGUID in allPrefabs)
        {
            string path = AssetDatabase.GUIDToAssetPath(prefabGUID);
            GameObject prefab = AssetDatabase.LoadAssetAtPath<GameObject>(path);

            list.Add(prefab);
        }

        if (list.Count > 0)
            DeleteInternal(list);
    }


    [MenuItem("Assets/Selection Delete Missing Scripts")]
    public static void DeleteMissingScriptInSelections()
    {
        List<GameObject> list = Selection.gameObjects.ToList();

        if (list.Count > 0)
            DeleteInternal(list);
    }


    private static void DeleteInternal(List<GameObject> list)
    {
        int deleteCount = 0;

        foreach(GameObject obj in list)
        {
            RecursiveDeleteMissingScript(obj, ref deleteCount);
        }

        if (deleteCount > 0)
        {
            Debug.LogWarning($"{nameof(DeleteMissingScripts)} : Delete Missing Script Count {deleteCount} ");
            AssetDatabase.SaveAssets();
        }
    }


    private static void RecursiveDeleteMissingScript(GameObject obj, ref int deleteCount)
    {
        int missingCount = GameObjectUtility.GetMonoBehavioursWithMissingScriptCount(obj);

        if (missingCount > 0)
        {
            GameObjectUtility.RemoveMonoBehavioursWithMissingScript(obj);
            deleteCount++;
        }

        foreach (Transform childTransform in obj.GetComponentsInChildren<Transform>(true))
        {
            GameObject child = childTransform.gameObject;
            missingCount = GameObjectUtility.GetMonoBehavioursWithMissingScriptCount(child);

            if (missingCount > 0)
            {
                GameObjectUtility.RemoveMonoBehavioursWithMissingScript(child);
                deleteCount++;
            }
        }
    }

#endif
}

 

 

 

 

 

[Custom] - [Delete Missing Script] 를 클릭해서 Project의 모든 프리팹을 검사해서 삭제할 수도 있고,

 

한 개의 프리팹 or 여러 개의 프리팹을 선택 후 -> 마우스 우클릭 -> Selection Delete Missing Scripts 버튼으로 선택된 프리팹만 삭제할 수도 있다.

 

 

 

 

Unity - Scripting API: GameObjectUtility.RemoveMonoBehavioursWithMissingScript

Success! Thank you for helping us improve the quality of Unity Documentation. Although we cannot accept all submissions, we do read each suggested change from our users and will make updates where applicable. Close

docs.unity3d.com

 

반응형