| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547 |
- // River Modeler
- // Staggart Creations (http://staggart.xyz)
- // Copyright protected under Unity Asset Store EULA
- // Copying or referencing source code for the production of new asset store content is strictly prohibited.
- using System;
- using sc.modeling.river.runtime;
- using sc.modeling.water.common.editor;
- using UnityEditor;
- using UnityEditor.EditorTools;
- using UnityEditor.SceneManagement;
- using UnityEngine;
- #if SPLINES
- using UnityEngine.Splines;
- using UnityEditor.Splines;
- #endif
- namespace sc.modeling.river.editor
- {
- [CustomEditor(typeof(RiverModeler))]
- [CanEditMultipleObjects]
- public class RiverModelerInspector : Editor
- {
- //References
- private SerializedProperty splineContainer;
- private SerializedProperty splineChangeMode;
-
- private SerializedProperty rebuildTriggers;
-
- private SerializedProperty meshFilter;
- private SerializedProperty orderInLayer;
-
- private SerializedProperty settings;
- private SerializedProperty triangulation;
- private SerializedProperty shape;
- private SerializedProperty displacement;
- private SerializedProperty uv;
- private SerializedProperty foam;
- private SerializedProperty transparency;
- private SerializedProperty debugMode;
-
- private SerializedProperty microVerseSettings;
-
- private SerializedProperty exportToFBX;
- private SerializedProperty fbxFilePath;
- private SerializedProperty onPreRebuild;
- private SerializedProperty onPostRebuild;
-
- private bool isPrefab;
-
- #if MICROVERSE_SPLINES
- private const bool MICROVERSE_INSTALLED = true;
- #else
- private const bool MICROVERSE_INSTALLED = false;
- #endif
-
- private static bool ExpandMesh
- {
- get => SessionState.GetBool("RM_EXPAND_MESH", true);
- set => SessionState.SetBool("RM_EXPAND_MESH", value);
- }
- private static bool ExpandEvents
- {
- get => SessionState.GetBool("RM_EXPAND_EVENTS", false);
- set => SessionState.SetBool("RM_EXPAND_EVENTS", value);
- }
- private static bool ExpandMV
- {
- get => SessionState.GetBool("RM_EXPAND_MV", false);
- set => SessionState.SetBool("RM_EXPAND_MV", value);
- }
- private static bool ExpandExport
- {
- get => SessionState.GetBool("RM_EXPAND_EXPORT", false);
- set => SessionState.SetBool("RM_EXPAND_EXPORT", value);
- }
- private RiverModeler.ChangeFlags changeFlags;
- private bool requiresRebuild = false;
- private System.Diagnostics.Stopwatch rebuildTimer;
- private void OnEnable()
- {
- rebuildTimer = new System.Diagnostics.Stopwatch();
- #if SPLINES
- splineContainer = serializedObject.FindProperty("splineContainer");
- splineChangeMode = serializedObject.FindProperty("splineChangeMode");
- #endif
-
- rebuildTriggers = serializedObject.FindProperty("rebuildTriggers");
- meshFilter = serializedObject.FindProperty("meshFilter");
- orderInLayer = serializedObject.FindProperty("orderInLayer");
-
- settings = serializedObject.FindProperty("settings");
- {
- triangulation = settings.FindPropertyRelative("triangulation");
- shape = settings.FindPropertyRelative("shape");
- displacement = settings.FindPropertyRelative("displacement");
- uv = settings.FindPropertyRelative("uv");
- foam = settings.FindPropertyRelative("foam");
- transparency = settings.FindPropertyRelative("transparency");
- }
-
- debugMode = serializedObject.FindProperty("debugMode");
- #pragma warning disable CS0162
- if (MICROVERSE_INSTALLED)
- {
- microVerseSettings = serializedObject.FindProperty("microVerseSettings");
- }
- #pragma warning restore CS0162
- isPrefab = PrefabUtility.IsPartOfPrefabInstance((RiverModeler)target) || PrefabStageUtility.GetCurrentPrefabStage();
- //may be too annoying, since a Spline Mesher prefab may serve as a settings container
- //isPrefab |= PrefabUtility.GetPrefabAssetType(target) != PrefabAssetType.NotAPrefab;
-
- exportToFBX = serializedObject.FindProperty("exportToFBX");
- fbxFilePath = serializedObject.FindProperty("fbxFilePath");
-
- onPreRebuild = serializedObject.FindProperty("onPreRebuild");
- onPostRebuild = serializedObject.FindProperty("onPostRebuild");
- }
- private void OnDisable()
- {
- ExportToFBX();
- }
- public override void OnInspectorGUI()
- {
- //base.OnInspectorGUI();
- UI.DrawHeader(Asset.NAME, Asset.VERSION);
- #if !SPLINES || !MATHEMATICS
- #if !SPLINES
- EditorGUILayout.HelpBox("The Spline package isn't installed, please install this through the Package Manager", MessageType.Error);
- #endif
- #if !MATHEMATICS
- EditorGUILayout.HelpBox("The Mathematics package isn't installed or outdated, please install this through the Package Manager", MessageType.Error);
- #endif
- return;
- #else
- //Reset
- changeFlags = RiverModeler.ChangeFlags.All;
- requiresRebuild = false;
- serializedObject.Update();
- EditorGUI.BeginChangeCheck();
-
- EditorGUILayout.LabelField("Source", EditorStyles.boldLabel);
- using (new EditorGUILayout.HorizontalScope())
- {
- EditorGUI.BeginChangeCheck();
- EditorGUILayout.PropertyField(splineContainer);
- if (EditorGUI.EndChangeCheck())
- {
- if (splineContainer.objectReferenceValue)
- {
- foreach (var target in targets)
- {
- ((RiverModeler)target).ValidateData(splineContainer.objectReferenceValue as SplineContainer);
- }
-
- changeFlags |= RiverModeler.ChangeFlags.Spline;
- requiresRebuild = true;
- }
- }
- EditorGUI.BeginDisabledGroup(splineContainer.objectReferenceValue == null);
- if (GUILayout.Button("Edit", EditorStyles.miniButton, GUILayout.Width(50f)))
- {
- Selection.activeGameObject = ((RiverModeler)target).splineContainer.gameObject;
- EditorApplication.delayCall += ToolManager.SetActiveContext<SplineToolContext>;
- }
- EditorGUI.EndDisabledGroup();
- }
- if (splineContainer.objectReferenceValue)
- {
- EditorGUILayout.Space();
-
- int rebuildTrigger = rebuildTriggers.intValue;
-
- if ((rebuildTrigger & (int)RiverModeler.RebuildTriggers.OnStart) != (int)RiverModeler.RebuildTriggers.OnStart && isPrefab)
- {
- EditorGUILayout.HelpBox("Procedurally created geometry cannot be used in a prefab." +
- "\n\nMesh data will be lost when the prefab is used outside of the scene it was created in." +
- "\n\nExport the created mesh to an FBX file, and use that instead. Or enable the \"On Start()\" option under Rebuild Triggers.", MessageType.Warning);
- }
-
- EditorGUILayout.Space();
- using (new EditorGUILayout.HorizontalScope())
- {
- EditorGUILayout.PropertyField(rebuildTriggers, new GUIContent("Rebuild triggers", rebuildTriggers.tooltip), GUILayout.Width(EditorGUIUtility.labelWidth + 140f));
- if (GUILayout.Button(new GUIContent(" Rebuild", EditorGUIUtility.IconContent("d_Refresh").image)))
- {
- Rebuild();
- }
- GUILayout.FlexibleSpace();
- }
- if ((rebuildTrigger & (int)RiverModeler.RebuildTriggers.OnSplineChanged) == (int)RiverModeler.RebuildTriggers.OnSplineChanged)
- {
- EditorGUI.indentLevel++;
- EditorGUILayout.PropertyField(splineChangeMode, new GUIContent("Spline Change Mode", splineChangeMode.tooltip), GUILayout.MaxWidth(EditorGUIUtility.labelWidth + 140f));
- EditorGUI.indentLevel--;
- }
- EditorGUILayout.Space();
- EditorGUILayout.LabelField("Destination", EditorStyles.boldLabel);
- EditorGUI.BeginChangeCheck();
- EditorGUILayout.PropertyField(meshFilter);
- if (EditorGUI.EndChangeCheck())
- {
- changeFlags |= RiverModeler.ChangeFlags.Geometry;
- requiresRebuild = true;
- }
- EditorGUI.indentLevel++;
- EditorGUILayout.PropertyField(orderInLayer);
- EditorGUI.indentLevel--;
- EditorGUILayout.Space();
-
- EditorGUILayout.PropertyField(debugMode, new GUIContent("Visualize"));
-
- EditorGUILayout.Space();
-
- if (meshFilter.objectReferenceValue)
- {
- ExpandMesh = EditorGUILayout.Foldout(ExpandMesh, "Mesh generation settings", EditorStyles.foldoutHeader);
-
- EditorGUILayout.BeginFadeGroup(ExpandMesh ? 1f : 0.001f);
- {
- EditorGUI.indentLevel++;
- EditorGUI.BeginChangeCheck();
-
- EditorGUILayout.PropertyField(triangulation);
- EditorGUILayout.PropertyField(shape);
- EditorGUILayout.PropertyField(displacement);
- if (EditorGUI.EndChangeCheck())
- {
- changeFlags |= RiverModeler.ChangeFlags.Geometry;
- requiresRebuild = true;
- }
-
- if (displacement.isExpanded)
- {
- using (new EditorGUILayout.HorizontalScope())
- {
- GUILayout.FlexibleSpace();
- if (GUILayout.Button(new GUIContent("Open Editor")))
- {
- ToolManager.SetActiveTool<ScaleTool>();
- }
- }
- }
- EditorGUI.BeginChangeCheck();
- EditorGUILayout.PropertyField(uv, new GUIContent("UV Coordinates", "Controls the UV coordinates, used for tiling and animating textures in the shader"));
-
- if (EditorGUI.EndChangeCheck())
- {
- changeFlags |= RiverModeler.ChangeFlags.VertexAttribute;
- requiresRebuild = true;
- }
-
- EditorGUI.BeginChangeCheck();
- EditorGUILayout.PropertyField(foam);
- if (EditorGUI.EndChangeCheck())
- {
- changeFlags |= RiverModeler.ChangeFlags.VertexAttribute | RiverModeler.ChangeFlags.Foam;
- requiresRebuild = true;
- }
-
- if (foam.isExpanded)
- {
- using (new EditorGUILayout.HorizontalScope())
- {
- GUILayout.FlexibleSpace();
- if (GUILayout.Button(new GUIContent("Open Editor")))
- {
- ToolManager.SetActiveTool<FoamTool>();
- }
- }
- }
-
- EditorGUI.BeginChangeCheck();
- EditorGUILayout.PropertyField(transparency);
- if (EditorGUI.EndChangeCheck())
- {
- changeFlags |= RiverModeler.ChangeFlags.VertexAttribute;
- requiresRebuild = true;
- }
- if (transparency.isExpanded)
- {
- using (new EditorGUILayout.HorizontalScope())
- {
- GUILayout.FlexibleSpace();
- if (GUILayout.Button(new GUIContent("Open Editor")))
- {
- ToolManager.SetActiveTool<TransparencyTool>();
- }
- }
- }
- EditorGUI.indentLevel--;
- }
- EditorGUILayout.EndFadeGroup();
- EditorGUILayout.Space();
-
- ExpandEvents = EditorGUILayout.Foldout(ExpandEvents, "Events", EditorStyles.foldoutHeader);
- EditorGUILayout.BeginFadeGroup(ExpandEvents ? 1f : 0.001f);
- {
- EditorGUILayout.PropertyField(onPreRebuild);
- EditorGUILayout.PropertyField(onPostRebuild);
- }
- EditorGUILayout.EndFadeGroup();
- EditorGUILayout.Space();
- //EditorGUILayout.LabelField("MicroVerse integration", EditorStyles.boldLabel);
- ExpandMV = EditorGUILayout.Foldout(ExpandMV, "MicroVerse integration", EditorStyles.foldoutHeader);
- EditorGUILayout.BeginFadeGroup(ExpandMV ? 1f : 0.001f);
- {
- #pragma warning disable CS0162
- if (MICROVERSE_INSTALLED)
- {
- microVerseSettings.isExpanded = true;
-
- EditorGUI.BeginChangeCheck();
- EditorGUILayout.PropertyField(microVerseSettings, true);
- if (EditorGUI.EndChangeCheck())
- {
- changeFlags |= RiverModeler.ChangeFlags.Data;
-
- foreach (var target in targets)
- {
- ((RiverModeler)target).UpdateMicroVerseSpline();
- }
- }
- }
- else
- {
- UI.DrawActionBox("The MicroVerse Splines module isn't installed", MessageType.Info, "Open Store Page", () => UI.OpenStorePage(232974, "rivermodelereditor"));
- EditorGUILayout.HelpBox("The MicroVerse asset, with its Splines module, allows for rivers to carve into the terrain and create a bank on its sides.\n\n" +
- "When installed, updates to this component's will trigger the MicroVerse spline to update as well.", MessageType.None);
- }
- #pragma warning restore CS0162
- }
- EditorGUILayout.EndFadeGroup();
-
- EditorGUILayout.Space();
- ExpandExport = EditorGUILayout.Foldout(ExpandExport, "FBX Export", EditorStyles.foldoutHeader);
- EditorGUILayout.BeginFadeGroup(ExpandExport ? 1f : 0.001f);
- {
- EditorGUILayout.PropertyField(exportToFBX, new GUIContent("Enable", exportToFBX.tooltip));
-
- if (exportToFBX.boolValue == false)
- {
- EditorGUILayout.HelpBox("\n" +
- "Saving the generated mesh to an FBX file is recommended to benefit from file compression and segmenting scene contents for optimal loading performance " +
- "(in large and complex scenes)." +
- "\n\n" +
- "For use in Prefabs, this is required to retain the mesh data. It is otherwise saved and available purely only the scene." +
- "\n", MessageType.Info);
- }
- if (exportToFBX.boolValue)
- {
- EditorGUILayout.Space();
- #if FBX_EXPORTER
- EditorGUILayout.BeginHorizontal();
- {
- EditorGUILayout.PropertyField(fbxFilePath, new GUIContent("File path", fbxFilePath.tooltip));
-
- if (GUILayout.Button(new GUIContent("...", "Browse"), GUILayout.Width(50f)))
- {
- string newPath = EditorUtility.SaveFilePanelInProject("FBX destination folder", target.name, "fbx", "Choose FBX file location");
- if (newPath != string.Empty)
- {
- fbxFilePath.stringValue = newPath;
- }
- }
-
- if (GUILayout.Button("Ping", GUILayout.Width(60f)))
- {
- UnityEngine.Object exportedObject = AssetDatabase.LoadAssetAtPath<UnityEngine.Object>(fbxFilePath.stringValue);
- if (exportedObject)
- {
- EditorGUIUtility.PingObject(exportedObject);
-
- var fileInfo = new System.IO.FileInfo(fbxFilePath.stringValue);
- float bytes = (fileInfo.Length / 1024f) / 1024f;
- SceneView.lastActiveSceneView.ShowNotification(new GUIContent($"File size: {(float)System.Math.Round(bytes, 2)}mb"), 1f);
- }
- }
- }
- EditorGUILayout.EndHorizontal();
- if (fbxFilePath.stringValue == string.Empty)
- {
- EditorGUILayout.HelpBox("File path should not be blank", MessageType.Warning);
- }
-
- EditorGUILayout.HelpBox("The mesh will be re-exported if it has changed once the inspector is closed.", MessageType.Info);
- #else
- UI.DrawActionBox("The FBX Exporter package is not installed, it is required for this functionality", MessageType.Error, "Install", PackageInstaller.InstallFBXExporter);
- #endif
- }
- }
- EditorGUILayout.EndFadeGroup();
- }
- else
- {
- EditorGUILayout.HelpBox("A Mesh Filter for output is required. Assign one you wish to generate a river mesh for.", MessageType.Error);
- }
- }
- else
- {
- EditorGUILayout.HelpBox("A spline container must be assigned. Assign one you wish to generate a river from.", MessageType.Warning);
- }
- if (EditorGUI.EndChangeCheck())
- {
- serializedObject.ApplyModifiedProperties();
- if (requiresRebuild)
- {
- if(((RiverModeler)target).rebuildTriggers.HasFlag(RiverModeler.RebuildTriggers.OnUIChange))
- {
- Rebuild();
- }
- }
- }
-
- EditorGUILayout.Space();
- if (((RiverModeler)target).rebuildTriggers.HasFlag(RiverModeler.RebuildTriggers.OnUIChange) == false)
- {
- EditorGUILayout.HelpBox("Auto-rebuilding on UI change is disabled (see Rebuilder Triggers)", MessageType.None);
-
- using (new EditorGUILayout.HorizontalScope())
- {
- GUILayout.FlexibleSpace();
- if (GUILayout.Button("Rebuild now"))
- {
- Rebuild();
- }
- GUILayout.FlexibleSpace();
- }
- }
-
- #endif
-
- UI.DrawFooter();
-
- #if WGT_DEV
- using (new EditorGUILayout.HorizontalScope())
- {
- EditorGUILayout.LabelField($"Rebuild time: {rebuildTimer.ElapsedMilliseconds}ms", EditorStyles.miniLabel);
- }
- #endif
- }
-
- private void Rebuild()
- {
- requiresRebuild = false;
- if (Asset.Preferences.RebuildEveryFrame)
- {
- RebuildTargets();
- }
- else
- {
- EditorApplication.delayCall += RebuildTargets;
- }
- }
-
- private void RebuildTargets()
- {
- rebuildTimer.Reset();
- rebuildTimer.Start();
-
- foreach (var m_target in targets)
- {
- ((RiverModeler)m_target).Rebuild(changeFlags);
- }
-
- rebuildTimer.Stop();
- }
- private void ExportToFBX()
- {
- #if FBX_EXPORTER
- foreach (var target in targets)
- {
- if (((RiverModeler)target).exportToFBX)
- {
- RiverModeler component = ((RiverModeler)target);
-
- if (component.meshFilter && component.meshFilter.sharedMesh)
- {
- if (EditorUtility.IsDirty(component.meshFilter.sharedMesh) || !EditorUtility.IsPersistent(component.meshFilter.sharedMesh))
- {
- //Debug.Log($"Mesh ({component.meshFilter.sharedMesh.name}) was changed, exporting to {component.fbxFilePath}");
- EditorUtilities.FBX.SaveToFileAndReference(component.gameObject, component.fbxFilePath);
- }
- /*
- else
- {
- Debug.Log($"Mesh ({component.meshFilter.sharedMesh.name}) hasn't changed, so won't require exporting");
- }
- */
- }
- }
- }
- #endif
- }
- }
- }
|