# How to achieve a stable hover in Unity

In the game that I am currently making the play character is supposed to hover off the ground. I had used the code from the Hover Car tutorial on the unity website however this causes a lot of fluctuation in height even when staying still on a flat surface. This is a problem because the game is supposed to be in the first person. Is there a way to make the player character more stable?

public float hoverForce = 65f;
public float hoverHeight = 3.5f;
public Rigidbody playerRB;
// Start is called before the first frame update
void Start()
{
playerRB = GetComponent<Rigidbody>();
}

// Update is called once per frame
void FixedUpdate()
{
Ray ray = new Ray(transform.position, -transform.up);
RaycastHit hit;

if (Physics.Raycast(ray, out hit, hoverHeight))
{
float proportionalHeight = (hoverHeight - hit.distance) / hoverHeight;
Vector3 appliedHoverForce = Vector3.up * proportionalHeight * hoverForce;
}
}


My first instinct would be to fake it. That is, create an invisible cube collider beneath the car that acts as a force field, then attach it to the car with a prismatic joint, which disallows movement between the two in the X and Z axes, and has a spring to try to keep the y-axis distance between the two constant, while allowing the car to sort of bounce up and down a bit.

Of course, if you don’t want to allow bouncing, you could just have the invisible collider be part of the same rigidbody as the car and it will just sit on top of the floor by that amount all the time.

On the other hand, if you want a bit of bounciness, there’s unfortunately no such thing as a prismatic joint in Unity, but as this answer explains, we can create one using a Configurable Joint.

I’m going to steal that answer and adjust it for this situation.

• Connected Body: assuming this joint is on the force field, set the connected body to be the car’s main body.

• Anchor: this is the position in the invisible collider’s local coordinates that should act as the attachment point. If it’s a 1-unit cube, set it to (0,1,0) to have the top of the force field attach to the car.

• Axis: this is the direction of movement, in your object's local coordinate space. Set to (0,1,0) so that it moves along the y-axis

• Auto-Configure Connected Anchor: check this. The joint will treat the force fields's placed position as the center of its movement range, allowing it to slide both up & down. If unchecked, we would need to configure the “Connected Anchor” manually

• X/Y/Z Motion: Y should be set to "Limited", and the others should be set to "Locked” to allow vertical movement while not letting the force field get out from under the car.

• Angular X/Y/Z Motion: We don’t want to allow any. Lock it up.

• Linear Limit: Set to 0. We don’t need the force field to freely change the distance between itself and the car.

• Linear Limit Spring: Set spring to the value you set in your script’s hoverForce to start with (looks like 65?), and adjust from there. Damping should also be non-zero so that the car doesn’t bounce and down indefinitely.

• Enable Collision: unchecked. The force field collider should be able to freely move into the car. However, you may want to use a special layer on the force field so that it doesn’t hit anything other than the floor, using the physics settings’ layer collision matrix.

If I'm not mistaken, increasing the drag should help. Maybe you can fake it only on the y axis, maybe even only when the velocity is going downward/upward. This code should work fine for drag, it's what I use (but increasing the rigidbody's drag might be all that's needed):

velocity = velocity * (1 - deltaTime * drag);