private void ComputeOrbital(RenderContext11 renderContext) { CAAEllipticalObjectElements ee = Elements; Vector3d point = CAAElliptical.CalculateRectangular(SpaceTimeController.JNow, ee, out MeanAnomoly); Vector3d pointInstantLater = CAAElliptical.CalculateRectangular(ee, MeanAnomoly + .001); Vector3d direction = point - pointInstantLater; direction.Normalize(); Vector3d up = point; up.Normalize(); direction.Normalize(); double dist = point.Length(); double scaleFactor = 1.0; switch (SemiMajorAxisUnits) { case AltUnits.Meters: scaleFactor = 1.0; break; case AltUnits.Feet: scaleFactor = 1.0 / 3.2808399; break; case AltUnits.Inches: scaleFactor = (1.0 / 3.2808399) / 12; break; case AltUnits.Miles: scaleFactor = 1609.344; break; case AltUnits.Kilometers: scaleFactor = 1000; break; case AltUnits.AstronomicalUnits: scaleFactor = UiTools.KilometersPerAu * 1000; break; case AltUnits.LightYears: scaleFactor = UiTools.AuPerLightYear * UiTools.KilometersPerAu * 1000; break; case AltUnits.Parsecs: scaleFactor = UiTools.AuPerParsec * UiTools.KilometersPerAu * 1000; break; case AltUnits.MegaParsecs: scaleFactor = UiTools.AuPerParsec * UiTools.KilometersPerAu * 1000 * 1000000; break; case AltUnits.Custom: scaleFactor = 1; break; default: break; } scaleFactor *= 1 / renderContext.NominalRadius; Matrix3d look = Matrix3d.LookAtLH(new Vector3d(0, 0, 0), direction, up); look.Invert(); WorldMatrix = Matrix3d.Identity; WorldMatrix.Translate(Translation); double localScale = (1 / renderContext.NominalRadius) * Scale * MeanRadius; WorldMatrix.Scale(new Vector3d(localScale, localScale, localScale)); WorldMatrix.Rotate(Quaternion.RotationYawPitchRoll((float)((Heading) / 180.0 * Math.PI), (float)(Pitch / 180.0 * Math.PI), (float)(Roll / 180.0 * Math.PI))); if (RotationalPeriod != 0) { double rotationCurrent = (((SpaceTimeController.JNow - this.ZeroRotationDate) / RotationalPeriod) * Math.PI * 2) % (Math.PI * 2); WorldMatrix.Multiply(Matrix3d.RotationX(-rotationCurrent)); } point = Vector3d.Scale(point, scaleFactor); WorldMatrix.Translate(point); if (StationKeeping) { WorldMatrix = look * WorldMatrix; } }
private void ComputeFrameTrajectory(RenderContext11 renderContext) { Vector3d vector = new Vector3d(); Vector3d point = GetTragectoryPoint(SpaceTimeController.JNow, out vector); Vector3d direction = vector; direction.Normalize(); Vector3d up = point; up.Normalize(); direction.Normalize(); double dist = point.Length(); double scaleFactor = 1.0; //scaleFactor = UiTools.KilometersPerAu * 1000; scaleFactor *= 1 / renderContext.NominalRadius; Matrix3d look = Matrix3d.LookAtLH(new Vector3d(0, 0, 0), direction, new Vector3d(0, 1, 0)); look.Invert(); WorldMatrix = Matrix3d.Identity; WorldMatrix.Translate(Translation); double localScale = (1 / renderContext.NominalRadius) * Scale * MeanRadius; WorldMatrix.Scale(new Vector3d(localScale, localScale, localScale)); WorldMatrix.Rotate(Quaternion.RotationYawPitchRoll((float)((Heading) / 180.0 * Math.PI), (float)(Pitch / 180.0 * Math.PI), (float)(Roll / 180.0 * Math.PI))); if (RotationalPeriod != 0) { double rotationCurrent = (((SpaceTimeController.JNow - this.ZeroRotationDate) / RotationalPeriod) * Math.PI * 2) % (Math.PI * 2); WorldMatrix.Multiply(Matrix3d.RotationX(-rotationCurrent)); } point = Vector3d.Scale(point, scaleFactor); WorldMatrix.Translate(point); if (StationKeeping) { WorldMatrix = look * WorldMatrix; } }
private void ComputeFixedSherical(RenderContext11 renderContext) { if (ObservingLocation) { Lat = SpaceTimeController.Location.Lat; Lng = SpaceTimeController.Location.Lng; Altitude = SpaceTimeController.Altitude; } WorldMatrix = Matrix3d.Identity; WorldMatrix.Translate(Translation); double localScale = (1 / renderContext.NominalRadius) * Scale * MeanRadius; WorldMatrix.Scale(new Vector3d(localScale, localScale, localScale)); //WorldMatrix.Scale(new Vector3d(1000, 1000, 1000)); WorldMatrix.Rotate(Quaternion.RotationYawPitchRoll((float)((Heading) / 180.0 * Math.PI), (float)(Pitch / 180.0 * Math.PI), (float)(Roll / 180.0 * Math.PI))); WorldMatrix.Multiply(Matrix3d.RotationZ(-90.0 / 180.0 * Math.PI)); if (RotationalPeriod != 0) { double rotationCurrent = (((SpaceTimeController.JNow - this.ZeroRotationDate) / RotationalPeriod) * Math.PI * 2) % (Math.PI * 2); WorldMatrix.Multiply(Matrix3d.RotationX(-rotationCurrent)); } WorldMatrix.Translate(new Vector3d(1 + (Altitude / renderContext.NominalRadius), 0, 0)); WorldMatrix.Multiply(Matrix3d.RotationZ(Lat / 180 * Math.PI)); WorldMatrix.Multiply(Matrix3d.RotationY(-(Lng) / 180 * Math.PI)); }
private void ComputeFrameSynodic(RenderContext11 renderContext) { // A synodic frame is a rotating frame of reference in which // the x-axis is the direction between the bodies in a two-body // system. The origin is at the secondary body, and +x points // in the direction opposite the primary. The z-axis is in the orbital // plane and normal to x; it points in the direction of the instantaneous // orbital velocity of the secondary. // The origin is offset by then translation. The five libration points in a // two-body system can be approximated by choosing different offsets. For // example, the Sun-Earth L2 point is approximated by using x = 1,500,000 km, y = 0 and z = 0. WorldMatrix = Matrix3d.Identity; double localScale = (1 / renderContext.NominalRadius) * Scale * MeanRadius; WorldMatrix.Scale(new Vector3d(localScale, localScale, localScale)); WorldMatrix.Rotate(Quaternion.RotationYawPitchRoll((float)((Heading) / 180.0 * Math.PI), (float)(Pitch / 180.0 * Math.PI), (float)(Roll / 180.0 * Math.PI))); WorldMatrix.Translate(Translation / 6371.000); // Currently we assume the Sun-Earth system double jd = SpaceTimeController.JNow; double B = CAACoordinateTransformation.DegreesToRadians(CAAEarth.EclipticLatitude(jd)); double L = CAACoordinateTransformation.DegreesToRadians(CAAEarth.EclipticLongitude(jd)); Vector3d eclPos = new Vector3d(Math.Cos(L) * Math.Cos(B), Math.Sin(L) * Math.Cos(B), Math.Sin(B)); // Just approximate the orbital velocity for now Vector3d eclVel = Vector3d.Cross(eclPos, new Vector3d(0.0, 0.0, 1.0)); eclVel.Normalize(); // Convert to WWT's coordinate convention by swapping Y and Z eclPos = new Vector3d(eclPos.X, eclPos.Z, eclPos.Y); eclVel = new Vector3d(eclVel.X, eclVel.Z, eclVel.Y); Vector3d xaxis = eclPos; Vector3d yaxis = Vector3d.Cross(eclVel, eclPos); Vector3d zaxis = eclVel; Matrix3d rotation = new Matrix3d(xaxis.X, yaxis.X, zaxis.X, 0, xaxis.Y, yaxis.Y, zaxis.Y, 0, xaxis.Z, yaxis.Z, zaxis.Z, 0, 0, 0, 0, 1); // Convert from ecliptic to J2000 EME (equatorial) system double earthObliquity = CAACoordinateTransformation.DegreesToRadians(Coordinates.MeanObliquityOfEcliptic(jd)); rotation = rotation * Matrix3d.RotationX(-earthObliquity); WorldMatrix.Multiply(rotation); }
private void ComputeFixedRectangular(RenderContext11 renderContext) { WorldMatrix = Matrix3d.Identity; WorldMatrix.Translate(Translation); WorldMatrix.Rotate(Quaternion.RotationYawPitchRoll((float)((Heading) / 180.0 * Math.PI), (float)(Pitch / 180.0 * Math.PI), (float)(Roll / 180.0 * Math.PI))); WorldMatrix.Scale(new Vector3d(Scale, Scale, Scale)); WorldMatrix.Rotate(Quaternion.RotationYawPitchRoll((float)(Coordinates.MstFromUTC2(SpaceTimeController.Now, 0) / 180 * Math.PI), (float)0, (float)0)); }