]> git.mxchange.org Git - flightgear.git/commitdiff
Clean up dynamics/parking handing code.
authorJames Turner <zakalawe@mac.com>
Sun, 23 Sep 2012 20:42:40 +0000 (21:42 +0100)
committerJames Turner <zakalawe@mac.com>
Sun, 23 Sep 2012 20:42:40 +0000 (21:42 +0100)
Refactor some parking / airport-dynamics APIs, in preparation for caching the ground cache data in the nav-cache.

12 files changed:
src/AIModel/AIFlightPlan.hxx
src/AIModel/AIFlightPlanCreate.cxx
src/AIModel/AIFlightPlanCreatePushBack.cxx
src/ATC/atc_mgr.cxx
src/ATC/trafficcontrol.cxx
src/Airports/dynamics.cxx
src/Airports/dynamics.hxx
src/Airports/gnnode.hxx
src/Airports/parking.hxx
src/Airports/simple.cxx
src/Airports/xmlloader.cxx
src/Main/positioninit.cxx

index 40ba4efdcab79447e719baccc2f32399188ef80a..e5e4bb10db4090f3b77f281d429954de4101ec4b 100644 (file)
@@ -129,7 +129,7 @@ public:
 
   bool    create(FGAIAircraft *, FGAirport *dep, FGAirport *arr, int leg, double alt, double speed, double lat, double lon,
                 bool firstLeg, double radius, const std::string& fltType, const std::string& aircraftType, const std::string& airline, double distance);
-  bool createPushBack(FGAIAircraft *, bool, FGAirport*, double, double, double, const std::string&, const std::string&, const std::string&);
+  bool createPushBack(FGAIAircraft *, bool, FGAirport*, double radius, const std::string&, const std::string&, const std::string&);
   bool createTakeOff(FGAIAircraft *, bool, FGAirport *, double, const std::string&);
 
   void setLeg(int val) { leg = val;}
@@ -189,7 +189,7 @@ private:
   std::string name;
   bool isValid;
 
-  void createPushBackFallBack(FGAIAircraft *, bool, FGAirport*, double, double, double, const std::string&, const std::string&, const std::string&);
+  void createPushBackFallBack(FGAIAircraft *, bool, FGAirport*, double radius, const std::string&, const std::string&, const std::string&);
   bool createClimb(FGAIAircraft *, bool, FGAirport *, double, double, const std::string&);
   bool createCruise(FGAIAircraft *, bool, FGAirport*, FGAirport*, double, double, double, double, const std::string&);
   bool createDescent(FGAIAircraft *, FGAirport *,  double latitude, double longitude, double speed, double alt,const std::string&, double distance);
