app.hypergames.hypersdk 1.11.0-beta.1 → 1.11.0-beta.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +72 -0
- package/Runtime/Internal/Core/HyperRuntime.cs +62 -5
- package/Runtime/Internal/Managers/DataManager.cs +2 -1
- package/Runtime/Internal/Managers/GameManager.cs +102 -52
- package/Runtime/Internal/Managers/ReplayManager.cs +7 -0
- package/Runtime/Internal/Managers/TimeManager.cs +57 -40
- package/Runtime/Internal/Replay/ReplaySessionState.cs +60 -3
- package/Runtime/Internal/UI/Components/ReplayController.cs +40 -10
- package/Runtime/Internal/UI/Modals/ReplayOverModal.cs +7 -0
- package/Runtime/Internal/UI/Modals/ReplayPausedModal.cs +145 -0
- package/Runtime/Internal/UI/Modals/ReplayPausedModal.cs.meta +2 -0
- package/Runtime/Internal/UI/Modals/StartingInstructionModal.cs +2 -1
- package/Runtime/Public/Core/HyperSDK.cs +16 -0
- package/Runtime/Public/Replay/ReplayPlaybackEngine.cs +56 -1
- package/Runtime/Resources/Fonts/Nunito/Nunito-Bold SDF.asset +500 -457
- package/Runtime/Resources/Sprites/Buttons/Hyper Long White Button_Normal.png +0 -0
- package/Runtime/Resources/Sprites/Buttons/Hyper Long White Button_Normal.png.meta +156 -0
- package/Runtime/Resources/Sprites/Buttons/Hyper Long White Button_Pressed.png +0 -0
- package/Runtime/Resources/Sprites/Buttons/Hyper Long White Button_Pressed.png.meta +156 -0
- package/Runtime/Resources/Sprites/Replays/Replay.png +0 -0
- package/Runtime/Resources/Sprites/Replays/{Recording.png.meta → Replay.png.meta} +9 -9
- package/Runtime/Resources/UIPrefabs/ControlBar.prefab +5 -5
- package/Runtime/Resources/UIPrefabs/ReplayController.prefab +302 -183
- package/Runtime/Resources/UIPrefabs/ReplayPausedModal.prefab +2194 -0
- package/Runtime/Resources/UIPrefabs/ReplayPausedModal.prefab.meta +7 -0
- package/Runtime/Shared/Replay/IReplayPlaybackEngine.cs +3 -0
- package/Samples~/LaneRunner/LaneRunnerSample.unity +4 -3
- package/Samples~/LaneRunner/Prefabs/DoubleScorePickup.prefab +1 -1
- package/Samples~/LaneRunner/Prefabs/Obstacle.prefab +1 -1
- package/Samples~/LaneRunner/README.md +8 -1
- package/Samples~/LaneRunner/Scripts/Gameplay/LaneRunnerPlayer.cs +18 -4
- package/Samples~/LaneRunner/Scripts/Gameplay/LaneRunnerSpawner.cs +3 -1
- package/Samples~/LaneRunner/Scripts/Hyper/LaneRunnerTournamentAdapter.cs +8 -0
- package/package.json +1 -1
- package/Runtime/Resources/Sprites/Replays/Recording.png +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,75 @@
|
|
|
1
|
+
# [1.11.0-beta.10](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.9...v1.11.0-beta.10) (2026-08-30)
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
### Bug Fixes
|
|
5
|
+
|
|
6
|
+
* **replay:** reduce default seek speed ([f70551a](https://github.com/mvmhyper/hyper-sdk/commit/f70551aea942274ace1cb952ddae4e9edb0c1c12))
|
|
7
|
+
|
|
8
|
+
# [1.11.0-beta.9](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.8...v1.11.0-beta.9) (2026-08-30)
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
### Bug Fixes
|
|
12
|
+
|
|
13
|
+
* **replay:** show loader while exiting paused replay ([4a2e7a6](https://github.com/mvmhyper/hyper-sdk/commit/4a2e7a6045017ea8ed3ae3525271440dbf013e6c))
|
|
14
|
+
|
|
15
|
+
# [1.11.0-beta.8](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.7...v1.11.0-beta.8) (2026-08-30)
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
### Bug Fixes
|
|
19
|
+
|
|
20
|
+
* **replay:** mute audio while seeking ([5ab8cd1](https://github.com/mvmhyper/hyper-sdk/commit/5ab8cd1411493cb5add07b51dc190c85251f99d2))
|
|
21
|
+
|
|
22
|
+
# [1.11.0-beta.7](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.6...v1.11.0-beta.7) (2026-08-30)
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
### Bug Fixes
|
|
26
|
+
|
|
27
|
+
* **replay:** stabilize scene reload seeking ([dd9ac63](https://github.com/mvmhyper/hyper-sdk/commit/dd9ac632d08349d9578f64ae0b2dc2ab905a26af))
|
|
28
|
+
|
|
29
|
+
# [1.11.0-beta.6](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.5...v1.11.0-beta.6) (2026-08-29)
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
### Bug Fixes
|
|
33
|
+
|
|
34
|
+
* **timer:** restore gameplay timers after pause ([ca82d57](https://github.com/mvmhyper/hyper-sdk/commit/ca82d57df87618807cbae611c0a9d6acc14f8470))
|
|
35
|
+
|
|
36
|
+
# [1.11.0-beta.5](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.4...v1.11.0-beta.5) (2026-08-28)
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
### Bug Fixes
|
|
40
|
+
|
|
41
|
+
* **replay:** wait for custom restart readiness ([43f1aeb](https://github.com/mvmhyper/hyper-sdk/commit/43f1aeb6a127c8c12dbb8379e7230d64ef5e0763))
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
### Features
|
|
45
|
+
|
|
46
|
+
* **replay:** add replay pause controls ([b9fb470](https://github.com/mvmhyper/hyper-sdk/commit/b9fb470e65c69e66a8a9611b0caa7e5417b1e4bf))
|
|
47
|
+
* **replay:** update replay control bar assets ([79ce8c0](https://github.com/mvmhyper/hyper-sdk/commit/79ce8c0f1b68129ae5b8bcf18a302117cf11c885))
|
|
48
|
+
|
|
49
|
+
# [1.11.0-beta.4](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.3...v1.11.0-beta.4) (2026-08-28)
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
### Bug Fixes
|
|
53
|
+
|
|
54
|
+
* **replay:** align recording with fixed simulation ([ae2b322](https://github.com/mvmhyper/hyper-sdk/commit/ae2b32216a0a9ea125572d788eee3bfd846414b0))
|
|
55
|
+
|
|
56
|
+
# [1.11.0-beta.3](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.2...v1.11.0-beta.3) (2026-08-28)
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
### Bug Fixes
|
|
60
|
+
|
|
61
|
+
* **replay:** reset random state before playback restart ([526a4d9](https://github.com/mvmhyper/hyper-sdk/commit/526a4d98c9b22241e3c52bb6837145bad999fb2b))
|
|
62
|
+
* **sample:** support lane runner custom restart ([49da385](https://github.com/mvmhyper/hyper-sdk/commit/49da385aaa917de438672a8630d4fe7927741b2a))
|
|
63
|
+
|
|
64
|
+
# [1.11.0-beta.2](https://github.com/mvmhyper/hyper-sdk/compare/v1.11.0-beta.1...v1.11.0-beta.2) (2026-08-27)
|
|
65
|
+
|
|
66
|
+
|
|
67
|
+
### Bug Fixes
|
|
68
|
+
|
|
69
|
+
* **replay:** respect custom restart flows ([7470a17](https://github.com/mvmhyper/hyper-sdk/commit/7470a17c60534465500a202c24b0e360f61850fc))
|
|
70
|
+
* **replay:** shorten automatic replay start ([d05dc92](https://github.com/mvmhyper/hyper-sdk/commit/d05dc9267fbf05d392135eac3bb7c4f69b786eff))
|
|
71
|
+
* **timer:** align game time with fixed simulation ([b690d86](https://github.com/mvmhyper/hyper-sdk/commit/b690d861e178f05b21f1a7fbd87e255d97008a8b))
|
|
72
|
+
|
|
1
73
|
# [1.11.0-beta.1](https://github.com/mvmhyper/hyper-sdk/compare/v1.10.0...v1.11.0-beta.1) (2026-08-26)
|
|
2
74
|
|
|
3
75
|
|
|
@@ -20,6 +20,8 @@ namespace Hyper.Internal
|
|
|
20
20
|
|
|
21
21
|
private static bool _isInitialized;
|
|
22
22
|
private static bool _isSoftRestarting;
|
|
23
|
+
private static bool _replayRandomResetPending;
|
|
24
|
+
private static bool _replayCustomRestartPending;
|
|
23
25
|
private static bool _customLoadingComplete;
|
|
24
26
|
private static bool _customLoadingActive;
|
|
25
27
|
private static float _customLoadingProgress;
|
|
@@ -32,6 +34,7 @@ namespace Hyper.Internal
|
|
|
32
34
|
private static EventManager _eventManager;
|
|
33
35
|
private static TimerManager _timerManager;
|
|
34
36
|
private static ReplayManager _replayManager;
|
|
37
|
+
private static double _fixedSimulationTimeSeconds;
|
|
35
38
|
|
|
36
39
|
internal static bool IsInitialized => _isInitialized;
|
|
37
40
|
internal static bool IsSoftRestarting
|
|
@@ -39,6 +42,7 @@ namespace Hyper.Internal
|
|
|
39
42
|
get => _isSoftRestarting;
|
|
40
43
|
set => _isSoftRestarting = value;
|
|
41
44
|
}
|
|
45
|
+
internal static bool IsReplayCustomRestartPending => _replayCustomRestartPending;
|
|
42
46
|
internal static bool CustomLoadingComplete
|
|
43
47
|
{
|
|
44
48
|
get => _customLoadingComplete;
|
|
@@ -58,6 +62,7 @@ namespace Hyper.Internal
|
|
|
58
62
|
internal static EventManager EventManager => _eventManager;
|
|
59
63
|
internal static TimerManager Timer => _timerManager;
|
|
60
64
|
internal static ReplayManager ReplayManager => _replayManager;
|
|
65
|
+
internal static double FixedSimulationTimeSeconds => _fixedSimulationTimeSeconds;
|
|
61
66
|
|
|
62
67
|
internal static event Action CustomLoadingStarted
|
|
63
68
|
{
|
|
@@ -118,13 +123,12 @@ namespace Hyper.Internal
|
|
|
118
123
|
}
|
|
119
124
|
|
|
120
125
|
/// <summary>
|
|
121
|
-
/// Restarts
|
|
122
|
-
/// Replay metadata, including the original seed value, remains available to the loader.
|
|
126
|
+
/// Restarts replay playback through HyperLoader while preserving replay session data.
|
|
123
127
|
/// </summary>
|
|
124
128
|
internal static void RestartReplaySession()
|
|
125
129
|
{
|
|
126
130
|
ReplaySessionState.ResetForWatchAgain();
|
|
127
|
-
|
|
131
|
+
RestartReplay();
|
|
128
132
|
}
|
|
129
133
|
|
|
130
134
|
internal static void SeekReplaySession(float targetProgress, float resumeSpeed, float seekSpeed)
|
|
@@ -133,14 +137,18 @@ namespace Hyper.Internal
|
|
|
133
137
|
|
|
134
138
|
ReplaySessionState.RequestSeek(targetProgress, resumeSpeed, seekSpeed);
|
|
135
139
|
ReplaySessionState.ResetForSeekRestart();
|
|
136
|
-
|
|
140
|
+
RestartReplay();
|
|
137
141
|
}
|
|
138
142
|
|
|
139
|
-
private static void
|
|
143
|
+
private static void RestartReplay()
|
|
140
144
|
{
|
|
141
145
|
_isSoftRestarting = true;
|
|
142
146
|
Time.timeScale = 1f;
|
|
143
147
|
|
|
148
|
+
_replayCustomRestartPending = false;
|
|
149
|
+
_replayRandomResetPending = false;
|
|
150
|
+
_replayManager?.PrepareForRestart();
|
|
151
|
+
|
|
144
152
|
if (_host != null)
|
|
145
153
|
{
|
|
146
154
|
_host.StartCoroutine(RestartSessionCoroutine());
|
|
@@ -152,6 +160,47 @@ namespace Hyper.Internal
|
|
|
152
160
|
}
|
|
153
161
|
}
|
|
154
162
|
|
|
163
|
+
internal static void ResetReplayRandomState()
|
|
164
|
+
{
|
|
165
|
+
int originalSeed = unchecked((int)ReplaySessionState.OriginalRandomSeed);
|
|
166
|
+
if (HyperRandom.CurrentSeed == originalSeed)
|
|
167
|
+
{
|
|
168
|
+
// Preserve references held by game code while rewinding every stream.
|
|
169
|
+
HyperRandom.ResetAll();
|
|
170
|
+
return;
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
HyperRandom.Init(ReplaySessionState.OriginalRandomSeed);
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
internal static void ApplyPendingReplayRandomReset()
|
|
177
|
+
{
|
|
178
|
+
if (!_replayRandomResetPending) return;
|
|
179
|
+
|
|
180
|
+
_replayRandomResetPending = false;
|
|
181
|
+
ResetReplayRandomState();
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
internal static void DeferReplayRandomReset()
|
|
185
|
+
{
|
|
186
|
+
_replayRandomResetPending = true;
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
internal static void CompleteCustomRestart()
|
|
190
|
+
{
|
|
191
|
+
if (!_replayCustomRestartPending || _host == null) return;
|
|
192
|
+
|
|
193
|
+
_replayCustomRestartPending = false;
|
|
194
|
+
_host.StartCoroutine(CompleteReplayCustomRestartNextFrame());
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
private static IEnumerator CompleteReplayCustomRestartNextFrame()
|
|
198
|
+
{
|
|
199
|
+
yield return null;
|
|
200
|
+
_gameManager?.CompleteReplayCustomRestart();
|
|
201
|
+
_isSoftRestarting = false;
|
|
202
|
+
}
|
|
203
|
+
|
|
155
204
|
/// <summary>
|
|
156
205
|
/// Coroutine-based restart that properly unloads all scenes before reloading.
|
|
157
206
|
/// Handles async scene operations and ensures clean state before restart.
|
|
@@ -160,6 +209,7 @@ namespace Hyper.Internal
|
|
|
160
209
|
{
|
|
161
210
|
yield return UnloadAllScenesCoroutine();
|
|
162
211
|
|
|
212
|
+
Clear();
|
|
163
213
|
ClearAllDontDestroyOnLoadObjects();
|
|
164
214
|
SceneManager.LoadScene("HyperLoader");
|
|
165
215
|
}
|
|
@@ -357,6 +407,7 @@ namespace Hyper.Internal
|
|
|
357
407
|
internal static void FixedTick()
|
|
358
408
|
{
|
|
359
409
|
if (!_isInitialized) return;
|
|
410
|
+
_fixedSimulationTimeSeconds += Time.fixedDeltaTime;
|
|
360
411
|
_replayManager?.FixedTick();
|
|
361
412
|
_timerManager?.FixedTick();
|
|
362
413
|
}
|
|
@@ -390,6 +441,9 @@ namespace Hyper.Internal
|
|
|
390
441
|
_customLoadingComplete = false;
|
|
391
442
|
_customLoadingActive = false;
|
|
392
443
|
_customLoadingProgress = 0f;
|
|
444
|
+
_replayRandomResetPending = false;
|
|
445
|
+
_replayCustomRestartPending = false;
|
|
446
|
+
_fixedSimulationTimeSeconds = 0d;
|
|
393
447
|
|
|
394
448
|
if (_singletonObject != null)
|
|
395
449
|
{
|
|
@@ -448,6 +502,9 @@ namespace Hyper.Internal
|
|
|
448
502
|
_customLoadingComplete = false;
|
|
449
503
|
_customLoadingActive = false;
|
|
450
504
|
_customLoadingProgress = 0f;
|
|
505
|
+
_replayRandomResetPending = false;
|
|
506
|
+
_replayCustomRestartPending = false;
|
|
507
|
+
_fixedSimulationTimeSeconds = 0d;
|
|
451
508
|
}
|
|
452
509
|
}
|
|
453
510
|
}
|
|
@@ -219,6 +219,7 @@ namespace Hyper.Internal.Managers
|
|
|
219
219
|
internal void ConfigurePlayerSoundSetting()
|
|
220
220
|
{
|
|
221
221
|
SetSound(GetSound());
|
|
222
|
+
ReplaySessionState.EnsureAudioMutedDuringSeek();
|
|
222
223
|
if (_gameManager == null) _gameManager = HyperRuntime.GameManager;
|
|
223
224
|
}
|
|
224
225
|
|
|
@@ -462,7 +463,7 @@ namespace Hyper.Internal.Managers
|
|
|
462
463
|
|
|
463
464
|
private static double GetSimulationTimeSeconds()
|
|
464
465
|
{
|
|
465
|
-
return
|
|
466
|
+
return HyperRuntime.FixedSimulationTimeSeconds;
|
|
466
467
|
}
|
|
467
468
|
|
|
468
469
|
private ScoreData GetPooledScoreData()
|
|
@@ -191,6 +191,41 @@ namespace Hyper.Internal.Managers
|
|
|
191
191
|
Resources.UnloadUnusedAssets();
|
|
192
192
|
}
|
|
193
193
|
|
|
194
|
+
internal void PauseReplay()
|
|
195
|
+
{
|
|
196
|
+
if (!IsReplayMode || !_hasGameStarted || _isPaused || _hasGameEnded)
|
|
197
|
+
{
|
|
198
|
+
return;
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
_isPaused = true;
|
|
202
|
+
_savedReplayTimeScale = Time.timeScale > 0f
|
|
203
|
+
? Time.timeScale
|
|
204
|
+
: ReplaySessionState.PlaybackSpeed;
|
|
205
|
+
Time.timeScale = 0f;
|
|
206
|
+
HyperRuntime.Timer.PauseGameplayTimers();
|
|
207
|
+
|
|
208
|
+
_previousTimeScale = 0f;
|
|
209
|
+
_eventManager.InvokeTimeScaleFrozenEvent();
|
|
210
|
+
ReplayPresentationCanvas.SetSeekingLayer(false);
|
|
211
|
+
SetBlockerActive(true);
|
|
212
|
+
ShowReplayPauseModal();
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
internal void ResumeReplay()
|
|
216
|
+
{
|
|
217
|
+
if (!IsReplayMode || !_isPaused || _hasGameEnded) return;
|
|
218
|
+
|
|
219
|
+
_isPaused = false;
|
|
220
|
+
HidePauseModals();
|
|
221
|
+
Time.timeScale = _savedReplayTimeScale > 0f ? _savedReplayTimeScale : 1f;
|
|
222
|
+
HyperRuntime.Timer.ResumeGameTimersAfterPause();
|
|
223
|
+
|
|
224
|
+
_previousTimeScale = Time.timeScale;
|
|
225
|
+
_eventManager.InvokeTimeScaleResumedEvent();
|
|
226
|
+
ReplayPresentationCanvas.SetSeekingLayer(ReplaySessionState.IsSeeking);
|
|
227
|
+
}
|
|
228
|
+
|
|
194
229
|
internal void ResumeGame()
|
|
195
230
|
{
|
|
196
231
|
_isPaused = false;
|
|
@@ -222,51 +257,7 @@ namespace Hyper.Internal.Managers
|
|
|
222
257
|
private void HandleReplayFocus(bool hasFocus)
|
|
223
258
|
{
|
|
224
259
|
if (!_hasGameStarted || _hasGameEnded) return;
|
|
225
|
-
|
|
226
|
-
if (!hasFocus && _replayFocusResumeCoroutine != null)
|
|
227
|
-
{
|
|
228
|
-
StopCoroutine(_replayFocusResumeCoroutine);
|
|
229
|
-
_replayFocusResumeCoroutine = null;
|
|
230
|
-
}
|
|
231
|
-
|
|
232
|
-
if (!hasFocus && !_replayFocusSuspended)
|
|
233
|
-
{
|
|
234
|
-
_replayFocusSuspended = true;
|
|
235
|
-
_savedReplayTimeScale = Time.timeScale;
|
|
236
|
-
Time.timeScale = 0f;
|
|
237
|
-
HyperRuntime.Timer.PauseGameplayTimers();
|
|
238
|
-
|
|
239
|
-
// WebGL may stop producing frames immediately after focus loss,
|
|
240
|
-
// so suspend replay timing here instead of waiting for Update.
|
|
241
|
-
_previousTimeScale = 0f;
|
|
242
|
-
_eventManager.InvokeTimeScaleFrozenEvent();
|
|
243
|
-
HyperDebug.Log("Time scale frozen event invoked");
|
|
244
|
-
}
|
|
245
|
-
else if (hasFocus && _replayFocusSuspended)
|
|
246
|
-
{
|
|
247
|
-
if (_replayFocusResumeCoroutine == null)
|
|
248
|
-
{
|
|
249
|
-
_replayFocusResumeCoroutine = StartCoroutine(ResumeReplayAfterFocus());
|
|
250
|
-
}
|
|
251
|
-
}
|
|
252
|
-
}
|
|
253
|
-
|
|
254
|
-
private IEnumerator ResumeReplayAfterFocus()
|
|
255
|
-
{
|
|
256
|
-
// WebGL reports focus before Unity refreshes its unscaled clock. Keep
|
|
257
|
-
// gameplay and replay frozen briefly while session time continues.
|
|
258
|
-
yield return new WaitForSecondsRealtime(1f);
|
|
259
|
-
|
|
260
|
-
_replayFocusResumeCoroutine = null;
|
|
261
|
-
if (!_replayFocusSuspended || _hasGameEnded) yield break;
|
|
262
|
-
|
|
263
|
-
_replayFocusSuspended = false;
|
|
264
|
-
Time.timeScale = _savedReplayTimeScale > 0f ? _savedReplayTimeScale : 1f;
|
|
265
|
-
HyperRuntime.Timer.ResumeGameTimersAfterPause();
|
|
266
|
-
|
|
267
|
-
_previousTimeScale = Time.timeScale;
|
|
268
|
-
_eventManager.InvokeTimeScaleResumedEvent();
|
|
269
|
-
HyperDebug.Log("Time scale resumed event invoked");
|
|
260
|
+
if (!hasFocus) PauseReplay();
|
|
270
261
|
}
|
|
271
262
|
|
|
272
263
|
void HandlePauseState(bool shouldPause)
|
|
@@ -552,7 +543,7 @@ namespace Hyper.Internal.Managers
|
|
|
552
543
|
|
|
553
544
|
internal void ShowStartGameDeadline(int timeLeft)
|
|
554
545
|
{
|
|
555
|
-
if (_hasGameStarted || !IsInGameScene) return;
|
|
546
|
+
if (_hasGameStarted || !IsInGameScene || IsReplayMode) return;
|
|
556
547
|
|
|
557
548
|
EnsureStartGameDeadlineBar();
|
|
558
549
|
_eventManager.OnSessionAboutToExpire += ChangeDeadlineColorToRed;
|
|
@@ -728,7 +719,6 @@ namespace Hyper.Internal.Managers
|
|
|
728
719
|
private bool _isPortrait;
|
|
729
720
|
private float _previousTimeScale = 1f;
|
|
730
721
|
private float _savedTimeScaleBeforePause = 1f;
|
|
731
|
-
private bool _replayFocusSuspended;
|
|
732
722
|
private float _savedReplayTimeScale = 1f;
|
|
733
723
|
|
|
734
724
|
#endregion
|
|
@@ -1025,6 +1015,8 @@ namespace Hyper.Internal.Managers
|
|
|
1025
1015
|
if (_gameStartRequested || _hasGameStarted || _hasGameEnded || !IsInGameScene) return;
|
|
1026
1016
|
_gameStartRequested = true;
|
|
1027
1017
|
|
|
1018
|
+
HyperRuntime.ApplyPendingReplayRandomReset();
|
|
1019
|
+
|
|
1028
1020
|
HideStartGameDeadlineSnackBar();
|
|
1029
1021
|
_dataManager.UpdateScore(0);
|
|
1030
1022
|
HyperRuntime.Timer.StartActiveGameTimer();
|
|
@@ -1062,26 +1054,58 @@ namespace Hyper.Internal.Managers
|
|
|
1062
1054
|
|
|
1063
1055
|
/// <summary>
|
|
1064
1056
|
/// Resets SDK UI state for custom restart flow.
|
|
1065
|
-
/// Called
|
|
1057
|
+
/// Called before OnCustomRestart so the developer's cleanup starts from reset SDK state.
|
|
1066
1058
|
/// </summary>
|
|
1067
1059
|
internal void ResetUIStateForCustomRestart()
|
|
1068
1060
|
{
|
|
1069
1061
|
HideGameOverModal();
|
|
1070
1062
|
HidePauseModals();
|
|
1063
|
+
if (_replayOverModal != null) _replayOverModal.SetActive(false);
|
|
1071
1064
|
|
|
1072
1065
|
// Reset game state flags
|
|
1073
1066
|
_hasGameStarted = false;
|
|
1074
1067
|
_gameStartRequested = false;
|
|
1075
1068
|
_hasGameEnded = false;
|
|
1069
|
+
_replayEndHandled = false;
|
|
1076
1070
|
_isPaused = false;
|
|
1077
1071
|
_isFrozenBeforePause = false;
|
|
1078
1072
|
|
|
1079
|
-
HyperRuntime.Timer.
|
|
1073
|
+
HyperRuntime.Timer.ResetForGameRestart();
|
|
1080
1074
|
HyperRuntime.DataManager.UpdateScore(0);
|
|
1081
1075
|
HyperRuntime.DataManager.RestoreAudioAfterGameSessionEnd();
|
|
1082
1076
|
|
|
1083
1077
|
ShowControlBarElements();
|
|
1084
|
-
|
|
1078
|
+
_replayControllerComponent?.ResetForReplayRestart();
|
|
1079
|
+
|
|
1080
|
+
if (IsReplayMode && HyperRuntime.IsReplayCustomRestartPending)
|
|
1081
|
+
{
|
|
1082
|
+
HideStartingInstructionModal();
|
|
1083
|
+
return;
|
|
1084
|
+
}
|
|
1085
|
+
|
|
1086
|
+
if (IsReplayMode && ReplaySessionState.IsSeeking)
|
|
1087
|
+
{
|
|
1088
|
+
HideStartingInstructionModal();
|
|
1089
|
+
StartCoroutine(StartSeekingReplayWhenReady());
|
|
1090
|
+
}
|
|
1091
|
+
else
|
|
1092
|
+
{
|
|
1093
|
+
ShowStartingInstructionModal();
|
|
1094
|
+
}
|
|
1095
|
+
}
|
|
1096
|
+
|
|
1097
|
+
internal void CompleteReplayCustomRestart()
|
|
1098
|
+
{
|
|
1099
|
+
if (!IsReplayMode || _gameStartRequested || _hasGameStarted || _hasGameEnded) return;
|
|
1100
|
+
|
|
1101
|
+
if (ReplaySessionState.IsSeeking)
|
|
1102
|
+
{
|
|
1103
|
+
StartCoroutine(StartSeekingReplayWhenReady());
|
|
1104
|
+
}
|
|
1105
|
+
else
|
|
1106
|
+
{
|
|
1107
|
+
ShowStartingInstructionModal();
|
|
1108
|
+
}
|
|
1085
1109
|
}
|
|
1086
1110
|
|
|
1087
1111
|
#endregion
|
|
@@ -1125,7 +1149,6 @@ namespace Hyper.Internal.Managers
|
|
|
1125
1149
|
|
|
1126
1150
|
_replayEndHandled = true;
|
|
1127
1151
|
_hasGameEnded = true;
|
|
1128
|
-
_replayFocusSuspended = false;
|
|
1129
1152
|
Time.timeScale = 1f;
|
|
1130
1153
|
_eventManager.InvokeGameEndedEvent();
|
|
1131
1154
|
HyperRuntime.Timer.StopAllTimers();
|
|
@@ -1147,10 +1170,12 @@ namespace Hyper.Internal.Managers
|
|
|
1147
1170
|
_eventManager.InvokeGameEndedEvent();
|
|
1148
1171
|
}
|
|
1149
1172
|
|
|
1173
|
+
_isPaused = false;
|
|
1150
1174
|
Time.timeScale = 1f;
|
|
1151
1175
|
HyperRuntime.Timer.StopAllTimers();
|
|
1152
1176
|
_dataManager.StopCapturingScores();
|
|
1153
1177
|
HyperRuntime.BackendManager.StopSendingScores();
|
|
1178
|
+
HidePauseModals();
|
|
1154
1179
|
_replayControllerComponent?.SetReplayEnded();
|
|
1155
1180
|
ReplaySessionState.Clear();
|
|
1156
1181
|
ReplayPresentationCanvas.DestroyCurrent();
|
|
@@ -1261,8 +1286,8 @@ namespace Hyper.Internal.Managers
|
|
|
1261
1286
|
private GameObject _replayControllerObject;
|
|
1262
1287
|
private ReplayController _replayControllerComponent;
|
|
1263
1288
|
private GameObject _replayOverModal;
|
|
1289
|
+
private GameObject _replayPausedModal;
|
|
1264
1290
|
private Coroutine _replayConnectionCheckCoroutine;
|
|
1265
|
-
private Coroutine _replayFocusResumeCoroutine;
|
|
1266
1291
|
|
|
1267
1292
|
private GameObject _connectionStatusBar;
|
|
1268
1293
|
private GameObject _startGameDeadlineStatusBar;
|
|
@@ -1492,6 +1517,30 @@ namespace Hyper.Internal.Managers
|
|
|
1492
1517
|
_replayOverModal.transform.SetAsLastSibling();
|
|
1493
1518
|
}
|
|
1494
1519
|
|
|
1520
|
+
private void ShowReplayPauseModal()
|
|
1521
|
+
{
|
|
1522
|
+
if (_replayPausedModal == null)
|
|
1523
|
+
{
|
|
1524
|
+
if (_canvas == null) CreateCanvas();
|
|
1525
|
+
GameObject prefab = Resources.Load<GameObject>("UIPrefabs/ReplayPausedModal");
|
|
1526
|
+
if (prefab == null)
|
|
1527
|
+
{
|
|
1528
|
+
HyperDebug.LogWarning("[GameManager] ReplayPausedModal prefab not found.");
|
|
1529
|
+
ResumeReplay();
|
|
1530
|
+
return;
|
|
1531
|
+
}
|
|
1532
|
+
|
|
1533
|
+
_replayPausedModal = InstantiateModal(prefab);
|
|
1534
|
+
if (_replayPausedModal.GetComponent<ReplayPausedModal>() == null)
|
|
1535
|
+
{
|
|
1536
|
+
_replayPausedModal.AddComponent<ReplayPausedModal>();
|
|
1537
|
+
}
|
|
1538
|
+
}
|
|
1539
|
+
|
|
1540
|
+
_replayPausedModal.SetActive(true);
|
|
1541
|
+
_replayPausedModal.transform.SetAsLastSibling();
|
|
1542
|
+
}
|
|
1543
|
+
|
|
1495
1544
|
private void EnsureConnectionStatusBar()
|
|
1496
1545
|
{
|
|
1497
1546
|
if (_connectionStatusBar != null) return;
|
|
@@ -1740,6 +1789,7 @@ namespace Hyper.Internal.Managers
|
|
|
1740
1789
|
internal void HidePauseModals()
|
|
1741
1790
|
{
|
|
1742
1791
|
SetBlockerActive(false);
|
|
1792
|
+
if (_replayPausedModal != null) _replayPausedModal.SetActive(false);
|
|
1743
1793
|
if (_battleGamePausedModal != null) _battleGamePausedModal.SetActive(false);
|
|
1744
1794
|
if (_practicePausedModal != null) _practicePausedModal.SetActive(false);
|
|
1745
1795
|
if (_battleGamePausedLandscapeModal != null) _battleGamePausedLandscapeModal.SetActive(false);
|
|
@@ -39,6 +39,12 @@ namespace Hyper.Internal.Managers
|
|
|
39
39
|
ReplaySessionState.SetProgress(_playback.Progress01);
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
+
internal void PrepareForRestart()
|
|
43
|
+
{
|
|
44
|
+
_endingGame = false;
|
|
45
|
+
_playback?.Stop();
|
|
46
|
+
}
|
|
47
|
+
|
|
42
48
|
internal void Cleanup()
|
|
43
49
|
{
|
|
44
50
|
if (_eventManager != null)
|
|
@@ -68,6 +74,7 @@ namespace Hyper.Internal.Managers
|
|
|
68
74
|
}
|
|
69
75
|
|
|
70
76
|
_playback.Begin(ReplaySessionState.ReplayNdjson);
|
|
77
|
+
ReplaySessionState.SetGameplayStartProgress(_playback.GameplayStartProgress01);
|
|
71
78
|
}
|
|
72
79
|
|
|
73
80
|
private void HandleGameEnded()
|