Hello, I am having an issue with the application of forces upon my player character. Both the PlayerAttackState.TryApplyForce() and ForceReceiver.AddForce(Vector3 force) are being called at the appropriate times, I have verified this with debug logs, but no forces are being applied to my character.
I have set up the fields in the inspector, I receive no errors, but even when I crank the numbers up to 1000, nothing happens.
Edit:
Actually after further testing, it seems it is being applied but like WAY late… after all three animations have completed and the character is back at Idle.
My attack state
public class PlayerAttackState : PlayerBaseState
{
bool alreadyAppliedForce;
Attack attack;
float previousFrameTime;
public PlayerAttackState(PlayerStateMachine stateMachine, int attackIndex) : base(stateMachine)
{
attack = stateMachine.Attacks[attackIndex];
}
public override void Enter()
{
stateMachine.Animator.CrossFadeInFixedTime(attack.AnimationName, attack.TransitionDuration);
}
public override void Tick(float deltaTime)
{
Move(deltaTime);
FaceTarget();
float normalizedTime = GetNormalizedTime();
if (normalizedTime > previousFrameTime && normalizedTime < 1)
{
if(stateMachine.InputReader.isAttacking)
{
if (normalizedTime >= attack.ForceTime)
{
TryApplyForce();
}
TryComboAttack(normalizedTime);
}
}
else
{
//go back to prvious locomotion state
}
}
private void TryComboAttack(float normalizedTime)
{
if (attack.ComboStateIndex == -1)
{
return;
}
if (normalizedTime < attack.ComboAttackTime) { return; }
stateMachine.SwitchState(new PlayerAttackState(stateMachine, attack.ComboStateIndex));
}
private void TryApplyForce()
{
if (alreadyAppliedForce) return;
Debug.Log("Attack applying force");
stateMachine.ForceReciever.AddForce(stateMachine.transform.forward * attack.Force);
alreadyAppliedForce = true;
}
public override void Exit()
{
}
private float GetNormalizedTime()
{
AnimatorStateInfo currentStateInfo = stateMachine.Animator.GetCurrentAnimatorStateInfo(0);
AnimatorStateInfo nextStateInfo = stateMachine.Animator.GetNextAnimatorStateInfo(0);
if (stateMachine.Animator.IsInTransition(0) && nextStateInfo.IsTag("Attack"))
{
return nextStateInfo.normalizedTime;
}
else if (!stateMachine.Animator.IsInTransition(0) && currentStateInfo.IsTag("Attack"))
{
return currentStateInfo.normalizedTime;
}
else
{
return 0;
}
}
}
my Force Receiver
public class ForceReciever : MonoBehaviour
{
//Customizable Parameters:
[Title("Force Reciever", "Playing with physics...", TitleAlignments.Centered),BoxGroup("Force Receiver", centerLabel:true),SerializeField]
CharacterController controller;
[BoxGroup("Force Receiver"),SerializeField] float drag = 0.3f;
//Private fields:
private float verticalVelocity;
private Vector3 impactForce;
private Vector3 dampingVelocity;
//Public Properties:
public Vector3 movement => impactForce + Vector3.up * verticalVelocity;
private void Update()
{
if(verticalVelocity < 0f && controller.isGrounded)
{
verticalVelocity = Physics.gravity.y * Time.deltaTime;
}
else
{
verticalVelocity += Physics.gravity.y * Time.deltaTime;
}
impactForce = Vector3.SmoothDamp(impactForce, Vector3.zero, ref dampingVelocity, drag);
}
public void AddForce(Vector3 force)
{
Debug.Log("Reciever - Adding Force");
impactForce += force;
}
}