From ab84c97675d72f9af998ea935f74941e6dbe21cb Mon Sep 17 00:00:00 2001 From: Michal Pikulski Date: Mon, 13 Oct 2025 09:22:18 +0200 Subject: [PATCH] Add skip functionality to Cinematics Manager --- Assets/Art/Sprites/UI/progress_circle.png | Bin 0 -> 11210 bytes .../Art/Sprites/UI/progress_circle.png.meta | 195 +++++++++++++++ .../Prefabs/Managers/CinematicsManager.prefab | 95 +++++++- Assets/Prefabs/UI/LoadingScreen.prefab | 225 ++++++++++++++++++ Assets/Prefabs/UI/LoadingScreen.prefab.meta | 7 + Assets/Scenes/MainMenu.unity | 2 +- .../Scripts/Cinematics/CinematicsManager.cs | 100 +++++++- Assets/Scripts/Cinematics/SkipCinematic.cs | 112 +++++++++ .../Scripts/Cinematics/SkipCinematic.cs.meta | 2 + Assets/Scripts/Core/QuickAccess.cs | 6 +- Assets/Scripts/Input/InputManager.cs | 31 ++- 11 files changed, 753 insertions(+), 22 deletions(-) create mode 100644 Assets/Art/Sprites/UI/progress_circle.png create mode 100644 Assets/Art/Sprites/UI/progress_circle.png.meta create mode 100644 Assets/Prefabs/UI/LoadingScreen.prefab create mode 100644 Assets/Prefabs/UI/LoadingScreen.prefab.meta create mode 100644 Assets/Scripts/Cinematics/SkipCinematic.cs create mode 100644 Assets/Scripts/Cinematics/SkipCinematic.cs.meta diff --git a/Assets/Art/Sprites/UI/progress_circle.png b/Assets/Art/Sprites/UI/progress_circle.png new file mode 100644 index 0000000000000000000000000000000000000000..b74eed1591a01dbbc0a28647787e1430f737da92 GIT binary patch literal 11210 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 SX+g0pq$sB*Tk*sq /// Handles loading, playing and unloading cinematics @@ -20,6 +18,10 @@ namespace CinematicsM private Image cinematicSprites; public PlayableAsset cinematicToPlay; + // Dictionary to track addressable handles by PlayableDirector + private Dictionary> _addressableHandles + = new Dictionary>(); + public static CinematicsManager Instance { get @@ -41,8 +43,24 @@ namespace CinematicsM private void OnEnable() { - + // Subscribe to application quit event to ensure cleanup + Application.quitting += OnApplicationQuit; } + + private void OnDisable() + { + // Unsubscribe from application quit event + Application.quitting -= OnApplicationQuit; + + // Clean up any remaining addressable handles when disabled + ReleaseAllHandles(); + } + + private void OnApplicationQuit() + { + ReleaseAllHandles(); + } + /// /// Plays a cinematic from an object reference and returns the PlayableDirector playing the timeline /// @@ -59,6 +77,9 @@ namespace CinematicsM { cinematicSprites.enabled = false; Debug.Log("Cinematic stopped!"); + + // Release the addressable handle associated with this director + ReleaseAddressableHandle(director); } /// @@ -66,18 +87,73 @@ namespace CinematicsM /// public PlayableDirector LoadAndPlayCinematic(string key) { + // Load the asset via addressables var handle = Addressables.LoadAssetAsync(key); var result = handle.WaitForCompletion(); + + // Store the handle for later release + _addressableHandles[playableDirector] = handle; + + Debug.Log($"[CinematicsManager] Loaded addressable cinematic: {key}"); + return PlayCinematic(result); } - // Update is called once per frame - void Update() - { - - } - private void Awake() + /// + /// Skips the currently playing cinematic if one is active + /// + public void SkipCurrentCinematic() { + if (playableDirector != null && playableDirector.state == PlayState.Playing) + { + Debug.Log("Skipping current cinematic"); + playableDirector.Stop(); + } + } + + /// + /// Checks if a cinematic is currently playing + /// + public bool IsCinematicPlaying() + { + return playableDirector != null && playableDirector.state == PlayState.Playing; + } + + /// + /// Releases the addressable handle associated with a specific PlayableDirector + /// + private void ReleaseAddressableHandle(PlayableDirector director) + { + if (_addressableHandles.TryGetValue(director, out var handle)) + { + Debug.Log($"[CinematicsManager] Releasing addressable handle for cinematic"); + Addressables.Release(handle); + _addressableHandles.Remove(director); + } + } + + /// + /// Releases all active addressable handles + /// + private void ReleaseAllHandles() + { + foreach (var handle in _addressableHandles.Values) + { + if (handle.IsValid()) + { + Addressables.Release(handle); + } + } + _addressableHandles.Clear(); + } + + private void Start() + { + if (!SceneManager.GetActiveScene().name.ToLower().Contains("mainmenu")) + { + return; + } + _instance = this; playableDirector = GetComponent(); cinematicSprites = GetComponentInChildren(true); diff --git a/Assets/Scripts/Cinematics/SkipCinematic.cs b/Assets/Scripts/Cinematics/SkipCinematic.cs new file mode 100644 index 00000000..d058cb3d --- /dev/null +++ b/Assets/Scripts/Cinematics/SkipCinematic.cs @@ -0,0 +1,112 @@ +using Input; +using UnityEngine; +using UnityEngine.UI; + +namespace Cinematics +{ + public class SkipCinematic : MonoBehaviour, ITouchInputConsumer + { + [Header("Configuration")] + [SerializeField] private float holdDuration = 2.0f; + [SerializeField] private Image radialProgressBar; + + private float _holdStartTime; + private bool _isHolding; + private bool _skipPerformed; + + void Start() + { + // Reset the progress bar + if (radialProgressBar != null) + { + radialProgressBar.fillAmount = 0f; + } + } + + void OnEnable() + { + // Register as override consumer when enabled + InputManager.Instance.RegisterOverrideConsumer(this); + } + + void OnDisable() + { + // Unregister when disabled + InputManager.Instance.UnregisterOverrideConsumer(this); + } + + void Update() + { + // Only process while cinematic is playing and we're holding + if (_isHolding && CinematicsManager.Instance.IsCinematicPlaying()) + { + float holdTime = Time.time - _holdStartTime; + float progress = Mathf.Clamp01(holdTime / holdDuration); + + // Update progress bar + if (radialProgressBar != null) + { + radialProgressBar.fillAmount = progress; + } + + // Check if we've held long enough to skip + if (progress >= 1.0f && !_skipPerformed) + { + _skipPerformed = true; + DoSkipCinematic(); + } + } + } + + private void DoSkipCinematic() + { + CinematicsManager.Instance.SkipCurrentCinematic(); + Debug.Log("Cinematic skipped via touch hold"); + + // Reset UI + if (radialProgressBar != null) + { + radialProgressBar.fillAmount = 0f; + } + + // Remember to clear up input override + InputManager.Instance.UnregisterOverrideConsumer(this); + } + + #region ITouchInputConsumer Implementation + public void OnTap(Vector2 position) + { + // Not using tap for skipping + } + + public void OnHoldStart(Vector2 position) + { + // Start tracking hold time + _isHolding = true; + _skipPerformed = false; + _holdStartTime = Time.time; + + Debug.Log("Starting cinematic skip gesture"); + } + + public void OnHoldMove(Vector2 position) + { + // Hold movement is tracked in Update method + } + + public void OnHoldEnd(Vector2 position) + { + // Reset state when hold ends + _isHolding = false; + + // Reset UI + if (radialProgressBar != null) + { + radialProgressBar.fillAmount = 0f; + } + + Debug.Log("Cinematic skip gesture canceled"); + } + #endregion + } +} diff --git a/Assets/Scripts/Cinematics/SkipCinematic.cs.meta b/Assets/Scripts/Cinematics/SkipCinematic.cs.meta new file mode 100644 index 00000000..f5235e06 --- /dev/null +++ b/Assets/Scripts/Cinematics/SkipCinematic.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: 5526348c1593f9b43987b0edcaccdd24 \ No newline at end of file diff --git a/Assets/Scripts/Core/QuickAccess.cs b/Assets/Scripts/Core/QuickAccess.cs index 17d43235..17fd16f1 100644 --- a/Assets/Scripts/Core/QuickAccess.cs +++ b/Assets/Scripts/Core/QuickAccess.cs @@ -1,12 +1,8 @@ using UnityEngine; -using Interactions; -using System.Collections.Generic; -using AppleHills.Core.Settings; using AppleHills.Data.CardSystem; -using CinematicsM; +using Cinematics; using Core; using Input; -using Minigames.DivingForPictures; using PuzzleS; namespace AppleHills.Core diff --git a/Assets/Scripts/Input/InputManager.cs b/Assets/Scripts/Input/InputManager.cs index bb8929ad..dbbd3c71 100644 --- a/Assets/Scripts/Input/InputManager.cs +++ b/Assets/Scripts/Input/InputManager.cs @@ -31,6 +31,9 @@ namespace Input // Override consumer stack - using a list to support multiple overrides that can be removed in LIFO order private readonly List _overrideConsumers = new List(); + // Track which consumer is handling the current hold operation + private ITouchInputConsumer _activeHoldConsumer; + public static InputManager Instance { get @@ -193,6 +196,18 @@ namespace Input Vector3 worldPos = Camera.main.ScreenToWorldPoint(screenPos); Vector2 worldPos2D = new Vector2(worldPos.x, worldPos.y); Debug.Log($"[InputManager] HoldMove started at {worldPos2D}"); + + // First check for override consumers + if (_overrideConsumers.Count > 0) + { + _activeHoldConsumer = _overrideConsumers[_overrideConsumers.Count - 1]; + Debug.Log($"[InputManager] Hold delegated to override consumer: {_activeHoldConsumer}"); + _activeHoldConsumer.OnHoldStart(worldPos2D); + return; + } + + // If no override consumers, use default consumer + _activeHoldConsumer = defaultConsumer; defaultConsumer?.OnHoldStart(worldPos2D); } @@ -207,7 +222,10 @@ namespace Input Vector3 worldPos = Camera.main.ScreenToWorldPoint(screenPos); Vector2 worldPos2D = new Vector2(worldPos.x, worldPos.y); Debug.Log($"[InputManager] HoldMove canceled at {worldPos2D}"); - defaultConsumer?.OnHoldEnd(worldPos2D); + + // Notify the active hold consumer that the hold has ended + _activeHoldConsumer?.OnHoldEnd(worldPos2D); + _activeHoldConsumer = null; } /// @@ -221,7 +239,9 @@ namespace Input Vector3 worldPos = Camera.main.ScreenToWorldPoint(screenPos); Vector2 worldPos2D = new Vector2(worldPos.x, worldPos.y); // Debug.Log($"[InputManager] HoldMove update at {worldPos2D}"); - defaultConsumer?.OnHoldMove(worldPos2D); + + // Send hold move updates to the active hold consumer + _activeHoldConsumer?.OnHoldMove(worldPos2D); } } @@ -342,6 +362,12 @@ namespace Input if (consumer == null || !_overrideConsumers.Contains(consumer)) return; + // If this is the active hold consumer, reset it + if (_activeHoldConsumer == consumer) + { + _activeHoldConsumer = null; + } + _overrideConsumers.Remove(consumer); Debug.Log($"[InputManager] Override consumer unregistered: {consumer}"); } @@ -351,6 +377,7 @@ namespace Input /// public void ClearOverrideConsumers() { + _activeHoldConsumer = null; _overrideConsumers.Clear(); Debug.Log("[InputManager] All override consumers cleared."); }