Exemplo n.º 1
0
    public virtual void SetUpSheet()
    {
        Infos      = new SpriteData();
        Infos.List = new List <List <List <SpriteInfo> > >();
        for (int i = 0; i < spriteList.Count; i++)
        {
            Infos.List.Add(new List <List <SpriteInfo> >());
            var path = AssetDatabase.GetAssetPath(spriteList[i])
                       .Substring(17);          //Substring(17) To remove the "Assets/Resources/"
            Sprite[] spriteSheetSprites = Resources.LoadAll <Sprite>(path.Remove(path.Length - 4));
            if (spriteSheetSprites.Length > 1)
            {
                var p = AssetDatabase.GetAssetPath(spriteList[i]);
                int extensionIndex = p.LastIndexOf(".");
                p = p.Substring(0, extensionIndex) + ".json";
                string json = System.IO.File.ReadAllText(p);
                Logger.Log(json.ToString());
                spriteJson = JsonConvert.DeserializeObject <SpriteJson>(json);

                int c    = 0;
                int cone = 0;
                for (int J = 0; J < spriteJson.Number_Of_Variants; J++)
                {
                    Infos.List[i].Add(new List <SpriteInfo>());
                }

                foreach (var SP in spriteSheetSprites)
                {
                    var info = new SpriteInfo();
                    info.sprite = SP;
                    if (spriteJson.Delays.Count > 0)
                    {
                        info.waitTime = spriteJson.Delays[c][cone];
                    }

                    Infos.List[i][c].Add(info);

                    if (c >= (spriteJson.Number_Of_Variants - 1))
                    {
                        c = 0;
                        cone++;
                    }
                    else
                    {
                        c++;
                    }
                }
            }
            else
            {
                var info = new SpriteInfo()
                {
                    sprite   = spriteSheetSprites[0],
                    waitTime = 0
                };
                Infos.List[i].Add(new List <SpriteInfo>());
                Infos.List[i][0].Add(info);
            }
        }

        Infos.SerializeT();

        var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();

        if (prefabStage != null)
        {
            EditorSceneManager.MarkSceneDirty(prefabStage.scene);
            Logger.Log("Setup Complete", Category.SpriteHandler);
        }
    }
Exemplo n.º 2
0
        static void DrawSkeletons(SceneView sceneview)
        {
            var gizmoColor = Gizmos.color;

            pyramidMeshRenderer.Clear();
            boxMeshRenderer.Clear();

            for (var i = 0; i < s_BoneRendererComponents.Count; i++)
            {
                var boneRenderer = s_BoneRendererComponents[i];

                if (boneRenderer.bones == null)
                {
                    continue;
                }

                PrefabStage prefabStage = PrefabStageUtility.GetCurrentPrefabStage();
                if (prefabStage != null)
                {
                    StageHandle stageHandle = prefabStage.stageHandle;
                    if (stageHandle.IsValid() && !stageHandle.Contains(boneRenderer.gameObject))
                    {
                        continue;
                    }
                }

                if (boneRenderer.drawBones)
                {
                    var size           = boneRenderer.boneSize * 0.025f;
                    var shape          = boneRenderer.boneShape;
                    var color          = boneRenderer.boneColor;
                    var nubColor       = new Color(color.r, color.g, color.b, color.a);
                    var selectionColor = Color.white;

                    for (var j = 0; j < boneRenderer.bones.Length; j++)
                    {
                        var bone = boneRenderer.bones[j];
                        if (bone.first == null || bone.second == null)
                        {
                            continue;
                        }

                        DoBoneRender(bone.first, bone.second, shape, color, size);
                    }

                    for (var k = 0; k < boneRenderer.tips.Length; k++)
                    {
                        var tip = boneRenderer.tips[k];
                        if (tip == null)
                        {
                            continue;
                        }

                        DoBoneRender(tip, null, shape, color, size);
                    }
                }

                if (boneRenderer.drawTripods)
                {
                    var size = boneRenderer.tripodSize * 0.025f;
                    for (var j = 0; j < boneRenderer.transforms.Length; j++)
                    {
                        var tripodSize = 1f;
                        var transform  = boneRenderer.transforms[j];
                        if (transform == null)
                        {
                            continue;
                        }

                        var position = transform.position;
                        var xAxis    = position + transform.rotation * Vector3.right * size * tripodSize;
                        var yAxis    = position + transform.rotation * Vector3.up * size * tripodSize;
                        var zAxis    = position + transform.rotation * Vector3.forward * size * tripodSize;

                        Handles.color = Color.red;
                        Handles.DrawLine(position, xAxis);
                        Handles.color = Color.green;
                        Handles.DrawLine(position, yAxis);
                        Handles.color = Color.blue;
                        Handles.DrawLine(position, zAxis);
                    }
                }
            }

            pyramidMeshRenderer.Render();
            boxMeshRenderer.Render();

            Gizmos.color = gizmoColor;
        }
        private void DoPrefabButtons()
        {
            if (!m_IsPrefabInstanceAnyRoot || m_IsAsset)
            {
                return;
            }

            using (new EditorGUI.DisabledScope(m_PlayModeObjects))
            {
                EditorGUILayout.BeginHorizontal(Styles.prefabButtonsHorizontalLayout);

                // Prefab information
                PrefabAssetType      singlePrefabType     = PrefabUtility.GetPrefabAssetType(target);
                PrefabInstanceStatus singleInstanceStatus = PrefabUtility.GetPrefabInstanceStatus(target);
                GUIContent           prefixLabel;
                if (targets.Length > 1)
                {
                    prefixLabel = Styles.goTypeLabelMultiple;
                }
                else
                {
                    prefixLabel = Styles.goTypeLabel[(int)singlePrefabType, (int)singleInstanceStatus];
                }

                if (prefixLabel != null)
                {
                    EditorGUILayout.BeginHorizontal(GUILayout.Width(kIconSize + Styles.tagFieldWidth));
                    GUILayout.FlexibleSpace();
                    if (m_IsDisconnected || m_IsMissing)
                    {
                        GUI.contentColor = GUI.skin.GetStyle("CN StatusWarn").normal.textColor;
                        GUILayout.Label(prefixLabel, EditorStyles.whiteLabel, GUILayout.ExpandWidth(false));
                        GUI.contentColor = Color.white;
                    }
                    else
                    {
                        GUILayout.Label(prefixLabel, GUILayout.ExpandWidth(false));
                    }
                    EditorGUILayout.EndHorizontal();
                }

                if (!m_IsMissing)
                {
                    using (new EditorGUI.DisabledScope(targets.Length > 1))
                    {
                        if (singlePrefabType == PrefabAssetType.Model)
                        {
                            // Open Model Prefab
                            if (GUILayout.Button(Styles.openString, EditorStyles.miniButtonLeft))
                            {
                                GameObject asset = PrefabUtility.GetOriginalSourceOrVariantRoot(target);
                                AssetDatabase.OpenAsset(asset);
                                GUIUtility.ExitGUI();
                            }
                        }
                        else
                        {
                            // Open non-Model Prefab
                            using (new EditorGUI.DisabledScope(m_ImmutableSourceAsset))
                            {
                                if (GUILayout.Button(Styles.openString, EditorStyles.miniButtonLeft))
                                {
                                    GameObject asset = PrefabUtility.GetOriginalSourceOrVariantRoot(target);
                                    PrefabStageUtility.OpenPrefab(AssetDatabase.GetAssetPath(asset), (GameObject)target, StageNavigationManager.Analytics.ChangeType.EnterViaInstanceInspectorOpenButton);
                                    GUIUtility.ExitGUI();
                                }
                            }
                        }
                    }

                    // Select prefab
                    if (GUILayout.Button(Styles.selectString, EditorStyles.miniButtonRight))
                    {
                        HashSet <GameObject> selectedAssets = new HashSet <GameObject>();
                        for (int i = 0; i < targets.Length; i++)
                        {
                            GameObject prefabGo = PrefabUtility.GetOriginalSourceOrVariantRoot(targets[i]);

                            // Because of legacy prefab references we have to have this extra step
                            // to make sure we ping the prefab asset correctly.
                            // Reason is that scene files created prior to making prefabs CopyAssets
                            // will reference prefabs as if they are serialized assets. Those references
                            // works fine but we are not able to ping objects loaded directly from the asset
                            // file, so we have to make sure we ping the metadata version of the prefab.
                            var assetPath = AssetDatabase.GetAssetPath(prefabGo);
                            selectedAssets.Add((GameObject)AssetDatabase.LoadMainAssetAtPath(assetPath));
                        }

                        Selection.objects = selectedAssets.ToArray();
                        if (Selection.gameObjects.Length == 1)
                        {
                            EditorGUIUtility.PingObject(Selection.activeObject);
                        }
                    }

                    // Should be EditorGUILayout.Space, except it does not have ExpandWidth set to false.
                    // Maybe we can change that?
                    GUILayoutUtility.GetRect(6, 6, GUILayout.ExpandWidth(false));

                    // Reserve space regardless of whether the button is there or not to avoid jumps in button sizes.
                    Rect rect = GUILayoutUtility.GetRect(Styles.overridesContent, Styles.overridesDropdown);
                    if (m_IsPrefabInstanceOutermostRoot)
                    {
                        if (EditorGUI.DropdownButton(rect, Styles.overridesContent, FocusType.Passive))
                        {
                            if (targets.Length > 1)
                            {
                                PopupWindow.Show(rect, new PrefabOverridesWindow(targets.Select(e => (GameObject)e).ToArray()));
                            }
                            else
                            {
                                PopupWindow.Show(rect, new PrefabOverridesWindow((GameObject)target));
                            }
                            GUIUtility.ExitGUI();
                        }
                    }
                }
                EditorGUILayout.EndHorizontal();
            }
        }
Exemplo n.º 4
0
        protected override DragAndDropVisualMode HandleDragAndDrop(DragAndDropArgs args)
        {
            var objectReferences = DragAndDrop.objectReferences;

            if (objectReferences == null || objectReferences.Length == 0)
            {
                return(DragAndDropVisualMode.Rejected);
            }

            var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();
            var validItems  = new List <Object>(objectReferences.Length);

            foreach (var reference in objectReferences)
            {
                // reject any objects from assets
                if (AssetDatabase.Contains(reference))
                {
                    continue;
                }

                var validObject = false;
                var component   = reference as Component;
                var gameObject  = reference as GameObject;
                if (component != null)
                {
                    gameObject = component.gameObject;
                }
                else if (gameObject == null)
                {
                    continue;
                }

                if (gameObject != null)
                {
                    if (prefabStage != null && PrefabStageUtility.GetPrefabStage(gameObject) == prefabStage)
                    {
                        validObject = true;
                    }
                    else if (gameObject.scene.IsValid())
                    {
                        validObject = true;
                    }
                }

                if (validObject)
                {
                    validItems.Add(reference);
                }
            }

            if (validItems.Count == 0)
            {
                return(DragAndDropVisualMode.Rejected);
            }

            if (Event.current.type == EventType.DragPerform)
            {
                var alt = Event.current.alt;

                EditorApplication.delayCall += () =>
                {
                    ReferencesFinder.FindObjectsReferencesInHierarchy(validItems.ToArray(), !alt);
                };
                DragAndDrop.AcceptDrag();
            }

            return(DragAndDropVisualMode.Generic);
        }
