00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #include "Matrix.h"
00012 #include "Rotation.h"
00013 #include "Attitude.h"
00014 #include "Orbit.h"
00015 #include "CombinedNumericPropagator.h"
00016 #include "RungeKuttaFehlbergIntegrator.h"
00017 #include "orbitmodels/TwoBodyDynamics.h"
00018 #include "CentralBody/EarthCentralBody.h"
00019 #include "OrbitState.h"
00020 #include "AttitudeState.h"
00021 #include "orbitstaterep/PositionVelocity.h"
00022 #include "orbitframes/OrbitFrameIJK.h"
00023 #include "Disturbances/GravityFunctions.h"
00024 #include "Disturbances/SimpleAerodynamicDisturbances.h"
00025 #include "Plot.h"
00026 #include <string>
00027 #include <stdlib.h>
00028 #include <sstream>
00029 using namespace O_SESSAME;
00030
00031
00032 static Orbit* myOrbit = NULL;
00033 static Attitude* myAttitude = NULL;
00034 static Environment* myEnvironment = NULL;
00035 static CombinedNumericPropagator* myPropagator = NULL;
00036 static RungeKuttaFehlbergIntegrator* orbitIntegrator = NULL;
00037 static RungeKuttaFehlbergIntegrator* attitudeIntegrator = NULL;
00038 static vector<ssfTime> propTimes;
00039
00040 void SetupPropagator();
00041 void SetupEnvironment();
00042 void SetupOrbit();
00043 void SetupAttitude();
00044
00045 void ChangePropagator();
00046 void ChangeEnvironment();
00047 void ChangeOrbit();
00048 void ChangeOrbitIntegrator();
00049 void ChangeAttitude();
00050 void ChangeAttitudeIntegrator();
00051
00052 void Propagate();
00053 void Plot();
00054
00055 Vector SimpleController(const ssfTime &_currentTime, const OrbitState &_currentOrbitState, const AttitudeState &_currentAttitudeState, const EnvFuncParamaterType &_parameterList);
00056 void myOrbitStateConvFunc(const Matrix &_meshPoint, OrbitState &_convertedOrbitState);
00057 void myAttitudeStateConvFunc(const Matrix &_meshPoint, AttitudeState &_convertedAttitudeState);
00058
00059 void DisplayOrbit()
00060 {
00061 if(myOrbit->IsIntegrateable())
00062 cout << "Orbit State (km, km/s): " << ~myOrbit->GetStateObject().GetStateRepresentation()->GetPositionVelocity() << endl;
00063 else
00064 cout << "Orbit State: [ uninitialized ]" << endl;
00065 return;
00066 }
00067
00068 void DisplayAttitude()
00069 {
00070 if(myAttitude->IsIntegrateable())
00071 cout << "Attitude State: (-, rad/s)" << ~myAttitude->GetStateObject().GetState() << endl;
00072 else
00073 cout << "Attitude State: [ uninitialized ]" << endl;
00074 return;
00075 }
00076 void DisplayPropagator()
00077 {
00078 if(myPropagator)
00079 cout << "Propagate times: [" << propTimes[0] << " -> " << propTimes[1] << "] (s)" << endl;
00080 else
00081 cout << "Propagate State: [ uninitialized ]" << endl;
00082 return;
00083 }
00084 int DisplayMenu()
00085 {
00086 DisplayOrbit();
00087 DisplayAttitude();
00088 DisplayPropagator();
00089 cout << endl;
00090 cout << "[1] Setup Orbit" << endl;
00091 cout << "[2] Setup Orbit Integrator" << endl;
00092 cout << "[3] Setup Attitude" << endl;
00093 cout << "[4] Setup Attitude Integrator" << endl;
00094 cout << "[5] Setup Environment" << endl;
00095 cout << "[6] Setup Propagator" << endl;
00096 cout << "[7] Propagate" << endl;
00097 cout << "[8] Plot" << endl;
00098 cout << "[0] Exit" << endl;
00099 cout << endl << "Selection: " << flush;
00100
00101 int selection;
00102 cin >> selection;
00103 return selection;
00104 }
00105
00106 void Select()
00107 {
00108 switch(DisplayMenu())
00109 {
00110 case 1:
00111 ChangeOrbit();
00112 break;
00113 case 2:
00114 ChangePropagator();
00115
00116 break;
00117 case 3:
00118 ChangeAttitude();
00119 break;
00120 case 4:
00121 ChangePropagator();
00122
00123 break;
00124 case 5:
00125 ChangeEnvironment();
00126 break;
00127 case 6:
00128 ChangePropagator();
00129 break;
00130 case 7:
00131 Propagate();
00132 break;
00133 case 8:
00134 ::Plot();
00135 break;
00136 case 0:
00137 return;
00138 break;
00139 default:
00140 cout << "Incorrect Selection." << endl;
00141 break;
00142 }
00143 Select();
00144
00145 }
00146 int main()
00147 {
00148 SetupOrbit();
00149 SetupAttitude();
00150 SetupPropagator();
00151 myOrbit->SetPropagator(myPropagator);
00152 myAttitude->SetPropagator(myPropagator);
00153
00154 SetupEnvironment();
00155 myOrbit->SetEnvironment(myEnvironment);
00156 myAttitude->SetEnvironment(myEnvironment);
00157
00158 Select();
00159
00160 ofstream ofile;
00161
00162 double requestTime;
00163 cout << "Output requested time (s): " << flush;
00164 cin >> requestTime;
00165
00166 if(myOrbit)
00167 if (myOrbit->IsIntegrateable())
00168 {
00169 cout << "Orbit State (km, km/s): " << ~myOrbit->GetHistoryObject().GetState(requestTime).GetStateRepresentation()->GetPositionVelocity() << endl;
00170 ofile.open("OrbitHistory.dat");
00171 ofile << setprecision(15) << myOrbit->GetHistoryObject().GetHistory();
00172 ofile.close();
00173 }
00174
00175 if(myAttitude)
00176 if (myAttitude->IsIntegrateable())
00177 {
00178 cout << "Attitude State: (-, rad/s)" << ~myAttitude->GetHistoryObject().GetState(requestTime).GetState() << endl;
00179
00180 ofile.open("AttitudeHistory.dat");
00181 ofile << setprecision(15) << myAttitude->GetHistoryObject().GetHistory();
00182 ofile.close();
00183 }
00184 return 0;
00185
00186 }
00187
00188 void Plot()
00189 {
00190 if(myOrbit)
00191 if (myOrbit->IsIntegrateable())
00192 {
00193 Matrix orbitHistory = myOrbit->GetHistoryObject().GetHistory();
00194 Matrix orbitPlotting = orbitHistory(_,_(MatrixIndexBase+1,MatrixIndexBase+3));
00195 Plot3D(orbitPlotting);
00196 }
00197 if(myAttitude)
00198 if (myAttitude->IsIntegrateable())
00199 {
00200 Matrix attitudeHistory = myAttitude->GetHistoryObject().GetHistory();
00201 Matrix attitudePlotting = attitudeHistory(_,_(MatrixIndexBase,MatrixIndexBase+4));
00202 Plot2D(attitudePlotting);
00203 }
00204
00205 }
00206
00207 void Propagate()
00208 {
00209
00210 cout << "PropTime = " << propTimes[0].GetSeconds() << " s -> " << propTimes[1].GetSeconds() << " s" << endl;
00211 Vector orbInitState(6);
00212 Vector attInitState(7);
00213 if(myOrbit->IsIntegrateable())
00214 {
00215 orbInitState = myOrbit->GetStateObject().GetState();
00216 cout << "Orbit State: " << ~orbInitState << endl;
00217 }
00218 if(myAttitude->IsIntegrateable())
00219 {
00220 attInitState = myAttitude->GetStateObject().GetState();
00221 cout << "Attitude State: " << ~attInitState << endl;
00222 }
00223
00224 tick();
00225 myPropagator->Propagate(propTimes, orbInitState, attInitState);
00226 ssfSeconds calcTime = tock();
00227 cout << "finished propagating in " << calcTime << " seconds." << endl;
00228 }
00229
00230
00231
00232 void SetupEnvironment()
00233 {
00234
00235 myEnvironment = new Environment;
00236 EarthCentralBody *pCBEarth = new EarthCentralBody;
00237 myEnvironment->SetCentralBody(pCBEarth);
00238
00239 return;
00240 }
00241 void ChangeEnvironment()
00242 {
00243
00244 cout << "Filling Parameters" << endl;
00245 EnvFunction TwoBodyGravity(&GravityForceFunction);
00246 myEnvironment->AddForceFunction(TwoBodyGravity);
00247
00248 cout << "Add Drag? (y or n): " << flush;
00249 char answer;
00250 cin >> answer;
00251 if(answer == 'y')
00252 {
00253
00254 EnvFunction DragForce(&SimpleAerodynamicDragForce);
00255 double *BC = new double(200);
00256 DragForce.AddParameter(reinterpret_cast<void*>(BC), 1);
00257 double *rho = new double(1.13 * pow(static_cast<double>(10), static_cast<double>(-12)));
00258 DragForce.AddParameter(reinterpret_cast<void*>(rho), 2);
00259 myEnvironment->AddForceFunction(DragForce);
00260 }
00261 cout << "Finished Setting up Earth Environment" << endl;
00262
00263
00264
00265 EnvFunction Controller(&SimpleController);
00266 Vector* Gains = new Vector(3);
00267 cout << "Input Control gains: "<< flush;
00268 cin >> (*Gains)(1);
00269 cin >> (*Gains)(2);
00270 cin >> (*Gains)(3);
00271
00272 Controller.AddParameter(reinterpret_cast<void*>(Gains),1);
00273 myEnvironment->AddTorqueFunction(Controller);
00274
00275 return;
00276 }
00277
00278
00279
00280
00281 void SetupPropagator()
00282 {
00283 myPropagator = new CombinedNumericPropagator;
00284 orbitIntegrator = new RungeKuttaFehlbergIntegrator;
00285 attitudeIntegrator = new RungeKuttaFehlbergIntegrator;
00286
00287 myPropagator->SetOrbitIntegrator(orbitIntegrator);
00288 myPropagator->SetAttitudeIntegrator(attitudeIntegrator);
00289
00290
00291 double intTime = 1;
00292 ssfTime begin(0);
00293 ssfTime end(begin + intTime);
00294 propTimes.push_back(begin);
00295 propTimes.push_back(end);
00296 return;
00297 }
00298
00299 void ChangePropagator()
00300 {
00301 DisplayPropagator();
00302
00303
00304
00305 int stepSize = 1;
00306
00307
00308 double intTime = 1;
00309 cout << "Integration duration (s): " << flush;
00310 cin >> intTime;
00311
00312
00313
00314
00315
00316
00317
00318
00319
00320 double tolerance;
00321 orbitIntegrator->SetStepSizes(1, 300);
00322 cout << "Orbit Tolerance: " << flush;
00323 cin >> tolerance;
00324 orbitIntegrator->SetTolerance(tolerance);
00325 attitudeIntegrator->SetStepSizes(0.01, 5);
00326 cout << "Attitude Tolerance: " << flush;
00327 cin >> tolerance;
00328 attitudeIntegrator->SetTolerance(tolerance);
00329 ssfTime begin(0);
00330 ssfTime end(begin + intTime);
00331 propTimes[0] = begin;
00332 propTimes[1] = end;
00333 }
00334
00335
00336
00337 void myOrbitStateConvFunc(const Matrix &_meshPoint, OrbitState &_convertedOrbitState)
00338 {
00339 static Vector tempVector(_meshPoint[MatrixColsIndex].getIndexBound() - 1);
00340 tempVector(_) = ~_meshPoint(_,_(MatrixIndexBase+1, _meshPoint[MatrixColsIndex].getIndexBound()));
00341 _convertedOrbitState.SetState(tempVector);
00342 return;
00343 }
00344
00345 void ChangeOrbit()
00346 {
00347 DisplayOrbit();
00348
00349
00350 OrbitState myOrbitState;
00351 myOrbitState.SetStateRepresentation(new PositionVelocity);
00352 myOrbitState.SetOrbitFrame(new OrbitFrameIJK);
00353 Vector initPV(6);
00354
00355
00356 cout << "Enter the position vector (km): " << flush;
00357 cin >> initPV(VectorIndexBase+0);
00358 cin >> initPV(VectorIndexBase+1);
00359 cin >> initPV(VectorIndexBase+2);
00360 cout << "Enter the velocity vector (km): " << flush;
00361 cin >> initPV(VectorIndexBase+3);
00362 cin >> initPV(VectorIndexBase+4);
00363 cin >> initPV(VectorIndexBase+5);
00364 myOrbitState.SetState(initPV);
00365 myOrbit->SetStateObject(myOrbitState);
00366
00367
00368 myOrbit->SetDynamicsEq(&TwoBodyDynamics);
00369 myOrbit->SetStateConversion(&myOrbitStateConvFunc);
00370
00371
00372 return;
00373 }
00374 void SetupOrbit()
00375 {
00376 myOrbit = new Orbit;
00377 return;
00378 }
00379
00380
00381
00382
00383
00384 void myAttitudeStateConvFunc(const Matrix &_meshPoint, AttitudeState &_convertedAttitudeState)
00385 {
00386 static Vector tempQ(4); tempQ(_) = ~_meshPoint(_,_(2, 5));
00387 static Vector tempVector(3); tempVector(_) = ~_meshPoint(_, _(6, 8));
00388 _convertedAttitudeState.SetState(Rotation(Quaternion(tempQ)), tempVector);
00389 return;
00390 }
00391 static Vector AttituteDynamics(const ssfTime &_time, const Vector& _integratingState, Orbit *_Orbit, Attitude *_Attitude, const Matrix &_parameters, const Functor &_forceFunctorPtr)
00392 {
00393 static Vector stateDot(7);
00394 static Matrix bMOI(3,3);
00395 static Matrix qtemp(4,3);
00396 static Vector Tmoment(3);
00397 static Vector qIn(4);
00398 static Vector wIn(3);
00399
00400 qIn = _integratingState(_(VectorIndexBase,VectorIndexBase + 3));
00401 wIn = _integratingState(_(VectorIndexBase + 4,VectorIndexBase + 6));
00402 qIn /= norm2(qIn);
00403
00404 qtemp(_(VectorIndexBase+0,VectorIndexBase+2),_) = skew(qIn(_(VectorIndexBase+0,VectorIndexBase+2))) + qIn(VectorIndexBase+3) * eye(3);
00405 qtemp(VectorIndexBase+3, _) = -(~qIn(_(VectorIndexBase+0,VectorIndexBase+2)));
00406
00407 bMOI = _parameters(_(MatrixIndexBase+0,MatrixIndexBase+2),_(MatrixIndexBase+0,MatrixIndexBase+2));
00408 Tmoment = _forceFunctorPtr.Call(_time, _Orbit->GetStateObject(), _Attitude->GetStateObject());
00409
00410 stateDot(_(VectorIndexBase,VectorIndexBase + 3)) = 0.5 * qtemp * wIn;
00411 stateDot(_(VectorIndexBase + 4,VectorIndexBase + 6)) = (bMOI.inverse() * (Tmoment - skew(wIn) * (bMOI * wIn)));
00412
00413 return stateDot;
00414 }
00415
00416 void ChangeAttitude()
00417 {
00418 DisplayAttitude();
00419 double q1,q2,q3,q4;
00420 cout << "Enter Attitude quaternion: " << flush;
00421 cin >> q1 >> q2 >> q3 >> q4;
00422
00423 AttitudeState myAttitudeState;
00424 myAttitudeState.SetRotation(Rotation(Quaternion(q1,q2,q3,q4)));
00425
00426 cout << "Enter Attitude angular velocity (rad/s): " << flush;
00427 cin >> q1 >> q2 >> q3;
00428 Vector initAngVelVector(3);
00429 initAngVelVector(1) = q1;
00430 initAngVelVector(2) = q2;
00431 initAngVelVector(3) = q3;
00432
00433 myAttitudeState.SetAngularVelocity(initAngVelVector);
00434
00435 myAttitude->SetStateObject(myAttitudeState);
00436 myAttitude->SetDynamicsEq(&AttituteDynamics);
00437 myAttitude->SetStateConversion(&myAttitudeStateConvFunc);
00438 cout << "Enter Principle Moments of Inertia: " << flush;
00439 Matrix MOI = eye(3);
00440 cin >> MOI(1,1);
00441 cin >> MOI(2,2);
00442 cin >> MOI(3,3);
00443 myAttitude->SetParameters(MOI);
00444
00445 return;
00446 }
00447 void SetupAttitude()
00448 {
00449 myAttitude = new Attitude;
00450
00451 return;
00452
00453 }
00454 Vector SimpleController(const ssfTime &_currentTime, const OrbitState &_currentOrbitState, const AttitudeState &_currentAttitudeState, const EnvFuncParamaterType &_parameterList)
00455 {
00456 static Vector Torques(3);
00457 Torques(1) = (*reinterpret_cast<Vector*>(_parameterList[0]))(1) * sin(_currentTime.GetSeconds());
00458 Torques(2) = (*reinterpret_cast<Vector*>(_parameterList[0]))(2) * cos(_currentTime.GetSeconds());
00459 Torques(3) = (*reinterpret_cast<Vector*>(_parameterList[0]))(3);
00460 return Torques;
00461 }
00462
00463
00464
00465
00466
00467
00468
00469
00470
00471
00472
00473
00474
00475
00476
00477
00478
00479
00480
00481
00482
00483
00484
00485
00486