X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=src%2FNavaids%2Fnavdb.cxx;h=4f7c10e7f8e89241e3d67d532ee6d7cfac6e0856;hb=2e6d7e111aa3681e764ba57dc5c03e595dea8422;hp=40f487c5c22ea9b5699615cd23f9231a90749857;hpb=89010e6b0ac344970dfe3e802e4e51703fedc8ff;p=flightgear.git diff --git a/src/Navaids/navdb.cxx b/src/Navaids/navdb.cxx index 40f487c5c..4f7c10e7f 100644 --- a/src/Navaids/navdb.cxx +++ b/src/Navaids/navdb.cxx @@ -38,10 +38,67 @@ #include "navrecord.hxx" #include "navlist.hxx" #include "navdb.hxx" -#include "Main/globals.hxx" +#include
+#include +#include using std::string; +static FGPositioned::Type +mapRobinTypeToFGPType(int aTy) +{ + switch (aTy) { + // case 1: + case 2: return FGPositioned::NDB; + case 3: return FGPositioned::VOR; + case 4: return FGPositioned::ILS; + case 5: return FGPositioned::LOC; + case 6: return FGPositioned::GS; + case 12: + case 13: return FGPositioned::DME; + case 99: return FGPositioned::INVALID; // end-of-file code + default: + throw sg_range_exception("Got a nav.dat type we don't recognize", "FGNavRecord::createFromStream"); + } +} + +static FGNavRecord* createNavFromStream(std::istream& aStream) +{ + int rawType; + aStream >> rawType; + if (aStream.eof() || (rawType == 99)) { + return NULL; // happens with, eg, carrier_nav.dat + } + + double lat, lon, elev_ft, multiuse; + int freq, range; + std::string name, ident; + aStream >> lat >> lon >> elev_ft >> freq >> range >> multiuse >> ident; + getline(aStream, name); + + SGGeod pos(SGGeod::fromDegFt(lon, lat, elev_ft)); + name = simgear::strutils::strip(name); + + if ((rawType >= 7) && (rawType <= 9)) { + // marker beacons use a different run-time class now + FGMarkerBeaconRecord::create(rawType, name, pos); + return NULL; // not a nav-record, but that's okay + } + + FGPositioned::Type type = mapRobinTypeToFGPType(rawType); + if (type == FGPositioned::INVALID) { + return NULL; + } + + // silently multiply adf frequencies by 100 so that adf + // vs. nav/loc frequency lookups can use the same code. + if (type == FGPositioned::NDB) { + freq *= 100; + } + + return new FGNavRecord(type, ident, name, pos, + freq, range, multiuse); +} // load and initialize the navigational databases bool fgNavDBInit( FGNavList *navlist, FGNavList *loclist, FGNavList *gslist, @@ -50,17 +107,6 @@ bool fgNavDBInit( FGNavList *navlist, FGNavList *loclist, FGNavList *gslist, FGTACANList *channellist) { SG_LOG(SG_GENERAL, SG_INFO, "Loading Navaid Databases"); - // SG_LOG(SG_GENERAL, SG_INFO, " VOR/NDB"); - // SGPath p_nav( globals->get_fg_root() ); - // p_nav.append( "Navaids/default.nav" ); - // navlist->init( p_nav ); - - // SG_LOG(SG_GENERAL, SG_INFO, " ILS and Marker Beacons"); - // beacons->init(); - // SGPath p_ils( globals->get_fg_root() ); - // p_ils.append( "Navaids/default.ils" ); - // ilslist->init( p_ils ); - SGPath path( globals->get_fg_root() ); path.append( "Navaids/nav.dat" ); @@ -76,9 +122,9 @@ bool fgNavDBInit( FGNavList *navlist, FGNavList *loclist, FGNavList *gslist, in >> skipeol; while (!in.eof()) { - FGNavRecord *r = FGNavRecord::createFromStream(in); + FGNavRecord *r = createNavFromStream(in); if (!r) { - break; + continue; } switch (r->type()) { @@ -96,12 +142,6 @@ bool fgNavDBInit( FGNavList *navlist, FGNavList *loclist, FGNavList *gslist, gslist->add(r); break; - case FGPositioned::OM: - case FGPositioned::MM: - case FGPositioned::IM: - // no need to add this to a list, never searched by frequency - break; - case FGPositioned::DME: { dmelist->add(r); @@ -143,7 +183,7 @@ bool fgNavDBInit( FGNavList *navlist, FGNavList *loclist, FGNavList *gslist, //incarrier >> skipeol; while ( ! incarrier.eof() ) { - FGNavRecord *r = FGNavRecord::createFromStream(incarrier); + FGNavRecord *r = createNavFromStream(incarrier); if (!r) { continue; } @@ -185,3 +225,25 @@ bool fgNavDBInit( FGNavList *navlist, FGNavList *loclist, FGNavList *gslist, return true; } + +FGRunway* getRunwayFromName(const std::string& aName) +{ + vector parts = simgear::strutils::split(aName); + if (parts.size() < 2) { + SG_LOG(SG_GENERAL, SG_WARN, "getRunwayFromName: malformed name:" << aName); + return NULL; + } + + const FGAirport* apt = fgFindAirportID(parts[0]); + if (!apt) { + SG_LOG(SG_GENERAL, SG_WARN, "navaid " << aName << " associated with bogus airport ID:" << parts[0]); + return NULL; + } + + if (!apt->hasRunwayWithIdent(parts[1])) { + SG_LOG(SG_GENERAL, SG_WARN, "navaid " << aName << " associated with bogus runway ID:" << parts[1]); + return NULL; + } + + return apt->getRunwayByIdent(parts[1]); +}