chore: release v0.27.12
This commit is contained in:
+73
-2
@@ -9,6 +9,7 @@ package cat
|
||||
import (
|
||||
"fmt"
|
||||
"runtime"
|
||||
"strings"
|
||||
"sync"
|
||||
"time"
|
||||
)
|
||||
@@ -240,15 +241,81 @@ func (m *Manager) freqOffsetHz() int64 {
|
||||
// display trick: the readout would say 144 and every spot click, band change and
|
||||
// memory recall would send the rig somewhere 116 MHz away.
|
||||
func (m *Manager) SetFrequency(hz int64) error {
|
||||
real := hz
|
||||
if off := m.freqOffsetHz(); off != 0 && hz > off {
|
||||
hz -= off
|
||||
}
|
||||
return m.exec(func(b Backend) error { return b.SetFrequency(hz) })
|
||||
err := m.exec(func(b Backend) error { return b.SetFrequency(hz) })
|
||||
if err == nil {
|
||||
m.noteCommandedFreq(real)
|
||||
}
|
||||
return err
|
||||
}
|
||||
|
||||
// noteCommandedFreq publishes a frequency the radio has just acknowledged,
|
||||
// without waiting for the next poll to come round and read it back.
|
||||
//
|
||||
// The wait is what this is about. A rigctl client — WSJT-X above all — sets a
|
||||
// frequency and then READS it back before it believes it is there, and until
|
||||
// then it will not decode, transmit or even update its own dial. Everything
|
||||
// answering "f" here comes from the last poll, so the answer was the OLD
|
||||
// frequency for as long as a poll cycle takes; on a rig reached over the
|
||||
// internet, where one cycle is many round trips, a band change from WSJT-X took
|
||||
// ten seconds to be believed while the radio itself had moved instantly.
|
||||
//
|
||||
// Only when NOT split. In split the two frequencies mean different VFOs and a
|
||||
// guess about which one just moved is how a client ends up writing the transmit
|
||||
// frequency onto the dial — the poll is left to settle that case.
|
||||
func (m *Manager) noteCommandedFreq(hz int64) {
|
||||
if hz <= 0 {
|
||||
return
|
||||
}
|
||||
m.mu.Lock()
|
||||
st := m.state
|
||||
if !st.Connected || st.Split || st.FreqHz == hz {
|
||||
m.mu.Unlock()
|
||||
return
|
||||
}
|
||||
st.FreqHz = hz
|
||||
st.Band = BandFromHz(hz)
|
||||
st.UpdatedAt = time.Now()
|
||||
m.state = st
|
||||
m.mu.Unlock()
|
||||
m.emitState()
|
||||
}
|
||||
|
||||
// SetMode dispatches a SetMode call to the CAT goroutine.
|
||||
func (m *Manager) SetMode(mode string) error {
|
||||
return m.exec(func(b Backend) error { return b.SetMode(mode) })
|
||||
err := m.exec(func(b Backend) error { return b.SetMode(mode) })
|
||||
if err == nil {
|
||||
m.noteCommandedMode(mode)
|
||||
}
|
||||
return err
|
||||
}
|
||||
|
||||
// noteCommandedMode is the mode half of noteCommandedFreq, and exists for the
|
||||
// same client readback.
|
||||
//
|
||||
// "DATA" is deliberately not published. A backend reports data mode under the
|
||||
// operator's own digital mode (FT8, JS8, RTTY…), and that name is what a QSO is
|
||||
// logged with — a plain "DATA" standing in for a poll cycle is a mode nobody
|
||||
// works, in a field that ends up in an ADIF file. The poll is a fraction of a
|
||||
// second away and knows the real name.
|
||||
func (m *Manager) noteCommandedMode(mode string) {
|
||||
if mode == "" || strings.EqualFold(mode, "DATA") {
|
||||
return
|
||||
}
|
||||
m.mu.Lock()
|
||||
st := m.state
|
||||
if !st.Connected || st.Mode == mode {
|
||||
m.mu.Unlock()
|
||||
return
|
||||
}
|
||||
st.Mode = mode
|
||||
st.UpdatedAt = time.Now()
|
||||
m.state = st
|
||||
m.mu.Unlock()
|
||||
m.emitState()
|
||||
}
|
||||
|
||||
// SetPTT dispatches a transmit on/off request to the CAT goroutine.
|
||||
@@ -704,6 +771,10 @@ type IcomController interface {
|
||||
SetVOXGain(int) error
|
||||
SetAntiVOX(int) error
|
||||
SetPower(bool) error // turn the transceiver on/off (manual — never auto on connect)
|
||||
// RecallBandStack moves the VFO to what the radio's own band stacking
|
||||
// register holds — the operator's last frequency and mode on that band.
|
||||
// Returns the frequency landed on.
|
||||
RecallBandStack(band, reg int) (int64, error)
|
||||
}
|
||||
|
||||
// ScopeSweep is one complete spectrum-scope sweep reassembled from the Icom's
|
||||
|
||||
Reference in New Issue
Block a user