// This file is in the Public Domain and comes with no warranty.
#include "submodel.hxx"
+
+#include <simgear/structure/exception.hxx>
+#include <simgear/misc/sg_path.hxx>
+
#include <Main/fg_props.hxx>
#include <Main/util.hxx>
#include <AIModel/AIManager.hxx>
SubmodelSystem::SubmodelSystem ()
{
- firing = false;
x_offset = y_offset = 0.0;
z_offset = -4.0;
pitch_offset = 2.0;
void
SubmodelSystem::init ()
{
- _serviceable_node = fgGetNode("/systems/submodel/serviceable", true);
-
- _trigger_node = fgGetNode("/systems/submodel/trigger", true);
- _trigger_node->setBoolValue(false);
+ load();
+ _serviceable_node = fgGetNode("/sim/systems/submodels/serviceable", true);
- _amount_node = fgGetNode("/systems/submodel/amount", true);
-
_user_lat_node = fgGetNode("/position/latitude-deg", true);
_user_lon_node = fgGetNode("/position/longitude-deg", true);
_user_alt_node = fgGetNode("/position/altitude-ft", true);
_user_speed_node = fgGetNode("/velocities/uBody-fps", true);
- elapsed_time = 0.0;
- initial_velocity = 2750.0; // feet per second, .50 caliber
-
ai = (FGAIManager*)globals->get_subsystem("ai_model");
}
void
SubmodelSystem::update (double dt)
{
- if (_trigger_node->getBoolValue()) {
- if (_serviceable_node->getBoolValue()) {
- if (_amount_node->getIntValue() > 0) {
- firing = true;
- release(dt);
- }
- }
- } else {
- if (firing){
- firing = false;
- elapsed_time = 0.0;
- }
+ if (!(_serviceable_node->getBoolValue())) return;
+
+ submodel_iterator = submodels.begin();
+ while(submodel_iterator != submodels.end()) {
+
+ if ((*submodel_iterator)->trigger->getBoolValue()) {
+ if ((*submodel_iterator)->count > 0) {
+ release( (*submodel_iterator), dt);
+ }
+ }
+ ++submodel_iterator;
}
+
}
bool
-SubmodelSystem::release (double dt)
+SubmodelSystem::release (submodel* sm, double dt)
{
- // releases a submodel every 0.25 seconds
- elapsed_time += dt;
- if (elapsed_time < 0.25) return false;
- elapsed_time = 0.0;
-
- int rval = ai->createBallistic( "Models/Geometry/tracer.ac",
- _user_lat_node->getDoubleValue(),
- _user_lon_node->getDoubleValue(),
- _user_alt_node->getDoubleValue() + z_offset,
- _user_heading_node->getDoubleValue() + yaw_offset,
- _user_pitch_node->getDoubleValue() + pitch_offset,
- _user_speed_node->getDoubleValue() + initial_velocity );
-
- _amount_node->setIntValue( _amount_node->getIntValue() - 1);
+ sm->timer += dt;
+ if (sm->timer < sm->delay) return false;
+ sm->timer = 0.0;
+
+ transform(sm); // calculate submodel's initial conditions in world-coordinates
+
+ int rval = ai->createBallistic( sm->model, IC.lat, IC.lon, IC.alt, IC.azimuth,
+ IC.elevation, IC.speed );
+ sm->count--;
return true;
}
+void
+SubmodelSystem::load ()
+{
+ int i;
+ SGPropertyNode *path = fgGetNode("/sim/systems/submodels/path");
+ SGPropertyNode root;
+
+ if (path) {
+ SGPath config( globals->get_fg_root() );
+ config.append( path->getStringValue() );
+
+ try {
+ readProperties(config.str(), &root);
+ } catch (const sg_exception &e) {
+ SG_LOG(SG_GENERAL, SG_ALERT,
+ "Unable to read submodels file: ");
+ cout << config.str() << endl;
+ return;
+ }
+ }
+
+ int count = root.nChildren();
+ for (i = 0; i < count; i++) {
+ // cout << "Reading submodel " << i << endl;
+ submodel* sm = new submodel;
+ submodels.push_back( sm );
+ SGPropertyNode * entry_node = root.getChild(i);
+ sm->trigger = fgGetNode(entry_node->getStringValue("trigger", "none"), true);
+ sm->name = entry_node->getStringValue("name", "none_defined");
+ sm->model = entry_node->getStringValue("model", "Models/Geometry/tracer.ac");
+ sm->speed = entry_node->getDoubleValue("speed", 0.0);
+ sm->repeat = entry_node->getBoolValue ("repeat", false);
+ sm->delay = entry_node->getDoubleValue("delay", 0.25);
+ sm->count = entry_node->getIntValue ("count", 1);
+ sm->slaved = entry_node->getBoolValue ("slaved", false);
+ sm->x_offset = entry_node->getDoubleValue("x-offset", 0.0);
+ sm->y_offset = entry_node->getDoubleValue("y_offset", 0.0);
+ sm->z_offset = entry_node->getDoubleValue("z-offset", 0.0);
+ sm->yaw_offset = entry_node->getDoubleValue("yaw-offset", 0.0);
+ sm->pitch_offset = entry_node->getDoubleValue("pitch-offset", 0.0);
+
+ sm->trigger->setBoolValue(false);
+ sm->timer = 0.0;
+ }
+
+
+ submodel_iterator = submodels.begin();
+ // cout << submodels.size() << " submodels read." << endl;
+}
+
+void
+SubmodelSystem::transform( submodel* sm)
+{
+IC.lat = _user_lat_node->getDoubleValue();
+IC.lon = _user_lon_node->getDoubleValue();
+IC.alt = _user_alt_node->getDoubleValue();
+IC.azimuth = _user_heading_node->getDoubleValue() + sm->yaw_offset;
+IC.elevation = _user_pitch_node->getDoubleValue() + sm->pitch_offset;
+IC.speed = _user_speed_node->getDoubleValue() + sm->speed;
+}
+
// end of submodel.cxx
#include <simgear/props/props.hxx>
#include <simgear/structure/subsystem_mgr.hxx>
#include <AIModel/AIManager.hxx>
+#include <vector>
+#include <string>
+SG_USING_STD(vector);
+SG_USING_STD(string);
class SubmodelSystem : public SGSubsystem
public:
+ typedef struct {
+ SGPropertyNode_ptr trigger;
+ string name;
+ string model;
+ double speed;
+ bool slaved;
+ bool repeat;
+ double delay;
+ double timer;
+ int count;
+ double x_offset;
+ double y_offset;
+ double z_offset;
+ double yaw_offset;
+ double pitch_offset;
+ } submodel;
+
+ typedef struct {
+ double lat;
+ double lon;
+ double alt;
+ double azimuth;
+ double elevation;
+ double speed;
+ } IC_struct;
+
SubmodelSystem ();
~SubmodelSystem ();
+ void load ();
void init ();
void bind ();
void unbind ();
void update (double dt);
- bool release (double dt);
+ bool release (submodel* sm, double dt);
+ void transform (submodel* sm);
private:
+ typedef vector <submodel*> submodel_vector_type;
+ typedef submodel_vector_type::iterator submodel_vector_iterator;
+
+ submodel_vector_type submodels;
+ submodel_vector_iterator submodel_iterator;
+
+
double x_offset, y_offset, z_offset;
double pitch_offset, yaw_offset;
SGPropertyNode_ptr _serviceable_node;
- SGPropertyNode_ptr _trigger_node;
- SGPropertyNode_ptr _amount_node;
-
SGPropertyNode_ptr _user_lat_node;
SGPropertyNode_ptr _user_lon_node;
SGPropertyNode_ptr _user_heading_node;
SGPropertyNode_ptr _user_yaw_node;
SGPropertyNode_ptr _user_speed_node;
- double elapsed_time;
FGAIManager* ai;
- double initial_velocity;
- bool firing;
+ IC_struct IC;
};
#endif // __SYSTEMS_SUBMODEL_HXX