Ray direction based on vehicle rotation

Is there a concrete way to detect if a vehicle wheel is on the ground? I suspected not, so before asking I tried various ray collision tests, and found the best solution is to add an empty node to the vehiclenode in the position of the wheel, and cast a ray from that nodes world position.

This does work, but I’m not sure how to get a Vector3f direction for when the vehicle is not flat to the ground. See the picture below to explain what I mean.

That image shows the collision results (bottom-left of the picture) using the code below, but as the ray construction shows in the code below, I’m using Vector3f.UNIT_Y.negate() to fire the ray directly down. This isnt going to work well for when the vehicle is in the position in the picture above.

Is it possible to calculate the direction the ray should fire based on the rotation of the vehicle?

[java]
private void checkIsOnGround(float tpf)
{
// these are empty nodes attached at the same location as the wheel joints
Vector3f n1Loc = frontTest.getWorldTranslation();
Vector3f n2Loc = rearTest.getWorldTranslation();

    Ray frontRay = new Ray(n1Loc, Vector3f.UNIT_Y.negate());
    Ray rearRay = new Ray(n2Loc, Vector3f.UNIT_Y.negate());

    CollisionResults frontResults = new CollisionResults();
    CollisionResults rearResults = new CollisionResults();

    rootNode.collideWith(frontRay, frontResults);
    rootNode.collideWith(rearRay, rearResults);

    removeScooterCollisions(frontResults);
    removeScooterCollisions(rearResults);

    CollisionResult frontResult = frontResults.getClosestCollision();
    if (frontResult != null)
    {
        float height = frontResult.getDistance();

        if (height > 1.4f)
        {
            this.frontWheelOnGround = false;

            if (this.getVehicleControl().getCurrentVehicleSpeedKmHour() > 5 && this.rearWheelOnGround == true)
                this.frontWheelAirTime += tpf;
        }
        else
        {
            this.frontWheelOnGround = true;
            this.frontWheelAirTime = 0f;
        }
    }

    CollisionResult rearResult = rearResults.getClosestCollision();
    if (rearResult != null)
    {
        float height = rearResult.getDistance();

        if (height > 2.5f)
        {
            this.rearWheelOnGround = false;

            if (this.getVehicleControl().getCurrentVehicleSpeedKmHour() > 5 && this.frontWheelOnGround == true)
                this.rearWheelAirTime += tpf;
        }
        else
        {
            this.rearWheelOnGround = true;
            this.rearWheelAirTime = 0f;
        }
    }

    if (this.frontWheelOnGround == false && this.rearWheelOnGround == false)
    {
        this.airTime += tpf;
    }
    else
    {
        this.airTime = 0f;
    }

}

[/java]

you have a vector, say 0,-1,0 you currently use.
you have a quaternion (world) for the vehicle

now you can multiply(i love 4d) the quaternion with the vector, and have a vector rotated by the quaternion.
http://www.jmonkeyengine.org/doc/com/jme/math/Quaternion.html#mult(com.jme.math.Vector3f)

this will result in something like

0.4,-0.5,0 for the above rotation assuming x+ is right. and y- down

you know… I’m sure I tried that last night and again this morning… Works perfectly. :facepalm:

@jayfella said: you know.. I'm sure I tried that last night and again this morning... Works perfectly. :facepalm:

Maybe your Quaternion was in local, not world?