using System.Collections; using System.Collections.Generic; using UnityEngine; using BITKit; using BITKit.Entities; using System; using System.Linq; using UnityEngine.AddressableAssets; namespace BITFALL { public interface IEntityInventoryCallback { void OnAdd(IBasicItem item); void OnRemove(IBasicItem item); } public abstract class EntityInventory : EntityComponent, IBasicItemContainer { /// /// 数据字典 /// Dictionary dictionary = new(); /// /// 隐式接口实现 /// public int Id => entity.Id; /// /// 工厂方法 /// public event Func AddFactory; public event Func RemoveFactory; public event Func DropFactory; /// /// 回调 /// public event Action OnAdd; public event Action OnRemove; public event Action OnSet; public event Action OnDrop; public event Action OnRebuild; public virtual bool Add(IBasicItem item) { var pars = new object[] { item }; if (AddFactory != null) foreach (var x in AddFactory.GetInvocationList()) { if (x.Method.Invoke(x.Target, pars) is false) { return false; } } if (dictionary.TryAdd(item.Id, item)) { OnAdd?.Invoke(item); foreach (var x in entity.GetCallbacks()) { x.OnAdd(item); } return true; } else { return false; } } public virtual IBasicItem[] GetItems() => dictionary.Values.ToArray(); public virtual bool Remove(IBasicItem item) { return Remove(item.Id); } public virtual bool Remove(int id) { if (dictionary.TryGetValue(id, out var item)) { var pars = new object[] { item }; if(RemoveFactory is not null) foreach (var x in RemoveFactory.GetInvocationList()) { if (x.Method.Invoke(x.Target, pars) is false) { return false; } } dictionary.Remove(id); foreach (var x in entity.GetCallbacks()) { x.OnRemove(item); } OnRemove?.Invoke(item); return true; } else { return false; } } public virtual bool Remove(Func removeFactory) { bool isRemoved = false; foreach (var x in dictionary.Values.ToArray()) { if (removeFactory.Invoke(x)) { Remove(x.Id); isRemoved = true; } } return isRemoved; } public bool TryGetItem(Func func, out IBasicItem item) { return dictionary.Values.TryGetAny(func, out item); } public bool Drop(int Id) { if (dictionary.TryGetValue(Id, out var item)) { if (Remove(item)) { var pars = new object[] { item }; if (DropFactory is not null) foreach (var x in DropFactory.GetInvocationList()) { if (x.Method.Invoke(x.Target, pars) is false) { return false; } } var prefab = Addressables.LoadAssetAsync(item.AdressablePath).WaitForCompletion(); var instance = Instantiate(prefab.GetPrefab(), transform.position, transform.rotation); instance.CopyItemsFrom(item); return true; } } return false; } } }