Exemplo n.º 5
0
        /// <summary>
        /// Get every basic prefab-related info about this node.
        /// </summary>
        public static Properties GetPrefabProperties(GameObject gameObject)
        {
            if (gameObject == null)
            {
                return(null);
            }

            Properties p = new Properties(gameObject);

#if false // Does not required anymore, also generate warning in Editor
          // Wappen hack: From https://forum.unity.com/threads/problem-with-prefab-api-upgrade.537074/
          // Check if it is nesting prefab
          //bool isPartOfPrefabInstance = PrefabUtility.IsPartOfPrefabInstance(gameObject);
#endif

            // First group of check is to test everything about "Prefab Asset"
            {
                // First is to determine isPartOfPrefabAsset
                p.isPartOfPrefabAsset = PrefabUtility.IsPartOfPrefabAsset(gameObject);

                // Second alternate test, using direct AssetDatabase
                if (!p.isPartOfPrefabAsset)
                {
                    p.isPartOfPrefabAsset = !string.IsNullOrEmpty(AssetDatabase.GetAssetPath(gameObject));
                }

                // If it is under prefab asset, determine its root
                // Use gameObject.transform.root.gameObject to test for prefab asset root.
                if (p.isPartOfPrefabAsset)
                {
                    p.prefabAssetRoot   = gameObject.transform.root.gameObject;
                    p.isPrefabAssetRoot = (gameObject == p.prefabAssetRoot);
                    p.prefabAssetType   = PrefabUtility.GetPrefabAssetType(gameObject);
                }
            }

            // Second group of check is to test everything about "Prefab Instance"
            // This is when you instance an prefab asset into scene or nested under other prefab.
            // First check is obvious, it should not and cannot be prefab asset root in the first place.
            if (!p.isPrefabAssetRoot)
            {
                // Use PrefabUtility.GetNearestPrefabInstanceRoot to test for prefab instance root.

                /* Basic visualization
                 * The node with its [Name] inside bracket is blue gameobject node.
                 * See image in https://docs.unity3d.com/ScriptReference/PrefabUtility.GetNearestPrefabInstanceRoot.html
                 * For possible prefab configuration
                 *
                 * - [OUTERMOST]
                 *   - CHILD 1
                 *   - CHILD 2
                 *   - [prefab instance head] < If we are running on this node, isPrefabInstanceRoot = true
                 *     - child 1
                 *     - child 2 < If we are running on this node, isPrefabInstanceRoot = false, but we still have nearestInstanceRoot points to 'prefab instance head'
                 */

                // Note: "PrefabUtility.GetNearestPrefabInstanceRoot" Causes following warning message on editor:
                // SendMessage cannot be called during Awake, CheckConsistency, or OnValidate
                // If this API is called in such timing, it is unavoidable, live with it
                // https://forum.unity.com/threads/sendmessage-cannot-be-called-during-awake-checkconsistency-or-onvalidate-can-we-suppress.537265/
                p.nearestInstanceRoot    = PrefabUtility.GetNearestPrefabInstanceRoot(gameObject);
                p.isPartOfPrefabInstance = (p.nearestInstanceRoot != null);
                p.isPrefabInstanceRoot   = gameObject == p.nearestInstanceRoot; // Equivalent to PrefabUtility.IsAnyPrefabInstanceRoot, see UnityReferenceSource
            }

            // Third test is testing everything about Prefab stage property
            // needed to be checked separately as it is very special rule
            var editorPrefabStage = PrefabStageUtility.GetCurrentPrefabStage( );
            if (editorPrefabStage != null)
            {
                // We are in prefab stage, but is selected gameobject really an object from prefab stage?
                // There is no 100% direct API to determine this, plus there is following observed obstacle when in prefab stage:
                // - root object editing in prefab stage wont have connection to its original prefab (it becomes gray gameobject icon), so we cannot test it with any prefab API. (bad)
                // - Also cannot test for 'editorPrefabStage.prefabContentsRoot == gameObject.transform.root.gameObject' directly, both seems to always be different object instance.
                // but we could derive from the following fact:

                // If it was NOT under prefab asset (from above test)
                // we can almost sure that it is in prefab stage
                if (p.isPartOfPrefabAsset == false)
                {
                    p.isPartOfPrefabStage = true;
                }

                // Editor prefab stage root object wont have transform.parent
                // That's how we determine if it is isPrefabStageRoot
                if (p.isPartOfPrefabStage && gameObject.transform.parent == null)
                {
                    p.isPrefabStageRoot = true;
                }
            }

            // AssetPath determination
            // PrefabHelper will try its best to detect most accurate prefab path for this prefab
            // Has to be done separately based on API priority
            if (p.isRootOfAnyPrefab)
            {
                if (p.isPrefabStageRoot)
                {
                    p.prefabAssetPath = editorPrefabStage.prefabAssetPath;
                }
                else if (p.isPrefabInstanceRoot)  // It is nested prefab instance inside another prefab
                {
                    // Note: GetPrefabAssetPathOfNearestInstanceRoot is the only way to obtain real asset path of this nested prefab instance
                    // internally it uses PrefabUtility.GetOriginalSourceOrVariantRoot which is internal function to Unity, see UnityReferenceSource
                    // FYI: Calling GetAssetPath will get the "top/outermost" one. Not this nested one. (dont want that)
                    p.prefabAssetPath = PrefabUtility.GetPrefabAssetPathOfNearestInstanceRoot(p.nearestInstanceRoot);
                }
                else if (p.isPrefabAssetRoot)
                {
                    // Ordinary prefab asset root
                    p.prefabAssetPath = AssetDatabase.GetAssetPath(gameObject);
                }
            }
            else
            {
                // This object is not root of any prefab, but could still be part of some prefab, find that nearest asset path
                if (p.isPartOfPrefabStage)
                {
                    p.prefabAssetPath = editorPrefabStage.prefabAssetPath;
                }
                else if (p.isPartOfPrefabInstance)
                {
                    p.prefabAssetPath = PrefabUtility.GetPrefabAssetPathOfNearestInstanceRoot(p.nearestInstanceRoot);
                }
                else if (p.isPartOfPrefabAsset)
                {
                    p.prefabAssetPath = AssetDatabase.GetAssetPath(gameObject.transform.root.gameObject);
                }
            }

            return(p);
        }
Exemplo n.º 6
0
        public bool IsEditingAPrefabAsset()
        {
            var stage = PrefabStageUtility.GetCurrentPrefabStage();

            return(stage != null && editSequence.director != null && stage.IsPartOfPrefabContents(editSequence.director.gameObject));
        }
Exemplo n.º 7
0
        public static string GetHierarchyPath(GameObject gameObject, bool includeScene = true)
        {
            if (gameObject == null)
                return String.Empty;

            StringBuilder sb;
            if (_SbPool.Count > 0)
            {
                sb = _SbPool.Pop();
                sb.Clear();
            }
            else
            {
                sb = new StringBuilder(200);
            }

            try
            {
                if (includeScene)
                {
                    var sceneName = gameObject.scene.name;
                    if (sceneName == string.Empty)
                    {
                        #if UNITY_2018_3_OR_NEWER
                        var prefabStage = PrefabStageUtility.GetPrefabStage(gameObject);
                        if (prefabStage != null)
                        {
                            sceneName = "Prefab Stage";
                        }
                        else
                        #endif
                        {
                            sceneName = "Unsaved Scene";
                        }
                    }

                    sb.Append("<b>" + sceneName + "</b>");
                }

                sb.Append(GetTransformPath(gameObject.transform));

                #if false
                bool isPrefab;
                #if UNITY_2018_3_OR_NEWER
                isPrefab = PrefabUtility.GetPrefabAssetType(gameObject.gameObject) != PrefabAssetType.NotAPrefab;
                #else
                isPrefab = UnityEditor.PrefabUtility.GetPrefabType(o) == UnityEditor.PrefabType.Prefab;
                #endif
                var assetPath = string.Empty;
                if (isPrefab)
                {
                    #if UNITY_2018_3_OR_NEWER
                    assetPath = PrefabUtility.GetPrefabAssetPathOfNearestInstanceRoot(gameObject);
                    #else
                    assetPath = AssetDatabase.GetAssetPath(gameObject);
                    #endif
                    sb.Append(" (" + System.IO.Path.GetFileName(assetPath) + ")");
                }
                #endif

                var path = sb.ToString();
                sb.Clear();
                return path;
            }
            finally
            {
                _SbPool.Push(sb);
            }
        }
Exemplo n.º 8
0
        private static void Reference(Transform root, GameObject gameObject, Object value, bool stackReferencer, GameObject prefab)
        {
            var holder = default(GameObject);

            var existingReferencer = root.GetComponentInChildren <IReferencer>() as Component;

            if (existingReferencer != null)
            {
                holder = existingReferencer.gameObject;
            }
            else
            {
                holder = new GameObject("Referencer");

                GameObjectUtility.SetParentAndAlign(holder, root.gameObject);
                holder.transform.SetAsFirstSibling();

                Undo.RegisterCreatedObjectUndo(holder, "Create " + holder.name);
            }

            Object referencer = stackReferencer ? (Object)holder.AddComponent <StackReferencer>() : holder.AddComponent <Referencer>();

            var serializedObject = new SerializedObject(referencer);
            var valueProperty    = serializedObject.FindProperty("value");

            valueProperty.objectReferenceInstanceIDValue = value.GetInstanceID();

            var rootPath = "Assets/Objects";

            if (!Directory.Exists(rootPath))
            {
                Directory.CreateDirectory(rootPath);
            }

            var componentIndex = Array.IndexOf(gameObject.GetComponents <Component>(), value);
            var type           = componentIndex == -1 ? value.GetType().Name : $"[{componentIndex}]{value.GetType().Name}";

            var tokenPath = string.Empty;
            var isPrefab  = false;

            if (prefab != null)
            {
                var prefabPath = $"{rootPath}/Prefabs";
                if (!Directory.Exists(prefabPath))
                {
                    Directory.CreateDirectory(prefabPath);
                }

                tokenPath = $"{prefabPath}/{prefab.name}-{type}-{value.name}Token.asset";
                isPrefab  = true;
            }
            else
            {
                var scenePath = $"{rootPath}/Scenes";
                if (!Directory.Exists(scenePath))
                {
                    Directory.CreateDirectory(scenePath);
                }

                var activeScene      = SceneManager.GetActiveScene();
                var currentScenePath = $"{scenePath}/{activeScene.name}";
                if (!Directory.Exists(currentScenePath))
                {
                    Directory.CreateDirectory(currentScenePath);
                }

                var number = activeScene.buildIndex.ToString().Remove(0, 1);
                var index  = activeScene.buildIndex < 10 ? $"0{number}" : number;
                var prefix = string.Concat(activeScene.name.Where(c => c >= 'A' && c <= 'Z')) + index;
                tokenPath = $"{currentScenePath}/{prefix}-{type}-{value.name}Token.asset";
            }

            var token = ScriptableObject.CreateInstance <Token>();

            AssetDatabase.CreateAsset(token, tokenPath);

            AssetDatabase.SaveAssets();
            AssetDatabase.Refresh();

            var tokenProperty = serializedObject.FindProperty("token");

            tokenProperty.objectReferenceInstanceIDValue = token.GetInstanceID();

            serializedObject.ApplyModifiedProperties();
            if (isPrefab && PrefabStageUtility.GetCurrentPrefabStage() == null)
            {
                PrefabUtility.ApplyPrefabInstance(prefab, InteractionMode.UserAction);
            }

            Selection.activeObject = referencer;
            EditorGUIUtility.PingObject(referencer);
        }
