0
votes

How can I determine whether a game object is a prefab asset or is an instance of a prefab within my scene?

I tried making a custom editor and doing

public override void OnInspectorGUI()
{
   if (EditorUtility.IsPersistent(this.target))
   {
      Debug.Log("is persisent");
   }
   else
   {
      Debug.Log("is not persistent");
   }
}

But whether I select the prefab asset in the Project view or I select the prefab instance in my scene, both scenarios print "is not persistent"

The reason I'm doing this is that I want to have a MonoBehaviour with a Guid field, and the MonoBehaviour should generate a unique GUID for itself if it's part of a game object within a scene, but it should leave its Guid field blank if its part of a prefab asset (so that each instance of the same prefab gets a unique GUID).

2
sounds more like you need a factory or prefab manager, but technically they are all prefab instances in your scene, there only assets in there folder.Technivorous
PrinceOfRavens is right, scenes don't contain assets (including prefabs). Unity instead creates prototypes that it clones when you call Instantiate. But maybe there is a way to distinguish those prototypes.Nikaas
You maybe able to tell with docs.unity3d.com/ScriptReference/… - it sounds a bit like a long shotBugFinder
Be aware that some of the functions being used here are Editor methods that won't work when you build your game. I can't tell if you already know that or not.Draco18s no longer trusts SE

2 Answers

0
votes

I found a solution, although I don't think it's an ideal one.

public override void OnInspectorGUI()
{
   var component = this.target as MyScript;

   if (component.gameObject.scene.name.Equals(UnityEngine.SceneManagement.SceneManager.GetActiveScene().name))
   {
      Debug.Log("editing the prefab instance in the scene");          
   }
   else
   {
      Debug.Log("editing the prefab asset");       
   }
}
0
votes

I found out a solution that seems to be always working which is

if (gameObject.scene.name == null || gameObject.scene.name == gameObject.name)

I personally never name a scene the same way I name a prefab so it works well, but I prefer to warn that it will ignore object of the same name than the scene they are in.