fix: 'stations on air' widget updates instantly after a QSO (UDP/FT8 path now emits qso:logged; publishLiveStatus emits livestatus:updated so the widget re-reads exactly when the shared row changes) — was lagging ~15-45s behind the ON-AIR badge
This commit is contained in:
@@ -9636,6 +9636,13 @@ func (a *App) LogUDPLoggedADIF(adifText string) (int64, error) {
|
|||||||
q.ID = id
|
q.ID = id
|
||||||
a.noteLiveQSO() // multi-op: flip this operator back "online"
|
a.noteLiveQSO() // multi-op: flip this operator back "online"
|
||||||
a.materializeAwardRefs(q)
|
a.materializeAwardRefs(q)
|
||||||
|
// Announce the log so UI widgets refresh AT ONCE (the Recent-QSOs grid, the
|
||||||
|
// ON-AIR badge and the "stations on air" widget). The manual log path always
|
||||||
|
// did this; the UDP/FT8 path did not, so a station running MSHV saw the top
|
||||||
|
// "on air" list lag ~15-45s behind the instant bottom badge.
|
||||||
|
if a.ctx != nil {
|
||||||
|
wruntime.EventsEmit(a.ctx, "qso:logged", id)
|
||||||
|
}
|
||||||
a.saveQSORecording(&q)
|
a.saveQSORecording(&q)
|
||||||
if a.extsvc != nil {
|
if a.extsvc != nil {
|
||||||
a.extsvc.OnQSOLogged(id)
|
a.extsvc.OnQSOLogged(id)
|
||||||
|
|||||||
@@ -452,9 +452,13 @@ export default function App() {
|
|||||||
const load = () => GetLiveStations().then((s) => setLiveStations((s ?? []) as LiveStation[])).catch(() => {});
|
const load = () => GetLiveStations().then((s) => setLiveStations((s ?? []) as LiveStation[])).catch(() => {});
|
||||||
load();
|
load();
|
||||||
const id = window.setInterval(load, 5 * 1000);
|
const id = window.setInterval(load, 5 * 1000);
|
||||||
// Small delay lets the async publishLiveStatus MySQL write land before we read.
|
// Refresh the instant the backend actually publishes a row change (a QSO put
|
||||||
|
// someone on air, or a 5-min silence took them off) — so this widget tracks the
|
||||||
|
// bottom ON-AIR badge instead of lagging behind its poll. Keep the qso:logged
|
||||||
|
// fallback too (a small delay lets the async publish land) for older paths.
|
||||||
|
const offStatus = EventsOn('livestatus:updated', load);
|
||||||
const offLogged = EventsOn('qso:logged', () => { window.setTimeout(load, 1500); });
|
const offLogged = EventsOn('qso:logged', () => { window.setTimeout(load, 1500); });
|
||||||
return () => { window.clearInterval(id); offLogged?.(); };
|
return () => { window.clearInterval(id); offStatus?.(); offLogged?.(); };
|
||||||
}, [liveStationsOn]);
|
}, [liveStationsOn]);
|
||||||
// Mode OpsLog shows when the rig reports generic DIG_U/DIG_L. OmniRig
|
// Mode OpsLog shows when the rig reports generic DIG_U/DIG_L. OmniRig
|
||||||
// can't tell us if it's FT8 vs FT4 vs RTTY, so the user picks the default
|
// can't tell us if it's FT8 vs FT4 vs RTTY, so the user picks the default
|
||||||
|
|||||||
@@ -6,9 +6,21 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
|
wruntime "github.com/wailsapp/wails/v2/pkg/runtime"
|
||||||
|
|
||||||
"hamlog/internal/applog"
|
"hamlog/internal/applog"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// emitLiveStatusChanged nudges the frontend to re-read GetLiveStations right when
|
||||||
|
// the shared table actually changes (a row appeared or was removed) — so the
|
||||||
|
// "stations on air" widget updates the instant a QSO is published, matching the
|
||||||
|
// bottom ON-AIR badge instead of waiting for its poll.
|
||||||
|
func (a *App) emitLiveStatusChanged() {
|
||||||
|
if a.ctx != nil {
|
||||||
|
wruntime.EventsEmit(a.ctx, "livestatus:updated", nil)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Live operator status — for multi-operator events on a SHARED MySQL logbook
|
// Live operator status — for multi-operator events on a SHARED MySQL logbook
|
||||||
// (e.g. a special-event call like TM74FR with several ops on different bands).
|
// (e.g. a special-event call like TM74FR with several ops on different bands).
|
||||||
// Each OpsLog instance heartbeats its current activity (operator call + station
|
// Each OpsLog instance heartbeats its current activity (operator call + station
|
||||||
@@ -231,6 +243,7 @@ func (a *App) publishLiveStatus() {
|
|||||||
if _, err := a.logDb.ExecContext(a.ctx, "DELETE FROM live_status WHERE operator=?", op); err != nil {
|
if _, err := a.logDb.ExecContext(a.ctx, "DELETE FROM live_status WHERE operator=?", op); err != nil {
|
||||||
applog.Printf("livestatus: offline DELETE failed: %v", err)
|
applog.Printf("livestatus: offline DELETE failed: %v", err)
|
||||||
}
|
}
|
||||||
|
a.emitLiveStatusChanged()
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
lastQSOArg := lastQSO.UTC()
|
lastQSOArg := lastQSO.UTC()
|
||||||
@@ -246,6 +259,7 @@ func (a *App) publishLiveStatus() {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
applog.Printf("livestatus: published op=%s station=%s %dHz %s %s ON AIR", op, station, freqHz, band, mode)
|
applog.Printf("livestatus: published op=%s station=%s %dHz %s %s ON AIR", op, station, freqHz, band, mode)
|
||||||
|
a.emitLiveStatusChanged()
|
||||||
}
|
}
|
||||||
|
|
||||||
// LiveStation is one operator's live status for the multi-op "who's on air" widget.
|
// LiveStation is one operator's live status for the multi-op "who's on air" widget.
|
||||||
|
|||||||
Reference in New Issue
Block a user