BITFALL/Assets/Artists/Scripts/Player/CharacterControllerPro/PlayerCharacterControllerSt...

83 lines
2.5 KiB
C#

using System;
using System.Collections;
using System.Collections.Generic;
using BITFALL.Player.Movement;
using BITFALL.Props;
using BITKit;
using BITKit.Entities;
using Cysharp.Threading.Tasks;
using UnityEditor.UI;
using UnityEngine;
namespace BITFALL.Entities.Player.Movement
{
[CustomType(typeof(IStunObject))]
public class PlayerCharacterControllerStun : EntityBehavior,IStunObject
{
[Inject] private IEntityMovement _movement;
[SerializeField] private float breatheFrequency = 0.5f; // 呼吸的频率,值越大呼吸越快
[SerializeField] private float breatheAmplitude = 0.005f; // 呼吸的幅度,即准星上下移动的最大距离
[SerializeField] private LocationAdditive viewAdditive;
[SerializeField] private LocationAdditive inverseAdditive;
private readonly ValidHandle allow = new();
public float Weight { get;private set; }
public event Action<float> OnWeightChanged;
private readonly IntervalUpdate _resetInterval = new(1f);
public async void Stun(float distance, float duration)
{
Weight = 1;
OnWeightChanged?.Invoke(Weight);
_resetInterval.AddDelay(duration);
var id = Guid.NewGuid().GetHashCode();
_movement.ExecuteCommand(new PlayerPauseRunCommand(id,true));
_movement.ExecuteCommand(new PlayerLimitMoveSpeedCommand()
{
Id = id,
Speed =1f,
Limit = true,
});
_movement.ExecuteCommand(new PlayerLimitSensitivityCommand()
{
Id = id,
Sensitivity = 0.1f,
Limit = true,
});
allow.AddElement(id);
await UniTask.Delay(TimeSpan.FromSeconds(duration));
if(destroyCancellationToken.IsCancellationRequested) return;
_movement.ExecuteCommand(new PlayerPauseRunCommand(id,false));
_movement.ExecuteCommand(new PlayerLimitMoveSpeedCommand()
{
Id = id,
Limit = false,
});
_movement.ExecuteCommand(new PlayerLimitSensitivityCommand()
{
Id = id,
Limit = false,
});
allow.RemoveElement(id);
}
public override void OnUpdate(float deltaTime)
{
if (Weight <= 0) return;
if(_resetInterval.AllowUpdateWithoutReset)
{
Weight = Mathf.Clamp(Weight -= deltaTime, 0, 1);
OnWeightChanged?.Invoke(Weight);
}
var breatheOffset = Mathf.Sin(Time.time * breatheFrequency) * breatheAmplitude;
breatheOffset *= Weight;
if (viewAdditive)
viewAdditive.AddRotation(Quaternion.Euler(breatheOffset, breatheOffset, 0), nameof(IStunObject));
if (inverseAdditive)
inverseAdditive.AddRotation(Quaternion.Euler(-breatheOffset, -breatheOffset, 0), nameof(IStunObject));
}
}
}