Exemplo n.º 9
0
        public override void OnInspectorGUI()
        {
            EditorGUILayout.BeginVertical(EditorStyles.inspectorFullWidthMargins);

            // Allow opening prefab even if file is not open for edit.
            // For things with explicit save operations (scenes, prefabs) we allow editing
            // and handle the potential version control conflict at the time when the user saves.
            bool wasEnabled = GUI.enabled;

            GUI.enabled = true;
            using (new EditorGUI.DisabledScope(assetTargets.Length > 1))
            {
                GUILayout.Space(10);

                EditorGUILayout.BeginHorizontal();
                GUILayout.FlexibleSpace();
                if (GUILayout.Button(Styles.openContent, Styles.openButtonStyle))
                {
                    // We only support opening one prefab at a time (so do not use 'targets')
                    PrefabStageUtility.OpenPrefab(AssetDatabase.GetAssetPath(assetTarget), null, StageNavigationManager.Analytics.ChangeType.EnterViaAssetInspectorOpenButton);

                    GUIUtility.ExitGUI();
                }
                GUILayout.FlexibleSpace();
                EditorGUILayout.EndHorizontal();

                GUILayout.Space(5);

                if (!hasMissingScripts && !m_SavingHasFailed)
                {
                    EditorGUILayout.HelpBox(Styles.openHelpText.text, MessageType.Info, true);
                }
            }
            GUI.enabled = wasEnabled;

            if (hasMissingScripts)
            {
                if (assetTargets.Length > 1)
                {
                    // List all assets that have missing scripts (but only if we have a multi-selection)
                    GUILayout.Space(5);
                    EditorGUILayout.HelpBox(Styles.multiSelectionMissingScriptsHelpText.text, MessageType.Warning, true);
                    using (new EditorGUILayout.HorizontalScope())
                    {
                        GUILayout.Space(10);

                        using (new EditorGUILayout.VerticalScope())
                        {
                            foreach (var prefabAssetPath in m_PrefabsWithMissingScript)
                            {
                                if (GUILayout.Button(prefabAssetPath, EditorStyles.label))
                                {
                                    PrefabStageUtility.OpenPrefab(prefabAssetPath);
                                }
                            }
                        }
                    }
                }
                else
                {
                    EditorGUILayout.HelpBox(Styles.missingScriptsHelpText.text, MessageType.Warning, true);
                }
            }
            else if (m_SavingHasFailed)
            {
                EditorGUILayout.HelpBox(Styles.savingFailedHelpText.text, MessageType.Warning, true);
            }

            EditorGUILayout.EndVertical();
        }
Exemplo n.º 10
0
        private void LateUpdate()
        {
#if UNITY_EDITOR
            // We don't run in "prefab scenes", i.e. when editing a prefab. Bail out if prefab scene is detected.
            if (PrefabStageUtility.GetCurrentPrefabStage() != null)
            {
                return;
            }
#endif

            if (OceanRenderer.Instance == null || !ShowEffect())
            {
                _rend.enabled = false;
                return;
            }

            // Pass true in last arg for a crap reason - in edit mode LateUpdate can be called very frequently, and the height sampler mistakenly thinks
            // this is erroneous and complains.
            _sampleWaterHeight.Init(transform.position, 0f, true);
            _sampleWaterHeight.Sample(out var waterHeight);

            float heightOffset = transform.position.y - waterHeight;

            // Disable skirt when camera not close to water. In the first few frames collision may not be avail, in that case no choice
            // but to assume enabled. In the future this could detect if camera is far enough under water, render a simple quad to avoid
            // finding the intersection line.
            _rend.enabled = heightOffset < _maxHeightAboveWater;

            if (_rend.enabled)
            {
                if (_copyParamsEachFrame)
                {
                    _rend.sharedMaterial.CopyPropertiesFromMaterial(OceanRenderer.Instance.OceanMaterial);
                }

                // Assign lod0 shape - trivial but bound every frame because lod transform comes from here
                if (_mpb == null)
                {
                    _mpb = new PropertyWrapperMPB();
                }
                _rend.GetPropertyBlock(_mpb.materialPropertyBlock);

                // Underwater rendering uses displacements for intersecting the waves with the near plane, and ocean depth/shadows for ScatterColour()
                _mpb.SetInt(LodDataMgr.sp_LD_SliceIndex, 0);
                OceanRenderer.Instance._lodDataAnimWaves.BindResultData(_mpb);

                if (OceanRenderer.Instance._lodDataSeaDepths != null)
                {
                    OceanRenderer.Instance._lodDataSeaDepths.BindResultData(_mpb);
                }
                else
                {
                    LodDataMgrSeaFloorDepth.BindNull(_mpb);
                }

                if (OceanRenderer.Instance._lodDataShadow != null)
                {
                    OceanRenderer.Instance._lodDataShadow.BindResultData(_mpb);
                }
                else
                {
                    LodDataMgrShadow.BindNull(_mpb);
                }

                _mpb.SetFloat(sp_HeightOffset, heightOffset);

                _mpb.SetVector(OceanChunkRenderer.sp_InstanceData, new Vector3(OceanRenderer.Instance.ViewerAltitudeLevelAlpha, 0f, 0f));

                _rend.SetPropertyBlock(_mpb.materialPropertyBlock);
            }
        }
Exemplo n.º 11
0
        private void OnGUI()
        {
            // Find max label width.
            var maxLabelWidth = 110.0f;

            for (int i = 0; i < lxfml.groups.Length; i++)
            {
                var size = EditorStyles.boldLabel.CalcSize(new GUIContent(lxfml.groups[i].name));
                maxLabelWidth = Mathf.Max(maxLabelWidth, size.x);
            }

            minSize = new Vector2(leftMargin + maxLabelWidth + 360, 226);
            maxSize = new Vector2(leftMargin + maxLabelWidth + 360, 2000);

            scrollPosition = GUILayout.BeginScrollView(scrollPosition, false, false);

            GUI.Box(new Rect(20, 20, 100, 100), logoTexture);

            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 20.0f, 100.0f), "Colliders", "Add colliders to bricks.");
            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 50.0f, 100.0f), "Connectivity", "Add connectivity to bricks. Connectivity requires colliders.");

            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 100.0f, 100.0f), "Static", "Make bricks static.");
            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 130.0f, 100.0f), "Lightmapped", "Add lightmap UVs to bricks. Bricks must be static to be lightmapped.");

            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 180.0f, 100.0f), "Randomize Rotation", "Slightly rotate bricks to improve realism.");
            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 230.0f, 100.0f), "Prefer Legacy", "Prefer legacy geometry over new geometry.");
            CreateHeaderUI(new Vector2(leftMargin + maxLabelWidth + 280.0f, 100.0f), "LOD", "LOD 0 includes chamfered edges.\nLOD 1 does not.\nLOD 2 simplifies knobs.");

            // Reserve the space for the GUILayout scroll view.
            GUILayout.Space(135.0f);
            var nextY = 135.0f;

            var showAllBoolsUI = model == null && group == null && lxfml.groups.Length > 1; // When importing a new model, just check if there is more than one lxfml group.

            showAllBoolsUI |= model != null && importSettings.Count > 1;                    // When reimporting an entire model, check if the existing model has more than one group.
            if (showAllBoolsUI)
            {
                CreateAllBoolsUI(new Vector2(leftMargin + maxLabelWidth + 15.0f, nextY), importSettings, "colliders", "connectivity", null);
                CreateAllBoolsUI(new Vector2(leftMargin + maxLabelWidth + 45.0f, nextY), importSettings, "connectivity", null, "colliders");

                CreateAllBoolsUI(new Vector2(leftMargin + maxLabelWidth + 95.0f, nextY), importSettings, "isStatic", "lightmapped", null);
                CreateAllBoolsUI(new Vector2(leftMargin + maxLabelWidth + 125.0f, nextY), importSettings, "lightmapped", null, "isStatic");

                CreateAllBoolsUI(new Vector2(leftMargin + maxLabelWidth + 175.0f, nextY), importSettings, "randomizeRotation");
                CreateAllBoolsUI(new Vector2(leftMargin + maxLabelWidth + 225.0f, nextY), importSettings, "preferLegacy");
                CreateAllLODsUI(new Vector2(leftMargin + maxLabelWidth + 275.0f, nextY), importSettings);

                // Reserve the space for the GUILayout scroll view.
                GUILayout.Space(25.0f);
                nextY += 25.0f;
            }

            var collidersOrConnectivityWhilePreferringLegacy = false;

            for (int i = 0; i < lxfml.groups.Length; i++)
            {
                var showGroup = group == null && model == null;              // When importing a new model, show all groups.
                showGroup |= model != null && importSettings.ContainsKey(i); // When reimporting an entire model, only show groups already in the existing model.
                showGroup |= group != null && i == group.number;             // When reimporting a model group, only show that group.
                if (showGroup)
                {
                    GUI.Label(new Rect(leftMargin, nextY, maxLabelWidth, 20.0f), lxfml.groups[i].name);

                    CreateBoolUI(new Vector2(leftMargin + maxLabelWidth + 15.0f, nextY), importSettings, "colliders", i, "connectivity", null);
                    CreateBoolUI(new Vector2(leftMargin + maxLabelWidth + 45.0f, nextY), importSettings, "connectivity", i, null, "colliders");

                    CreateBoolUI(new Vector2(leftMargin + maxLabelWidth + 95.0f, nextY), importSettings, "isStatic", i, "lightmapped", null);
                    CreateBoolUI(new Vector2(leftMargin + maxLabelWidth + 125.0f, nextY), importSettings, "lightmapped", i, null, "isStatic");

                    CreateBoolUI(new Vector2(leftMargin + maxLabelWidth + 175.0f, nextY), importSettings, "randomizeRotation", i);
                    CreateBoolUI(new Vector2(leftMargin + maxLabelWidth + 225.0f, nextY), importSettings, "preferLegacy", i);
                    CreateLODUI(new Vector2(leftMargin + maxLabelWidth + 275.0f, nextY), importSettings, i);

                    if ((importSettings[i].colliders || importSettings[i].connectivity) && importSettings[i].preferLegacy)
                    {
                        collidersOrConnectivityWhilePreferringLegacy = true;
                    }

                    // Reserve the space for the GUILayout scroll view.
                    GUILayout.Space(20.0f);
                    nextY += 20.0f;
                }
            }

            if (collidersOrConnectivityWhilePreferringLegacy)
            {
                EditorGUI.HelpBox(new Rect(leftMargin, nextY, position.width - leftMargin - 20.0f, 38.0f), "Legacy parts might not contain colliders or connectivity information.", MessageType.Warning);
                // Reserve the space for the GUILayout scroll view.
                GUILayout.Space(42.0f);
                nextY += 42.0f;
            }

            // Reserve the space for the GUILayout scroll view.
            GUILayout.Space(5.0f);
            nextY += 5.0f;

            // Only show pivot option when not reimporting group.
            if (group == null)
            {
                GUI.Label(new Rect(leftMargin, nextY, maxLabelWidth, 20.0f), "Pivot");
                pivot = (Model.Pivot)EditorGUI.EnumPopup(new Rect(leftMargin + maxLabelWidth + 15.0f, nextY, 126.0f, 16.0f), pivot);

                // Reserve the space for the GUILayout scroll view.
                GUILayout.Space(25.0f);
                nextY += 25.0f;
            }

            // Create the right import/reimport button and handle the import/reimport based on the three cases:
            // - Reimport model
            // - Reimport model group
            // - Import model
            bool importPressed;

            if (model)
            {
                // ----------------------
                // Reimport entire model.
                // ----------------------
                importPressed = GUI.Button(new Rect(leftMargin, nextY, maxLabelWidth + 15.0f + 126.0f, 32.0f), "Reimport Model");

                if (importPressed)
                {
                    // Register undo.
                    Undo.RegisterFullObjectHierarchyUndo(model.gameObject, "Reimport");
                    var oldPivot = model.pivot;
                    model.pivot = pivot;

                    // Update the path if it is new.
                    if (filePath != null)
                    {
                        model.absoluteFilePath = filePath;
                        model.relativeFilePath = PathUtils.GetRelativePath(Directory.GetCurrentDirectory(), filePath);
                    }

                    ModelImporter.ReimportModel(lxfml, model, oldPivot, importSettings);

                    var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();
                    if (prefabStage != null)
                    {
                        EditorSceneManager.MarkSceneDirty(prefabStage.scene);
                    }
                    SceneBrickBuilder.MarkSceneDirty();
                }
            }
            else if (group)
            {
                // ---------------------
                // Reimport model group.
                // ---------------------
                importPressed = GUI.Button(new Rect(leftMargin, nextY, maxLabelWidth + 15.0f + 126.0f, 32.0f), "Reimport Model Group");

                if (importPressed)
                {
                    // Register undo.
                    Undo.RegisterFullObjectHierarchyUndo(group.gameObject, "Reimport");

                    ModelImporter.ReimportModelGroup(lxfml, group, importSettings[group.number], true);

                    var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();
                    if (prefabStage != null)
                    {
                        EditorSceneManager.MarkSceneDirty(prefabStage.scene);
                    }
                    SceneBrickBuilder.MarkSceneDirty();
                }
            }
            else
            {
                // ----------------------
                // Import model.
                // ----------------------
                importPressed = GUI.Button(new Rect(leftMargin, nextY, maxLabelWidth + 15.0f + 126.0f, 32.0f), "Import Model");

                if (importPressed)
                {
                    // Check for connectivity updates.
                    ConnectivityVersionChecker.CheckForUpdates();

                    model = ModelImporter.InstantiateModel(lxfml, filePath, pivot, importSettings).GetComponent <Model>();
                    var camera = SceneView.lastActiveSceneView.camera;
                    if (camera)
                    {
                        var cameraRay = new Ray(camera.transform.position, camera.transform.forward);

                        var bricksInModel = model.GetComponentsInChildren <Brick>();
                        var bricks        = new HashSet <Brick>(bricksInModel);
                        var sourceBrick   = bricks.First();

                        BrickBuildingUtility.AlignBricks(sourceBrick, bricks, BrickBuildingUtility.ComputeBounds(bricks), sourceBrick.transform.position, Vector3.zero, cameraRay,
                                                         new Plane(Vector3.up, Vector3.zero), 100.0f, out Vector3 offset, out Vector3 alignedOffset, out _, out _);

                        var offsetPosition = model.transform.position + alignedOffset;

                        model.transform.position = offsetPosition;

                        Selection.activeGameObject = model.gameObject;
                        Physics.SyncTransforms();
                    }
                    SceneBrickBuilder.SyncAndUpdateBrickCollision(true);
                }
            }

            // Reserve the space for the GUILayout scroll view.
            GUILayout.Space(36.0f);
            nextY += 36.0f;

            // List tracked errors.
            foreach (var trackedError in trackedErrors)
            {
                EditorGUI.HelpBox(new Rect(leftMargin, nextY, maxLabelWidth + 340.0f, 38.0f), trackedError.Key, MessageType.Warning);
                // Reserve the space for the GUILayout scroll view.
                GUILayout.Space(42.0f);
                nextY += 42.0f;

                foreach (var id in trackedError.Value)
                {
                    GUI.Label(new Rect(leftMargin, nextY, maxLabelWidth + 340.0f, 16.0f), id);
                    // Reserve the space for the GUILayout scroll view.
                    GUILayout.Space(20.0f);
                    nextY += 20.0f;
                }
            }

            GUILayout.EndScrollView();

            if (importPressed)
            {
                this.Close();
            }
        }
