- Home /
PrefabUtility - Check if Changes have been made to Prefab?
Hello,
I'm working on an EditorScript Window to help with my workflow within Unity. I want to be able to check if a prefab within the Scene has been modified in any way (such as a child of the prefab has been moved slightly).
Basically - I want to be able to tell the developer that a specific prefab within the scene has been modified but NOT applied, and from then, it will alert the developer to Apply the prefab before Removing it from the scene.
I am able to check if the Prefab has been Applied (or Updated) by 'PrefabUtility.prefabInstanceUpdated' which is also useful to me, but not for this particular case.
Is there something like this that exists? :
//reference to the prefab within the scene
GameObject _scene_prefab;
void GUI(){
if(PrefabUtility._HasBeenModified_(_scene_prefab) == true)
Debug.Log("Prefab has been modified");
else
Debug.Log("Prefab has not been modified");
}
Thanks.
Answer by edwardrowe · Aug 31, 2016 at 04:01 PM
As u/danilonishimura suggested you can use GetPropertyModifications to get a list of modifications, though that won't give you the complete picture for instances in scenes.
Since you place prefab instances into scenes (that's what they're for), they will always have their Transforms modified. If you look, you'll see position is always bold in the Inspector, even if it matches the parent. Same with RootOrder (transform sibling index).
Another thing it won't tell you is if you add a component, or add a transform to one of the children.
Unfortunately, there's no Unity function that I've found to tell you if it's been modified outside of that. The only way I know to fix it is to write your own. If all you care about is PropertyModifications, it's easy enough to use the suggested function in PrefabUtility, and ignore the transform properties:
var propertyModifications = PrefabUtility.GetPropertyModfiications(gameObject);
foreach (var propertyModification in propertyModifications)
{
if (modification.target.name == gameObject &&
modification.propertyPath == "m_LocalPosition.x")
{
// Do not consider this as a modification, since it's a modification on the root's transform.
}
}
Something like that.
Answer by danilonishimura · Jun 23, 2016 at 03:31 PM
Check out the docs https://docs.unity3d.com/ScriptReference/PrefabUtility.html I think what you're looking for is the GetPropertyModifications method.
Thanks, I saw this - but I don't actually know how to implement it? The documentation is very weak.
Well, it should be pretty straight forward. You pass a reference to a prefab instance and the method returns a list of differences compared to it's prefab.
It returns an array of Property$$anonymous$$odification instances. Each element represents a modification. Since you're only interested in if there is any modification you might be able to just check the legnth of the array. However it's possible that a different position of the object counts as modification as well.
Answer by Landerk · Jun 24, 2016 at 05:02 AM
When you change a property of a prefab, it will show bold in the Inspector. Once the change is applied, it goes back to normal. This can be hard to see, though, so I like the idea of a Debug.Log message.