-// // FGAIAircraft - FGAIBase-derived class creates an AI airplane
+// FGAIAircraft - FGAIBase-derived class creates an AI airplane
//
// Written by David Culp, started October 2003.
//
#include "performancedata.hxx"
#include "performancedb.hxx"
+
+#define TGT_VS_CUTOFF 10000
//#include <Airports/trafficcontroller.hxx>
static string tempReg;
else
groundOffset = 0;
- fp = 0;
- controller = 0;
- prevController = 0;
+ fp = 0;
+ controller = 0;
+ prevController = 0;
+ towerController = 0;
dt_count = 0;
dt_elev_count = 0;
use_perf_vs = true;
_performance = 0; //TODO initialize to JET_TRANSPORT from PerformanceDB
dt = 0;
+ takeOffStatus = 0;
}
void FGAIAircraft::Run(double dt) {
+
FGAIAircraft::dt = dt;
bool outOfSight = false,
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;
bool FGAIAircraft::loadNextLeg(double distance) {
int leg;
- if ((leg = fp->getLeg()) == 10) {
+ if ((leg = fp->getLeg()) == 9) {
if (!trafficRef->next()) {
return false;
}
setCallSign(trafficRef->getCallSign());
- leg = 1;
+ leg = 0;
fp->setLeg(leg);
}
void FGAIAircraft::doGroundAltitude() {
+
if ((fabs(altitude_ft - (tgt_altitude_ft+groundOffset)) > 1000.0)||
(isStationary()))
altitude_ft = (tgt_altitude_ft + groundOffset);
}
}
+void FGAIAircraft::scheduleForATCTowerDepartureControl(int state) {
+ if (!takeOffStatus) {
+ int leg = fp->getLeg();
+ if (trafficRef) {
+ if (trafficRef->getDepartureAirport()->getDynamics()) {
+ towerController = trafficRef->getDepartureAirport()->getDynamics()->getTowerController();
+ } else {
+ cerr << "Error: Could not find Dynamics at airport : " << trafficRef->getDepartureAirport()->getId() << endl;
+ }
+ if (towerController) {
+ towerController->announcePosition(getID(), fp, fp->getCurrentWaypoint()->getRouteIndex(),
+ _getLatitude(), _getLongitude(), hdg, speed, altitude_ft,
+ trafficRef->getRadius(), leg, this);
+ //cerr << "Scheduling " << trafficRef->getCallSign() << " for takeoff " << endl;
+ }
+ }
+ }
+ takeOffStatus = state;
+}
+
// Process ATC instructions and report back
void FGAIAircraft::processATC(FGATCInstruction instruction) {
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;
}
if (trafficRef) {
//cerr << "Tracking callsign : \"" << fgGetString("/ai/track-callsign") << "\"" << endl;
-/* if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
+ if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
cerr << trafficRef->getCallSign() << " " << tgt_altitude_ft << " " << _getSpeed() << " "
- << _getAltitude() << " "<< _getLatitude() << " " << _getLongitude() << " " << dist_to_go << " " << lead_dist << " " << curr->name << " " << vs << " " << tgt_vs << " " << bearing << " " << minBearing << " " << speedFraction << endl;
- }*/
+ << _getAltitude() << " "<< _getLatitude() << " " << _getLongitude() << " " << dist_to_go << " " << lead_dist << " " << curr->getName() << " " << vs << " " << tgt_vs << " " << bearing << " " << minBearing << " " << speedFraction << " " << invisible << endl;
+ }
}
if ((dist_to_go < lead_dist) || (bearing > (minBearing * 1.1))) {
minBearing = 360;
// This waypoint marks the fact that the aircraft has passed the initial taxi
// departure waypoint, so it can release the parking.
//cerr << trafficRef->getCallSign() << " has passed waypoint " << prev->name << " at speed " << speed << endl;
+ //cerr << "Passing waypoint : " << prev->getName() << endl;
if (prev->contains("PushBackPoint")) {
dep->getDynamics()->releaseParking(fp->getGate());
AccelTo(0.0);
- setTaxiClearanceRequest(true);
+ //setTaxiClearanceRequest(true);
}
if (prev->contains("legend")) {
fp->incrementLeg();
}
+ if (prev->contains(string("DepartureHold"))) {
+ //cerr << "Passing point DepartureHold" << endl;
+ scheduleForATCTowerDepartureControl(2);
+ }
// This is the last taxi waypoint, and marks the the end of the flight plan
// so, the schedule should update and wait for the next departure time.
if (nextDeparture < (now+1200)) {
nextDeparture = now + 1200;
}
- fp->setTime(nextDeparture); // should be "next departure"
+ fp->setTime(nextDeparture);
}
return true;
double distanceCovered = descentSpeed * descentTimeNeeded;
//cerr << "Tracking : " << fgGetString("/ai/track-callsign");
- if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
- cerr << "Checking for end of cruise stage for :" << trafficRef->getCallSign() << endl;
- cerr << "Descent rate : " << descentRate << endl;
- cerr << "Descent speed : " << descentSpeed << endl;
- cerr << "VerticalDistance : " << verticalDistance << ". Altitude : " << altitude_ft << ". Elevation " << trafficRef->getArrivalAirport()->getElevation() << endl;
- cerr << "DecentTimeNeeded : " << descentTimeNeeded << endl;
- cerr << "DistanceCovered : " << distanceCovered << endl;
- }
+// if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
+// cerr << "Checking for end of cruise stage for :" << trafficRef->getCallSign() << endl;
+// cerr << "Descent rate : " << descentRate << endl;
+// cerr << "Descent speed : " << descentSpeed << endl;
+// cerr << "VerticalDistance : " << verticalDistance << ". Altitude : " << altitude_ft << ". Elevation " << trafficRef->getArrivalAirport()->getElevation() << endl;
+// cerr << "DecentTimeNeeded : " << descentTimeNeeded << endl;
+// cerr << "DistanceCovered : " << distanceCovered << endl;
+// }
//cerr << "Distance = " << distance << endl;
distance = distanceCovered;
if (dist < distanceCovered) {
- if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
- //exit(1);
- }
+// if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
+// //exit(1);
+// }
return true;
} else {
return false;
time_t ete = tracklength / ((speed * SG_NM_TO_METER) / 3600.0);
time_t secondsToGo = arrivalTime - now;
- if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
- cerr << "Checking arrival time: ete " << ete << ". Time to go : " << secondsToGo << ". Track length = " << tracklength << endl;
- }
+// if (trafficRef->getCallSign() == fgGetString("/ai/track-callsign")) {
+// cerr << "Checking arrival time: ete " << ete << ". Time to go : " << secondsToGo << ". Track length = " << tracklength << endl;
+// }
return (ete - secondsToGo); // Positive when we're too slow...
}