Example #1
0
    /// <summary>
    /// Sets parent Transform of child, with option to skip Hierarchy Folders.
    /// When <paramref name="skipHierarchyFolders"/> is false will also automatically handle Flatten Hierarchy play mode behaviour (when enabled in preferences).
    /// </summary>
    /// <param name="child"> Child whose parent is being set. </param>
    /// <param name="parent"> New parent for child. </param>
    /// <param name="worldPositionStays"></param>
    /// <param name="skipHierarchyFolders">
    /// If true then Hierarchy Folders will be skipped when determining the parent. If <paramref name="parent"/> and all parents it might have are hierarchy folders,
    /// then <paramref name="child"/> will be moved to hierarchy root.
    /// </param>
    public static void SetParent([NotNull] this Transform child, [CanBeNull] Transform parent, bool worldPositionStays, bool skipHierarchyFolders)
    {
                #if UNITY_EDITOR
        if (parent != null && parent.gameObject.IsHierarchyFolder())
        {
            if (skipHierarchyFolders)
            {
                child.SetParent(parent.GetParent(true), worldPositionStays);
            }
            else if (HierarchyFolderPreferences.FlattenHierarchy)
            {
                int moveToIndex    = HierarchyFolderUtility.GetLastChildIndexInFlatMode(parent.gameObject);
                var parentOfFolder = parent.parent;
                child.transform.SetParent(parentOfFolder, worldPositionStays);
                if (moveToIndex < 0)
                {
                                        #if DEV_MODE
                    Debug.LogWarning("GetLastChildIndexInFlatMode result < 0");
                                        #endif
                    return;
                }
                child.transform.SetSiblingIndex(moveToIndex);
                return;
            }
        }
                #endif

        child.transform.SetParent(parent, worldPositionStays);
    }
Example #2
0
        private void OnHierarchyChangedInPlayModeFlattened()
        {
            if (this == null)
            {
                EditorApplication.hierarchyChanged -= OnHierarchyChangedInPlayModeFlattened;
                return;
            }

            OnHierarchyChangedShared();

                        #if DEV_MODE
            if (transform.childCount > 0)
            {
                if (HierarchyFolderUtility.NowStripping)
                {
                    Debug.LogWarning(name + " child count is " + transform.childCount + " but won't flatten because HierarchyFolderUtility.NowStripping already true.", gameObject);
                }
                else
                {
                    Debug.Log(name + " child count " + transform.childCount + ". Flattening now...", gameObject);
                }
            }
                        #endif

            if (transform.childCount > 0 && !HierarchyFolderUtility.NowStripping)
            {
                int moveToIndex = HierarchyFolderUtility.GetLastChildIndexInFlatMode(gameObject);
                for (int n = transform.childCount - 1; n >= 0; n--)
                {
                    var child = transform.GetChild(n);
                    child.SetParent(null, true);
                    child.SetSiblingIndex(moveToIndex);
                }
            }
        }
Example #3
0
        internal static void CreateHierarchyFolderParent()
        {
            int count = Selection.transforms.Length;

            var members = new Transform[count];

            Array.Copy(Selection.transforms, 0, members, 0, count);
            Array.Sort(members, SortByHierarchyOrder);

            var firstMember           = members[0];
            var hierarchyFolderParent = firstMember.parent;

            var folder = CreateHierarchyFolderInternal(firstMember is RectTransform);

            // if not all selected have the same parent, then create folders as last item in hierarchy
            for (int n = 1; n < count; n++)
            {
                if (members[n].parent != hierarchyFolderParent)
                {
                    hierarchyFolderParent = null;
                    break;
                }
            }

            if (hierarchyFolderParent != null)
            {
                folder.transform.UndoableSetParent(hierarchyFolderParent, "Hierarchy Folder Parent");
            }
            int hierarchyFolderSiblingIndex = firstMember.GetSiblingIndex();

            folder.transform.SetSiblingIndex(hierarchyFolderSiblingIndex);

            Undo.RegisterCreatedObjectUndo(folder, "Hierarchy Folder Parent");

                        #if UNITY_EDITOR
            if (EditorApplication.isPlayingOrWillChangePlaymode && HierarchyFolderPreferences.Get().playModeBehaviour == StrippingType.FlattenHierarchy)
            {
                int moveToIndex = HierarchyFolderUtility.GetLastChildIndexInFlatMode(folder);
                for (int n = count - 1; n >= 0; n--)
                {
                    Undo.SetTransformParent(members[n], hierarchyFolderParent, "Hierarchy Folder Parent");
                    members[n].SetSiblingIndex(moveToIndex);
                }
                return;
            }
                        #endif

            for (int n = 0; n < count; n++)
            {
                Undo.SetTransformParent(members[n], folder.transform, "Hierarchy Folder Parent");
                members[n].SetAsLastSibling();
            }

            Selection.activeGameObject = folder;
        }
