Files
2026-03-05 11:39:06 +08:00

240 lines
6.7 KiB
C#

using Fantasy.Assembly;
using Fantasy.Async;
using Fantasy.DataStructure.Collection;
using Fantasy.Entitas;
#pragma warning disable CS8604 // Possible null reference argument.
#pragma warning disable CS8600 // Converting null literal or possible null value to non-nullable type.
namespace Fantasy;
public class ItemUseComponent : Entity, IAssembly
{
private readonly Dictionary<int, IItemUse> _handlers = new Dictionary<int, IItemUse>();
private readonly OneToManyList<long, int> _assemblyHandlers = new OneToManyList<long, int>();
public override void Dispose()
{
base.Dispose();
_handlers.Clear();
_assemblyHandlers.Clear();
}
#region Assembly
public async FTask Initialize()
{
await AssemblySystem.Register(this);
}
public async FTask Load(long assemblyIdentity)
{
var tcs = FTask.Create(false);
Scene.ThreadSynchronizationContext.Post(() =>
{
InnerLoad(assemblyIdentity);
tcs.SetResult();
});
await tcs;
}
public async FTask ReLoad(long assemblyIdentity)
{
var tcs = FTask.Create(false);
Scene.ThreadSynchronizationContext.Post(() =>
{
InnerUnLoad(assemblyIdentity);
InnerLoad(assemblyIdentity);
tcs.SetResult();
});
await tcs;
}
public async FTask OnUnLoad(long assemblyIdentity)
{
var tcs = FTask.Create(false);
Scene.ThreadSynchronizationContext.Post(() =>
{
InnerUnLoad(assemblyIdentity);
tcs.SetResult();
});
await tcs;
}
private void InnerLoad(long assemblyIdentity)
{
foreach (var type in AssemblySystem.ForEach(assemblyIdentity,typeof(IItemUse)))
{
var customAttributes = type.GetCustomAttributes(typeof(ItemUseAttribute), false);
if (customAttributes.Length == 0)
{
Log.Warning($"type {type.FullName} Implemented the interface of IItemUse, requiring the implementation of ItemUseAttribute");
continue;
}
var instance = (IItemUse)Activator.CreateInstance(type);
foreach (ItemUseAttribute customAttribute in customAttributes)
{
var customAttributeType = (int)customAttribute.Type;
_handlers.Add(customAttributeType, instance);
_assemblyHandlers.Add(assemblyIdentity, customAttributeType);
}
}
}
private void InnerUnLoad(long assemblyIdentity)
{
if (!_assemblyHandlers.TryGetValue(assemblyIdentity, out var assemblyHandlers))
{
return;
}
foreach (var assemblyHandler in assemblyHandlers)
{
_handlers.Remove(assemblyHandler);
}
_assemblyHandlers.RemoveByKey(assemblyIdentity);
}
#endregion
public uint CanUse(Account account, ItemConfig config, ref int count)
{
var itemUseEffect = (ItemUseEffect)config.Effect;
if (itemUseEffect == ItemUseEffect.None)
{
Log.Error($"config.Effect is zero!");
return 1;
}
return CanUse(account, config, itemUseEffect, ref count);
}
public void Use(Account account, ItemConfig config, ref int count)
{
var itemUseEffect = (ItemUseEffect)config.Effect;
if (itemUseEffect == ItemUseEffect.None)
{
Log.Error($"config.Effect is zero!");
return;
}
if (!_handlers.TryGetValue((int)itemUseEffect, out var handler))
{
return;
}
handler.Use(account, config, ref count);
}
public uint UseHandler(Account account, ItemConfig config, ref int count)
{
var itemUseEffect = (ItemUseEffect)config.Effect;
if (itemUseEffect == ItemUseEffect.None)
{
Log.Error($"config.Effect is zero!");
return 1;
}
if (!_handlers.TryGetValue((int)itemUseEffect, out var handler))
{
return 0;
}
var canUse = handler.CanUse(account, config, ref count);
if (canUse != 0)
{
return canUse;
}
handler.Use(account, config, ref count);
return 0;
}
public uint CanUse(Account account, ItemConfig config, ItemUseEffect itemUseEffect, ref int count)
{
if (!_handlers.TryGetValue((int)itemUseEffect, out var handler))
{
return 0;
}
return handler.CanUse(account, config, ref count);
}
public void Use(Account account, ItemConfig config, ItemUseEffect itemUseEffect, ref int count)
{
if (!_handlers.TryGetValue((int)itemUseEffect, out var handler))
{
return;
}
handler.Use(account, config, ref count);
}
public uint UseHandler(Account account, ItemConfig config, ItemUseEffect itemUseEffect, ref int count)
{
if (!_handlers.TryGetValue((int)itemUseEffect, out var handler))
{
return 0;
}
var canUse = handler.CanUse(account, config, ref count);
if (canUse != 0)
{
return canUse;
}
handler.Use(account, config, ref count);
return 0;
}
}
// public static class ItemUseHelper
// {
// private static readonly Dictionary<int, IItemUse> Handlers = new Dictionary<int, IItemUse>();
//
// public static void Init()
// {
// Handlers.Add((int)ItemType.Drug, new ItemUse_Drug());
// Handlers.Add((int)ItemType.Equip , new ItemUse_Equip());
// }
//
// public static uint CanUse(Account account, ItemConfig config, ref int count)
// {
// if (!Handlers.TryGetValue((int)config.Type, out var handler))
// {
// return 0;
// }
//
// return handler.CanUse(account, config, ref count);
// }
//
// public static void Use(Account account, ItemConfig config, ref int count)
// {
// if (!Handlers.TryGetValue((int)config.Type, out var handler))
// {
// return;
// }
//
// handler.Use(account, config, ref count);
// }
//
// public static uint UseHandler(Account account, ItemConfig config, ref int count)
// {
// if (!Handlers.TryGetValue((int)config.Type, out var handler))
// {
// return 0;
// }
//
// var canUse = handler.CanUse(account, config, ref count);
// if (canUse != 0)
// {
// return canUse;
// }
//
// handler.CanUse(account, config, ref count);
// return 0;
// }
// }