index fdb5c50019e82b635f546f8e1ac4e388f78c7d8c..a9dfb15fe152b240aed88a5f47999d462890e30d 100644 (file)
@@ -62,7 +62,7 @@ bool FGAIFlightPlan::create(FGAIAircraft * ac, FGAirport * dep,
     int currWpt = wpt_iterator - waypoints.begin();
     switch (legNr) {
     case 1:
-        retVal = createPushBack(ac, firstFlight, dep, latitude, longitude,
+        retVal = createPushBack(ac, firstFlight, dep,
                                 radius, fltType, aircraftType, airline);
         // Pregenerate the taxi leg.
         //if (retVal) {
@@ -206,22 +206,21 @@ bool FGAIFlightPlan::createTakeoffTaxi(FGAIAircraft * ac, bool firstFlight,
                                        const string & acType,
                                        const string & airline)
 {
-    double heading, lat, lon;
 
     // If this function is called during initialization,
     // make sure we obtain a valid gate ID first
     // and place the model at the location of the gate.
-    if (firstFlight) {
-        if (!(apt->getDynamics()->getAvailableParking(&lat, &lon,
-                                                      &heading, &gateId,
-                                                      radius, fltType,
-                                                      acType, airline))) {
-            SG_LOG(SG_AI, SG_WARN, "Could not find parking for a " <<
-                   acType <<
-                   " of flight type " << fltType <<
-                   " of airline     " << airline <<
-                   " at airport     " << apt->getId());
-        }
+    if (firstFlight)
+    {
+      gateId =  apt->getDynamics()->getAvailableParking(radius, fltType,
+                                                        acType, airline);
+      if (gateId < 0) {
+        SG_LOG(SG_AI, SG_WARN, "Could not find parking for a " <<
+               acType <<
+               " of flight type " << fltType <<
+               " of airline     " << airline <<
+               " at airport     " << apt->getId());
+      }
     }
 
     string rwyClass = getRunwayClassFromTrafficType(fltType);
@@ -355,11 +354,9 @@ void FGAIFlightPlan::createDefaultLandingTaxi(FGAIAircraft * ac,
                        ac->getPerformance()->vTaxi());
     pushBackWaypoint(wpt);
 
-    double heading, lat, lon;
-    aAirport->getDynamics()->getParking(gateId, &lat, &lon, &heading);
-    wpt =
-        createOnGround(ac, "ENDtaxi", SGGeod::fromDeg(lon, lat), airportElev,
-                       ac->getPerformance()->vTaxi());
+    FGParking* parkPos = aAirport->getDynamics()->getParking(gateId);
+    wpt = createOnGround(ac, "ENDtaxi", parkPos->getGeod(), airportElev,
+                         ac->getPerformance()->vTaxi());
     pushBackWaypoint(wpt);
 }
 
@@ -369,9 +366,7 @@ bool FGAIFlightPlan::createLandingTaxi(FGAIAircraft * ac, FGAirport * apt,
                                        const string & acType,
                                        const string & airline)
 {
-    double heading, lat, lon;
-    apt->getDynamics()->getAvailableParking(&lat, &lon, &heading,
-                                            &gateId, radius, fltType,
+    gateId = apt->getDynamics()->getAvailableParking(radius, fltType,
                                             acType, airline);
 
     SGGeod lastWptPos =
@@ -1012,34 +1007,25 @@ bool FGAIFlightPlan::createParking(FGAIAircraft * ac, FGAirport * apt,
 {
     FGAIWaypoint *wpt;
     double aptElev = apt->getElevation();
-    double lat = 0.0, lat2 = 0.0;
-    double lon = 0.0, lon2 = 0.0;
-    double az2 = 0.0;
-    double heading = 0.0;
-
     double vTaxi = ac->getPerformance()->vTaxi();
     double vTaxiReduced = vTaxi * (2.0 / 3.0);
-    apt->getDynamics()->getParking(gateId, &lat, &lon, &heading);
-    heading += 180.0;
-    if (heading > 360)
-        heading -= 360;
-    geo_direct_wgs_84(0, lat, lon, heading,
-                      2.2 * radius, &lat2, &lon2, &az2);
-    wpt =
-        createOnGround(ac, "taxiStart", SGGeod::fromDeg(lon2, lat2),
-                       aptElev, vTaxiReduced);
+    FGParking* parking = apt->getDynamics()->getParking(gateId);
+    double heading = SGMiscd::normalizePeriodic(0, 360, parking->getHeading() + 180.0);
+    double az; // unused
+    SGGeod pos;
+  
+    SGGeodesy::direct(parking->getGeod(), heading, 2.2 * parking->getRadius(),
+                      pos, az);
+  
+    wpt = createOnGround(ac, "taxiStart", pos, aptElev, vTaxiReduced);
     pushBackWaypoint(wpt);
 
-    geo_direct_wgs_84(0, lat, lon, heading,
-                      0.1 * radius, &lat2, &lon2, &az2);
-
-    wpt =
-        createOnGround(ac, "taxiStart2", SGGeod::fromDeg(lon2, lat2),
-                       aptElev, vTaxiReduced);
+    SGGeodesy::direct(parking->getGeod(), heading, 0.1 * parking->getRadius(),
+                    pos, az);
+    wpt = createOnGround(ac, "taxiStart2", pos, aptElev, vTaxiReduced);
     pushBackWaypoint(wpt);
 
-    wpt =
-        createOnGround(ac, "END-Parking", SGGeod::fromDeg(lon, lat), aptElev,
+    wpt = createOnGround(ac, "END-Parking", parking->getGeod(), aptElev,
                        vTaxiReduced);
     pushBackWaypoint(wpt);
     return true;
index bf256bac94b29ec3cdc05c7b3156adf3f1346b19..07d7eeca18f37239237811fcd0003d19b1f7f383 100644 (file)
 // TODO: Use James Turner's createOnGround functions.
 bool FGAIFlightPlan::createPushBack(FGAIAircraft *ac,
                                     bool firstFlight, FGAirport *dep,
-                                    double latitude,
-                                    double longitude,
                                     double radius,
                                     const string& fltType,
                                     const string& aircraftType,
                                     const string& airline)
 {
-    double lat, lon, heading;
     double vTaxi = ac->getPerformance()->vTaxi();
     double vTaxiBackward = vTaxi * (-2.0/3.0);
     double vTaxiReduced  = vTaxi * (2.0/3.0);
@@ -59,132 +56,111 @@ bool FGAIFlightPlan::createPushBack(FGAIAircraft *ac,
 
     if (!(dep->getDynamics()->getGroundNetwork()->exists())) {
         //cerr << "Push Back fallback" << endl;
-        createPushBackFallBack(ac, firstFlight, dep, latitude, longitude,
+        createPushBackFallBack(ac, firstFlight, dep,
                                radius, fltType, aircraftType, airline);
+      return true;
+    }
+  
+  // establish the parking position / gate if required
+    if (firstFlight) {
+      gateId = dep->getDynamics()->getAvailableParking(radius, fltType,
+                                                       aircraftType, airline);
+      if (gateId < 0) {
+        SG_LOG(SG_AI, SG_WARN, "Warning: Could not find parking for a " <<
+               aircraftType <<
+               " of flight type " << fltType <<
+               " of airline     " << airline <<
+               " at airport     " << dep->getId());
+        return false;
+      }
     } else {
-        if (firstFlight) {
-
-            if (!(dep->getDynamics()->getAvailableParking(&lat, &lon,
-                    &heading, &gateId,
-                    radius, fltType,
-                    aircraftType, airline))) {
-                SG_LOG(SG_AI, SG_WARN, "Warning: Could not find parking for a " <<
-                       aircraftType <<
-                       " of flight type " << fltType <<
-                       " of airline     " << airline <<
-                       " at airport     " << dep->getId());
-                return false;
-                char buffer[10];
-                snprintf (buffer, 10, "%d", gateId);
-                SGGeod coord = coord.fromDeg(lon, lat);
-                //FGTaxiNode *tn = dep->getDynamics()->getGroundNetwork()->findNode(node);
-                FGAIWaypoint *wpt = createOnGround(ac, string(buffer), coord, dep->getElevation(), vTaxiBackward);
-                wpt->setRouteIndex(-1);
-                pushBackWaypoint(wpt);
-            }
-            //cerr << "Success : GateId = " << gateId << endl;
-            SG_LOG(SG_AI, SG_WARN, "Warning: Successfully found a parking for a " <<
-                   aircraftType <<
-                   " of flight type " << fltType <<
-                   " of airline     " << airline <<
-                   " at airport     " << dep->getId());
-        } else {
-            //cerr << "Push Back follow-up Flight" << endl;
-            dep->getDynamics()->getParking(gateId, &lat, &lon, &heading);
-        }
-        if (gateId < 0) {
-            createPushBackFallBack(ac, firstFlight, dep, latitude, longitude,
-                                   radius, fltType, aircraftType, airline);
-            return true;
+      dep->getDynamics()->getParking(gateId);
+    }
+  
+    if (gateId < 0) {
+        createPushBackFallBack(ac, firstFlight, dep,
+                               radius, fltType, aircraftType, airline);
+        return true;
 
-        }
-        //cerr << "getting parking " << gateId;
-        //cerr << " for a " <<
-        //                                      aircraftType <<
-        //                                      " of flight type " << fltType <<
-        //                                      " of airline     " << airline <<
-        //                                      " at airport     " << dep->getId() << endl;
-        FGParking *parking = dep->getDynamics()->getParking(gateId);
-        int pushBackNode = parking->getPushBackPoint();
+    }
+
+    FGParking *parking = dep->getDynamics()->getParking(gateId);
+    int pushBackNode = parking->getPushBackPoint();
+
+    pushBackRoute = parking->getPushBackRoute();
+    if ((pushBackNode > 0) && (pushBackRoute == 0)) {  // Load the already established route for this gate
+        int node, rte;
+        FGTaxiRoute route;
+        //cerr << "Creating push-back for " << gateId << " (" << parking->getName() << ") using push-back point " << pushBackNode << endl;
+        route = dep->getDynamics()->getGroundNetwork()->findShortestRoute(gateId, pushBackNode, false);
+        parking->setPushBackRoute(new FGTaxiRoute(route));
 
 
         pushBackRoute = parking->getPushBackRoute();
-        if ((pushBackNode > 0) && (pushBackRoute == 0)) {  // Load the already established route for this gate
-            int node, rte;
-            FGTaxiRoute route;
-            //cerr << "Creating push-back for " << gateId << " (" << parking->getName() << ") using push-back point " << pushBackNode << endl;
-            route = dep->getDynamics()->getGroundNetwork()->findShortestRoute(gateId, pushBackNode, false);
-            parking->setPushBackRoute(new FGTaxiRoute(route));
-
-
-            pushBackRoute = parking->getPushBackRoute();
-            int size = pushBackRoute->size();
-            if (size < 2) {
-                SG_LOG(SG_AI, SG_ALERT, "Push back route from gate " << gateId << " has only " << size << " nodes.");
-                SG_LOG(SG_AI, SG_ALERT, "Using  " << pushBackNode);
-            }
-            pushBackRoute->first();
-            while (pushBackRoute->next(&node, &rte))
-            {
-                //FGTaxiNode *tn = apt->getDynamics()->getGroundNetwork()->findSegment(node)->getEnd();
-                char buffer[10];
-                snprintf (buffer, 10, "%d", node);
-                FGTaxiNode *tn = dep->getDynamics()->getGroundNetwork()->findNode(node);
-                //ids.pop_back();
-                //wpt = new waypoint;
-                SGGeod coord = coord.fromDeg(tn->getLongitude(), tn->getLatitude());
-                FGAIWaypoint *wpt = createOnGround(ac, string(buffer), coord, dep->getElevation(), vTaxiBackward);
-
-                wpt->setRouteIndex(rte);
-                pushBackWaypoint(wpt);
-            }
-            // some special considerations for the last point:
-            waypoints.back()->setName(string("PushBackPoint"));
-            waypoints.back()->setSpeed(vTaxi);
-            ac->setTaxiClearanceRequest(true);
-        } else {  // In case of a push forward departure...
-            ac->setTaxiClearanceRequest(false);
-            double lat2 = 0.0, lon2 = 0.0, az2 = 0.0;
-
-            //cerr << "Creating final push forward point for gate " << gateId << endl;
-            FGTaxiNode *tn = dep->getDynamics()->getGroundNetwork()->findNode(gateId);
-            FGTaxiSegmentVectorIterator ts = tn->getBeginRoute();
-            FGTaxiSegmentVectorIterator te = tn->getEndRoute();
-            // if the starting node equals the ending node, then there aren't any routes for this parking.
-            // in cases like these we should flag the gate as being inoperative and return false
-            if (ts == te) {
-                SG_LOG(SG_AI, SG_ALERT, "Gate " << gateId << "doesn't seem to have routes associated with it.");
-                parking->setAvailable(false);
-                return false;
-            }
-            tn = (*ts)->getEnd();
-            lastNodeVisited = tn->getIndex();
-            if (tn == NULL) {
-                SG_LOG(SG_AI, SG_ALERT, "No valid taxinode found");
-                exit(1);
-            }
-            double distance = (*ts)->getLength();
-            //cerr << "Length of push forward route = " << distance << " and heading is " << heading << endl;
-            lat2 =  tn->getLatitude();
-            lon2 =  tn->getLongitude();
-
-            for (int i = 1; i < 10; i++) {
-                geo_direct_wgs_84 ( 0, lat, lon, heading,
-                                    ((i / 10.0) * distance), &lat2, &lon2, &az2 );
-                char buffer[16];
-                snprintf(buffer, 16, "pushback-%02d", i);
-                SGGeod coord = coord.fromDeg(lon2, lat2);
-                //cerr << i << endl;
-                FGAIWaypoint *wpt = createOnGround(ac, string(buffer), coord, dep->getElevation(), vTaxiReduced);
-
-                wpt->setRouteIndex((*ts)->getIndex());
-                pushBackWaypoint(wpt);
-            }
-            // cerr << "Done " << endl;
-            waypoints.back()->setName(string("PushBackPoint"));
-            // cerr << "Done assinging new name" << endl;
+        int size = pushBackRoute->size();
+        if (size < 2) {
+            SG_LOG(SG_AI, SG_ALERT, "Push back route from gate " << gateId << " has only " << size << " nodes.");
+            SG_LOG(SG_AI, SG_ALERT, "Using  " << pushBackNode);
+        }
+        pushBackRoute->first();
+        while (pushBackRoute->next(&node, &rte))
+        {
+            //FGTaxiNode *tn = apt->getDynamics()->getGroundNetwork()->findSegment(node)->getEnd();
+            char buffer[10];
+            snprintf (buffer, 10, "%d", node);
+            FGTaxiNode *tn = dep->getDynamics()->getGroundNetwork()->findNode(node);
+            //ids.pop_back();
+            //wpt = new waypoint;
+            FGAIWaypoint *wpt = createOnGround(ac, string(buffer), tn->getGeod(), dep->getElevation(), vTaxiBackward);
+
+            wpt->setRouteIndex(rte);
+            pushBackWaypoint(wpt);
         }
+        // some special considerations for the last point:
+        waypoints.back()->setName(string("PushBackPoint"));
+        waypoints.back()->setSpeed(vTaxi);
+        ac->setTaxiClearanceRequest(true);
+    } else {  // In case of a push forward departure...
+        ac->setTaxiClearanceRequest(false);
+        double az2 = 0.0;
+
+        //cerr << "Creating final push forward point for gate " << gateId << endl;
+        FGTaxiNode *tn = dep->getDynamics()->getGroundNetwork()->findNode(gateId);
+        FGTaxiSegmentVectorIterator ts = tn->getBeginRoute();
+        FGTaxiSegmentVectorIterator te = tn->getEndRoute();
+        // if the starting node equals the ending node, then there aren't any routes for this parking.
+        // in cases like these we should flag the gate as being inoperative and return false
+        if (ts == te) {
+            SG_LOG(SG_AI, SG_ALERT, "Gate " << gateId << "doesn't seem to have routes associated with it.");
+            parking->setAvailable(false);
+            return false;
+        }
+        tn = (*ts)->getEnd();
+        lastNodeVisited = tn->getIndex();
+        if (tn == NULL) {
+            SG_LOG(SG_AI, SG_ALERT, "No valid taxinode found");
+            exit(1);
+        }
+        double distance = (*ts)->getLength();
+
+        double parkingHeading = parking->getHeading();
+      
+        for (int i = 1; i < 10; i++) {
+            SGGeod pushForwardPt;
+            SGGeodesy::direct(parking->getGeod(), parkingHeading,
+                              ((i / 10.0) * distance), pushForwardPt, az2);
+            char buffer[16];
+            snprintf(buffer, 16, "pushback-%02d", i);
+            FGAIWaypoint *wpt = createOnGround(ac, string(buffer), pushForwardPt, dep->getElevation(), vTaxiReduced);
+
+            wpt->setRouteIndex((*ts)->getIndex());
+            pushBackWaypoint(wpt);
+        }
+        // cerr << "Done " << endl;
+        waypoints.back()->setName(string("PushBackPoint"));
+        // cerr << "Done assinging new name" << endl;
     }
+
     return true;
 }
 /*******************************************************************
@@ -193,49 +169,29 @@ bool FGAIFlightPlan::createPushBack(FGAIAircraft *ac,
 * network yet.
 ******************************************************************/
 void FGAIFlightPlan::createPushBackFallBack(FGAIAircraft *ac, bool firstFlight, FGAirport *dep,
-        double latitude,
-        double longitude,
         double radius,
         const string& fltType,
         const string& aircraftType,
         const string& airline)
 {
-    double heading;
-    double lat;
-    double lon;
-    double lat2 = 0.0;
-    double lon2 = 0.0;
     double az2 = 0.0;
 
     double vTaxi = ac->getPerformance()->vTaxi();
     double vTaxiBackward = vTaxi * (-2.0/3.0);
     double vTaxiReduced  = vTaxi * (2.0/3.0);
 
-
-
-    dep->getDynamics()->getParking(-1, &lat, &lon, &heading);
-
-    heading += 180.0;
-    if (heading > 360)
-        heading -= 360;
-
-    SGGeod coord = coord.fromDeg(lon, lat);
-    FGAIWaypoint *wpt = createOnGround(ac, string("park"), coord, dep->getElevation(), vTaxiBackward);
+    double heading = 180.0; // this is a completely arbitrary heading!
+    FGAIWaypoint *wpt = createOnGround(ac, string("park"), dep->geod(), dep->getElevation(), vTaxiBackward);
 
     pushBackWaypoint(wpt);
 
-    geo_direct_wgs_84 ( 0, lat, lon, heading,
-                        10,
-                        &lat2, &lon2, &az2 );
-    coord = coord.fromDeg(lon2, lat2);
+    SGGeod coord;
+    SGGeodesy::direct(dep->geod(), heading, 10, coord, az2);
     wpt = createOnGround(ac, string("park2"), coord, dep->getElevation(), vTaxiBackward);
 
     pushBackWaypoint(wpt);
-
-    geo_direct_wgs_84 ( 0, lat, lon, heading,
-                        2.2*radius,
-                        &lat2, &lon2, &az2 );
-    coord = coord.fromDeg(lon2, lat2);
+  
+    SGGeodesy::direct(dep->geod(), heading, 2.2 * radius, coord, az2);
     wpt = createOnGround(ac, string("taxiStart"), coord, dep->getElevation(), vTaxiReduced);
     pushBackWaypoint(wpt);
 
index 3b727c903cea81cd3bd47df09a63a545441d92c8..c4372173934b045cf55d3bd36d82dfc292997f8e 100644 (file)
@@ -143,8 +143,6 @@ void FGATCManager::init() {
             if (!(fp->createPushBack(&ai_ac,
                                false, 
                                apt, 
-                               latitude,
-                               longitude,
                                aircraftRadius,
                                fltType,
                                aircraftType,
index 621687687d13ddc350db3223b9933c74820ad147..93878e4ea2f93c22355083fe4c5bc4e79db53ba5 100644 (file)
@@ -589,8 +589,7 @@ void FGATCController::transmit(FGTrafficRecord * rec, FGAirportDynamics *parent,
         getDynamics()->getActiveRunway(rwyClass, 1, activeRunway,
                                        heading);
         rec->getAircraft()->GetFlightPlan()->setRunway(activeRunway);
-        fp = rec->getAircraft()->getTrafficRef()->getDepartureAirport()->
-             getDynamics()->getSID(activeRunway, heading);
+        fp = NULL;
         rec->getAircraft()->GetFlightPlan()->setSID(fp);
         if (fp) {
             SID = fp->getName() + " departure";
@@ -737,11 +736,8 @@ void FGATCController::transmit(FGTrafficRecord * rec, FGAirportDynamics *parent,
                        SGGeod sender_pos;
                        double sender_alt_ft, sender_alt;
                        if(ground_to_air) {
-                                     sender_alt_ft = parent->getElevation();
-                                     sender_alt = sender_alt_ft * SG_FEET_TO_METER;
-                                     sender_pos= SGGeod::fromDegM( parent->getLongitude(),
-                                     parent->getLatitude(), sender_alt );
-                               }
+                  sender_pos = parent->parent()->geod();
+                                }
                                else {
                                      sender_alt_ft = rec->getAltitude();
                                      sender_alt = sender_alt_ft * SG_FEET_TO_METER;
index b4e91554e92ee75fda649abcc2e7f6776c557d9a..21d45d08be4296056321b0aa59ed221545d052bb 100644 (file)
 #endif
 
 #include <algorithm>
+#include <string>
+#include <vector>
+
+#include <boost/foreach.hpp>
 
 #include <simgear/compiler.h>
 
 #include <Airports/runways.hxx>
 #include <ATCDCL/ATCutils.hxx>
 
-#include <string>
-#include <vector>
+#include "simple.hxx"
+#include "dynamics.hxx"
 
 using std::string;
 using std::vector;
 using std::sort;
 using std::random_shuffle;
 
-#include "simple.hxx"
-#include "dynamics.hxx"
-
 FGAirportDynamics::FGAirportDynamics(FGAirport * ap):
-    _ap(ap), rwyPrefs(ap), SIDs(ap),
-        startupController    (this),
+    _ap(ap), rwyPrefs(ap),
+    startupController    (this),
     towerController      (this),
     approachController   (this),
     atisSequenceIndex(-1),
@@ -85,159 +86,67 @@ void FGAirportDynamics::init()
     
 }
 
-bool FGAirportDynamics::getAvailableParking(double *lat, double *lon,
-                                            double *heading, int *gateId,
-                                            double rad,
-                                            const string & flType,
-                                            const string & acType,
-                                            const string & airline)
+int FGAirportDynamics::innerGetAvailableParking(double radius, const string & flType,
+                                           const string & acType,
+                                           const string & airline,
+                                           bool skipEmptyAirlineCode)
 {
-    bool found = false;
-    bool available = false;
-
-
-    FGParkingVecIterator i;
-    if (parkings.begin() == parkings.end()) {
-        //cerr << "Could not find parking spot at " << _ap->getId() << endl;
-        *lat = _ap->getLatitude();
-        *lon = _ap->getLongitude();
-        * gateId = -1;
-        *heading = 0;
-        found = true;
-    } else {
-        // First try finding a parking with a designated airline code
-        for (i = parkings.begin(); !(i == parkings.end() || found); i++) {
-            available = true;
-            // Taken by another aircraft
-            if (!(i->isAvailable())) {
-                available = false;
-                continue;
-            }
-            // No airline codes, so skip
-            if (i->getCodes().empty()) {
-                available = false;
-                continue;
-            } else {             // Airline code doesn't match
-                //cerr << "Code = " << airline << ": Codes " << i->getCodes();
-                if (i->getCodes().find(airline, 0) == string::npos) {
-                    available = false;
-                    //cerr << "Unavailable" << endl;
-                    continue;
-                } else {
-                    //cerr << "Available" << endl;
-                }
-            }
-            // Type doesn't match
-            if (i->getType() != flType) {
-                available = false;
-                continue;
-            }
-            // too small
-            if (i->getRadius() < rad) {
-                available = false;
-                continue;
-            }
-
-            if (available) {
-                *lat = i->getLatitude();
-                *lon = i->getLongitude();
-                *heading = i->getHeading();
-                *gateId = i->getIndex();
-                i->setAvailable(false);
-                found = true;
-            }
-        }
-        // then try again for those without codes. 
-        for (i = parkings.begin(); !(i == parkings.end() || found); i++) {
-            available = true;
-            if (!(i->isAvailable())) {
-                available = false;
-                continue;
-            }
-            if (!(i->getCodes().empty())) {
-                if ((i->getCodes().find(airline, 0) == string::npos)) {
-                    available = false;
-                    continue;
-                }
-            }
-            if (i->getType() != flType) {
-                available = false;
-                continue;
-            }
-
-            if (i->getRadius() < rad) {
-                available = false;
-                continue;
-            }
-
-            if (available) {
-                *lat = i->getLatitude();
-                *lon = i->getLongitude();
-                *heading = i->getHeading();
-                *gateId = i->getIndex();
-                i->setAvailable(false);
-                found = true;
-            }
-        }
-        // And finally once more if that didn't work. Now ignore the airline codes, as a last resort
-        for (i = parkings.begin(); !(i == parkings.end() || found); i++) {
-            available = true;
-            if (!(i->isAvailable())) {
-                available = false;
-                continue;
-            }
-            if (i->getType() != flType) {
-                available = false;
-                continue;
-            }
-
-            if (i->getRadius() < rad) {
-                available = false;
-                continue;
-            }
-
-            if (available) {
-                *lat = i->getLatitude();
-                *lon = i->getLongitude();
-                *heading = i->getHeading();
-                *gateId = i->getIndex();
-                i->setAvailable(false);
-                found = true;
-            }
-        }
+  FGParkingVecIterator i;
+  for (i = parkings.begin(); i != parkings.end(); i++) {
+    // Taken by another aircraft, or no airline codes
+    if (!i->isAvailable()) {
+      continue;
+    }
+    
+    if (skipEmptyAirlineCode && i->getCodes().empty()) {
+      continue;
+    }
+    
+    // check airline codes match
+    if (!airline.empty() && !i->getCodes().empty()) {
+      if (i->getCodes().find(airline, 0) == string::npos) {
+        continue;
+      }
+    }
+    
+    // Type doesn't match
+    if (i->getType() != flType) {
+      continue;
     }
-    if (!found) {
-        //cerr << "Traffic overflow at" << _ap->getId() 
-        //           << ". flType = " << flType 
-        //           << ". airline = " << airline 
-        //           << " Radius = " <<rad
-        //           << endl;
-        *lat = _ap->getLatitude();
-        *lon = _ap->getLongitude();
-        *heading = 0;
-        *gateId = -1;
-        //exit(1);
+    // too small
+    if (i->getRadius() < radius) {
+      continue;
     }
-    return found;
+    
+    i->setAvailable(false);
+    return i->getIndex();
+  }
+  
+  return -1;
 }
 
-void FGAirportDynamics::getParking(int id, double *lat, double *lon,
-                                   double *heading)
+int FGAirportDynamics::getAvailableParking(double radius, const string & flType,
+                                            const string & acType,
+                                            const string & airline)
 {
-    if (id < 0) {
-        *lat = _ap->getLatitude();
-        *lon = _ap->getLongitude();
-        *heading = 0;
-    } else {
-        FGParkingVecIterator i = parkings.begin();
-        for (i = parkings.begin(); i != parkings.end(); i++) {
-            if (id == i->getIndex()) {
-                *lat = i->getLatitude();
-                *lon = i->getLongitude();
-                *heading = i->getHeading();
-            }
-        }
+    if (parkings.empty()) {
+      return -1;
     }
+  
+  // most exact seach - airline codes must be present and match
+  int result = innerGetAvailableParking(radius, flType, acType, airline, true);
+  if (result >= 0) {
+    return result;
+  }
+  
+  // more tolerant - gates with empty airline codes are permitted
+  result = innerGetAvailableParking(radius, flType, acType, airline, false);
+  if (result >= 0) {
+    return result;
+  }
+
+  // fallback - ignore the airline code entirely
+  return innerGetAvailableParking(radius, flType, acType, string(), false);
 }
 
 FGParking *FGAirportDynamics::getParking(int id)
@@ -263,6 +172,18 @@ string FGAirportDynamics::getParkingName(int id)
     return string("overflow");
 }
 
+int FGAirportDynamics::findParkingByName(const std::string& name) const
+{
+  FGParkingVec::const_iterator i = parkings.begin();
+  for (i = parkings.begin(); i != parkings.end(); i++) {
+    if (i->getName() == name) {
+      return i->getIndex();
+    }
+  }
+  
+  return -1;
+}
+
 void FGAirportDynamics::releaseParking(int id)
 {
     if (id >= 0) {
@@ -279,8 +200,6 @@ void FGAirportDynamics::releaseParking(int id)
 void FGAirportDynamics::setRwyUse(const FGRunwayPreference & ref)
 {
     rwyPrefs = ref;
-    //cerr << "Exiting due to not implemented yet" << endl;
-    //exit(1);
 }
 
 bool FGAirportDynamics::innerGetActiveRunway(const string & trafficType,
@@ -466,22 +385,12 @@ void FGAirportDynamics::addParking(FGParking & park)
     parkings.push_back(park);
 }
 
-double FGAirportDynamics::getLatitude() const
-{
-    return _ap->getLatitude();
-}
-
-double FGAirportDynamics::getLongitude() const
-{
-    return _ap->getLongitude();
-}
-
 double FGAirportDynamics::getElevation() const
 {
     return _ap->getElevation();
 }
 
-const string FGAirportDynamics::getId() const
+const string FGAirportDynamics::getId() const
 {
     return _ap->getId();
 }
@@ -543,13 +452,6 @@ int FGAirportDynamics::getTowerFrequency(unsigned nr)
     return towerFreq;
 }
 
-
-FGAIFlightPlan *FGAirportDynamics::getSID(string activeRunway,
-                                          double heading)
-{
-    return SIDs.getBest(activeRunway, heading);
-}
-
 const std::string FGAirportDynamics::getAtisSequence()
 {
    if (atisSequenceIndex == -1) {
index 7e828e4f9c3e5b5212f32ae36bbc4b8e82e5342d..cb489bfa3db458163ef71ac3cb01d0d91eedb8f3 100644 (file)
@@ -26,7 +26,6 @@
 #include "parking.hxx"
 #include "groundnetwork.hxx"
 #include "runwayprefs.hxx"
-#include "sidstar.hxx"
 
 // forward decls
 class FGAirport;
@@ -39,7 +38,6 @@ private:
 
     FGParkingVec         parkings;
     FGRunwayPreference   rwyPrefs;
-    FGSidStar            SIDs;
     FGStartupController  startupController;
     FGGroundNetwork      groundNetwork;
     FGTowerController    towerController;
@@ -65,8 +63,9 @@ private:
     bool innerGetActiveRunway(const std::string &trafficType, int action, std::string &runway, double heading);
     std::string chooseRwyByHeading(stringVec rwys, double heading);
 
-    double elevation;
-
+  int innerGetAvailableParking(double radius, const std::string & flType,
+                               const std::string & acType, const std::string & airline,
+                               bool skipEmptyAirlineCode);
 public:
     FGAirportDynamics(FGAirport* ap);
     ~FGAirportDynamics();
@@ -91,36 +90,36 @@ public:
     };
 
     void init();
-    double getLongitude() const;
-    // Returns degrees
-    double getLatitude()  const;
-    // Returns ft
+  
     double getElevation() const;
-    const string& getId() const;
-
+    const std::string getId() const;
+  
+    FGAirport* parent() const
+    { return _ap; }
+  
     void getActiveRunway(const string& trafficType, int action, string& runway, double heading);
 
     void addParking(FGParking& park);
-    bool getAvailableParking(double *lat, double *lon,
-                             double *heading, int *gate, double rad, const string& fltype,
-                             const string& acType, const string& airline);
-    void getParking         (int id, double *lat, double* lon, double *heading);
+    
+    /**
+     * retrieve an available parking by GateID, or -1 if no suitable
+     * parking location could be found.
+     */
+    int getAvailableParking(double radius, const std::string& fltype,
+                          const std::string& acType, const std::string& airline);
+
     FGParking *getParking(int i);
     void releaseParking(int id);
-    string getParkingName(int i);
+    std::string getParkingName(int i);
     int getNrOfParkings() {
         return parkings.size();
     };
-    //FGAirport *getAddress() { return this; };
-    //const string &getName() const { return _name;};
-    // Returns degrees
-
-    // Departure / Arrival procedures
-    FGSidStar * getSIDs() {
-        return &SIDs;
-    };
-    FGAIFlightPlan * getSID(string activeRunway, double heading);
 
+    /**
+     * Find a parking gate index by name. Note names are often not unique
+     * in our data, so will return the first match.
+     */
+    int findParkingByName(const std::string& name) const;
 
     // ATC related functions.
     FGStartupController    *getStartupController()    {
index aa4e7ed2637f199724ca5969ffd0d19f4a305736..c64b51fd0fb51248a2d92d97229f3cbaa095b1b5 100644 (file)
@@ -31,7 +31,7 @@ bool sortByLength     (FGTaxiSegment *a, FGTaxiSegment *b);
 
 class FGTaxiNode 
 {
-private:
+protected:
   SGGeod geod;
   int index;
 
@@ -106,9 +106,9 @@ FGTaxiNode &operator =(const FGTaxiNode &other)
 
   const SGGeod& getGeod() const { return geod; }
 
-  int getIndex() { return index; };
-  int getHoldPointType() { return holdType; };
-  bool getIsOnRunway() { return isOnRunway; };
+  int getIndex() const { return index; };
+  int getHoldPointType() const { return holdType; };
+  bool getIsOnRunway() const { return isOnRunway; };
 
   FGTaxiNode *getAddress() { return this;};
   FGTaxiSegmentVectorIterator getBeginRoute() { return next.begin(); };
index 0cac08bbcdc9069bc2b0f97c50a3776a3e9a1e7c..1d009c03cacbad84996188ec4b8af12b2e1685a5 100644 (file)
@@ -36,9 +36,6 @@
 
 #include "gnnode.hxx"
 
-using std::string;
-using std::vector;
-
 class FGTaxiRoute;
 
 
@@ -46,9 +43,9 @@ class FGParking : public FGTaxiNode {
 private:
   double heading;
   double radius;
-  string parkingName;
-  string type;
-  string airlineCodes;
+  std::string parkingName;
+  std::string type;
+  std::string airlineCodes;
  
   bool available;
   int pushBackPoint;
@@ -92,34 +89,26 @@ public:
       return *this;
   };
   ~FGParking();
-//   FGParking(double lat,
-//         double lon,
-//         double hdg,
-//         double rad,
-//         int idx,
-//         const string& name,
-//         const string& tpe,
-//         const string& codes);
 
   void setHeading  (double hdg)  { heading     = hdg;  };
   void setRadius   (double rad)  { radius      = rad;  };
 
-  void setName     (const string& name) { parkingName = name; };
-  void setType     (const string& tpe)  { type        = tpe;  };
-  void setCodes    (const string& codes){ airlineCodes= codes;};
+  void setName     (const std::string& name) { parkingName = name; };
+  void setType     (const std::string& tpe)  { type        = tpe;  };
+  void setCodes    (const std::string& codes){ airlineCodes= codes;};
 
   void setPushBackRoute(FGTaxiRoute *val) { pushBackRoute = val; };
   void setPushBackPoint(int val)          { pushBackPoint = val; };
 
-  bool isAvailable ()         { return available;};
+  bool isAvailable ()   const { return available;};
   void setAvailable(bool val) { available = val; };
   
-  double getHeading  () { return heading;     };
-  double getRadius   () { return radius;      };
+  double getHeading  () const { return heading;     };
+  double getRadius   () const { return radius;      };
 
-  string getType     () { return type;        };
-  string getCodes    () { return airlineCodes;};
-  string getName     () { return parkingName; };
+  std::string getType     () const { return type;        };
+  std::string getCodes    () const { return airlineCodes;};
+  std::string getName     () const { return parkingName; };
 
   FGTaxiRoute * getPushBackRoute () { return pushBackRoute; };
 
@@ -129,8 +118,8 @@ public:
     return radius < other.radius; };
 };
 
-typedef vector<FGParking> FGParkingVec;
-typedef vector<FGParking>::iterator FGParkingVecIterator;
-typedef vector<FGParking>::const_iterator FGParkingVecConstIterator;
+typedef std::vector<FGParking> FGParkingVec;
+typedef std::vector<FGParking>::iterator FGParkingVecIterator;
+typedef std::vector<FGParking>::const_iterator FGParkingVecConstIterator;
 
 #endif
index 63e28c9e6d66f4500881e41ecebddd1b259b2abc..aac730e5041ff2750844e474988cf3881bdacfd5 100644 (file)
@@ -38,6 +38,7 @@
 #include <simgear/props/props_io.hxx>
 #include <simgear/debug/logstream.hxx>
 #include <simgear/sg_inlines.h>
+#include <simgear/structure/exception.hxx>
 
 #include <Environment/environment_mgr.hxx>
 #include <Environment/environment.hxx>
@@ -115,7 +116,6 @@ FGAirportDynamics * FGAirport::getDynamics()
     FGRunwayPreference rwyPrefs(this);
     XMLLoader::load(&rwyPrefs);
     _dynamics->setRwyUse(rwyPrefs);
-    XMLLoader::load(_dynamics->getSIDs());
     
     return _dynamics;
 }
index 71082a331732b96c96459835d468df87f452feca..8b35cabd5b03bab346f5df79fd9f2ec9f8a83219 100644 (file)
@@ -29,6 +29,7 @@
 #include "runwayprefloader.hxx"
 
 #include "dynamics.hxx"
+#include "simple.hxx"
 #include "runwayprefs.hxx"
 
 using std::string;
@@ -36,9 +37,10 @@ using std::string;
 XMLLoader::XMLLoader() {}
 XMLLoader::~XMLLoader() {}
 
-void XMLLoader::load(FGAirportDynamics* d) {
+void XMLLoader::load(FGAirportDynamics* d)
+{
   FGAirportDynamicsXMLLoader visitor(d);
-  if(loadAirportXMLDataIntoVisitor(d->getId(), "groundnet", visitor)) {
+  if(loadAirportXMLDataIntoVisitor(d->parent()->ident(), "groundnet", visitor)) {
     d->init();
   }
 }
@@ -48,13 +50,6 @@ void XMLLoader::load(FGRunwayPreference* p) {
   loadAirportXMLDataIntoVisitor(p->getId(), "rwyuse", visitor);
 }
 
-void XMLLoader::load(FGSidStar* p) {
-  SGPath path;
-  if (findAirportData(p->getId(), "SID", path)) {
-    p->load(path);
-  }
-}
-
 bool XMLLoader::findAirportData(const std::string& aICAO, 
     const std::string& aFileName, SGPath& aPath)
 {
index 884c821812ba98dc8589aa95cc9f237d38bfcd6c..fd5db70b1069253774454940766f7188f4d41848 100644 (file)
@@ -24,6 +24,7 @@
 
 // simgear
 #include <simgear/props/props_io.hxx>
+#include <simgear/structure/exception.hxx>
 
 #include "globals.hxx"
 #include "fg_props.hxx"
@@ -150,7 +151,8 @@ bool setPosFromAirportIDandHdg( const string& id, double tgt_hdg ) {
 }
 
 // Set current_options lon/lat given an airport id and parkig position name
-static bool fgSetPosFromAirportIDandParkpos( const string& id, const string& parkpos ) {
+static bool fgSetPosFromAirportIDandParkpos( const string& id, const string& parkpos )
+{
   if ( id.empty() )
     return false;
   
@@ -167,11 +169,9 @@ static bool fgSetPosFromAirportIDandParkpos( const string& id, const string& par
     return false;
   }
   
-  int park_index = dcs->getNrOfParkings() - 1;
-  bool succes;
+  int gateID;
   double radius = fgGetDouble("/sim/dimensions/radius-m");
   if ((parkpos == string("AVAILABLE")) && (radius > 0)) {
-    double lat, lon, heading;
     string fltType;
     string acOperator;
     SGPath acData;
@@ -203,30 +203,27 @@ static bool fgSetPosFromAirportIDandParkpos( const string& id, const string& par
     }
     
     string acType; // Currently not used by findAvailable parking, so safe to leave empty.
-    succes = dcs->getAvailableParking(&lat, &lon, &heading, &park_index, radius, fltType, acType, acOperator);
-    if (succes) {
+    gateID = dcs->getAvailableParking(radius, fltType, acType, acOperator);
+    if (gateID >=0 ) {
       fgGetString("/sim/presets/parkpos");
-      fgSetString("/sim/presets/parkpos", dcs->getParking(park_index)->getName());
+      fgSetString("/sim/presets/parkpos", dcs->getParking(gateID)->getName());
     } else {
       SG_LOG( SG_GENERAL, SG_ALERT,
              "Failed to find a suitable parking at airport " << id );
       return false;
     }
   } else {
-    //cerr << "We shouldn't get here when AVAILABLE" << endl;
-    while (park_index >= 0 && dcs->getParkingName(park_index) != parkpos) park_index--;
-    if (park_index < 0) {
+    gateID = dcs->findParkingByName(parkpos);
+    if (gateID < 0) {
       SG_LOG( SG_GENERAL, SG_ALERT,
-             "Failed to find parking position " << parkpos <<
-             " at airport " << id );
+               "Failed to find a parking at airport " << id << ":" << parkpos);
       return false;
     }
   }
-  FGParking* parking = dcs->getParking(park_index);
+  
+  FGParking* parking = dcs->getParking(gateID);
   parking->setAvailable(false);
-  fgApplyStartOffset(
-                     SGGeod::fromDeg(parking->getLongitude(), parking->getLatitude()),
-                     parking->getHeading());
+  fgApplyStartOffset(parking->getGeod(), parking->getHeading());
   return true;
 }