1 /*******************************************************************************
3 Header: FGInitialCondition.h
7 ------------- Copyright (C) 1999 Anthony K. Peden (apeden@earthlink.net) -------------
9 This program is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free Software
11 Foundation; either version 2 of the License, or (at your option) any later
14 This program is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16 FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
19 You should have received a copy of the GNU General Public License along with
20 this program; if not, write to the Free Software Foundation, Inc., 59 Temple
21 Place - Suite 330, Boston, MA 02111-1307, USA.
23 Further information about the GNU General Public License can also be found on
24 the world wide web at http://www.gnu.org.
28 --------------------------------------------------------------------------------
32 FUNCTIONAL DESCRIPTION
33 --------------------------------------------------------------------------------
35 The purpose of this class is to take a set of initial conditions and provide
36 a kinematically consistent set of body axis velocity components, euler
37 angles, and altitude. This class does not attempt to trim the model i.e.
38 the sim will most likely start in a very dynamic state (unless, of course,
39 you have chosen your IC's wisely) even after setting it up with this class.
41 ********************************************************************************
43 *******************************************************************************/
45 #ifndef FGINITIALCONDITION_H
46 #define FGINITIALCONDITION_H
48 /*******************************************************************************
50 *******************************************************************************/
52 #include "FGFDMExec.h"
53 #include "FGAtmosphere.h"
56 /*******************************************************************************
58 *******************************************************************************/
60 typedef enum { setvt, setvc, setve, setmach } speedset;
64 With a valid object of FGFDMExec and an aircraft model loaded
65 FGInitialCondition fgic=new FGInitialCondition(FDMExec);
66 fgic->SetVcalibratedKtsIC()
67 fgic->SetAltitudeFtIC();
71 //to directly into Run
72 FDMExec->GetState()->Initialize(fgic)
76 //or to loop the sim w/o integrating
82 Since vc, ve, vt, and mach all represent speed, the remaining
83 three are recalculated each time one of them is set (using the
84 current altitude). The most recent speed set is remembered so
85 that if and when altitude is reset, the last set speed is used
86 to recalculate the remaining three. Setting any of the body
87 components forces a recalculation of vt and vt then becomes the
88 most recent speed set.
90 Alpha,Gamma, and Theta:
91 This class assumes that it will be used to set up the sim for a
92 steady, zero pitch rate condition. This entails the assumption
93 that alpha=theta-gamma. Since any two of those angles specifies
94 the third (again, for zero pitch rate) gamma (flight path angle)
95 is favored when setting alpha and theta and alpha is favored when
97 set alpha : recalculate theta using gamma as currently set
98 set theta : recalculate alpha using gamma as currently set
99 set gamma : recalculate theta using alpha as currently set
101 The idea being that gamma is most interesting to pilots (since it
102 is indicative of climb rate).
104 Setting climb rate is, for the purpose of this discussion,
105 considered equivalent to setting gamma.
108 class FGInitialCondition {
111 FGInitialCondition(FGFDMExec *fdmex);
112 ~FGInitialCondition(void);
114 void SetVcalibratedKtsIC(float tt);
115 void SetVequivalentKtsIC(float tt);
116 void SetVtrueKtsIC(float tt);
117 void SetMachIC(float tt);
119 void SetUBodyFpsIC(float tt);
120 void SetVBodyFpsIC(float tt);
121 void SetWBodyFpsIC(float tt);
123 void SetAltitudeFtIC(float tt);
124 void SetAltitudeAGLFtIC(float tt);
126 //"vertical" flight path, recalculate theta
127 inline void SetFlightPathAngleDegIC(float tt) { SetFlightPathAngleRadIC(gamma=tt*DEGTORAD); }
128 void SetFlightPathAngleRadIC(float tt);
130 void SetClimbRateFpmIC(float tt);
131 //use currently stored gamma, recalcualte theta
132 inline void SetAlphaDegIC(float tt) { alpha=tt*DEGTORAD; getTheta(); }
133 inline void SetAlphaRadIC(float tt) { alpha=tt; getTheta(); }
134 //use currently stored gamma, recalcualte alpha
135 inline void SetPitchAngleDegIC(float tt) { theta=tt*DEGTORAD; getAlpha(); }
136 inline void SetPitchAngleRadIC(float tt) { theta=tt; getAlpha(); }
138 inline void SetBetaDegIC(float tt) { beta=tt*DEGTORAD; getTheta();}
139 inline void SetBetaRadIC(float tt) { beta=tt; getTheta(); }
141 inline void SetRollAngleDegIC(float tt) { phi=tt*DEGTORAD; getTheta(); }
142 inline void SetRollAngleRadIC(float tt) { phi=tt; getTheta(); }
144 inline void SetHeadingDegIC(float tt) { psi=tt*DEGTORAD; }
145 inline void SetHeadingRadIC(float tt) { psi=tt; }
147 inline void SetLatitudeDegIC(float tt) { latitude=tt*DEGTORAD; }
148 inline void SetLatitudeRadIC(float tt) { latitude=tt; }
150 inline void SetLongitudeDegIC(float tt) { longitude=tt*DEGTORAD; }
151 inline void SetLongitudeRadIC(float tt) { longitude=tt; }
153 inline float GetVcalibratedKtsIC(void) { return vc*FPSTOKTS; }
154 inline float GetVequivalentKtsIC(void) { return ve*FPSTOKTS; }
155 inline float GetVtrueKtsIC(void) { return vt*FPSTOKTS; }
156 inline float GetVtrueFpsIC(void) { return vt; }
157 inline float GetMachIC(void) { return mach; }
159 inline float GetAltitudeFtIC(void) { return altitude; }
161 inline float GetFlightPathAngleDegIC(void) { return gamma*RADTODEG; }
162 inline float GetFlightPathAngleRadIC(void) { return gamma; }
164 inline float GetClimbRateFpmIC(void) { return hdot*60; }
165 inline float GetClimbRateFpsIC(void) { return hdot; }
167 inline float GetAlphaDegIC(void) { return alpha*RADTODEG; }
168 inline float GetAlphaRadIC(void) { return alpha; }
170 inline float GetPitchAngleDegIC(void) { return theta*RADTODEG; }
171 inline float GetPitchAngleRadIC(void) { return theta; }
174 inline float GetBetaDegIC(void) { return beta*RADTODEG; }
175 inline float GetBetaRadIC(void) { return beta*RADTODEG; }
177 inline float GetRollAngleDegIC(void) { return phi*RADTODEG; }
178 inline float GetRollAngleRadIC(void) { return phi; }
180 inline float GetHeadingDegIC(void) { return psi*RADTODEG; }
181 inline float GetHeadingRadIC(void) { return psi; }
183 inline float GetLatitudeDegIC(void) { return latitude*RADTODEG; }
184 inline float GetLatitudeRadIC(void) { return latitude; }
186 inline float GetLongitudeDegIC(void) { return longitude*RADTODEG; }
187 inline float GetLongitudeRadIC(void) { return longitude; }
189 inline float GetUBodyFpsIC(void) { return vt*cos(alpha)*cos(beta); }
190 inline float GetVBodyFpsIC(void) { return vt*sin(beta); }
191 inline float GetWBodyFpsIC(void) { return vt*sin(alpha)*cos(beta); }
193 inline float GetThetaRadIC(void) { return theta; }
194 inline float GetPhiRadIC(void) { return phi; }
195 inline float GetPsiRadIC(void) { return psi; }
201 float alpha,beta,gamma,theta,phi,psi;
204 float latitude,longitude;
207 float xlo, xhi,xmin,xmax;
209 typedef float (FGInitialCondition::*fp)(float x);
212 speedset lastSpeedSet;
219 bool getMachFromVcas(float *Mach,float vcas);
221 float GammaEqOfTheta(float Theta);
222 float GammaEqOfAlpha(float Alpha);
223 float calcVcas(float Mach);
225 bool findInterval(float x,float guess);
226 bool solve(float *y, float x);