#include <vector>
#include <simgear/sg_inlines.h>
-#include <simgear/math/SGMath.hxx>
#include <simgear/math/sg_geodesy.hxx>
+#include <simgear/math/sg_random.h>
#include <math.h>
#include <Main/util.hxx>
-#include <Main/viewer.hxx>
+#include <Viewer/viewer.hxx>
#include <Scenery/scenery.hxx>
-#include <Scenery/tilemgr.hxx>
#include "AIEscort.hxx"
+using std::string;
+
FGAIEscort::FGAIEscort() :
FGAIShip(otEscort),
-_selected_ac(0),
_relbrg (0),
-_stn_truebrg(0),
_parent_speed(0),
-_stn_limit(0),
-_stn_angle_limit(0),
-_stn_speed(0),
+_interval(0),
+_stn_truebrg(0),
_stn_height(0),
+_stn_speed(0),
+_stn_angle_limit(0),
+_stn_limit(0),
_max_speed(0),
-_interval(0),
_MPControl(false),
_patrol(false),
-_stn_deg_true(false),
-_parent("")
+_stn_deg_true(false)
{
invisible = false;
void FGAIEscort::bind() {
FGAIShip::bind();
- props->tie("station/rel-bearing-deg",
+ tie("station/rel-bearing-deg",
SGRawValuePointer<double>(&_stn_relbrg));
- props->tie("station/true-bearing-deg",
+ tie("station/true-bearing-deg",
SGRawValuePointer<double>(&_stn_truebrg));
- props->tie("station/range-nm",
+ tie("station/range-nm",
SGRawValuePointer<double>(&_stn_range));
- props->tie("station/range-limit-nm",
+ tie("station/range-limit-nm",
SGRawValuePointer<double>(&_stn_limit));
- props->tie("station/angle-limit-deg",
+ tie("station/angle-limit-deg",
SGRawValuePointer<double>(&_stn_angle_limit));
- props->tie("station/speed-kts",
+ tie("station/speed-kts",
SGRawValuePointer<double>(&_stn_speed));
- props->tie("station/height-ft",
+ tie("station/height-ft",
SGRawValuePointer<double>(&_stn_height));
- props->tie("controls/update-interval-sec",
+ tie("controls/update-interval-sec",
SGRawValuePointer<double>(&_interval));
- props->tie("controls/parent-mp-control",
+ tie("controls/parent-mp-control",
SGRawValuePointer<bool>(&_MPControl));
- props->tie("station/target-range-nm",
+ tie("station/target-range-nm",
SGRawValuePointer<double>(&_tgtrange));
- props->tie("station/target-brg-deg-t",
+ tie("station/target-brg-deg-t",
SGRawValuePointer<double>(&_tgtbrg));
- props->tie("station/patrol",
+ tie("station/patrol",
SGRawValuePointer<bool>(&_patrol));
}
-void FGAIEscort::unbind() {
- FGAIShip::unbind();
-
- props->untie("station/rel-bearing-deg");
- props->untie("station/true-bearing-deg");
- props->untie("station/range-nm");
- props->untie("station/range-limit-nm");
- props->untie("station/angle-limit-deg");
- props->untie("station/speed-kts");
- props->untie("station/height-ft");
- props->untie("controls/update-interval-sec");
-
-}
-
bool FGAIEscort::init(bool search_in_AI_path) {
if (!FGAIShip::init(search_in_AI_path))
return false;
+ reinit();
+ return true;
+}
+void FGAIEscort::reinit() {
invisible = false;
no_roll = false;
props->setStringValue("controls/parent-name", _parent.c_str());
- setParent();
- pos = _tgtpos;
- speed = _parent_speed;
- hdg = _parent_hdg;
- return true;
+ if (setParentNode()){
+ setParent();
+ pos = _tgtpos;
+ speed = _parent_speed;
+ hdg = _parent_hdg;
+ }
+
+ FGAIShip::reinit();
}
void FGAIEscort::update(double dt) {
_patrol = p;
}
-void FGAIEscort::setParentName(const string& p) {
- _parent = p;
-}
-
bool FGAIEscort::getGroundElev(SGGeod inpos) {
double height_m ;
- if (globals->get_scenery()->get_elevation_m(SGGeod::fromGeodM(inpos, 3000), height_m, &_material,0)){
+ const simgear::BVHMaterial* mat = 0;
+ if (globals->get_scenery()->get_elevation_m(SGGeod::fromGeodM(inpos, 3000), height_m, &mat, 0)){
+ const SGMaterial* material = dynamic_cast<const SGMaterial*>(mat);
_ht_agl_ft = inpos.getElevationFt() - height_m * SG_METER_TO_FEET;
- if (_material) {
- const vector<string>& names = _material->get_names();
+ if (material) {
+ const std::vector<std::string>& names = material->get_names();
- _solid = _material->get_solid();
+ _solid = material->get_solid();
if (!names.empty())
props->setStringValue("material/name", names[0].c_str());
}
-void FGAIEscort::setParent() {
-
- const SGPropertyNode *ai = fgGetNode("/ai/models", true);
-
- for (int i = ai->nChildren() - 1; i >= -1; i--) {
- const SGPropertyNode *model;
-
- if (i < 0) { // last iteration: selected model
- model = _selected_ac;
- } else {
- model = ai->getChild(i);
- string path = ai->getPath();
- const string name = model->getStringValue("name");
-
- if (!model->nChildren()){
- continue;
- }
- if (name == _parent) {
- _selected_ac = model; // save selected model for last iteration
- break;
- }
-
- }
- if (!model)
- continue;
-
- }// end for loop
-
- if (_selected_ac != 0){
- const string name = _selected_ac->getStringValue("name");
- double lat = _selected_ac->getDoubleValue("position/latitude-deg");
- double lon = _selected_ac->getDoubleValue("position/longitude-deg");
- double elevation = _selected_ac->getDoubleValue("position/altitude-ft");
- _MPControl = _selected_ac->getBoolValue("controls/mp-control");
-
- _selectedpos.setLatitudeDeg(lat);
- _selectedpos.setLongitudeDeg(lon);
- _selectedpos.setElevationFt(elevation);
-
- _parent_speed = _selected_ac->getDoubleValue("velocities/speed-kts");
- _parent_hdg = _selected_ac->getDoubleValue("orientation/true-heading-deg");
-
- if(!_stn_deg_true){
- _stn_truebrg = calcTrueBearingDeg(_stn_brg, _parent_hdg);
- _stn_relbrg = _stn_brg;
- //cout << _name <<" set rel"<<endl;
- } else {
- _stn_truebrg = _stn_brg;
- _stn_relbrg = calcRelBearingDeg(_stn_brg, _parent_hdg);
- //cout << _name << " set true"<<endl;
- }
-
- double course2;
+void FGAIEscort::setParent()
+{
+ double lat = _selected_ac->getDoubleValue("position/latitude-deg");
+ double lon = _selected_ac->getDoubleValue("position/longitude-deg");
+ double elevation = _selected_ac->getDoubleValue("position/altitude-ft");
+ _MPControl = _selected_ac->getBoolValue("controls/mp-control");
+
+ _selectedpos.setLatitudeDeg(lat);
+ _selectedpos.setLongitudeDeg(lon);
+ _selectedpos.setElevationFt(elevation);
+
+ _parent_speed = _selected_ac->getDoubleValue("velocities/speed-kts");
+ _parent_hdg = _selected_ac->getDoubleValue("orientation/true-heading-deg");
+
+ if(!_stn_deg_true){
+ _stn_truebrg = calcTrueBearingDeg(_stn_brg, _parent_hdg);
+ _stn_relbrg = _stn_brg;
+ //cout << _name <<" set rel"<<endl;
+ } else {
+ _stn_truebrg = _stn_brg;
+ _stn_relbrg = calcRelBearingDeg(_stn_brg, _parent_hdg);
+ //cout << _name << " set true"<<endl;
+ }
- SGGeodesy::direct( _selectedpos, _stn_truebrg, _stn_range * SG_NM_TO_METER,
- _tgtpos, course2);
+ double course2;
- _tgtpos.setElevationFt(_stn_height);
+ SGGeodesy::direct( _selectedpos, _stn_truebrg, _stn_range * SG_NM_TO_METER,
+ _tgtpos, course2);
- calcRangeBearing(pos.getLatitudeDeg(), pos.getLongitudeDeg(),
- _tgtpos.getLatitudeDeg(), _tgtpos.getLongitudeDeg(), _tgtrange, _tgtbrg);
+ _tgtpos.setElevationFt(_stn_height);
- _relbrg = calcRelBearingDeg(_tgtbrg, hdg);
+ calcRangeBearing(pos.getLatitudeDeg(), pos.getLongitudeDeg(),
+ _tgtpos.getLatitudeDeg(), _tgtpos.getLongitudeDeg(), _tgtrange, _tgtbrg);
- } else {
- SG_LOG(SG_GENERAL, SG_ALERT, "AIEscort: " << _name
- << " parent not found: dying ");
- setDie(true);
- }
+ _relbrg = calcRelBearingDeg(_tgtbrg, hdg);
}
range = distance * SG_METER_TO_NM;
}
-double FGAIEscort::calcRelBearingDeg(double bearing, double heading)
-{
- double angle = bearing - heading;
- SG_NORMALIZE_RANGE(angle, -180.0, 180.0);
- return angle;
-}
-
double FGAIEscort::calcTrueBearingDeg(double bearing, double heading)
{
double angle = bearing + heading;
return angle;
}
-double FGAIEscort::calcRecipBearingDeg(double bearing)
-{
- double angle = bearing - 180;
- SG_NORMALIZE_RANGE(angle, 0.0, 360.0);
- return angle;
-}
-
SGVec3d FGAIEscort::getCartHitchPosAt(const SGVec3d& _off) const {
double hdg = _selected_ac->getDoubleValue("orientation/true-heading-deg");
double pitch = _selected_ac->getDoubleValue("orientation/pitch-deg");
// these are the AI rules for the manoeuvring of escorts
if (_MPControl && _tgtrange > 4 * _stn_limit){
- SG_LOG(SG_GENERAL, SG_ALERT, "AIEscort: " << _name
+ SG_LOG(SG_AI, SG_ALERT, "AIEscort: " << _name
<< " re-aligning to MP pos");
pos = _tgtpos;
speed = 0;
setParent();
setStationSpeed();
- //getGroundElev(pos);
_dt_count = 0;
}
-// end AIGroundvehicle
+// end AIEscort