44 * Created on: 9/4/2022 (en-US)
55 */
66
7+ using Cysharp . Threading . Tasks ;
78using System ;
89using System . Collections ;
910using UnityEngine ;
11+ using UnityEngine . SceneManagement ;
1012using Object = UnityEngine . Object ;
1113
1214namespace MyGameDevTools . SceneLoading
@@ -22,13 +24,13 @@ public SceneLoaderCoroutine(ISceneManager manager)
2224 _manager = manager ?? throw new ArgumentNullException ( "Cannot create a scene loader with a null Scene Manager" ) ;
2325 }
2426
25- public void TransitionToScene ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo ) => TransitionToSceneAsync ( targetSceneInfo , intermediateSceneInfo ) ;
27+ public void TransitionToScene ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo , Scene externalOriginScene ) => TransitionToSceneAsync ( targetSceneInfo , intermediateSceneInfo , externalOriginScene ) ;
2628
2729 public void UnloadScene ( ILoadSceneInfo sceneInfo ) => UnloadSceneAsync ( sceneInfo ) ;
2830
2931 public void LoadScene ( ILoadSceneInfo sceneInfo , bool setActive ) => LoadSceneAsync ( sceneInfo , setActive ) ;
3032
31- public Coroutine TransitionToSceneAsync ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo ) => RoutineBehaviour . Instance . StartCoroutine ( intermediateSceneInfo == null ? TransitionDirectlyRoutine ( targetSceneInfo ) : TransitionWithIntermediateRoutine ( targetSceneInfo , intermediateSceneInfo ) ) ;
33+ public Coroutine TransitionToSceneAsync ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo , Scene externalOriginScene ) => RoutineBehaviour . Instance . StartCoroutine ( intermediateSceneInfo == null ? TransitionDirectlyRoutine ( targetSceneInfo , externalOriginScene ) : TransitionWithIntermediateRoutine ( targetSceneInfo , intermediateSceneInfo , externalOriginScene ) ) ;
3234
3335 public Coroutine UnloadSceneAsync ( ILoadSceneInfo sceneInfo ) => RoutineBehaviour . Instance . StartCoroutine ( UnloadRoutine ( sceneInfo ) ) ;
3436
@@ -44,42 +46,57 @@ IEnumerator UnloadRoutine(ILoadSceneInfo sceneInfo)
4446 yield return new WaitTask ( _manager . UnloadSceneAsync ( sceneInfo ) . AsTask ( ) ) ;
4547 }
4648
47- IEnumerator TransitionWithIntermediateRoutine ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo )
49+ IEnumerator TransitionDirectlyRoutine ( ILoadSceneInfo targetSceneInfo , Scene externalOriginScene )
4850 {
49- var currentScene = _manager . GetActiveScene ( ) ;
51+ var externalOrigin = externalOriginScene . IsValid ( ) ;
52+ var currentScene = externalOrigin ? externalOriginScene : _manager . GetActiveScene ( ) ;
53+ yield return UnloadCurrentScene ( currentScene , externalOrigin ) ;
54+ yield return LoadRoutine ( targetSceneInfo , true , null ) ;
55+ }
56+
57+ IEnumerator TransitionWithIntermediateRoutine ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo , Scene externalOriginScene )
58+ {
59+ var externalOrigin = externalOriginScene . IsValid ( ) ;
60+ var currentScene = externalOrigin ? externalOriginScene : _manager . GetActiveScene ( ) ;
5061 yield return new WaitTask ( _manager . LoadSceneAsync ( intermediateSceneInfo ) . AsTask ( ) ) ;
5162
5263 var loadingBehavior = Object . FindObjectOfType < LoadingBehavior > ( ) ;
53- if ( loadingBehavior )
54- {
55- var progress = loadingBehavior . Progress ;
56- yield return new WaitUntil ( ( ) => progress . State == LoadingState . Loading ) ;
64+ yield return loadingBehavior
65+ ? TransitionWithIntermediateLoadingAsync ( targetSceneInfo , intermediateSceneInfo , loadingBehavior , currentScene , externalOrigin )
66+ : TransitionWithIntermediateNoLoadingAsync ( targetSceneInfo , intermediateSceneInfo , currentScene , externalOrigin ) ;
67+ }
68+
69+ IEnumerator TransitionWithIntermediateLoadingAsync ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo , LoadingBehavior loadingBehavior , Scene currentScene , bool externalOrigin )
70+ {
71+ var progress = loadingBehavior . Progress ;
72+ yield return new WaitUntil ( ( ) => progress . State == LoadingState . Loading ) ;
5773
58- if ( currentScene . IsValid ( ) )
59- yield return UnloadRoutine ( new LoadSceneInfoScene ( currentScene ) ) ;
74+ yield return UnloadCurrentScene ( currentScene , externalOrigin ) ;
6075
61- yield return new WaitTask ( _manager . LoadSceneAsync ( targetSceneInfo , true , progress ) . AsTask ( ) ) ;
62- progress . SetState ( LoadingState . TargetSceneLoaded ) ;
76+ yield return new WaitTask ( _manager . LoadSceneAsync ( targetSceneInfo , true , progress ) . AsTask ( ) ) ;
77+ progress . SetState ( LoadingState . TargetSceneLoaded ) ;
6378
64- yield return new WaitUntil ( ( ) => progress . State == LoadingState . TransitionComplete ) ;
79+ yield return new WaitUntil ( ( ) => progress . State == LoadingState . TransitionComplete ) ;
6580
66- UnloadSceneAsync ( intermediateSceneInfo ) ;
67- }
68- else
69- {
70- if ( currentScene . IsValid ( ) )
71- yield return UnloadRoutine ( new LoadSceneInfoScene ( currentScene ) ) ;
72- yield return LoadRoutine ( targetSceneInfo , true , null ) ;
73- UnloadSceneAsync ( intermediateSceneInfo ) ;
74- }
81+ UnloadSceneAsync ( intermediateSceneInfo ) ;
7582 }
7683
77- IEnumerator TransitionDirectlyRoutine ( ILoadSceneInfo targetSceneInfo )
84+ IEnumerator TransitionWithIntermediateNoLoadingAsync ( ILoadSceneInfo targetSceneInfo , ILoadSceneInfo intermediateSceneInfo , Scene currentScene , bool externalOrigin )
7885 {
79- var currentScene = _manager . GetActiveScene ( ) ;
80- if ( currentScene . IsValid ( ) )
81- yield return UnloadRoutine ( new LoadSceneInfoScene ( currentScene ) ) ;
86+ yield return UnloadCurrentScene ( currentScene , externalOrigin ) ;
8287 yield return LoadRoutine ( targetSceneInfo , true , null ) ;
88+ UnloadSceneAsync ( intermediateSceneInfo ) ;
89+ }
90+
91+ IEnumerator UnloadCurrentScene ( Scene currentScene , bool externalOrigin )
92+ {
93+ if ( ! currentScene . IsValid ( ) )
94+ yield break ;
95+
96+ if ( externalOrigin )
97+ yield return UnityEngine . SceneManagement . SceneManager . UnloadSceneAsync ( currentScene ) ;
98+ else
99+ yield return UnloadRoutine ( new LoadSceneInfoScene ( currentScene ) ) ;
83100 }
84101 }
85102}
0 commit comments