feat(display): скорость водопада с max-hold накоплением + MSAA спектра

- настройка Speed (wf_speed_div 1/2/4/8, Waterfall→Rendering): замедление
  накапливает кадры max-hold'ом в SetWaterfallData — короткие посылки (CW)
  не выпадают из строки; двойная децимация MainForm убрана
  (EffectiveWfInterval, CPU-путь не быстрее полукадровой)
- настройка Anti-aliasing (spec_msaa 1/2/4/8, дефолт 4x, Spectrum→Rendering):
  MultiSampling на GL-контроле спектра; смена в рантайме пересоздаёт
  контекст → ResetGLCache обнуляет текстурные кэши без glDelete

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-04 16:48:55 +03:00
co-authored by Claude Fable 5
parent 092a202f5f
commit e260995218
6 changed files with 164 additions and 35 deletions
+10 -1
View File
@@ -307,7 +307,13 @@ procedure TWaterfallView.SetWaterfallData(const Pixels: array of Single; Count:
var i, N: Integer;
begin
N := Min(Count, WF_MAX_PIXELS);
for i := 0 to N - 1 do FWaterfallBuf[i] := Pixels[i];
// Замедление (WfFrameInterval>1) накапливает кадры max-hold'ом, а не
// выбрасывает их — короткие посылки (CW) не выпадают из строки.
if (FWfFrameCounter = 0) or (N <> FWaterfallBufCount) then
for i := 0 to N - 1 do FWaterfallBuf[i] := Pixels[i]
else
for i := 0 to N - 1 do
if Pixels[i] > FWaterfallBuf[i] then FWaterfallBuf[i] := Pixels[i];
FWaterfallBufCount := N;
Inc(FWfFrameCounter);
if FWfFrameCounter >= Max(1, FWfFrameInterval) then
@@ -548,6 +554,9 @@ begin
finally
FWfBitmap.EndUpdate(False);
end;
// Строка потреблена — иначе фронтенд (OnWaterfallReady) считал бы кадр
// «несобранным» и дёргал перерисовку на каждый кадр анализатора.
FWaterfallDirty := False;
end;
// ────────────────────────────────────────────────────────────────────────────