|
From: <fli...@li...> - 2017-10-23 19:53:43
|
Revision: 3059
http://sourceforge.net/p/flightgear/fgaddon/3059
Author: wlbragg
Date: 2017-10-23 19:53:40 +0000 (Mon, 23 Oct 2017)
Log Message:
-----------
AirCrane: Correct error in calculating liquid flow into and out of external tank
Modified Paths:
--------------
trunk/Aircraft/AirCrane/Nasal/aircrane.nas
trunk/Aircraft/AirCrane/Nasal/tankoperations.nas
trunk/Aircraft/AirCrane/Systems/aircrane-base.xml
Added Paths:
-----------
trunk/Aircraft/AirCrane/Nasal/hoseanimation.nas
Modified: trunk/Aircraft/AirCrane/Nasal/aircrane.nas
===================================================================
--- trunk/Aircraft/AirCrane/Nasal/aircrane.nas 2017-10-19 19:52:10 UTC (rev 3058)
+++ trunk/Aircraft/AirCrane/Nasal/aircrane.nas 2017-10-23 19:53:40 UTC (rev 3059)
@@ -380,7 +380,7 @@
update_rotor_cone_angle();
rotor_wash_loop();
- tank_operations();
+ flexhose_animation();
settimer(main_loop, 0);
}
@@ -446,6 +446,21 @@
#wildfire.resolve_retardant_drop(pos, 10, 0);
});
+ var tankop_timer = maketimer(0.25, func{tank_operations()});
+
+ if (getprop("/sim/model/firetank/enabled"))
+ tankop_timer.start();
+ else
+ setlistener("/sim/model/firetank/enabled", func {
+ if (getprop("/sim/model/firetank/enabled"))
+ tankop_timer.start();
+ else {
+ tankop_timer.stop();
+ setprop("sim/model/firetank/opencannonvalve", 0);
+ setprop("sim/model/firetank/opentankdoors", 0);
+ }
+ });
+
# the attitude indicator needs pressure
# settimer(func { setprop("engines/engine/rpm", 3000) }, 8);
Added: trunk/Aircraft/AirCrane/Nasal/hoseanimation.nas
===================================================================
--- trunk/Aircraft/AirCrane/Nasal/hoseanimation.nas (rev 0)
+++ trunk/Aircraft/AirCrane/Nasal/hoseanimation.nas 2017-10-23 19:53:40 UTC (rev 3059)
@@ -0,0 +1,207 @@
+#################### flexhose ####################
+
+var flex_angle_v_array = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
+var flex_angle_vr_array = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
+var flex_angle_r_array = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
+var onground_flag = 0;
+var drop_flag = 0;
+
+var flexhose_animation = func {
+
+ var sniffer = getprop("sim/model/firetank/deployflexhose/position-norm");
+ var altitude = getprop("position/altitude-agl-ft");
+ var overland = getprop("gear/gear/ground-is-solid");
+ var alt_agl = altitude * 0.3048 + getprop("/sim/model/firetank/flexhose/offset");
+ var n_segments = 31;
+ var segment_length = getprop("/sim/model/firetank/flexhose/factor");
+
+ if (overland)
+ {
+ if (alt_agl - n_segments * segment_length < 0.0)
+ {
+ onground_flag = 1;
+ }
+ else
+ onground_flag = 0;
+ }
+ else
+ {
+ onground_flag = 0;
+ }
+
+ setprop("/sim/model/firetank/flexhose/hosehitsground", onground_flag);
+
+ if (sniffer == 1)
+ {
+ drop_flag = 50;
+ return;
+ }
+ else
+ if (drop_flag > 1 and !onground_flag)
+ drop_flag -= 1;
+ else
+ {
+ #setprop("sim/model/firetank/deployflexhose/position-norm", 0);
+ #sniffer = 0;
+ drop_flag = 0;
+ }
+
+ var flex_force = getprop("/sim/model/firetank/flexhose/flex-force");
+ var damping = getprop("/sim/model/firetank/flexhose/damping");
+ var stiffness = getprop("/sim/model/firetank/flexhose/stiffness");
+ var sum_angle = 0.0;
+ var dt = getprop("/sim/time/delta-sec");
+ var bend_force = getprop("/sim/model/firetank/flexhose/bendforce");
+ var angle_correction = getprop("/sim/model/firetank/flexhose/correction");
+
+ if (onground_flag == 0)
+ {
+ if (drop_flag and overland)
+ {
+ var ax = drop_flag;
+ var ay = 0;
+ var az = -60;
+ }
+ else
+ {
+ var ax = getprop("/accelerations/pilot/x-accel-fps_sec");
+ var ay = getprop("/accelerations/pilot/y-accel-fps_sec");
+ var az = getprop("/accelerations/pilot/z-accel-fps_sec");
+ }
+ }
+ else
+ {
+ var ax = 0;
+ var ay = 0;
+ var az = 0;
+ }
+
+ var a = math.sqrt(ax* ax + ay*ay + az*az);
+
+ if (a==0.0) {a=1.0;}
+
+ var ref_ang1 = math.asin(ax/a) * 180.0/math.pi;
+ var ref_ang2 = math.asin(ay/a) * 180.0/math.pi;
+
+ var damping_factor = math.pow(damping, dt);
+
+ if (onground_flag == 0)
+ {
+
+ var current_angle = getprop("/sim/model/firetank/flexhose/pitch1");
+ var ang_error = ref_ang1 - current_angle;
+
+ flex_angle_v_array[0] += ang_error * stiffness * dt;
+ flex_angle_v_array[0] *= damping_factor;
+
+ var ang_speed = flex_angle_v_array[0];
+
+ setprop("/sim/model/firetank/flexhose/pitch1", current_angle + dt * ang_speed);
+
+ var current_roll = getprop("/sim/model/firetank/flexhose/roll1");
+ ang_error = ref_ang2 - current_roll;
+
+
+ flex_angle_vr_array[0] += ang_error * stiffness * dt;
+ flex_angle_vr_array[0] *= damping_factor;
+
+ ang_speed = flex_angle_vr_array[0];
+
+ var next_roll = current_roll + dt * ang_speed;
+ setprop("/sim/model/firetank/flexhose/roll1", next_roll);
+
+ # kink excitation
+
+ var kink = -(next_roll - flex_angle_r_array[0]);
+
+ setprop("/sim/model/firetank/flexhose/roll2", kink) ;
+ flex_angle_r_array[1] = kink;
+
+ }
+ else
+ {
+
+ setprop("/sim/model/firetank/flexhose/pitch1", ref_ang1);
+ setprop("/sim/model/firetank/flexhose/roll1", ref_ang2);
+
+ }
+
+ var roll_target = 0.0;
+
+ for (var i = 1; i< n_segments; i=i+1)
+ {
+
+ var gravity = n_segments - i;
+
+ var velocity = getprop("/velocities/equivalent-kt") - (drop_flag*2);
+
+ if (velocity == nil) {velocity = 0;}
+ if (velocity > 500.0) {velocity = 500.0;}
+
+ var dist_above_ground = alt_agl - (i+1) * segment_length;
+
+ var force = flex_force * math.cos(sum_angle * math.pi/180.0) * 0.05 * velocity;
+
+ if (overland)
+ {
+ if (dist_above_ground < 0.0)
+ {
+ force = force + bend_force * math.cos(sum_angle * math.pi/180.0);
+ }
+ }
+
+ if (force > 1.0 * gravity) {force = 1.0 * gravity;}
+
+ var angle = - 180.0 /math.pi * math.atan2(force, gravity);#(force/gravity);
+ sum_angle += angle;
+
+ if (onground_flag == 0)
+ {
+ current_angle = getprop("/sim/model/firetank/flexhose/pitch"~(i+1));
+ ang_error = angle - current_angle;
+
+
+ flex_angle_v_array[i] += ang_error * stiffness * dt;
+ flex_angle_v_array[i] *= damping_factor;
+
+ ang_speed = flex_angle_v_array[i];
+
+ setprop("/sim/model/firetank/flexhose/pitch"~(i+1), current_angle + dt * ang_speed);
+
+ # the transverse dynamics is largely waves excited by the helicopter
+
+ if (i==1) # this is set by the kink excitation
+ {
+ continue;
+ }
+ else
+ {
+ roll_target = flex_angle_r_array[i-1];
+ }
+
+ ang_error = roll_target - flex_angle_r_array[i];
+
+ flex_angle_vr_array[i] += ang_error * stiffness * dt;
+ flex_angle_vr_array[i] *= damping_factor;
+
+ ang_speed = flex_angle_vr_array[i];
+
+ setprop("/sim/model/firetank/flexhose/roll"~(i+1), roll_target);
+
+ }
+ else
+ {
+ setprop("/sim/model/firetank/flexhose/pitch"~(i+1), angle + angle_correction);
+ setprop("/sim/model/firetank/flexhose/roll"~(i+1), 0.0);
+ }
+
+ }
+
+ # copy the current values into the last step array
+
+ for (var i = 0; i< n_segments; i=i+1)
+ {
+ flex_angle_r_array[i] = getprop("/sim/model/firetank/flexhose/roll"~(i+1));
+ }
+
+}
\ No newline at end of file
Modified: trunk/Aircraft/AirCrane/Nasal/tankoperations.nas
===================================================================
--- trunk/Aircraft/AirCrane/Nasal/tankoperations.nas 2017-10-19 19:52:10 UTC (rev 3058)
+++ trunk/Aircraft/AirCrane/Nasal/tankoperations.nas 2017-10-23 19:53:40 UTC (rev 3059)
@@ -1,20 +1,15 @@
+#################### watertank ####################
+
# 1 Gallon = 8.345404 lbs * 2500 = 20863 lbs
var capacity = 0.0;
-var flex_angle_v_array = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
-var flex_angle_vr_array = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
-var flex_angle_r_array = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0];
-var onground_flag = 0;
-var drop_flag = 0;
var tank_operations = func {
-
- var payload = getprop("sim/model/firetank/enabled");
var paused = getprop("sim/freeze/clock");
var crashed = getprop("sim/crashed");
- if (!payload or crashed or paused) {
+ if (crashed or paused) {
setprop("sim/model/firetank/waterdropparticlectrl", 0);
setprop("sim/model/firetank/waterdropretardantctrl", 0);
setprop("sim/model/firetank/watercannonparticlectrl", 0);
@@ -30,7 +25,7 @@
var sniffer = getprop("sim/model/firetank/deployflexhose/position-norm");
var overland = getprop("gear/gear/ground-is-solid");
var altitude = getprop("position/altitude-agl-ft");
- var airspeed = getprop("velocities/airspeed-kt");
+ var groundspeed = getprop("velocities/groundspeed-kt");
var particles = getprop("sim/model/aircrane/effects/particles/enabled");
var normalized = 1-(altitude-0)/(60-0);
@@ -60,7 +55,7 @@
setprop("sim/model/firetank/watercannonretardantctrl", 0);
}
- if (cannonvalveopen and hopperweight and cannon) {
+ if (cannonvalveopen and hopperweight and cannon) {
#300 * 8.345 weight per gal = 2503.5 weight per minute / 60 = 41.72 per second / 4 (.25 seconds timer cycle) = 10.43 capacity per cycle
#300 gal per minute / 60 = 5 per second / 4 (.25 seconds timer cycle) = 1.25 per cycle * 8.345 weight per gallon = 10.43 capacity per cycle
capacity = 10.43;
@@ -75,9 +70,9 @@
if (hopperweight > 0)
hopperweight = hopperweight - capacity;
setprop("sim/weight[3]/weight-lb", hopperweight);
- }
+ }
- if (!overland and scoopdown == 1 and altitude < 26.5 and airspeed > 25) {
+ if (!overland and scoopdown == 1 and altitude < 26.5 and groundspeed > 25) {
#2500 gal * 8.345 weight per gal = 20862.5 / 40 second fill = 521.56 per sec / 4 (.25 seconds timer cycle) = 130.39 capacity per cycle
#2500 gal / 40 sec = 62.5 per sec / 4 (.25 seconds timer cycle) = 15.62 * 8.345 weight per gallon = 130.35 capacity per cycle
capacity = 130.37;
@@ -85,7 +80,7 @@
hopperweight = hopperweight + capacity;
setprop("sim/weight[3]/weight-lb", hopperweight);
}
- if (!overland and !sniffer and altitude < 27.5 and airspeed < 35) {
+ if (!overland and !sniffer and altitude < 27.5 and groundspeed < 35) {
#2500 gal * 8.345 weight per gal = 20862.5 / 45 second fill = 463.61 per sec / 4 (.25 seconds timer cycle) = 115.90 capacity per cycle
#2500 gal / 45 sec = 55.55 per second / 4 (.25 seconds timer cycle) = 13.89 * 8.345 weight per gallon = 115.91 capacity per cycle
capacity = 115.91;
@@ -98,200 +93,4 @@
hopperweight = 0;
setprop("sim/weight[3]/weight-lb", hopperweight);
}
-
- #################### flexhose ####################
-
- var alt_agl = altitude * 0.3048 + getprop("/sim/model/firetank/flexhose/offset");
- var n_segments = 31;
- var segment_length = getprop("/sim/model/firetank/flexhose/factor");
-
- if (overland)
- {
- if (alt_agl - n_segments * segment_length < 0.0)
- {
- onground_flag = 1;
- }
- else
- onground_flag = 0;
- }
- else
- {
- onground_flag = 0;
- }
-
- setprop("/sim/model/firetank/flexhose/hosehitsground", onground_flag);
-
- if (sniffer == 1)
- {
- drop_flag = 50;
- return;
- }
- else
- if (drop_flag > 1 and !onground_flag)
- drop_flag -= 1;
- else
- {
- #setprop("sim/model/firetank/deployflexhose/position-norm", 0);
- #sniffer = 0;
- drop_flag = 0;
- }
-
- var flex_force = getprop("/sim/model/firetank/flexhose/flex-force");
- var damping = getprop("/sim/model/firetank/flexhose/damping");
- var stiffness = getprop("/sim/model/firetank/flexhose/stiffness");
- var sum_angle = 0.0;
- var dt = getprop("/sim/time/delta-sec");
- var bend_force = getprop("/sim/model/firetank/flexhose/bendforce");
- var angle_correction = getprop("/sim/model/firetank/flexhose/correction");
-
- if (onground_flag == 0)
- {
- if (drop_flag and overland)
- {
- var ax = drop_flag;
- var ay = 0;
- var az = -60;
- }
- else
- {
- var ax = getprop("/accelerations/pilot/x-accel-fps_sec");
- var ay = getprop("/accelerations/pilot/y-accel-fps_sec");
- var az = getprop("/accelerations/pilot/z-accel-fps_sec");
- }
- }
- else
- {
- var ax = 0;
- var ay = 0;
- var az = 0;
- }
-
- var a = math.sqrt(ax* ax + ay*ay + az*az);
-
- if (a==0.0) {a=1.0;}
-
- var ref_ang1 = math.asin(ax/a) * 180.0/math.pi;
- var ref_ang2 = math.asin(ay/a) * 180.0/math.pi;
-
- var damping_factor = math.pow(damping, dt);
-
- if (onground_flag == 0)
- {
-
- var current_angle = getprop("/sim/model/firetank/flexhose/pitch1");
- var ang_error = ref_ang1 - current_angle;
-
- flex_angle_v_array[0] += ang_error * stiffness * dt;
- flex_angle_v_array[0] *= damping_factor;
-
- var ang_speed = flex_angle_v_array[0];
-
- setprop("/sim/model/firetank/flexhose/pitch1", current_angle + dt * ang_speed);
-
- var current_roll = getprop("/sim/model/firetank/flexhose/roll1");
- ang_error = ref_ang2 - current_roll;
-
-
- flex_angle_vr_array[0] += ang_error * stiffness * dt;
- flex_angle_vr_array[0] *= damping_factor;
-
- ang_speed = flex_angle_vr_array[0];
-
- var next_roll = current_roll + dt * ang_speed;
- setprop("/sim/model/firetank/flexhose/roll1", next_roll);
-
- # kink excitation
-
- var kink = -(next_roll - flex_angle_r_array[0]);
-
- setprop("/sim/model/firetank/flexhose/roll2", kink) ;
- flex_angle_r_array[1] = kink;
-
- }
- else
- {
-
- setprop("/sim/model/firetank/flexhose/pitch1", ref_ang1);
- setprop("/sim/model/firetank/flexhose/roll1", ref_ang2);
-
- }
-
- var roll_target = 0.0;
-
- for (var i = 1; i< n_segments; i=i+1)
- {
-
- var gravity = n_segments - i;
-
- var velocity = getprop("/velocities/equivalent-kt") - (drop_flag*2);
-
- if (velocity == nil) {velocity = 0;}
- if (velocity > 500.0) {velocity = 500.0;}
-
- var dist_above_ground = alt_agl - (i+1) * segment_length;
-
- var force = flex_force * math.cos(sum_angle * math.pi/180.0) * 0.05 * velocity;
-
- if (overland)
- {
- if (dist_above_ground < 0.0)
- {
- force = force + bend_force * math.cos(sum_angle * math.pi/180.0);
- }
- }
-
- if (force > 1.0 * gravity) {force = 1.0 * gravity;}
-
- var angle = - 180.0 /math.pi * math.atan2(force, gravity);#(force/gravity);
- sum_angle += angle;
-
- if (onground_flag == 0)
- {
- current_angle = getprop("/sim/model/firetank/flexhose/pitch"~(i+1));
- ang_error = angle - current_angle;
-
-
- flex_angle_v_array[i] += ang_error * stiffness * dt;
- flex_angle_v_array[i] *= damping_factor;
-
- ang_speed = flex_angle_v_array[i];
-
- setprop("/sim/model/firetank/flexhose/pitch"~(i+1), current_angle + dt * ang_speed);
-
- # the transverse dynamics is largely waves excited by the helicopter
-
- if (i==1) # this is set by the kink excitation
- {
- continue;
- }
- else
- {
- roll_target = flex_angle_r_array[i-1];
- }
-
- ang_error = roll_target - flex_angle_r_array[i];
-
- flex_angle_vr_array[i] += ang_error * stiffness * dt;
- flex_angle_vr_array[i] *= damping_factor;
-
- ang_speed = flex_angle_vr_array[i];
-
- setprop("/sim/model/firetank/flexhose/roll"~(i+1), roll_target);
-
- }
- else
- {
- setprop("/sim/model/firetank/flexhose/pitch"~(i+1), angle + angle_correction);
- setprop("/sim/model/firetank/flexhose/roll"~(i+1), 0.0);
- }
-
- }
-
- # copy the current values into the last step array
-
- for (var i = 0; i< n_segments; i=i+1)
- {
- flex_angle_r_array[i] = getprop("/sim/model/firetank/flexhose/roll"~(i+1));
- }
-
}
\ No newline at end of file
Modified: trunk/Aircraft/AirCrane/Systems/aircrane-base.xml
===================================================================
--- trunk/Aircraft/AirCrane/Systems/aircrane-base.xml 2017-10-19 19:52:10 UTC (rev 3058)
+++ trunk/Aircraft/AirCrane/Systems/aircrane-base.xml 2017-10-23 19:53:40 UTC (rev 3059)
@@ -207,6 +207,7 @@
<file>Aircraft/AirCrane/Nasal/liveries.nas</file>
<file>Aircraft/AirCrane/Nasal/bladevisible.nas</file>
<file>Aircraft/AirCrane/Nasal/rotorwash.nas</file>
+ <file>Aircraft/AirCrane/Nasal/hoseanimation.nas</file>
<file>Aircraft/AirCrane/Nasal/tankoperations.nas</file>
</aircrane>
<fcs>
|