-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Still not completely happy with it, but don't want to hold it off
any longer. Wind layer configuration is at the top. You can add
as many as you want, but remember to add them in order from low
to high.
Usage: nc -vve wind <host> <port>
===[ wind ]==================================================================
#!/bin/sh
exec awk -W interactive '
function initwinds(wN, wE, wU)
{
toplayer = 0
# wind layer configuration
setwind( 0, "foot", 23, "knot", 260, "degree", 0, "foot/minute")
setwind( 1000, "foot", 40, "knot", 270, "degree", 0, "foot/minute")
setwind( 2000, "foot", 110, "knot", 280, "degree", 0, "foot/minute")
setwind( 4000, "foot", 110, "knot", 350, "degree", 0, "foot/minute")
setwind(10000, "foot", 40, "knot", 050, "degree", 0, "foot/minute")
if (toplayer <= 0) {
WIND[0, "altitude"] = 0
WIND[0, "up"] = wU
WIND[0, "north"] = wN
WIND[0, "east"] = wE
toplayer = 1
}
toplayer--
}
function abs(n)
{
if (n < 0) return -n
return n
}
function sgn(n)
{
if (n < 0) return -1
if (n > 0) return 1
return 0
}
function msg(m)
{
print m > "/dev/stderr"
}
function fail(m)
{
msg(m)
exitcode = 1
exit exitcode
}
function datamode()
{
msg("entering data mode")
print "data"
msg("data mode entered")
}
function getproperty(p , ret)
{
msg("req: " p)
print "get " p
status = getline ret
msg("result: " ret)
return ret
}
function setproperty(p, v , dummy)
{
msg("set: " p " = " v)
print "set " p " " v
status = getline dummy
}
function parse_unit2(u, TOP, BOT , a, b, s, tobot)
{
tobot = 0
while (u != "") {
a = index(u, "/")
b = index(u, ".")
if (a && (b <= 0 || a < b)) {
s = substr(u, 1, a - 1)
while(s in UNITRANS) s = UNITRANS[s]
if (tobot) BOT[s]++
else TOP[s]++
u = substr(u, a + 1)
tobot = 1
}
else if (b && (a <= 0 || b < a)) {
s = substr(u, 1, b - 1)
while(s in UNITRANS) s = UNITRANS[s]
if (tobot) BOT[s]++
else TOP[s]++
u = substr(u, b + 1)
}
else {
while(u in UNITRANS) u = UNITRANS[u]
if (tobot) BOT[u]++
else TOP[u]++
u = ""
}
}
}
function parse_unit(u, TOP, BOT)
{
delete TOP
delete BOT
TOP[""] = 0
BOT[""] = 0
parse_unit2(u, TOP, BOT)
mod = 1
while(mod) {
mod = 0
for (s in TOP) if (TOP[s] > 0 && match(s, "[\./]")) {
mod = 1
parse_unit2(s, TOP, BOT)
TOP[s]--
}
for (s in BOT) if (BOT[s] > 0 && match(s, "[\./]")) {
mod = 1
parse_unit2(s, BOT, TOP)
BOT[s]--
}
}
for (s in TOP) {
while (s in BOT && TOP[s] > 0 && BOT[s] > 0) {
TOP[s]--
BOT[s]--
}
}
}
function unitconvert3(v, from, to)
{
if (from == to) return v
else if ( (from, to) in UNICONV)
return (v + UNICONV[from, to, "offset"]) * UNICONV[from, to]
else if ( (to, from) in UNICONV)
return v / UNICONV[to, from] + UNICONV[to, from, "offset"]
return "err"
}
function unitconvert4(v, d, FROM, TO)
{
for (s in FROM) if (FROM[s] > 0) {
w = ""
for (t in TO) if (TO[t] > 0) {
if (d) w = unitconvert3(v, t, s)
else w = unitconvert3(v, s, t)
if (w != "err") {
FROM[s]--
TO[t]--
v = w
break
}
}
if (w == "err") {
msg("Unable to convert:")
for (s in FROM) msg(s ": " FROM[s])
msg("to")
for (s in TO) msg(s ": " TO[s])
fail("!")
}
}
return v
}
function unitconvert2(v, from, to)
{
FTOP[""] = 0
FBOT[""] = 0
TTOP[""] = 0
TBOT[""] = 0
parse_unit(from, FTOP, FBOT)
parse_unit(to, TTOP, TBOT)
v = unitconvert4(v, 0, FTOP, TTOP)
v = unitconvert4(v, 1, FBOT, TBOT)
return v
}
function unitconvert(v, from, to , tmp)
{
msg("converting: " v " (" from " -> " to ")")
tmp = unitconvert2(v, from, to)
msg("converted: " v " " from " = " tmp " " to)
return tmp
}
function initunits()
{
# unit conversion table
UNICONV["foot", "meter"] = 0.304801
UNICONV["seamile", "kilometer"] = 1.85
UNICONV["seamile", "foot"] = 6080
UNICONV["landmile", "kilometer"] = 1.61
UNICONV["radian", "degree"] = 180 / PI
UNICONV["hour", "minute"] = 60
UNICONV["minute", "second"] = 60
UNICONV["hour", "second"] = 3600
UNICONV["Fahrenheit", "Celcius"] = 5/9
UNICONV["Fahrenheit", "Celcius", "offset"] = -32
UNICONV["gallon", "liter"] = 3.78543
# synonyms and shorthands
UNITRANS["statute mile"] = "landmile"
UNITRANS["nautical mile"] = "seamile"
UNITRANS["knot"] = "seamile/hour"
}
function setwind(alt, alt_u, spd, spd_u, dir, dir_u, upd, upd_u , wn, we, wu)
{
alt = unitconvert(alt, alt_u, altitude_units)
spd = unitconvert(spd, spd_u, wind_units)
dir = unitconvert(dir, dir_u, "radian") - PI
wn = spd * cos(dir)
we = spd * sin(dir)
wu = unitconvert(upd, upd_u, wind_units)
msg("wn: " wn)
msg("we: " we)
msg("wu: " wu)
WIND[toplayer, "altitude"] = alt
WIND[toplayer, "up"] = wu
WIND[toplayer, "north"] = wn
WIND[toplayer, "east"] = we
toplayer++
}
BEGIN {
# config parameters
dspd = 1 # maximum amount of time increase (sec/iteration)
diff_limit = 0.2 # wind change rate limit for delay increase
(fps/iteration)
min_delay = 0 # minimum iteration delay (sec)
max_delay = 3 # maximum iteration delay (sec)
smooth = 1 # maximum difference per change (fps)
min_change = 0.05 # change threshold before sending new value
# properties
wind_north_prop = "/environment/wind-north-fps"
wind_east_prop = "/environment/wind-east-fps"
wind_up_prop = "/environment/wind-down-fps"
altitude_msl_prop = "/position/altitude-ft"
altitude_agl_prop = "/position/altitude-agl-ft"
# target units
wind_units = "foot/second"
altitude_units = "foot"
# constants
PI = 3.14159265358979323846
initunits()
datamode()
prev_wind_up = -getproperty(wind_up_prop)
prev_wind_north = getproperty(wind_north_prop)
prev_wind_east = getproperty(wind_east_prop)
initwinds(prev_wind_north, prev_wind_east, prev_wind_up)
delay = 1
while(status >= 0) {
if (delay > max_delay) delay = max_delay
if (delay < min_delay) delay = min_delay
if (delay < 0) delay = 0
msg("delay: " delay)
system("sleep " int(delay))
alt = getproperty(altitude_msl_prop)
while (wl >= 0 && alt < WIND[wl, "altitude"]) wl--
while (wl < toplayer && alt >= WIND[wl + 1, "altitude"]) wl++
msg("layer: " wl)
if (wl < 0) {
wind_north = WIND[0, "north"]
wind_east = WIND[0, "east"]
wind_up = WIND[0, "up"]
}
else if (wl >= toplayer) {
wind_north = WIND[toplayer, "north"]
wind_east = WIND[toplayer, "east"]
wind_up = WIND[toplayer, "up"]
}
else {
c1 = (WIND[wl + 1, "altitude"] - alt) \
/ (WIND[wl + 1, "altitude"] - WIND[wl, "altitude"])
c2 = (alt - WIND[wl, "altitude"]) \
/ (WIND[wl + 1, "altitude"] - WIND[wl, "altitude"])
wind_north = WIND[wl, "north"] * c1 + WIND[wl + 1, "north"] *
c2
wind_east = WIND[wl, "east"] * c1 + WIND[wl + 1, "east"] * c2
wind_up = WIND[wl, "up"] * c1 + WIND[wl + 1, "up"] * c2
msg("floor: " WIND[wl, "altitude"])
msg("ceil: " WIND[wl + 1, "altitude"])
msg("c1: " c1)
msg("c2: " c2)
}
dN = prev_wind_north - wind_north
dE = prev_wind_east - wind_east
dU = prev_wind_up - wind_up
delay = delay + dspd \
- dspd * (diff_limit + abs(dN)) / diff_limit / 6 \
- dspd * (diff_limit + abs(dE)) / diff_limit / 6 \
- dspd * (diff_limit + abs(dU)) / diff_limit / 6
while (abs(prev_wind_north - wind_north) > min_change) {
if (abs(prev_wind_north - wind_north) > smooth)
prev_wind_north += sgn(wind_north - prev_wind_north) *
smooth
else
prev_wind_north = wind_north
setproperty(wind_north_prop, prev_wind_north)
}
while (abs(prev_wind_east - wind_east) > min_change) {
if (abs(prev_wind_east - wind_east) > smooth)
prev_wind_east += sgn(wind_east - prev_wind_east) *
smooth
else
prev_wind_east = wind_east
setproperty(wind_east_prop, prev_wind_east)
}
while (abs(prev_wind_up - wind_up) > min_change) {
if (abs(prev_wind_up - wind_up) > smooth)
prev_wind_up += sgn(wind_up - prev_wind_up) * smooth
else
prev_wind_up = wind_up
setproperty(wind_up_prop, -prev_wind_up)
}
}
}
#END {
# if (exitcode) exit exitcode
# # other code
#}
' 2> /dev/tty
=============================================================================
- --
Regards, "I RADIS, do you?"
=Martin= http://www.iradis.org/
PGP: FE87448B DDF8 677C 9244 D119 4FE0 AE3A 37CF 3458 FE87 448B
From: Martin van Beilen <[EMAIL PROTECTED]>
To: [EMAIL PROTECTED]
Subject: Layered wind.
X-S-Issue: [EMAIL PROTECTED] 2002/02/19 01:23:53
55a7fe351251fb8e34a1a827e23278c0
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.0.6 (GNU/Linux)
iEYEARECAAYFAjxxmykACgkQN880WP6HRIu2kgCdE7qEBrrMqZ+CcfxVi8VqLpiy
1G4An2Ru0yMCV/RB/pesvs3dwvfwO+MC
=R0q4
-----END PGP SIGNATURE-----
_______________________________________________
Flightgear-devel mailing list
[EMAIL PROTECTED]
http://mail.flightgear.org/mailman/listinfo/flightgear-devel