Exemplo n.º 12
0
        /// <summary>
        /// 在场景中搜索任务目标
        /// </summary>
        private static void SearchTaskTarget(TaskGameObjects taskGameObjects, int index)
        {
            if (taskGameObjects.GUIDs[index] == "<None>")
            {
                return;
            }

            if (taskGameObjects._gameObjects[index] != null)
            {
                return;
            }

            PrefabStage prefabStage = PrefabStageUtility.GetCurrentPrefabStage();

            if (prefabStage != null)
            {
                taskGameObjects._gameObjects[index] = prefabStage.prefabContentsRoot.FindChildren(taskGameObjects.Paths[index]);
                if (taskGameObjects._gameObjects[index] == null)
                {
                    TaskTarget[] targets = prefabStage.prefabContentsRoot.GetComponentsInChildren <TaskTarget>(true);
                    foreach (TaskTarget target in targets)
                    {
                        if (taskGameObjects.GUIDs[index] == target.GUID)
                        {
                            taskGameObjects._gameObjects[index] = target.gameObject;
                            taskGameObjects.Paths[index]        = target.transform.FullName();
                            taskGameObjects.Paths[index]        = taskGameObjects.Paths[index].Substring(taskGameObjects.Paths[index].IndexOf("/") + 1);
                            break;
                        }
                    }
                }
            }
            else
            {
                taskGameObjects._gameObjects[index] = GameObject.Find(taskGameObjects.Paths[index]);
                if (taskGameObjects._gameObjects[index] == null)
                {
                    TaskTarget[] targets = UnityEngine.Object.FindObjectsOfType <TaskTarget>();
                    foreach (TaskTarget target in targets)
                    {
                        if (taskGameObjects.GUIDs[index] == target.GUID)
                        {
                            taskGameObjects._gameObjects[index] = target.gameObject;
                            taskGameObjects.Paths[index]        = target.transform.FullName();
                            break;
                        }
                    }
                }
            }

            if (taskGameObjects._gameObjects[index] != null)
            {
                TaskTarget target = taskGameObjects._gameObjects[index].GetComponent <TaskTarget>();
                if (!target)
                {
                    target      = taskGameObjects._gameObjects[index].AddComponent <TaskTarget>();
                    target.GUID = taskGameObjects.GUIDs[index];
                    EditorUtility.SetDirty(taskGameObjects._gameObjects[index]);
                }
            }
        }
Exemplo n.º 13
0
        private static void HierarchyWindowListElementOnGUI(int instanceID, Rect selectionRect)
        {
            if (EditorApplication.isPlayingOrWillChangePlaymode || !VCSettings.HierarchyIcons || !VCCommands.Active)
            {
                return;
            }
            var obj = EditorUtility.InstanceIDToObject(instanceID);

            if (obj == null)
            {
                string sceneAssetPath = SceneManagerUtilities.GetSceneAssetPathFromHandle(instanceID);
                if (!string.IsNullOrEmpty(sceneAssetPath))
                {
                    VCUtility.RequestStatus(sceneAssetPath, VCSettings.HierarchyReflectionMode);
                    DrawIcon(selectionRect, IconUtils.rubyIcon, sceneAssetPath, null, -20f);
                }
            }
            else
            {
                var currentPrefabStage = PrefabStageUtility.GetCurrentPrefabStage();
                if (currentPrefabStage != null)
                {
                    var go = obj as GameObject;
                    if (go)
                    {
                        if (PrefabStageUtility.GetCurrentPrefabStage().prefabContentsRoot == go)
                        {
                            DrawIcon(selectionRect, IconUtils.squareIcon, PrefabStageUtility.GetCurrentPrefabStage().prefabAssetPath, PrefabStageUtility.GetCurrentPrefabStage().prefabContentsRoot, 0f);
                        }
                    }
                }
            }
        }
Exemplo n.º 14
0
        public static bool IsPrefabModeRoot(GameObject test)
        {
            PrefabStage prefabStage = PrefabStageUtility.GetCurrentPrefabStage();

            return(prefabStage != null && prefabStage.prefabContentsRoot == test);
        }
Exemplo n.º 15
0
        internal static void UpdateAllMockups()
        {
            //When building, the scene may open-close multiple times and brought back the mockup canvas,
            //which combined with bugs mentioned at https://github.com/5argon/NotchSolution/issues/11,
            //will fail the build. This `if` prevents mockup refresh while building.
            if (BuildPipeline.isBuildingPlayer)
            {
                return;
            }

            EnsureCanvasAndEventSetup();

            //Make the editing environment contains an another copy of mockup canvas.
            var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();

            if (prefabStage != null)
            {
                EnsureCanvasAndEventSetup(prefabStage: prefabStage);
            }

            var  settings         = Settings.Instance;
            bool enableSimulation = settings.EnableSimulation;
            var  selectedDevice   = SimulationDatabase.ByIndex(Settings.Instance.ActiveConfiguration.DeviceIndex);

            if (enableSimulation && selectedDevice != null)
            {
                var    name         = selectedDevice.Meta.overlay;
                Sprite mockupSprite = null;
                if (!string.IsNullOrEmpty(name))
                {
                    var filePath = Path.Combine(NotchSimulatorUtility.DevicesFolder, name);
                    mockupSprite = AssetDatabase.LoadAssetAtPath <Sprite>(filePath);
                    if (mockupSprite == null)
                    {
                        if (System.IO.File.Exists(filePath))
                        {
                            Texture2D tex = new Texture2D(1, 1);
                            tex.LoadImage(System.IO.File.ReadAllBytes(filePath));
                            mockupSprite = Sprite.Create(tex, new Rect(0.0f, 0.0f, tex.width, tex.height), new Vector2(0.5f, 0.5f), 100.0f);
                        }
                        else
                        {
                            Debug.LogWarning($"No mockup image named {name} in {NotchSimulatorUtility.DevicesFolder} folder!");
                        }
                    }
                }


                foreach (var mockup in AllMockupCanvases)
                {
                    mockup.UpdateMockupSprite(
                        sprite: mockupSprite,
                        orientation: NotchSimulatorUtility.GetGameViewOrientation(),
                        simulate: enableSimulation,
                        flipped: settings.FlipOrientation,
                        prefabModeOverlayColor: Settings.Instance.PrefabModeOverlayColor
                        );
                }
            }
            else
            {
                DestroyHiddenCanvas();
            }
        }
Exemplo n.º 16
0
 private static bool CreateMixedRealityToolkitGameObjectValidation()
 {
     return(PrefabStageUtility.GetCurrentPrefabStage() == null);
 }
Exemplo n.º 17
0
        public float PrefabModeButton(GameObjectTreeViewItem item, Rect selectionRect)
        {
            float contentRectRight = selectionRect.xMax;

            if (item.showPrefabModeButton)
            {
                float yOffset    = (selectionRect.height - GameObjectStyles.rightArrow.fixedWidth) / 2;
                Rect  buttonRect = new Rect(
                    selectionRect.xMax - GameObjectStyles.rightArrow.fixedWidth - GameObjectStyles.rightArrow.margin.right,
                    selectionRect.y + yOffset,
                    GameObjectStyles.rightArrow.fixedWidth,
                    GameObjectStyles.rightArrow.fixedHeight);

                int        instanceID = item.id;
                GUIContent content    = buttonRect.Contains(Event.current.mousePosition) ? PrefabStageUtility.GetPrefabButtonContent(instanceID) : GUIContent.none;
                if (GUI.Button(buttonRect, content, GameObjectStyles.rightArrow))
                {
                    GameObject go             = EditorUtility.InstanceIDToObject(instanceID) as GameObject;
                    string     assetPath      = PrefabUtility.GetPrefabAssetPathOfNearestInstanceRoot(go);
                    Object     originalSource = AssetDatabase.LoadMainAssetAtPath(assetPath);
                    if (originalSource != null)
                    {
                        var prefabStageMode = PrefabStageUtility.GetPrefabStageModeFromModifierKeys();
                        PrefabStageUtility.OpenPrefab(assetPath, go, prefabStageMode, StageNavigationManager.Analytics.ChangeType.EnterViaInstanceHierarchyRightArrow);
                    }
                }

                contentRectRight = buttonRect.xMin;
            }

            return(contentRectRight);
        }
