]> git.mxchange.org Git - flightgear.git/blob - src/Environment/atmosphere.hxx
NavDisplay - custom symbol support enabled.
[flightgear.git] / src / Environment / atmosphere.hxx
1 // atmosphere.hxx -- routines to model the air column
2 //
3 // Written by David Megginson, started February 2002.
4 // Modified by John Denker to correct physics errors in 2007
5 //
6 // Copyright (C) 2002  David Megginson - david@megginson.com
7 //
8 // This program is free software; you can redistribute it and/or
9 // modify it under the terms of the GNU General Public License as
10 // published by the Free Software Foundation; either version 2 of the
11 // License, or (at your option) any later version.
12 //
13 // This program is distributed in the hope that it will be useful, but
14 // WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16 // General Public License for more details.
17 //
18 // You should have received a copy of the GNU General Public License
19 // along with this program; if not, write to the Free Software
20 // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21 //
22 // $Id$
23
24
25 #ifndef _ATMOSPHERE_HXX
26 #define _ATMOSPHERE_HXX
27
28 #include <simgear/compiler.h>
29 #include <simgear/math/interpolater.hxx>
30
31 #include <cmath>
32 #include <utility>
33
34 /**
35  * Model the atmosphere in a way consistent with the laws
36  * of physics.
37  *
38  * Each instance of this class models a particular air mass.
39  * You may freely move up, down, or sideways in the air mass.
40  * In contrast, if you want to compare different air masses,
41  * you should use a separate instance for each one.
42  *
43  * See also ./environment.hxx
44  */
45
46 #define SCD(name,val) const double name(val)
47 namespace atmodel {
48     SCD(g, 9.80665);            // [m/s/s] acceleration of gravity
49     SCD(mm, .0289644);          // [kg/mole] molar mass of air (dry?)
50     SCD(Rgas, 8.31432);         // [J/K/mole] gas constant
51     SCD(inch, 0.0254);          // [m] definition of inch
52     SCD(foot, 12 * inch);       // [m]
53     SCD(inHg, 101325.0 / 760 * 1000 * inch);  // [Pa] definition of inHg
54     SCD(mbar, 100.);            // [Pa] definition of millibar
55     SCD(freezing, 273.15);      // [K] centigrade - kelvin offset
56     SCD(nm, 1852);              // [m] nautical mile (NIST)
57     SCD(sm, 5280*foot);         // [m] nautical mile (NIST)
58
59     namespace ISA {
60         SCD(P0, 101325.0);              // [pascals] ISA sea-level pressure
61         SCD(T0, 15. + freezing);        // [K] ISA sea-level temperature
62         SCD(lam0, .0065);               // [K/m] ISA troposphere lapse rate
63     }
64 }
65 #undef SCD
66
67
68
69 class ISA_layer {
70 public:
71   double height;
72   double temp;
73   double lapse;
74   ISA_layer(int, double h, double, double, double, double t, double,
75                     double l=-1, double=0)
76    :  height(h),        // [meters]
77       temp(t),          // [kelvin]
78       lapse(l)          // [K/m]
79   {}
80 };
81
82 extern const ISA_layer ISA_def[];
83
84 std::pair<double,double> PT_vs_hpt(
85           const double hh, 
86           const double _p0 = atmodel::ISA::P0,
87           const double _t0 = atmodel::ISA::T0);
88
89 double P_layer(const double height, const double href,
90   const double Pref, const double Tref, const double lapse );
91
92 double T_layer(const double height, const double href,
93   const double Pref, const double Tref,  const double lapse );
94
95 // The base class is little more than a namespace.
96 // It has no constructor, no destructor, and no variables.
97 class FGAtmo {
98 public:
99     double a_vs_p(const double press, const double qnh = atmodel::ISA::P0);
100     double fake_T_vs_a_us(const double h_ft, 
101                 const double Tsl = atmodel::ISA::T0) const;
102     double fake_dp_vs_a_us(const double dpsl, const double h_ft);
103     void check_one(const double height);
104
105 // Altimeter setting _in pascals_ 
106 //  ... caller gets to convert to inHg or millibars
107 // Field elevation in m
108 // Field pressure in pascals
109 // Valid for fields within the troposphere only.
110     double QNH(const double field_elev, const double field_press);
111 /**
112  * Invert the QNH calculation to get the field pressure from a metar
113  * report. Valid for fields within the troposphere only.
114  * @param field_elev field elevation in m
115  * @param qnh altimeter setting in pascals
116  * @return field pressure _in pascals_. Caller gets to convert to inHg
117  * or millibars 
118  */
119     static double fieldPressure(const double field_elev, const double qnh);
120 };
121
122
123
124 class FGAtmoCache : FGAtmo {
125     friend class FGAltimeter;
126     SGInterpTable * a_tvs_p;    // _tvs_ means "tabulated versus"
127
128 public:
129     FGAtmoCache();
130     ~FGAtmoCache();
131     void tabulate();
132     void cache();
133     void check_model();  // debug
134 };
135
136
137
138 class FGAltimeter : public FGAtmoCache {
139     double kset;
140     double kft;
141
142 public:
143     FGAltimeter();
144     double reading_ft(const double p_inHg,
145             const double set_inHg = atmodel::ISA::P0/atmodel::inHg);
146     inline double press_alt_ft(const double p_inHg) {
147         return a_tvs_p->interpolate(p_inHg);
148     }
149     inline double kollsman_ft(const double set_inHg) {
150         return a_tvs_p->interpolate(set_inHg);
151     }
152
153     // debug
154     void dump_stack();
155     void dump_stack1(const double Tref);
156 };
157
158 #endif // _ATMOSPHERE_HXX