Rework of base interactables and managed behaviors

This commit is contained in:
Michal Pikulski
2025-11-04 11:11:27 +01:00
parent 0dc3f3e803
commit c57e3aa7e0
62 changed files with 11193 additions and 1376 deletions

View File

@@ -5,8 +5,8 @@ using System.Linq;
using UnityEngine;
using UnityEngine.SceneManagement;
using AppleHills.Core.Settings;
using Bootstrap;
using Core;
using Core.Lifecycle;
using Core.SaveLoad;
using UnityEngine.AddressableAssets;
using UnityEngine.ResourceManagement.AsyncOperations;
@@ -28,7 +28,7 @@ namespace PuzzleS
/// <summary>
/// Manages puzzle step registration, dependency management, and step completion for the puzzle system.
/// </summary>
public class PuzzleManager : MonoBehaviour, ISaveParticipant
public class PuzzleManager : ManagedBehaviour, ISaveParticipant
{
private static PuzzleManager _instance;
@@ -81,29 +81,20 @@ namespace PuzzleS
/// </summary>
public bool HasBeenRestored => _hasBeenRestored;
void Awake()
public override int ManagedAwakePriority => 80; // Puzzle systems
private new void Awake()
{
base.Awake(); // CRITICAL: Register with LifecycleManager!
// Set instance immediately so it's available before OnManagedAwake() is called
_instance = this;
// Initialize settings reference
_interactionSettings = GameManager.GetSettingsObject<IInteractionSettings>();
// Register for post-boot initialization
BootCompletionService.RegisterInitAction(InitializePostBoot);
}
private void InitializePostBoot()
protected override void OnManagedAwake()
{
// Subscribe to SceneManagerService events after boot is complete
SceneManagerService.Instance.SceneLoadCompleted += OnSceneLoadCompleted;
SceneManagerService.Instance.SceneLoadStarted += OnSceneLoadStarted;
// Register with save/load system
BootCompletionService.RegisterInitAction(() =>
{
SaveLoadManager.Instance.RegisterParticipant(this);
Logging.Debug("[PuzzleManager] Registered with SaveLoadManager");
});
// Initialize settings reference
_interactionSettings = GameManager.GetSettingsObject<IInteractionSettings>();
// Find player transform
_playerTransform = GameObject.FindGameObjectWithTag("Player")?.transform;
@@ -117,46 +108,44 @@ namespace PuzzleS
LoadPuzzleDataForCurrentScene();
}
Logging.Debug("[PuzzleManager] Subscribed to SceneManagerService events");
// Register with save/load system
SaveLoadManager.Instance.RegisterParticipant(this);
Logging.Debug("[PuzzleManager] Registered with SaveLoadManager");
// Subscribe to scene load events from SceneManagerService
// This is necessary because PuzzleManager is in DontDestroyOnLoad and won't receive OnSceneReady() callbacks
if (SceneManagerService.Instance != null)
{
SceneManagerService.Instance.SceneLoadCompleted += OnSceneLoadCompleted;
}
Logging.Debug("[PuzzleManager] Initialized");
}
void OnDestroy()
/// <summary>
/// Called when any scene finishes loading. Loads puzzles for the new scene.
/// </summary>
private void OnSceneLoadCompleted(string sceneName)
{
StopProximityChecks();
Logging.Debug($"[Puzzles] Scene loaded: {sceneName}, loading puzzle data");
LoadPuzzlesForScene(sceneName);
}
protected override void OnDestroy()
{
base.OnDestroy();
// Unsubscribe from scene manager events
// Unsubscribe from SceneManagerService events
if (SceneManagerService.Instance != null)
{
SceneManagerService.Instance.SceneLoadCompleted -= OnSceneLoadCompleted;
SceneManagerService.Instance.SceneLoadStarted -= OnSceneLoadStarted;
}
// Unregister from save/load system
SaveLoadManager.Instance.UnregisterParticipant(GetSaveId());
Logging.Debug("[PuzzleManager] Unregistered from SaveLoadManager");
// Release addressable handle if needed
if (_levelDataLoadOperation.IsValid())
{
Addressables.Release(_levelDataLoadOperation);
}
}
/// <summary>
/// Called when a scene is starting to load
/// Loads puzzle data for the specified scene
/// </summary>
public void OnSceneLoadStarted(string sceneName)
{
// Reset data loaded state when changing scenes to avoid using stale data
_isDataLoaded = false;
Logging.Debug($"[Puzzles] Scene load started: {sceneName}, marked puzzle data as not loaded");
}
/// <summary>
/// Called when a scene is loaded
/// </summary>
public void OnSceneLoadCompleted(string sceneName)
private void LoadPuzzlesForScene(string sceneName)
{
// Skip for non-gameplay scenes
if (sceneName == "BootstrapScene" || string.IsNullOrEmpty(sceneName))