Exemplo n.º 18
0
 public static bool IsPrefabStage(this GameObject gameObject)
 {
     return(PrefabStageUtility.GetCurrentPrefabStage() != null);
 }
Exemplo n.º 19
0
        protected override void OnEnable()
        {
            base.OnEnable();

            configurationProfile = target as MixedRealityToolkitConfigurationProfile;

            var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();

            // Create The MR Manager if none exists.
            if (!MixedRealityToolkit.IsInitialized && prefabStage == null)
            {
                // TODO Check base scene for service locator existence?

                // Search for all instances, in case we've just hot reloaded the assembly.
                var managerSearch = FindObjectsOfType <MixedRealityToolkit>();

                if (managerSearch.Length == 0)
                {
                    if (EditorUtility.DisplayDialog(
                            "Attention!",
                            "There is no active Mixed Reality Toolkit in your scene!\n\nWould you like to create one now?",
                            "Yes",
                            "Later"))
                    {
                        if (MixedRealityToolkit.CameraSystem != null)
                        {
                            var playspace = MixedRealityToolkit.CameraSystem.CameraRig.PlayspaceTransform;
                            Debug.Assert(playspace != null);
                        }

                        MixedRealityToolkit.Instance.ActiveProfile = configurationProfile;
                    }
                    else
                    {
                        Debug.LogWarning("No Mixed Reality Toolkit in your scene.");
                    }
                }
            }

            // Camera configuration
            enableCameraSystem = serializedObject.FindProperty("enableCameraSystem");
            cameraSystemType   = serializedObject.FindProperty("cameraSystemType");
            cameraProfile      = serializedObject.FindProperty("cameraProfile");
            // Input system configuration
            enableInputSystem  = serializedObject.FindProperty("enableInputSystem");
            inputSystemType    = serializedObject.FindProperty("inputSystemType");
            inputSystemProfile = serializedObject.FindProperty("inputSystemProfile");
            // Boundary system configuration
            enableBoundarySystem         = serializedObject.FindProperty("enableBoundarySystem");
            boundarySystemType           = serializedObject.FindProperty("boundarySystemType");
            boundaryVisualizationProfile = serializedObject.FindProperty("boundaryVisualizationProfile");
            // Teleport system configuration
            enableTeleportSystem = serializedObject.FindProperty("enableTeleportSystem");
            teleportSystemType   = serializedObject.FindProperty("teleportSystemType");
            // Spatial Awareness system configuration
            enableSpatialAwarenessSystem = serializedObject.FindProperty("enableSpatialAwarenessSystem");
            spatialAwarenessSystemType   = serializedObject.FindProperty("spatialAwarenessSystemType");
            spatialAwarenessProfile      = serializedObject.FindProperty("spatialAwarenessProfile");
            // Networking system configuration
            enableNetworkingSystem  = serializedObject.FindProperty("enableNetworkingSystem");
            networkingSystemType    = serializedObject.FindProperty("networkingSystemType");
            networkingSystemProfile = serializedObject.FindProperty("networkingSystemProfile");
            // Diagnostics system configuration
            enableDiagnosticsSystem  = serializedObject.FindProperty("enableDiagnosticsSystem");
            diagnosticsSystemType    = serializedObject.FindProperty("diagnosticsSystemType");
            diagnosticsSystemProfile = serializedObject.FindProperty("diagnosticsSystemProfile");

            // Additional registered components configuration
            registeredServiceProvidersProfile = serializedObject.FindProperty("registeredServiceProvidersProfile");
        }
Exemplo n.º 20
0
 public static bool IsRootPrefabStage(this GameObject gameObject)
 {
     // return PrefabStageUtility.GetCurrentPrefabStage() != null && !PrefabUtility.IsPartOfPrefabInstance(gameObject);
     return(PrefabStageUtility.GetCurrentPrefabStage() != null && !PrefabUtility.IsPartOfAnyPrefab(gameObject));
 }
Exemplo n.º 21
0
        /// <summary>
        /// Draws the contents of a scriptable inline inside a foldout. Depending on if there's an actual scriptable
        /// linked, the values will be greyed out or editable in case the scriptable is created inside the serialized object.
        /// </summary>
        static public bool DrawScriptableFoldout <T>(SerializedProperty scriptable, string description, bool isExpanded) where T : ScriptableObject
        {
            isExpanded = EditorGUILayout.Foldout(isExpanded, description, true, MixedRealityStylesUtility.BoldFoldoutStyle);
            if (isExpanded)
            {
                using (new EditorGUI.IndentLevelScope())
                {
                    if (scriptable.objectReferenceValue == null)
                    {
                        // If there's no scriptable linked we're creating a local instance that allows to store a
                        // local version of the scriptable in the serialized object owning the scriptable property.
                        scriptable.objectReferenceValue = ScriptableObject.CreateInstance <T>();
                    }

                    // We have currently 5 different states to display to the user:
                    // 1. the scriptable is local to the object instance
                    // 2. the scriptable is a linked nested scriptable inside of the currently displayed prefab
                    // 3. the scriptable is a linked nested scriptable inside of another prefab
                    // 4. the scriptable is a shared standalone asset
                    // 5. the scriptable slot is empty but inside of a prefab asset which needs special handling as
                    // prefabs can only display linked or nested scriptables.

                    // Depending on the type of link we show the user the scriptable configuration either:
                    // case 1 &2: editable inlined
                    // case 3 & 4: greyed out readonly
                    // case 5: only show the link

                    // case 5 -> can't create and/or store the local scriptable above - show link
                    bool isStoredAsset         = (scriptable.objectReferenceValue == null) ? false : AssetDatabase.Contains(scriptable.objectReferenceValue);
                    bool isEmptyInStagedPrefab = !isStoredAsset && ((Component)scriptable.serializedObject.targetObject).gameObject.scene.path == "";
                    if (scriptable.objectReferenceValue == null || isEmptyInStagedPrefab)
                    {
                        EditorGUILayout.HelpBox("No scriptable " + scriptable.displayName + " linked to this prefab. Prefabs can't store " +
                                                "local versions of scriptables and need to be linked to a scriptable asset.", MessageType.Warning);
                        EditorGUILayout.PropertyField(scriptable, new GUIContent(scriptable.displayName + " (Empty): "));
                    }
                    else
                    {
                        bool isNestedInCurrentPrefab = false;
                        var  prefabStage             = PrefabStageUtility.GetCurrentPrefabStage();
                        if (prefabStage != null)
                        {
                            var instancePath = AssetDatabase.GetAssetPath(scriptable.objectReferenceValue);
                            isNestedInCurrentPrefab = instancePath != "" &&
#if UNITY_2020_1_OR_NEWER
                                                      instancePath == prefabStage.assetPath
#else
                                                      instancePath == prefabStage.prefabAssetPath
#endif
                            ;
                        }


                        if (isStoredAsset && !isNestedInCurrentPrefab)
                        {
                            // case 3 & 4 - greyed out drawer
                            bool isMainAsset     = AssetDatabase.IsMainAsset(scriptable.objectReferenceValue);
                            var  sharedAssetPath = AssetDatabase.GetAssetPath(scriptable.objectReferenceValue);
                            if (isMainAsset)
                            {
                                EditorGUILayout.HelpBox("Editing a shared " + scriptable.displayName + ", located at " + sharedAssetPath, MessageType.Warning);
                            }
                            else
                            {
                                EditorGUILayout.HelpBox("Editing a nested " + scriptable.displayName + ", located inside of " + sharedAssetPath, MessageType.Warning);
                            }
                            EditorGUILayout.PropertyField(scriptable, new GUIContent(scriptable.displayName + " (Shared asset): "));

                            // In case there's a shared scriptable linked we're disabling the inlined scriptable properties
                            // (this will render them grayed out) so users won't accidentally modify the shared scriptable.
                            GUI.enabled = false;
                            DrawScriptableSubEditor(scriptable);
                            GUI.enabled = true;
                        }
                        else
                        {
                            // case 1 & 2 - inline editable drawer
                            if (isNestedInCurrentPrefab)
                            {
                                EditorGUILayout.HelpBox("Editing a nested version of " + scriptable.displayName + ".", MessageType.Info);
                            }
                            else
                            {
                                EditorGUILayout.HelpBox("Editing a local version of " + scriptable.displayName + ".", MessageType.Info);
                            }
                            EditorGUILayout.PropertyField(scriptable, new GUIContent(scriptable.displayName + " (local): "));
                            DrawScriptableSubEditor(scriptable);
                        }
                    }
                }
            }

            return(isExpanded);
        }
Exemplo n.º 22
0
        public void Draw(Rect r, Rect visibleArea)
        {
            var prefabStage = PrefabStageUtility.GetCurrentPrefabStage();

            m_IsNotInPrefabContextModeWithOverrides = prefabStage == null || prefabStage.mode != PrefabStage.Mode.InContext || !PrefabStage.s_PatchAllOverriddenProperties ||
                                                      Selection.objects.All(obj => PrefabUtility.IsPartOfAnyPrefab(obj) && !AssetDatabase.AssetPathToGUID(AssetDatabase.GetAssetPath(obj)).Equals(AssetDatabase.AssetPathToGUID(prefabStage.assetPath)));
            m_ReorderableList.draggable = m_Reorderable && m_IsNotInPrefabContextModeWithOverrides;

            Rect headerRect = new Rect(r.x, r.y, r.width, m_HeaderHeight);
            Rect sizeRect   = new Rect(headerRect.xMax - Constants.kArraySizeWidth, headerRect.y,
                                       Constants.kArraySizeWidth, m_HeaderHeight);

            EventType prevType = Event.current.type;

            if (Event.current.type == EventType.MouseUp && sizeRect.Contains(Event.current.mousePosition))
            {
                Event.current.type = EventType.Used;
            }

            EditorGUI.BeginChangeCheck();
            m_Foldout = EditorGUI.BeginFoldoutHeaderGroup(headerRect, m_Foldout, m_Header);
            EditorGUI.EndFoldoutHeaderGroup();
            if (EditorGUI.EndChangeCheck())
            {
                m_ReorderableList.ClearCacheRecursive();
            }

            if (Event.current.type == EventType.Used && sizeRect.Contains(Event.current.mousePosition))
            {
                Event.current.type = prevType;
            }

            EditorGUI.DefaultPropertyField(sizeRect, m_ArraySize, GUIContent.none);
            EditorGUI.LabelField(sizeRect, new GUIContent("", "Array Size"));

            if (headerRect.Contains(Event.current.mousePosition))
            {
                if (Event.current.type == EventType.DragUpdated || Event.current.type == EventType.DragPerform)
                {
                    Object[] objReferences = DragAndDrop.objectReferences;
                    foreach (var o in objReferences)
                    {
                        if (EditorGUI.ValidateObjectFieldAssignment(new[] { o }, typeof(Object), m_ReorderableList.serializedProperty,
                                                                    EditorGUI.ObjectFieldValidatorOptions.None) != null)
                        {
                            DragAndDrop.visualMode = DragAndDropVisualMode.Generic;
                        }
                        else
                        {
                            continue;
                        }

                        if (Event.current.type == EventType.DragPerform)
                        {
                            ReorderableList.defaultBehaviours.DoAddButton(m_ReorderableList, o);
                        }
                    }
                    DragAndDrop.AcceptDrag();
                    Event.current.Use();
                }
            }

            if (Event.current.type == EventType.DragExited)
            {
                DragAndDrop.visualMode = DragAndDropVisualMode.None;
                Event.current.Use();
            }

            if (m_Foldout)
            {
                r.y      += m_HeaderHeight + Constants.kHeaderPadding;
                r.height -= m_HeaderHeight + Constants.kHeaderPadding;

                visibleArea.y -= r.y;
                m_ReorderableList.DoList(r, visibleArea);
            }
        }
