Aircraft, from the menus, on a live board, over a real map
Four things the ADS-B mode was missing, and one it was actively getting
wrong.
The band plan lists 1090 MHz because that is where ADS-B is, so choosing
it from the band plan is the obvious thing to do -- and it records the
bursts as clicks in a WAV file and decodes nothing, silently. Both the
scanner and the menus now say so, before the sweep starts, and name the
mode that does decode it. It is not refused: looking at the raw spectrum
is a fair thing to want.
Menu 5, Aircraft (ADS-B), is the whole mode without a command line. Every
option on one screen with a line saying what it does, ?N for the long
version and the flag it corresponds to, l to listen, m to draw a map from
any log, s to keep the options. The listening and the drawing moved into
bandsaunter/aircraft.py so the menus and the command line run the same
code.
While it listens the screen is a live board: one line per aircraft in the
order first heard, the counter climbing as frames arrive, height coloured
low warm to high cold with an arrow for climb or descent, the age of the
last report going green to red, and the line removed once nothing has been
heard for --hold seconds, everything below moving up. The registers are
asked while it runs, so registration, type, operator and route fill
themselves in as the answers arrive.
--speed-unit knots|mph|kph changes the heading of that board, the speed
beside every aircraft on the map and the speeds in the report, and moves
the distances with it so that one picture never carries two different
miles. The log stays in knots, which is what the aircraft broadcast.
And there is a real map under the flight paths: {z}/{x}/{y} tiles fetched
once, cached in ~/.cache/bandsaunter/tiles, reprojected from Web Mercator
pixel by pixel, inverted and dimmed so the aircraft stay the brightest
thing on the picture. The PNGs are decoded here -- zlib and the five row
filters from the specification, checked byte for byte against Pillow on
real tiles -- so nothing new is depended on. Tiles are cached and never
re-fetched, every request says who is asking, and the attribution is drawn
onto the picture, because a GIF travels without its readme.
conftest now fails any test that reaches for a tile server or a register.
It caught four of these on the way in.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016PsWPTweCT6pwxKngvVxcg
This commit is contained in:
parent
4239635f74
commit
96fc21ac7d
18 changed files with 3298 additions and 281 deletions
|
|
@ -1,5 +1,5 @@
|
|||
.\" Generated by packaging/make-man.py -- do not edit by hand.
|
||||
.TH BANDSAUNTER 1 "2026-09-03" "bandsaunter 2026-09-03_05" "User Commands"
|
||||
.TH BANDSAUNTER 1 "2026-09-04" "bandsaunter 2026-09-04_01" "User Commands"
|
||||
.SH NAME
|
||||
bandsaunter \- scan, record and identify radio signals with an RTL-SDR
|
||||
.SH SYNOPSIS
|
||||
|
|
@ -1285,6 +1285,62 @@ checksums, the same decoder \[em] for trying all of this without an aerial;
|
|||
says where they are flying. An aerial cut for 1090 MHz makes the difference
|
||||
between hearing the airport and hearing the county; the whip supplied with a
|
||||
dongle is a quarter of the length it wants.
|
||||
.SS While it listens
|
||||
The screen is a live board of what is overhead: one line per aircraft, in the
|
||||
order they were first heard, with everything the frames have said \[em] callsign,
|
||||
address, height with an arrow for climb or descent, ground speed, track as
|
||||
degrees and a point of the compass, position \[em] and a counter that climbs as
|
||||
frames arrive. Height is coloured low warm to high cold, and the age of the
|
||||
last frame green, then yellow, then red.
|
||||
.PP
|
||||
An aircraft that has not been heard from for
|
||||
.B \-\-hold
|
||||
seconds is removed from the board and everything below it moves up: the board
|
||||
is the sky now, not a list of everything ever heard. Nothing is lost by it, as
|
||||
the log holds every frame and the report at the end lists every aircraft.
|
||||
.PP
|
||||
The registers are asked while the listening runs, so the registration, type,
|
||||
operator and route appear on the line as the answers arrive. A narrow terminal
|
||||
drops the columns a website supplied and keeps the ones only the aircraft can
|
||||
give.
|
||||
.B \-\-frames
|
||||
prints the raw stream instead, and output that is not a terminal gets a plain
|
||||
running count rather than a display that redraws four times a second.
|
||||
.PP
|
||||
.BI \-\-speed\-unit " knots|mph|kph"
|
||||
changes what speeds are shown in: the heading on the live display, the speed
|
||||
written beside every aircraft on the map, and the speeds in the report. The
|
||||
distances move with it \[em] nautical miles with knots, statute miles with miles
|
||||
an hour, kilometres with km/h \[em] so that one picture never carries two
|
||||
different miles. The log always holds knots, because that is what the aircraft
|
||||
broadcast: the recording stays the thing that arrived and the conversion
|
||||
happens at the moment of showing it to somebody.
|
||||
.SS From the menus
|
||||
Running
|
||||
.B bandsaunter
|
||||
with no arguments and choosing
|
||||
.B 5
|
||||
.RB ( "Aircraft (ADS-B)" )
|
||||
does all of this without a command line. Every option is listed on one screen
|
||||
with a line saying what it does;
|
||||
.BI ? N
|
||||
explains one at length, including the flag it corresponds to,
|
||||
.B l
|
||||
listens,
|
||||
.B m
|
||||
draws a map from any log in the recordings directory, and
|
||||
.B s
|
||||
saves the options to
|
||||
.IR ~/.config/bandsaunter/aircraft.yaml .
|
||||
.SS Not a scan
|
||||
The band plan lists 1090 MHz because that is where ADS-B is, but sweeping it
|
||||
records the bursts as clicks in a WAV file and decodes nothing: the signalling
|
||||
is a megabit a second and the scan path is twelve and a half kilohertz wide.
|
||||
Both the scanner and the menus say so when a sweep is pointed at 1090 MHz or
|
||||
at the 978 MHz UAT band, rather than letting it run silently. Scanning it
|
||||
anyway is a fair thing to want if what you are after is the raw spectrum;
|
||||
.B \-\-save\-iq
|
||||
keeps the samples.
|
||||
.SS Who the aircraft is
|
||||
The frames say an address, not a registration. Two registers are asked \[em]
|
||||
adsbdb for the airframe and the route, then hexdb \[em] and the answers are
|
||||
|
|
@ -1324,6 +1380,26 @@ where ffmpeg is installed, or a
|
|||
for the whole evening in one picture. Altitude is the colour, low warm to high
|
||||
cold. The GIF is written from first principles \[em] a palette, an LZW stream
|
||||
and frame differencing \[em] so nothing but numpy is needed to draw one.
|
||||
.SS The ground under it
|
||||
A real map is drawn under the aircraft: standard {z}/{x}/{y} raster tiles,
|
||||
OpenStreetMap by default, fetched the first time an area is drawn and
|
||||
reprojected from Web Mercator onto the picture, inverted and dimmed so the
|
||||
aircraft stay the brightest thing on it. The tiles are decoded here, from
|
||||
zlib and the five row filters the PNG specification defines, with no imaging
|
||||
library.
|
||||
.PP
|
||||
Tiles are cached in
|
||||
.I ~/.cache/bandsaunter/tiles
|
||||
and never fetched twice, every request identifies this program in its
|
||||
User-Agent, and the attribution the tiles require is written onto the picture
|
||||
\[em] a GIF travels without the readme that would otherwise carry it. A drawing
|
||||
is capped at a few dozen tiles; past that the zoom drops instead.
|
||||
.PP
|
||||
.B \-\-no\-basemap
|
||||
draws the tracks on their own,
|
||||
.BI \-\-tiles " URL"
|
||||
points at another server, and where there is no network and nothing cached
|
||||
the picture falls back to the plain grid.
|
||||
.SH METERS AND SENSORS
|
||||
Two things on the ISM bands are worth naming rather than reporting as
|
||||
hexadecimal.
|
||||
|
|
@ -1398,9 +1474,17 @@ frequency to dial into a radio.
|
|||
.I ~/.config/bandsaunter/config.yaml
|
||||
The settings every run starts from.
|
||||
.TP
|
||||
.I ~/.config/bandsaunter/aircraft.yaml
|
||||
The aircraft options, as saved from the menus.
|
||||
.TP
|
||||
.I ~/.config/bandsaunter/*.yaml
|
||||
Named profiles.
|
||||
.TP
|
||||
.IR adsb_ * .jsonl
|
||||
Every ADS-B frame heard in one listening session, with a
|
||||
.I .txt
|
||||
report and any picture drawn from it beside it.
|
||||
.TP
|
||||
.I ~/bandsaunter/
|
||||
Where recordings, transcripts and logs are written, unless
|
||||
.B \-\-output
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue