308 lines
10 KiB
C#
308 lines
10 KiB
C#
using GameFramework.Resource;
|
|
using GeometryTD.CustomUtility;
|
|
using GeometryTD.DataTable;
|
|
using GeometryTD.Definition;
|
|
using GeometryTD.Entity;
|
|
using GeometryTD.Entity.EntityData;
|
|
using GeometryTD.UI;
|
|
using UnityEngine;
|
|
using UnityGameFramework.Runtime;
|
|
|
|
namespace GeometryTD.CustomComponent
|
|
{
|
|
internal sealed class CombatLoadSession
|
|
{
|
|
internal enum EventHandleStatus : byte
|
|
{
|
|
Ignored = 0,
|
|
Succeeded = 1,
|
|
Failed = 2
|
|
}
|
|
|
|
private EntityComponent _entity;
|
|
private CombatInfoFormUseCase _combatInfoFormUseCase;
|
|
private int _loadingMapEntityId;
|
|
private int _loadedMapEntityId;
|
|
private int? _loadingCombatInfoFormSerialId;
|
|
private bool _isCombatInfoFormReady;
|
|
private MapEntity _currentMap;
|
|
|
|
public MapEntity CurrentMap => _currentMap;
|
|
public bool IsReady => _currentMap != null && _isCombatInfoFormReady;
|
|
|
|
public void OnInit(EntityComponent entityComponent)
|
|
{
|
|
_entity = entityComponent;
|
|
Reset();
|
|
}
|
|
|
|
public void Reset()
|
|
{
|
|
_loadingMapEntityId = 0;
|
|
_loadedMapEntityId = 0;
|
|
_loadingCombatInfoFormSerialId = null;
|
|
_isCombatInfoFormReady = false;
|
|
_currentMap = null;
|
|
}
|
|
|
|
public bool StartLoading(DRLevel level, MapData mapData, CombatScheduler scheduler, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (_entity == null)
|
|
{
|
|
errorMessage = "CombatLoadSession start failed. Entity component is null.";
|
|
return false;
|
|
}
|
|
|
|
if (!TryShowMap(level, mapData, out errorMessage))
|
|
{
|
|
return false;
|
|
}
|
|
|
|
if (!TryOpenCombatInfoForm(scheduler, out errorMessage))
|
|
{
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public void RefreshCombatInfoForm(DRLevel currentLevel)
|
|
{
|
|
if (currentLevel == null)
|
|
{
|
|
return;
|
|
}
|
|
|
|
GameEntry.UIRouter.OpenUI(UIFormType.CombatInfoForm);
|
|
}
|
|
|
|
public void Cleanup()
|
|
{
|
|
if (_entity == null)
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (_loadingMapEntityId != 0 && _entity.IsLoadingEntity(_loadingMapEntityId))
|
|
{
|
|
_entity.HideEntity(_loadingMapEntityId);
|
|
}
|
|
|
|
if (_currentMap != null)
|
|
{
|
|
_entity.HideEntity(_currentMap);
|
|
}
|
|
else if (_loadedMapEntityId != 0)
|
|
{
|
|
UnityGameFramework.Runtime.Entity loadedMapEntity = _entity.GetEntity(_loadedMapEntityId);
|
|
if (loadedMapEntity != null)
|
|
{
|
|
_entity.HideEntity(loadedMapEntity);
|
|
}
|
|
}
|
|
|
|
CloseCombatInfoForm();
|
|
}
|
|
|
|
public EventHandleStatus HandleShowEntitySuccess(ShowEntitySuccessEventArgs args, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (args == null)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
if (args.EntityLogicType != typeof(MapEntity) || args.Entity == null ||
|
|
args.Entity.Id != _loadingMapEntityId)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
_loadedMapEntityId = _loadingMapEntityId;
|
|
_loadingMapEntityId = 0;
|
|
_currentMap = args.Entity.Logic as MapEntity;
|
|
if (_currentMap == null)
|
|
{
|
|
errorMessage = $"Loaded map entity logic is invalid. EntityId={args.Entity.Id}.";
|
|
return EventHandleStatus.Failed;
|
|
}
|
|
|
|
return EventHandleStatus.Succeeded;
|
|
}
|
|
|
|
public EventHandleStatus HandleShowEntityFailure(ShowEntityFailureEventArgs args, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (args == null)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
if (args.EntityLogicType != typeof(MapEntity) || args.EntityId != _loadingMapEntityId)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
_loadingMapEntityId = 0;
|
|
_currentMap = null;
|
|
errorMessage = $"Map load failed. Asset='{args.EntityAssetName}', Error='{args.ErrorMessage}'.";
|
|
return EventHandleStatus.Failed;
|
|
}
|
|
|
|
public void HandleHideEntityComplete(HideEntityCompleteEventArgs args)
|
|
{
|
|
if (args == null)
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (args.EntityId == _loadedMapEntityId)
|
|
{
|
|
_loadedMapEntityId = 0;
|
|
_currentMap = null;
|
|
}
|
|
|
|
if (args.EntityId == _loadingMapEntityId)
|
|
{
|
|
_loadingMapEntityId = 0;
|
|
}
|
|
}
|
|
|
|
public EventHandleStatus HandleOpenUIFormSuccess(OpenUIFormSuccessEventArgs args, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (args == null || !_loadingCombatInfoFormSerialId.HasValue || args.UIForm == null)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
if (args.UIForm.SerialId != _loadingCombatInfoFormSerialId.Value)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
_isCombatInfoFormReady = args.UIForm.Logic is CombatInfoForm;
|
|
if (!_isCombatInfoFormReady)
|
|
{
|
|
errorMessage = "CombatInfoForm open success but form logic type is invalid.";
|
|
return EventHandleStatus.Failed;
|
|
}
|
|
|
|
return EventHandleStatus.Succeeded;
|
|
}
|
|
|
|
public EventHandleStatus HandleOpenUIFormFailure(OpenUIFormFailureEventArgs args, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (args == null || !_loadingCombatInfoFormSerialId.HasValue)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
if (args.SerialId != _loadingCombatInfoFormSerialId.Value)
|
|
{
|
|
return EventHandleStatus.Ignored;
|
|
}
|
|
|
|
_isCombatInfoFormReady = false;
|
|
errorMessage = $"CombatInfoForm load failed. Asset='{args.UIFormAssetName}', Error='{args.ErrorMessage}'.";
|
|
return EventHandleStatus.Failed;
|
|
}
|
|
|
|
public void HandleCloseUIFormComplete(CloseUIFormCompleteEventArgs args)
|
|
{
|
|
if (args == null || !_loadingCombatInfoFormSerialId.HasValue)
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (args.SerialId == _loadingCombatInfoFormSerialId.Value)
|
|
{
|
|
_loadingCombatInfoFormSerialId = null;
|
|
_isCombatInfoFormReady = false;
|
|
}
|
|
}
|
|
|
|
private bool TryShowMap(DRLevel level, MapData mapData, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (level == null)
|
|
{
|
|
errorMessage = "CombatLoadSession map load failed. Level is null.";
|
|
return false;
|
|
}
|
|
|
|
string mapAssetName = level.Id.ToString();
|
|
string mapAssetPath = AssetUtility.GetLevelMapAsset(mapAssetName);
|
|
if (GameEntry.Resource.HasAsset(mapAssetPath) == HasAssetResult.NotExist)
|
|
{
|
|
errorMessage = $"CombatLoadSession map asset not found. Level='{level.Id}', Asset='{mapAssetPath}'.";
|
|
return false;
|
|
}
|
|
|
|
_loadingMapEntityId = _entity.GenerateSerialId();
|
|
MapData resolvedMapData = mapData != null
|
|
? mapData.CloneForEntity(_loadingMapEntityId, Vector3.zero)
|
|
: new MapData(_loadingMapEntityId, level.Id, Vector3.zero);
|
|
_entity.ShowMap(resolvedMapData, mapAssetName);
|
|
return true;
|
|
}
|
|
|
|
private bool TryOpenCombatInfoForm(CombatScheduler scheduler, out string errorMessage)
|
|
{
|
|
errorMessage = null;
|
|
if (_combatInfoFormUseCase == null)
|
|
{
|
|
_combatInfoFormUseCase = new CombatInfoFormUseCase();
|
|
GameEntry.UIRouter.BindUIUseCase(UIFormType.CombatInfoForm, _combatInfoFormUseCase);
|
|
}
|
|
|
|
_combatInfoFormUseCase.Configure(
|
|
() => BuildCombatInfoFormRawData(scheduler),
|
|
() => scheduler != null && scheduler.CanEndCombat && scheduler.TryEndCombatByPlayer(),
|
|
() => scheduler != null && scheduler.TryDebugFail("Manual debug fail from CombatInfoForm."));
|
|
|
|
int? serialId = GameEntry.UIRouter.OpenUI(UIFormType.CombatInfoForm);
|
|
if (!serialId.HasValue)
|
|
{
|
|
errorMessage = "CombatLoadSession failed to open CombatInfoForm.";
|
|
return false;
|
|
}
|
|
|
|
_loadingCombatInfoFormSerialId = serialId.Value;
|
|
_isCombatInfoFormReady = GameEntry.UI.HasUIForm(serialId.Value);
|
|
return true;
|
|
}
|
|
|
|
private static CombatInfoFormRawData BuildCombatInfoFormRawData(CombatScheduler scheduler)
|
|
{
|
|
if (scheduler == null)
|
|
{
|
|
return null;
|
|
}
|
|
|
|
DRLevel level = scheduler.CurrentLevel;
|
|
LevelThemeType themeType = level != null ? level.LevelThemeType : LevelThemeType.None;
|
|
int levelId = level != null ? level.Id : 0;
|
|
int baseHpMax = level != null ? Mathf.Max(0, level.BaseHp) : 0;
|
|
return CombatInfoFormUseCase.BuildRawData(
|
|
themeType,
|
|
levelId,
|
|
scheduler.DisplayPhaseIndex,
|
|
scheduler.PhaseCount,
|
|
scheduler.CurrentCoin,
|
|
scheduler.CurrentBaseHp,
|
|
baseHpMax,
|
|
scheduler.CanEndCombat);
|
|
}
|
|
|
|
private void CloseCombatInfoForm()
|
|
{
|
|
GameEntry.UIRouter.CloseUI(UIFormType.CombatInfoForm);
|
|
_loadingCombatInfoFormSerialId = null;
|
|
_isCombatInfoFormReady = false;
|
|
}
|
|
}
|
|
}
|