Exemplo n.º 23
0
        protected static GameObject getSourcePrefab42019(GameObject gameObject, out bool isSceneObject, out GameObject sourceRoot, out string childPath)
        {
            GameObject           source;
            PrefabAssetType      assetType = PrefabUtility.GetPrefabAssetType(gameObject);
            PrefabInstanceStatus status    = PrefabUtility.GetPrefabInstanceStatus(gameObject);
            PrefabStage          stage     = PrefabStageUtility.GetCurrentPrefabStage();

            if (stage != null && stage.IsPartOfPrefabContents(gameObject))
            {
                //编辑场景
                isSceneObject = false;
                childPath     = stage.prefabContentsRoot.transform.getChildPath(gameObject.transform);
                sourceRoot    = AssetDatabase.LoadAssetAtPath <GameObject>(stage.prefabAssetPath);
                Transform sourceTransform = sourceRoot.transform.Find(childPath);
                if (sourceTransform != null)
                {
                    source = sourceTransform.gameObject;
                }
                else
                {
                    sourceRoot = null;
                    childPath  = string.Empty;
                    return(null);
                }
            }
            else if (string.IsNullOrEmpty(gameObject.scene.path))
            {
                //Assets
                isSceneObject = false;
                source        = gameObject;
                sourceRoot    = source.transform.root.gameObject;
                childPath     = sourceRoot.transform.getChildPath(source.transform);
                //switch (assetType)
                //{
                //    case PrefabAssetType.Regular:
                //    case PrefabAssetType.Variant:
                //    case PrefabAssetType.Model:
                //    case PrefabAssetType.MissingAsset:
                //    case PrefabAssetType.NotAPrefab:
                //    default:
                //        break;
                //}
            }
            else
            {
                //场景物体
                switch (status)
                {
                case PrefabInstanceStatus.Connected:
                    switch (assetType)
                    {
                    case PrefabAssetType.Regular:
                    case PrefabAssetType.Model:
                        isSceneObject = false;
                        source        = PrefabUtility.GetCorrespondingObjectFromSource(gameObject);
                        sourceRoot    = source.transform.root.gameObject;
                        childPath     = sourceRoot.transform.getChildPath(source.transform);
                        break;

                    case PrefabAssetType.Variant:
                        isSceneObject = false;
                        source        = PrefabUtility.GetCorrespondingObjectFromSource(gameObject);
                        sourceRoot    = source.transform.root.gameObject;
                        childPath     = sourceRoot.transform.getChildPath(source.transform);
                        break;

                    case PrefabAssetType.MissingAsset:
                    case PrefabAssetType.NotAPrefab:
                    default:
                        isSceneObject = true;
                        source        = gameObject;
                        sourceRoot    = null;
                        childPath     = null;
                        break;
                    }
                    break;

                case PrefabInstanceStatus.NotAPrefab:
                case PrefabInstanceStatus.MissingAsset:
                case PrefabInstanceStatus.Disconnected:
                default:
                    isSceneObject = true;
                    source        = gameObject;
                    sourceRoot    = null;
                    childPath     = null;
                    break;
                }
            }
            return(source);
        }
Exemplo n.º 24
0
        public void LogStageInformation()
        {
#if UNITY_EDITOR
            // First check if input GameObject is persistent before checking what stage the GameObject is in
            if (EditorUtility.IsPersistent(gameObject))
            {
                if (!PrefabUtility.IsPartOfPrefabAsset(gameObject))
                {
                    LogConsole("The GameObject is a temporary object created during import. OnValidate() is called two times with a temporary object during import: First time is when saving cloned objects to .prefab file. Second event is when reading .prefab file objects during import");
                }
                else
                {
                    LogConsole("GameObject is part of an imported Prefab Asset (from the Library folder)");
                }
                return;
            }

            // If the GameObject is not persistent let's determine which stage we are in first because getting Prefab info depends on it
            var mainStage    = StageUtility.GetMainStageHandle();
            var currentStage = StageUtility.GetStageHandle(gameObject);
            if (currentStage == mainStage)
            {
                if (PrefabUtility.IsPartOfPrefabInstance(gameObject))
                {
                    var type = PrefabUtility.GetPrefabAssetType(gameObject);
                    var path = AssetDatabase.GetAssetPath(PrefabUtility.GetCorrespondingObjectFromSource(gameObject));
                    LogConsole(string.Format("GameObject is part of a Prefab Instance in the MainStage and is of type: {0}. It comes from the prefab asset: {1}", type, path));
                }
                else
                {
                    LogConsole("GameObject is a plain GameObject in the MainStage");
                }
            }
            else
            {
                var prefabStage = PrefabStageUtility.GetPrefabStage(gameObject);
                if (prefabStage != null)
                {
                    if (PrefabUtility.IsPartOfPrefabInstance(gameObject))
                    {
                        var type             = PrefabUtility.GetPrefabAssetType(gameObject);
                        var nestedPrefabPath = AssetDatabase.GetAssetPath(PrefabUtility.GetCorrespondingObjectFromSource(gameObject));
                        LogConsole(string.Format("GameObject is in a PrefabStage. The GameObject is part of a nested Prefab Instance and is of type: {0}. The opened Prefab asset is: {1} and the nested Prefab asset is: {2}", type, prefabStage.prefabAssetPath, nestedPrefabPath));
                    }
                    else
                    {
                        var prefabAssetRoot = AssetDatabase.LoadAssetAtPath <GameObject>(prefabStage.prefabAssetPath);
                        var type            = PrefabUtility.GetPrefabAssetType(prefabAssetRoot);
                        LogConsole(string.Format("GameObject is in a PrefabStage. The opened Prefab is of type: {0}. The GameObject comes from the prefab asset: {1}", type, prefabStage.prefabAssetPath));
                    }
                }
                else if (EditorSceneManager.IsPreviewSceneObject(gameObject))
                {
                    LogConsole("GameObject is not in the MainStage, nor in a PrefabStage. But it is in a PreviewScene so could be used for Preview rendering or other utilities.");
                }
                else
                {
                    LogConsole("Unknown GameObject Info");
                }
            }
#endif
        }
Exemplo n.º 25
0
 public static bool IsPartOfPrefabStage(GameObject gameObject, out PrefabStage pfs)
 {
     pfs = PrefabStageUtility.GetPrefabStage(gameObject);
     return(pfs != null);
 }
Exemplo n.º 26
0
        public void LogPrefabInformation()
        {
#if UNITY_EDITOR
            StringBuilder stringBuilder = new StringBuilder();

            // First check if input GameObject is persistent before checking what stage the GameObject is in
            if (EditorUtility.IsPersistent(gameObject))
            {
                if (!PrefabUtility.IsPartOfPrefabAsset(gameObject))
                {
                    stringBuilder.Append("The GameObject is a temporary object created during import. OnValidate() is called two times with a temporary object during import: First time is when saving cloned objects to .prefab file. Second event is when reading .prefab file objects during import");
                }
                else
                {
                    stringBuilder.Append("GameObject is part of an imported Prefab Asset (from the Library folder).\n");
                    stringBuilder.AppendLine("Prefab Asset: " + GetPrefabInfoString(gameObject));
                }

                Debug.Log(stringBuilder.ToString());
                return;
            }

            PrefabStage prefabStage = PrefabStageUtility.GetPrefabStage(gameObject);
            if (prefabStage != null)
            {
                GameObject openPrefabThatContentsIsPartOf = AssetDatabase.LoadAssetAtPath <GameObject>(prefabStage.prefabAssetPath);
                stringBuilder.AppendFormat(
                    "The GameObject is part of the Prefab contents of the Prefab Asset:\n{0}\n\n",
                    GetPrefabInfoString(openPrefabThatContentsIsPartOf));
            }

            if (!PrefabUtility.IsPartOfPrefabInstance(gameObject))
            {
                stringBuilder.Append("The GameObject is a plain GameObject (not part of a Prefab instance).\n");
            }
            else
            {
                // This is the Prefab Asset that can be applied to via the Overrides dropdown.
                GameObject outermostPrefabAssetObject = PrefabUtility.GetCorrespondingObjectFromSource(gameObject);
                // This is the Prefab Asset that determines the icon that is shown in the Hierarchy for the nearest root.
                GameObject nearestRootPrefabAssetObject = AssetDatabase.LoadAssetAtPath <GameObject>(PrefabUtility.GetPrefabAssetPathOfNearestInstanceRoot(gameObject));
                // This is the Prefab Asset where the original version of the object comes from.
                GameObject originalPrefabAssetObject = PrefabUtility.GetCorrespondingObjectFromOriginalSource(gameObject);
                stringBuilder.AppendFormat(
                    @"Prefab Asset of the outermost Prefab instance the input GameObject is part of is:
{0}
Prefab Asset of the nearest Prefab instance root the input GameObject is part of is:
{1}
Prefab Asset of the innermost Prefab instance the input GameObject is part of is:
{2}
Complete nesting chain from outermost to original:
",
                    GetPrefabInfoString(outermostPrefabAssetObject),
                    GetPrefabInfoString(nearestRootPrefabAssetObject),
                    GetPrefabInfoString(originalPrefabAssetObject));

                GameObject current = outermostPrefabAssetObject;
                while (current != null)
                {
                    stringBuilder.AppendLine(GetPrefabInfoString(current));
                    current = PrefabUtility.GetCorrespondingObjectFromSource(current);
                }
            }

            stringBuilder.AppendLine("");

            Debug.Log(stringBuilder.ToString());
#endif
        }
