1
This commit is contained in:
@@ -40,13 +40,13 @@ namespace BITFALL.Entities.Armor
|
||||
public override void OnAwake()
|
||||
{
|
||||
base.OnAwake();
|
||||
_health.OnDamage += OnDamage;
|
||||
_inventory.OnUsed += OnUsed;
|
||||
|
||||
_health.OnDamageFactory += OnDamageFactory;
|
||||
_inventory.OnUsedItem += OnUsedItem;
|
||||
|
||||
_equipmentContainer.OnEquip += OnEquip;
|
||||
_equipmentContainer.OnDeEquip += OnDeEquip;
|
||||
|
||||
_playerEquipSelector.OnTryEquip += OnTryEquip;
|
||||
_playerEquipSelector.TryEquipFactory += OnTryEquip;
|
||||
}
|
||||
|
||||
private bool OnTryEquip(IBasicItem arg)
|
||||
@@ -81,7 +81,7 @@ namespace BITFALL.Entities.Armor
|
||||
OnEquipArmor?.Invoke(arg2);
|
||||
}
|
||||
|
||||
private void OnUsed(IBasicItem obj)
|
||||
private void OnUsedItem(IBasicItem obj)
|
||||
{
|
||||
if (_currentArmor?.GetAssetable() is not AssetableArmor assetableArmor) return;
|
||||
if (obj.GetAssetable().TryGetProperty<AddArmor>(out var addArmor))
|
||||
@@ -89,7 +89,7 @@ namespace BITFALL.Entities.Armor
|
||||
Armor = Mathf.Clamp(Armor + addArmor.Armor, 0, assetableArmor.MaxArmor);
|
||||
}
|
||||
}
|
||||
private int OnDamage(DamageMessage arg1, int damage)
|
||||
private int OnDamageFactory(DamageMessage arg1, int damage)
|
||||
{
|
||||
if (_currentArmor is null) return damage;
|
||||
if (Armor is 0) return damage;
|
||||
|
@@ -13,8 +13,7 @@
|
||||
"GUID:9e24947de15b9834991c9d8411ea37cf",
|
||||
"GUID:84651a3751eca9349aac36a66bba901b",
|
||||
"GUID:f6155d9ae143f3949ac54e8355593d6c",
|
||||
"GUID:b355af20142c0c541ba9588ab1d0f64e",
|
||||
"GUID:ef0bb553b58b90b488bdbe8672e3be0b"
|
||||
"GUID:48ef04d98836e2640bf90b524bdff904"
|
||||
],
|
||||
"includePlatforms": [],
|
||||
"excludePlatforms": [],
|
||||
|
@@ -7,7 +7,8 @@
|
||||
"GUID:7efac18f239530141802fb139776f333",
|
||||
"GUID:d525ad6bd40672747bde77962f1c401e",
|
||||
"GUID:49b49c76ee64f6b41bf28ef951cb0e50",
|
||||
"GUID:f51ebe6a0ceec4240a699833d6309b23"
|
||||
"GUID:f51ebe6a0ceec4240a699833d6309b23",
|
||||
"GUID:bea3628e8b592ae47ade218cb9ec98db"
|
||||
],
|
||||
"includePlatforms": [],
|
||||
"excludePlatforms": [],
|
||||
|
@@ -1,16 +1,21 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
using BITKit;
|
||||
using BITKit.Animations;
|
||||
using BITKit.Entities;
|
||||
using BITKit.Physics;
|
||||
|
||||
namespace BITFALL.Entites
|
||||
{
|
||||
public class EntityProxyCharacter : EntityComponent
|
||||
{
|
||||
public UnityAnimator animator;
|
||||
[SerializeField] private UnityAnimator animator;
|
||||
[SerializeReference, SubclassSelector] public References _getDamage;
|
||||
[SerializeField] private Optional<Collider> aliveCollider = new();
|
||||
[SerializeField] private bool allowAnimatorParameter;
|
||||
[SerializeField] private Optional<PhysicsBasedAnimation> physicsBasedAnimation = new();
|
||||
[Inject]
|
||||
private IHealth _health;
|
||||
public override void OnStart()
|
||||
@@ -20,10 +25,27 @@ namespace BITFALL.Entites
|
||||
_health.OnSetHealthPoint += OnSetHP;
|
||||
}
|
||||
|
||||
private void FixedUpdate()
|
||||
{
|
||||
if (physicsBasedAnimation.Allow)
|
||||
{
|
||||
physicsBasedAnimation.Value.Blend =
|
||||
Mathf.MoveTowards(
|
||||
physicsBasedAnimation.Value.Blend,
|
||||
_health.IsAlive ? 1 : 0,
|
||||
Time.fixedTime
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
public void OnSetAlive(bool alive)
|
||||
{
|
||||
if (aliveCollider.Allow)
|
||||
aliveCollider.Value.enabled = alive;
|
||||
if (allowAnimatorParameter && animator is not null)
|
||||
{
|
||||
animator.animator.SetBool(nameof(IHealth.IsAlive), alive);
|
||||
}
|
||||
}
|
||||
|
||||
public void OnSetHP(int hp)
|
||||
|
@@ -15,7 +15,7 @@ namespace BITFALL
|
||||
/// </summary>
|
||||
public interface IPlayerEquipSelector
|
||||
{
|
||||
event Func<IBasicItem,bool> OnTryEquip;
|
||||
event Func<IBasicItem,bool> TryEquipFactory;
|
||||
event Action<IDictionary<int, IBasicItem>> OnUpdateEquip;
|
||||
bool TryDeEquip(IBasicItem item);
|
||||
bool Cancel();
|
||||
|
@@ -1,3 +1,4 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using BITKit;
|
||||
@@ -7,6 +8,12 @@ namespace BITFALL.Entities.Inventory
|
||||
{
|
||||
public interface IEntityInventory : IBasicItemContainer
|
||||
{
|
||||
bool UseItem(IBasicItem item);
|
||||
/// <summary>
|
||||
/// 已使用Item的回调
|
||||
/// </summary>
|
||||
event Action<IBasicItem> OnUsedItem;
|
||||
bool TryUseItem(IBasicItem item);
|
||||
event Func<IBasicItem,bool> TryUseItemFactory;
|
||||
void UseItem(IBasicItem item);
|
||||
}
|
||||
}
|
||||
|
@@ -17,7 +17,8 @@
|
||||
"GUID:ef0bb553b58b90b488bdbe8672e3be0b",
|
||||
"GUID:f6155d9ae143f3949ac54e8355593d6c",
|
||||
"GUID:d9ed46adfa0436d42b5f66480c967c74",
|
||||
"GUID:f51ebe6a0ceec4240a699833d6309b23"
|
||||
"GUID:f51ebe6a0ceec4240a699833d6309b23",
|
||||
"GUID:48ef04d98836e2640bf90b524bdff904"
|
||||
],
|
||||
"includePlatforms": [],
|
||||
"excludePlatforms": [],
|
||||
|
@@ -11,6 +11,7 @@ using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using BITFALL.Entities;
|
||||
using BITFALL.Entities.Improvised;
|
||||
using BITFALL.Entities.Inventory;
|
||||
using BITFALL.Player.Inventory;
|
||||
using BITKit.Entities.Player;
|
||||
using Cysharp.Threading.Tasks;
|
||||
@@ -27,13 +28,11 @@ namespace BITFALL.Entities.Equipment
|
||||
[Header(Constant.Header.InternalVariables)]
|
||||
private readonly Dictionary<int, IBasicItem> equips=new();
|
||||
|
||||
public event Func<IBasicItem, bool> OnTryEquip;
|
||||
public event Func<IBasicItem, bool> TryEquipFactory;
|
||||
public event Action<IDictionary<int, IBasicItem>> OnUpdateEquip;
|
||||
|
||||
[Inject(true)]
|
||||
private IPlayerInventory _playerInventory;
|
||||
[Inject]
|
||||
private IBasicItemContainer _inventory;
|
||||
private IEntityInventory _inventory;
|
||||
[Inject(true)]
|
||||
private IKnockdown _knockdown;
|
||||
[Inject]
|
||||
@@ -44,6 +43,8 @@ namespace BITFALL.Entities.Equipment
|
||||
private IEntityEquipment _equipment;
|
||||
[Inject(true)]
|
||||
private ImprovisedServiceInterface _improvisedService;
|
||||
[Inject]
|
||||
private IEntityEquipmentContainer _equipmentContainer;
|
||||
|
||||
private readonly DoubleBuffer<IBasicItem> _cachedItem=new();
|
||||
|
||||
@@ -68,22 +69,17 @@ namespace BITFALL.Entities.Equipment
|
||||
_improvisedService.OnTryUnEquipImprovisedItem += OnTryUnEquipImprovisedItem;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public override void OnStart()
|
||||
{
|
||||
base.OnStart();
|
||||
|
||||
if (_playerInventory is not null)
|
||||
{
|
||||
_playerInventory.OnUseItem += TryExecute;
|
||||
_playerInventory.OnUseItemCustom += TryUseItemCustom;
|
||||
_inventory.OnUsed += OnUsed;
|
||||
_inventory.OnAdd += OnAdd;
|
||||
_inventory.OnRemove += OnRemove;
|
||||
}
|
||||
_inventory.TryUseItemFactory += TryEquip;
|
||||
_inventory.OnUsedItem += OnEquip;
|
||||
_inventory.OnAdd += OnAdd;
|
||||
_inventory.OnRemove += OnRemove;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
private bool OnTryUnEquipImprovisedItem(IBasicItem arg)
|
||||
{
|
||||
@@ -135,7 +131,7 @@ namespace BITFALL.Entities.Equipment
|
||||
public void OnQuaternary(InputAction.CallbackContext context)
|
||||
{
|
||||
if (context is not {interaction:PressInteraction ,performed:true}) return;
|
||||
Equip(4);
|
||||
Equip<EquipmentAsArmorPlate>();
|
||||
}
|
||||
public void OnHolster(InputAction.CallbackContext context)
|
||||
{
|
||||
@@ -153,7 +149,7 @@ namespace BITFALL.Entities.Equipment
|
||||
UpdateEquip();
|
||||
Equip(-1);
|
||||
}
|
||||
private bool TryExecute(IBasicItem value)
|
||||
private bool TryEquip(IBasicItem value)
|
||||
{
|
||||
if (_knockdown is not null && _knockdown.IsKnockdown) return false;
|
||||
var asset = value.GetAssetable();
|
||||
@@ -167,31 +163,21 @@ namespace BITFALL.Entities.Equipment
|
||||
UpdateEquip();
|
||||
_improvisedService?.TryUnEquipImprovised(out _);
|
||||
currentEquip = value;
|
||||
_inventory.UseItem(value);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
private bool TryUseItemCustom(IBasicItem value)
|
||||
{
|
||||
if (_knockdown is not null && _knockdown.IsKnockdown) return false;
|
||||
var asset = value.GetAssetable();
|
||||
if (_equipment.IsSupportItem(value) is false) return false;
|
||||
switch (asset)
|
||||
{
|
||||
case var _ when asset.TryGetProperty<EquipmentUseItem>(out _):
|
||||
if (OnTryEquip?.CastAsFunc().Any(x => x.Invoke(value)) is false) return false;
|
||||
_equipment.EntryEquip(value);
|
||||
_improvisedService?.TryUnEquipImprovised(out _);
|
||||
if (currentEquip is not null)
|
||||
{
|
||||
_cachedItem.Release(currentEquip);
|
||||
}
|
||||
currentEquip = value;
|
||||
return true;
|
||||
if (TryEquipFactory?.CastAsFunc().Any(x => x.Invoke(value)) is false) return false;
|
||||
_equipment.EntryEquip(value);
|
||||
_improvisedService?.TryUnEquipImprovised(out _);
|
||||
if (currentEquip is not null)
|
||||
{
|
||||
_cachedItem.Release(currentEquip);
|
||||
}
|
||||
currentEquip = value;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
public async void OnAdd(IBasicItem item)
|
||||
@@ -216,9 +202,9 @@ namespace BITFALL.Entities.Equipment
|
||||
{
|
||||
await UniTask.NextFrame();
|
||||
}
|
||||
if (_equipment.IsSupportItem(item))
|
||||
if (_equipment.IsSupportItem(item) && item.GetAssetable().TryGetProperty<EquipmentAsWeapon>(out _))
|
||||
{
|
||||
_playerInventory.TryUseItem(item);
|
||||
_inventory.TryUseItem(item);
|
||||
}
|
||||
}
|
||||
catch(OperationCanceledException){}
|
||||
@@ -227,17 +213,25 @@ namespace BITFALL.Entities.Equipment
|
||||
|
||||
public void Throw(InputAction.CallbackContext context)
|
||||
{
|
||||
if (context is not { interaction: HoldInteraction, performed: true }) return;
|
||||
if(currentEquip is null) return;
|
||||
if(equips.TryGetAny(x=>x.Value.AddressablePath == currentEquip.AddressablePath,out var pair))
|
||||
switch (context)
|
||||
{
|
||||
if (_inventory.DropOrSpawn(currentEquip))
|
||||
{
|
||||
equips.Remove(pair.Key);
|
||||
_equipment.EntryEquip((IBasicItem)null);
|
||||
currentEquip = null;
|
||||
UpdateEquip();
|
||||
}
|
||||
case { interaction: HoldInteraction, performed: true }:
|
||||
if (currentEquip is null) return;
|
||||
if (equips.TryGetAny(x => x.Value.AddressablePath == currentEquip.AddressablePath, out var pair))
|
||||
{
|
||||
if (_inventory.DropOrSpawn(currentEquip))
|
||||
{
|
||||
equips.Remove(pair.Key);
|
||||
_equipment.EntryEquip((IBasicItem)null);
|
||||
currentEquip = null;
|
||||
UpdateEquip();
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
case { interaction: TapInteraction, performed: true }:
|
||||
Equip<EquipmentAsThrow>();
|
||||
break;
|
||||
}
|
||||
}
|
||||
public void OnRemove(IBasicItem item)
|
||||
@@ -249,7 +243,7 @@ namespace BITFALL.Entities.Equipment
|
||||
|
||||
_blockList.Add(item.Id);
|
||||
}
|
||||
private void OnUsed(IBasicItem obj)
|
||||
private void OnEquip(IBasicItem obj)
|
||||
{
|
||||
_blockList.Remove(obj.Id);
|
||||
}
|
||||
@@ -297,5 +291,13 @@ namespace BITFALL.Entities.Equipment
|
||||
_equipment.EntryEquip(x);
|
||||
return true;
|
||||
}
|
||||
|
||||
private bool Equip<T>() where T : IEquipmentSlot
|
||||
{
|
||||
if (!_equipmentContainer.Equipment.TryGetAny(x => x.Key is T, out var item)) return false;
|
||||
//if (!_inventory.TryUseItem(item.Value)) return false;
|
||||
Equip(item.Value);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
@@ -15,7 +15,8 @@
|
||||
"GUID:d8b63aba1907145bea998dd612889d6b",
|
||||
"GUID:30cdc242b1ac6a944a460f4ab0b77b88",
|
||||
"GUID:7efac18f239530141802fb139776f333",
|
||||
"GUID:ef0bb553b58b90b488bdbe8672e3be0b"
|
||||
"GUID:ef0bb553b58b90b488bdbe8672e3be0b",
|
||||
"GUID:48ef04d98836e2640bf90b524bdff904"
|
||||
],
|
||||
"includePlatforms": [],
|
||||
"excludePlatforms": [],
|
||||
|
@@ -19,11 +19,12 @@ namespace BITKit.Entities
|
||||
public abstract class BITEquipBase<T> : StateBasedMonoBehaviour<T>, IEquipBase where T : IState
|
||||
{
|
||||
[Header(Constant.Header.Settings)]
|
||||
[SerializeField] protected AssetableEquip item;
|
||||
[SerializeField] protected AssetableItem item;
|
||||
|
||||
[Header(Constant.Header.Components)]
|
||||
public UnityAnimator animator;
|
||||
[SerializeField] private Renderer[] renderers;
|
||||
[SerializeField] protected Transform cameraTransform;
|
||||
|
||||
[Header(Constant.Header.Services)]
|
||||
[SerializeReference,SubclassSelector] protected IMeleeService meleeService;
|
||||
@@ -39,12 +40,12 @@ namespace BITKit.Entities
|
||||
public virtual string AddressablePath => item.AddressablePath;
|
||||
protected virtual Vector3 meleeForce => Transform.forward;
|
||||
public bool IsEntered { get; set; }
|
||||
private Quaternion _initialCameraRotation;
|
||||
|
||||
public virtual void Entry()
|
||||
{
|
||||
AllowRendering.AddElement(this);
|
||||
animator.animator.enabled = true;
|
||||
animator.animator.Update(0);
|
||||
inputActionGroup.allowInput.AddElement(this);
|
||||
}
|
||||
public virtual UniTask EntryAsync()
|
||||
{
|
||||
@@ -58,18 +59,26 @@ namespace BITKit.Entities
|
||||
public virtual UniTask ExitAsync()
|
||||
{
|
||||
AllowRendering.RemoveElement(this);
|
||||
if (cameraTransform is not null)
|
||||
{
|
||||
cameraTransform.localPosition = default;
|
||||
cameraTransform.localRotation = _initialCameraRotation;
|
||||
}
|
||||
return UniTask.CompletedTask;
|
||||
}
|
||||
|
||||
public virtual void OnAwake()
|
||||
{
|
||||
AllowRendering.AddListener(x=>renderers.ForEach(y=>
|
||||
AllowRendering.AddListener(x => renderers.ForEach(y =>
|
||||
{
|
||||
y.enabled = x;
|
||||
animator.animator.enabled = x;
|
||||
animator.enabled = x;
|
||||
}));
|
||||
AllowRendering.Invoke();
|
||||
|
||||
if (cameraTransform is not null)
|
||||
_initialCameraRotation = cameraTransform.localRotation;
|
||||
Initialize();
|
||||
inputActionGroup.allowInput.Invoke();
|
||||
}
|
||||
|
||||
public virtual void OnDestroy()
|
||||
@@ -86,6 +95,7 @@ namespace BITKit.Entities
|
||||
public virtual void AnimationEvent(string eventName)
|
||||
{
|
||||
if (IsEntered is false) return;
|
||||
if (item is not AssetableEquip equip) return;
|
||||
switch (eventName)
|
||||
{
|
||||
case "Melee":
|
||||
@@ -94,9 +104,9 @@ namespace BITKit.Entities
|
||||
{
|
||||
PlayerId = Entity.Id,
|
||||
Position = Transform.position,
|
||||
Force = meleeForce * item.MeleeForce,
|
||||
Range = item.MeleeRange,
|
||||
Damage = item.MeleeDamage
|
||||
Force = meleeForce * equip.MeleeForce,
|
||||
Range = equip.MeleeRange,
|
||||
Damage = equip.MeleeDamage
|
||||
});
|
||||
break;
|
||||
case "HeavyAttack":
|
||||
@@ -104,9 +114,9 @@ namespace BITKit.Entities
|
||||
{
|
||||
PlayerId = Entity.Id,
|
||||
Position = Transform.position,
|
||||
Force = meleeForce * item.HeavyMeleeForce,
|
||||
Range = item.HeavyMeleeRange,
|
||||
Damage = item.HeavyMeleeDamage,
|
||||
Force = meleeForce * equip.HeavyMeleeForce,
|
||||
Range = equip.HeavyMeleeRange,
|
||||
Damage = equip.HeavyMeleeDamage,
|
||||
});
|
||||
break;
|
||||
}
|
||||
|
@@ -3,14 +3,17 @@ using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using BITFALL.Entities.Equipment;
|
||||
using BITFALL.Entities.Inventory;
|
||||
using BITFALL.Player.Inventory;
|
||||
using UnityEngine;
|
||||
using BITKit;
|
||||
using BITKit.Entities;
|
||||
using Unity.IO.LowLevel.Unsafe;
|
||||
using UnityEditor.Graphs;
|
||||
|
||||
namespace BITFALL
|
||||
{
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 玩家装备容器
|
||||
/// 支持,护甲,头盔和背包等
|
||||
@@ -18,9 +21,11 @@ namespace BITFALL
|
||||
[CustomType(typeof(IEntityEquipmentContainer))]
|
||||
public class EntityEquipmentContainer : EntityComponent, IEntityEquipmentContainer
|
||||
{
|
||||
private readonly Dictionary<IEquipmentSlot, IBasicItem> dictionary = new();
|
||||
[Inject]
|
||||
private IBasicItemContainer inventory;
|
||||
public IDictionary<IEquipmentSlot, IBasicItem> Equipment { get; } =
|
||||
new Dictionary<IEquipmentSlot, IBasicItem>();
|
||||
|
||||
[Inject] private IEntityInventory _inventory;
|
||||
|
||||
public override void OnAwake()
|
||||
{
|
||||
var health = entity.Get<IHealth>();
|
||||
@@ -30,20 +35,19 @@ namespace BITFALL
|
||||
private void OnSetAlive(bool obj)
|
||||
{
|
||||
if (obj) return;
|
||||
foreach (var x in dictionary.ToArray())
|
||||
foreach (var x in Equipment.ToArray())
|
||||
{
|
||||
OnDeEquip?.Invoke(x.Key, x.Value);
|
||||
inventory.Add(x.Value);
|
||||
_inventory.Add(x.Value);
|
||||
}
|
||||
dictionary.Clear();
|
||||
|
||||
Equipment.Clear();
|
||||
}
|
||||
|
||||
public override void OnStart()
|
||||
{
|
||||
base.OnStart();
|
||||
inventory = entity.Get<IBasicItemContainer>();
|
||||
var playerInventory = entity.Get<IPlayerInventory>();
|
||||
playerInventory.OnUseItem += TryExecute;
|
||||
_inventory.TryUseItemFactory += TryExecute;
|
||||
}
|
||||
|
||||
public Action<IEquipmentSlot, IBasicItem> OnEquip { get; set; }
|
||||
@@ -51,49 +55,66 @@ namespace BITFALL
|
||||
|
||||
public bool TryDeEquip<T>(T slot) where T : IEquipmentSlot
|
||||
{
|
||||
if (!dictionary.TryGetValue(slot, out var equipable)) return false;
|
||||
if (inventory.Add(equipable))
|
||||
if (!Equipment.TryGetAny(x => x.Key.GetType().IsInstanceOfType(slot), out var pair)) return false;
|
||||
if (_inventory.Add(pair.Value))
|
||||
{
|
||||
DeEquip(slot, equipable);
|
||||
DeEquip(slot, pair.Value);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public bool TryUseEquip<T>(T slot) where T : IEquipmentSlot
|
||||
{
|
||||
return TryUseEquip(System.Activator.CreateInstance(typeof(T)) as IEquipmentSlot);
|
||||
}
|
||||
|
||||
public bool TryUseEquip(IEquipmentSlot slot)
|
||||
{
|
||||
if (!Equipment.TryGetAny(x => x.Key.GetType().IsInstanceOfType(slot), out var pair)) return false;
|
||||
if (!Equipment.TryRemove(pair.Key)) return false;
|
||||
OnDeEquip?.Invoke(pair.Key, pair.Value);
|
||||
_inventory.UseItem(pair.Value);
|
||||
|
||||
if (_inventory.TryGetItem(x => x.AddressablePath == pair.Value.AddressablePath, out var item))
|
||||
{
|
||||
Equip(pair.Key, item);
|
||||
_inventory.Remove(item);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
private bool Equip(IEquipmentSlot slot, IBasicItem item)
|
||||
{
|
||||
dictionary.Add(slot, item);
|
||||
if (Equipment.TryAdd(slot, item) is false) return false;
|
||||
OnEquip?.Invoke(slot, item);
|
||||
return true;
|
||||
}
|
||||
|
||||
private bool DeEquip(IEquipmentSlot slot, IBasicItem item)
|
||||
{
|
||||
dictionary.Remove(slot);
|
||||
if (Equipment.TryRemove(slot) is false) return false;
|
||||
OnDeEquip?.Invoke(slot, item);
|
||||
return true;
|
||||
}
|
||||
|
||||
public int Priority => 0;
|
||||
|
||||
public bool TryExecute(IBasicItem value)
|
||||
{
|
||||
var asset = value.GetAssetable();
|
||||
//尝试获取可装备信息
|
||||
if (!asset.TryGetProperty<EquipmentAsSlot>(out var equipable)) return false;
|
||||
if (!asset.TryGetProperty<EquipmentAsSlot>(out var equipmentAsSlot)) return false;
|
||||
//已装备物品
|
||||
if (dictionary.TryGetValue(equipable.slot, out var equipedItem))
|
||||
if (Equipment.TryGetValue(equipmentAsSlot.slot, out _))
|
||||
{
|
||||
//尝试将装配放回背包
|
||||
if (inventory.Add(equipedItem))
|
||||
{
|
||||
//移除已装备物品
|
||||
DeEquip(equipable.slot, value);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
//从库存中移除物品
|
||||
if (inventory.Remove(value))
|
||||
{
|
||||
//装配物品
|
||||
Equip(equipable.slot, value);
|
||||
}
|
||||
return false;
|
||||
//装配物品
|
||||
Equip(equipmentAsSlot.slot, value);
|
||||
_inventory.Remove(value);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -16,7 +16,7 @@ namespace BITFALL
|
||||
{
|
||||
[CustomType(typeof(IEntityInventory))]
|
||||
[CustomType(typeof(IBasicItemContainer))]
|
||||
public abstract class EntityInventory : EntityComponent, IEntityInventory
|
||||
public abstract class EntityInventory : EntityComponent, IEntityInventory,IBasicItemContainer
|
||||
{
|
||||
/// <summary>
|
||||
/// 数据字典
|
||||
@@ -41,20 +41,30 @@ namespace BITFALL
|
||||
public event Func<IBasicItem, bool> DropFactory;
|
||||
// 回调
|
||||
public event Action<IBasicItem> OnAdd;
|
||||
public event Action<IBasicItem> OnUsed;
|
||||
public event Action<IBasicItem> OnUsedItem;
|
||||
public event Action<IBasicItem> OnRemove;
|
||||
public event Func<IBasicItem, bool> TryUseItemFactory;
|
||||
public event Action<IBasicItem> OnSet;
|
||||
public event Action<IBasicItem> OnDrop;
|
||||
public event Action<IBasicItemContainer> OnRebuild;
|
||||
public bool UseItem(IBasicItem item)
|
||||
public bool Clear(int id)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public bool TryUseItem(IBasicItem item)
|
||||
{
|
||||
if (dictionary.ContainsKey(item.Id) is false)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
dictionary.Remove(item.Id);
|
||||
OnUsed?.Invoke(item);
|
||||
return true;
|
||||
return TryUseItemFactory is not null && TryUseItemFactory.CastAsFunc().Any(x => x.Invoke(item));
|
||||
}
|
||||
|
||||
public void UseItem(IBasicItem item)
|
||||
{
|
||||
OnUsedItem?.Invoke(item);
|
||||
dictionary.TryRemove(item.Id);
|
||||
}
|
||||
|
||||
[Inject]
|
||||
|
@@ -1,5 +1,6 @@
|
||||
using System;
|
||||
using BITFALL.Entities.Equipment;
|
||||
using BITFALL.Entities.Inventory;
|
||||
using UnityEngine;
|
||||
using BITKit;
|
||||
using BITKit.Entities;
|
||||
@@ -17,20 +18,30 @@ namespace BITFALL
|
||||
public double currentWeight;
|
||||
[Header(Constant.Header.Settings)]
|
||||
public double maxWeight =8;
|
||||
|
||||
[Header(Constant.Header.InternalVariables)]
|
||||
private IBasicItemContainer container;
|
||||
[Inject]
|
||||
private IBasicItemContainer _container;
|
||||
[Inject(true)]
|
||||
private IEntityInventory _inventory;
|
||||
[Inject(true)]
|
||||
private IEntityEquipmentContainer playerEquipContainer;
|
||||
public override void OnStart()
|
||||
{
|
||||
base.OnStart();
|
||||
container = entity.Get<IBasicItemContainer>();
|
||||
container.AddFactory += AddFactory;
|
||||
container.OnAdd += OnAdd;
|
||||
container.OnUsed += OnRemove;
|
||||
container.OnRemove += OnRemove;
|
||||
_container.AddFactory += AddFactory;
|
||||
_container.OnAdd += OnAdd;
|
||||
_container.OnRemove += OnRemove;
|
||||
|
||||
var playerEquipContainer = entity.Get<IEntityEquipmentContainer>();
|
||||
playerEquipContainer.OnEquip += OnEquip;
|
||||
playerEquipContainer.OnDeEquip += DeEquip;
|
||||
if (_inventory is not null)
|
||||
{
|
||||
_inventory.OnUsedItem += OnRemove;
|
||||
}
|
||||
|
||||
if (playerEquipContainer is not null)
|
||||
{
|
||||
playerEquipContainer.OnEquip += OnEquip;
|
||||
playerEquipContainer.OnDeEquip += DeEquip;
|
||||
}
|
||||
}
|
||||
|
||||
private bool AddFactory(IBasicItem item)
|
||||
|
@@ -1,98 +1,99 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using BITFALL.Player.Inventory;
|
||||
using UnityEngine;
|
||||
using BITKit;
|
||||
using BITKit.Entities;
|
||||
|
||||
namespace BITFALL
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// 玩家装备容器
|
||||
/// 支持,护甲,头盔和背包等
|
||||
/// </summary>
|
||||
[CustomType(typeof(IPlayerEquipContainer))]
|
||||
public class PlayerEquipContainer : EntityComponent, IPlayerEquipContainer
|
||||
{
|
||||
private readonly Dictionary<IEquipmentSlot, IBasicItem> dictionary = new();
|
||||
[Inject]
|
||||
private IBasicItemContainer inventory;
|
||||
public override void OnAwake()
|
||||
{
|
||||
var health = entity.Get<IHealth>();
|
||||
health.OnSetAlive += OnSetAlive;
|
||||
}
|
||||
|
||||
private void OnSetAlive(bool obj)
|
||||
{
|
||||
if (obj) return;
|
||||
foreach (var x in dictionary.ToArray())
|
||||
{
|
||||
OnDeEquip?.Invoke(x.Key, x.Value);
|
||||
inventory.Add(x.Value);
|
||||
}
|
||||
dictionary.Clear();
|
||||
}
|
||||
|
||||
public override void OnStart()
|
||||
{
|
||||
base.OnStart();
|
||||
inventory = entity.Get<IBasicItemContainer>();
|
||||
var playerInventory = entity.Get<IPlayerInventory>();
|
||||
playerInventory.OnUseItem += TryExecute;
|
||||
}
|
||||
|
||||
public Action<IEquipmentSlot, IBasicItem> OnEquip { get; set; }
|
||||
public Action<IEquipmentSlot, IBasicItem> OnDeEquip { get; set; }
|
||||
|
||||
public bool TryDeEquip<T>(T slot) where T : IEquipmentSlot
|
||||
{
|
||||
if (!dictionary.TryGetValue(slot, out var equipable)) return false;
|
||||
if (inventory.Add(equipable))
|
||||
{
|
||||
DeEquip(slot, equipable);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
private bool Equip(IEquipmentSlot slot, IBasicItem item)
|
||||
{
|
||||
dictionary.Add(slot, item);
|
||||
OnEquip?.Invoke(slot, item);
|
||||
return true;
|
||||
}
|
||||
private bool DeEquip(IEquipmentSlot slot, IBasicItem item)
|
||||
{
|
||||
dictionary.Remove(slot);
|
||||
OnDeEquip?.Invoke(slot, item);
|
||||
return true;
|
||||
}
|
||||
public int Priority => 0;
|
||||
|
||||
public bool TryExecute(IBasicItem value)
|
||||
{
|
||||
var asset = value.GetAssetable();
|
||||
//尝试获取可装备信息
|
||||
if (!asset.TryGetProperty<EquipmentAsSlot>(out var equipable)) return false;
|
||||
//已装备物品
|
||||
if (dictionary.TryGetValue(equipable.slot, out var equipedItem))
|
||||
{
|
||||
//尝试将装配放回背包
|
||||
if (inventory.Add(equipedItem))
|
||||
{
|
||||
//移除已装备物品
|
||||
DeEquip(equipable.slot, value);
|
||||
}
|
||||
}
|
||||
//从库存中移除物品
|
||||
if (inventory.Remove(value))
|
||||
{
|
||||
//装配物品
|
||||
Equip(equipable.slot, value);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
// using System;
|
||||
// using System.Collections;
|
||||
// using System.Collections.Generic;
|
||||
// using System.Linq;
|
||||
// using BITFALL.Entities.Equipment;
|
||||
// using BITFALL.Player.Inventory;
|
||||
// using UnityEngine;
|
||||
// using BITKit;
|
||||
// using BITKit.Entities;
|
||||
//
|
||||
// namespace BITFALL
|
||||
// {
|
||||
//
|
||||
// /// <summary>
|
||||
// /// 玩家装备容器
|
||||
// /// 支持,护甲,头盔和背包等
|
||||
// /// </summary>
|
||||
// [CustomType(typeof(IEntityEquipmentContainer))]
|
||||
// public class PlayerEquipContainer : EntityComponent, IEntityEquipmentContainer
|
||||
// {
|
||||
// private Dictionary<IEquipmentSlot, IBasicItem> Equipment = new();
|
||||
// [Inject]
|
||||
// private IBasicItemContainer inventory;
|
||||
// public override void OnAwake()
|
||||
// {
|
||||
// var health = entity.Get<IHealth>();
|
||||
// health.OnSetAlive += OnSetAlive;
|
||||
// }
|
||||
//
|
||||
// private void OnSetAlive(bool obj)
|
||||
// {
|
||||
// if (obj) return;
|
||||
// foreach (var x in Equipment.ToArray())
|
||||
// {
|
||||
// OnDeEquip?.Invoke(x.Key, x.Value);
|
||||
// inventory.Add(x.Value);
|
||||
// }
|
||||
// Equipment.Clear();
|
||||
// }
|
||||
//
|
||||
// public override void OnStart()
|
||||
// {
|
||||
// base.OnStart();
|
||||
// inventory = entity.Get<IBasicItemContainer>();
|
||||
// var playerInventory = entity.Get<IPlayerInventory>();
|
||||
// playerInventory.OnUseItem += TryExecute;
|
||||
// }
|
||||
//
|
||||
// public Action<IEquipmentSlot, IBasicItem> OnEquip { get; set; }
|
||||
// public Action<IEquipmentSlot, IBasicItem> OnDeEquip { get; set; }
|
||||
//
|
||||
// public bool TryDeEquip<T>(T slot) where T : IEquipmentSlot
|
||||
// {
|
||||
// if (!Equipment.TryGetValue(slot, out var equipable)) return false;
|
||||
// if (inventory.Add(equipable))
|
||||
// {
|
||||
// DeEquip(slot, equipable);
|
||||
// }
|
||||
// return false;
|
||||
// }
|
||||
// private bool Equip(IEquipmentSlot slot, IBasicItem item)
|
||||
// {
|
||||
// Equipment.Add(slot, item);
|
||||
// OnEquip?.Invoke(slot, item);
|
||||
// return true;
|
||||
// }
|
||||
// private bool DeEquip(IEquipmentSlot slot, IBasicItem item)
|
||||
// {
|
||||
// Equipment.Remove(slot);
|
||||
// OnDeEquip?.Invoke(slot, item);
|
||||
// return true;
|
||||
// }
|
||||
// public int Priority => 0;
|
||||
//
|
||||
// public bool TryExecute(IBasicItem value)
|
||||
// {
|
||||
// var asset = value.GetAssetable();
|
||||
// //尝试获取可装备信息
|
||||
// if (!asset.TryGetProperty<EquipmentAsSlot>(out var equipable)) return false;
|
||||
// //已装备物品
|
||||
// if (Equipment.TryGetValue(equipable.slot, out var equipedItem))
|
||||
// {
|
||||
// //尝试将装配放回背包
|
||||
// if (inventory.Add(equipedItem))
|
||||
// {
|
||||
// //移除已装备物品
|
||||
// DeEquip(equipable.slot, value);
|
||||
// }
|
||||
// }
|
||||
// //从库存中移除物品
|
||||
// if (inventory.Remove(value))
|
||||
// {
|
||||
// //装配物品
|
||||
// Equip(equipable.slot, value);
|
||||
// }
|
||||
// return false;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
@@ -39,43 +39,24 @@ namespace BITFALL
|
||||
}
|
||||
private void OnActive(ISelectable obj)
|
||||
{
|
||||
if (obj.Transform.TryGetComponentAny<WorldableItem>(out var item))
|
||||
if (!obj.Transform.TryGetComponentAny<WorldItem>(out var item)) return;
|
||||
var _item = item.Pick();
|
||||
if(item.GetAssetable().TryGetProperty<Improvisable>(out _))
|
||||
{
|
||||
var _item = item.Pick();
|
||||
if(item.GetAssetable().TryGetProperty<Improvisable>(out _))
|
||||
if (_knockdown is not null && _knockdown.IsKnockdown)
|
||||
{
|
||||
if (_knockdown is not null && _knockdown.IsKnockdown)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (_improvisedService.TryEquipImprovisedItem(_item))
|
||||
{
|
||||
item.Picked();
|
||||
}
|
||||
return;
|
||||
}
|
||||
else if (Add(_item))
|
||||
if (_improvisedService.TryEquipImprovisedItem(_item))
|
||||
{
|
||||
item.Picked();
|
||||
}
|
||||
}
|
||||
// else if(obj.Transform.TryGetComponentAny<IBasicItemContainer>(out _))
|
||||
// {
|
||||
//
|
||||
// }
|
||||
else if (Add(_item))
|
||||
{
|
||||
item.Picked();
|
||||
}
|
||||
}
|
||||
public bool TryUseItem(IBasicItem item)
|
||||
{
|
||||
if (OnUseItem is null) return false;
|
||||
return OnUseItem.CastAsFunc().Any(func => func.Invoke(item)) && UseItem(item);
|
||||
}
|
||||
|
||||
public event Func<IBasicItem, bool> OnUseItem;
|
||||
public bool TryUseItemCustom(IBasicItem item)
|
||||
{
|
||||
return OnUseItemCustom is not null && OnUseItemCustom.CastAsFunc().Any(func => func.Invoke(item));
|
||||
}
|
||||
|
||||
public event Func<IBasicItem, bool> OnUseItemCustom;
|
||||
}
|
||||
#if UNITY_EDITOR
|
||||
[UnityEditor.CustomEditor(typeof(PlayerInventory))]
|
||||
|
@@ -0,0 +1,84 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using BITFALL.Entities.Inventory;
|
||||
using BITFALL.Items;
|
||||
using BITKit;
|
||||
using BITKit.Entities;
|
||||
using BITKit.Selection;
|
||||
using UnityEngine;
|
||||
|
||||
namespace BITFALL.Player.Inventory
|
||||
{
|
||||
[CustomType(typeof(IEntitySwapItem))]
|
||||
public class PlayerInventorySwap : EntityComponent,IEntitySwapItem
|
||||
{
|
||||
public bool TryGetCurrentContainer(out IBasicItemContainer container)
|
||||
{
|
||||
container = _currentContainer;
|
||||
return container is not null;
|
||||
}
|
||||
|
||||
public event Func<IBasicItemContainer, bool> OpenSwapFactory;
|
||||
public event Action<IBasicItemContainer> OnSwapOpened;
|
||||
public event Action<IBasicItemContainer> OnSwapClosed;
|
||||
|
||||
[Inject] private ISelector _selector;
|
||||
[Inject] private IHealth _health;
|
||||
[Inject] private IEntityInventory _inventory;
|
||||
|
||||
private IBasicItemContainer _currentContainer;
|
||||
|
||||
public override void OnStart()
|
||||
{
|
||||
base.OnStart();
|
||||
_selector.OnActive += OnActive;
|
||||
_health.OnSetAlive += OnSetAlive;
|
||||
}
|
||||
|
||||
private void OnSetAlive(bool obj)
|
||||
{
|
||||
if (obj is false)
|
||||
{
|
||||
Close();
|
||||
}
|
||||
}
|
||||
|
||||
private void OnActive(ISelectable obj)
|
||||
{
|
||||
if (_currentContainer is not null) return;
|
||||
if (obj.Transform.TryGetComponent<IBasicItemContainer>(out var container) is false) return;
|
||||
Open(container);
|
||||
}
|
||||
|
||||
public bool Add(IBasicItem item)
|
||||
{
|
||||
if (_currentContainer is null) return false;
|
||||
return _inventory.Add(item) && _currentContainer.Remove(item);
|
||||
}
|
||||
public bool Remove(IBasicItem item)
|
||||
{
|
||||
if (_currentContainer is null) return false;
|
||||
return _currentContainer.Add(item) && _inventory.Remove(item);
|
||||
}
|
||||
|
||||
public bool Open(IBasicItemContainer container)
|
||||
{
|
||||
if (_currentContainer is not null) return false;
|
||||
if (OpenSwapFactory.CastAsFunc().Any(x=>x.Invoke(container) is false)) return false;
|
||||
_currentContainer = container;
|
||||
OnSwapOpened?.Invoke(_currentContainer);
|
||||
return true;
|
||||
}
|
||||
|
||||
public bool Close()
|
||||
{
|
||||
if (_currentContainer is null) return false;
|
||||
OnSwapClosed?.Invoke(_currentContainer);
|
||||
_currentContainer = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
@@ -1,8 +1,8 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using BITFALL.Entities.Inventory;
|
||||
using BITFALL.Items;
|
||||
using BITFALL.Player.Inventory;
|
||||
using BITKit;
|
||||
using BITKit.Entities;
|
||||
using UnityEditor;
|
||||
@@ -31,32 +31,30 @@ namespace BITFALL.Entities
|
||||
private IHealth _health;
|
||||
|
||||
[Inject]
|
||||
private IPlayerInventory _inventory;
|
||||
private IEntityInventory _inventory;
|
||||
|
||||
public override void OnStart()
|
||||
{
|
||||
_health.OnDamage += OnDamage;
|
||||
_health.OnDamageFactory += OnDamageFactory;
|
||||
_health.OnSetAlive += OnSetAlive;
|
||||
_health.OnSetHealthPoint += OnSetHealthPoint;
|
||||
|
||||
_inventory.OnUseItem += OnUseItem;
|
||||
_inventory.OnUsedItem += OnUseItem;
|
||||
}
|
||||
|
||||
private void OnSetHealthPoint(int obj)
|
||||
{
|
||||
if (obj > 0 && IsKnockdown && _health.IsAlive)
|
||||
{
|
||||
IsKnockdown = false;
|
||||
OnRevive?.Invoke();
|
||||
}
|
||||
}
|
||||
|
||||
private bool OnUseItem(IBasicItem arg)
|
||||
{
|
||||
if (IsKnockdown is false || arg.GetAssetable().TryGetProperty<PlayerReviveItem>(out var reviveItem) is false) return false;
|
||||
OnRevive?.Invoke();
|
||||
if (obj <= 0 || !IsKnockdown || !_health.IsAlive) return;
|
||||
IsKnockdown = false;
|
||||
return true;
|
||||
OnRevive?.Invoke();
|
||||
}
|
||||
private void OnUseItem(IBasicItem arg)
|
||||
{
|
||||
if (IsKnockdown is false ||
|
||||
arg.GetAssetable().TryGetProperty<PlayerReviveItem>(out var reviveItem) is false) return;
|
||||
IsKnockdown = false;
|
||||
OnRevive?.Invoke();
|
||||
|
||||
}
|
||||
|
||||
private void OnSetAlive(bool obj)
|
||||
@@ -64,7 +62,7 @@ namespace BITFALL.Entities
|
||||
IsKnockdown = false;
|
||||
}
|
||||
|
||||
private int OnDamage(DamageMessage arg,int currentDamage)
|
||||
private int OnDamageFactory(DamageMessage arg,int currentDamage)
|
||||
{
|
||||
if (IsKnockdown || _health.HealthPoint - currentDamage >=0 ) return currentDamage;
|
||||
IsKnockdown = true;
|
||||
|
@@ -1,27 +1,46 @@
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Xml;
|
||||
using BITFALL.Combat;
|
||||
using BITKit.Animations;
|
||||
using BITKit.Entities.Melee;
|
||||
using Unity.Mathematics;
|
||||
using UnityEngine;
|
||||
namespace BITKit.Entities
|
||||
{
|
||||
public interface IEntityMelee
|
||||
{
|
||||
void Execute();
|
||||
}
|
||||
public class EntityMelee : EntityComponent
|
||||
[CustomType(typeof(IMeleeCombat))]
|
||||
public class EntityMelee : EntityComponent,IMeleeCombat
|
||||
{
|
||||
[SerializeField] private UnityAnimator unityAnimator;
|
||||
|
||||
[Header(Constant.Header.Settings)]
|
||||
public int damage=50;
|
||||
public bool singleTarget;
|
||||
[SerializeField] private int damage=50;
|
||||
|
||||
|
||||
[SerializeReference, SubclassSelector, Inject(true)] private IMeleeService meleeService;
|
||||
[Inject(true)] private IEntityOverride entityOverride;
|
||||
public override void OnStart()
|
||||
{
|
||||
entity.AddListener<int>("Melee", Melee);
|
||||
entity.AddListener<string>(AIAction);
|
||||
|
||||
unityAnimator[0].onStateEnter += OnStateEnter;
|
||||
}
|
||||
|
||||
private void OnStateEnter(string obj)
|
||||
{
|
||||
if(entityOverride is null)return;
|
||||
if (obj is "HitStun")
|
||||
{
|
||||
entityOverride.AddOverride(this);
|
||||
}
|
||||
else
|
||||
{
|
||||
entityOverride.RemoveOverride(this);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void AIAction(string actionName)
|
||||
{
|
||||
switch (actionName)
|
||||
@@ -40,7 +59,14 @@ namespace BITKit.Entities
|
||||
Range = 1.6f,
|
||||
Damage = _damage,
|
||||
});
|
||||
entity.Invoke(Constant.Animation.Play, "Melee");
|
||||
unityAnimator.Play("Attack");
|
||||
//entity.Invoke(Constant.Animation.Play, "Melee");
|
||||
}
|
||||
|
||||
public void Execute() => Melee(damage);
|
||||
public void HitStun()
|
||||
{
|
||||
unityAnimator.Play("HitStun");
|
||||
}
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user