diff --git a/DunGenPlus/DunGenPlus/Collections/DunGenExtenderPropertiesCollection.cs b/DunGenPlus/DunGenPlus/Collections/DunGenExtenderPropertiesCollection.cs index 03e34d4..2c01ca0 100644 --- a/DunGenPlus/DunGenPlus/Collections/DunGenExtenderPropertiesCollection.cs +++ b/DunGenPlus/DunGenPlus/Collections/DunGenExtenderPropertiesCollection.cs @@ -179,6 +179,27 @@ namespace DunGenPlus.Collections { [Tooltip("The weight scale for the branch path's number of connections to other main paths. For each possible connection, the main path normalized depth difference is multiplied by the scale and is added to the branch path's weight.\n\nIncreasing this value will prioritize branch paths who make generally deep path loops to other main paths.")] public float DiffPathNormalizedDepthWeightScale = 2f; + public float GetWeightBase(float length, float normalizedLength){ + var weight = 0f; + weight += length * LengthWeightScale; + weight += normalizedLength * NormalizedLengthWeightScale; + return weight; + } + + public float GetWeightPathConnection(bool samePath, float depthDifference, float normalizedDepthDifference){ + var weight = 0f; + if (samePath) { + weight += SamePathBaseWeightScale; + weight += depthDifference * SamePathDepthWeightScale; + weight += normalizedDepthDifference * SamePathNormalizedDepthWeightScale; + } else { + weight += DiffPathBaseWeightScale; + weight += depthDifference * DiffPathDepthWeightScale; + weight += normalizedDepthDifference * DiffPathNormalizedDepthWeightScale; + } + return weight; + } + internal void CopyFrom(BranchPathMultiSimulationProperties props) { UseBranchPathMultiSim = props.UseBranchPathMultiSim; SimulationCount = props.SimulationCount; diff --git a/DunGenPlus/DunGenPlus/Collections/NullObject.cs b/DunGenPlus/DunGenPlus/Collections/NullObject.cs index e84ce3a..e44200e 100644 --- a/DunGenPlus/DunGenPlus/Collections/NullObject.cs +++ b/DunGenPlus/DunGenPlus/Collections/NullObject.cs @@ -7,7 +7,7 @@ using System.Threading.Tasks; namespace DunGenPlus.Collections { // https://stackoverflow.com/questions/4632945/why-doesnt-dictionarytkey-tvalue-support-null-key - internal struct NullObject where T: class{ + internal struct NullObject where T: UnityEngine.Object { public T Item; private bool isNull; @@ -31,7 +31,7 @@ namespace DunGenPlus.Collections { } public override string ToString() { - return (Item != null) ? Item.ToString() : "NULL"; + return (Item != null) ? Item.name : "NULL"; } public override bool Equals(object obj) { diff --git a/DunGenPlus/DunGenPlus/DevTools/DevDebugManager.cs b/DunGenPlus/DunGenPlus/DevTools/DevDebugManager.cs index 5b0eca7..5fd1a66 100644 --- a/DunGenPlus/DunGenPlus/DevTools/DevDebugManager.cs +++ b/DunGenPlus/DunGenPlus/DevTools/DevDebugManager.cs @@ -13,6 +13,7 @@ using UnityEngine.InputSystem; using DunGenPlus.DevTools.Panels; using DunGenPlus.DevTools.UIElements; using DunGenPlus.Generation; +using DunGenPlus.DevTools.Panels.Collections; namespace DunGenPlus.DevTools { internal partial class DevDebugManager : MonoBehaviour { @@ -25,7 +26,12 @@ namespace DunGenPlus.DevTools { public TMP_Dropdown dungeonFlowSelectionDropDown; private ExtendedDungeonFlow[] dungeonFlows; - internal ExtendedDungeonFlow selectedDungeonFlow; + + internal ExtendedDungeonFlow selectedExtendedDungeonFlow; + internal DungeonFlow selectedDungeonFlow; + internal DungeonFlowCacheAssets selectedAssetCache; + + internal Dictionary cacheDictionary = new Dictionary(); public TextMeshProUGUI statusTextMesh; public TextMeshProUGUI statsTextMesh; @@ -51,6 +57,7 @@ namespace DunGenPlus.DevTools { foreach(var p in panels) p.AwakeCall(); OpenPanel(0); + UpdatePanels(); dungeon.Generator.OnGenerationStatusChanged += OnDungeonFinished; @@ -61,6 +68,12 @@ namespace DunGenPlus.DevTools { void OnDestroy(){ Instance = null; + MainPanel.Instance = null; + DunFlowPanel.Instance = null; + DunGenPlusPanel.Instance = null; + + Cursor.lockState = CursorLockMode.Locked; + Cursor.visible = false; EndDevCamera(); } @@ -86,10 +99,19 @@ namespace DunGenPlus.DevTools { } public void SelectDungeonFlow(int index){ - selectedDungeonFlow = dungeonFlows[index]; - dungeon.Generator.DungeonFlow = selectedDungeonFlow.DungeonFlow; - UpdatePlusPanel(); - Plugin.logger.LogInfo($"Selecting {selectedDungeonFlow.DungeonName}"); + selectedExtendedDungeonFlow = dungeonFlows[index]; + selectedDungeonFlow = selectedExtendedDungeonFlow.DungeonFlow; + dungeon.Generator.DungeonFlow = selectedDungeonFlow; + + if (!cacheDictionary.TryGetValue(selectedDungeonFlow, out var cache)) { + var extender = API.GetDunGenExtender(selectedDungeonFlow); + cache = new DungeonFlowCacheAssets(selectedDungeonFlow, extender); + cacheDictionary.Add(selectedDungeonFlow, cache); + } + selectedAssetCache = cache; + + UpdatePanels(); + Plugin.logger.LogInfo($"Selecting {selectedExtendedDungeonFlow.DungeonName}"); } public void GenerateDungeon(){ @@ -99,7 +121,7 @@ namespace DunGenPlus.DevTools { fakeRoundManager = disabledGameObject.AddComponent(); fakeRoundManager.dungeonGenerator = dungeon; - selectedDungeonFlow.DungeonEvents.onBeforeDungeonGenerate?.Invoke(fakeRoundManager); + selectedExtendedDungeonFlow.DungeonEvents.onBeforeDungeonGenerate?.Invoke(fakeRoundManager); DungeonManager.GlobalDungeonEvents?.onBeforeDungeonGenerate?.Invoke(fakeRoundManager); DunGenPlusGenerator.GenerateBranchBoostedPathsTime = 0f; @@ -171,21 +193,16 @@ namespace DunGenPlus.DevTools { } public void RecordNewSeed(int seed){ - MainPanel.Instance.seedInputField.Set(seed); + MainPanel.Instance?.seedInputField.Set(seed); } - private void UpdatePlusPanel() { - foreach(var p in panels) { - var plusPanel = p as DunGenPlusPanel; - if (plusPanel) plusPanel.UpdatePanel(); - } + private void UpdatePanels() { + DunFlowPanel.Instance?.UpdatePanel(true); + DunGenPlusPanel.Instance?.UpdatePanel(true); } public void UpdateDungeonBounds(){ - foreach(var p in panels) { - var plusPanel = p as DunGenPlusPanel; - if (plusPanel) plusPanel.UpdateDungeonBoundsHelper(); - } + DunGenPlusPanel.Instance?.UpdateDungeonBoundsHelper(); } private void GetAllDungeonFlows(){ diff --git a/DunGenPlus/DunGenPlus/DevTools/DevDebugManagerUI.cs b/DunGenPlus/DunGenPlus/DevTools/DevDebugManagerUI.cs index a246690..09acdb3 100644 --- a/DunGenPlus/DunGenPlus/DevTools/DevDebugManagerUI.cs +++ b/DunGenPlus/DunGenPlus/DevTools/DevDebugManagerUI.cs @@ -32,6 +32,8 @@ namespace DunGenPlus.DevTools { public GameObject boolInputFieldPrefab; public GameObject stringInputFieldPrefab; public GameObject vector3InputFieldPrefab; + public GameObject intRangeInputFieldPrefab; + public GameObject floatRangeInputFieldPrefab; public GameObject intSliderFieldPrefab; [Header("Special Fields")] @@ -95,6 +97,20 @@ namespace DunGenPlus.DevTools { return field; } + public IntRangeInputField CreateIntRangeInputField(Transform parentTransform, TitleParameter titleParameter, IntRange baseValue, Action setAction){ + var gameObject = Instantiate(intRangeInputFieldPrefab, parentTransform); + var field = gameObject.GetComponent(); + field.SetupInputField(titleParameter, baseValue, setAction); + return field; + } + + public FloatRangeInputField CreateFloatRangeInputField(Transform parentTransform, TitleParameter titleParameter, FloatRange baseValue, Action setAction){ + var gameObject = Instantiate(floatRangeInputFieldPrefab, parentTransform); + var field = gameObject.GetComponent(); + field.SetupInputField(titleParameter, baseValue, setAction); + return field; + } + public IntSliderField CreateIntSliderField(Transform parentTransform, TitleParameter titleParameter, IntParameter intParameter, Action setAction){ var gameObject = Instantiate(intSliderFieldPrefab, parentTransform); var field = gameObject.GetComponent(); @@ -123,23 +139,23 @@ namespace DunGenPlus.DevTools { } public DropdownInputField CreateTileOptionsUIField(Transform parentTransform, TitleParameter titleParameter, int baseValue, Action setAction){ - var assetCache = DunGenPlusPanel.Instance.selectedAssetCache; + var assetCache = DevDebugManager.Instance.selectedAssetCache; return CreateOptionsUIField(parentTransform, titleParameter, baseValue, setAction, (i) => assetCache.tiles.list[i].Item, assetCache.tiles.options); } public DropdownInputField CreateTileSetsOptionsUIField(Transform parentTransform, TitleParameter titleParameter, int baseValue, Action setAction){ - var assetCache = DunGenPlusPanel.Instance.selectedAssetCache; + var assetCache = DevDebugManager.Instance.selectedAssetCache; return CreateOptionsUIField(parentTransform, titleParameter, baseValue, setAction, (i) => assetCache.tileSets.list[i].Item, assetCache.tileSets.options); } public DropdownInputField CreateArchetypeOptionsUIField(Transform parentTransform, TitleParameter titleParameter, int baseValue, Action setAction){ - var assetCache = DunGenPlusPanel.Instance.selectedAssetCache; + var assetCache = DevDebugManager.Instance.selectedAssetCache; return CreateOptionsUIField(parentTransform, titleParameter, baseValue, setAction, (i) => assetCache.archetypes.list[i].Item, assetCache.archetypes.options); } - public DropdownInputField CreateCopyNodeBehaviourOptionsUIField(Transform parentTransform, TitleParameter titleParameter, int baseValue, Action setAction){ - var options = Enum.GetNames(typeof(DunGenExtenderProperties.CopyNodeBehaviour)); - return CreateOptionsUIField(parentTransform, titleParameter, baseValue, setAction, (i) => (DunGenExtenderProperties.CopyNodeBehaviour)i, options); + public DropdownInputField CreateEnumOptionsUIField(Transform parentTransform, TitleParameter titleParameter, int baseValue, Action setAction) where T: Enum{ + var options = Enum.GetNames(typeof(T)); + return CreateOptionsUIField(parentTransform, titleParameter, baseValue, setAction, (i) => (T)(object)i, options); } public DropdownInputField CreateAnimationCurveOptionsUIField(Transform parentTransform, TitleParameter titleParameter, AnimationCurve baseValue, Action setAction){ diff --git a/DunGenPlus/DunGenPlus/DevTools/Panels/BasePanel.cs b/DunGenPlus/DunGenPlus/DevTools/Panels/BasePanel.cs index e1c4dc0..d8ae702 100644 --- a/DunGenPlus/DunGenPlus/DevTools/Panels/BasePanel.cs +++ b/DunGenPlus/DunGenPlus/DevTools/Panels/BasePanel.cs @@ -1,5 +1,6 @@ using DunGen; using DunGen.Graph; +using DunGenPlus.DevTools.Panels.Collections; using LethalLevelLoader; using System; using System.Collections.Generic; @@ -13,10 +14,11 @@ namespace DunGenPlus.DevTools.Panels { internal abstract class BasePanel : MonoBehaviour { public DevDebugManager manager => DevDebugManager.Instance; - public RuntimeDungeon dungeon => manager.dungeon; - public ExtendedDungeonFlow selectedExtendedDungeonFlow => manager.selectedDungeonFlow; - public DungeonFlow selectedDungeonFlow => selectedExtendedDungeonFlow.DungeonFlow; - + protected RuntimeDungeon dungeon => manager.dungeon; + protected ExtendedDungeonFlow selectedExtendedDungeonFlow => manager.selectedExtendedDungeonFlow; + protected DungeonFlow selectedDungeonFlow => manager.selectedDungeonFlow; + protected DungeonFlowCacheAssets selectedAssetCache => manager.selectedAssetCache; + [Header("Renders")] public GameObject mainGameObject; public PanelTab tab; diff --git a/DunGenPlus/DunGenPlus/DevTools/Panels/Collections/DungeonFlowCacheAssets.cs b/DunGenPlus/DunGenPlus/DevTools/Panels/Collections/DungeonFlowCacheAssets.cs index cb50159..e14198a 100644 --- a/DunGenPlus/DunGenPlus/DevTools/Panels/Collections/DungeonFlowCacheAssets.cs +++ b/DunGenPlus/DunGenPlus/DevTools/Panels/Collections/DungeonFlowCacheAssets.cs @@ -1,4 +1,5 @@ using DunGen; +using DunGen.Graph; using DunGenPlus.Collections; using System; using System.Collections.Generic; @@ -35,14 +36,16 @@ namespace DunGenPlus.DevTools.Panels.Collections { public readonly Collection> tiles; public readonly Collection> archetypes; - public DungeonFlowCacheAssets(DunGenExtender extender){ - originalProperties = extender.Properties.Copy(); - + public DungeonFlowCacheAssets(DungeonFlow dungeonFlow, DunGenExtender extender){ + if (extender){ + originalProperties = extender.Properties.Copy(); + } + var tileSetsHashSet = new HashSet>() { new NullObject(null) }; var tilesHashSet = new HashSet>() { new NullObject(null) }; var archetypesHashSet = new HashSet>() { new NullObject(null) }; - foreach(var t in extender.DungeonFlow.Nodes) { + foreach(var t in dungeonFlow.Nodes) { var label = t.Label.ToLowerInvariant(); if (label == "lchc gate" || label == "goal"){ foreach(var n in t.TileSets.SelectMany(x => x.TileWeights.Weights)) { @@ -78,14 +81,18 @@ namespace DunGenPlus.DevTools.Panels.Collections { } } - AddTileSets(extender.DungeonFlow.Nodes.SelectMany(n => n.TileSets)); - AddArchetypes(extender.DungeonFlow.Lines.SelectMany(l => l.DungeonArchetypes)); - AddArchetypes(extender.Properties.NormalNodeArchetypesProperties.NormalNodeArchetypes.SelectMany(l => l.archetypes)); - AddTileSets(extender.Properties.ForcedTilesProperties.ForcedTileSets.SelectMany(l => l.Tilesets)); + AddTileSets(dungeonFlow.Nodes.SelectMany(n => n.TileSets)); + AddArchetypes(dungeonFlow.Lines.SelectMany(l => l.DungeonArchetypes)); + AddTileSets(dungeonFlow.TileInjectionRules.Select(n => n.TileSet)); - AddTiles(extender.Properties.AssetCacheTileList); - AddTileSets(extender.Properties.AssetCacheTileSetList); - AddArchetypes(extender.Properties.AssetCacheArchetypeList); + if (extender) { + AddArchetypes(extender.Properties.NormalNodeArchetypesProperties.NormalNodeArchetypes.SelectMany(l => l.archetypes)); + AddTileSets(extender.Properties.ForcedTilesProperties.ForcedTileSets.SelectMany(l => l.Tilesets)); + + AddTiles(extender.Properties.AssetCacheTileList); + AddTileSets(extender.Properties.AssetCacheTileSetList); + AddArchetypes(extender.Properties.AssetCacheArchetypeList); + } tileSets = new Collection>(tileSetsHashSet.ToList()); tiles = new Collection>(tilesHashSet.ToList()); diff --git a/DunGenPlus/DunGenPlus/DevTools/Panels/DunFlowPanel.cs b/DunGenPlus/DunGenPlus/DevTools/Panels/DunFlowPanel.cs new file mode 100644 index 0000000..26c431d --- /dev/null +++ b/DunGenPlus/DunGenPlus/DevTools/Panels/DunFlowPanel.cs @@ -0,0 +1,72 @@ +using DunGen; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; + +namespace DunGenPlus.DevTools.Panels { + internal class DunFlowPanel : BasePanel { + public static DunFlowPanel Instance { get; internal set; } + + private GameObject branchPathParentGameobject; + + public override void AwakeCall(){ + Instance = this; + Plugin.logger.LogInfo("AwakeCall"); + } + + + public override void SetPanelVisibility(bool visible){ + base.SetPanelVisibility(visible); + if (visible) UpdatePanel(false); + } + + public void UpdatePanel(bool refreshPanel){ + if (refreshPanel) { + ClearPanel(); + SetupPanel(); + } + } + + public void SetupPanel(){ + var parentTransform = mainGameObject.transform; + + var branchPathParentTransform = manager.CreateVerticalLayoutUIField(parentTransform); + branchPathParentGameobject = branchPathParentTransform.gameObject; + manager.CreateHeaderUIField(parentTransform, "Paths"); + manager.CreateIntRangeInputField(parentTransform, "Main Path Length", selectedDungeonFlow.Length, SetLength); + manager.CreateEnumOptionsUIField(parentTransform, "Branch Mode", (int)selectedDungeonFlow.BranchMode, SetBranchMode); + manager.CreateIntRangeInputField(branchPathParentTransform, "Branch Path Count", selectedDungeonFlow.BranchCount, SetBranchCount); + branchPathParentTransform.SetAsLastSibling(); + manager.CreateSpaceUIField(parentTransform); + + manager.CreateHeaderUIField(parentTransform, "Generation"); + manager.CreateListUIField(parentTransform, "Tile Injection Rules", selectedDungeonFlow.TileInjectionRules); + manager.CreateSpaceUIField(parentTransform); + manager.CreateListUIField(parentTransform, "Nodes", selectedDungeonFlow.Nodes); + manager.CreateSpaceUIField(parentTransform); + manager.CreateListUIField(parentTransform, "Lines", selectedDungeonFlow.Lines); + manager.CreateSpaceUIField(parentTransform); + } + + public void ClearPanel(){ + manager.ClearTransformChildren(mainGameObject.transform); + } + + + public void SetLength(IntRange value){ + selectedDungeonFlow.Length = value; + } + + public void SetBranchMode(DunGen.BranchMode value){ + selectedDungeonFlow.BranchMode = value; + branchPathParentGameobject.SetActive(value == BranchMode.Global); + } + + public void SetBranchCount(IntRange value){ + selectedDungeonFlow.BranchCount = value; + } + } +} diff --git a/DunGenPlus/DunGenPlus/DevTools/Panels/DunGenPlusPanel.cs b/DunGenPlus/DunGenPlus/DevTools/Panels/DunGenPlusPanel.cs index 731661c..1279b65 100644 --- a/DunGenPlus/DunGenPlus/DevTools/Panels/DunGenPlusPanel.cs +++ b/DunGenPlus/DunGenPlus/DevTools/Panels/DunGenPlusPanel.cs @@ -17,11 +17,9 @@ using DunGenPlus.DevTools.Panels.Collections; namespace DunGenPlus.DevTools.Panels { internal class DunGenPlusPanel : BasePanel { - public static DunGenPlusPanel Instance { get; private set; } + public static DunGenPlusPanel Instance { get; internal set; } - internal DungeonFlow previousDungeonFlow; internal DunGenExtender selectedExtenderer; - internal DungeonFlowCacheAssets selectedAssetCache; [Header("Panel References")] public GameObject createGameObject; @@ -38,8 +36,6 @@ namespace DunGenPlus.DevTools.Panels { private GameObject branchLoopBoostParentGameobject; private GameObject maxShadowsParentGameobject; - public Dictionary cacheDictionary = new Dictionary(); - public override void AwakeCall() { Instance = this; @@ -48,47 +44,36 @@ namespace DunGenPlus.DevTools.Panels { public override void SetPanelVisibility(bool visible) { base.SetPanelVisibility(visible); - - if (visible) UpdatePanel(); + if (visible) UpdatePanel(false); } public void CreateDunGenPlusExtenderer(){ var asset = API.CreateDunGenExtender(selectedDungeonFlow); selectedDungeonFlow.TileInjectionRules = new List(); API.AddDunGenExtender(asset); - SetPanelVisibility(true); - UpdatePanel(); + + UpdatePanel(true); } - public void UpdatePanel(){ - if (previousDungeonFlow == selectedDungeonFlow) return; - + public void UpdatePanel(bool refreshPanel){ var hasAsset = API.ContainsDungeonFlow(selectedDungeonFlow); selectedGameObject.SetActive(hasAsset); createGameObject.SetActive(!hasAsset); - ClearPanel(); - if (hasAsset) { - SetupPanel(); - } else { - previousDungeonFlow = null; - selectedExtenderer = null; - selectedAssetCache = null; - dungeonBoundsHelperGameObject.SetActive(false); + if (refreshPanel) { + ClearPanel(); + if (hasAsset) { + SetupPanel(); + } else { + selectedExtenderer = null; + dungeonBoundsHelperGameObject.SetActive(false); + } } + } public void SetupPanel() { - var dungeonFlow = selectedDungeonFlow; - var extender = API.GetDunGenExtender(dungeonFlow); - if (!cacheDictionary.TryGetValue(dungeonFlow, out var cache)) { - cache = new DungeonFlowCacheAssets(extender); - cacheDictionary.Add(dungeonFlow, cache); - } - - previousDungeonFlow = dungeonFlow; - selectedExtenderer = extender; - selectedAssetCache = cache; + selectedExtenderer = API.GetDunGenExtender(selectedDungeonFlow); var parentTransform = selectedListGameObject.transform; var properties = selectedExtenderer.Properties; @@ -101,7 +86,7 @@ namespace DunGenPlus.DevTools.Panels { manager.CreateIntSliderField(parentTransform, "Main Path Count", new IntParameter(properties.MainPathProperties.MainPathCount, 1, 10), SetMainPathCount); mainPathTransform.SetAsLastSibling(); manager.CreateTileOptionsUIField(mainPathTransform, "Main Room Tile Prefab", selectedAssetCache.tiles.dictionary[properties.MainPathProperties.MainRoomTilePrefab], SetMainRoom); - manager.CreateCopyNodeBehaviourOptionsUIField(mainPathTransform, "Copy Node Behaviour", (int)properties.MainPathProperties.CopyNodeBehaviour, SetCopyNodeBehaviour); + manager.CreateEnumOptionsUIField(mainPathTransform, "Copy Node Behaviour", (int)properties.MainPathProperties.CopyNodeBehaviour, SetCopyNodeBehaviour); manager.CreateSpaceUIField(parentTransform); var dungeonBoundsTransform = manager.CreateVerticalLayoutUIField(parentTransform); @@ -139,19 +124,19 @@ namespace DunGenPlus.DevTools.Panels { manager.CreateIntInputField(branchLoopTransform, "Simulation Count", new IntParameter(properties.BranchPathMultiSimulationProperties.SimulationCount, 1, 10, 1), SetSimulationCount); manager.CreateFloatInputField(branchLoopTransform, "Length Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.LengthWeightScale, 0f, 2f, 0f), SetLengthScale); manager.CreateFloatInputField(branchLoopTransform, "Norm. Length Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.NormalizedLengthWeightScale, 0f, 2f, 0f), SetNormalizedLengthScale); - manager.CreateSpaceUIField(parentTransform); + manager.CreateSpaceUIField(branchLoopTransform); manager.CreateTextUIField(branchLoopTransform, "Same Path Connect"); manager.CreateFloatInputField(branchLoopTransform, "Base Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.SamePathBaseWeightScale, 0f, 2f, 0f), SamePathBaseConnectScale); manager.CreateFloatInputField(branchLoopTransform, "Depth Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.SamePathDepthWeightScale, 0f, 2f, 0f), SamePathConnectDepthScale); manager.CreateFloatInputField(branchLoopTransform, "Norm. Depth Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.SamePathNormalizedDepthWeightScale, 0f, 2f, 0f), SamePathConnectNormalizedDepthScale); - manager.CreateSpaceUIField(parentTransform); + manager.CreateSpaceUIField(branchLoopTransform); manager.CreateTextUIField(branchLoopTransform, "Diff Path Connect"); manager.CreateFloatInputField(branchLoopTransform, "Base Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.DiffPathBaseWeightScale, 0f, 2f, 0f), DiffPathBaseConnectScale); manager.CreateFloatInputField(branchLoopTransform, "Depth Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.DiffPathDepthWeightScale, 0f, 2f, 0f), DiffPathConnectDepthScale); manager.CreateFloatInputField(branchLoopTransform, "Norm. Depth Weight Scale", new FloatParameter(properties.BranchPathMultiSimulationProperties.DiffPathNormalizedDepthWeightScale, 0f, 2f, 0f), DiffPathConnectNormalizedDepthScale); - manager.CreateSpaceUIField(parentTransform); + manager.CreateSpaceUIField(branchLoopTransform); manager.CreateHeaderUIField(parentTransform, "Miscellaneous"); var maxShadowTransform = manager.CreateVerticalLayoutUIField(parentTransform); diff --git a/DunGenPlus/DunGenPlus/DevTools/Panels/MainPanel.cs b/DunGenPlus/DunGenPlus/DevTools/Panels/MainPanel.cs index c80dc15..c2cd33f 100644 --- a/DunGenPlus/DunGenPlus/DevTools/Panels/MainPanel.cs +++ b/DunGenPlus/DunGenPlus/DevTools/Panels/MainPanel.cs @@ -14,7 +14,7 @@ using UnityEngine.UI; namespace DunGenPlus.DevTools.Panels { internal class MainPanel : BasePanel { - public static MainPanel Instance { get; private set; } + public static MainPanel Instance { get; internal set; } internal IntInputField seedInputField; internal TextUIElement lengthMultiplierField; diff --git a/DunGenPlus/DunGenPlus/DevTools/UIElements/Collections/ListEntryType.cs b/DunGenPlus/DunGenPlus/DevTools/UIElements/Collections/ListEntryType.cs new file mode 100644 index 0000000..b2b2ed7 --- /dev/null +++ b/DunGenPlus/DunGenPlus/DevTools/UIElements/Collections/ListEntryType.cs @@ -0,0 +1,110 @@ +using DunGen; +using DunGen.Graph; +using DunGenPlus.Collections; +using DunGenPlus.DevTools.Panels; +using System; +using System.Collections; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; + +namespace DunGenPlus.DevTools.UIElements.Collections { + internal abstract class ListEntryType { + public abstract object CreateEmptyObject(); + public abstract void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset); + } + + internal class ListEntryDungeonArchetype : ListEntryType { + public override object CreateEmptyObject() => null; + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset) { + var entry = (DungeonArchetype)list[index]; + var baseValue = DevDebugManager.Instance.selectedAssetCache.archetypes.dictionary[entry]; + DevDebugManager.Instance.CreateArchetypeOptionsUIField(parentTransform, new TitleParameter("Archetype", layoutOffset), baseValue, (t) => list[index] = t); + } + } + + internal class ListEntryTileSet : ListEntryType { + public override object CreateEmptyObject() => null; + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset) { + var entry = (TileSet)list[index]; + var baseValue = DevDebugManager.Instance.selectedAssetCache.tileSets.dictionary[entry]; + DevDebugManager.Instance.CreateTileSetsOptionsUIField(parentTransform, new TitleParameter("Tile Set", layoutOffset), baseValue, (t) => list[index] = t); + } + } + + internal class ListEntryNodeArchetype : ListEntryType { + public override object CreateEmptyObject() => new NodeArchetype(); + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset) { + var entry = (NodeArchetype)list[index]; + DevDebugManager.Instance.CreateStringInputField(parentTransform, new TitleParameter("Label", layoutOffset), entry.label, (t) => entry.label = t); + DevDebugManager.Instance.CreateListUIField(parentTransform, new TitleParameter("Archetypes", layoutOffset), entry.archetypes); + } + } + + internal class ListEntryForcedTileSetList : ListEntryType { + public override object CreateEmptyObject() { + var forcedTileset = new ForcedTileSetList(); + forcedTileset.DepthWeightScale = null; + return forcedTileset; + } + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset) { + var entry = (ForcedTileSetList)list[index]; + DevDebugManager.Instance.CreateFloatInputField(parentTransform, new TitleParameter("Main Path Weight", layoutOffset), entry.MainPathWeight, (t) => entry.MainPathWeight = t); + DevDebugManager.Instance.CreateFloatInputField(parentTransform, new TitleParameter("Branch Path Weight", layoutOffset), entry.BranchPathWeight, (t) => entry.BranchPathWeight = t); + + // depth is weird cause we have to account for every entry's unique depth curve, even if they don't have one + DevDebugManager.Instance.CreateAnimationCurveOptionsUIField(parentTransform, new TitleParameter("Depth Weight Scale", layoutOffset), entry.DepthWeightScale, (t) => entry.DepthWeightScale = t); + DevDebugManager.Instance.CreateListUIField(parentTransform, new TitleParameter("Tile Sets", layoutOffset), entry.Tilesets); + } + } + + internal class ListEntryTileInjectionRule : ListEntryType { + + public override object CreateEmptyObject() => new TileInjectionRule(); + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset){ + var entry = (TileInjectionRule)list[index]; + var baseValue = DevDebugManager.Instance.selectedAssetCache.tileSets.dictionary[entry.TileSet]; + DevDebugManager.Instance.CreateTileSetsOptionsUIField(parentTransform, "Tile Set", baseValue, (t) => entry.TileSet = t); + + DevDebugManager.Instance.CreateFloatRangeInputField(parentTransform, "Norm. Path Depth", entry.NormalizedPathDepth, (t) => entry.NormalizedPathDepth = t); + DevDebugManager.Instance.CreateFloatRangeInputField(parentTransform, "Norm. Branch Depth", entry.NormalizedBranchDepth, (t) => entry.NormalizedBranchDepth = t); + + DevDebugManager.Instance.CreateBoolInputField(parentTransform, "Appear On Main Path", entry.CanAppearOnMainPath, (t) => entry.CanAppearOnMainPath = t); + DevDebugManager.Instance.CreateBoolInputField(parentTransform, "Appear On Branch Path", entry.CanAppearOnBranchPath, (t) => entry.CanAppearOnBranchPath = t); + DevDebugManager.Instance.CreateBoolInputField(parentTransform, "Is Required", entry.IsRequired, (t) => entry.IsRequired = t); + } + } + + internal class ListEntryGraphNode : ListEntryType { + + public override object CreateEmptyObject() => new GraphNode(DevDebugManager.Instance.selectedDungeonFlow); + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset){ + var entry = (GraphNode)list[index]; + DevDebugManager.Instance.CreateListUIField(parentTransform, "Tile Sets", entry.TileSets); + DevDebugManager.Instance.CreateEnumOptionsUIField(parentTransform, "Node Type", (int)entry.NodeType, (t) => entry.NodeType = t); + DevDebugManager.Instance.CreateFloatInputField(parentTransform, "Position", new FloatParameter(entry.Position, 0f, 1f), (t) => entry.Position = t); + DevDebugManager.Instance.CreateStringInputField(parentTransform, "Label", entry.Label, (t) => entry.Label = t); + } + } + + internal class ListEntryGraphLine : ListEntryType { + + public override object CreateEmptyObject() => new GraphLine(DevDebugManager.Instance.selectedDungeonFlow); + + public override void CreateEntry(IList list, int index, Transform parentTransform, float layoutOffset){ + var entry = (GraphLine)list[index]; + DevDebugManager.Instance.CreateListUIField(parentTransform, "Dungeon Archetypes", entry.DungeonArchetypes); + DevDebugManager.Instance.CreateFloatInputField(parentTransform, "Position", new FloatParameter(entry.Position, 0f, 1f), (t) => entry.Position = t); + DevDebugManager.Instance.CreateFloatInputField(parentTransform, "Length", new FloatParameter(entry.Length, 0f, 1f), (t) => entry.Length = t); + } + } + +} diff --git a/DunGenPlus/DunGenPlus/DevTools/UIElements/DropdownInputField.cs b/DunGenPlus/DunGenPlus/DevTools/UIElements/DropdownInputField.cs index 3583426..a132fe1 100644 --- a/DunGenPlus/DunGenPlus/DevTools/UIElements/DropdownInputField.cs +++ b/DunGenPlus/DunGenPlus/DevTools/UIElements/DropdownInputField.cs @@ -5,6 +5,7 @@ using System.Linq; using System.Text; using System.Threading.Tasks; using TMPro; +using UnityEngine; using UnityEngine.UI; namespace DunGenPlus.DevTools.UIElements @@ -16,8 +17,9 @@ namespace DunGenPlus.DevTools.UIElements public void SetupDropdown(TitleParameter titleParameter, int baseValue, Action setAction, Func convertIndex, IEnumerable options) { SetupBase(titleParameter); + var maxLength = (int)Mathf.LerpUnclamped(24f, 20f, layoutOffset / 24f); dropDown.options = options.Select(c => { - return new TMP_Dropdown.OptionData(c.Substring(0, Math.Min(24, c.Length))); + return new TMP_Dropdown.OptionData(c.Substring(0, Math.Min(maxLength, c.Length))); }).ToList(); dropDown.onValueChanged.AddListener((t) => SetValue(setAction, convertIndex, t)); diff --git a/DunGenPlus/DunGenPlus/DevTools/UIElements/FloatRangeInputField.cs b/DunGenPlus/DunGenPlus/DevTools/UIElements/FloatRangeInputField.cs new file mode 100644 index 0000000..1123390 --- /dev/null +++ b/DunGenPlus/DunGenPlus/DevTools/UIElements/FloatRangeInputField.cs @@ -0,0 +1,45 @@ +using DunGen; +using DunGenPlus.DevTools.UIElements.Collections; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using TMPro; + +namespace DunGenPlus.DevTools.UIElements +{ + internal class FloatRangeInputField : BaseInputField { + + public TMP_InputField minInputField; + public TMP_InputField maxInputField; + private FloatRange _value; + + public void SetupInputField(TitleParameter titleParameter, FloatRange baseValue, Action setAction) { + SetupBase(titleParameter); + + minInputField.onValueChanged.AddListener((t) => SetMinValue(setAction, t)); + maxInputField.onValueChanged.AddListener((t) => SetMaxValue(setAction, t)); + + Set(baseValue); + } + + private void SetMinValue(Action setAction, string text){ + Plugin.logger.LogInfo($"Setting {title}.min to {text}"); + _value.Min = ParseTextFloat(text); + setAction.Invoke(_value); + } + + private void SetMaxValue(Action setAction, string text){ + Plugin.logger.LogInfo($"Setting {title}.max to {text}"); + _value.Max = ParseTextFloat(text); + setAction.Invoke(_value); + } + + public override void Set(FloatRange value){ + _value = value; + minInputField.text = value.Min.ToString(); + maxInputField.text = value.Max.ToString(); + } + } +} diff --git a/DunGenPlus/DunGenPlus/DevTools/UIElements/IntRangeInputField.cs b/DunGenPlus/DunGenPlus/DevTools/UIElements/IntRangeInputField.cs new file mode 100644 index 0000000..42c43b1 --- /dev/null +++ b/DunGenPlus/DunGenPlus/DevTools/UIElements/IntRangeInputField.cs @@ -0,0 +1,47 @@ +using DunGen; +using DunGenPlus.DevTools.UIElements.Collections; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using TMPro; +using UnityEngine; +using UnityEngine.Rendering; + +namespace DunGenPlus.DevTools.UIElements +{ + internal class IntRangeInputField : BaseInputField { + + public TMP_InputField minInputField; + public TMP_InputField maxInputField; + private IntRange _value; + + public void SetupInputField(TitleParameter titleParameter, IntRange baseValue, Action setAction) { + SetupBase(titleParameter); + + minInputField.onValueChanged.AddListener((t) => SetMinValue(setAction, t)); + maxInputField.onValueChanged.AddListener((t) => SetMaxValue(setAction, t)); + + Set(baseValue); + } + + private void SetMinValue(Action setAction, string text){ + Plugin.logger.LogInfo($"Setting {title}.min to {text}"); + _value.Min = ParseTextInt(text); + setAction.Invoke(_value); + } + + private void SetMaxValue(Action setAction, string text){ + Plugin.logger.LogInfo($"Setting {title}.max to {text}"); + _value.Max = ParseTextInt(text); + setAction.Invoke(_value); + } + + public override void Set(IntRange value){ + _value = value; + minInputField.text = value.Min.ToString(); + maxInputField.text = value.Max.ToString(); + } + } +} diff --git a/DunGenPlus/DunGenPlus/DevTools/UIElements/ListUIElement.cs b/DunGenPlus/DunGenPlus/DevTools/UIElements/ListUIElement.cs index d28e6f0..81dfdb7 100644 --- a/DunGenPlus/DunGenPlus/DevTools/UIElements/ListUIElement.cs +++ b/DunGenPlus/DunGenPlus/DevTools/UIElements/ListUIElement.cs @@ -1,4 +1,5 @@ using DunGen; +using DunGen.Graph; using DunGenPlus.Collections; using DunGenPlus.DevTools.Panels; using DunGenPlus.DevTools.UIElements.Collections; @@ -22,6 +23,16 @@ namespace DunGenPlus.DevTools.UIElements { internal IList list; internal Type listType; + public static readonly Dictionary typeDictionary = new Dictionary() { + { typeof(DungeonArchetype), new ListEntryDungeonArchetype() }, + { typeof(TileSet), new ListEntryTileSet() }, + { typeof(NodeArchetype), new ListEntryNodeArchetype() }, + { typeof(ForcedTileSetList), new ListEntryForcedTileSetList() }, + { typeof(TileInjectionRule), new ListEntryTileInjectionRule() }, + { typeof(GraphNode), new ListEntryGraphNode() }, + { typeof(GraphLine), new ListEntryGraphLine() } + }; + public void SetupList(TitleParameter titleParameter, List list) { SetupBase(titleParameter); @@ -37,16 +48,10 @@ namespace DunGenPlus.DevTools.UIElements { public void AddElement() { object item = null; - if (listType == typeof(DungeonArchetype) || listType == typeof(TileSet)) { - item = null; - } else if (listType == typeof(NodeArchetype)) { - item = new NodeArchetype(); - } else if (listType == typeof(ForcedTileSetList)){ - var forcedTileset = new ForcedTileSetList(); - forcedTileset.DepthWeightScale = null; - item = forcedTileset; + if (!typeDictionary.TryGetValue(listType, out var value)){ + Plugin.logger.LogError($"Type {listType} does not has a defined list UI display"); } - + item = value.CreateEmptyObject(); list.Add(item); CreateEntry(list.Count - 1); } @@ -61,34 +66,10 @@ namespace DunGenPlus.DevTools.UIElements { var copy = CreateCopy(index); var copyParentTransform = copy.transform.Find("Items"); - if (listType == typeof(DungeonArchetype)){ - var entry = (DungeonArchetype)list[index]; - var baseValue = DunGenPlusPanel.Instance.selectedAssetCache.archetypes.dictionary[entry]; - DevDebugManager.Instance.CreateArchetypeOptionsUIField(copyParentTransform, new TitleParameter("Archetype", layoutOffset + 24f), baseValue, (t) => list[index] = t); + if (!typeDictionary.TryGetValue(listType, out var value)){ + Plugin.logger.LogError($"Type {listType} does not has a defined list UI display"); } - - else if (listType == typeof(TileSet)){ - var entry = (TileSet)list[index]; - var baseValue = DunGenPlusPanel.Instance.selectedAssetCache.tileSets.dictionary[entry]; - DevDebugManager.Instance.CreateTileSetsOptionsUIField(copyParentTransform, new TitleParameter("Tile Set", layoutOffset + 24f), baseValue, (t) => list[index] = t); - } - - else if (listType == typeof(NodeArchetype)) { - var entry = (NodeArchetype)list[index]; - DevDebugManager.Instance.CreateStringInputField(copyParentTransform, new TitleParameter("Label", layoutOffset + 24f), entry.label, (t) => entry.label = t); - DevDebugManager.Instance.CreateListUIField(copyParentTransform, new TitleParameter("Archetypes", layoutOffset + 24f), entry.archetypes); - } - - else if (listType == typeof(ForcedTileSetList)) { - var entry = (ForcedTileSetList)list[index]; - DevDebugManager.Instance.CreateFloatInputField(copyParentTransform, new TitleParameter("Main Path Weight", layoutOffset + 24f), entry.MainPathWeight, (t) => entry.MainPathWeight = t); - DevDebugManager.Instance.CreateFloatInputField(copyParentTransform, new TitleParameter("Branch Path Weight", layoutOffset + 24f), entry.BranchPathWeight, (t) => entry.BranchPathWeight = t); - - // depth is weird cause we have to account for every entry's unique depth curve, even if they don't have one - DevDebugManager.Instance.CreateAnimationCurveOptionsUIField(copyParentTransform, new TitleParameter("Depth Weight Scale", layoutOffset + 24f), entry.DepthWeightScale, (t) => entry.DepthWeightScale = t); - DevDebugManager.Instance.CreateListUIField(copyParentTransform, new TitleParameter("Tile Sets", layoutOffset + 24f), entry.Tilesets); - } - + value.CreateEntry(list, index, copyParentTransform, layoutOffset + 24f); copy.SetActive(true); } diff --git a/DunGenPlus/DunGenPlus/DevTools/UIElements/Vector3InputField.cs b/DunGenPlus/DunGenPlus/DevTools/UIElements/Vector3InputField.cs index b520327..c57414a 100644 --- a/DunGenPlus/DunGenPlus/DevTools/UIElements/Vector3InputField.cs +++ b/DunGenPlus/DunGenPlus/DevTools/UIElements/Vector3InputField.cs @@ -52,7 +52,5 @@ namespace DunGenPlus.DevTools.UIElements { yInputField.text = value.y.ToString(); zInputField.text = value.z.ToString(); } - - } } diff --git a/DunGenPlus/DunGenPlus/DunGenPlus.csproj b/DunGenPlus/DunGenPlus/DunGenPlus.csproj index 4c35e79..604af37 100644 --- a/DunGenPlus/DunGenPlus/DunGenPlus.csproj +++ b/DunGenPlus/DunGenPlus/DunGenPlus.csproj @@ -151,15 +151,19 @@ + + + + diff --git a/DunGenPlus/DunGenPlus/Generation/DunGenPlusGeneratorBranchLoop.cs b/DunGenPlus/DunGenPlus/Generation/DunGenPlusGeneratorBranchLoop.cs index 8a170a0..b1f4aa7 100644 --- a/DunGenPlus/DunGenPlus/Generation/DunGenPlusGeneratorBranchLoop.cs +++ b/DunGenPlus/DunGenPlus/Generation/DunGenPlusGeneratorBranchLoop.cs @@ -1,4 +1,5 @@ using DunGen; +using DunGenPlus.Collections; using System; using System.Collections; using System.Collections.Generic; @@ -47,21 +48,12 @@ namespace DunGenPlus.Generation var count = list.Count; if (count == 0) return; - var lengthWeightScale = Properties.BranchPathMultiSimulationProperties.LengthWeightScale; - var normalizedWeightScale = Properties.BranchPathMultiSimulationProperties.NormalizedLengthWeightScale; - - var samePathWeightScale = Properties.BranchPathMultiSimulationProperties.SamePathBaseWeightScale; - var diffPathWeightScale = Properties.BranchPathMultiSimulationProperties.DiffPathBaseWeightScale; - - var samePathDepthWeightScale = Properties.BranchPathMultiSimulationProperties.SamePathDepthWeightScale; - var diffPathDepthWeightScale = Properties.BranchPathMultiSimulationProperties.DiffPathDepthWeightScale; - - var samePathNormalizedDepthWeightScale = Properties.BranchPathMultiSimulationProperties.SamePathNormalizedDepthWeightScale; - var diffPathNormalizedDepthWeightScale = Properties.BranchPathMultiSimulationProperties.DiffPathNormalizedDepthWeightScale; - var lastNode = list[count - 1]; - weight += lastNode.tileProxy.Placement.BranchDepth * lengthWeightScale; - weight += lastNode.tileProxy.Placement.NormalizedBranchDepth * normalizedWeightScale; + var simProp = Properties.BranchPathMultiSimulationProperties; + var depth = lastNode.tileProxy.Placement.BranchDepth; + var normalizedDepth = lastNode.tileProxy.Placement.NormalizedBranchDepth; + + weight += simProp.GetWeightBase(depth, normalizedDepth); var allDungeonDoorways = gen.proxyDungeon.AllTiles.SelectMany(t => t.Doorways); foreach(var t in list) { foreach(var d in allDungeonDoorways) { @@ -77,9 +69,7 @@ namespace DunGenPlus.Generation var normalDiff = Mathf.Abs(d.TileProxy.Placement.NormalizedPathDepth - l.TileProxy.Placement.NormalizedPathDepth); var samePath = mainPathIndex == dIndex; - weight += samePath ? samePathWeightScale : diffPathWeightScale; - weight += diff * (samePath ? samePathDepthWeightScale : diffPathDepthWeightScale); - weight += normalDiff * (samePath ? samePathNormalizedDepthWeightScale : diffPathNormalizedDepthWeightScale); + weight += simProp.GetWeightPathConnection(samePath, diff, normalDiff); } } } diff --git a/DunGenPlus/DunGenPlus/dungen b/DunGenPlus/DunGenPlus/dungen index cadddbb..8762463 100644 Binary files a/DunGenPlus/DunGenPlus/dungen and b/DunGenPlus/DunGenPlus/dungen differ