[Tools] Add a simple quest preview window for Puzzle Step SO
This commit is contained in:
@@ -14,7 +14,7 @@ MonoBehaviour:
|
||||
m_EditorClassIdentifier:
|
||||
stepId: ass1
|
||||
displayName: Pickup Ass 1
|
||||
description:
|
||||
description: Some description of the quest
|
||||
icon: {fileID: 0}
|
||||
unlocks:
|
||||
- {fileID: 11400000, guid: 9de0c57af6191384e96e2ba7c04a3d0d, type: 2}
|
||||
|
||||
@@ -14,7 +14,7 @@ MonoBehaviour:
|
||||
m_EditorClassIdentifier:
|
||||
stepId: ass2
|
||||
displayName: Pickup Ass 2
|
||||
description:
|
||||
description: Some other description of the quest
|
||||
icon: {fileID: 0}
|
||||
unlocks:
|
||||
- {fileID: 11400000, guid: 13b0c411066f85a41ba40c3bbbc281ed, type: 2}
|
||||
|
||||
@@ -14,7 +14,7 @@ MonoBehaviour:
|
||||
m_EditorClassIdentifier:
|
||||
stepId: ass3
|
||||
displayName: Pickup Ass 3
|
||||
description:
|
||||
description: Designers were too lazy to write this one
|
||||
icon: {fileID: 0}
|
||||
unlocks:
|
||||
- {fileID: 11400000, guid: 9de0c57af6191384e96e2ba7c04a3d0d, type: 2}
|
||||
|
||||
@@ -14,10 +14,6 @@ MonoBehaviour:
|
||||
m_EditorClassIdentifier:
|
||||
stepId: head
|
||||
displayName: Pickup Head
|
||||
description:
|
||||
description: Skeet
|
||||
icon: {fileID: 0}
|
||||
dependencies:
|
||||
- {fileID: 11400000, guid: 0b13ff4f31443b74281b13e0eef865c2, type: 2}
|
||||
- {fileID: 11400000, guid: a84cbe9804e13f74e857c55d90cc10d1, type: 2}
|
||||
- {fileID: 11400000, guid: 13b0c411066f85a41ba40c3bbbc281ed, type: 2}
|
||||
unlocks: []
|
||||
|
||||
88
Assets/Editor/PuzzleChainEditorWindow.cs
Normal file
88
Assets/Editor/PuzzleChainEditorWindow.cs
Normal file
@@ -0,0 +1,88 @@
|
||||
using UnityEditor;
|
||||
using UnityEngine;
|
||||
using System.Collections.Generic;
|
||||
|
||||
public class PuzzleChainEditorWindow : EditorWindow
|
||||
{
|
||||
private List<PuzzleStepSO> puzzleSteps = new List<PuzzleStepSO>();
|
||||
private Dictionary<PuzzleStepSO, List<PuzzleStepSO>> dependencyGraph;
|
||||
private Vector2 scrollPos;
|
||||
private const int INDENT_SIZE = 24;
|
||||
|
||||
[MenuItem("Tools/Puzzle Chain Editor")]
|
||||
public static void ShowWindow()
|
||||
{
|
||||
var window = GetWindow<PuzzleChainEditorWindow>("Puzzle Chain Editor");
|
||||
window.minSize = new Vector2(600, 400);
|
||||
window.maxSize = new Vector2(1200, 800);
|
||||
window.position = new Rect(100, 100, 700, 500); // Reasonable default size and position
|
||||
}
|
||||
|
||||
private void OnEnable()
|
||||
{
|
||||
LoadPuzzleSteps();
|
||||
ProcessPuzzleChains();
|
||||
}
|
||||
|
||||
private void LoadPuzzleSteps()
|
||||
{
|
||||
puzzleSteps.Clear();
|
||||
string[] guids = AssetDatabase.FindAssets("t:PuzzleStepSO", new[] { "Assets/Data/Puzzles" });
|
||||
foreach (var guid in guids)
|
||||
{
|
||||
var path = AssetDatabase.GUIDToAssetPath(guid);
|
||||
var step = AssetDatabase.LoadAssetAtPath<PuzzleStepSO>(path);
|
||||
if (step != null)
|
||||
puzzleSteps.Add(step);
|
||||
}
|
||||
}
|
||||
|
||||
private void ProcessPuzzleChains()
|
||||
{
|
||||
dependencyGraph = PuzzleGraphUtility.BuildDependencyGraph(puzzleSteps);
|
||||
}
|
||||
|
||||
private void OnGUI()
|
||||
{
|
||||
EditorGUILayout.LabelField("Puzzle Chain Visualization", EditorStyles.boldLabel);
|
||||
if (puzzleSteps.Count == 0)
|
||||
{
|
||||
EditorGUILayout.HelpBox("No PuzzleStepSO assets found in Assets/Data/Puzzles.", MessageType.Warning);
|
||||
return;
|
||||
}
|
||||
scrollPos = EditorGUILayout.BeginScrollView(scrollPos);
|
||||
var initialSteps = PuzzleGraphUtility.FindInitialSteps(dependencyGraph);
|
||||
foreach (var step in initialSteps)
|
||||
{
|
||||
EditorGUILayout.BeginVertical("box");
|
||||
EditorGUILayout.LabelField($"Step Path: {step.displayName} ({step.stepId})", EditorStyles.largeLabel);
|
||||
GUILayout.Space(6);
|
||||
DrawStepTree(step, 0);
|
||||
EditorGUILayout.EndVertical();
|
||||
GUILayout.Space(12); // Space between step paths
|
||||
}
|
||||
EditorGUILayout.EndScrollView();
|
||||
}
|
||||
|
||||
private void DrawStepTree(PuzzleStepSO step, int indent)
|
||||
{
|
||||
EditorGUILayout.BeginHorizontal();
|
||||
GUILayout.Space(indent * INDENT_SIZE);
|
||||
EditorGUILayout.BeginVertical("box");
|
||||
EditorGUILayout.LabelField($"{step.displayName} ({step.stepId})", EditorStyles.boldLabel);
|
||||
EditorGUILayout.LabelField(step.description ?? "", EditorStyles.wordWrappedLabel);
|
||||
GUILayout.Space(4);
|
||||
if (GUILayout.Button("Open in Inspector", GUILayout.Width(150)))
|
||||
{
|
||||
Selection.activeObject = step; // Opens in Inspector
|
||||
EditorGUIUtility.PingObject(step); // Highlights in Project
|
||||
}
|
||||
EditorGUILayout.EndVertical();
|
||||
EditorGUILayout.EndHorizontal();
|
||||
GUILayout.Space(6); // Spacer between steps
|
||||
foreach (var unlock in step.unlocks)
|
||||
{
|
||||
DrawStepTree(unlock, indent + 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
3
Assets/Editor/PuzzleChainEditorWindow.cs.meta
Normal file
3
Assets/Editor/PuzzleChainEditorWindow.cs.meta
Normal file
@@ -0,0 +1,3 @@
|
||||
fileFormatVersion: 2
|
||||
guid: f7bfaa69d42e45adaa4a44dd143efc2f
|
||||
timeCreated: 1756991142
|
||||
3
Assets/Scripts/Editor.meta
Normal file
3
Assets/Scripts/Editor.meta
Normal file
@@ -0,0 +1,3 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 7c8178e4dbe545d691ce5f513299adcb
|
||||
timeCreated: 1756991127
|
||||
50
Assets/Scripts/PuzzleGraphUtility.cs
Normal file
50
Assets/Scripts/PuzzleGraphUtility.cs
Normal file
@@ -0,0 +1,50 @@
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
|
||||
public static class PuzzleGraphUtility
|
||||
{
|
||||
// Builds a dependency graph: for each step, lists the steps it depends on
|
||||
public static Dictionary<PuzzleStepSO, List<PuzzleStepSO>> BuildDependencyGraph(IEnumerable<PuzzleStepSO> steps)
|
||||
{
|
||||
var graph = new Dictionary<PuzzleStepSO, List<PuzzleStepSO>>();
|
||||
foreach (var step in steps)
|
||||
{
|
||||
graph[step] = new List<PuzzleStepSO>();
|
||||
}
|
||||
foreach (var step in steps)
|
||||
{
|
||||
foreach (var unlocked in step.unlocks)
|
||||
{
|
||||
if (!graph.ContainsKey(unlocked))
|
||||
graph[unlocked] = new List<PuzzleStepSO>();
|
||||
graph[unlocked].Add(step);
|
||||
}
|
||||
}
|
||||
return graph;
|
||||
}
|
||||
|
||||
// Finds initial steps (no dependencies)
|
||||
public static List<PuzzleStepSO> FindInitialSteps(Dictionary<PuzzleStepSO, List<PuzzleStepSO>> graph)
|
||||
{
|
||||
var initial = new List<PuzzleStepSO>();
|
||||
foreach (var kvp in graph)
|
||||
{
|
||||
if (kvp.Value.Count == 0)
|
||||
initial.Add(kvp.Key);
|
||||
}
|
||||
return initial;
|
||||
}
|
||||
|
||||
// Finds all steps unlocked by a given step
|
||||
public static List<PuzzleStepSO> FindUnlocks(PuzzleStepSO step, IEnumerable<PuzzleStepSO> allSteps)
|
||||
{
|
||||
var unlocks = new List<PuzzleStepSO>();
|
||||
foreach (var s in allSteps)
|
||||
{
|
||||
if (s.unlocks.Contains(step))
|
||||
unlocks.Add(s);
|
||||
}
|
||||
return unlocks;
|
||||
}
|
||||
}
|
||||
|
||||
3
Assets/Scripts/PuzzleGraphUtility.cs.meta
Normal file
3
Assets/Scripts/PuzzleGraphUtility.cs.meta
Normal file
@@ -0,0 +1,3 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 9f484cf99777457a8bc38430a0d67416
|
||||
timeCreated: 1756991444
|
||||
@@ -1,5 +1,6 @@
|
||||
using UnityEngine;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
public class PuzzleManager : MonoBehaviour
|
||||
{
|
||||
@@ -62,19 +63,12 @@ public class PuzzleManager : MonoBehaviour
|
||||
|
||||
private void BuildRuntimeDependencies()
|
||||
{
|
||||
runtimeDependencies.Clear();
|
||||
foreach (var step in stepBehaviours.Keys)
|
||||
runtimeDependencies = PuzzleGraphUtility.BuildDependencyGraph(stepBehaviours.Keys);
|
||||
foreach (var step in runtimeDependencies.Keys)
|
||||
{
|
||||
runtimeDependencies[step] = new List<PuzzleStepSO>();
|
||||
}
|
||||
foreach (var step in stepBehaviours.Keys)
|
||||
{
|
||||
foreach (var unlocked in step.unlocks)
|
||||
foreach (var dep in runtimeDependencies[step])
|
||||
{
|
||||
if (!runtimeDependencies.ContainsKey(unlocked))
|
||||
runtimeDependencies[unlocked] = new List<PuzzleStepSO>();
|
||||
runtimeDependencies[unlocked].Add(step);
|
||||
Debug.Log($"[Puzzles] Step {unlocked.stepId} depends on {step.stepId}");
|
||||
Debug.Log($"[Puzzles] Step {step.stepId} depends on {dep.stepId}");
|
||||
}
|
||||
}
|
||||
Debug.Log($"[Puzzles] Runtime dependencies built. Total steps: {stepBehaviours.Count}");
|
||||
@@ -82,13 +76,11 @@ public class PuzzleManager : MonoBehaviour
|
||||
|
||||
private void UnlockInitialSteps()
|
||||
{
|
||||
foreach (var step in stepBehaviours.Keys)
|
||||
var initialSteps = PuzzleGraphUtility.FindInitialSteps(runtimeDependencies);
|
||||
foreach (var step in initialSteps)
|
||||
{
|
||||
if (runtimeDependencies[step].Count == 0)
|
||||
{
|
||||
Debug.Log($"[Puzzles] Initial step unlocked: {step.stepId}");
|
||||
UnlockStep(step);
|
||||
}
|
||||
Debug.Log($"[Puzzles] Initial step unlocked: {step.stepId}");
|
||||
UnlockStep(step);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user