using XGame.Framework.Asyncs;
using System;
namespace XGame.Framework.Asset
{
///
/// 该类也继承IAssetPreloadAsync,少创建一个对象
/// 业务禁止将IAssetPreloadAsync强转为IAssetLoadAsync
///
///
internal sealed class AssetLoadAsync : IAssetLoadAsync, IAssetEventListenerSetter, IAssetPreloadAsync
{
private AsyncListenerOperation _operation;
private IAssetAsync _assetAsync;
private IAssetCacheHandle _cacheHandle;
private IAssetEventListener _eventListener;
IAssetEventListener IAssetEventListenerSetter.AssetEventListener { set => _eventListener = value; }
internal AssetLoadAsync(string addressableName, IAssetAsync assetAsync, IAssetCacheHandle handle)
{
AddressableName = addressableName;
_assetAsync = assetAsync;
_cacheHandle = handle;
if (assetAsync != null && assetAsync.IsCompleted == false)
{
assetAsync.On(OnAsyncCompleted);
}
}
private void OnAsyncCompleted(IAsync aAsync)
{
_operation.OnCompleted(this);
PreRelease();
}
private void PreRelease()
{
if (_operation.HaveListener)
return;
RemoveAll();
}
#region 接口实现
object IAsync.State
{
set
{
var assetAsync = _assetAsync;
if (assetAsync != null)
assetAsync.State = value;
}
get => _assetAsync?.State;
}
public Exception Exception => _assetAsync?.Exception;
public bool IsCompleted => _assetAsync?.IsCompleted ?? true;
///
/// 返回加载进度
/// async为空时默认加载完成
///
public float Progress => _assetAsync?.Progress ?? 1;
public string AddressableName { get; private set; }
public IAsync On(OnAsyncCompleted action)
{
if (action != null)
{
if (IsCompleted)
{
action.SaveInvoke(this);
PreRelease();
}
else
{
_operation.On(action);
}
}
return this;
}
public IAsync On(IAsyncListener listener, int order = 0)
{
if (listener == null) return this;
if (IsCompleted)
{
listener.SaveInvoke(this);
PreRelease();
return this;
}
_operation.On(listener, order);
return this;
}
public IAsync RemoveOn(OnAsyncCompleted action)
{
_operation.RemoveOn(action);
return this;
}
public IAsync RemoveOn(IAsyncListener listener)
{
_operation.RemoveOn(listener);
return this;
}
public IAsync RemoveAll()
{
//Log.Debug($"AssetLoadAsync RemoveAll Name:{AddressableName}");
if (!IsCompleted)
_assetAsync?.RemoveOn(OnAsyncCompleted);
_assetAsync = null;
_cacheHandle?.ReleaseAsync(this);
_cacheHandle = null;
_eventListener?.ReleaseAsync(this);
_eventListener = null;
_operation.Clear();
return this;
}
public TResult GetResult()
{
TResult result = default;
var addressableName = AddressableName;
if (_cacheHandle != null)
result = _cacheHandle.GetAssetFromCache(addressableName).Convert(addressableName);
//先 Convert, 保证getResultCallback和最终返回的是同一个对象
if (result != null)
{
_eventListener?.OnGetResult(addressableName, result);
}
return result;
}
#endregion
#if UNITY_EDITOR
public override string ToString()
{
return $"AssetLoadAsync Type:{typeof(TResult)} Name:{AddressableName} IsCompleted:{IsCompleted}";
}
#endif
}
}