Hi,
I wrote a small simulation of our solar system using the irrlicht engine. It works very well by now. The planets are positioned by:
I recently started adding a projection mode or call it planning mode where the user can utilize at any point and in any direction a nifty "burn" button which de- or accelerates the satellite to a certain speed in km/s and projects onward to plot the trajectory.
Green line from earth to mars. I also added a function with the name calcLaunchSolution which attempts to find valid launch windows between planets and prints a valid delta-V or lets just call it velocity to enter a transfer orbit. It also works very well and I just keep on missing mars by a few hundred thousend km. Unfortunately. 
I guess most of you here already know why that is so, but to state it again, it stems from the fact that all the math stuff one is able to find for hohmann transfers assume perfect circular and perfectly coplanar orbits, which none of our planets actually has. Well you could argue that since the eccliptic is considered to be on the plane of the coordinate system we use (heliocentric eccliptic) earth does, but no there is inclination and of course eccentricity in all 8 planets orbits.
So, additionally to finding the right day, I need to find for the departure planet the distance from the sun at time of departure and the distance of the arrival planet from sun at the time of arrival. Those two distances are then the perigee and apogee of my transfer. But because in finding the right day I use the mean distances, the transfer period is schoolbook style 258 days(mars), in reality it varies +/- 3/4 days everything is then corrupt.
Secondly even if I get close by trial and error the inclination change between the orbits makes me arrive on a completly different plane, which corrupts even more.
Well, long talk, I hope someone knows what I'm talking about and can provide me with interesting links and readings on the subject so I can get that fixed asap.
Many Thanks in advance
EDIT:
Long day, I found a promising fortran app that I could translate with f2c using a lambert solver, unfortunately the provided source only extends a library which costs 179 $, so I guess I need to work it out using the Java Astrodynamics Toolkit lambert solver, but indeed looks promising...
...and for the record, these are my attempts so far, be warned it is a mess and reflects many sleepless nights...
I wrote a small simulation of our solar system using the irrlicht engine. It works very well by now. The planets are positioned by:
- Finding the julian day since the date of the elements (J2000)
- Finding the average (or mean) orbital elements of the planet
- Finding the true anomaly, the angle to the planet from perihelion.
- Finding the heliocentric radius, distance from planet to sun
- Finding the heliocentric ecliptic rectangular coordinates of the planet
I recently started adding a projection mode or call it planning mode where the user can utilize at any point and in any direction a nifty "burn" button which de- or accelerates the satellite to a certain speed in km/s and projects onward to plot the trajectory.
I guess most of you here already know why that is so, but to state it again, it stems from the fact that all the math stuff one is able to find for hohmann transfers assume perfect circular and perfectly coplanar orbits, which none of our planets actually has. Well you could argue that since the eccliptic is considered to be on the plane of the coordinate system we use (heliocentric eccliptic) earth does, but no there is inclination and of course eccentricity in all 8 planets orbits.
So, additionally to finding the right day, I need to find for the departure planet the distance from the sun at time of departure and the distance of the arrival planet from sun at the time of arrival. Those two distances are then the perigee and apogee of my transfer. But because in finding the right day I use the mean distances, the transfer period is schoolbook style 258 days(mars), in reality it varies +/- 3/4 days everything is then corrupt.
Secondly even if I get close by trial and error the inclination change between the orbits makes me arrive on a completly different plane, which corrupts even more.
Well, long talk, I hope someone knows what I'm talking about and can provide me with interesting links and readings on the subject so I can get that fixed asap.
Many Thanks in advance
EDIT:
Long day, I found a promising fortran app that I could translate with f2c using a lambert solver, unfortunately the provided source only extends a library which costs 179 $, so I guess I need to work it out using the Java Astrodynamics Toolkit lambert solver, but indeed looks promising...
...and for the record, these are my attempts so far, be warned it is a mess and reflects many sleepless nights...
Code:
void calcLaunchSolution(u32 start, u32 destination)// f64 *launchday, core::vector3df *velocity
{
// 1st.
//calculate mean transfer orbit period
f64 distPerigee = pMeanDist2[start]*1000.0f;
f64 distApogee = pMeanDist2[destination]*1000.0f;
f64 semiMajorAxisM = ((distPerigee+distApogee)/2);
f64 pConst = Gconst*pMass[9];
//calculate orbital period in days, for an ellipse that is tangential to start and destination planet
//the formula for an ellipse is
//p = 2PI*sqrt(semi-major axis^3/GM) where p is in seconds and semi-major axis in meters
//then divide it by 2 to give us a transfer orbit period
f64 TOPeriod = ((((2*core::PI*sqrt(pow(semiMajorAxisM,3)/pConst))/60.0f)/60.0f)/24.0f);
//printf("Period in days: %f\n",oPeriod);
//Half of the elipse is the Transfer Orbit, therefore we divide by 2;
TOPeriod /= 2.0f;
printf("\n\nTransfer Period = %.9f\n",TOPeriod);
//2nd
//Find time delta angle for the launch window
//calculate destination Planet orbital Period DIVIDED 2 MINUS transfer orbit Period
//if the destination planets orbital period is greater than the start planets orbital period,
//ie. it moves more slow, then the launch window occurs after the day with matching delta angle,
//otherwise before...
f64 angleOffset = 180.0f + (core::PI * (1.0 - TOPeriod / orbitT[destination])*core::RADTODEG64);
if(angleOffset > 360)
angleOffset - 360.0;
if(orbitT[start] < orbitT[destination])
angleOffset = angleOffset;
else
angleOffset = 360.0 - angleOffset;
printf("Angle Offset = %.9f\n",angleOffset);
if(orbitT[start] < orbitT[destination])
{
angleOffset = angleOffset;
}
else
{
angleOffset = 360.0f - angleOffset;
}
//3rd
//find a day with this angular offset between start and destination planet
bool windowNotFound = true;
f64 testday = Day;
f64 approxWindowDay;
core::stringc date;
u32 dates = 0;
while(dates < 1)
{
testday += 0.1f;
date = mySolarSystem->J2000ToGreg(testday).c_str();
core::array<core::vector3df> startPos = mySolarSystem->calculateAtDay(testday, start);
core::array<core::vector3df> DestPos = mySolarSystem->calculateAtDay(testday, destination);
core::vector3df startAngle = startPos[0].getHorizontalAngle();
core::vector3df DestAngle = DestPos[0].getHorizontalAngle();
f32 delta = DestAngle.Y - startAngle.Y;
//printf("Delta:%f,- %s\n",delta,date);
if( core::abs_(delta - angleOffset) <= 0.1f)
{
approxWindowDay = testday;
date = mySolarSystem->J2000ToGreg(approxWindowDay).c_str();
printf("Approximate Launch Date = %s\n",date);
windowNotFound = false;
dates++;
}
};
//Day = approxWindowDay;
//4th
//calculate precise transfer period based on determined launch date
core::array<core::vector3df> perigeePos = mySolarSystem->calculateAtDay(approxWindowDay,start);
core::array<core::vector3df> apogeePos = mySolarSystem->calculateAtDay(approxWindowDay + TOPeriod,destination);
f32 lDPerigee = perigeePos[0].getLength()*1000.0f;
f32 lDApogee = apogeePos[0].getLength()*1000.0f;
f64 semiMajorAxisLD = ((lDPerigee+lDApogee)/2);
f64 lDTOPeriod = ((((2*core::PI*sqrt(pow(semiMajorAxisLD,3)/pConst))/60.0f)/60.0f)/24.0f)/2.0f;
printf("precise Transfer Period = %f\n",lDTOPeriod);
//4th
//Calculate precise launch date
angleOffset = 180.0f + (core::PI * (1.0 - lDTOPeriod / orbitT[destination])*core::RADTODEG64);
if(angleOffset > 360)
angleOffset - 360;
printf("True Angle Offset = %.9f\n",angleOffset);
if(orbitT[start] < orbitT[destination])
{
angleOffset = angleOffset;
}
else
{
angleOffset = 360.0f - angleOffset;
}
testday = Day;
dates = 0;
while(dates < 1)
{
testday += 0.1f;
date = mySolarSystem->J2000ToGreg(testday).c_str();
core::array<core::vector3df> startPos = mySolarSystem->calculateAtDay(testday, start);
core::array<core::vector3df> DestPos = mySolarSystem->calculateAtDay(testday, destination);
core::vector3df startAngle = startPos[0].getHorizontalAngle();
core::vector3df DestAngle = DestPos[0].getHorizontalAngle();
f32 delta = DestAngle.Y - startAngle.Y;
//printf("Delta:%f,- %s\n",delta,date);
if( core::abs_(delta - angleOffset) <= 0.1f)
{
approxWindowDay = testday;
date = mySolarSystem->J2000ToGreg(approxWindowDay).c_str();
printf("Precise Launch Date = %s\n",date);
windowNotFound = false;
dates++;
}
};
Day = approxWindowDay;
f64 arrivalDay = Day+lDTOPeriod;
core::stringc arrivalDate = mySolarSystem->J2000ToGreg(arrivalDay).c_str();
printf("Precise Arrival Date = %s\n",arrivalDate);
//5th
//Calculate the Orbital Velocity at perigee
//Velocity at Perigee = sqrt( GM * ( ( 2 * distApogee) / ( distPerigee * ( distPerigee+distApogee ) ) ) )
core::array<core::vector3df> nperigeePos = mySolarSystem->calculateAtDay(approxWindowDay,start);
core::array<core::vector3df> napogeePos = mySolarSystem->calculateAtDay(approxWindowDay + lDTOPeriod,destination);
f64 nlDPerigee = nperigeePos[0].getLength()*1000.0f;
f64 nlDApogee = napogeePos[0].getLength()*1000.0f;
f64 ellipticOrbVelocity = sqrt( pConst * ( ( 2 * nlDApogee) / ( nlDPerigee * ( nlDPerigee + nlDApogee ) ) ) );
ellipticOrbVelocity /= 1000.0;
printf("Velocity = %.9f\n",ellipticOrbVelocity);
//Day = approxWindowDay;
ellipticOrbVelocity /= scaleF;
printf("Dist Perigee %.9f\n",lDPerigee/1000.0);
printf("Dist Apogee %.9f\n",lDApogee/1000.0);
f64 yDiff = core::max_(perigeePos[0].Y,apogeePos[0].Y) - core::min_(perigeePos[0].Y,apogeePos[0].Y);
f64 yDiff2d = (yDiff/scaleF) / (lDTOPeriod/fpsincrement);
yDiffSpeed = core::vector3df(0,yDiff2d,0);
}
Last edited:
ready to go !