feat: docked watch-list panel, and auto-call learns the orthogonal markers
The watch list was a tab, and an operator working FT8 lives on the decodes one: a station they had asked to be told about turned up on a screen they were not looking at. The same answer is now docked in the widget strip, above the tabs, reduced to what is worth acting on — on the air and still needed, one row per band and mode, with the cluster's own NEW DXCC / NEW BAND / NEW SLOT badge and a click that tunes. Off by default. The "active and needed" answer costs a debounced query per visible slot, so it is written once (lib/watchlistSpots) and the tab uses it too. Auto-call: - It answers a new prefix, county, state, square or park. Those markers are orthogonal to the entity, they ranked as nothing-needed, and the engine sat through a never-worked WPX prefix calling CQ. New rung at the foot of the ladder, gated by the chase switches the badges use — which meant making those switches portable, since the backend cannot read localStorage. - It calls THROUGH a pileup. Giving up the moment the DX answered somebody else is precisely how a queue is not worked; the call and miss counters already bound the effort, and a station in mid-exchange is still never chosen as a new target. The PSK Reporter panel now follows the station auto-call is waiting for: the analysis takes a history query and a period or two to fill, so starting it when the DX comes free is starting it too late. Callbook lookup: a compound callsign with a page of its OWN keeps that page's location. QRZ files HP/WE9G under exactly that form, with the Panama square the station is operating from, and the rule that drops a home address from a portable call was throwing it away. The record's own country tells an operation's page from a home page. Changelog: entries may open with [NEW], drawn as a pill in the What's new dialog — a release is mostly fixes and the two or three genuinely new things should not have to be found by reading all of it.
This commit is contained in:
@@ -91,3 +91,60 @@ func TestSameEntityPortableKeepsItsLocation(t *testing.T) {
|
||||
t.Errorf("lat/lon = %v/%v — the precise home position was replaced by the entity centroid", r.Lat, r.Lon)
|
||||
}
|
||||
}
|
||||
|
||||
// The other half again, and the one an operator reported: a compound call with
|
||||
// a callbook page OF ITS OWN. QRZ files HP/WE9G under that exact form, with the
|
||||
// Panama address and square the station is actually operating from — and the
|
||||
// QSO was being logged with no grid at all while the page plainly showed one.
|
||||
func TestACompoundCallWithItsOwnPageKeepsThatPagesLocation(t *testing.T) {
|
||||
dxcc := testDXCC()
|
||||
dxcc["HP/WE9G"] = struct {
|
||||
num int
|
||||
country string
|
||||
cont string
|
||||
cqz, ituz int
|
||||
lat, lon float64
|
||||
}{num: 88, country: "Panama", cont: "NA", cqz: 7, ituz: 11, lat: 8.5, lon: -80.0}
|
||||
dxcc["WE9G"] = struct {
|
||||
num int
|
||||
country string
|
||||
cont string
|
||||
cqz, ituz int
|
||||
lat, lon float64
|
||||
}{num: 291, country: "United States", cont: "NA", cqz: 5, ituz: 8, lat: 39.8, lon: -98.5}
|
||||
|
||||
r := Result{
|
||||
Callsign: "HP/WE9G",
|
||||
Name: "Richard B",
|
||||
Country: "Panama", // the RECORD's own country: this page is the operation
|
||||
Grid: "EJ98xq",
|
||||
Lat: 8.686667, Lon: -80.043333,
|
||||
}
|
||||
fillFromDXCC(&r, dxcc)
|
||||
|
||||
if r.Grid != "EJ98xq" {
|
||||
t.Errorf("grid = %q, want EJ98xq — the page describes the operation, not a home address", r.Grid)
|
||||
}
|
||||
if r.Lat != 8.686667 || r.Lon != -80.043333 {
|
||||
t.Errorf("lat/lon = %v/%v — the station's own position was replaced by the entity centroid", r.Lat, r.Lon)
|
||||
}
|
||||
}
|
||||
|
||||
func TestSameEntityNameAcrossVocabularies(t *testing.T) {
|
||||
same := [][2]string{
|
||||
{"Germany", "Fed. Rep. of Germany"},
|
||||
{"United States", "United States of America"},
|
||||
{"Panama", "Panama"},
|
||||
{"Kosovo", "Republic of Kosovo"},
|
||||
}
|
||||
for _, p := range same {
|
||||
if !sameEntityName(p[0], p[1]) {
|
||||
t.Errorf("%q and %q read as different entities", p[0], p[1])
|
||||
}
|
||||
}
|
||||
for _, p := range [][2]string{{"Costa Rica", "United States"}, {"France", "Belgium"}, {"", "Panama"}} {
|
||||
if sameEntityName(p[0], p[1]) {
|
||||
t.Errorf("%q and %q read as the same entity", p[0], p[1])
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user