From 3d46809ea8030af12d3148a8f4007a9f8332af3e Mon Sep 17 00:00:00 2001 From: James Turner Date: Tue, 24 Apr 2012 10:53:46 +0100 Subject: [PATCH] Expose waypoint source (airport/runway/navaid) to Nasal --- src/Navaids/route.cxx | 5 ++ src/Navaids/route.hxx | 7 +++ src/Navaids/waypoint.cxx | 5 ++ src/Navaids/waypoint.hxx | 9 +++- src/Scripting/NasalPositioned.cxx | 82 ++++++++++++++++++++++++++++++- 5 files changed, 105 insertions(+), 3 deletions(-) diff --git a/src/Navaids/route.cxx b/src/Navaids/route.cxx index d922fd0b0..ada75fe4e 100644 --- a/src/Navaids/route.cxx +++ b/src/Navaids/route.cxx @@ -151,6 +151,11 @@ double Waypt::magvarDeg() const return _magVarDeg; } +double Waypt::headingRadialDeg() const +{ + return 0.0; +} + /////////////////////////////////////////////////////////////////////////// // persistence diff --git a/src/Navaids/route.hxx b/src/Navaids/route.hxx index c18c3883d..e0ddb6334 100644 --- a/src/Navaids/route.hxx +++ b/src/Navaids/route.hxx @@ -164,6 +164,13 @@ public: * For some waypoint types this will always return 0. */ virtual double magvarDeg() const; + + /** + * return the assoicated heading or radial for this waypoint. + * The exact meaning varies by type - for a hold it's the inbound radial, + * for a DME intercept it's the heading to hold, and so on. + */ + virtual double headingRadialDeg() const; protected: friend class NavdataVisitor; diff --git a/src/Navaids/waypoint.cxx b/src/Navaids/waypoint.cxx index 12cee7744..7327107b0 100644 --- a/src/Navaids/waypoint.cxx +++ b/src/Navaids/waypoint.cxx @@ -211,6 +211,11 @@ FGPositioned* RunwayWaypt::source() const { return _runway; } + +double RunwayWaypt::headingRadialDeg() const +{ + return _runway->headingDeg(); +} void RunwayWaypt::initFromProperties(SGPropertyNode_ptr aProp) { diff --git a/src/Navaids/waypoint.hxx b/src/Navaids/waypoint.hxx index 0b2ae7d95..ece8cadf5 100644 --- a/src/Navaids/waypoint.hxx +++ b/src/Navaids/waypoint.hxx @@ -133,6 +133,7 @@ public: FGRunway* runway() const { return _runway; } + virtual double headingRadialDeg() const; protected: virtual std::string type() const { return "runway"; } @@ -170,6 +171,8 @@ public: double timeOrDistance() const { return _holdTD;} + virtual double headingRadialDeg() const + { return inboundRadial(); } protected: virtual void initFromProperties(SGPropertyNode_ptr aProp); virtual void writeToProperties(SGPropertyNode_ptr aProp) const; @@ -209,6 +212,8 @@ public: virtual double magvarDeg() const { return 0.0; } + virtual double headingRadialDeg() const + { return headingDegMagnetic(); } private: std::string _ident; double _magHeading; @@ -239,7 +244,9 @@ public: double dmeDistanceNm() const { return _dmeDistanceNm; } - + + virtual double headingRadialDeg() const + { return courseDegMagnetic(); } private: std::string _ident; SGGeod _pos; diff --git a/src/Scripting/NasalPositioned.cxx b/src/Scripting/NasalPositioned.cxx index 5105a283c..979ef06a8 100644 --- a/src/Scripting/NasalPositioned.cxx +++ b/src/Scripting/NasalPositioned.cxx @@ -145,6 +145,8 @@ naRef hashForWaypoint(naContext c, flightgear::Waypt* wpt, flightgear::Waypt* ne flightgear::Procedure* proc = dynamic_cast(wpt->owner()); if (proc) { hashset(c, h, "wp_parent_name", stringToNasal(c, proc->ident())); + // set 'wp_parent' route object to query the SID / STAR / airway? + // TODO - needs some extensions to flightgear::Route } if (wpt->type() == "hold") { @@ -172,7 +174,7 @@ naRef hashForWaypoint(naContext c, flightgear::Waypt* wpt, flightgear::Waypt* ne next->courseAndDistanceFrom(pos); hashset(c, h, "leg_distance", naNum(crsDist.second * SG_METER_TO_NM)); hashset(c, h, "leg_bearing", naNum(crsDist.first)); - hashset(c, h, "hdg_radial", naNum(crsDist.first)); + hashset(c, h, "hdg_radial", naNum(wpt->headingRadialDeg())); } // leg bearing, distance, etc @@ -742,6 +744,75 @@ static naRef f_route_numWaypoints(naContext c, naRef me, int argc, naRef* args) return naNum(rm->numWaypts()); } +static flightgear::Waypt* wayptFromMe(naRef me) +{ + naRef ghost = naHash_cget(me, (char*) "_waypt"); + if (naIsNil(ghost)) { + return NULL; + } + + return wayptGhost(ghost); +} + +static naRef f_waypoint_navaid(naContext c, naRef me, int argc, naRef* args) +{ + flightgear::Waypt* w = wayptFromMe(me); + if (!w) { + naRuntimeError(c, "waypoint.navaid called on non-waypoint object"); + } + + FGPositioned* pos = w->source(); + if (!pos) { + return naNil(); + } + + switch (pos->type()) { + case FGPositioned::VOR: + case FGPositioned::NDB: + case FGPositioned::ILS: + case FGPositioned::LOC: + case FGPositioned::GS: + case FGPositioned::DME: + case FGPositioned::TACAN: { + FGNavRecord* nav = (FGNavRecord*) pos; + return hashForNavRecord(c, nav, globals->get_aircraft_position()); + } + + default: + return naNil(); + } +} + +static naRef f_waypoint_airport(naContext c, naRef me, int argc, naRef* args) +{ + flightgear::Waypt* w = wayptFromMe(me); + if (!w) { + naRuntimeError(c, "waypoint.navaid called on non-waypoint object"); + } + + FGPositioned* pos = w->source(); + if (!pos || FGAirport::isAirportType(pos)) { + return naNil(); + } + + return hashForAirport(c, (FGAirport*) pos); +} + +static naRef f_waypoint_runway(naContext c, naRef me, int argc, naRef* args) +{ + flightgear::Waypt* w = wayptFromMe(me); + if (!w) { + naRuntimeError(c, "waypoint.navaid called on non-waypoint object"); + } + + FGPositioned* pos = w->source(); + if (!pos || (pos->type() != FGPositioned::RUNWAY)) { + return naNil(); + } + + return hashForRunway(c, (FGRunway*) pos); +} + // Table of extension functions. Terminate with zeros. static struct { const char* name; naCFunction func; } funcs[] = { { "carttogeod", f_carttogeod }, @@ -769,12 +840,19 @@ naRef initNasalPositioned(naRef globals, naContext c, naRef gcSave) routePrototype = naNewHash(c); hashset(c, gcSave, "routeProto", routePrototype); - + hashset(c, routePrototype, "getWP", naNewFunc(c, naNewCCode(c, f_route_getWP))); hashset(c, routePrototype, "currentWP", naNewFunc(c, naNewCCode(c, f_route_currentWP))); hashset(c, routePrototype, "currentIndex", naNewFunc(c, naNewCCode(c, f_route_currentIndex))); hashset(c, routePrototype, "getPlanSize", naNewFunc(c, naNewCCode(c, f_route_numWaypoints))); + waypointPrototype = naNewHash(c); + hashset(c, gcSave, "wayptProto", waypointPrototype); + + hashset(c, waypointPrototype, "navaid", naNewFunc(c, naNewCCode(c, f_waypoint_navaid))); + hashset(c, waypointPrototype, "runway", naNewFunc(c, naNewCCode(c, f_waypoint_runway))); + hashset(c, waypointPrototype, "airport", naNewFunc(c, naNewCCode(c, f_waypoint_airport))); + for(int i=0; funcs[i].name; i++) { hashset(c, globals, funcs[i].name, naNewFunc(c, naNewCCode(c, funcs[i].func))); -- 2.39.5