ソースコード
using System.Linq;
using System.Text;
using UnityEditor;
using UnityEngine;
internal sealed class MissingSpriteFinder : EditorWindow
{
[MenuItem( "Window/Missing Sprite Finder" )]
private static void Open()
{
GetWindow<MissingSpriteFinder>();
}
private void OnGUI()
{
if ( GUILayout.Button( "Find Missing Sprites" ) )
{
Find();
}
}
private static void Find()
{
var guids = AssetDatabase.FindAssets( "t:Prefab" );
var stringBuilder = new StringBuilder();
foreach ( var guid in guids )
{
var path = AssetDatabase.GUIDToAssetPath( guid );
var prefab = AssetDatabase.LoadAssetAtPath<GameObject>( path );
if ( prefab == null ) continue;
var spriteRenderers = prefab.GetComponentsInChildren<SpriteRenderer>( true );
foreach ( var spriteRenderer in spriteRenderers )
{
if ( MissingReferenceUtils.HasMissingReference( spriteRenderer ) )
{
stringBuilder.AppendLine( path );
break;
}
}
}
var result = stringBuilder.ToString();
EditorGUIUtility.systemCopyBuffer = result;
Debug.Log( result );
}
}
internal static class MissingReferenceUtils
{
public static bool HasMissingReference( GameObject gameObject )
{
return gameObject
.GetComponents<Component>()
.Where( x => x != null )
.Any( x => HasMissingReference( x ) )
;
}
public static bool HasMissingReference( Component component )
{
var so = new SerializedObject( component );
var sp = so.GetIterator();
while ( sp.NextVisible( true ) )
{
if ( sp.propertyType != SerializedPropertyType.ObjectReference ) continue;
if ( sp.objectReferenceValue != null ) continue;
if ( !sp.hasChildren ) continue;
var fileId = sp.FindPropertyRelative( "m_FileID" );
if ( fileId == null ) continue;
if ( fileId.intValue == 0 ) continue;
return true;
}
return false;
}
}