Exemplo n.º 27
0
        /// <summary>
        /// Recompute the model and model group hierarchy.
        /// Some rules:
        /// 1. A brick will always be in a model group, which will always be in a model.
        /// 2. Empty models and model groups are destroyed.
        /// 3. Bricks can not contain bricks, model groups can not contain model groups and models can not contain models. So they are flattened.
        /// </summary>
        /// <param name="bricks">The bricks that we need to check the hierarchy for</param>
        /// <param name="alignRotation">Whether or not we also align rotation when we recompute pivot</param>
        /// <param name="undoBehavior">Whether or not to register undo for the recomputation of hierarchy</param>
        public static void RecomputeHierarchy(IEnumerable <Brick> bricks, bool alignRotation = true, UndoBehavior undoBehavior = UndoBehavior.withUndo)
        {
            // Group numbers are numbers in parentheses
            // So group 1 with three bricks is shown as (1, 1, 1)
            // In case the group is part of a prefab it is suffixed with a p like (1p, 1p)
            // In case one of the bricks in a group is an override it is noted with a + as in (1p, 1p+)

            // Cases for splitting:
            // (1, 1) -> (1) (1)
            // (1, 1) (2) -> (1) (1, 2) -> (1) (2, 2)

            // Cases for unpacking:
            // (1p) (2p) -> (1, 2p) -> (2p+, 2p)
            // (1p, 1p+) (2p) -> (1, 1, 2p) -> (2p+, 2p+, 2p)
            // (1p, 1p) -> (1p) (1p) -> (1) (1)

            // Only set parent:
            // (1) (2) -> (1, 2) -> (2, 2)
            // (1p, 1p+) (2p) -> (1p) (1p+, 2p) -> (1p) (2p+, 2p)
            // (1p, 1p+) (2) -> (1p) (1p+, 2) -> (1p) (2, 2)

            if (PrefabStageUtility.GetCurrentPrefabStage() != null)
            {
                var rootObject = PrefabStageUtility.GetCurrentPrefabStage().prefabContentsRoot;
                var brick      = rootObject.GetComponent <Brick>();
                if (brick)
                {
                    return;
                }
            }

            // First we flatten models
            var modelsToCheck = new HashSet <Model>();
            var groupsToCheck = new HashSet <ModelGroup>();
            var bricksToCheck = new HashSet <Brick>();

            foreach (var brick in bricks)
            {
                var bricksInParent = brick.GetComponentsInParent <Brick>(true);
                if (bricksInParent.Length > 1)
                {
                    bricksToCheck.Add(brick);
                }
                var modelsInParent = brick.GetComponentsInParent <Model>(true);
                if (modelsInParent.Length > 1)
                {
                    modelsToCheck.UnionWith(modelsInParent);
                }
                var groupsInParent = brick.GetComponentsInParent <ModelGroup>(true);
                if (groupsInParent.Length > 1)
                {
                    groupsToCheck.UnionWith(groupsInParent);
                }
            }

            foreach (var model in modelsToCheck)
            {
                var modelsInModel = model.GetComponentsInChildren <Model>(true);
                foreach (var inModel in modelsInModel)
                {
                    if (inModel == model)
                    {
                        continue;
                    }

                    var groupsInModel = inModel.GetComponentsInChildren <ModelGroup>(true);
                    foreach (var group in groupsInModel)
                    {
                        SetParent(group.transform, model.transform, undoBehavior);
                    }
                }
            }

            // Now flatten groups
            foreach (var group in groupsToCheck)
            {
                var groupsInGroup = group.GetComponentsInChildren <ModelGroup>(true);
                foreach (var inGroup in groupsInGroup)
                {
                    if (inGroup == group)
                    {
                        continue;
                    }

                    var bricksInGroup = inGroup.GetComponentsInChildren <Brick>(true);
                    foreach (var brick in bricksInGroup)
                    {
                        SetParent(brick.transform, group.transform, undoBehavior);
                    }
                }
            }

            // Now flatten bricks
            foreach (var brick in bricksToCheck)
            {
                var group = GetGroupInParent(brick.transform);
                if (group)
                {
                    SetParent(brick.transform, group.transform, undoBehavior);
                }
            }

            var connectedClusters = new List <HashSet <Brick> >();

            // Collect all connected brick lists
            foreach (var brick in bricks)
            {
                if (connectedClusters.Any(x => x.Contains(brick)))
                {
                    continue;
                }

                if (!brick.HasConnectivity())
                {
                    var group = GetGroupInParent(brick.transform);
                    if (!group)
                    {
                        connectedClusters.Add(new HashSet <Brick> {
                            brick
                        });
                    }
                    else
                    {
                        var model = GetModelInParent(brick.transform);
                        if (!model)
                        {
                            var bricksInGroup = group.GetComponentsInChildren <Brick>(true);
                            var connected     = new HashSet <Brick>();
                            connected.Add(brick);
                            connectedClusters.Add(connected);
                        }
                    }
                }
                else
                {
                    var connected = brick.GetConnectedBricks();
                    connected.Add(brick);
                    connectedClusters.Add(connected);
                }
            }

            // Now find all groups for each cluster
            var groupsPerCluster = new List <(HashSet <Brick>, HashSet <ModelGroup>, HashSet <Brick>)>();

            foreach (var cluster in connectedClusters)
            {
                if (cluster.Count == 0)
                {
                    continue;
                }

                var bricksNotInGroup = new HashSet <Brick>();
                var groups           = new HashSet <ModelGroup>();
                foreach (var brick in cluster)
                {
                    var group = GetGroupInParent(brick.transform);
                    if (group)
                    {
                        groups.Add(group);
                    }
                    else
                    {
                        bricksNotInGroup.Add(brick);
                    }
                }
                groupsPerCluster.Add((cluster, groups, bricksNotInGroup));
            }

            // Sorting makes sure we merge before we split. Merging will make it easier to see what we need to split later.
            groupsPerCluster = groupsPerCluster.OrderByDescending(x => x.Item2.Count).ToList();

            // Check through each of these groups in the cluster
            foreach (var groupPerCluster in groupsPerCluster)
            {
                var cluster    = groupPerCluster.Item1;
                var groups     = groupPerCluster.Item2;
                var notInGroup = groupPerCluster.Item3;

                // If the cluster has more than one group, we need to merge them
                if (groups.Count > 1)
                {
                    // Merge some groups
                    ModelGroup largestGroup     = null;
                    int        largestGroupSize = 0;
                    foreach (var group in groups)
                    {
                        var bricksInGroup   = group.GetComponentsInChildren <Brick>(true);
                        var bricksInCluster = bricksInGroup.Count(x => cluster.Contains(x));
                        if (bricksInCluster >= largestGroupSize)
                        {
                            largestGroup     = group;
                            largestGroupSize = bricksInCluster;
                        }
                    }

                    foreach (var brick in cluster)
                    {
                        if (brick.transform.parent == largestGroup.transform)
                        {
                            continue;
                        }

                        if (IsPartOfPrefab(brick))
                        {
                            UnpackPrefab(brick, undoBehavior);
                        }
                        SetParent(brick.transform, largestGroup.transform, undoBehavior);
                    }

                    RecomputePivot(largestGroup, alignRotation, undoBehavior);
                    var modelGO = largestGroup.transform.parent;
                    var model   = modelGO.GetComponent <Model>();
                    if (model)
                    {
                        RecomputePivot(model, alignRotation, undoBehavior);
                    }
                }
                else if (groups.Count == 1) // In case the cluster only has one group, we need to check if the group contains bricks not in this cluster
                {
                    var group = groups.FirstOrDefault();
                    if (!group)
                    {
                        continue;
                    }

                    var bricksInGroup    = group.GetComponentsInChildren <Brick>(true);
                    var clustersForGroup = new HashSet <HashSet <Brick> >();

                    // If this group contains more than one cluster, split
                    foreach (var brick in bricksInGroup)
                    {
                        if (!clustersForGroup.Any(x => x.Contains(brick)))
                        {
                            if (brick.HasConnectivity())
                            {
                                var connected = brick.GetConnectedBricks();
                                connected.Add(brick);
                                clustersForGroup.Add(connected);
                            }
                        }
                    }

                    // Only split if we found multiple clusters in group
                    if (clustersForGroup.Count > 1)
                    {
                        // Get the model for the group
                        var model = GetModelInParent(group.transform);

                        // Find all prefabs we need to unpack by looking through the clusters in the group
                        foreach (var clusterInGroup in clustersForGroup)
                        {
                            // Look through each brick in the cluster
                            foreach (var brick in clusterInGroup)
                            {
                                // First check if there is a brick in this cluster that is part of a prefab and not an override
                                // If there is, then check if there is another cluster containing a prefab that is not an override
                                // In that case, we have to unpack, because we are changing the parents of gameobjects in a prefab
                                if (IsPartOfPrefab(brick))
                                {
                                    if (clustersForGroup.Any(clust => clust != clusterInGroup && clust.Any(obj => !PrefabUtility.IsAddedGameObjectOverride(obj.gameObject))))
                                    {
                                        UnpackPrefab(brick, undoBehavior);
                                        break;
                                    }
                                }
                            }
                        }

                        // Optimization: Check for largest group containing only a single cluster and keep that group intact
                        HashSet <Brick> largestGroupBricks   = null;
                        ModelGroup      largestGroup         = null;
                        int             largestGroupSize     = 0;
                        var             sharedParentClusters = new HashSet <ModelGroup>();

                        foreach (var clusterInGroup in clustersForGroup)
                        {
                            var parent     = clusterInGroup.First().transform.parent;
                            var modelGroup = parent.GetComponent <ModelGroup>();
                            if (!modelGroup)
                            {
                                continue;
                            }

                            var skip = false;
                            foreach (var brick in clusterInGroup)
                            {
                                if (brick.transform.parent != parent)
                                {
                                    skip = true;
                                    break;
                                }
                            }
                            if (skip)
                            {
                                continue;
                            }

                            if (largestGroupSize < clusterInGroup.Count())
                            {
                                largestGroupSize   = clusterInGroup.Count();
                                largestGroupBricks = clusterInGroup;
                                largestGroup       = modelGroup;
                            }
                        }

                        if (largestGroupBricks != null)
                        {
                            clustersForGroup.Remove(largestGroupBricks);
                        }

                        foreach (var clusterInGroup in clustersForGroup)
                        {
                            var newObject = new GameObject();
                            var newGroup  = newObject.AddComponent <ModelGroup>();

                            // Add LEGOModelGroupAsset component.
                            newObject.AddComponent <LEGOModelGroupAsset>();

                            if (undoBehavior == UndoBehavior.withUndo)
                            {
                                Undo.RegisterCreatedObjectUndo(newObject, "Created new group");
                            }

                            newGroup.transform.position = group.transform.position;

                            if (model)
                            {
                                SetParent(newGroup.transform, model.transform, undoBehavior);
                            }

                            newGroup.name             = group.groupName;
                            newGroup.groupName        = group.groupName;
                            newGroup.parentName       = group.parentName;
                            newGroup.optimizations    = group.optimizations;
                            newGroup.randomizeNormals = group.randomizeNormals;
                            foreach (var view in group.views)
                            {
                                newGroup.views.Add(new CullingCameraConfig()
                                {
                                    name        = view.name,
                                    perspective = view.perspective,
                                    position    = view.position,
                                    rotation    = view.rotation,
                                    fov         = view.fov,
                                    size        = view.size,
                                    minRange    = view.minRange,
                                    maxRange    = view.maxRange,
                                    aspect      = view.aspect
                                });
                            }
                            newGroup.autoGenerated = true;

                            foreach (var brick in clusterInGroup)
                            {
                                SetParent(brick.transform, newGroup.transform, undoBehavior);
                            }
                            RecomputePivot(newGroup, alignRotation, undoBehavior);
                        }

                        if (model)
                        {
                            RecomputePivot(model, alignRotation, undoBehavior);
                        }
                    }
                    else if (notInGroup.Count > 0)
                    {
                        foreach (var brick in notInGroup)
                        {
                            if (IsPartOfPrefab(brick))
                            {
                                UnpackPrefab(brick, undoBehavior);
                            }
                            SetParent(brick.transform, group.transform, undoBehavior);
                        }
                    }
                    else
                    {
                        RecomputePivot(group, alignRotation, undoBehavior);

                        var   modelGO        = group.transform.parent;
                        Model model          = null;
                        bool  createNewModel = (PrefabStageUtility.GetCurrentPrefabStage() != null && modelGO && !modelGO.GetComponent <Model>()) ||
                                               (PrefabStageUtility.GetCurrentPrefabStage() == null && (!modelGO || !modelGO.GetComponent <Model>()));
                        if (createNewModel)
                        {
                            model = CreateNewDefaultModel(group.name, undoBehavior);
                            if (modelGO != null)
                            {
                                if (PrefabStageUtility.GetCurrentPrefabStage() == null && PrefabUtility.IsPartOfAnyPrefab(modelGO))
                                {
                                    UnpackPrefab(modelGO.gameObject, undoBehavior);
                                }
                                SetParent(model.transform, modelGO.transform, undoBehavior);
                            }
                            SetParent(group.transform, model.transform, undoBehavior);
                            EditorGUIUtility.PingObject(group.gameObject);
                        }
                        else
                        {
                            model = modelGO.GetComponent <Model>();
                        }

                        if (model)
                        {
                            RecomputePivot(model, alignRotation, undoBehavior);
                        }
                    }
                }
                else // No groups.
                {
                    var   name  = cluster.FirstOrDefault()?.name;
                    Model model = null;

                    if (PrefabStageUtility.GetCurrentPrefabStage() != null)
                    {
                        var rootObject = PrefabStageUtility.GetCurrentPrefabStage().prefabContentsRoot;
                        model = rootObject.GetComponent <Model>();
                        if (!model)
                        {
                            model = CreateNewDefaultModel(name);
                            SetParent(model.transform, rootObject.transform, undoBehavior);
                        }
                    }
                    else
                    {
                        model = CreateNewDefaultModel(name);
                    }

                    ModelGroup newGroup = CreateNewDefaultModelGroup(name);

                    SetParent(newGroup.transform, model.transform, undoBehavior);
                    var bounds = BrickBuildingUtility.ComputeBounds(cluster, Matrix4x4.identity);
                    model.transform.position = new Vector3(bounds.center.x, bounds.min.y, bounds.center.z);

                    Transform originalParent = null;
                    foreach (var brick in cluster)
                    {
                        if (!originalParent)
                        {
                            originalParent = brick.transform.parent;
                        }
                        if (brick.transform.parent != originalParent)
                        {
                            originalParent = null;
                            break;
                        }
                    }

                    if (originalParent)
                    {
                        SetParent(model.transform, originalParent, undoBehavior);
                    }

                    foreach (var brick in cluster)
                    {
                        SetParent(brick.transform, newGroup.transform, undoBehavior);
                        EditorGUIUtility.PingObject(brick.gameObject);
                    }
                }
            }

            var modelsInScene = StageUtility.GetCurrentStageHandle().FindComponentsOfType <Model>();

            foreach (var model in modelsInScene)
            {
                var children = model.GetComponentsInChildren <Brick>(true);
                if (children.Length == 0)
                {
                    if (undoBehavior == UndoBehavior.withUndo)
                    {
                        Undo.DestroyObjectImmediate(model.gameObject);
                    }
                    else
                    {
                        Object.DestroyImmediate(model.gameObject);
                    }
                }
            }

            var groupsInScene = StageUtility.GetCurrentStageHandle().FindComponentsOfType <ModelGroup>();

            foreach (var group in groupsInScene)
            {
                var children = group.GetComponentsInChildren <Brick>(true);
                if (children.Length == 0)
                {
                    if (undoBehavior == UndoBehavior.withUndo)
                    {
                        Undo.DestroyObjectImmediate(group.gameObject);
                    }
                    else
                    {
                        Object.DestroyImmediate(group.gameObject);
                    }
                }
            }
        }
