Jump to content
  • Advertisement

Spaceship Autopilot to face direction ignoring roll.

This topic is 385 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I'm working on a spaceship simulation and am working on implementing autopilot. Setting the right torque in order to make the ship's heading in the right direction has been tricky. The parts I'm not sure about are how to properly translate the quaternion difference to torque and how to do it ignoring the roll of the ship. When I set the target to a identity quaternion, it seems to align just fine, but anything else, and it goes haywire. The simulation starts with a random quaternion normalized.

The steps I'm currently taking are:

  1. Compute the target heading (forward is unit Y, I want it to point to unit X, I get {[ 0, 0, -0.7071068, 0.7071068 ]} in xyzw)
  2. Compute the delta orientation (I don't know how to tell it to ignore roll or choose the closet roll with this rotation).
  3. Covert it to euler.
  4. Subtract the current velocity from the euler velocity, The euler velocity is the target we are aiming for.
  5. Apply it as torque.
Quaternion target = Quaternion.FromVectors(Vector3.UnitY, Vector3.UnitX); //Quaternion.Identity;
Quaternion current = Entity.AngularPosition;

Quaternion deltaOrientation = target * current.Inverse();
Vector3 euler = Quaternion.ToEuler(deltaOrientation);

Vector3 difference = euler - Entity.AngularVelocity;
//Quaternion deltaVelocity = deltaOrientation * Quaternion.FromEuler(Entity.AngularVelocity).Inverse();
//difference = Quaternion.ToEuler(deltaOrientation);

//Entity.AngularVelocity = new Vector3();

// Primary thrusters
var heading = Entity.AngularPosition.Transform(Vector3.UnitY);

Console.WriteLine($"\tNavigating {euler}\n\tHeading {heading}");

The integration code is based on bullet physics. I think that the angularVelocity is convertable to euler rotation, but I'm not sure. Also generally euler is clamped, which doesn't work here. But since the equations I've come across all seem to expect the clamp, I don't know if it works correctly with unclamped values.

float angle = angularVelocity.Length();
Vector3 axis;

if (angle < 0.001f)
  // use Taylor's expansions of sync function
  axis = angularVelocity * (0.5f * delta - (delta * delta * delta) * 0.020833333333f) * angle * angle;
  axis = angularVelocity * ((float)Math.Sin(0.5f * angle * delta) / angle);

Quaternion deltaOrientation = new Quaternion(axis, (float)Math.Cos(0.5f * angle * delta));
angularPosition = angularPosition * deltaOrientation;
angularPosition = angularPosition.Normalize();


Share this post

Link to post
Share on other sites

  • Advertisement

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!