Raised when a HierarchyViewItem is unbound from a HierarchyView. Use this event to clean up the view item. Note that hierarchy view items are recycled by their handler, so unbinding doesn't mean destruction. For performance reasons, the recommended best practice is to not undo styles or modifications done during binding in this unbind event.
The following example adds a button next to a GameObject in the Hierarchy window if that GameObject is a prefab instance. You can select the button to locate and highlight the prefab asset in the Project window. It uses UnbindViewItem to remove custom buttons added to HierarchyViewItem.RightCustomContainer during binding, because view items are pooled and reused.
The example requires a USS file called PrefabActionButtons.uss.
To use this example, save the script and USS file in a folder called Assets/Editor/PrefabActionButtons. Scripts in an Editor folder can use the Hierarchy module API without additional setup. If you save the script outside of an Editor folder, you must enable the Hierarchy built-in module in the Package Manager window, which also adds the module to your Player builds.
using Unity.Hierarchy; using Unity.Hierarchy.Editor; using UnityEditor; using UnityEngine; using UnityEngine.UIElements;
namespace Unity.HierarchySamples.Editor { class PrefabActionButtons { const string k_PingButtonClassName = "prefab-ping-button"; const string k_PingButtonText = "\u25B6";
[InitializeOnLoadMethod] static void Initialize() { HierarchyWindow.BindView += OnBindView; HierarchyWindow.BindViewItem += OnBindViewItem; HierarchyWindow.UnbindViewItem += OnUnbindViewItem; }
static void OnBindView(HierarchyWindow window, HierarchyView view) => view.styleSheets.Add(AssetDatabase.LoadAssetAtPath<StyleSheet>("Assets/Editor/PrefabActionButtons/PrefabActionButtons.uss"));
static void OnBindViewItem(HierarchyWindow window, HierarchyView view, HierarchyViewItem item) { if (item.Handler is not HierarchyGameObjectHandler handler) return;
GameObject gameObject = handler.GetGameObject(item.Node);
if (!PrefabUtility.IsPartOfPrefabInstance(gameObject)) return;
GameObject prefabRoot = PrefabUtility.GetOutermostPrefabInstanceRoot(gameObject); GameObject prefabAsset = PrefabUtility.GetCorrespondingObjectFromSource(prefabRoot);
if (prefabAsset == null) return;
Button pingButton = new Button(() => EditorGUIUtility.PingObject(prefabAsset)) { text = k_PingButtonText, tooltip = "Ping Prefab Asset in Project Browser" }; pingButton.AddToClassList(k_PingButtonClassName);
item.RightCustomContainer.Add(pingButton); }
static void OnUnbindViewItem(HierarchyWindow window, HierarchyView view, HierarchyViewItem item) { // Remove the button so it doesn't persist when this item is rebound. UQueryBuilder<Button> pingButtons = item.RightCustomContainer.Query<Button>(className: k_PingButtonClassName); pingButtons.ForEach(button => button.RemoveFromHierarchy()); } } }
The following example shows how to style PrefabActionButtons.uss.
.prefab-ping-button {
width: 16px;
height: 16px;
font-size: 8px;
padding-bottom: 4px;
margin-left: 2px;
margin-right: 2px;
-unity-text-align: middle-center;
}