Second commit
This commit is contained in:
commit
36840f3ad4
999 files changed
+61364
No files matched your search
@@ -0,0 +1,109 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Code.Infrastructure.Configs;
|
||||
using Code.Infrastructure.Utils;
|
||||
using Cysharp.Threading.Tasks;
|
||||
using ObservableCollections;
|
||||
using Reflex.Core;
|
||||
using UnityEngine;
|
||||
using UnityEngine.ResourceManagement.AsyncOperations;
|
||||
using UnityEngine.ResourceManagement.ResourceProviders;
|
||||
using UnityEngine.SceneManagement;
|
||||
|
||||
namespace Code.Infrastructure.SceneLoader
|
||||
{
|
||||
using UnityEngine.AddressableAssets;
|
||||
|
||||
public interface ISceneLoader
|
||||
{
|
||||
UniTask LoadSceneAsync(SceneId id, LoadSceneMode loadMode, bool setActive, Action<Scene, ContainerBuilder> extraInstall = null);
|
||||
Scene GetScene(SceneId id);
|
||||
UniTask UnloadSceneAsync(SceneId id);
|
||||
}
|
||||
|
||||
public interface ISceneContainerManager
|
||||
{
|
||||
ObservableDictionary<SceneId, Container> ScenesContainers { get; }
|
||||
}
|
||||
|
||||
public interface ICustomSceneManagerInitializer
|
||||
{
|
||||
UniTask LoadConfigs();
|
||||
}
|
||||
|
||||
public class CustomCustomSceneManager : IDisposable, ISceneLoader, ISceneContainerManager,
|
||||
ICustomSceneManagerInitializer
|
||||
{
|
||||
private AsyncOperationHandle<IList<SceneInfo>> _loadHandle;
|
||||
private AsyncOperationHandle<IList<SceneInfo>> _configHandle;
|
||||
private readonly string _configsLabel;
|
||||
|
||||
public ObservableDictionary<SceneId, Container> ScenesContainers { get; } = new();
|
||||
|
||||
private Dictionary<SceneId, SceneInfo> _sceneInfos = new();
|
||||
private Dictionary<SceneId, AsyncOperationHandle<SceneInstance>> _loadedScenes = new();
|
||||
|
||||
public CustomCustomSceneManager(IConfigLocator configLocator)
|
||||
{
|
||||
_configsLabel = configLocator.TryGetManyConfigAssetReferences<SceneInfo>();
|
||||
}
|
||||
|
||||
// Киська
|
||||
// TODO При загрузке нескольких сцен сразу может быть неприятность
|
||||
public async UniTask LoadSceneAsync(
|
||||
SceneId id,
|
||||
LoadSceneMode loadMode,
|
||||
bool setActive,
|
||||
Action<Scene, ContainerBuilder> extraInstall = null)
|
||||
{
|
||||
if (loadMode == LoadSceneMode.Single)
|
||||
for (var i = 0; i < _loadedScenes.Count; i++)
|
||||
UnloadSceneAsync(_loadedScenes.Keys.ToList()[i]).Forget();
|
||||
|
||||
if (extraInstall != null) ContainerScope.OnSceneContainerBuilding += extraInstall;
|
||||
|
||||
_loadedScenes.Add(id, Addressables.LoadSceneAsync(_sceneInfos[id].SceneAsset, LoadSceneMode.Additive));
|
||||
|
||||
await _loadedScenes[id];
|
||||
|
||||
if (extraInstall != null) ContainerScope.OnSceneContainerBuilding -= extraInstall;
|
||||
|
||||
if (setActive) SceneManager.SetActiveScene(_loadedScenes[id].Result.Scene);
|
||||
}
|
||||
|
||||
public Scene GetScene(SceneId id) => _loadedScenes[id].Result.Scene;
|
||||
|
||||
public async UniTask UnloadSceneAsync(SceneId id)
|
||||
{
|
||||
await Addressables.UnloadSceneAsync(_loadedScenes[id]);
|
||||
_loadedScenes.Remove(id);
|
||||
}
|
||||
|
||||
|
||||
public async UniTask LoadConfigs()
|
||||
{
|
||||
if (!await AddressablesUtilities.CheckLabelExists(_configsLabel)) return;
|
||||
|
||||
_configHandle =
|
||||
Addressables.LoadAssetsAsync<SceneInfo>(_configsLabel, OnSceneConfigLoaded,
|
||||
Addressables.MergeMode.Union);
|
||||
|
||||
await _configHandle.ToUniTask();
|
||||
}
|
||||
|
||||
private void OnSceneConfigLoaded(SceneInfo sceneInfoConfig)
|
||||
{
|
||||
SceneInfo sceneInfo = ScriptableObject.CreateInstance<SceneInfo>();
|
||||
sceneInfo.SceneId = sceneInfoConfig.SceneId;
|
||||
sceneInfo.SceneAsset = sceneInfoConfig.SceneAsset;
|
||||
|
||||
_sceneInfos.Add(sceneInfoConfig.SceneId, sceneInfo);
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
if(_configHandle.IsValid()) Addressables.Release(_configHandle);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user