Detect if falling with custom gravity
So I'm working on a state machine with a BUNCH of states and I'm trying to determine when the player enters the falling state. I see a bunch of examples that follow something like this: yVel = rigidbody.velocity.y; //y velocity of rigidbody
if (yVel < 0) //if it's negative, that means it's falling down so set to true
isFalling = true;
That would likely work just fine IF i wasn't using a custom gravity script. The script applies a gravitational force to the rigidbody in the direction of gravity.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
[RequireComponent(typeof(Rigidbody))]
public class GravityBody : MonoBehaviour
{
//override the monobehavior's rigidbody getter
private new Rigidbody rigidbody;
[SerializeField]
private float m_Acceleration;
[SerializeField]
private Vector3 m_GravityDirection = new Vector3(0,1,0);
public bool useGravity = true;
public bool useFixedUpdate = true; //basically allows us to apply gravity in this script (true) or apply it in a class that uses it
public float jumpForce = 10;
/// <summary>The acceleration rate of gravity.</summary>
public float Acceleration
{
get
{
return m_Acceleration;
}
set
{
m_Acceleration = Mathf.Min(value, 0);
}
}
/// <summary>The direction of gravity.</summary>
public Vector3 GravityDirection
{
get
{
return m_GravityDirection;
}
set
{
m_GravityDirection = value.normalized;
}
}
///<summary>Force applied to body</summary>
public Vector3 Gravity
{
get
{
return -Acceleration * GravityDirection.normalized * rigidbody.mass;
}
}
public RigidbodyConstraints Constraints
{
get
{
return rigidbody != null ? rigidbody.constraints : RigidbodyConstraints.None;
}
set
{
rigidbody.constraints = value;
}
}
private void Start()
{
rigidbody = GetComponent<Rigidbody>();
rigidbody.useGravity = false;
}
private void FixedUpdate()
{
if (useFixedUpdate)
ApplyGravity();
//For testing purposes only
if (Input.GetButtonDown("Jump"))
rigidbody.AddForce(GravityDirection * jumpForce, ForceMode.Impulse);
}
public void InitGravityBody(Rigidbody rb)
{
rigidbody = rb;
useFixedUpdate = false;
}
public void ApplyGravity()
{
if (useGravity)
{
rigidbody.AddForce(Gravity);
}
}
//Editor
private void OnValidate()
{
m_Acceleration = Mathf.Max(m_Acceleration, 0f);
m_GravityDirection = m_GravityDirection.normalized;
}
}
This means that won't work in this regards. How do I check if my player is falling in this regards? Is there a cheat I can do to do what I described earlier?
Answer by Dorscherl · Dec 31, 2018 at 09:05 AM
So I figured it out with some help from the Infallible Code Discord (thanks apieceoffruit!) He told be about Vector3.dots and this is what we came up with
public bool CheckFalling(bool grounded = false)
{
var gravDir = useGravity ? GravityDirection : Vector3.zero;
FallingVelocity = Vector3.Dot(rigidbody.velocity, gravDir);
if (Mathf.Approximately(FallingVelocity, 0))
FallingVelocity = 0f;
if ( FallingVelocity < 0 && grounded == false)
{
return true;
}
return false;
}
So if the character is falling, the dot's value return negative and if the character is ascending it returns positive, all relative to the gravity's direction and velocity of the rigidbody
Your answer
Follow this Question
Related Questions
Using rb.velocity causes low gravity. 2 Answers
How can I make my player jump faster but not higher? 3 Answers
Can only go horizontally while walking on walls, and not vertically 0 Answers
If button is not pressed fall. 2 Answers
Slow falling speed on player (with RB), but all other objects are fine (checked scaling). 0 Answers