-/*******************************************************************************
+/** *****************************************************************************
Module: FGAircraft.cpp
Author: Jon S. Berndt
- Date started: 12/12/98
+ Date started: 12/12/98
Purpose: Encapsulates an aircraft
Called by: FGFDMExec
FUNCTIONAL DESCRIPTION
--------------------------------------------------------------------------------
-Models the aircraft reactions and forces.
-
-ARGUMENTS
---------------------------------------------------------------------------------
-
+Models the aircraft reactions and forces. This class is instantiated by the
+FGFDMExec class and scheduled as an FDM entry. LoadAircraft() is supplied with a
+name of a valid, registered aircraft, and the data file is parsed.
HISTORY
--------------------------------------------------------------------------------
********************************************************************************
INCLUDES
*******************************************************************************/
-#include "FGAircraft.h"
-
#include <stdlib.h>
#include <dirent.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <math.h>
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGFCS.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
+
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-
-FGAircraft::FGAircraft(void) : FGModel()
+FGAircraft::FGAircraft(FGFDMExec* fdmex) : FGModel(fdmex)
{
int i;
bool FGAircraft::LoadAircraft(char* fname)
{
- char path[250];
- char fullpath[275];
- char filename[275];
- char aircraftDef[2100];
- char tag[220];
+ char path[256];
+ char fullpath[256];
+ char filename[256];
+ char aircraftDef[256];
+ char tag[256];
DIR* dir;
DIR* coeffdir;
- struct dirent* dirEntry = 0L;
- struct dirent* coeffdirEntry = 0L;
+ struct dirent* dirEntry;
+ struct dirent* coeffdirEntry;
struct stat st;
struct stat st2;
ifstream coeffInFile;
- char scratch[250];
-
sprintf(aircraftDef, "/h/curt/projects/FlightGear/Simulator/FDM/JSBsim/aircraft/%s/%s.dat", fname, fname);
ifstream aircraftfile(aircraftDef);
if (aircraftfile) {
- aircraftfile >> AircraftName;
- aircraftfile >> WingArea;
- aircraftfile >> WingSpan;
- aircraftfile >> cbar;
- aircraftfile >> Ixx;
- aircraftfile >> Iyy;
- aircraftfile >> Izz;
- aircraftfile >> Ixz;
- aircraftfile >> Weight;
- m = Weight / 32.174;
+ aircraftfile >> AircraftName; // String with no embedded spaces
+ aircraftfile >> WingArea; // square feet
+ aircraftfile >> WingSpan; // feet
+ aircraftfile >> cbar; // feet
+ aircraftfile >> Ixx; // slug ft^2
+ aircraftfile >> Iyy; // "
+ aircraftfile >> Izz; // "
+ aircraftfile >> Ixz; // "
+ aircraftfile >> EmptyWeight; // pounds
+ EmptyMass = EmptyWeight / GRAVITY;
aircraftfile >> tag;
numTanks = numEngines = 0;
while (strstr(tag,"EOF") == 0) {
if (strstr(tag,"CGLOC")) {
- aircraftfile >> Xcg;
- aircraftfile >> Ycg;
- aircraftfile >> Zcg;
+ aircraftfile >> Xcg; // inches
+ aircraftfile >> Ycg; // inches
+ aircraftfile >> Zcg; // inches
} else if (strstr(tag,"EYEPOINTLOC")) {
- aircraftfile >> Xep;
- aircraftfile >> Yep;
- aircraftfile >> Zep;
+ aircraftfile >> Xep; // inches
+ aircraftfile >> Yep; // inches
+ aircraftfile >> Zep; // inches
} else if (strstr(tag,"TANK")) {
Tank[numTanks] = new FGTank(aircraftfile);
switch(Tank[numTanks]->GetType()) {
numTanks++;
} else if (strstr(tag,"ENGINE")) {
aircraftfile >> tag;
- Engine[numEngines] = new FGEngine(tag);
+ Engine[numEngines] = new FGEngine(FDMExec, tag, numEngines);
numEngines++;
}
aircraftfile >> tag;
// previously mentioned axis.
sprintf(path,"/h/curt/projects/FlightGear/Simulator/FDM/JSBsim/aircraft/%s/",AircraftName);
- if ( dir = opendir(path) ) {
+ if (dir = opendir(path)) {
while (dirEntry = readdir(dir)) {
sprintf(fullpath,"%s%s",path,dirEntry->d_name);
sprintf(filename,"%s%s/%s",path,Axis[axis_ctr],coeffdirEntry->d_name);
stat(filename,&st2);
if (st2.st_size > 6) {
- Coeff[axis_ctr][coeff_ctr[axis_ctr]] = new FGCoefficient(filename);
+ Coeff[axis_ctr][coeff_ctr[axis_ctr]] = new FGCoefficient(FDMExec, filename);
coeff_ctr[axis_ctr]++;
}
}
for (int i = 0; i < 3; i++) Forces[i] = Moments[i] = 0.0;
+ MassChange();
+
FProp(); FAero(); FGear(); FMass();
MProp(); MAero(); MGear(); MMass();
}
-void FGAircraft::FAero(void)
+void FGAircraft::MassChange()
{
- float F[3];
-
- F[0] = F[1] = F[2] = 0.0;
-
- for (int axis_ctr = 0; axis_ctr < 3; axis_ctr++)
- for (int ctr=0; ctr < coeff_ctr[axis_ctr]; ctr++)
- F[axis_ctr] += Coeff[axis_ctr][ctr]->Value();
-
- Forces[0] += F[LiftCoeff]*sin(alpha) - F[DragCoeff]*cos(alpha) - F[SideCoeff]*sin(beta);
- Forces[1] += F[SideCoeff]*cos(beta);
- Forces[2] += -F[LiftCoeff]*cos(alpha) - F[DragCoeff]*sin(alpha);
-}
-
-
-void FGAircraft::FGear(void)
-{
- if (GearUp) {
- } else {
- }
-}
-
-
-void FGAircraft::FMass(void)
-{
- Forces[0] += -g*sin(tht) * m;
- Forces[1] += g*sin(phi)*cos(tht) * m;
- Forces[2] += g*cos(phi)*cos(tht) * m;
-}
-
-
-void FGAircraft::FProp(void)
-{
- float Oshortage, Fshortage;
-
- for (int i=0;i<numEngines;i++) {
- Forces[0] += Engine[i]->CalcThrust();
- }
-
- //
// UPDATE TANK CONTENTS
//
// For each engine, cycle through the tanks and draw an equal amount of
// and will be drawn from the next tank. If the engine cannot be fed what it
// needs, it will be considered to be starved, and will shut down.
+ float Oshortage, Fshortage;
+
for (int e=0; e<numEngines; e++) {
Fshortage = Oshortage = 0.0;
for (int t=0; t<numTanks; t++) {
switch(Tank[t]->GetType()) {
case 0: // Fuel
if (Tank[t]->GetSelected()) {
- Fshortage = Tank[t]->Reduce((Engine[e]->CalcFuelNeed()/numSelectedFuelTanks)*(dt*rate) + Fshortage);
+ Fshortage = Tank[t]->Reduce((Engine[e]->CalcFuelNeed()/
+ numSelectedFuelTanks)*(dt*rate) + Fshortage);
}
break;
case 1: // Oxidizer
if (Tank[t]->GetSelected()) {
- Oshortage = Tank[t]->Reduce((Engine[e]->CalcOxidizerNeed()/numSelectedOxiTanks)*(dt*rate) + Oshortage);
+ Oshortage = Tank[t]->Reduce((Engine[e]->CalcOxidizerNeed()/
+ numSelectedOxiTanks)*(dt*rate) + Oshortage);
}
break;
}
break;
default: // piston, turbojet, turbofan, etc.
if (Tank[t]->GetSelected()) {
- Fshortage = Tank[t]->Reduce((Engine[e]->CalcFuelNeed()/numSelectedFuelTanks)*(dt*rate) + Fshortage);
+ Fshortage = Tank[t]->Reduce((Engine[e]->CalcFuelNeed()/
+ numSelectedFuelTanks)*(dt*rate) + Fshortage);
}
break;
}
}
- if ((Fshortage < 0.0) || (Oshortage < 0.0)) Engine[e]->SetStarved();
+ if ((Fshortage <= 0.0) || (Oshortage <= 0.0)) Engine[e]->SetStarved();
else Engine[e]->SetStarved(false);
}
+ Weight = EmptyWeight;
+ for (int t=0; t<numTanks; t++)
+ Weight += Tank[t]->GetContents();
+
+ Mass = Weight / GRAVITY;
+}
+
+
+void FGAircraft::FAero(void)
+{
+ float F[3];
+
+ F[0] = F[1] = F[2] = 0.0;
+
+ for (int axis_ctr = 0; axis_ctr < 3; axis_ctr++)
+ for (int ctr=0; ctr < coeff_ctr[axis_ctr]; ctr++)
+ F[axis_ctr] += Coeff[axis_ctr][ctr]->Value();
+
+ Forces[0] += F[LiftCoeff]*sin(alpha) - F[DragCoeff]*cos(alpha) - F[SideCoeff]*sin(beta);
+ Forces[1] += F[SideCoeff]*cos(beta);
+ Forces[2] += -F[LiftCoeff]*cos(alpha) - F[DragCoeff]*sin(alpha);
+}
+
+
+void FGAircraft::FGear(void)
+{
+ if (GearUp) {
+ } else {
+ }
+}
+
+
+void FGAircraft::FMass(void)
+{
+ Forces[0] += -GRAVITY*sin(tht) * Mass;
+ Forces[1] += GRAVITY*sin(phi)*cos(tht) * Mass;
+ Forces[2] += GRAVITY*cos(phi)*cos(tht) * Mass;
+}
+
+
+void FGAircraft::FProp(void)
+{
+ for (int i=0;i<numEngines;i++) {
+ Forces[0] += Engine[i]->CalcThrust();
+ }
}
void FGAircraft::GetState(void)
{
- Ixx = State->GetIxx();
- Iyy = State->GetIyy();
- Izz = State->GetIzz();
- Ixz = State->GetIxz();
- alpha = State->Getalpha();
- beta = State->Getbeta();
- m = State->Getm();
- phi = State->Getphi();
- tht = State->Gettht();
- psi = State->Getpsi();
- g = State->Getg();
dt = State->Getdt();
+
+ alpha = Translation->Getalpha();
+ beta = Translation->Getbeta();
+ phi = Rotation->Getphi();
+ tht = Rotation->Gettht();
+ psi = Rotation->Getpsi();
}
void FGAircraft::PutState(void)
{
- State->SetIxx(Ixx);
- State->SetIyy(Iyy);
- State->SetIzz(Izz);
- State->SetIxz(Ixz);
- State->SetFx(Forces[0]);
- State->SetFy(Forces[1]);
- State->SetFz(Forces[2]);
- State->SetL(Moments[0]);
- State->SetM(Moments[1]);
- State->SetN(Moments[2]);
- State->Setm(m);
}
HISTORY
--------------------------------------------------------------------------------
12/12/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
#include "FGCoefficient.h"
#include "FGEngine.h"
#include "FGTank.h"
-//#include "FGMatrix.h"
/*******************************************************************************
DEFINITIONS
class FGAircraft : public FGModel
{
public:
- FGAircraft(void);
+ FGAircraft(FGFDMExec*);
~FGAircraft(void);
bool Run(void);
+
bool LoadAircraft(char*);
- char* GetAircraftName(void) {return AircraftName;}
+
+ inline char* GetAircraftName(void) {return AircraftName;}
+
inline void SetGearUp(bool tt) {GearUp = tt;}
inline bool GetGearUp(void) {return GearUp;}
inline float GetWingArea(void) {return WingArea;}
inline float Getcbar(void) {return cbar;}
inline FGEngine* GetEngine(int tt) {return Engine[tt];}
inline FGTank* GetTank(int tt) {return Tank[tt];}
+ inline float GetWeight(void) {return Weight;}
+ inline float GetMass(void) {return Mass;}
+
+ inline float GetL(void) {return Moments[0];}
+ inline float GetM(void) {return Moments[1];}
+ inline float GetN(void) {return Moments[2];}
+
+ inline float GetFx(void) {return Forces[0];}
+ inline float GetFy(void) {return Forces[1];}
+ inline float GetFz(void) {return Forces[2];}
+
+ inline float GetIxx(void) {return Ixx;}
+ inline float GetIyy(void) {return Iyy;}
+ inline float GetIzz(void) {return Izz;}
+ inline float GetIxz(void) {return Ixz;}
private:
void GetState(void);
void MMass(void);
void MProp(void);
+ void MassChange(void);
+
float Moments[3];
float Forces[3];
char AircraftName[50];
- float Ixx, Iyy, Izz, Ixz, m;
+ float Ixx, Iyy, Izz, Ixz, EmptyMass, Mass;
float Xcg, Ycg, Zcg;
float Xep, Yep, Zep;
float rho, qbar, Vt;
float alpha, beta;
float WingArea, WingSpan, cbar;
- float g, phi, tht, psi;
- float Weight;
+ float phi, tht, psi;
+ float Weight, EmptyWeight;
float dt;
int numTanks;
int numEngines;
int numSelectedOxiTanks;
int numSelectedFuelTanks;
- FGTank* Tank[30];
- FGEngine *Engine[10];
+ FGTank* Tank[MAX_TANKS];
+ FGEngine *Engine[MAX_ENGINES];
FGCoefficient *Coeff[6][10];
int coeff_ctr[6];
};
-#ifndef FDM_MAIN
-extern FGAircraft* Aircraft;
-#else
-FGAircraft* Aircraft;
-#endif
-
/******************************************************************************/
#endif
Models the atmosphere. The equation used below was determined by a third order
curve fit using Excel. The data is from the ICAO atmosphere model.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
11/24/98 JSB Created
*******************************************************************************/
#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGAtmosphere::FGAtmosphere() : FGModel()
+FGAtmosphere::FGAtmosphere(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name,"FGAtmosphere");
}
bool FGAtmosphere::Run(void)
{
if (!FGModel::Run()) { // if false then execute this Run()
- State->Setrho(0.002377 - 7.0E-08*State->Geth()
+ rho = 0.002377 - 7.0E-08*State->Geth()
+ 7.0E-13*State->Geth()*State->Geth()
- - 2.0E-18*State->Geth()*State->Geth()*State->Geth());
+ - 2.0E-18*State->Geth()*State->Geth()*State->Geth();
State->SetMach(State->GetVt()/State->Geta());
} else { // skip Run() execution this time
HISTORY
--------------------------------------------------------------------------------
11/24/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
class FGAtmosphere : public FGModel
{
public:
- FGAtmosphere(void);
+ FGAtmosphere(FGFDMExec*);
~FGAtmosphere(void);
+
bool Run(void);
+ inline float Getrho(void) {return rho;}
+
protected:
private:
-
+ float rho;
};
-#ifndef FDM_MAIN
-extern FGAtmosphere* Atmosphere;
-#else
-FGAtmosphere* Atmosphere;
-#endif
-
/******************************************************************************/
#endif
This class calculates various auxiliary parameters, mostly used by the visual
system
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
01/26/99 JSB Created
*******************************************************************************/
#include "FGAuxiliary.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGPosition.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGAuxiliary::FGAuxiliary() : FGModel()
+FGAuxiliary::FGAuxiliary(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name, "FGAuxiliary");
}
if (!FGModel::Run()) {
} else {
}
+ return false;
}
HISTORY
--------------------------------------------------------------------------------
11/22/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
class FGAuxiliary : public FGModel
{
public:
- FGAuxiliary(void);
+ FGAuxiliary(FGFDMExec*);
~FGAuxiliary(void);
bool Run(void);
-
+
protected:
private:
};
-#ifndef FDM_MAIN
-extern FGAuxiliary* Auxiliary;
-#else
-FGAuxiliary* Auxiliary;
-#endif
-
/******************************************************************************/
#endif
See the header file FGCoefficient.h for the values of the identifiers.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
12/28/98 JSB Created
INCLUDES
*******************************************************************************/
-class FGCoefficient;
#include <stdio.h>
#include <stdlib.h>
+#include "FGCoefficient.h"
+
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
#include "FGFCS.h"
#include "FGAircraft.h"
-#include "FGCoefficient.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGCoefficient::FGCoefficient(void)
+FGCoefficient::FGCoefficient(FGFDMExec* fdex)
{
+ FDMExec = fdex;
+ State = FDMExec->GetState();
+ Atmosphere = FDMExec->GetAtmosphere();
+ FCS = FDMExec->GetFCS();
+ Aircraft = FDMExec->GetAircraft();
+ Translation = FDMExec->GetTranslation();
+ Rotation = FDMExec->GetRotation();
+ Position = FDMExec->GetPosition();
+ Auxiliary = FDMExec->GetAuxiliary();
+ Output = FDMExec->GetOutput();
+
rows = columns = 0;
}
-FGCoefficient::FGCoefficient(char* fname)
+FGCoefficient::FGCoefficient(FGFDMExec* fdex, char* fname)
{
int r, c;
float ftrashcan;
+ FDMExec = fdex;
+ State = FDMExec->GetState();
+ Atmosphere = FDMExec->GetAtmosphere();
+ FCS = FDMExec->GetFCS();
+ Aircraft = FDMExec->GetAircraft();
+ Translation = FDMExec->GetTranslation();
+ Rotation = FDMExec->GetRotation();
+ Position = FDMExec->GetPosition();
+ Auxiliary = FDMExec->GetAuxiliary();
+ Output = FDMExec->GetOutput();
+
ifstream coeffDefFile(fname);
if (coeffDefFile) {
}
-FGCoefficient::FGCoefficient(int r, int c)
+FGCoefficient::FGCoefficient(FGFDMExec* fdex, int r, int c)
{
+ FDMExec = fdex;
+ State = FDMExec->GetState();
+ Atmosphere = FDMExec->GetAtmosphere();
+ FCS = FDMExec->GetFCS();
+ Aircraft = FDMExec->GetAircraft();
+ Translation = FDMExec->GetTranslation();
+ Rotation = FDMExec->GetRotation();
+ Position = FDMExec->GetPosition();
+ Auxiliary = FDMExec->GetAuxiliary();
+ Output = FDMExec->GetOutput();
+
rows = r;
columns = c;
Allocate(r,c);
}
-FGCoefficient::FGCoefficient(int n)
+FGCoefficient::FGCoefficient(FGFDMExec* fdex, int n)
{
+ FDMExec = fdex;
+ State = FDMExec->GetState();
+ Atmosphere = FDMExec->GetAtmosphere();
+ FCS = FDMExec->GetFCS();
+ Aircraft = FDMExec->GetAircraft();
+ Translation = FDMExec->GetTranslation();
+ Rotation = FDMExec->GetRotation();
+ Position = FDMExec->GetPosition();
+ Auxiliary = FDMExec->GetAuxiliary();
+ Output = FDMExec->GetOutput();
+
rows = n;
columns = 0;
Allocate(n);
case FG_CBAR:
return Aircraft->Getcbar();
case FG_ALPHA:
- return State->Getalpha();
+ return Translation->Getalpha();
case FG_ALPHADOT:
return State->Getadot();
case FG_BETA:
- return State->Getbeta();
+ return Translation->Getbeta();
case FG_BETADOT:
return State->Getbdot();
case FG_PITCHRATE:
- return State->GetQ();
+ return Rotation->GetQ();
case FG_ROLLRATE:
- return State->GetP();
+ return Rotation->GetP();
case FG_YAWRATE:
- return State->GetR();
+ return Rotation->GetR();
case FG_ELEVATOR:
return FCS->GetDe();
case FG_AILERON:
HISTORY
--------------------------------------------------------------------------------
12/28/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
CLASS DECLARATION
*******************************************************************************/
+class FGFDMExec;
+class FGState;
+class FGAtmosphere;
+class FGFCS;
+class FGAircraft;
+class FGTranslation;
+class FGRotation;
+class FGPosition;
+class FGAuxiliary;
+class FGOutput;
+
class FGCoefficient
{
public:
- FGCoefficient(void);
- FGCoefficient(int, int);
- FGCoefficient(int);
- FGCoefficient(char*);
+ FGCoefficient(FGFDMExec*);
+ FGCoefficient(FGFDMExec*, int, int);
+ FGCoefficient(FGFDMExec*, int);
+ FGCoefficient(FGFDMExec*, char*);
~FGCoefficient(void);
bool Allocate(int);
float LookupR, LookupC;
float GetCoeffVal(int);
+
+ FGFDMExec* FDMExec;
+ FGState* State;
+ FGAtmosphere* Atmosphere;
+ FGFCS* FCS;
+ FGAircraft* Aircraft;
+ FGTranslation* Translation;
+ FGRotation* Rotation;
+ FGPosition* Position;
+ FGAuxiliary* Auxiliary;
+ FGOutput* Output;
};
/******************************************************************************/
--------------------------------------------------------------------------------
See header file.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
INCLUDES
*******************************************************************************/
-#include "FGEngine.h"
-#include "FGState.h"
-#include "FGFCS.h"
#include <fstream.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
+#include "FGEngine.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGAtmosphere.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
+
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGEngine::FGEngine(char *engineName)
+FGEngine::FGEngine(FGFDMExec* fdex, char *engineName, int num)
{
- char fullpath[250];
- char tag[220];
+ char fullpath[256];
+ char tag[256];
+
+ FDMExec = fdex;
+
+ State = FDMExec->GetState();
+ Atmosphere = FDMExec->GetAtmosphere();
+ FCS = FDMExec->GetFCS();
+ Aircraft = FDMExec->GetAircraft();
+ Translation = FDMExec->GetTranslation();
+ Rotation = FDMExec->GetRotation();
+ Position = FDMExec->GetPosition();
+ Auxiliary = FDMExec->GetAuxiliary();
+ Output = FDMExec->GetOutput();
strcpy(Name, engineName);
sprintf(fullpath,"/h/curt/projects/FlightGear/Simulator/FDM/JSBsim/engine/%s.dat", engineName);
cerr << "Unable to open engine definition file " << engineName << endl;
}
+ EngineNumber = num;
Thrust = 0.0;
Starved = Flameout = false;
}
{
float lastThrust;
- Throttle = FCS->GetThrottle();
+ Throttle = FCS->GetThrottle(EngineNumber);
lastThrust = Thrust; // last actual thrust
if (Throttle < MinThrottle || Starved) {
Flameout = true;
} else {
PctPower = Throttle / MaxThrottle;
- Thrust = PctPower*((1.0 - State->Getrho() / 0.002378)*(VacThrustMax - SLThrustMax) +
+ Thrust = PctPower*((1.0 - Atmosphere->Getrho() / 0.002378)*(VacThrustMax - SLThrustMax) +
SLThrustMax); // desired thrust
Flameout = false;
}
switch(Type) {
case 0: // Rocket
return CalcRocketThrust();
- break;
+ // break;
case 1: // Piston
return CalcPistonThrust();
- break;
+ // break;
default:
return 9999.0;
- break;
+ // break;
}
}
HISTORY
--------------------------------------------------------------------------------
01/21/99 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
CLASS DECLARATION
*******************************************************************************/
+class FGFDMExec;
+class FGState;
+class FGAtmosphere;
+class FGFCS;
+class FGAircraft;
+class FGTranslation;
+class FGRotation;
+class FGPosition;
+class FGAuxiliary;
+class FGOutput;
+
class FGEngine
{
public:
- FGEngine(void);
- FGEngine(char*);
+ FGEngine(FGFDMExec*, char*, int);
~FGEngine(void);
float GetThrust(void) {return Thrust;}
bool Starved;
bool Flameout;
float PctPower;
-
+ int EngineNumber;
+
+ FGFDMExec* FDMExec;
+ FGState* State;
+ FGAtmosphere* Atmosphere;
+ FGFCS* FCS;
+ FGAircraft* Aircraft;
+ FGTranslation* Translation;
+ FGRotation* Rotation;
+ FGPosition* Position;
+ FGAuxiliary* Auxiliary;
+ FGOutput* Output;
+
protected:
float CalcRocketThrust(void);
float CalcPistonThrust(void);
};
/******************************************************************************/
-#endif
+#endif
\ No newline at end of file
--------------------------------------------------------------------------------
This class models the flight controls for a specific airplane
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
12/12/98 JSB Created
*******************************************************************************/
#include "FGFCS.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGAtmosphere.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGFCS::FGFCS(void) : FGModel()
+FGFCS::FGFCS(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name, "FGFCS");
}
HISTORY
--------------------------------------------------------------------------------
12/12/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
class FGFCS : public FGModel
{
public:
- FGFCS(void);
+ FGFCS(FGFDMExec*);
~FGFCS(void);
bool Run(void);
-
+
inline float GetDa(void) {return Da;}
inline float GetDe(void) {return De;}
inline float GetDr(void) {return Dr;}
inline float GetDf(void) {return Df;}
inline float GetDs(void) {return Ds;}
- inline float GetThrottle(void) {return Throttle;}
+ inline float GetThrottle(int ii) {return Throttle[ii];}
inline void SetDa(float tt) {Da = tt;}
inline void SetDe(float tt) {De = tt;}
inline void SetDr(float tt) {Dr = tt;}
inline void SetDf(float tt) {Df = tt;}
inline void SetDs(float tt) {Ds = tt;}
- inline void SetThrottle(float tt) {Throttle = tt;}
+ inline void SetThrottle(int ii, float tt) {Throttle[ii] = tt;}
protected:
private:
float Da, De, Dr, Df, Ds;
- float Throttle;
+ float Throttle[MAX_ENGINES];
};
-#ifndef FDM_MAIN
-extern FGFCS* FCS;
-#else
-FGFCS* FCS;
-#endif
-
/******************************************************************************/
-#endif
+#endif
\ No newline at end of file
This class wraps up the simulation scheduling routines.
-
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
11/17/98 JSB Created
INCLUDES
*******************************************************************************/
-#include "FGFDMExec.h"
#include <stdio.h>
#include <stdlib.h>
#include <iostream.h>
#include <time.h>
+#include "FGFDMExec.h"
+#include "FGState.h"
+
+#include "FGAtmosphere.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
+
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
FGFDMExec::FGFDMExec(void)
{
- FirstModel = 0L;
-
- State = new FGState();
- Atmosphere = new FGAtmosphere();
- FCS = new FGFCS();
- Aircraft = new FGAircraft();
- Translation = new FGTranslation();
- Rotation = new FGRotation();
- Position = new FGPosition();
- Auxiliary = new FGAuxiliary();
- Output = new FGOutput();
+ FirstModel = 0;
+ Error = 0;
+ State = 0;
+ Atmosphere = 0;
+ FCS = 0;
+ Aircraft = 0;
+ Translation = 0;
+ Rotation = 0;
+ Position = 0;
+ Auxiliary = 0;
+ Output = 0;
+
+ // Instantiate this FDM Executive's Models
+
+ Atmosphere = new FGAtmosphere(this);
+ FCS = new FGFCS(this);
+ Aircraft = new FGAircraft(this);
+ Translation = new FGTranslation(this);
+ Rotation = new FGRotation(this);
+ Position = new FGPosition(this);
+ Auxiliary = new FGAuxiliary(this);
+ Output = new FGOutput(this);
+
+ State = new FGState(this);
+
+ // Initialize models so they can communicate with each other
+
+ if (!Atmosphere->InitModel()) {cerr << "Atmosphere model init failed"; Error+=1;}
+ if (!FCS->InitModel()) {cerr << "FCS model init failed"; Error+=2;}
+ if (!Aircraft->InitModel()) {cerr << "Aircraft model init failed"; Error+=4;}
+ if (!Translation->InitModel()){cerr << "Translation model init failed"; Error+=8;}
+ if (!Rotation->InitModel()) {cerr << "Rotation model init failed"; Error+=16;}
+ if (!Position->InitModel()) {cerr << "Position model init failed"; Error+=32;}
+ if (!Auxiliary->InitModel()) {cerr << "Auxiliary model init failed"; Error+=64;}
+ if (!Output->InitModel()) {cerr << "Output model init failed"; Error+=128;}
Schedule(Atmosphere, 5);
Schedule(FCS, 1);
Schedule(Output, 5);
terminate = false;
- freeze = false;
+ frozen = false;
}
{
FGModel* model_iterator;
+ if (frozen) return true;
+
model_iterator = FirstModel;
if (model_iterator == 0L) return false;
if (model_iterator == 0L) break;
}
+ State->IncrTime();
+
return true;
}
HISTORY
--------------------------------------------------------------------------------
11/17/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
*******************************************************************************/
#include "FGModel.h"
-#include "FGAtmosphere.h"
-#include "FGFCS.h"
-#include "FGAircraft.h"
-#include "FGTranslation.h"
-#include "FGRotation.h"
-#include "FGPosition.h"
-#include "FGAuxiliary.h"
-#include "FGOutput.h"
/*******************************************************************************
CLASS DECLARATION
*******************************************************************************/
+class FGState;
+class FGAtmosphere;
+class FGFCS;
+class FGAircraft;
+class FGTranslation;
+class FGRotation;
+class FGPosition;
+class FGAuxiliary;
+class FGOutput;
+
class FGFDMExec
{
public:
- FGFDMExec::FGFDMExec(void);
- FGFDMExec::~FGFDMExec(void);
-
- FGModel* FirstModel;
-
- bool Initialize(void);
- int Schedule(FGModel* model, int rate);
- bool Run(void);
- bool Freeze(void);
- bool Resume(void);
+ FGFDMExec::FGFDMExec(void);
+ FGFDMExec::~FGFDMExec(void);
+
+ FGModel* FirstModel;
+
+ bool Initialize(void);
+ int Schedule(FGModel* model, int rate);
+ bool Run(void);
+ void Freeze(void) {frozen = true;}
+ void Resume(void) {frozen = false;}
+
+ inline FGState* GetState(void) {return State;}
+ inline FGAtmosphere* GetAtmosphere(void) {return Atmosphere;}
+ inline FGFCS* GetFCS(void) {return FCS;}
+ inline FGAircraft* GetAircraft(void) {return Aircraft;}
+ inline FGTranslation* GetTranslation(void) {return Translation;}
+ inline FGRotation* GetRotation(void) {return Rotation;}
+ inline FGPosition* GetPosition(void) {return Position;}
+ inline FGAuxiliary* GetAuxiliary(void) {return Auxiliary;}
+ inline FGOutput* GetOutput(void) {return Output;}
private:
- bool freeze;
- bool terminate;
+ bool frozen;
+ bool terminate;
+ int Error;
+
+ FGState* State;
+ FGAtmosphere* Atmosphere;
+ FGFCS* FCS;
+ FGAircraft* Aircraft;
+ FGTranslation* Translation;
+ FGRotation* Rotation;
+ FGPosition* Position;
+ FGAuxiliary* Auxiliary;
+ FGOutput* Output;
protected:
};
-#ifndef FDM_MAIN
-extern FGFDMExec* FDMExec;
-#else
-FGFDMExec* FDMExec;
-#endif
-
/******************************************************************************/
#endif
-#define FDM_MAIN
#include "FGFDMExec.h"
-#undef FDM_MAIN
+#include "FGRotation.h"
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
#include <iostream.h>
#include <time.h>
FDMExec = new FGFDMExec();
- Aircraft->LoadAircraft(argv[1]);
- State->Reset(argv[2]);
+ FDMExec->GetAircraft()->LoadAircraft(argv[1]);
+ FDMExec->GetState()->Reset(argv[2]);
- while (State->Setsim_time(State->Getsim_time() + 0.1) <= 25.0)
+ while (FDMExec->GetState()->Getsim_time() <= 25.0)
{
FDMExec->Run();
nanosleep(&short_wait,&no_wait);
This base class for the FGAero, FGRotational, etc. classes defines methods
common to all models.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
-
+11/11/98 JSB Created
********************************************************************************
INCLUDES
*******************************************************************************/
#include "FGModel.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGAtmosphere.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGModel::FGModel()
+FGModel::FGModel(FGFDMExec* fdmex)
{
- NextModel = 0L;
- exe_ctr = 1;
+ FDMExec = fdmex;
+ NextModel = 0L;
+
+ State = 0;
+ Atmosphere = 0;
+ FCS = 0;
+ Aircraft = 0;
+ Translation = 0;
+ Rotation = 0;
+ Position = 0;
+ Auxiliary = 0;
+ Output = 0;
+
+ exe_ctr = 1;
}
}
+bool FGModel::InitModel(void)
+{
+ State = FDMExec->GetState();
+ Atmosphere = FDMExec->GetAtmosphere();
+ FCS = FDMExec->GetFCS();
+ Aircraft = FDMExec->GetAircraft();
+ Translation = FDMExec->GetTranslation();
+ Rotation = FDMExec->GetRotation();
+ Position = FDMExec->GetPosition();
+ Auxiliary = FDMExec->GetAuxiliary();
+ Output = FDMExec->GetOutput();
+
+ if (!State ||
+ !Atmosphere ||
+ !FCS ||
+ !Aircraft ||
+ !Translation ||
+ !Rotation ||
+ !Position ||
+ !Auxiliary ||
+ !Output) return(false);
+ else return(true);
+}
+
+
bool FGModel::Run()
{
if (exe_ctr == 1) {
HISTORY
--------------------------------------------------------------------------------
11/22/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
INCLUDES
*******************************************************************************/
+#include "FGDefs.h"
#include <stdio.h>
#include <string.h>
#include <iostream.h>
-#include "FGState.h"
/*******************************************************************************
DEFINES
CLASS DECLARATION
*******************************************************************************/
+class FGFDMExec;
+class FGState;
+class FGAtmosphere;
+class FGFCS;
+class FGAircraft;
+class FGTranslation;
+class FGRotation;
+class FGPosition;
+class FGAuxiliary;
+class FGOutput;
+
class FGModel
{
public:
- FGModel(void);
+ FGModel(FGFDMExec*);
~FGModel(void);
-
+
FGModel* NextModel;
char Name[30];
virtual bool Run(void);
+ virtual bool InitModel(void);
void SetRate(int tt) {rate = tt;};
protected:
int exe_ctr;
int rate;
+
+ FGFDMExec* FDMExec;
+ FGState* State;
+ FGAtmosphere* Atmosphere;
+ FGFCS* FCS;
+ FGAircraft* Aircraft;
+ FGTranslation* Translation;
+ FGRotation* Rotation;
+ FGPosition* Position;
+ FGAuxiliary* Auxiliary;
+ FGOutput* Output;
private:
-
};
/******************************************************************************/
later. Some machines may not support the ncurses console output. Borland is one
of those environments which does not, so the ncurses stuff is commented out.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
12/02/98 JSB Created
INCLUDES
*******************************************************************************/
-/*
-#if !defined( __BORLANDC__ )
-# define HAVE_NCURSES
-#endif
-*/
-
-#include "FGOutput.h"
-
#include <stdio.h>
#include <stdlib.h>
#include <iostream.h>
-
-#ifndef HAVE_NCURSES
- #include "FGPosition.h"
-#else
+#ifdef HAVE_CURSES
#include <ncurses.h>
- #include "FGPosition.h"
#endif
+#include "FGOutput.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGAtmosphere.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGOutput::FGOutput(void) : FGModel()
+FGOutput::FGOutput(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name, "FGOutput");
FirstPass = true;
-#ifdef HAVE_NCURSES
+#ifdef HAVE_CURSES
initscr();
cbreak();
noecho();
void FGOutput::ConsoleOutput(void)
{
+#ifdef HAVE_CURSES
char buffer[20];
-#ifdef HAVE_NCURSES
clear();
move(1,1); insstr("Quaternions");
move(2,5); insstr("Q0");
move(2,27); insstr("Q2");
move(2,38); insstr("Q3");
- move(3,1); sprintf(buffer,"%4.4f",State->GetQ0()); insstr(buffer);
- move(3,12); sprintf(buffer,"%4.4f",State->GetQ1()); insstr(buffer);
- move(3,23); sprintf(buffer,"%4.4f",State->GetQ2()); insstr(buffer);
- move(3,34); sprintf(buffer,"%4.4f",State->GetQ3()); insstr(buffer);
+ move(3,1); sprintf(buffer,"%4.4f",Rotation->GetQ0()); insstr(buffer);
+ move(3,12); sprintf(buffer,"%4.4f",Rotation->GetQ1()); insstr(buffer);
+ move(3,23); sprintf(buffer,"%4.4f",Rotation->GetQ2()); insstr(buffer);
+ move(3,34); sprintf(buffer,"%4.4f",Rotation->GetQ3()); insstr(buffer);
move(0,0); insstr("Time: ");
move(0,6); insstr(gcvt(State->Getsim_time(),6,buffer));
move(2,55); insstr("Tht");
move(2,64); insstr("Psi");
- move(3,45); sprintf(buffer,"%3.3f",State->Getphi()); insstr(buffer);
- move(3,54); sprintf(buffer,"%3.3f",State->Gettht()); insstr(buffer);
- move(3,63); sprintf(buffer,"%3.3f",State->Getpsi()); insstr(buffer);
+ move(3,45); sprintf(buffer,"%3.3f",Rotation->Getphi()); insstr(buffer);
+ move(3,54); sprintf(buffer,"%3.3f",Rotation->Gettht()); insstr(buffer);
+ move(3,63); sprintf(buffer,"%3.3f",Rotation->Getpsi()); insstr(buffer);
move(5,47); insstr("U");
move(5,56); insstr("V");
move(5,65); insstr("W");
- move(6,45); sprintf(buffer,"%5.2f",State->GetU()); insstr(buffer);
- move(6,54); sprintf(buffer,"%5.2f",State->GetV()); insstr(buffer);
- move(6,63); sprintf(buffer,"%5.2f",State->GetW()); insstr(buffer);
+ move(6,45); sprintf(buffer,"%5.2f",Translation->GetU()); insstr(buffer);
+ move(6,54); sprintf(buffer,"%5.2f",Translation->GetV()); insstr(buffer);
+ move(6,63); sprintf(buffer,"%5.2f",Translation->GetW()); insstr(buffer);
move(8,47); insstr("Fx");
move(8,56); insstr("Fy");
move(8,65); insstr("Fz");
- move(9,45); sprintf(buffer,"%5.2f",State->GetFx()); insstr(buffer);
- move(9,54); sprintf(buffer,"%5.2f",State->GetFy()); insstr(buffer);
- move(9,63); sprintf(buffer,"%5.2f",State->GetFz()); insstr(buffer);
+ move(9,45); sprintf(buffer,"%5.2f",Aircraft->GetFx()); insstr(buffer);
+ move(9,54); sprintf(buffer,"%5.2f",Aircraft->GetFy()); insstr(buffer);
+ move(9,63); sprintf(buffer,"%5.2f",Aircraft->GetFz()); insstr(buffer);
move(11,47); insstr("Fn");
move(11,56); insstr("Fe");
} else {
cout << State->Getsim_time() << ",";
cout << State->Geth() << ",";
- cout << State->Getphi() << ",";
- cout << State->Gettht() << ",";
- cout << State->Getpsi() << ",";
- cout << State->Getrho() << ",";
+ cout << Rotation->Getphi() << ",";
+ cout << Rotation->Gettht() << ",";
+ cout << Rotation->Getpsi() << ",";
+ cout << Atmosphere->Getrho() << ",";
cout << State->GetVt() << ",";
- cout << State->GetU() << ",";
- cout << State->GetV() << ",";
- cout << State->GetW() << ",";
- cout << State->GetVn() << ",";
- cout << State->GetVe() << ",";
- cout << State->GetVd() << ",";
- cout << State->GetUdot() << ",";
- cout << State->GetVdot() << ",";
- cout << State->GetWdot() << ",";
- cout << State->GetFx() << ",";
- cout << State->GetFy() << ",";
- cout << State->GetFz() << ",";
+ cout << Translation->GetU() << ",";
+ cout << Translation->GetV() << ",";
+ cout << Translation->GetW() << ",";
+ cout << Position->GetVn() << ",";
+ cout << Position->GetVe() << ",";
+ cout << Position->GetVd() << ",";
+ cout << Translation->GetUdot() << ",";
+ cout << Translation->GetVdot() << ",";
+ cout << Translation->GetWdot() << ",";
+ cout << Aircraft->GetFx() << ",";
+ cout << Aircraft->GetFy() << ",";
+ cout << Aircraft->GetFz() << ",";
cout << State->Getlatitude() << ",";
cout << State->Getlongitude() << ",";
cout << State->Getqbar() << ",";
- cout << State->Getalpha() << "";
+ cout << Translation->Getalpha() << "";
cout << endl;
}
}
HISTORY
--------------------------------------------------------------------------------
12/02/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
class FGOutput : public FGModel
{
public:
- FGOutput(void);
+ FGOutput(FGFDMExec*);
~FGOutput(void);
+
bool Run(void);
+
void ConsoleOutput(void);
void DelimitedOutput(void);
protected:
-
private:
bool FirstPass;
};
-#ifndef FDM_MAIN
-extern FGOutput* Output;
-#else
-FGOutput* Output;
-#endif
-
/******************************************************************************/
#endif
This class encapsulates the integration of rates and accelerations to get the
current position of the aircraft.
-ARGUMENTS
---------------------------------------------------------------------------------
-None
-
HISTORY
--------------------------------------------------------------------------------
01/05/99 JSB Created
INCLUDES
*******************************************************************************/
-#include "FGPosition.h"
#include <math.h>
+#include "FGPosition.h"
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGPosition::FGPosition(void) : FGModel()
+FGPosition::FGPosition(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name, "FGPosition");
- EarthRad = 20898908.00; // feet
- OmegaEarth = 7.2685E-3; // rad/sec
AccelN = AccelE = AccelD = 0.0;
LongitudeDot = LatitudeDot = RadiusDot = 0.0;
}
AccelE = invMass * Fe + invRadius * (Ve*Vd + Vn*Ve*tanLat); // From
AccelD = invMass * Fd - invRadius * (Vn*Vn + Ve*Ve); // Reference [3]
- Vn += 0.5*dt*(3.0*AccelN - lastAccelN); // Eqn. 3.7
- Ve += 0.5*dt*(3.0*AccelE - lastAccelE); // From
- Vd += 0.5*dt*(3.0*AccelD - lastAccelD); // Reference [3]
+ Vn += 0.5*dt*rate*(3.0*AccelN - lastAccelN); // Eqn. 3.7
+ Ve += 0.5*dt*rate*(3.0*AccelE - lastAccelE); // From
+ Vd += 0.5*dt*rate*(3.0*AccelD - lastAccelD); // Reference [3]
- Vee = Ve - OmegaEarth * (Radius) * cosLat; // From Eq. 3.8
+ Vee = Ve - OMEGAEARTH * (Radius) * cosLat; // From Eq. 3.8
// Reference [3]
lastLatitudeDot = LatitudeDot;
lastLongitudeDot = LongitudeDot;
LatitudeDot = Vn * invRadius;
RadiusDot = -Vd;
- Longitude += 0.5*dt*(LongitudeDot + lastLongitudeDot);
- Latitude += 0.5*dt*(LatitudeDot + lastLatitudeDot);
- Radius += 0.5*dt*(RadiusDot + lastRadiusDot);
+ Longitude += 0.5*dt*rate*(LongitudeDot + lastLongitudeDot);
+ Latitude += 0.5*dt*rate*(LatitudeDot + lastLatitudeDot);
+ Radius += 0.5*dt*rate*(RadiusDot + lastRadiusDot);
PutState();
return false;
void FGPosition::GetState(void)
{
- Q0 = State->GetQ0();
- Q1 = State->GetQ1();
- Q2 = State->GetQ2();
- Q3 = State->GetQ3();
+ dt = State->Getdt();
- Fx = State->GetFx();
- Fy = State->GetFy();
- Fz = State->GetFz();
+ Q0 = Rotation->GetQ0();
+ Q1 = Rotation->GetQ1();
+ Q2 = Rotation->GetQ2();
+ Q3 = Rotation->GetQ3();
- U = State->GetU();
- V = State->GetV();
- W = State->GetW();
+ Fx = Aircraft->GetFx();
+ Fy = Aircraft->GetFy();
+ Fz = Aircraft->GetFz();
+
+ U = Translation->GetU();
+ V = Translation->GetV();
+ W = Translation->GetW();
Latitude = State->Getlatitude();
Longitude = State->Getlongitude();
- invMass = 1.0 / State->Getm();
- invRadius = 1.0 / (State->Geth() + EarthRad);
- Radius = State->Geth() + EarthRad;
- dt = State->Getdt();
+ invMass = 1.0 / Aircraft->GetMass();
+ invRadius = 1.0 / (State->Geth() + EARTHRAD);
+ Radius = State->Geth() + EARTHRAD;
}
void FGPosition::PutState(void)
{
- for (int r=1;r<=3;r++)
- for (int c=1;c<=3;c++)
- State->SetT(r,c,T[r][c]);
-
State->Setlatitude(Latitude);
State->Setlongitude(Longitude);
- State->Seth(Radius - EarthRad);
-
- State->SetVn(Vn); // remove after testing
- State->SetVe(Ve); // remove after testing
- State->SetVd(Vd); // remove after testing
+ State->Seth(Radius - EARTHRAD);
}
********************************************************************************
COMMENTS, REFERENCES, and NOTES
-*******************************************************************************/
+********************************************************************************
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
class FGPosition : public FGModel
{
public:
- FGPosition(void);
+ FGPosition(FGFDMExec*);
~FGPosition(void);
- float GetFn() {return Fn;}
- float GetFe() {return Fe;}
- float GetFd() {return Fd;}
+ inline float GetFn(void) {return Fn;}
+ inline float GetFe(void) {return Fe;}
+ inline float GetFd(void) {return Fd;}
+
+ inline float GetVn(void) {return Vn;}
+ inline float GetVe(void) {return Ve;}
+ inline float GetVd(void) {return Vd;}
+
+ inline float GetT(int r, int c) {return T[r][c];}
+ inline void SetT(float t1, float t2, float t3, float t4, float t5, float t6,
+ float t7, float t8, float t9)
+ {T[1][1]=t1; T[1][2]=t2 ;T[1][3]=t3;
+ T[2][1]=t4; T[2][2]=t5 ;T[2][3]=t6;
+ T[3][1]=t7; T[3][2]=t8 ;T[3][3]=t9;}
bool Run(void);
float Q0, Q1, Q2, Q3;
float Fn, Fe, Fd;
float Fx, Fy, Fz;
+ float U, V, W;
+ float Vn, Ve, Vd, Vee;
float invMass, invRadius;
- float EarthRad, OmegaEarth, Radius;
+ float Radius;
float AccelN, AccelE, AccelD;
float lastAccelN, lastAccelE, lastAccelD;
float LatitudeDot, LongitudeDot, RadiusDot;
float lastLatitudeDot, lastLongitudeDot, lastRadiusDot;
float Longitude, Latitude;
- float U, V, W;
- float Vn, Ve, Vd, Vee;
float dt;
void GetState(void);
void PutState(void);
};
-#ifndef FDM_MAIN
-extern FGPosition* Position;
-#else
-FGPosition* Position;
-#endif
-
/******************************************************************************/
#endif
--------------------------------------------------------------------------------
This class integrates the rotational EOM.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
12/02/98 JSB Created
*******************************************************************************/
#include "FGRotation.h"
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGTranslation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGRotation::FGRotation(void) : FGModel()
+FGRotation::FGRotation(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name, "FGRotation");
Q0dot = Q1dot = Q2dot = Q3dot = 0.0;
+ Pdot = Qdot = Rdot = 0.0;
}
Qdot = (M - (Ixx-Izz)*P*R - Ixz*(P*P - R*R))/Iyy;
Rdot = (N1*Ixx + L2*Ixz) / (Ixx*Izz - Ixz*Ixz);
- P += dt*(lastPdot + Pdot)/2.0;
- Q += dt*(lastQdot + Qdot)/2.0;
- R += dt*(lastRdot + Rdot)/2.0;
+ P += dt*rate*(lastPdot + Pdot)/2.0;
+ Q += dt*rate*(lastQdot + Qdot)/2.0;
+ R += dt*rate*(lastRdot + Rdot)/2.0;
lastQ0dot = Q0dot;
lastQ1dot = Q1dot;
Q2dot = 0.5*(Q0*Q + Q3*P - Q1*R);
Q3dot = 0.5*(Q0*R + Q1*Q - Q2*P);
- Q0 += 0.5*dt*(lastQ0dot + Q0dot);
- Q1 += 0.5*dt*(lastQ1dot + Q1dot);
- Q2 += 0.5*dt*(lastQ2dot + Q2dot);
- Q3 += 0.5*dt*(lastQ3dot + Q3dot);
+ Q0 += 0.5*dt*rate*(lastQ0dot + Q0dot);
+ Q1 += 0.5*dt*rate*(lastQ1dot + Q1dot);
+ Q2 += 0.5*dt*rate*(lastQ2dot + Q2dot);
+ Q3 += 0.5*dt*rate*(lastQ3dot + Q3dot);
sum = Q0*Q0 + Q1*Q1 + Q2*Q2 + Q3*Q3;
void FGRotation::GetState(void)
{
dt = State->Getdt();
- P = State->GetP();
- Q = State->GetQ();
- R = State->GetR();
-
- Pdot = State->GetPdot();
- Qdot = State->GetQdot();
- Rdot = State->GetRdot();
- L = State->GetL();
- M = State->GetM();
- N = State->GetN();
+ L = Aircraft->GetL();
+ M = Aircraft->GetM();
+ N = Aircraft->GetN();
- Ixx = State->GetIxx();
- Iyy = State->GetIyy();
- Izz = State->GetIzz();
- Ixz = State->GetIxz();
-
- Q0 = State->GetQ0();
- Q1 = State->GetQ1();
- Q2 = State->GetQ2();
- Q3 = State->GetQ3();
+ Ixx = Aircraft->GetIxx();
+ Iyy = Aircraft->GetIyy();
+ Izz = Aircraft->GetIzz();
+ Ixz = Aircraft->GetIxz();
for (int r=1;r<=3;r++)
for (int c=1;c<=3;c++)
- T[r][c] = State->GetT(r,c);
+ T[r][c] = Position->GetT(r,c);
}
void FGRotation::PutState(void)
{
- State->SetP(P);
- State->SetQ(Q);
- State->SetR(R);
-
- State->Setphi(phi);
- State->Settht(tht);
- State->Setpsi(psi);
-
- State->SetQ0123(Q0, Q1, Q2, Q3);
}
The order of rotations used in this class corresponds to a 3-2-1 sequence,
or Y-P-R, or Z-Y-X, if you prefer.
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
INCLUDES
*******************************************************************************/
-#include "FGModel.h"
#include <math.h>
+#include "FGModel.h"
/*******************************************************************************
CLASS DECLARATION
class FGRotation : public FGModel
{
public:
- FGRotation(void);
+ FGRotation(FGFDMExec*);
~FGRotation(void);
bool Run(void);
+ inline float GetP(void) {return P;}
+ inline float GetQ(void) {return Q;}
+ inline float GetR(void) {return R;}
+
+ inline float GetPdot(void) {return Pdot;}
+ inline float GetQdot(void) {return Qdot;}
+ inline float GetRdot(void) {return Rdot;}
+
+ inline float Getphi(void) {return phi;}
+ inline float Gettht(void) {return tht;}
+ inline float Getpsi(void) {return psi;}
+
+ inline float GetQ0(void) {return Q0;}
+ inline float GetQ1(void) {return Q1;}
+ inline float GetQ2(void) {return Q2;}
+ inline float GetQ3(void) {return Q3;}
+
+ inline void SetP(float tt) {P = tt;}
+ inline void SetQ(float tt) {Q = tt;}
+ inline void SetR(float tt) {R = tt;}
+
+ inline void SetPQR(float t1, float t2, float t3) {P=t1;
+ Q=t2;
+ R=t3;}
+
+ inline void Setphi(float tt) {phi = tt;}
+ inline void Settht(float tt) {tht = tt;}
+ inline void Setpsi(float tt) {psi = tt;}
+
+ inline void SetEuler(float t1, float t2, float t3) {phi=t1;
+ tht=t2;
+ psi=t3;}
+
+ inline void SetQ0123(float t1, float t2, float t3, float t4) {Q0=t1;
+ Q1=t2;
+ Q2=t3;
+ Q3=t4;}
+
protected:
private:
void PutState(void);
};
-#ifndef FDM_MAIN
-extern FGRotation* Rotation;
-#else
-FGRotation* Rotation;
-#endif
-
/******************************************************************************/
#endif
/*******************************************************************************
-
+
Module: FGState.cpp
Author: Jon Berndt
Date started: 11/17/98
--------------------------------------------------------------------------------
See header file.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
-
11/17/98 JSB Created
********************************************************************************
INCLUDES
*******************************************************************************/
+#include <math.h>
+
#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGAtmosphere.h"
+#include "FGFCS.h"
#include "FGAircraft.h"
-
-#include <math.h>
+#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGState::FGState(void)
+FGState::FGState(FGFDMExec* fdex)
{
- U = V = W = Fx = Fy = Fz = 0.0;
- P = Q = R = L = M = N = 0.0;
- Q0 = Q1 = Q2 = Q3 = 0.0;
- Ixx = Iyy = Izz = Ixz = 0.0;
+ FDMExec = fdex;
+
Vt = 0.0;
latitude = longitude = 0.0;
- alpha = beta = gamma = 0.0;
adot = bdot = 0.0;
- phi = tht = psi = 0.0;
- Udot = Vdot = Wdot = 0.0;
- Pdot = Qdot = Rdot = 0.0;
h = 0.0;
a = 1000.0;
- rho = qbar = 0.0;
+ qbar = 0.0;
sim_time = dt = 0.1;
- m = 0.0;
- g = 32.174;
-
- const float EarthRad = 20925650.0;
}
bool FGState::Reset(char* fname)
{
- char resetDef[200];
+ char resetDef[256];
+ float U, V, W;
+ float phi, tht, psi;
+ float alpha, beta, gamma;
+ float Q0, Q1, Q2, Q3;
+ float T[4][4];
- sprintf(resetDef, "/h/curt/projects/FlightGear/Simulator/FDM/JSBsim/aircraft/%s/%s", Aircraft->GetAircraftName(), fname);
+ sprintf(resetDef, "/h/curt/projects/FlightGear/Simulator/FDM/JSBsim/aircraft/%s/%s", FDMExec->GetAircraft()->GetAircraftName(), fname);
ifstream resetfile(resetDef);
// Change all angular measurements from degrees (as in config file) to radians
+ gamma = 0.0;
if (W != 0.0)
alpha = U*U > 0.0 ? atan2(W, U) : 0.0;
+ else
+ alpha = 0.0;
if (V != 0.0)
beta = U*U+W*W > 0.0 ? atan2(V, (fabs(U)/U)*sqrt(U*U + W*W)) : 0.0;
+ else
+ beta = 0.0;
latitude *= M_PI / 180.0;
longitude *= M_PI / 180.0;
- alpha *= M_PI / 180.0;
- beta *= M_PI / 180.0;
- gamma *= M_PI / 180.0;
phi *= M_PI / 180.0;
tht *= M_PI / 180.0;
psi *= M_PI / 180.0;
+ FDMExec->GetTranslation()->SetUVW(U, V, W);
+ FDMExec->GetRotation()->SetEuler(phi, tht, psi);
+ FDMExec->GetTranslation()->SetABG(alpha, beta, gamma);
+
Vt = sqrt(U*U + V*V + W*W);
qbar = sqrt(U*U + V*V + W*W);
Q2 = sin(psi*0.5)*cos(tht*0.5)*sin(phi*0.5) + cos(psi*0.5)*sin(tht*0.5)*cos(phi*0.5);
Q3 = sin(psi*0.5)*cos(tht*0.5)*cos(phi*0.5) - cos(psi*0.5)*sin(tht*0.5)*sin(phi*0.5);
+ FDMExec->GetRotation()->SetQ0123(Q0, Q1, Q2, Q3);
+
T[1][1] = Q0*Q0 + Q1*Q1 - Q2*Q2 - Q3*Q3;
T[1][2] = 2*(Q1*Q2 + Q0*Q3);
T[1][3] = 2*(Q1*Q3 - Q0*Q2);
T[3][2] = 2*(Q2*Q3 - Q0*Q1);
T[3][3] = Q0*Q0 - Q1*Q1 - Q2*Q2 + Q3*Q3;
+ FDMExec->GetPosition()->SetT(T[1][1], T[1][2], T[1][3],
+ T[2][1], T[2][2], T[2][3],
+ T[3][1], T[3][2], T[3][3]);
+
return true;
} else {
cerr << "Unable to load reset file " << fname << endl;
ofstream datafile(fname);
if (datafile) {
- datafile << U;
- datafile << V;
- datafile << W;
- datafile << Fx;
- datafile << Fy;
- datafile << Fz;
- datafile << P;
- datafile << Q;
- datafile << R;
- datafile << L;
- datafile << M;
- datafile << N;
+ datafile << FDMExec->GetTranslation()->GetU();
+ datafile << FDMExec->GetTranslation()->GetV();
+ datafile << FDMExec->GetTranslation()->GetW();
datafile << latitude;
datafile << longitude;
- datafile << alpha;
- datafile << beta;
- datafile << gamma;
- datafile << phi;
- datafile << tht;
- datafile << psi;
- datafile << Udot;
- datafile << Vdot;
- datafile << Wdot;
- datafile << Pdot;
- datafile << Qdot;
- datafile << Rdot;
+ datafile << FDMExec->GetRotation()->Getphi();
+ datafile << FDMExec->GetRotation()->Gettht();
+ datafile << FDMExec->GetRotation()->Getpsi();
datafile << h;
- datafile << a;
- datafile << rho;
- datafile << qbar;
- datafile << sim_time;
- datafile << dt;
- datafile << g;
datafile.close();
return true;
} else {
ofstream datafile(fname);
if (datafile) {
- datafile << "U: " << U << endl;
- datafile << "V: " << V << endl;
- datafile << "W: " << W << endl;
- datafile << "Fx: " << Fx << endl;
- datafile << "Fy: " << Fy << endl;
- datafile << "Fz: " << Fz << endl;
- datafile << "P: " << P << endl;
- datafile << "Q: " << Q << endl;
- datafile << "R: " << R << endl;
- datafile << "L: " << L << endl;
- datafile << "M: " << M << endl;
- datafile << "N: " << N << endl;
+ datafile << "U: " << FDMExec->GetTranslation()->GetU() << endl;
+ datafile << "V: " << FDMExec->GetTranslation()->GetV() << endl;
+ datafile << "W: " << FDMExec->GetTranslation()->GetW() << endl;
+ datafile << "P: " << FDMExec->GetRotation()->GetP() << endl;
+ datafile << "Q: " << FDMExec->GetRotation()->GetQ() << endl;
+ datafile << "R: " << FDMExec->GetRotation()->GetR() << endl;
+ datafile << "L: " << FDMExec->GetAircraft()->GetL() << endl;
+ datafile << "M: " << FDMExec->GetAircraft()->GetM() << endl;
+ datafile << "N: " << FDMExec->GetAircraft()->GetN() << endl;
datafile << "latitude: " << latitude << endl;
datafile << "longitude: " << longitude << endl;
- datafile << "alpha: " << alpha << endl;
- datafile << "beta: " << beta << endl;
- datafile << "gamma: " << gamma << endl;
- datafile << "phi: " << phi << endl;
- datafile << "tht: " << tht << endl;
- datafile << "psi: " << psi << endl;
- datafile << "Udot: " << Udot << endl;
- datafile << "Vdot: " << Vdot << endl;
- datafile << "Wdot: " << Wdot << endl;
- datafile << "Pdot: " << Pdot << endl;
- datafile << "Qdot: " << Qdot << endl;
- datafile << "Rdot: " << Rdot << endl;
+ datafile << "alpha: " << FDMExec->GetTranslation()->Getalpha() << endl;
+ datafile << "beta: " << FDMExec->GetTranslation()->Getbeta() << endl;
+ datafile << "gamma: " << FDMExec->GetTranslation()->Getgamma() << endl;
+ datafile << "phi: " << FDMExec->GetRotation()->Getphi() << endl;
+ datafile << "tht: " << FDMExec->GetRotation()->Gettht() << endl;
+ datafile << "psi: " << FDMExec->GetRotation()->Getpsi() << endl;
+ datafile << "Pdot: " << FDMExec->GetRotation()->GetPdot() << endl;
+ datafile << "Qdot: " << FDMExec->GetRotation()->GetQdot() << endl;
+ datafile << "Rdot: " << FDMExec->GetRotation()->GetRdot() << endl;
datafile << "h: " << h << endl;
datafile << "a: " << a << endl;
- datafile << "rho: " << rho << endl;
+ datafile << "rho: " << FDMExec->GetAtmosphere()->Getrho() << endl;
datafile << "qbar: " << qbar << endl;
datafile << "sim_time: " << sim_time << endl;
datafile << "dt: " << dt << endl;
- datafile << "g: " << g << endl;
- datafile << "m: " << m << endl;
- datafile << "Ixx: " << Ixx << endl;
- datafile << "Iyy: " << Iyy << endl;
- datafile << "Izz: " << Izz << endl;
- datafile << "Ixz: " << Ixz << endl;
+ datafile << "m: " << FDMExec->GetAircraft()->GetMass() << endl;
datafile.close();
return true;
} else {
bool FGState::DisplayData(void)
{
- cout << "U: " << U << endl;
- cout << "V: " << V << endl;
- cout << "W: " << W << endl;
- cout << "Fx: " << Fx << endl;
- cout << "Fy: " << Fy << endl;
- cout << "Fz: " << Fz << endl;
- cout << "P: " << P << endl;
- cout << "Q: " << Q << endl;
- cout << "R: " << R << endl;
- cout << "L: " << L << endl;
- cout << "M: " << M << endl;
- cout << "N: " << N << endl;
+ cout << "U: " << FDMExec->GetTranslation()->GetU() << endl;
+ cout << "V: " << FDMExec->GetTranslation()->GetV() << endl;
+ cout << "W: " << FDMExec->GetTranslation()->GetW() << endl;
+ cout << "P: " << FDMExec->GetRotation()->GetP() << endl;
+ cout << "Q: " << FDMExec->GetRotation()->GetQ() << endl;
+ cout << "R: " << FDMExec->GetRotation()->GetR() << endl;
+ cout << "L: " << FDMExec->GetAircraft()->GetL() << endl;
+ cout << "M: " << FDMExec->GetAircraft()->GetM() << endl;
+ cout << "N: " << FDMExec->GetAircraft()->GetN() << endl;
cout << "Vt: " << Vt << endl;
cout << "latitude: " << latitude << endl;
cout << "longitude: " << longitude << endl;
- cout << "alpha: " << alpha << endl;
- cout << "beta: " << beta << endl;
- cout << "gamma: " << gamma << endl;
- cout << "phi: " << phi << endl;
- cout << "tht: " << tht << endl;
- cout << "psi: " << psi << endl;
- cout << "Udot: " << Udot << endl;
- cout << "Vdot: " << Vdot << endl;
- cout << "Wdot: " << Wdot << endl;
- cout << "Pdot: " << Pdot << endl;
- cout << "Qdot: " << Qdot << endl;
- cout << "Rdot: " << Rdot << endl;
+ cout << "alpha: " << FDMExec->GetTranslation()->Getalpha() << endl;
+ cout << "beta: " << FDMExec->GetTranslation()->Getbeta() << endl;
+ cout << "gamma: " << FDMExec->GetTranslation()->Getgamma() << endl;
+ cout << "phi: " << FDMExec->GetRotation()->Getphi() << endl;
+ cout << "tht: " << FDMExec->GetRotation()->Gettht() << endl;
+ cout << "psi: " << FDMExec->GetRotation()->Getpsi() << endl;
+ cout << "Pdot: " << FDMExec->GetRotation()->GetPdot() << endl;
+ cout << "Qdot: " << FDMExec->GetRotation()->GetQdot() << endl;
+ cout << "Rdot: " << FDMExec->GetRotation()->GetRdot() << endl;
cout << "h: " << h << endl;
cout << "a: " << a << endl;
- cout << "rho: " << rho << endl;
+ cout << "rho: " << FDMExec->GetAtmosphere()->Getrho() << endl;
cout << "qbar: " << qbar << endl;
cout << "sim_time: " << sim_time << endl;
cout << "dt: " << dt << endl;
- cout << "g: " << g << endl;
- cout << "m: " << m << endl;
- cout << "Ixx: " << Ixx << endl;
- cout << "Iyy: " << Iyy << endl;
- cout << "Izz: " << Izz << endl;
- cout << "Ixz: " << Ixz << endl;
+ cout << "m: " << FDMExec->GetAircraft()->GetMass() << endl;
return true;
}
HISTORY
--------------------------------------------------------------------------------
11/17/98 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
#include <stdio.h>
#include <fstream.h>
+#include "FGDefs.h"
/*******************************************************************************
DEFINES
CLASS DECLARATION
*******************************************************************************/
+class FGFDMExec;
class FGState
{
public:
- FGState(void);
+ FGState(FGFDMExec*);
~FGState(void);
bool Reset(char*);
bool StoreData(char*);
bool DumpData(char*);
bool DisplayData(void);
-
- inline float GetU(void) {return U;}
- inline float GetV(void) {return V;}
- inline float GetW(void) {return W;}
-
- inline float GetVn(void) {return Vn;}
- inline float GetVe(void) {return Ve;}
- inline float GetVd(void) {return Vd;}
inline float GetVt(void) {return Vt;}
- inline float GetFx(void) {return Fx;}
- inline float GetFy(void) {return Fy;}
- inline float GetFz(void) {return Fz;}
-
- inline float GetP(void) {return P;}
- inline float GetQ(void) {return Q;}
- inline float GetR(void) {return R;}
-
- inline float GetQ0(void) {return Q0;}
- inline float GetQ1(void) {return Q1;}
- inline float GetQ2(void) {return Q2;}
- inline float GetQ3(void) {return Q3;}
-
- inline float GetL(void) {return L;}
- inline float GetM(void) {return M;}
- inline float GetN(void) {return N;}
-
- inline float GetIxx(void) const {return Ixx;}
- inline float GetIyy(void) const {return Iyy;}
- inline float GetIzz(void) const {return Izz;}
- inline float GetIxz(void) const {return Ixz;}
-
inline float Getlatitude(void) {return latitude;}
inline float Getlongitude(void) {return longitude;}
inline float GetGeodeticLat(void) {return GeodeticLat;}
-
- inline float Getalpha(void) {return alpha;}
- inline float Getbeta(void) {return beta;}
- inline float Getgamma(void) {return gamma;}
inline float Getadot(void) {return adot;}
inline float Getbdot(void) {return bdot;}
-
- inline float GetUdot(void) {return Udot;}
- inline float GetVdot(void) {return Vdot;}
- inline float GetWdot(void) {return Wdot;}
-
- inline float GetPdot(void) {return Pdot;}
- inline float GetQdot(void) {return Qdot;}
- inline float GetRdot(void) {return Rdot;}
inline float Geth(void) {return h;}
inline float Geta(void) {return a;}
inline float GetMach(void) {return Mach;}
-
- inline float Getrho(void) {return rho;}
+
inline float Getsim_time(void) {return sim_time;}
inline float Getdt(void) {return dt;}
- inline float Getphi(void) {return phi;}
- inline float Gettht(void) {return tht;}
- inline float Getpsi(void) {return psi;}
-
- inline float Getg(void) {return g;}
- inline float Getm(void) {return m;}
-
inline float Getqbar(void) {return qbar;}
- inline float GetT(int r, int c) {return T[r][c];}
-
- inline void SetU(float tt) {U = tt;}
- inline void SetV(float tt) {V = tt;}
- inline void SetW(float tt) {W = tt;}
inline void SetVt(float tt) {Vt = tt;}
- inline void SetVn(float tt) {Vn = tt;}
- inline void SetVe(float tt) {Ve = tt;}
- inline void SetVd(float tt) {Vd = tt;}
-
- inline void SetFx(float tt) {Fx = tt;}
- inline void SetFy(float tt) {Fy = tt;}
- inline void SetFz(float tt) {Fz = tt;}
-
- inline void SetP(float tt) {P = tt;}
- inline void SetQ(float tt) {Q = tt;}
- inline void SetR(float tt) {R = tt;}
-
- inline void SetL(float tt) {L = tt;}
- inline void SetM(float tt) {M = tt;}
- inline void SetN(float tt) {N = tt;}
-
- inline void SetIxx(float tt) {Ixx = tt;}
- inline void SetIyy(float tt) {Iyy = tt;}
- inline void SetIzz(float tt) {Izz = tt;}
- inline void SetIxz(float tt) {Ixz = tt;}
-
inline void Setlatitude(float tt) {latitude = tt;}
inline void Setlongitude(float tt) {longitude = tt;}
inline void SetGeodeticLat(float tt) {GeodeticLat = tt;}
- inline void Setalpha(float tt) {alpha = tt;}
- inline void Setbeta(float tt) {beta = tt;}
- inline void Setgamma(float tt) {gamma = tt;}
-
inline void Setadot(float tt) {adot = tt;}
inline void Setbdot(float tt) {bdot = tt;}
- inline void SetUdot(float tt) {Udot = tt;}
- inline void SetVdot(float tt) {Vdot = tt;}
- inline void SetWdot(float tt) {Wdot = tt;}
-
- inline void SetPdot(float tt) {Pdot = tt;}
- inline void SetQdot(float tt) {Qdot = tt;}
- inline void SetRdot(float tt) {Rdot = tt;}
-
- inline void Setphi(float tt) {phi = tt;}
- inline void Settht(float tt) {tht = tt;}
- inline void Setpsi(float tt) {psi = tt;}
-
- inline void Setg(float tt) {g = tt;}
- inline void Setm(float tt) {m = tt;}
inline void Setqbar(float tt) {qbar = tt;}
inline void Seth(float tt) {h = tt;}
inline void Seta(float tt) {a = tt;}
inline void SetMach(float tt) {Mach = tt;}
- inline void Setrho(float tt) {rho = tt;}
inline float Setsim_time(float tt) {sim_time = tt; return sim_time;}
- inline void Setdt(float tt) {dt = tt;}
- inline void SetQ0123(float q0, float q1, float q2, float q3) {Q0=q0;Q1=q1;Q2=q2;Q3=q3;}
- inline void SetT(int r, int c, float tt) {T[r][c] = tt;}
+ inline void Setdt(float tt) {dt = tt;}
inline float IncrTime(void) {sim_time+=dt;return sim_time;}
- const float EarthRad;
-
private:
- float U, V, W, Fx, Fy, Fz; // A/C body axis velocities and forces
- float P, Q, R, L, M, N; // A/C body axis rates and moments
- float Q0, Q1, Q2, Q3; // Quaternion elements
- float Ixx, Iyy, Izz, Ixz; // Moments of Inertia
float Vt; // Total velocity
- float Vn, Ve, Vd; // North, East, and Down local velocities
float latitude, longitude; // position
float GeodeticLat; // Geodetic Latitude
- float alpha, beta, gamma; // angle of attack, sideslip, and roll
float adot, bdot; // alpha dot and beta dot
- float phi, tht, psi; // Euler angles
- float Udot, Vdot, Wdot; // A/C body axis accelerations
- float Pdot, Qdot, Rdot; // A/C body axis rotational accelerations
float h, a; // altitude above sea level, speed of sound
- float rho, qbar; // density of air in lb/ft^3, dynamic pressure
+ float qbar; // dynamic pressure
float sim_time, dt;
- float m, g; // mass and acceleration of gravity
- float T[4][4]; // Local to Body transformation matrix
float Mach; // Mach number
-protected:
+ FGFDMExec* FDMExec;
+protected:
};
-#ifndef FDM_MAIN
-extern FGState* State;
-#else
-FGState* State;
-#endif
-
/******************************************************************************/
#endif
--------------------------------------------------------------------------------
See header file.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
-
01/21/99 JSB Created
********************************************************************************
FGTank::FGTank(ifstream& acfile)
{
char type[20];
-
- acfile >> type;
+
+ acfile >> type; // Type = 0: rocket, 1: piston
if (strstr(type,"FUEL")) Type = 0;
else if (strstr(type,"OXIDIZER")) Type = 1;
else Type = -1;
- acfile >> X;
- acfile >> Y;
- acfile >> Z;
- acfile >> Radius;
- acfile >> Capacity;
- acfile >> Contents;
+ acfile >> X; // inches
+ acfile >> Y; // "
+ acfile >> Z; // "
+ acfile >> Radius; // "
+ acfile >> Capacity; // pounds (amount it can hold)
+ acfile >> Contents; // pounds (amount it is holding)
Selected = true;
- PctFull = 100.0*Contents/Capacity;
+ PctFull = 100.0*Contents/Capacity; // percent full; 0 to 100.0
}
HISTORY
--------------------------------------------------------------------------------
01/21/99 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
int GetType(void) {return Type;}
bool GetSelected(void) {return Selected;}
float GetPctFull(void) {return PctFull;}
+ float GetContents(void) {return Contents;}
private:
float X, Y, Z;
};
/******************************************************************************/
-#endif
+#endif
\ No newline at end of file
--------------------------------------------------------------------------------
This class integrates the translational EOM.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
12/02/98 JSB Created
*******************************************************************************/
#include "FGTranslation.h"
+#include "FGRotation.h"
+#include "FGAtmosphere.h"
+#include "FGState.h"
+#include "FGFDMExec.h"
+#include "FGFCS.h"
+#include "FGAircraft.h"
+#include "FGPosition.h"
+#include "FGAuxiliary.h"
+#include "FGOutput.h"
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-FGTranslation::FGTranslation(void) : FGModel()
+FGTranslation::FGTranslation(FGFDMExec* fdmex) : FGModel(fdmex)
{
strcpy(Name, "FGTranslation");
+ Udot = Vdot = Wdot = 0.0;
}
lastVdot = Vdot;
lastWdot = Wdot;
- Udot = V*R - W*Q + Fx/m;
- Vdot = W*P - U*R + Fy/m;
- Wdot = U*Q - V*P + Fz/m;
+ Udot = V*R - W*Q + Fx/Mass;
+ Vdot = W*P - U*R + Fy/Mass;
+ Wdot = U*Q - V*P + Fz/Mass;
- U += 0.5*dt*(lastUdot + Udot);
- V += 0.5*dt*(lastVdot + Vdot);
- W += 0.5*dt*(lastWdot + Wdot);
+ U += 0.5*dt*rate*(lastUdot + Udot);
+ V += 0.5*dt*rate*(lastVdot + Vdot);
+ W += 0.5*dt*rate*(lastWdot + Wdot);
Vt = U*U+V*V+W*W > 0.0 ? sqrt(U*U + V*V + W*W) : 0.0;
{
dt = State->Getdt();
- P = State->GetP();
- Q = State->GetQ();
- R = State->GetR();
-
- Fx = State->GetFx();
- Fy = State->GetFy();
- Fz = State->GetFz();
-
- m = State->Getm();
- g = State->Getg();
- rho = State->Getrho();
+ P = Rotation->GetP();
+ Q = Rotation->GetQ();
+ R = Rotation->GetR();
- phi = State->Getphi();
- tht = State->Gettht();
- psi = State->Getpsi();
+ Fx = Aircraft->GetFx();
+ Fy = Aircraft->GetFy();
+ Fz = Aircraft->GetFz();
- U = State->GetU();
- V = State->GetV();
- W = State->GetW();
+ Mass = Aircraft->GetMass();
+ rho = Atmosphere->Getrho();
- Udot = State->GetUdot();
- Vdot = State->GetVdot();
- Wdot = State->GetWdot();
-
- alpha = State->Getalpha();
- beta = State->Getbeta();
+ phi = Rotation->Getphi();
+ tht = Rotation->Gettht();
+ psi = Rotation->Getpsi();
}
void FGTranslation::PutState(void)
{
- State->SetU(U);
- State->SetV(V);
- State->SetW(W);
-
State->SetVt(Vt);
State->Setqbar(qbar);
-
- State->SetUdot(Udot);
- State->SetVdot(Vdot);
- State->SetWdot(Wdot);
-
- State->Setalpha(alpha);
- State->Setbeta(beta);
}
The order of rotations used in this class corresponds to a 3-2-1 sequence,
or Y-P-R, or Z-Y-X, if you prefer.
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
INCLUDES
*******************************************************************************/
-#include "FGModel.h"
#include <math.h>
+#include "FGModel.h"
/*******************************************************************************
CLASS DECLARATION
class FGTranslation : public FGModel
{
public:
- FGTranslation(void);
+ FGTranslation(FGFDMExec*);
~FGTranslation(void);
+ inline float GetU(void) {return U;}
+ inline float GetV(void) {return V;}
+ inline float GetW(void) {return W;}
+
+ inline float GetUdot(void) {return Udot;}
+ inline float GetVdot(void) {return Vdot;}
+ inline float GetWdot(void) {return Wdot;}
+
+ inline float Getalpha(void) {return alpha;}
+ inline float Getbeta (void) {return beta; }
+ inline float Getgamma(void) {return gamma;}
+
+ inline void SetU(float tt) {U = tt;}
+ inline void SetV(float tt) {V = tt;}
+ inline void SetW(float tt) {W = tt;}
+
+ inline void SetUVW(float t1, float t2, float t3) {U=t1; V=t2; W=t3;}
+
+ inline void Setalpha(float tt) {alpha = tt;}
+ inline void Setbeta (float tt) {beta = tt;}
+ inline void Setgamma(float tt) {gamma = tt;}
+
+ inline void SetABG(float t1, float t2, float t3) {alpha=t1; beta=t2; gamma=t3;}
+
bool Run(void);
protected:
private:
- float U, V, W;
+ float U, V, W; // Body frame velocities owned by FGTranslation
float P, Q, R;
float Vt, qbar;
float Udot, Vdot, Wdot;
float lastUdot, lastVdot, lastWdot;
float phi, tht, psi;
float Fx, Fy, Fz;
- float m, g, dt;
- float alpha, beta;
+ float Mass, dt;
+ float alpha, beta, gamma;
float rho;
void GetState(void);
void PutState(void);
};
-#ifndef FDM_MAIN
-extern FGTranslation* Translation;
-#else
-FGTranslation* Translation;
-#endif
-
/******************************************************************************/
#endif
This class is a container for all utility classes used by the flight dynamics
model.
-ARGUMENTS
---------------------------------------------------------------------------------
-
-
HISTORY
--------------------------------------------------------------------------------
01/09/99 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
DEFINES
*******************************************************************************/
-
-/********************************************************************************
+
+/*******************************************************************************
INCLUDES
*******************************************************************************/
#include "FGUtility.h"
#include "FGState.h"
+#include "FGFDMExec.h"
#include <math.h>
-#ifdef HAVE_NCURSES
- #include <ncurses.h>
-#endif
-
/*******************************************************************************
************************************ CODE **************************************
*******************************************************************************/
-const float EarthRadSqrd = 437882827922500.0;
-const float OneSecond = 4.848136811E-6;
-const float Eccentricity = 0.996647186;
-const float EccentSqrd = Eccentricity*Eccentricity;
-const float EPS = 0.081819221;
-
FGUtility::FGUtility()
{
+ // Move constant stuff to here (if any) so it won't take CPU time
+ // in the methods below.
+ SeaLevelR = EARTHRAD * ECCENT;
}
FGUtility::~FGUtility()
{
}
-
+
float FGUtility::ToGeodetic()
{
- float GeodeticLat, Latitude, Radius, Altitude, SeaLevelR;
+ float GeodeticLat, Latitude, Radius, Altitude;
float tanLat, xAlpha, muAlpha, sinmuAlpha, denom, rhoAlpha, dMu;
float lPoint, lambdaSL, sinlambdaSL, dLambda, rAlpha;
Latitude = State->Getlatitude();
- Radius = State->Geth() + State->EarthRad;
+ Radius = State->Geth() + EARTHRAD;
- if (( M_PI_2 - Latitude < OneSecond) ||
- ( M_PI_2 + Latitude < OneSecond)) { // Near a pole
+ if (( M_PI_2 - Latitude < ONESECOND) ||
+ ( M_PI_2 + Latitude < ONESECOND)) { // Near a pole
GeodeticLat = Latitude;
- SeaLevelR = State->EarthRad * Eccentricity;
Altitude = Radius - SeaLevelR;
} else {
tanLat = tan(Latitude);
- xAlpha = Eccentricity*State->EarthRad /
- sqrt(tanLat*tanLat + EccentSqrd);
- muAlpha = atan2(sqrt(EarthRadSqrd - xAlpha*xAlpha), Eccentricity*xAlpha);
+ xAlpha = ECCENT*EARTHRAD /
+ sqrt(tanLat*tanLat + ECCENTSQRD);
+ muAlpha = atan2(sqrt(EARTHRADSQRD - xAlpha*xAlpha), ECCENT*xAlpha);
if (Latitude < 0.0) muAlpha = -muAlpha;
lPoint = Radius - rAlpha;
Altitude = lPoint*cos(dLambda);
denom = sqrt(1-EPS*EPS*sinmuAlpha*sinmuAlpha);
- rhoAlpha = State->EarthRad*(1.0 - EPS) / (denom*denom*denom);
+ rhoAlpha = EARTHRAD*(1.0 - EPS) / (denom*denom*denom);
dMu = atan2(lPoint*sin(dLambda),rhoAlpha + Altitude);
State->SetGeodeticLat(muAlpha - dMu);
- lambdaSL = atan(EccentSqrd*tan(GeodeticLat));
+ lambdaSL = atan(ECCENTSQRD*tan(GeodeticLat));
sinlambdaSL = sin(lambdaSL);
- SeaLevelR = sqrt(EarthRadSqrd / (1 + (1/EccentSqrd - 1.0)* sinlambdaSL*sinlambdaSL));
+ SeaLevelR = sqrt(EARTHRADSQRD / (1 + INVECCENTSQRDM1* sinlambdaSL*sinlambdaSL));
}
return 0.0;
}
float lambdaSL, sinlambdaSL, coslambdaSL, sinMu, cosMu, py, px;
float Altitude, SeaLevelR;
- lambdaSL = atan(EccentSqrd*tan(State->GetGeodeticLat()));
+ lambdaSL = atan(ECCENTSQRD*tan(State->GetGeodeticLat()));
sinlambdaSL = sin(lambdaSL);
coslambdaSL = cos(lambdaSL);
sinMu = sin(State->GetGeodeticLat());
cosMu = cos(State->GetGeodeticLat());
- SeaLevelR = sqrt(EarthRadSqrd /
- (1 + ((1/EccentSqrd)-1)*sinlambdaSL*sinlambdaSL));
+ SeaLevelR = sqrt(EARTHRADSQRD /
+ (1 + INVECCENTSQRDM1*sinlambdaSL*sinlambdaSL));
px = SeaLevelR*coslambdaSL + Altitude*cosMu;
py = SeaLevelR*sinlambdaSL + Altitude*sinMu;
State->Setlatitude(atan2(py,px));
HISTORY
--------------------------------------------------------------------------------
01/09/99 JSB Created
-*******************************************************************************/
-/*******************************************************************************
+********************************************************************************
SENTRY
*******************************************************************************/
CLASS DECLARATION
*******************************************************************************/
+class FGFDMExec;
+class FGState;
+
class FGUtility
{
public:
protected:
private:
-
+ float SeaLevelR;
+ FGState* State;
+ FGFDMExec* FDMExec;
};
/******************************************************************************/