Example #4
0
    /// <summary>
    /// Sets parent Transform of child, with option to skip Hierarchy Folders.
    /// When <paramref name="skipHierarchyFolders"/> is false will also automatically handle Flatten Hierarchy play mode behaviour (when enabled in preferences).
    /// </summary>
    /// <param name="child"> Child whose parent is being set. </param>
    /// <param name="parent"> New parent for child. </param>
    /// <param name="worldPositionStays"></param>
    /// <param name="skipHierarchyFolders">
    /// If true then Hierarchy Folders will be skipped when determining the parent. If <paramref name="parent"/> and all parents it might have are hierarchy folders,
    /// then <paramref name="child"/> will be moved to hierarchy root.
    /// </param>
    public static void UndoableSetParent([NotNull] this Transform child, [CanBeNull] Transform parent, string undoName, bool skipHierarchyFolders = false)
    {
                #if UNITY_EDITOR
        if (parent != null && parent.gameObject.IsHierarchyFolder())
        {
            if (skipHierarchyFolders)
            {
                if (!Application.isPlaying)
                {
                    Undo.SetTransformParent(child, parent.GetParent(true), undoName);                     //NOTE: Doesn't support worldPositionStays=false
                }
                else
                {
                    child.SetParent(parent.GetParent(true), true);
                }
            }
            else if (HierarchyFolderPreferences.FlattenHierarchy)
            {
                int moveToIndex    = HierarchyFolderUtility.GetLastChildIndexInFlatMode(parent.gameObject);
                var parentOfFolder = parent.parent;

                if (!Application.isPlaying)
                {
                    Undo.SetTransformParent(child, parentOfFolder, undoName);                     //NOTE: Doesn't support worldPositionStays=false
                }
                else
                {
                    child.transform.SetParent(parentOfFolder, true);
                }

                if (moveToIndex < 0)
                {
                                        #if DEV_MODE
                    Debug.LogWarning("GetLastChildIndexInFlatMode result < 0");
                                        #endif
                    return;
                }
                child.transform.SetSiblingIndex(moveToIndex);
                return;
            }
        }

        if (!Application.isPlaying)
        {
            Undo.SetTransformParent(child, parent, undoName);
            return;
        }
                #endif

        child.transform.SetParent(parent, true);
    }
        private void OnHierarchyChangedInPlayModeFlattened()
        {
            hierarchyFolders.RemoveAll(isNull);
            hierarchyFolders.Sort(compareHierarchyDepth);

            for (int n = 0, count = hierarchyFolders.Count - 1; n < count; n++)
            {
                var hierarchyFolder = hierarchyFolders[n];

                // Only process scene objects, not prefabs.
                if (!hierarchyFolder.gameObject.scene.IsValid())
                {
                    continue;
                }

                OnHierarchyChangedShared(hierarchyFolder);

                var transform = hierarchyFolder.transform;

                                #if DEV_MODE
                if (transform.childCount > 0)
                {
                    if (HierarchyFolderUtility.NowStripping)
                    {
                        Debug.LogWarning(hierarchyFolder.name + " child count is " + transform.childCount + " but won't flatten because HierarchyFolderUtility.NowStripping already true.", hierarchyFolder);
                    }
                    else
                    {
                        Debug.Log(hierarchyFolder.name + " child count " + transform.childCount + ". Flattening now...", hierarchyFolder);
                    }
                }
                                #endif

                if (transform.childCount > 0 && !HierarchyFolderUtility.NowStripping)
                {
                    // todo: should we keep track of flattened children in play mode? Or only for prefabs?
                    // Would there be benefits to keeping track of them?
                    // Could select them when hierarchy folder is double clicked in hierarchy view?
                    // Could draw some sort of bounds around the children in the hierarchy?!!!
                    int moveToIndex = HierarchyFolderUtility.GetLastChildIndexInFlatMode(transform.gameObject);
                    for (int c = transform.childCount - 1; c >= 0; c--)
                    {
                        var child = transform.GetChild(c);
                        child.SetParent(null, true);
                        child.SetSiblingIndex(moveToIndex);
                    }
                }
            }

            hierarchyFolders.RemoveAll(isNull);
        }