1
0
Fork 0

Move more high-level GPS logic to Nasal/XML.

This commit is contained in:
James Turner 2013-04-07 21:45:29 +01:00
parent 4d3a00bf68
commit b64dd768d3
3 changed files with 129 additions and 35 deletions

View file

@ -1,13 +1,13 @@
# route_manager.nas - default FlightPlan delegate corresponding to the build # route_manager.nas - FlightPlan delegate(s) corresponding to the built-
# in route-manager dialog. Intended to provide a sensible default behaviour, # in route-manager dialog and GPS. Intended to provide a sensible default behaviour,
# but be disabled by an aircraft-specific FMS / GPS system. # but can be disabled by an aircraft-specific FMS / GPS system.
var RouteManagerDelegate = { var RouteManagerDelegate = {
new: func(fp) { new: func(fp) {
# if this property is set, don't build a delegate at all # if this property is set, don't build a delegate at all
if (getprop('/autopilot/route-manager/disable-fms')) if (getprop('/autopilot/route-manager/disable-route-manager'))
return nil; return nil;
var m = { parents: [RouteManagerDelegate] }; var m = { parents: [RouteManagerDelegate] };
m.flightplan = fp; m.flightplan = fp;
return m; return m;
@ -86,19 +86,66 @@ var RouteManagerDelegate = {
{ {
debug.dump("end of flight-plan, deactivating"); debug.dump("end of flight-plan, deactivating");
fgcommand("activate-flightplan", props.Node.new({"activate": 0})); fgcommand("activate-flightplan", props.Node.new({"activate": 0}));
}, }
};
var FMSDelegate = {
new: func(fp) {
# if this property is set, don't build a delegate at all
if (getprop('/autopilot/route-manager/disable-fms'))
return nil;
var m = { parents: [FMSDelegate], flightplan:fp, landingCheck:nil };
return m;
},
_landingCheckTimeout: func
{
var cur = me.flightplan.currentWP();
var wow = getprop('gear/gear[0]/wow');
var gs = getprop('velocities/groundspeed-kt');
if (wow and (gs < 25)) {
debug.dump('touchdown on destination runway, end of route.');
me.landingCheck.stop();
# record touch-down time?
me.flightplan.finish();
}
},
waypointsChanged: func waypointsChanged: func
{ {
}, },
endOfFlightPlan: func
{
debug.dump('end of flight-plan');
},
currentWaypointChanged: func currentWaypointChanged: func
{ {
debug.dump('saw current WP changed, now ' ~ me.flightplan.current); if (me.landingCheck != nil) {
me.landingCheck.stop();
me.landingCheck = nil; # delete timer
}
#debug.dump('saw current WP changed, now ' ~ me.flightplan.current);
var active = me.flightplan.currentWP();
if (active == nil) return;
if (active.alt_cstr_type != 'none') {
debug.dump('new WP has valid altitude restriction, setting on AP');
setprop('/autopilot/settings/target-altitude-ft', active.alt_cstr);
}
var activeRunway = active.runway();
if ((activeRunway != nil) and (activeRunway.id == me.flightplan.destination_runway.id)) {
me.landingCheck = maketimer(2.0, me, FMSDelegate._landingCheckTimeout);
me.landingCheck.start();
}
} }
}; };
# debug.dump('register routemanager delegate factory'); registerFlightPlanDelegate(FMSDelegate.new);
registerFlightPlanDelegate(RouteManagerDelegate.new); registerFlightPlanDelegate(RouteManagerDelegate.new);

View file

@ -11,14 +11,17 @@
var cmd = gps.getNode("command", 1); var cmd = gps.getNode("command", 1);
var scratch = gps.getNode("scratch", 1); var scratch = gps.getNode("scratch", 1);
var scratchValid = scratch.getNode("valid", 1); var scratchValid = scratch.getNode("valid", 1);
var searchIsWaypoints = 0;
var updateSearchResults = func var anySpec = 'vor,airport,heliport,ils,seaport,fix,ndb,waypoint,tacan,city,town';
{
debug.dump('search results is:', searchResults);
dlg.getNode("scratch-index", 1).setValue(0); var updateSearchResults = func(isWpts, index = 0)
dlg.getNode("scratch-has-next", 1).setBoolValue(size(searchResults) > 1); {
searchIsWaypoints = isWpts;
dlg.getNode("scratch-index", 1).setValue(index);
var lastIndex = size(searchResults) - 1;
dlg.getNode("scratch-has-next", 1).setValue((index + 1) < lastIndex);
if (size(searchResults) < 1) { if (size(searchResults) < 1) {
scratchValid.setBoolValue(0); scratchValid.setBoolValue(0);
return; return;
@ -34,23 +37,33 @@
scratchValid.setBoolValue(0); scratchValid.setBoolValue(0);
return; return;
} }
var ty = result.type;
scratchValid.setBoolValue(1); scratchValid.setBoolValue(1);
scratch.getNode("type", 1).setValue(ty);
scratch.getNode("latitude-deg", 1).setValue(result.lat); scratch.getNode("latitude-deg", 1).setValue(result.lat);
scratch.getNode("longitude-deg", 1).setValue(result.lon); scratch.getNode("longitude-deg", 1).setValue(result.lon);
scratch.getNode("altitude-ft", 1).setValue(result.elevation);
scratch.getNode("ident", 1).setValue(result.id); scratch.getNode("ident", 1).setValue(result.id);
scratch.getNode("name", 1).setValue(result.name); var cd = nil;
if (ty == 'vor') { if (searchIsWaypoints) {
scratch.getNode("frequency-mhz", 1).setValue(result.frequency); scratch.getNode("type", 1).setValue('WPT');
} elsif (ty == 'ndb') {
scratch.getNode("frequency-khz", 1).setValue(result.frequency); cd = result.courseAndDistanceFrom(geo.aircraft_position());
} else {
var ty = result.type;
scratch.getNode("type", 1).setValue(ty);
scratch.getNode("name", 1).setValue(result.name);
scratch.getNode("altitude-ft", 1).setValue(result.elevation);
if (ty == 'vor') {
scratch.getNode("frequency-mhz", 1).setValue(result.frequency);
} elsif (ty == 'ndb') {
scratch.getNode("frequency-khz", 1).setValue(result.frequency);
}
cd = positioned.courseAndDistance(result);
} }
var cd = positioned.courseAndDistance(result);
scratch.getNode("mag-bearing-deg", 1).setValue(cd[0] + magvar()); scratch.getNode("mag-bearing-deg", 1).setValue(cd[0] + magvar());
scratch.getNode("distance-nm", 1).setValue(cd[1]); scratch.getNode("distance-nm", 1).setValue(cd[1]);
@ -60,24 +73,27 @@
var doSearch = func() var doSearch = func()
{ {
var ty = dlg.getNode("search-type").getValue(); var ty = dlg.getNode("search-type").getValue();
if (ty == 'any') ty = anySpec;
var query = dlg.getNode("search-query").getValue(); var query = dlg.getNode("search-query").getValue();
searchResults = positioned.sortByRange(positioned.findByIdent(query, ty)); searchResults = positioned.sortByRange(positioned.findByIdent(query, ty));
updateSearchResults(); updateSearchResults(0);
} }
var doSearchNames = func var doSearchNames = func
{ {
var ty = dlg.getNode("search-type").getValue(); var ty = dlg.getNode("search-type").getValue();
if (ty == 'any') ty = anySpec;
var query = dlg.getNode("search-query").getValue(); var query = dlg.getNode("search-query").getValue();
searchResults = positioned.sortByRange(positioned.findByName(query, ty)); searchResults = positioned.sortByRange(positioned.findByName(query, ty));
updateSearchResults(); updateSearchResults(0);
} }
var doSearchNearest = func var doSearchNearest = func
{ {
var ty = dlg.getNode("search-type").getValue(); var ty = dlg.getNode("search-type").getValue();
searchResults = positioned.findWithinRange(200.0, ty); searchResults = positioned.findWithinRange(200.0, ty);
updateSearchResults(); updateSearchResults(0);
} }
var doLoadRouteWaypoint = func var doLoadRouteWaypoint = func
@ -87,7 +103,7 @@
for (var i=0; i < fp.getPlanSize(); i+=1) { for (var i=0; i < fp.getPlanSize(); i+=1) {
append(searchResults, fp.getWP(i)); append(searchResults, fp.getWP(i));
} }
updateSearchResults(); updateSearchResults(1, fp.current);
} }
var doScratchPrevious = func var doScratchPrevious = func
@ -111,7 +127,7 @@
} }
var searchResults = []; var searchResults = [];
updateSearchResults(); updateSearchResults(0);
var slaved = props.globals.getNode("/instrumentation/nav[0]/slaved-to-gps", 1); var slaved = props.globals.getNode("/instrumentation/nav[0]/slaved-to-gps", 1);
]]></open> ]]></open>
@ -399,6 +415,8 @@
<value>ndb</value> <value>ndb</value>
<value>fix</value> <value>fix</value>
<value>wpt</value> <value>wpt</value>
<value>city</value>
<value>town</value>
<live>true</live> <live>true</live>
<binding> <binding>
<command>dialog-apply</command> <command>dialog-apply</command>

View file

@ -224,9 +224,38 @@ command interface /autopilot/route-manager/input:
gui.dialog_update("route-manager", "approach"); gui.dialog_update("route-manager", "approach");
} }
var initPosition = func {
var routeActive = routem.getNode("active").getValue();
if (routeActive) return;
# FIXME have user waypoints check
var fp = flightplan();
var airborne = getprop('/gear/gear[0]/wow') == 0;
if (airborne) {
debug.dump('route-manager dialog, init in-air, clearing departure settings');
fp.departure = nil;
return;
}
# we're on the ground, find the nearest airport to start from
if (fp.departure == nil) {
var apts = findAirportsWithinRange(25.0);
if (size(apts) == 0) return; # no airports nearby
fp.departure = apts[0]; # use the closest one
}
if (fp.departure_runway == nil) {
debug.dump('selecting departure runway');
var rwy = fp.departure.findBestRunwayForPos( geo.aircraft_position() );
fp.departure_runway = rwy;
}
}
# initialise departure values based on current position # initialise departure values based on current position
cmd.setValue("@posinit"); initPosition();
updateRunways(); updateRunways();
updateSIDs(); updateSIDs();