Keep revising ATC
This commit is contained in:
parent
64aa3927a7
commit
3e1dc4683b
3 changed files with 123 additions and 130 deletions
|
@ -67,12 +67,6 @@ using std::string;
|
|||
/***************************************************************************
|
||||
* FGGroundController()
|
||||
**************************************************************************/
|
||||
|
||||
bool compare_trafficrecords(FGTrafficRecord a, FGTrafficRecord b)
|
||||
{
|
||||
return (a.getIntentions().size() < b.getIntentions().size());
|
||||
}
|
||||
|
||||
FGGroundController::FGGroundController() :
|
||||
parent(NULL)
|
||||
{
|
||||
|
@ -99,6 +93,31 @@ void FGGroundController::init(FGAirportDynamics* aDynamics)
|
|||
networkInitialized = true;
|
||||
}
|
||||
|
||||
bool compare_trafficrecords(FGTrafficRecord a, FGTrafficRecord b)
|
||||
{
|
||||
return (a.getIntentions().size() < b.getIntentions().size());
|
||||
}
|
||||
|
||||
/*
|
||||
* Search activeTraffic vector to find matching id
|
||||
* @param id integer to search for in the vector
|
||||
* @return the matching item OR activeTraffic.end()
|
||||
*/
|
||||
TrafficVectorIterator FGGroundController::searchActiveTraffic(int id)
|
||||
{
|
||||
// Possible optimization - investigate using map instead of vector
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
if (!activeTraffic.empty()) {
|
||||
while (i != activeTraffic.end()) {
|
||||
if (i->getId() == id) {
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
void FGGroundController::announcePosition(int id,
|
||||
FGAIFlightPlan * intendedRoute,
|
||||
int currentPosition, double lat,
|
||||
|
@ -112,19 +131,11 @@ void FGGroundController::announcePosition(int id,
|
|||
return;
|
||||
}
|
||||
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
// Search search if the current id alread has an entry
|
||||
// This might be faster using a map instead of a vector, but let's start by taking a safe route
|
||||
if (!activeTraffic.empty()) {
|
||||
//while ((i->getId() != id) && i != activeTraffic.end()) {
|
||||
while (i != activeTraffic.end()) {
|
||||
if (i->getId() == id) {
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
// Add a new TrafficRecord if no one exsists for this aircraft.
|
||||
// Search the activeTraffic vector to find a traffic vector with our id
|
||||
TrafficVectorIterator i = searchActiveTraffic(id);
|
||||
|
||||
// Add a new TrafficRecord if none exists for this aircraft
|
||||
// otherwise set the information for the TrafficRecord
|
||||
if (i == activeTraffic.end() || (activeTraffic.empty())) {
|
||||
FGTrafficRecord rec;
|
||||
rec.setId(id);
|
||||
|
@ -133,33 +144,27 @@ void FGGroundController::announcePosition(int id,
|
|||
rec.setPositionAndHeading(lat, lon, heading, speed, alt);
|
||||
rec.setRadius(radius); // only need to do this when creating the record.
|
||||
rec.setAircraft(aircraft);
|
||||
// add to the front of the list of activeTraffic if the aircraft is already taxiing
|
||||
if (leg == 2) {
|
||||
activeTraffic.push_front(rec);
|
||||
} else {
|
||||
activeTraffic.push_back(rec);
|
||||
}
|
||||
|
||||
} else {
|
||||
i->setPositionAndIntentions(currentPosition, intendedRoute);
|
||||
i->setPositionAndHeading(lat, lon, heading, speed, alt);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Search for and erase an aircraft with a certain id from the activeTraffic vector
|
||||
*/
|
||||
void FGGroundController::signOff(int id)
|
||||
{
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
// Search search if the current id alread has an entry
|
||||
// This might be faster using a map instead of a vector, but let's start by taking a safe route
|
||||
if (activeTraffic.size()) {
|
||||
//while ((i->getId() != id) && i != activeTraffic.end()) {
|
||||
while (i != activeTraffic.end()) {
|
||||
if (i->getId() == id) {
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
// Search the activeTraffic vector to find a traffic vector with our id
|
||||
TrafficVectorIterator i = searchActiveTraffic(id);
|
||||
|
||||
// If one is found erase the record, else give an error message
|
||||
if (i == activeTraffic.end() || (activeTraffic.size() == 0)) {
|
||||
SG_LOG(SG_GENERAL, SG_ALERT,
|
||||
"AI error: Aircraft without traffic record is signing off at " << SG_ORIGIN);
|
||||
|
@ -167,7 +172,8 @@ void FGGroundController::signOff(int id)
|
|||
i = activeTraffic.erase(i);
|
||||
}
|
||||
}
|
||||
/**
|
||||
|
||||
/*
|
||||
* The ground network can deal with the following states:
|
||||
* 0 = Normal; no action required
|
||||
* 1 = "Acknowledge "Hold position
|
||||
|
@ -179,7 +185,7 @@ void FGGroundController::signOff(int id)
|
|||
* 7 = Acknowledge report runway
|
||||
* 8 = Switch tower frequency
|
||||
* 9 = Acknowledge switch tower frequency
|
||||
*************************************************************************************************************************/
|
||||
*/
|
||||
bool FGGroundController::checkTransmissionState(int minState, int maxState, TrafficVectorIterator i, time_t now, AtcMsgId msgId,
|
||||
AtcMsgDir msgDir)
|
||||
{
|
||||
|
@ -220,7 +226,7 @@ void FGGroundController::updateAircraftInformation(int id, double lat, double lo
|
|||
// Transmit confirmation ...
|
||||
// Probably use a status mechanism similar to the Engine start procedure in the startup controller.
|
||||
|
||||
|
||||
// leave this here until I figure out what current, closest is all about
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
// Search search if the current id has an entry
|
||||
// This might be faster using a map instead of a vector, but let's start by taking a safe route
|
||||
|
@ -287,18 +293,18 @@ void FGGroundController::updateAircraftInformation(int id, double lat, double lo
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Scan for a speed adjustment change. Find the nearest aircraft that is in front
|
||||
and adjust speed when we get too close. Only do this when current position and/or
|
||||
intentions of the current aircraft match current taxiroute position of the proximate
|
||||
aircraft. For traffic that is on other routes we need to issue a "HOLD Position"
|
||||
instruction. See below for the hold position instruction.
|
||||
/*
|
||||
* Scan for a speed adjustment change. Find the nearest aircraft that is in front
|
||||
* and adjust speed when we get too close. Only do this when current position and/or
|
||||
* intentions of the current aircraft match current taxiroute position of the proximate
|
||||
* aircraft. For traffic that is on other routes we need to issue a "HOLD Position"
|
||||
* instruction. See below for the hold position instruction.
|
||||
|
||||
Note that there currently still is one flaw in the logic that needs to be addressed.
|
||||
There can be situations where one aircraft is in front of the current aircraft, on a separate
|
||||
route, but really close after an intersection coming off the current route. This
|
||||
aircraft is still close enough to block the current aircraft. This situation is currently
|
||||
not addressed yet, but should be.
|
||||
* Note that there currently still is one flaw in the logic that needs to be addressed.
|
||||
* There can be situations where one aircraft is in front of the current aircraft, on a separate
|
||||
* route, but really close after an intersection coming off the current route. This
|
||||
* aircraft is still close enough to block the current aircraft. This situation is currently
|
||||
* not addressed yet, but should be.
|
||||
*/
|
||||
|
||||
void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
||||
|
@ -330,6 +336,8 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
|
||||
// previousInstruction = current->getSpeedAdjustment();
|
||||
double mindist = HUGE_VAL;
|
||||
|
||||
// First check all our activeTraffic
|
||||
if (activeTraffic.size()) {
|
||||
double course, dist, bearing, az2; // minbearing,
|
||||
SGGeod curr(SGGeod::fromDegM(lon, lat, alt));
|
||||
|
@ -354,10 +362,10 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
closest = i;
|
||||
closestOnNetwork = i;
|
||||
// minbearing = bearing;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
//Check traffic at the tower controller
|
||||
// Next check with the tower controller
|
||||
if (towerController->hasActiveTraffic()) {
|
||||
for (TrafficVectorIterator i =
|
||||
towerController->getActiveTraffic().begin();
|
||||
|
@ -381,6 +389,7 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Finally, check UserPosition
|
||||
// Note, as of 2011-08-01, this should no longer be necessecary.
|
||||
/*
|
||||
|
@ -399,8 +408,11 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
otherReasonToSlowDown = true;
|
||||
}
|
||||
*/
|
||||
|
||||
// Clear any active speed adjustment, check if the aircraft needs to brake
|
||||
current->clearSpeedAdjustment();
|
||||
bool needBraking = false;
|
||||
|
||||
if (current->checkPositionAndIntentions(*closest)
|
||||
|| otherReasonToSlowDown) {
|
||||
double maxAllowableDistance =
|
||||
|
@ -411,6 +423,7 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
return;
|
||||
else
|
||||
current->setWaitsForId(closest->getId());
|
||||
|
||||
if (closest->getId() != current->getId()) {
|
||||
current->setSpeedAdjustment(closest->getSpeed() *
|
||||
(mindist / 100));
|
||||
|
@ -425,6 +438,7 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
} else {
|
||||
current->setSpeedAdjustment(0); // This can only happen when the user aircraft is the one closest
|
||||
}
|
||||
|
||||
if (mindist < maxAllowableDistance) {
|
||||
//double newSpeed = (maxAllowableDistance-mindist);
|
||||
//current->setSpeedAdjustment(newSpeed);
|
||||
|
@ -435,18 +449,19 @@ void FGGroundController::checkSpeedAdjustment(int id, double lat,
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ((closest->getId() == closestOnNetwork->getId()) && (current->getPriority() < closest->getPriority()) && needBraking) {
|
||||
swap(current, closest);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Check for "Hold position instruction".
|
||||
The hold position should be issued under the following conditions:
|
||||
1) For aircraft entering or crossing a runway with active traffic on it, or landing aircraft near it
|
||||
2) For taxiing aircraft that use one taxiway in opposite directions
|
||||
3) For crossing or merging taxiroutes.
|
||||
/*
|
||||
* Check for "Hold position instruction".
|
||||
* The hold position should be issued under the following conditions:
|
||||
* 1) For aircraft entering or crossing a runway with active traffic on it, or landing aircraft near it
|
||||
* 2) For taxiing aircraft that use one taxiway in opposite directions
|
||||
* 3) For crossing or merging taxiroutes.
|
||||
*/
|
||||
|
||||
void FGGroundController::checkHoldPosition(int id, double lat,
|
||||
|
@ -474,7 +489,6 @@ void FGGroundController::checkHoldPosition(int id, double lat,
|
|||
"AI error: Trying to access non-existing aircraft in FGGroundNetwork::checkHoldPosition at " << SG_ORIGIN);
|
||||
}
|
||||
current = i;
|
||||
//
|
||||
if (current->getAircraft()->getTakeOffStatus() == 1) {
|
||||
current->setHoldPosition(true);
|
||||
return;
|
||||
|
@ -585,7 +599,7 @@ void FGGroundController::checkHoldPosition(int id, double lat,
|
|||
//current->setState(0);
|
||||
}
|
||||
|
||||
/**
|
||||
/*
|
||||
* Check whether situations occur where the current aircraft is waiting for itself
|
||||
* due to higher order interactions.
|
||||
* A 'circular' wait is a situation where a waits for b, b waits for c, and c waits
|
||||
|
@ -601,7 +615,7 @@ void FGGroundController::checkHoldPosition(int id, double lat,
|
|||
|
||||
bool FGGroundController::checkForCircularWaits(int id)
|
||||
{
|
||||
SG_LOG(SG_ATC, SG_DEBUG, "Performing Wait check " << id);
|
||||
SG_LOG(SG_ATC, SG_DEBUG, "Performing circular check for " << id);
|
||||
int target = 0;
|
||||
TrafficVectorIterator current, other;
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
|
@ -696,18 +710,9 @@ bool FGGroundController::checkForCircularWaits(int id)
|
|||
// Note that this function is probably obsolete...
|
||||
bool FGGroundController::hasInstruction(int id)
|
||||
{
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
// Search search if the current id has an entry
|
||||
// This might be faster using a map instead of a vector, but let's start by taking a safe route
|
||||
if (activeTraffic.size()) {
|
||||
//while ((i->getId() != id) && i != activeTraffic.end()) {
|
||||
while (i != activeTraffic.end()) {
|
||||
if (i->getId() == id) {
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
// Search the activeTraffic vector to find a traffic vector with our id
|
||||
TrafficVectorIterator i = searchActiveTraffic(id);
|
||||
|
||||
if (i == activeTraffic.end() || (activeTraffic.size() == 0)) {
|
||||
SG_LOG(SG_GENERAL, SG_ALERT,
|
||||
"AI error: checking ATC instruction for aircraft without traffic record at " << SG_ORIGIN);
|
||||
|
@ -719,18 +724,9 @@ bool FGGroundController::hasInstruction(int id)
|
|||
|
||||
FGATCInstruction FGGroundController::getInstruction(int id)
|
||||
{
|
||||
TrafficVectorIterator i = activeTraffic.begin();
|
||||
// Search search if the current id has an entry
|
||||
// This might be faster using a map instead of a vector, but let's start by taking a safe route
|
||||
if (activeTraffic.size()) {
|
||||
//while ((i->getId() != id) && i != activeTraffic.end()) {
|
||||
while (i != activeTraffic.end()) {
|
||||
if (i->getId() == id) {
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
// Search the activeTraffic vector to find a traffic vector with our id
|
||||
TrafficVectorIterator i = searchActiveTraffic(id);
|
||||
|
||||
if (i == activeTraffic.end() || (activeTraffic.size() == 0)) {
|
||||
SG_LOG(SG_GENERAL, SG_ALERT,
|
||||
"AI error: requesting ATC instruction for aircraft without traffic record at " << SG_ORIGIN);
|
||||
|
@ -754,9 +750,7 @@ static void WorldCoordinate(osg::Matrix& obj_pos, double lat,
|
|||
0.0, 1.0, 0.0));
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/* Draw visible taxi routes */
|
||||
void FGGroundController::render(bool visible)
|
||||
{
|
||||
SGMaterialLib *matlib = globals->get_matlib();
|
||||
|
|
|
@ -76,7 +76,7 @@ public:
|
|||
};
|
||||
|
||||
|
||||
|
||||
virtual TrafficVectorIterator searchActiveTraffic(int id);
|
||||
virtual void announcePosition(int id, FGAIFlightPlan *intendedRoute, int currentRoute,
|
||||
double lat, double lon, double hdg, double spd, double alt,
|
||||
double radius, int leg, FGAIAircraft *aircraft);
|
||||
|
|
|
@ -532,7 +532,6 @@ FGATCInstruction::FGATCInstruction()
|
|||
alt = 0;
|
||||
}
|
||||
|
||||
|
||||
bool FGATCInstruction::hasInstruction() const
|
||||
{
|
||||
return (holdPattern || holdPosition || changeSpeed || changeHeading
|
||||
|
|
Loading…
Add table
Reference in a new issue