Project Overview
This is the result of an attempt spanning tenths of various iteratinos to simulate a realistically behaving vehicle. Taking account various environmental effects such as drag, rolling resistance, grip between the tyre and surface and gravity.
Engine Forces
The vehicle is simulated to take into account forces which a car would have to deal with in the real world such as air and roll resistance. Based on pre-set parameters, the vehicle's top-speed, acceleration, braking forces and turning ability can be easily edited to make get the desited behavior for the vehicle.

//Aero
float DragCoefficient = (0.5f * dragForce * frontArea * airDensity);
float RollCoefficient = rollForce * DragCoefficient;
Vector3 DragResistanceForce = -DragCoefficient * velocity * velocity.magnitude;
Vector3 RollResistanceForce = -CRoll * velocity;
//Braking
float BrakeTorque = brakePressure * brakeInput * -Mathf.Sign(speed);
//Engine
float avgAngularVelocity = 0;
for (int i = 0; i < wheels.Length; i++)
{
avgAngularVelocity += wheels[i].angularVelocity;
}
avgAngularVelocity /= wheels.Length;
RPM = (avgAngularVelocity * gearRatios[currentGear] * finalDriveRatio * 60) / (2 * Mathf.PI);
if (RPM < 1000) RPM = 1000; //Simulating anti-stall
if (RPM > maxRPM) throttleInput = 0; //Simulating rev limiter
float MaxTorque = torqueCurve.Evaluate(RPM);
float EngineTorque = MaxTorque * throttleInput;
float DriveTorque = EngineTorque * gearRatios[currentGear] * finalDriveRatio * engineEfficiency;
Dynamic Suspension
The suspension model actively simulates the behavior and movement of a real spring and damper that's typically found in vehicles. The strength of the spring and damber can be edited to fine-tune how the vehicle feels when driving over various surfaces.
//Suspension
Vector3 hingeWorldPos = transform.parent.TransformPoint(hingePoint);
Vector3 fixedHingeVelocity = (hingeWorldPos - prevPos) / Time.fixedDeltaTime;
float fixedDeltaLength = Vector3.Dot(transform.up, transform.position - hingeWorldPos) + offset;
float fixedHingeDeltaVelocity = Vector3.Dot(transform.up, fixedHingeVelocity - rigidbody.velocity);
float hingeVelocity = (hingeWorldPos.y - prevPos.y) / Time.fixedDeltaTime;
float deltaLength = (transform.position.y - hingeWorldPos.y);
float blockDeltaVelocity = hingeVelocity - rigidbody.velocity.y;
float spring = (fixedDeltaLength * stiffness);
float damper = (fixedHingeDeltaVelocity * damping);
float wheelForce = spring - damper;