Add configurable VFO frequency range with GHz support

- Settings > Display: new "VFO Display" control to select max frequency
  range (999 MHz / 9.999 GHz / 99.999 GHz), persisted as freq_mhz_digits
- FreqDisplay: extend digit map [0..10] to support up to 11 digit positions;
  keyboard navigation adapts to MinMhzDigits dynamically
- MainForm/LayoutTopVfoBlock: VFO panel width scales automatically with
  selected digit count using dynamic text measurement
- Web VFO: fix broken HTML (class attr not closed before data-s — wheel and
  hover were completely non-functional); rewrite fmtVfo to use variable MHz
  digit count synced from server state; fix missing </span> for .vfo-hz
- WebServer: publish freq_mhz_digits in state JSON; updated from
  ApplyFreqMhzDigits so desktop and web stay in sync
- Fix Int32 overflow on frequencies above ~2.15 GHz: CATEngine.Pad V param
  Int64, FormatFreq/FormatFreqSV Mhz var Int64 (Mhz*1000000 overflowed)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-05-15 13:13:52 +03:00
co-authored by Claude Sonnet 4.6
parent 5ac7ddc976
commit efc21b92e6
8 changed files with 105 additions and 35 deletions
+34 -2
View File
@@ -36,6 +36,7 @@ type
// TX-настройки целиком (любая правка → один callback с актуальной структурой)
TOnTXSettingsChange = procedure(const T: TTXSettings) of object;
TOnFreqMhzDigitsChange = procedure(Digits: Integer) of object;
TOnDisplayParamChange = procedure(FFTSize, WindowType, SpecDetector,
SpecAvgMode: Integer; SpecAvgTimeMS: Double) of object;
TOnWaterfallParamChange = procedure(WfDetector, WfAvgMode: Integer;
@@ -109,6 +110,7 @@ type
FChkShowWaterfall: TCheckBox;
FCmbFPS: TComboBox;
FChkLightTheme: TCheckBox;
FCmbFreqMhzDigits: TComboBox;
// ---- PA Settings tab controls ----
FEdMaxPower: TSpinEdit;
@@ -243,8 +245,9 @@ type
FOnAudioInDevChange: TOnAudioInDevChange;
FOnVisibilityChange: TOnVisibilityChange;
FOnFPSChange: TOnFPSChange;
FOnThemeChange: TOnThemeChange;
FOnTXChange: TOnTXSettingsChange;
FOnThemeChange: TOnThemeChange;
FOnFreqMhzDigitsChange: TOnFreqMhzDigitsChange;
FOnTXChange: TOnTXSettingsChange;
FLoading: Boolean;
@@ -298,6 +301,7 @@ type
procedure OnVisibilityChkChange(Sender: TObject);
procedure OnFPSCmbChange(Sender: TObject);
procedure OnLightThemeChkChange(Sender: TObject);
procedure OnFreqMhzDigitsCmbChange(Sender: TObject);
procedure OnMaxPowerChange(Sender: TObject);
procedure OnBandCalChange(Sender: TObject);
procedure OnCATSerialChange(Sender: TObject);
@@ -335,6 +339,7 @@ type
procedure LoadVisibility(ShowSpectrum, ShowWaterfall: Boolean);
procedure LoadFPS(FPS: Integer);
procedure LoadLightTheme(ALight: Boolean);
procedure LoadFreqMhzDigits(Digits: Integer);
procedure LoadPASettings(MaxPower: Double; const BandCal: array of Double);
procedure LoadCATSettings(
const SerEnabled: array of Boolean;
@@ -357,6 +362,7 @@ type
property OnVisibilityChange: TOnVisibilityChange read FOnVisibilityChange write FOnVisibilityChange;
property OnFPSChange: TOnFPSChange read FOnFPSChange write FOnFPSChange;
property OnThemeChange: TOnThemeChange read FOnThemeChange write FOnThemeChange;
property OnFreqMhzDigitsChange: TOnFreqMhzDigitsChange read FOnFreqMhzDigitsChange write FOnFreqMhzDigitsChange;
property OnTXChange: TOnTXSettingsChange read FOnTXChange write FOnTXChange;
end;
@@ -783,6 +789,15 @@ begin
FChkLightTheme.Font.Name := UI_FONT;
FChkLightTheme.Font.Size := 9;
FChkLightTheme.OnChange := OnLightThemeChkChange;
Grp := MakeGroupPanel(FPageDisplay, 'VFO Display', MARGIN, 378, 650, 92);
MakeLbl(Grp, 'Frequency range', PAD, R1 + 5, LW);
FCmbFreqMhzDigits := MakeCombo(Grp, CX, R1, 240, OnFreqMhzDigitsCmbChange);
FCmbFreqMhzDigits.Items.Add('up to 999 MHz (3 digits)');
FCmbFreqMhzDigits.Items.Add('up to 9.999 GHz (4 digits)');
FCmbFreqMhzDigits.Items.Add('up to 99.999 GHz (5 digits)');
FCmbFreqMhzDigits.ItemIndex := 0;
end;
// ---------------------------------------------------------------------------
@@ -2014,6 +2029,23 @@ begin
else ApplyTheme(DarkTheme);
end;
procedure TSettingsForm.LoadFreqMhzDigits(Digits: Integer);
begin
FLoading := True;
try
FCmbFreqMhzDigits.ItemIndex := EnsureRange(Digits - 3, 0, 2);
finally
FLoading := False;
end;
end;
procedure TSettingsForm.OnFreqMhzDigitsCmbChange(Sender: TObject);
begin
if FLoading then Exit;
if Assigned(FOnFreqMhzDigitsChange) then
FOnFreqMhzDigitsChange(FCmbFreqMhzDigits.ItemIndex + 3);
end;
procedure TSettingsForm.LoadPASettings(MaxPower: Double;
const BandCal: array of Double);
var i, n: Integer;