Wheel Collider Weird Acceleration

Hello gurus,
I am developing an asset for the Asset store. After going through dozens of difficulties and bugs, I got stuck on a very strange error. It is a car physics asset that I made using wheel collider. My problem is that if I make the car rwd or awd, it works fine. But if I make it fwd, it continues to accelerate for 1-2 seconds after I take my hand off the gas. I debugged all the values. throttle input is 0. engine torque is 0. All the values ​​are as they should be. However, the car continues to accelerate. Can anyone give an opinion on the subject?

private void ApplyDrive()
{
    if (isEngineOn)
    {
        if (inputSystem.gasInput > 0 || inputSystem.brakeInput > 0)
        {
            float normalizedRPM = Mathf.Clamp01(Mathf.InverseLerp(carSettings.minRPM, carSettings.maxRPM, engineRPM));
            currentTorque = carSettings.torqueCurve.Evaluate(normalizedRPM) * carSettings.maxTorque;

            float linearGasInput = inputSystem.gasInput * currentTorque;

            RevLimiter();

            if (currentGear == -1)
            {
                linearGasInput = inputSystem.brakeInput * currentTorque;
                currentWheelTorque = -linearGasInput * 1f * carSettings.differantial;
                isReverse = true;
            }
            else if (inputSystem.gasInput > 0)
            {
                currentWheelTorque = linearGasInput * carSettings.gearRatios[currentGear] * carSettings.differantial;
                isReverse = false;
            }
            else
            {
                currentTorque = 0;
                currentWheelTorque = 0;
            }
        }
        else
        {
            currentTorque = 0;
            currentWheelTorque = 0;
        }
        switch (carSettings.driveTrain)
        {
            case DriveTrain.FWD:
                if(inputSystem.gasInput > 0)
                {
                    ApplyTorqueToWheels(currentWheelTorque, frontLeftWheel, frontRightWheel);

                }
                ApplyTorqueToWheels(currentWheelTorque, frontLeftWheel, frontRightWheel);
                break;
            case DriveTrain.RWD:
                ApplyTorqueToWheels(currentWheelTorque, rearLeftWheel, rearRightWheel);
                break;
            case DriveTrain.AWD:
                ApplyTorqueToWheels((currentWheelTorque / 2) * (1 - carSettings.rearWheelTorqueDistribution), frontLeftWheel, frontRightWheel);
                ApplyTorqueToWheels((currentWheelTorque / 2) * carSettings.rearWheelTorqueDistribution, rearLeftWheel, rearRightWheel);
                break;
        }
    }
}
    private void ApplyTorqueToWheels(float torque, WheelCollider leftWheel, WheelCollider rightWheel)
    {
        leftWheel.motorTorque = torque;
        rightWheel.motorTorque = torque;
    }

That’s a lot of logic… I can see at least one codepath where you don’t change the torque in a given frame (if isEngineOn is false).

Why not instead have temporary variables with the torques, set them to zero each frame, then do your logic, possibly setting them to other values, and at the end of the logic assign those torque variables to the wheels? You can do the same thing with brakes.

That way when nothing is going, you know the torques / brakes will be reset to zero.

If that doesn’t reveal and/or solve your problem, that just means it is time to start debugging!

By debugging you can find out exactly what your program is doing so you can fix it.

Use the above techniques to get the information you need in order to reason about what the problem is.

You can also use Debug.Log(...); statements to find out if any of your code is even running. Don’t assume it is.

Once you understand what the problem is, you may begin to reason about a solution to the problem.

Remember with Unity the code is only a tiny fraction of the problem space. Everything asset- and scene- wise must also be set up correctly to match the associated code and its assumptions.

1 Like

I actually tried it the way you mentioned. At that time I had problems with going backwards in automatic transmission and this was the most trouble-free version for me. I’ve been debugging for two days and every value I check is as expected. Actually, the fact that the wheels continue to accelerate seems like a delay rather than a bug. Because it starts to slow down in two seconds at most.

Then prove it’s not a bug. Set the values every frame guaranteed.

Once you do that, if the problem still persists, then we can agree it’s some weird delay in the API, which I am going to predict is not actually happening.

If I can glance at code and see a codepath that would cause the exact issue you report, it will be tough to convince me otherwise until you close off that codepath.


        private void ApplyDrive()
        {
            currentTorque = 0;
            currentWheelTorque = 0;

            if (isEngineOn)
            {
                if (inputSystem.gasInput > 0 || inputSystem.brakeInput > 0)
                {
                    float normalizedRPM = Mathf.Clamp01(Mathf.InverseLerp(carSettings.minRPM, carSettings.maxRPM, engineRPM));
                    currentTorque = carSettings.torqueCurve.Evaluate(normalizedRPM) * carSettings.maxTorque;

                    RevLimiter();
                    float linearGasInput = inputSystem.gasInput * currentTorque;

                    if (currentGear == -1)
                    {
                        if (carSettings.transmissionType == TransmissionType.Manual)
                        {
                            linearGasInput = inputSystem.gasInput * currentTorque;
                        }
                        else
                        {
                            linearGasInput = inputSystem.brakeInput * currentTorque;
                        }
                        currentWheelTorque = -linearGasInput * 2f * carSettings.differantial;
                        isReverse = true;
                    }
                    else if (inputSystem.gasInput > 0)
                    {
                        currentWheelTorque = linearGasInput * carSettings.gearRatios[currentGear] * carSettings.differantial;
                        isReverse = false;
                    }
                }
                switch (carSettings.driveTrain)
                {
                    case DriveTrain.FWD:
                        ApplyTorqueToWheels(currentWheelTorque, frontLeftWheel, frontRightWheel);
                        break;
                    case DriveTrain.RWD:
                        ApplyTorqueToWheels(currentWheelTorque, rearLeftWheel, rearRightWheel);
                        break;
                    case DriveTrain.AWD:
                        ApplyTorqueToWheels((currentWheelTorque / 2) * (1 - carSettings.rearWheelTorqueDistribution), frontLeftWheel, frontRightWheel);
                        ApplyTorqueToWheels((currentWheelTorque / 2) * carSettings.rearWheelTorqueDistribution, rearLeftWheel, rearRightWheel);
                        break;
                }
            }
        }

I updated it like this, I think it’s closer to the situation you mentioned. Now there are delays of about 0.5 seconds in awd and fwd. MotorTorque, input values, etc. are instantly 0.


First debug comes from input value. The second one is motorTorque of every wheels when I release the button. It was still accelerating at that moment.

It seems I was looking for the problem in the wrong place. I simplified the code as you said but it did not solve the problem at all. However, I noticed that there was unnecessary smoke coming out of the wheels. I realized that it was related to the extreme slip value in the front. It was slipping too much and for some reason it was causing such a problem.