JSBSim Flight Dynamics Model  1.0 (02 March 2017)
An Open Source Flight Dynamics and Control Software Library in C++
FGInput.cpp
1 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2 
3  Module: FGInput.cpp
4  Author: Jon Berndt
5  Date started: 12/02/98
6  Purpose: Manage input of sim parameters from socket
7  Called by: FGSimExec
8 
9  ------------- Copyright (C) 1999 Jon S. Berndt (jon@jsbsim.org) -------------
10 
11  This program is free software; you can redistribute it and/or modify it under
12  the terms of the GNU Lesser General Public License as published by the Free Software
13  Foundation; either version 2 of the License, or (at your option) any later
14  version.
15 
16  This program is distributed in the hope that it will be useful, but WITHOUT
17  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
18  FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
19  details.
20 
21  You should have received a copy of the GNU Lesser General Public License along with
22  this program; if not, write to the Free Software Foundation, Inc., 59 Temple
23  Place - Suite 330, Boston, MA 02111-1307, USA.
24 
25  Further information about the GNU Lesser General Public License can also be found on
26  the world wide web at http://www.gnu.org.
27 
28 FUNCTIONAL DESCRIPTION
29 --------------------------------------------------------------------------------
30 This is the place where you create output routines to dump data for perusal
31 later.
32 
33 HISTORY
34 --------------------------------------------------------------------------------
35 12/02/98 JSB Created
36 
37 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
38 INCLUDES
39 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
40 
41 #include "FGInput.h"
42 #include "FGFDMExec.h"
43 #include "input_output/FGInputSocket.h"
44 #include "input_output/FGUDPInputSocket.h"
45 #include "input_output/FGXMLFileRead.h"
46 #include "input_output/FGXMLElement.h"
47 #include "input_output/FGModelLoader.h"
48 
49 using namespace std;
50 
51 namespace JSBSim {
52 
53 IDENT(IdSrc,"$Id: FGInput.cpp,v 1.35 2017/02/25 14:23:19 bcoconni Exp $");
54 IDENT(IdHdr,ID_INPUT);
55 
56 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
57 CLASS IMPLEMENTATION
58 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
59 
60 FGInput::FGInput(FGFDMExec* fdmex) : FGModel(fdmex)
61 {
62  Name = "FGInput";
63  enabled = true;
64 
65  Debug(0);
66 }
67 
68 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
69 
70 FGInput::~FGInput()
71 {
72  vector<FGInputType*>::iterator it;
73  for (it = InputTypes.begin(); it != InputTypes.end(); ++it)
74  delete (*it);
75 
76  Debug(1);
77 }
78 
79 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
80 
82 {
83  // Unlike the other FGModel classes, properties listed in the <input> section
84  // are not intended to create new properties. For that reason, FGInput
85  // cannot load its XML directives with FGModel::Load().
86  // Instead FGModelLoader::Open() and FGModel::PreLoad() must be explicitely
87  // called.
88  FGModelLoader ModelLoader(this);
89  Element* element = ModelLoader.Open(el);
90 
91  if (!element) return false;
92 
93  FGModel::PreLoad(element, PropertyManager);
94 
95  size_t idx = InputTypes.size();
96  string type = element->GetAttributeValue("type");
97  FGInputType* Input = 0;
98 
99  if (debug_lvl > 0) cout << endl << " Input data set: " << idx << " " << endl;
100 
101  type = to_upper(type);
102 
103  if (type.empty() || type == "SOCKET") {
104  Input = new FGInputSocket(FDMExec);
105  } else if (type == "QTJSBSIM") {
106  Input = new FGUDPInputSocket(FDMExec);
107  } else if (type != string("NONE")) {
108  cerr << element->ReadFrom()
109  << "Unknown type of input specified in config file" << endl;
110  }
111 
112  if (!Input) return false;
113 
114  Input->SetIdx(idx);
115  Input->Load(element);
116  PostLoad(element, PropertyManager);
117 
118  InputTypes.push_back(Input);
119 
120  Debug(2);
121  return true;
122 }
123 
124 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
125 
127 {
128  bool ret = false;
129 
130  if (!FGModel::InitModel()) return false;
131 
132  vector<FGInputType*>::iterator it;
133  for (it = InputTypes.begin(); it != InputTypes.end(); ++it)
134  ret &= (*it)->InitModel();
135 
136  return ret;
137 }
138 
139 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
140 
141 bool FGInput::Run(bool Holding)
142 {
143  if (FDMExec->GetTrimStatus()) return true;
144  if (FGModel::Run(Holding)) return true;
145  if (!enabled) return true;
146 
147  vector<FGInputType*>::iterator it;
148  for (it = InputTypes.begin(); it != InputTypes.end(); ++it)
149  (*it)->Run(Holding);
150 
151  return false;
152 }
153 
154 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
155 
156 bool FGInput::SetDirectivesFile(const SGPath& fname)
157 {
159  Element* document = XMLFile.LoadXMLDocument(fname);
160  bool result = Load(document);
161 
162  if (!result)
163  cerr << endl << "Aircraft input element has problems in file " << fname << endl;
164 
165  return result;
166 }
167 
168 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
169 
170 bool FGInput::Toggle(int idx)
171 {
172  if (idx >= (int)0 && idx < (int)InputTypes.size())
173  return InputTypes[idx]->Toggle();
174 
175  return false;
176 }
177 
178 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
179 
180 bool FGInput::SetInputName(unsigned int idx, const std::string& name)
181 {
182  if (idx >= InputTypes.size()) return false;
183 
184  InputTypes[idx]->SetInputName(name);
185  return true;
186 }
187 
188 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
189 
190 string FGInput::GetInputName(unsigned int idx) const
191 {
192  string name;
193 
194  if (idx < InputTypes.size())
195  name = InputTypes[idx]->GetInputName();
196  return name;
197 }
198 
199 
200 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
201 // The bitmasked value choices are as follows:
202 // unset: In this case (the default) JSBSim would only print
203 // out the normally expected messages, essentially echoing
204 // the config files as they are read. If the environment
205 // variable is not set, debug_lvl is set to 1 internally
206 // 0: This requests JSBSim not to output any messages
207 // whatsoever.
208 // 1: This value explicity requests the normal JSBSim
209 // startup messages
210 // 2: This value asks for a message to be printed out when
211 // a class is instantiated
212 // 4: When this value is set, a message is displayed when a
213 // FGModel object executes its Run() method
214 // 8: When this value is set, various runtime state variables
215 // are printed out periodically
216 // 16: When set various parameters are sanity checked and
217 // a message is printed out when they go out of bounds
218 
219 void FGInput::Debug(int from)
220 {
221  string scratch="";
222 
223  if (debug_lvl <= 0) return;
224 
225  if (debug_lvl & 1) { // Standard console startup message output
226  if (from == 0) { // Constructor
227  }
228  if (from == 2) {
229  }
230  }
231  if (debug_lvl & 2 ) { // Instantiation/Destruction notification
232  if (from == 0) cout << "Instantiated: FGInput" << endl;
233  if (from == 1) cout << "Destroyed: FGInput" << endl;
234  }
235  if (debug_lvl & 4 ) { // Run() method entry print for FGModel-derived objects
236  }
237  if (debug_lvl & 8 ) { // Runtime state variables
238  }
239  if (debug_lvl & 16) { // Sanity checking
240  }
241  if (debug_lvl & 64) {
242  if (from == 0) { // Constructor
243  cout << IdSrc << endl;
244  cout << IdHdr << endl;
245  }
246  }
247 }
248 }
std::string GetAttributeValue(const std::string &key)
Retrieves an attribute.
virtual bool Load(Element *el)
Init the input directives from an XML file (implement the FGModel interface).
Definition: FGInputType.cpp:81
void SetIdx(unsigned int idx)
Set the idx for this input instance.
Definition: FGInputType.cpp:74
STL namespace.
Implements a UDP input socket.
std::string GetInputName(unsigned int idx) const
Get the name identifier to which the input will be directed.
Definition: FGInput.cpp:190
Abstract class to provide functions generic to all the input directives.
Definition: FGInputType.h:79
virtual bool Run(bool Holding)
Runs the model; called by the Executive.
Definition: FGModel.cpp:92
bool Toggle(int idx)
Toggles the input generation of each input instance.
Definition: FGInput.cpp:170
bool Run(bool Holding)
Runs the Input model; called by the Executive Can pass in a value indicating if the executive is dire...
Definition: FGInput.cpp:141
bool SetDirectivesFile(const SGPath &fname)
Adds a new input instance to the Input Manager.
Definition: FGInput.cpp:156
bool Load(const SGPath &rstname, bool useStoredPath=true)
Loads the initial conditions.
bool Load(Element *el)
Load the input directives and adds a new input instance to the Input Manager list.
Definition: FGInput.cpp:81
This class is solely for the purpose of determining what type of file is given on the command line...
Definition: JSBSim.cpp:152
std::string ReadFrom(void) const
Return a string that contains a description of the location where the current XML element was read fr...
bool InitModel(void)
Initializes the instance.
Definition: FGInput.cpp:126
bool SetInputName(unsigned int idx, const std::string &name)
Overwrites the name identifier under which the input will be logged.
Definition: FGInput.cpp:180
Implements the input from a socket.
Definition: FGInputSocket.h:68