From 1142bde5e9cc13d320e137c2fcd2a6dca12346d8 Mon Sep 17 00:00:00 2001 From: "Curtis L. Olson" Date: Thu, 28 May 2015 10:29:38 -0500 Subject: [PATCH] Tomaskom writes: I was playing with the target tracking and decided to fix an old bug that causes it to behave wrong at higher altitudes. Background: the script continuously updates values in the autopilot to follow specified target aircraft (AI/MP). It is controlled directly through the property tree under /autopilot/target-tracking. Issue: the script reads out true airspeed, but autopilot expects indicated airspeed. This is why at higher altitudes, the tracking always overshoots. I fixed this by introducing an estimate on indicated airspeed of the target, using the ratio between local aircraft true and indicated airspeed. I also fixed an issue where it ignored minimum speed setting and polished initialization by using props.globals.initNode() instead of dedicated presence check for every property (and also ensured the nodes have correct types, no more bool stored as double). And the last thing I changed was to increase the default tracking distance to a more sane value, with the original value of 0.05nm the tracking was unstable in heading with most aircraft and started oscillating. With the changes I applied, the distance is now holding precisely at any altitude and with any winds. --- Nasal/track_target.nas | 53 +++++++++++++++--------------------------- 1 file changed, 19 insertions(+), 34 deletions(-) diff --git a/Nasal/track_target.nas b/Nasal/track_target.nas index bff46a4bf..efb81d18f 100644 --- a/Nasal/track_target.nas +++ b/Nasal/track_target.nas @@ -56,7 +56,7 @@ # script defaults (configurable if you like) var default_update_period = 0.05; -var default_goal_range_nm = 0.05; +var default_goal_range_nm = 0.15; var default_target_root = "/ai/models/aircraft[0]"; var default_min_speed_kt = 120; @@ -83,35 +83,11 @@ var TrackInit = func { if (props.globals.getNode("autopilot") == nil) return; - target_tracking_enable = getprop("/autopilot/target-tracking/enable"); - if ( target_tracking_enable == nil ) { - target_tracking_enable = 0; - setprop("/autopilot/target-tracking/enable", target_tracking_enable); - } - - update_period = getprop("/autopilot/target-tracking/update-period"); - if ( update_period == nil ) { - update_period = default_update_period; - setprop("/autopilot/target-tracking/update-period", update_period); - } - - goal_range_nm = getprop("/autopilot/target-tracking/goal-range-nm"); - if ( goal_range_nm == nil ) { - goal_range_nm = default_goal_range_nm; - setprop("/autopilot/target-tracking/goal-range-nm", goal_range_nm); - } - - min_speed_kt = getprop("/autopilot/target-tracking/min-speed-kt"); - if ( min_speed_kt == nil ) { - min_speed_kt = default_min_speed_kt; - setprop("/autopilot/target-tracking/min-speed-kt", min_speed_kt); - } - - target_root = getprop("/autopilot/target-tracking/target-root"); - if ( target_root == nil ) { - target_root = default_target_root; - setprop("/autopilot/target-tracking/target-root", target_root); - } + props.globals.initNode("/autopilot/target-tracking/enable", 0, "BOOL"); + props.globals.initNode("/autopilot/target-tracking/update-period", default_update_period, "DOUBLE"); + props.globals.initNode("/autopilot/target-tracking/goal-range-nm", default_goal_range_nm, "DOUBLE"); + props.globals.initNode("/autopilot/target-tracking/min-speed-kt", default_min_speed_kt, "DOUBLE"); + props.globals.initNode("/autopilot/target-tracking/target-root", default_target_root, "STRING"); setlistener("/autopilot/target-tracking/enable", func { startTimer();} ); } @@ -134,6 +110,7 @@ var TrackUpdate = func(loop_id) { # refresh user configurable values goal_range_nm = getprop("/autopilot/target-tracking/goal-range-nm"); target_root = getprop("/autopilot/target-tracking/target-root"); + min_speed_kt = getprop("/autopilot/target-tracking/min-speed-kt"); # force radar debug-mode on (forced radar calculations even if # no radar instrument and ai aircraft are out of range @@ -153,11 +130,19 @@ var TrackUpdate = func(loop_id) { } var speed_prop = sprintf("%s/velocities/true-airspeed-kt", target_root ); - var speed = getprop(speed_prop); - if ( speed == nil ) { + #correct by local IAS/TAS ratio, because autopilot uses IAS + #I need to calculate my TAS, not taking wind into account (MP velocities/true-airspeed-kt does not as well) + var northSpeed = getprop("/velocities/speed-north-fps"); + var eastSpeed = getprop("/velocities/speed-east-fps"); + var downSpeed = getprop("/velocities/speed-down-fps"); + var true_airspeed = FPS2KT * math.sqrt(northSpeed*northSpeed + eastSpeed*eastSpeed + downSpeed*downSpeed); + #take target TAS and multiply it by my own IAS/TAS ratio to get target IAS + var speedTAS = getprop(speed_prop); + if ( speedTAS == nil ) { print("bad property path: ", speed_prop); return; } + var speed = speedTAS * (getprop("/velocities/airspeed-kt") / true_airspeed); var range_prop = sprintf("%s/radar/range-nm", target_root ); var range = getprop(range_prop); @@ -181,7 +166,7 @@ var TrackUpdate = func(loop_id) { var range_error = goal_range_nm - range; } var target_speed = speed + range_error * 100.0; - if ( target_speed < min_speed_kt ) { + if ( !debug.isnan(target_speed) and target_speed < min_speed_kt ) { target_speed = min_speed_kt; } @@ -189,7 +174,7 @@ var TrackUpdate = func(loop_id) { setprop( "/autopilot/settings/heading-bug-deg", my_hdg + h_offset ); setprop( "/autopilot/settings/true-heading-deg", my_hdg_true + h_offset ); - setprop( "/autopilot/settings/target-speed-kt", target_speed ); + if( !debug.isnan(target_speed) ) setprop( "/autopilot/settings/target-speed-kt", target_speed ); #isnan check because I divide by TAS before # only keep the timer running when the feature is really enabled settimer(func() { TrackUpdate(loop_id); }, update_period );