1
0
Fork 0

Development for two new features:

* Some support for geometry information provided by the custom scenery
   project. Current support is for AI groundnets and runway use files only
   since this is a switch that involves a lot of data verification and
   updating, during the transistion the actual path where the data can be
   read from is user configurable. setting the property

   /sim/traffic-manager/use-custom-scenery-data to true

  will cause flightgear to read the ground networks from the scenery
  directory (--{fg-scenery}/Airports/[I]/[C]/[A]/[ICAO].groundnet.xml to be
  precise). Setting this property to false will retain the original
  behvior.
* For departing aircraft, runway takeoff calculations will be done on the
  basis of the performance database. For testing purposes, a performance
 estimate for a heavy jet has been added.
This commit is contained in:
durk 2009-01-30 18:48:44 +00:00 committed by Tim Moore
parent 5efca258c1
commit c6f88e5b9b
11 changed files with 160 additions and 83 deletions

View file

@ -353,7 +353,6 @@ bool FGAIAircraft::loadNextLeg() {
return false;
}
setCallSign(trafficRef->getCallSign());
//props->setStringValue("callsign", callsign.c_str());
leg = 1;
fp->setLeg(leg);
}
@ -366,10 +365,11 @@ bool FGAIAircraft::loadNextLeg() {
} else {
double cruiseAlt = trafficRef->getCruiseAlt() * 100;
fp->create (dep,
fp->create (this,
dep,
arr,
leg,
cruiseAlt, //(trafficRef->getCruiseAlt() * 100), // convert from FL to feet
cruiseAlt,
trafficRef->getSpeed(),
_getLatitude(),
_getLongitude(),

View file

@ -76,6 +76,7 @@ public:
virtual const char* getTypeString(void) const { return "aircraft"; }
// included as performance data needs them, who else?
inline PerformanceData* getPerformance() { return _performance; };
inline bool onGround() const { return no_roll; };
inline double getSpeed() const { return speed; };
inline double getRoll() const { return roll; };

View file

@ -101,7 +101,8 @@ FGAIFlightPlan::FGAIFlightPlan(const string& filename)
// Position computed by the traffic manager, as well
// as setting speeds and altitude computed by the
// traffic manager.
FGAIFlightPlan::FGAIFlightPlan(const std::string& p,
FGAIFlightPlan::FGAIFlightPlan(FGAIAircraft *ac,
const std::string& p,
double course,
time_t start,
FGAirport *dep,
@ -202,7 +203,7 @@ FGAIFlightPlan::FGAIFlightPlan(const std::string& p,
SG_LOG(SG_GENERAL, SG_INFO, "Route from " << dep->getId() << " to " << arr->getId() << ". Set leg to : " << leg);
wpt_iterator = waypoints.begin();
create(dep,arr, leg, alt, speed, lat, lon,
create(ac, dep,arr, leg, alt, speed, lat, lon,
firstLeg, radius, fltType, acType, airline);
wpt_iterator = waypoints.begin();
//cerr << "after create: " << (*wpt_iterator)->name << endl;

View file

@ -23,16 +23,20 @@
#include <vector>
#include <string>
#include <Airports/simple.hxx>
#include <Navaids/awynet.hxx>
#include "AIBase.hxx"
using std::vector;
using std::string;
class FGTaxiRoute;
class FGRunway;
class FGAIAircraft;
class FGAIFlightPlan {
@ -56,7 +60,8 @@ public:
} waypoint;
FGAIFlightPlan(const string& filename);
FGAIFlightPlan(const std::string& p,
FGAIFlightPlan(FGAIAircraft *,
const std::string& p,
double course,
time_t start,
FGAirport *dep,
@ -86,7 +91,7 @@ public:
double getBearing(double lat, double lon, waypoint* next) const;
time_t getStartTime() const { return start_time; }
void create(FGAirport *dep, FGAirport *arr, int leg, double alt, double speed, double lat, double lon,
void create(FGAIAircraft *, FGAirport *dep, FGAirport *arr, int leg, double alt, double speed, double lat, double lon,
bool firstLeg, double radius, const string& fltType, const string& aircraftType, const string& airline);
void setLeg(int val) { leg = val;}
@ -126,7 +131,7 @@ private:
void createPushBack(bool, FGAirport*, double, double, double, const string&, const string&, const string&);
void createPushBackFallBack(bool, FGAirport*, double, double, double, const string&, const string&, const string&);
void createTakeOff(bool, FGAirport *, double, const string&);
void createTakeOff(FGAIAircraft *, bool, FGAirport *, double, const string&);
void createClimb(bool, FGAirport *, double, double, const string&);
void createCruise(bool, FGAirport*, FGAirport*, double, double, double, double, const string&);
void createDecent(FGAirport *, const string&);

View file

@ -26,6 +26,8 @@
#include <simgear/math/sg_geodesy.hxx>
#include <Airports/runways.hxx>
#include <Airports/dynamics.hxx>
#include <AIAircraft.hxx>
#include <performancedata.hxx>
#include <Environment/environment_mgr.hxx>
#include <Environment/environment.hxx>
@ -41,7 +43,7 @@
// Check lat/lon values during initialization;
void FGAIFlightPlan::create(FGAirport *dep, FGAirport *arr, int legNr,
void FGAIFlightPlan::create(FGAIAircraft *ac, FGAirport *dep, FGAirport *arr, int legNr,
double alt, double speed, double latitude,
double longitude, bool firstFlight,double radius,
const string& fltType, const string& aircraftType,
@ -58,7 +60,7 @@ void FGAIFlightPlan::create(FGAirport *dep, FGAirport *arr, int legNr,
createTakeoffTaxi(firstFlight, dep, radius, fltType, aircraftType, airline);
break;
case 3:
createTakeOff(firstFlight, dep, speed, fltType);
createTakeOff(ac, firstFlight, dep, speed, fltType);
break;
case 4:
createClimb(firstFlight, dep, speed, alt, fltType);
@ -336,13 +338,24 @@ void FGAIFlightPlan::createLandingTaxi(FGAirport *apt,
* CreateTakeOff
* initialize the Aircraft at the parking location
******************************************************************/
void FGAIFlightPlan::createTakeOff(bool firstFlight, FGAirport *apt, double speed, const string &fltType)
void FGAIFlightPlan::createTakeOff(FGAIAircraft *ac, bool firstFlight, FGAirport *apt, double speed, const string &fltType)
{
double accel = ac->getPerformance()->acceleration();
double vRotate = ac->getPerformance()->vRotate();
// Acceleration = dV / dT
// Acceleration X dT = dV
// dT = dT / Acceleration
//d = (Vf^2 - Vo^2) / (2*a)
double accelTime = (vRotate - 15) / accel;
cerr << "Using " << accelTime << " as total acceleration time" << endl;
double accelDistance = (vRotate*vRotate - 15*15) / (2*accel);
cerr << "Using " << accelDistance << " " << accel << " " << vRotate << endl;
waypoint *wpt;
// Get the current active runway, based on code from David Luff
// This should actually be unified and extended to include
// Preferential runway use schema's
// NOTE: DT (2009-01-18: IIRC, this is currently already the case,
// because the getActive runway function takes care of that.
if (firstFlight)
{
string rwyClass = getRunwayClassFromTrafficType(fltType);
@ -358,7 +371,8 @@ void FGAIFlightPlan::createTakeOff(bool firstFlight, FGAirport *apt, double spee
//Start Climbing to 3000 ft. Let's do this
// at the center of the runway for now:
wpt = cloneWithPos(wpt, "SOC", rwy->geod());
SGGeod rotate = rwy->pointOnCenterline(105.0+accelDistance);
wpt = cloneWithPos(wpt, "SOC", rotate);
wpt->altitude = airportElev+1000;
wpt->on_ground = false;
waypoints.push_back(wpt);
@ -367,7 +381,7 @@ void FGAIFlightPlan::createTakeOff(bool firstFlight, FGAirport *apt, double spee
wpt->altitude = airportElev+3000;
waypoints.push_back(wpt);
// Finally, add two more waypoints, so that aircraft will remain under
// Finally, add two more waypoints, so that aircraft will remain under
// Tower control until they have reached the 3000 ft climb point
SGGeod pt = rwy->pointOnCenterline(5000 + rwy->lengthM() * 0.5);
wpt = cloneWithPos(wpt, "5000 ft", pt);

View file

@ -9,7 +9,7 @@ class FGAIAircraft;
/**
Data storage for aircraft performance data. This is used to properly simulate the flight of AIAircrafts.
@author Thomas Förster <t.foerster@biologie.hu-berlin.de>
@author Thomas F<EFBFBD>rster <t.foerster@biologie.hu-berlin.de>
*/
class PerformanceData
{
@ -38,10 +38,11 @@ public:
bool gearExtensible(const FGAIAircraft* ac);
inline double climbRate() { return _climbRate; };
inline double descentRate() { return _descentRate; };
inline double vRotate() { return _vRotate; };
inline double maximumBankAngle() { return _maxbank; };
inline double climbRate () { return _climbRate; };
inline double descentRate () { return _descentRate; };
inline double vRotate () { return _vRotate; };
inline double maximumBankAngle () { return _maxbank; };
inline double acceleration () { return _acceleration; };
private:
double _acceleration;

View file

@ -3,6 +3,9 @@
PerformanceDB::PerformanceDB()
{
// these are the 6 classes originally defined in the PERFSTRUCT
// Plus a few more for testing
registerPerformanceData("heavy_jet", new PerformanceData(
4.0, 2.0, 3000.0, 1500.0, 150.0, 160.0, 300.0, 430.0, 300.0, 170.0, 150.0, 15.0));
registerPerformanceData("light", new PerformanceData(
2.0, 2.0, 450.0, 1000.0, 70.0, 70.0, 80.0, 100.0, 80.0, 70.0, 60.0, 15.0));
registerPerformanceData("ww2_fighter", new PerformanceData(

View file

@ -26,40 +26,89 @@
XMLLoader::XMLLoader() {}
XMLLoader::~XMLLoader() {}
string XMLLoader::expandICAODirs(const string in){
cerr << "Expanding " << in << endl;
if (in.size() == 4) {
char buffer[11];
snprintf(buffer, 11, "%c/%c/%c", in[0], in[1], in[2]);
cerr << "result: " << buffer << endl;
return string(buffer);
} else {
return in;
}
//exit(1);
}
void XMLLoader::load(FGAirportDynamics* d) {
FGAirportDynamicsXMLLoader visitor(d);
if (fgGetBool("/sim/traffic-manager/use-custom-scenery-data") == false) {
SGPath parkpath( globals->get_fg_root() );
parkpath.append( "/AI/Airports/" );
parkpath.append( d->getId() );
parkpath.append( "parking.xml" );
if (parkpath.exists()) {
try {
readXML(parkpath.str(), visitor);
d->init();
} catch (const sg_exception &e) {
//cerr << "unable to read " << parkpath.str() << endl;
}
catch (const sg_exception &e) {
}
} else {
string_list sc = globals->get_fg_scenery();
char buffer[32];
snprintf(buffer, 32, "%s.groundnet.xml", d->getId().c_str() );
string airportDir = XMLLoader::expandICAODirs(d->getId());
for (string_list_iterator i = sc.begin(); i != sc.end(); i++) {
SGPath parkpath( *i );
parkpath.append( "Airports" );
parkpath.append ( airportDir );
parkpath.append( string (buffer) );
if (parkpath.exists()) {
try {
readXML(parkpath.str(), visitor);
d->init();
}
catch (const sg_exception &e) {
}
return;
}
}
}
}
void XMLLoader::load(FGRunwayPreference* p) {
FGRunwayPreferenceXMLLoader visitor(p);
if (fgGetBool("/sim/traffic-manager/use-custom-scenery-data") == false) {
SGPath rwyPrefPath( globals->get_fg_root() );
rwyPrefPath.append( "AI/Airports/" );
rwyPrefPath.append( p->getId() );
rwyPrefPath.append( "rwyuse.xml" );
//if (ai_dirs.find(id.c_str()) != ai_dirs.end()
// && rwyPrefPath.exists())
if (rwyPrefPath.exists()) {
try {
readXML(rwyPrefPath.str(), visitor);
} catch (const sg_exception &e) {
//cerr << "unable to read " << rwyPrefPath.str() << endl;
}
catch (const sg_exception &e) {
}
}
} else {
string_list sc = globals->get_fg_scenery();
char buffer[32];
snprintf(buffer, 32, "%s.rwyuse.xml", p->getId().c_str() );
string airportDir = expandICAODirs(p->getId());
for (string_list_iterator i = sc.begin(); i != sc.end(); i++) {
SGPath rwypath( *i );
rwypath.append( "Airports" );
rwypath.append ( airportDir );
rwypath.append( string(buffer) );
if (rwypath.exists()) {
try {
readXML(rwypath.str(), visitor);
}
catch (const sg_exception &e) {
}
return;
}
}
}
}

View file

@ -22,11 +22,12 @@ class FGAirportDynamics;
class FGRunwayPreference;
class XMLLoader {
public:
XMLLoader();
~XMLLoader();
static string expandICAODirs(const string in);
static void load(FGRunwayPreference* p);
static void load(FGAirportDynamics* d);

View file

@ -208,9 +208,11 @@ void FGGlobals::set_fg_scenery (const string &scenery) {
ulDir *td = ulOpenDir( pt.c_str() );
ulDir *od = ulOpenDir( po.c_str() );
if (td == NULL && od == NULL)
// "Terrain" and "Airports" directory don't exist. add directory as is
// otherwise, automatically append either Terrain, Objects, or both
//if (td == NULL && od == NULL)
fg_scenery.push_back( path_list[i] );
else {
//else {
if (td != NULL) {
fg_scenery.push_back( pt.str() );
ulCloseDir( td );
@ -219,7 +221,7 @@ void FGGlobals::set_fg_scenery (const string &scenery) {
fg_scenery.push_back( po.str() );
ulCloseDir( od );
}
}
//}
// insert a marker for FGTileEntry::load(), so that
// FG_SCENERY=A:B becomes list ["A/Terrain", "A/Objects", "",
// "B/Terrain", "B/Objects", ""]

View file

@ -427,7 +427,7 @@ bool FGAISchedule::update(time_t now)
aircraft->setAltitude((*i)->getCruiseAlt()*100); // convert from FL to feet
aircraft->setSpeed(speed);
aircraft->setBank(0);
aircraft->SetFlightPlan(new FGAIFlightPlan(flightPlanName, courseToDest, deptime,
aircraft->SetFlightPlan(new FGAIFlightPlan(aircraft, flightPlanName, courseToDest, deptime,
dep, arr,true, radius,
(*i)->getCruiseAlt()*100,
lat, lon, speed, flightType, acType,