Hi there, i have this situation where i need to apply different forces to an object and then apply the gravity manually, but this gravity can’t factor in the drag nor the mass of the object, meaning i want it to fall down as if the drag was 0 while not being set to 0 in the drag properties
this is enough to ignore the mass, but now i need to do some calculation to account for the drag of the object
i know unity uses physx but i can’t find information anywhere how the drag calculation is done inside, even other poster formulas don’t seem to work, all i know 0 means no influence and infinity means total influence
That can’t be right, if drag is zero i get to divide by zero?
Just for the sake of it i actually tried it in a falling cube with a drag of 2 and this script next to a cube without any drag and the first one is slower
As of the first being slower as the second, of course it is slower. Higher drag means more air friction, means less force/slower acceleration. In the above formular, 1 means no drag at all by the way.
Just to be accurate, this is a solution for drag, but prolly not the solution PhysX uses. Tho, when modelling physics in games it is not about pure correctness but about it looking good.
In this case i need it to be 100% correct, i have other objects in the scene that use the normal physics and interact with this object, a linear drag from 0 to 1 doesn’t work for me because this a situational case where i need to ignore the drag when falling down (other axis should have drag) so the object must fall down just like any other object around it
I only need to know the formula of how the drag is being used inside the unity, i’m not even sure if this is a physx thing or not because i can’t find any explanation if i search for physx
I can’t believe this isn’t documented somewhere, not even in nvidia physx documentation, i just need to know exactly how drag is being used, not a general way like “The higher the drag the more the object slows down.” this doesn’t help me at all
I’m gonna explain in detail for future reference in case anyone needs it. I actually stumbled into the solution in a Cocos2D forum thread… … …yeah… o_o
This is how PhysX applies unity drag (or linearDamping as they call it) in pseudo code:
velocity = velocity * ( 1 - deltaTime * drag);
With that said, reverse engineering still took me a while, had to record values frame by frame and trial and error formulas till i got it right.
In my case i wanted to apply gravity without mass or drag so this is what i got now:
I’ve confirmed this still works the same in Unity 5.
If anyone else wants to play with the physics to get a better understanding for how it works, I have included a script that’s basically a re-implementation of rigidbody force and drag.
using UnityEngine;
using System.Collections;
public class TransformDropTest : MonoBehaviour {
public float mass = 1f;
public float drag;
public Vector3 acceleration = Vector3.zero;
public Vector3 gravity = Physics.gravity;
private int fixedUpdateTicks = -1;
public bool atRest = false;
void FixedUpdate() {
//Stop moving if we're at rest.
if (atRest)
return;
//Log debugging information
fixedUpdateTicks++;
Debug.Log (string.Format (
"Fixed Update Ticks: {0}\n" +
"Position: {1}\n" +
//To derive velocity from acceleration, we need to divide by time
"Velocity: {2}\n", fixedUpdateTicks, transform.position, acceleration.magnitude/Time.fixedDeltaTime));
//Add the force
AddForce (gravity, ForceMode.Acceleration);
//Apply Linear Damping (drag)
ApplyDrag ();
//Move the object
transform.position += acceleration;
}
void OnTriggerEnter() {
atRest = true;
}
public void AddForce(Vector3 force, ForceMode forceType) {
switch (forceType) {
case ForceMode.Force:
//Force mode moves an object according to it's mass
acceleration = acceleration + force * mass * Time.fixedDeltaTime * Time.fixedDeltaTime;
break;
case ForceMode.Acceleration:
//Acceleration ignores mass
acceleration = acceleration + force * Time.fixedDeltaTime * Time.fixedDeltaTime;
break;
default:
throw new UnityException("Force mode not supported!");
}
}
//Apply Linear Damping
public void ApplyDrag() {
acceleration = acceleration * (1 - Time.deltaTime * drag);
}
}
Sorry for bumping but I’m working on the same thing. I’m doing a racing game and I need something to limit the speed and thinking about applying drag. I’m looking for a formula that given the maximum Speed, the added drag will becomes larger with the velocity so that the acceleration cancel out and the car achieve stable max speed. Any help is appreciated.
Thank you very much and sorry.
The idea of knowing what unity is doing with drag was to intercept it to do something else. It’s not to replace it entirely, you can do it anyway by putting drag and gravity at 0. This way you can do whatever you want with the object.
I know I’m not giving you ideas in how you can use something to your needs but maybe this topic is not what you need.
It isn’t all lost tho, nickdas script above is a re-implementation of what unity does, you can use that as a base for what you want.
I implemented it but my object is still falling slowly, I’m not sure what I did wrong because I basically just copied the code:
void ApplyGravity() // called during FixedUpdate
{
float vel = rb.velocity.y * rb.drag;
float coeff = (1f-Time.fixedDeltaTime*rb.drag);
float force = ((vel+gravity)/coeff) * rb.mass; // gravity = 9.81
rb.AddForce(-Vector3.up*force, ForceMode.Force);
}
Edit: I figured it out a couple minutes after posting, it’s because I made gravity positive and was multiplying by -Vector3.up, but because I was adding rb.velocity.y it was inverted. After fixing it works fine now.