Exemplo n.º 28
0
        // Drive state from OnEnable and OnDisable? OnEnable on RegisterLodDataInput seems to get called on script reload
        void OnEnable()
        {
            // We don't run in "prefab scenes", i.e. when editing a prefab. Bail out if prefab scene is detected.
#if UNITY_EDITOR
            if (PrefabStageUtility.GetCurrentPrefabStage() != null)
            {
                return;
            }
#endif

            if (!_primaryLight && _searchForPrimaryLightOnStartup)
            {
                _primaryLight = RenderSettings.sun;
            }

            if (!VerifyRequirements())
            {
                enabled = false;
                return;
            }

#if UNITY_EDITOR
            if (EditorApplication.isPlaying && !Validate(this, ValidatedHelper.DebugLog))
            {
                enabled = false;
                return;
            }
#endif

            _isFirstUpdate = true;

            Instance = this;
            Scale    = Mathf.Clamp(Scale, _minScale, _maxScale);

            _lodTransform = new LodTransform();
            _lodTransform.InitLODData(_lodCount);

            // Resolution is 4 tiles across.
            var baseMeshDensity = _lodDataResolution * 0.25f / _geometryDownSampleFactor;
            // 0.4f is the "best" value when base mesh density is 8. Scaling down from there produces results similar to
            // hand crafted values which looked good when the ocean is flat.
            _lodAlphaBlackPointFade = 0.4f / (baseMeshDensity / 8f);
            // We could calculate this in the shader, but we can save two subtractions this way.
            _lodAlphaBlackPointWhitePointFade = 1f - _lodAlphaBlackPointFade - _lodAlphaBlackPointFade;

            Root = OceanBuilder.GenerateMesh(this, _oceanChunkRenderers, _lodDataResolution, _geometryDownSampleFactor, _lodCount);

            CreateDestroySubSystems();

            _commandbufferBuilder = new BuildCommandBuffer();

            InitViewpoint();

            if (_attachDebugGUI && GetComponent <OceanDebugGUI>() == null)
            {
                gameObject.AddComponent <OceanDebugGUI>().hideFlags = HideFlags.DontSave;
            }

#if UNITY_EDITOR
            EditorApplication.update -= EditorUpdate;
            EditorApplication.update += EditorUpdate;
#endif
            foreach (var lodData in _lodDatas)
            {
                lodData.OnEnable();
            }

            _canSkipCulling = false;
        }
Exemplo n.º 29
0
        public static void Button(UnityEngine.Object target, MethodInfo methodInfo)
        {
            bool visible = ButtonUtility.IsVisible(target, methodInfo);

            if (!visible)
            {
                return;
            }

            if (methodInfo.GetParameters().All(p => p.IsOptional))
            {
                ButtonAttribute buttonAttribute = (ButtonAttribute)methodInfo.GetCustomAttributes(typeof(ButtonAttribute), true)[0];
                string          buttonText      = string.IsNullOrEmpty(buttonAttribute.Text) ? ObjectNames.NicifyVariableName(methodInfo.Name) : buttonAttribute.Text;

                bool buttonEnabled = ButtonUtility.IsEnabled(target, methodInfo);

                EButtonEnableMode mode = buttonAttribute.SelectedEnableMode;
                buttonEnabled &=
                    mode == EButtonEnableMode.Always ||
                    mode == EButtonEnableMode.Editor && !Application.isPlaying ||
                    mode == EButtonEnableMode.Playmode && Application.isPlaying;

                bool methodIsCoroutine = methodInfo.ReturnType == typeof(IEnumerator);
                if (methodIsCoroutine)
                {
                    buttonEnabled &= (Application.isPlaying ? true : false);
                }

                EditorGUI.BeginDisabledGroup(!buttonEnabled);

                if (GUILayout.Button(buttonText))
                {
                    object[]    defaultParams = methodInfo.GetParameters().Select(p => p.DefaultValue).ToArray();
                    IEnumerator methodResult  = methodInfo.Invoke(target, defaultParams) as IEnumerator;

                    if (!Application.isPlaying)
                    {
                        // Set target object and scene dirty to serialize changes to disk
                        EditorUtility.SetDirty(target);

                        PrefabStage stage = PrefabStageUtility.GetCurrentPrefabStage();
                        if (stage != null)
                        {
                            // Prefab mode
                            EditorSceneManager.MarkSceneDirty(stage.scene);
                        }
                        else
                        {
                            // Normal scene
                            EditorSceneManager.MarkSceneDirty(EditorSceneManager.GetActiveScene());
                        }
                    }
                    else if (methodResult != null && target is MonoBehaviour behaviour)
                    {
                        behaviour.StartCoroutine(methodResult);
                    }
                }

                EditorGUI.EndDisabledGroup();
            }
            else
            {
                string warning = typeof(ButtonAttribute).Name + " works only on methods with no parameters";
                HelpBox_Layout(warning, MessageType.Warning, context: target, logToConsole: true);
            }
        }
Exemplo n.º 30
0
    private void Rebuild(bool regenMesh)
    {
        TacticsTerrainMesh terrain = (TacticsTerrainMesh)target;

        PrefabStage prefabStage = PrefabStageUtility.GetPrefabStage(terrain.gameObject);

        if (prefabStage != null)
        {
            EditorSceneManager.MarkSceneDirty(prefabStage.scene);
        }

        MeshFilter filter = terrain.GetComponent <MeshFilter>();
        Mesh       mesh   = filter.sharedMesh;

        if (mesh == null)
        {
            mesh = new Mesh();
            AssetDatabase.CreateAsset(mesh, "Assets/Resources/TacticsMaps/Meshes/" + terrain.gameObject.name + ".asset");
            filter.sharedMesh = mesh;
        }

        quads    = new Dictionary <Vector3, Dictionary <Vector3, TerrainQuad> >();
        vertices = new List <Vector3>();
        uvs      = new List <Vector2>();
        tris     = new List <int>();
        for (int z = 0; z < terrain.size.y; z += 1)
        {
            for (int x = 0; x < terrain.size.x; x += 1)
            {
                // top vertices
                float height = terrain.HeightAt(x, z);
                AddQuad(new Vector3(x, height, z), new Vector3(x + 1, height, z + 1), terrain.TileAt(x, z),
                        new Vector3(x, height, z), new Vector3(0, 1, 0));

                // side vertices
                foreach (OrthoDir dir in Enum.GetValues(typeof(OrthoDir)))
                {
                    float currentHeight  = terrain.HeightAt(x, z);
                    float neighborHeight = terrain.HeightAt(x + dir.Px3DX(), z + dir.Px3DZ());
                    if (currentHeight > neighborHeight)
                    {
                        Vector2 off1 = Vector2.zero, off2 = Vector2.zero;
                        switch (dir)
                        {
                        case OrthoDir.South:
                            off1 = new Vector2(0, 0);
                            off2 = new Vector2(1, 0);
                            break;

                        case OrthoDir.East:
                            off1 = new Vector2(1, 1);
                            off2 = new Vector2(1, 0);
                            break;

                        case OrthoDir.North:
                            off1 = new Vector2(1, 1);
                            off2 = new Vector2(0, 1);
                            break;

                        case OrthoDir.West:
                            off1 = new Vector2(0, 0);
                            off2 = new Vector2(0, 1);
                            break;
                        }
                        for (float y = neighborHeight; y < currentHeight; y += 0.5f)
                        {
                            AddQuad(new Vector3(x + off1.x, y, z + off1.y),
                                    new Vector3(x + off2.x, y + 0.5f, z + off2.y),
                                    terrain.TileAt(x, z, y, dir),
                                    new Vector3(x, y + 0.5f, z), dir.Px3D());
                        }
                    }
                }
            }
        }

        if (regenMesh)
        {
            selectedQuads.Clear();
            mesh.Clear();

            mesh.vertices  = vertices.ToArray();
            mesh.triangles = tris.ToArray();
            mesh.uv        = uvs.ToArray();

            mesh.RecalculateBounds();
            mesh.RecalculateNormals();
        }
    }