214 lines
6.6 KiB
C#
214 lines
6.6 KiB
C#
|
using System.Collections;
|
|||
|
using System.Collections.Generic;
|
|||
|
using UnityEngine;
|
|||
|
using BITKit;
|
|||
|
using BITKit.Entities;
|
|||
|
using UnityEngine.UIElements;
|
|||
|
using UnityEngine.InputSystem;
|
|||
|
using UnityEngine.InputSystem.Interactions;
|
|||
|
using BITKit.Animations;
|
|||
|
using BITKit.StateMachine;
|
|||
|
using Net.Client;
|
|||
|
using Unity.Mathematics;
|
|||
|
using UnityEngine.VFX;
|
|||
|
using System.Diagnostics;
|
|||
|
using BITFALL.Guns;
|
|||
|
|
|||
|
namespace BITFALL
|
|||
|
{
|
|||
|
public interface IGunState : IState { }
|
|||
|
[System.Serializable]
|
|||
|
public abstract class GunState : IGunState
|
|||
|
{
|
|||
|
public BITGun root;
|
|||
|
public virtual void Initialize()
|
|||
|
{
|
|||
|
}
|
|||
|
|
|||
|
public virtual void OnStateEnter(IState old)
|
|||
|
{
|
|||
|
}
|
|||
|
|
|||
|
public virtual void OnStateExit(IState old, IState newState)
|
|||
|
{
|
|||
|
}
|
|||
|
|
|||
|
public virtual void OnStateUpdate()
|
|||
|
{
|
|||
|
}
|
|||
|
public virtual void OnMovementCallback(IMovementCallback callback) { }
|
|||
|
}
|
|||
|
[System.Serializable]
|
|||
|
public class GunStateMachine : MonoStateMachine<GunState> { }
|
|||
|
public class BITGun : BITEquipBase<GunState>
|
|||
|
{
|
|||
|
// 常数引用
|
|||
|
public const string _Movement = "Movement";
|
|||
|
public const string _Run = "Run";
|
|||
|
public const string _Aim = "Aim";
|
|||
|
public const string _Interactive = "Interactive";
|
|||
|
public const string _Equip = "Equip";
|
|||
|
public const string _Fire = "Fire";
|
|||
|
// 输入系统
|
|||
|
[Header(Constant.Header.Input)]
|
|||
|
public InputActionReference fireAction;
|
|||
|
public InputActionReference aimAction;
|
|||
|
public InputActionGroup actionGroup = new();
|
|||
|
// 状态机
|
|||
|
[Header(Constant.Header.State)]
|
|||
|
public GunStateMachine stateMachine;
|
|||
|
// 引用组件
|
|||
|
[Header(Constant.Header.Components)]
|
|||
|
public Renderer[] rendererComponents;
|
|||
|
public VFXPlayer vfxPlayer;
|
|||
|
// 引用预制体
|
|||
|
[Header(Constant.Header.Prefabs)]
|
|||
|
public AssetableGun assetable;
|
|||
|
[Header(Constant.Header.Reference)]
|
|||
|
// 内部变量
|
|||
|
[Header(Constant.Header.InternalVariables)]
|
|||
|
public ExpectState<bool> isFiring;
|
|||
|
public ExpectState<bool> isAiming;
|
|||
|
internal IntervalUpdate fireUpdater = new(0.32f);
|
|||
|
internal IntervalUpdate brustFireUpdater = new(0.1f);
|
|||
|
internal int burstFireCount;
|
|||
|
#region 接口实现
|
|||
|
public override string AddressablePath => assetable.AdressablePath;
|
|||
|
#endregion
|
|||
|
|
|||
|
|
|||
|
public override void Entry()
|
|||
|
{
|
|||
|
animator.animator.enabled = true;
|
|||
|
actionGroup.allowInput.SetElements(this, true);
|
|||
|
foreach (var x in rendererComponents)
|
|||
|
{
|
|||
|
x.enabled = true;
|
|||
|
}
|
|||
|
isFiring.Reset();
|
|||
|
stateMachine.StateMachine.TransitionState(stateMachine.states[0]);
|
|||
|
entity.AddListener<IMovementCallback>(OnMovementCallback);
|
|||
|
|
|||
|
fireUpdater.updateInterval = 1f / assetable.FireMode.FireRate;
|
|||
|
fireUpdater.Reset();
|
|||
|
|
|||
|
if(assetable.FireMode is BurstFireMode burstFireMode)
|
|||
|
{
|
|||
|
brustFireUpdater.updateInterval = burstFireMode.BurstFireInterval;
|
|||
|
brustFireUpdater.Reset();
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
}
|
|||
|
public override void Exit()
|
|||
|
{
|
|||
|
actionGroup.allowInput.SetElements(this, false);
|
|||
|
foreach (var x in rendererComponents)
|
|||
|
{
|
|||
|
x.enabled = false;
|
|||
|
}
|
|||
|
isFiring.Reset();
|
|||
|
animator.animator.enabled = false;
|
|||
|
entity.RemoveListener<IMovementCallback>(OnMovementCallback);
|
|||
|
}
|
|||
|
public override void OnAwake()
|
|||
|
{
|
|||
|
actionGroup.RegisterCallback(fireAction, OnFire);
|
|||
|
actionGroup.RegisterCallback(aimAction, OnAim);
|
|||
|
stateMachine.OnStart();
|
|||
|
}
|
|||
|
public override void OnStart()
|
|||
|
{
|
|||
|
base.OnStart();
|
|||
|
foreach (var x in rendererComponents)
|
|||
|
{
|
|||
|
x.enabled = false;
|
|||
|
}
|
|||
|
}
|
|||
|
public override void OnUpdate(float deltaTime)
|
|||
|
{
|
|||
|
stateMachine?.CurrentState?.OnStateUpdate();
|
|||
|
|
|||
|
if(assetable.FireMode is BurstFireMode && isFiring.being)
|
|||
|
{
|
|||
|
if(brustFireUpdater)
|
|||
|
{
|
|||
|
Fire();
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
public void Fire()
|
|||
|
{
|
|||
|
//如果启用了指针则不开火
|
|||
|
if(BITAppForUnity.AllowCursor)
|
|||
|
{
|
|||
|
return;
|
|||
|
}
|
|||
|
|
|||
|
//播放射击动画
|
|||
|
animator.Play(BITGun._Fire);
|
|||
|
|
|||
|
//调用IMovementCancenAction接口,取消奔跑或冲刺
|
|||
|
Entity.Invoke<IMovementCancelAction>(new CancelRunOrSprint());
|
|||
|
|
|||
|
//调用BulletManager生成子弹
|
|||
|
BulletService.Spawn(new()
|
|||
|
{
|
|||
|
initiator = entity.Id,
|
|||
|
pos = transform.position.Fix(),
|
|||
|
rot = transform.rotation,
|
|||
|
forward = transform.forward.Fix(),
|
|||
|
//pos=transform.position,
|
|||
|
//rot=transform.rotation,
|
|||
|
});
|
|||
|
|
|||
|
//播放枪口MuzzleFlash
|
|||
|
vfxPlayer.Excute();
|
|||
|
|
|||
|
//开火模式逻辑判断
|
|||
|
switch (assetable.FireMode)
|
|||
|
{
|
|||
|
case AutoFireMode:
|
|||
|
break;
|
|||
|
case SemiFireMode:
|
|||
|
//如果是半自动开火,则取消射击
|
|||
|
isFiring.Reset();
|
|||
|
break;
|
|||
|
case BurstFireMode burstFireMode:
|
|||
|
burstFireCount++;
|
|||
|
isFiring.being = true;
|
|||
|
if(burstFireCount > burstFireMode.BurstRound)
|
|||
|
{
|
|||
|
burstFireCount = 0;
|
|||
|
isFiring.Reset();
|
|||
|
}
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
void OnFire(InputAction.CallbackContext context)
|
|||
|
{
|
|||
|
switch (assetable.FireMode)
|
|||
|
{
|
|||
|
case AutoFireMode:
|
|||
|
case SemiFireMode:
|
|||
|
isFiring.shouldBe = context.ReadValueAsButton();
|
|||
|
break;
|
|||
|
case BurstFireMode:
|
|||
|
if(isFiring.being is false)
|
|||
|
isFiring.shouldBe = context.ReadValueAsButton();//|| context.action.triggered;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
void OnAim(InputAction.CallbackContext context)
|
|||
|
{
|
|||
|
isAiming.shouldBe = context.ReadValueAsButton();
|
|||
|
}
|
|||
|
void OnMovementCallback(IMovementCallback callback)
|
|||
|
{
|
|||
|
stateMachine?.CurrentState?.OnMovementCallback(callback);
|
|||
|
}
|
|||
|
}
|
|||
|
}
|