diff --git a/src/AIModel/AIAircraft.cxx b/src/AIModel/AIAircraft.cxx index 3791585ec..be0556c85 100644 --- a/src/AIModel/AIAircraft.cxx +++ b/src/AIModel/AIAircraft.cxx @@ -1,4 +1,4 @@ -// // FGAIAircraft - FGAIBase-derived class creates an AI airplane +// FGAIAircraft - FGAIBase-derived class creates an AI airplane // // Written by David Culp, started October 2003. // @@ -48,6 +48,8 @@ using std::string; #include "performancedata.hxx" #include "performancedb.hxx" + +#define TGT_VS_CUTOFF 10000 //#include <Airports/trafficcontroller.hxx> static string tempReg; @@ -155,6 +157,7 @@ void FGAIAircraft::setPerformance(const std::string& acclass) { void FGAIAircraft::Run(double dt) { + FGAIAircraft::dt = dt; bool outOfSight = false, @@ -355,9 +358,14 @@ void FGAIAircraft::ProcessFlightPlan( double dt, time_t now ) { tgt_altitude_ft = prev->getAltitude(); if (curr->getCrossat() > -1000.0) { use_perf_vs = false; - tgt_vs = (curr->getCrossat() - altitude_ft) / (fp->getDistanceToGo(pos.getLatitudeDeg(), pos.getLongitudeDeg(), curr) - / 6076.0 / speed*60.0); - checkTcas(); +// tgt_vs = (curr->getCrossat() - altitude_ft) / (fp->getDistanceToGo(pos.getLatitudeDeg(), pos.getLongitudeDeg(), curr) +// / 6076.0 / speed*60.0); +// if (fabs(tgt_vs) > TGT_VS_CUTOFF) { SG_LOG(SG_GENERAL, SG_ALERT, "Rediculously high vertical speed caculated at " << SG_ORIGIN << ". Corresponding to " << (tgt_vs * .005) << "degrees of pitch angle" << prev->getName()); }; +// if (tgt_vs < -1500) +// tgt_vs = -1500; +// if (tgt_vs > 1500) +// tgt_vs = 1500; +// checkTcas(); tgt_altitude_ft = curr->getCrossat(); } else { use_perf_vs = true; @@ -497,6 +505,7 @@ void FGAIAircraft::getGroundElev(double dt) { void FGAIAircraft::doGroundAltitude() { + if ((fabs(altitude_ft - (tgt_altitude_ft+groundOffset)) > 1000.0)|| (isStationary())) altitude_ft = (tgt_altitude_ft + groundOffset); @@ -676,10 +685,11 @@ void FGAIAircraft::handleFirstWaypoint() { if (curr->getCrossat() > -1000.0) //use a calculated descent/climb rate { use_perf_vs = false; - tgt_vs = (curr->getCrossat() - prev->getAltitude()) +/* tgt_vs = (curr->getCrossat() - prev->getAltitude()) / (fp->getDistanceToGo(pos.getLatitudeDeg(), pos.getLongitudeDeg(), curr) / 6076.0 / prev->getSpeed()*60.0); - checkTcas(); + if (fabs(tgt_vs) > TGT_VS_CUTOFF) { SG_LOG(SG_GENERAL, SG_ALERT, "Rediculously high vertical speed caculated at " << SG_ORIGIN); }; + checkTcas();*/ tgt_altitude_ft = curr->getCrossat(); } else { use_perf_vs = true; diff --git a/src/ATC/trafficcontrol.cxx b/src/ATC/trafficcontrol.cxx index 47f5acc8a..dc0552fe7 100644 --- a/src/ATC/trafficcontrol.cxx +++ b/src/ATC/trafficcontrol.cxx @@ -1318,7 +1318,7 @@ void FGStartupController::render(bool visible) elevationStart = ((i)->getAircraft()->_getAltitude()); } double elevationEnd = segment->getEnd()->getElevation(); - if (elevationEnd == 0) { + if ((elevationEnd == 0) || (elevationEnd == parent->getElevation())) { SGGeod center2 = end; center2.setElevationM(SG_MAX_ELEVATION_M); if (local_scenery->get_elevation_m( center2, elevationEnd, NULL )) { @@ -1326,7 +1326,7 @@ void FGStartupController::render(bool visible) //elevation_meters += 0.5; } else { - elevationEnd = parent->getElevation()+8+dx; + elevationEnd = parent->getElevation(); } segment->getEnd()->setElevation(elevationEnd); } @@ -1376,7 +1376,7 @@ void FGStartupController::render(bool visible) double elevationStart = segment->getStart()->getElevation(); double elevationEnd = segment->getEnd ()->getElevation(); - if (elevationStart == 0) { + if ((elevationStart == 0) || (elevationStart == parent->getElevation())) { SGGeod center2 = segment->getStart()->getGeod(); center2.setElevationM(SG_MAX_ELEVATION_M); if (local_scenery->get_elevation_m( center2, elevationStart, NULL )) { @@ -1384,11 +1384,11 @@ void FGStartupController::render(bool visible) //elevation_meters += 0.5; } else { - elevationStart = parent->getElevation()+8+dx; + elevationStart = parent->getElevation(); } segment->getStart()->setElevation(elevationStart); } - if (elevationEnd == 0) { + if ((elevationEnd == 0) || (elevationEnd == parent->getElevation())) { SGGeod center2 = segment->getEnd()->getGeod(); center2.setElevationM(SG_MAX_ELEVATION_M); if (local_scenery->get_elevation_m( center2, elevationEnd, NULL )) { @@ -1396,7 +1396,7 @@ void FGStartupController::render(bool visible) //elevation_meters += 0.5; } else { - elevationEnd = parent->getElevation()+8+dx; + elevationEnd = parent->getElevation(); } segment->getEnd()->setElevation(elevationEnd); } diff --git a/src/Airports/groundnetwork.cxx b/src/Airports/groundnetwork.cxx index 86beec118..0da6af35c 100644 --- a/src/Airports/groundnetwork.cxx +++ b/src/Airports/groundnetwork.cxx @@ -1,4 +1,3 @@ - // groundnet.cxx - Implimentation of the FlightGear airport ground handling code // // Written by Durk Talsma, started June 2005. @@ -243,6 +242,7 @@ FGGroundNetwork::~FGGroundNetwork() saveData = true; } } + cachefile << "[GroundNetcachedata:ref:2011:09:04]" << endl; for (FGTaxiNodeVectorIterator node = nodes.begin(); node != nodes.end(); node++) { if (saveData) { @@ -286,6 +286,7 @@ void FGGroundNetwork::saveElevationCache() { saveData = true; } } + cachefile << "[GroundNetcachedata:ref:2011:09:04]" << endl; for (FGTaxiNodeVectorIterator node = nodes.begin(); node != nodes.end(); node++) { if (saveData) { @@ -401,17 +402,24 @@ void FGGroundNetwork::init() cacheData.append(airport + "-groundnet-cache.txt"); if (cacheData.exists()) { ifstream data(cacheData.c_str()); - for (FGTaxiNodeVectorIterator i = nodes.begin(); - i != nodes.end(); - i++) { - (*i)->setElevation(parent->getElevation() * SG_FEET_TO_METER); - data >> index >> elev; - if (data.eof()) - break; - if (index != (*i)->getIndex()) { - SG_LOG(SG_GENERAL, SG_ALERT, "Index read from ground network cache at airport " << airport << " does not match index in the network itself"); - } else { - (*i)->setElevation(elev); + string revisionStr; + data >> revisionStr; + if (revisionStr != "[GroundNetcachedata:ref:2011:09:04]") { + SG_LOG(SG_GENERAL, SG_ALERT,"GroundNetwork Warning: discarding outdated cachefile " << + cacheData.c_str() << " for Airport " << airport); + } else { + for (FGTaxiNodeVectorIterator i = nodes.begin(); + i != nodes.end(); + i++) { + (*i)->setElevation(parent->getElevation() * SG_FEET_TO_METER); + data >> index >> elev; + if (data.eof()) + break; + if (index != (*i)->getIndex()) { + SG_LOG(SG_GENERAL, SG_ALERT, "Index read from ground network cache at airport " << airport << " does not match index in the network itself"); + } else { + (*i)->setElevation(elev); + } } } } @@ -1308,7 +1316,7 @@ void FGGroundNetwork::render(bool visible) double elevationEnd = segments[pos]->getEnd()->getElevation(); //cerr << "Using elevation " << elevationEnd << endl; - if (elevationEnd == 0) { + if ((elevationEnd == 0) || (elevationEnd = parent->getElevation())) { SGGeod center2 = end; center2.setElevationM(SG_MAX_ELEVATION_M); if (local_scenery->get_elevation_m( center2, elevationEnd, NULL )) { @@ -1316,7 +1324,7 @@ void FGGroundNetwork::render(bool visible) //elevation_meters += 0.5; } else { - elevationEnd = parent->getElevation()+8+dx; + elevationEnd = parent->getElevation(); } segments[pos]->getEnd()->setElevation(elevationEnd); } @@ -1363,7 +1371,7 @@ void FGGroundNetwork::render(bool visible) // Experimental: Calculate slope here, based on length, and the individual elevations double elevationStart = segments[k]->getStart()->getElevation(); double elevationEnd = segments[k]->getEnd ()->getElevation(); - if (elevationStart == 0) { + if ((elevationStart == 0) || (elevationStart == parent->getElevation())) { SGGeod center2 = segments[k]->getStart()->getGeod(); center2.setElevationM(SG_MAX_ELEVATION_M); if (local_scenery->get_elevation_m( center2, elevationStart, NULL )) { @@ -1371,11 +1379,11 @@ void FGGroundNetwork::render(bool visible) //elevation_meters += 0.5; } else { - elevationStart = parent->getElevation()+8+dx; + elevationStart = parent->getElevation(); } segments[k]->getStart()->setElevation(elevationStart); } - if (elevationEnd == 0) { + if ((elevationEnd == 0) || (elevationEnd == parent->getElevation())) { SGGeod center2 = segments[k]->getEnd()->getGeod(); center2.setElevationM(SG_MAX_ELEVATION_M); if (local_scenery->get_elevation_m( center2, elevationEnd, NULL )) { @@ -1383,7 +1391,7 @@ void FGGroundNetwork::render(bool visible) //elevation_meters += 0.5; } else { - elevationEnd = parent->getElevation()+8+dx; + elevationEnd = parent->getElevation(); } segments[k]->getEnd()->setElevation(elevationEnd); } diff --git a/src/Traffic/Schedule.cxx b/src/Traffic/Schedule.cxx index 0306fc4cd..288d5eb10 100644 --- a/src/Traffic/Schedule.cxx +++ b/src/Traffic/Schedule.cxx @@ -69,6 +69,7 @@ FGAISchedule::FGAISchedule() groundOffset = 0; distanceToUser = 0; valid = true; + lastRun = 0; //score = 0; } @@ -120,6 +121,7 @@ FGAISchedule::FGAISchedule(string model, firstRun = true; runCount = 0; hits = 0; + lastRun = 0; initialized = false; valid = true; } @@ -147,6 +149,7 @@ FGAISchedule::FGAISchedule(const FGAISchedule &other) firstRun = other.firstRun; runCount = other.runCount; hits = other.hits; + lastRun = other.lastRun; initialized = other.initialized; valid = other.valid; } @@ -371,8 +374,7 @@ void FGAISchedule::scheduleFlights() if (!flights.empty()) { return; } - - SG_LOG(SG_GENERAL, SG_BULK, "Scheduling for : " << modelPath << " " << registration << " " << homePort); + SG_LOG(SG_GENERAL, SG_BULK, "Scheduling Flights for : " << modelPath << " " << registration << " " << homePort); FGScheduledFlight *flight = NULL; do { flight = findAvailableFlight(currentDestination, flightIdentifier); @@ -400,14 +402,14 @@ void FGAISchedule::scheduleFlights() depT = depT.substr(0,24); arrT = arrT.substr(0,24); - SG_LOG(SG_GENERAL, SG_BULK, " " << flight->getCallSign() << ":" - << " " << flight->getDepartureAirport()->getId() << ":" - << " " << depT << ":" - << " \"" << flight->getArrivalAirport()->getId() << "\"" << ":" - << " " << arrT << ":"); + SG_LOG(SG_GENERAL, SG_BULK, " Flight " << flight->getCallSign() << ":" + << " " << flight->getDepartureAirport()->getId() << ":" + << " " << depT << ":" + << " \"" << flight->getArrivalAirport()->getId() << "\"" << ":" + << " " << arrT << ":"); flights.push_back(flight); - } while (currentDestination != homePort); + } while (1); //while (currentDestination != homePort); SG_LOG(SG_GENERAL, SG_BULK, " Done "); } @@ -488,7 +490,12 @@ FGScheduledFlight* FGAISchedule::findAvailableFlight (const string ¤tDesti continue; } } - //TODO: check time + if (flights.size()) { + time_t arrival = flights.back()->getArrivalTime(); + if ((*i)->getDepartureTime() < arrival) + continue; + } + // So, if we actually get here, we have a winner //cerr << "found flight: " << req << " : " << currentDestination << " : " << // (*i)->getArrivalAirport()->getId() << endl; @@ -537,48 +544,11 @@ bool compareSchedules(FGAISchedule*a, FGAISchedule*b) return (*a) < (*b); } - -// void FGAISchedule::setClosestDistanceToUser() -// { - - -// double course; -// double dist; - -// time_t -// totalTimeEnroute, -// elapsedTimeEnroute; - -// double userLatitude = fgGetDouble("/position/latitude-deg"); -// double userLongitude = fgGetDouble("/position/longitude-deg"); - -// FGAirport *dep; - -// #if defined( __CYGWIN__) || defined( __MINGW32__) -// #define HUGE HUGE_VAL -// #endif -// distanceToUser = HUGE; -// FGScheduledFlightVecIterator i = flights.begin(); -// while (i != flights.end()) -// { -// dep = i->getDepartureAirport(); -// //if (!(dep)) -// //return HUGE; - -// SGWayPoint user ( userLongitude, -// userLatitude, -// i->getCruiseAlt()); -// SGWayPoint current (dep->getLongitude(), -// dep->getLatitude(), -// 0); -// user.CourseAndDistance(current, &course, &dist); -// if (dist < distanceToUser) -// { -// distanceToUser = dist; -// //cerr << "Found closest distance to user for " << registration << " to be " << distanceToUser << " at airport " << dep->getId() << endl; -// } -// i++; -// } -// //return distToUser; -// } +bool FGAISchedule::operator< (const FGAISchedule &other) const +{ + //cerr << "Sorting " << registration << " and " << other.registration << endl; + double currentScore = score * (1.5 - lastRun); + double otherScore = other.score * (1.5 - other.lastRun); + return currentScore > otherScore; +} diff --git a/src/Traffic/Schedule.hxx b/src/Traffic/Schedule.hxx index 1f508271b..7c7816120 100644 --- a/src/Traffic/Schedule.hxx +++ b/src/Traffic/Schedule.hxx @@ -56,6 +56,7 @@ class FGAISchedule double score; unsigned int runCount; unsigned int hits; + unsigned int lastRun; bool firstRun; double courseToDest; bool initialized; @@ -124,8 +125,10 @@ class FGAISchedule FGScheduledFlight*findAvailableFlight (const string ¤tDestination, const string &req); // used to sort in decending order of score: I've probably found a better way to // decending order sorting, but still need to test that. - bool operator< (const FGAISchedule &other) const { return (score > other.score); }; + bool operator< (const FGAISchedule &other) const; void taint() { valid = false; }; + int getLastUsed() { return (int) valid;}; + void setLastUsed(unsigned int val) {lastRun = val; }; //void * getAiRef () { return AIManagerRef; }; //FGAISchedule* getAddress () { return this;}; diff --git a/src/Traffic/TrafficMgr.cxx b/src/Traffic/TrafficMgr.cxx index 9ebf78c1c..8870aa66f 100644 --- a/src/Traffic/TrafficMgr.cxx +++ b/src/Traffic/TrafficMgr.cxx @@ -109,6 +109,7 @@ FGTrafficManager::~FGTrafficManager() //cerr << "Saving AI traffic heuristics" << endl; saveData = true; cachefile.open(cacheData.str().c_str()); + cachefile << "[TrafficManagerCachedata:ref:2011:09:04]" << endl; } } for (ScheduleVectorIterator sched = scheduledAircraft.begin(); @@ -116,7 +117,8 @@ FGTrafficManager::~FGTrafficManager() if (saveData) { cachefile << (*sched)->getRegistration() << " " << (*sched)->getRunCount() << " " - << (*sched)->getHits() << endl; + << (*sched)->getHits() << " " + << (*sched)->getLastUsed() << endl; } delete(*sched); } @@ -182,23 +184,31 @@ void FGTrafficManager::init() airport[0], airport[1], airport[2]); cacheData.append(buffer); cacheData.append(airport + "-cache.txt"); + string revisionStr; if (cacheData.exists()) { ifstream data(cacheData.c_str()); - while (1) { - Heuristic h; // = new Heuristic; - data >> h.registration >> h.runCount >> h.hits; - if (data.eof()) - break; - HeuristicMapIterator itr = heurMap.find(h.registration); - if (itr != heurMap.end()) { - SG_LOG(SG_GENERAL, SG_WARN,"Traffic Manager Warning: found duplicate tailnumber " << - h.registration << " for AI aircraft"); + data >> revisionStr; + if (revisionStr != "[TrafficManagerCachedata:ref:2011:09:04]") { + SG_LOG(SG_GENERAL, SG_ALERT,"Traffic Manager Warning: discarding outdated cachefile " << + cacheData.c_str() << " for Airport " << airport); + } else { + while (1) { + Heuristic h; // = new Heuristic; + data >> h.registration >> h.runCount >> h.hits >> h.lastRun; + if (data.eof()) + break; + HeuristicMapIterator itr = heurMap.find(h.registration); + if (itr != heurMap.end()) { + SG_LOG(SG_GENERAL, SG_WARN,"Traffic Manager Warning: found duplicate tailnumber " << + h.registration << " for AI aircraft"); + } else { + heurMap[h.registration] = h; + heuristics.push_back(h); + } } - heurMap[h.registration] = h; - heuristics.push_back(h); } } - } + } for (currAircraft = scheduledAircraft.begin(); currAircraft != scheduledAircraft.end(); currAircraft++) { string registration = (*currAircraft)->getRegistration(); @@ -209,25 +219,26 @@ void FGTrafficManager::init() } else { (*currAircraft)->setrunCount(itr->second.runCount); (*currAircraft)->setHits(itr->second.hits); - //cerr <<"Runcount " << itr->second->runCount << ".Hits " << itr->second->hits << endl; + (*currAircraft)->setLastUsed(itr->second.lastRun); + //cerr <<"Runcount " << itr->second.runCount << ". Hits " << itr->second.hits << ". Last run " << itr->second.lastRun<< endl; } } //cerr << "Done" << endl; //for (heuristicsVectorIterator hvi = heuristics.begin(); // hvi != heuristics.end(); hvi++) { // delete(*hvi); - //} + //} } // Do sorting and scoring separately, to take advantage of the "homeport| variable for (currAircraft = scheduledAircraft.begin(); currAircraft != scheduledAircraft.end(); currAircraft++) { (*currAircraft)->setScore(); } + sort(scheduledAircraft.begin(), scheduledAircraft.end(), compareSchedules); currAircraft = scheduledAircraft.begin(); currAircraftClosest = scheduledAircraft.begin(); - inited = true; } diff --git a/src/Traffic/TrafficMgr.hxx b/src/Traffic/TrafficMgr.hxx index ab1e19880..c8f9faca1 100644 --- a/src/Traffic/TrafficMgr.hxx +++ b/src/Traffic/TrafficMgr.hxx @@ -64,6 +64,7 @@ public: std::string registration; unsigned int runCount; unsigned int hits; + unsigned int lastRun; }; typedef std::vector<Heuristic> heuristicsVector;