using UnityEngine;
using System;
using System.Collections.Generic;
using Spine.Unity;
public class BattlePreloadManager
{
private BattleCacheManager cacheManager = new BattleCacheManager();
private BattleUnloadManager unloadManager = new BattleUnloadManager();
private bool isLoading = false;
public BattleCacheManager CacheManager => cacheManager;
public BattleUnloadManager UnloadManager => unloadManager;
///
/// 预加载战斗资源
///
public void PreloadBattleResources(string battleGuid, List redTeamList, List blueTeamList,
Action progressCallback, Action completeCallback)
{
if (isLoading)
{
Debug.LogWarning("BattlePreloadManager: Already loading, ignoring request");
return;
}
isLoading = true;
var redTeamInfo = AnalyzeTeamList(redTeamList, true);
var blueTeamInfo = AnalyzeTeamList(blueTeamList, false);
// ===== 合并红蓝队资源,统一注册 =====
var allSpineResources = new List();
var allAudioResources = new List();
allSpineResources.AddRange(redTeamInfo.SpineResources);
allSpineResources.AddRange(blueTeamInfo.SpineResources);
allAudioResources.AddRange(redTeamInfo.AudioResources);
allAudioResources.AddRange(blueTeamInfo.AudioResources);
cacheManager.RegisterBattlefieldResources(battleGuid, allSpineResources, allAudioResources);
StartPreload(allSpineResources, allAudioResources, battleGuid, progressCallback, () =>
{
isLoading = false;
completeCallback?.Invoke();
});
}
private TeamResTracker.TeamResourceInfo AnalyzeTeamList(List teamList, bool isPersistent)
{
var combinedInfo = new TeamResTracker.TeamResourceInfo();
if (teamList == null || teamList.Count == 0)
{
return combinedInfo;
}
foreach (var team in teamList)
{
if (team == null)
continue;
var teamInfo = TeamResTracker.AnalyzeTeam(team, isPersistent);
MergeResourceInfo(combinedInfo, teamInfo);
}
return combinedInfo;
}
private void MergeResourceInfo(TeamResTracker.TeamResourceInfo target, TeamResTracker.TeamResourceInfo source)
{
// 合并Spine资源(去重)
foreach (var res in source.SpineResources)
{
if (!ContainsResource(target.SpineResources, res))
{
target.SpineResources.Add(res);
}
}
// 合并音频资源(去重)
foreach (var res in source.AudioResources)
{
if (!ContainsResource(target.AudioResources, res))
{
target.AudioResources.Add(res);
}
}
}
private bool ContainsResource(List list, BattleResCache.ResourceIdentifier resource)
{
foreach (var item in list)
{
if (item.GetKey() == resource.GetKey())
{
return true;
}
}
return false;
}
private void StartPreload(List spineResources,
List audioResources,
string battleGuid,
Action progressCallback, Action completeCallback)
{
int totalResources = spineResources.Count + audioResources.Count;
if (totalResources == 0)
{
Debug.Log("BattlePreloadManager: No resources to preload");
completeCallback?.Invoke();
return;
}
Debug.Log($"BattlePreloadManager: Preloading {totalResources} resources for battlefield {battleGuid}");
Debug.Log($" Spine={spineResources.Count}, Audio={audioResources.Count}");
int loadedCount = 0;
Action onSingleComplete = () =>
{
loadedCount++;
float progress = (float)loadedCount / totalResources;
progressCallback?.Invoke(progress);
if (loadedCount >= totalResources)
{
Debug.Log($"BattlePreloadManager: Completed! {cacheManager.GetCacheStats(battleGuid)}");
completeCallback?.Invoke();
}
};
// 异步加载所有Spine资源
foreach (var identifier in spineResources)
{
LoadSpineAsync(identifier, battleGuid, onSingleComplete);
}
// 异步加载所有Audio资源
foreach (var identifier in audioResources)
{
LoadAudioAsync(identifier, battleGuid, onSingleComplete);
}
}
private void LoadSpineAsync(BattleResCache.ResourceIdentifier identifier, string battleGuid, Action onComplete)
{
string key = identifier.GetKey();
ResManager.Instance.LoadAssetAsync(
identifier.Directory,
identifier.AssetName,
(success, asset) =>
{
if (success && asset != null)
{
var skeletonData = asset as SkeletonDataAsset;
if (skeletonData != null)
{
var cachedRes = new BattleResCache.CachedResource(identifier, skeletonData, false);
cacheManager.UpdateResourceReference(key, cachedRes, battleGuid, identifier.OwnerId);
Debug.Log($"BattlePreloadManager: Loaded spine: {key}");
}
}
else
{
Debug.LogError($"BattlePreloadManager: Failed to load spine: {key}");
}
onComplete?.Invoke();
}
);
}
private void LoadAudioAsync(BattleResCache.ResourceIdentifier identifier, string battleGuid, Action onComplete)
{
string key = identifier.GetKey();
ResManager.Instance.LoadAssetAsync(
identifier.Directory,
identifier.AssetName,
(success, asset) =>
{
if (success && asset != null)
{
var audioClip = asset as AudioClip;
if (audioClip != null)
{
var cachedRes = new BattleResCache.CachedResource(identifier, audioClip, false);
cacheManager.UpdateResourceReference(key, cachedRes, battleGuid, identifier.OwnerId);
Debug.Log($"BattlePreloadManager: Loaded audio: {key}");
}
}
else
{
Debug.LogError($"BattlePreloadManager: Failed to load audio: {key}");
}
onComplete?.Invoke();
},
false // needExt = false
);
}
}