ui: плашка ADC OVERLOAD — общий образ CPU/GL без пер-кадрового жора

AlertOverlay переписан в общий builder: BuildAlertImage строит RGBA-образ
плашки (попиксельная альфа, Canvas один раз на своём битмапе). GL грузит
образ текстурой (кэш как был), CPU блендит кэш в raw-кадр — убраны
canvas-путь в кадре и полный проход восстановления альфы битмапа.
GL-плашка теперь 1:1 с CPU (было: упрощённый бокс по центру), позиция —
правый верхний угол в обоих рендерах. Удалена мёртвая подсветочная линия
(перекрывалась рамкой).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-18 10:36:23 +03:00
co-authored by Claude Fable 5
parent e337f29314
commit bd2a6bc2ea
3 changed files with 193 additions and 135 deletions
+14 -26
View File
@@ -94,6 +94,7 @@ type
FTXOverlay: Boolean;
// ── ADC overload overlay ─────────────────────────────────────────────────
FADCOverloadVisible: Boolean;
FADCAlertImg: TAlertImage; // кэш образа плашки (BuildAlertImage, 1 раз)
FSampleRateOverlay: TSampleRateOverlay;
FVfoOverlay: TVfoOverlay;
FSliceOverlays: TFPList; // доп. слайс-флаги (B+); не владеет (владелец MainForm)
@@ -173,7 +174,7 @@ type
procedure BlendBand(X1, X2, H: Integer; R, G, B, Alpha: Byte);
procedure FillBandRaw(X1, X2, H: Integer; Color: TColor);
procedure CopyGridToSpectrum(W, H: Integer);
procedure DrawADCOverloadOverlay(C: TCanvas; W, H: Integer);
procedure DrawADCOverloadRaw(W, H: Integer);
procedure CalcFilterBandX(VfoFreq: Double; W: Integer;
out X1, X2, VfoX: Integer);
procedure CalcFilterBandXFor(VfoFreq: Double; Mode, BW, W: Integer;
@@ -1240,10 +1241,18 @@ begin
{$ENDIF}
end;
procedure TSpectrumView.DrawADCOverloadOverlay(C: TCanvas; W, H: Integer);
procedure TSpectrumView.DrawADCOverloadRaw(W, H: Integer);
// Плашка ADC OVERLOAD: общий с GL-рендером образ (AlertOverlay.BuildAlertImage,
// строится один раз и кэшируется), в кадре — только straight-alpha бленд
// внутри RawBegin/RawEnd: без Canvas (дорогой raw↔canvas синк Qt6) и без
// пофреймового восстановления альфы всего битмапа.
begin
if not FADCOverloadVisible then Exit;
DrawAlertOverlay(FSpectrumBitmap, C, W, H, 'ADC OVERLOAD', 'Input clipping detected');
if (W < 220) or (H < 60) or (FRawBase = nil) then Exit;
if FADCAlertImg.W = 0 then
BuildAlertImage('ADC OVERLOAD', 'Input clipping detected', FADCAlertImg);
BlendAlertImage(FADCAlertImg, FRawBase, FRawBPL, FRawW, FRawH,
W - ALERT_PAD - FADCAlertImg.W, ALERT_PAD);
end;
procedure TSpectrumView.CalcFilterBandX(VfoFreq: Double; W: Integer;
@@ -1732,33 +1741,12 @@ begin
for i := 0 to FSliceOverlays.Count - 1 do
TVfoOverlay(FSliceOverlays[i]).DrawOverlay(FSpectrumBitmap, W, H);
DrawADCOverloadRaw(W, H);
finally
RawEnd;
end;
// ADC overload — редкий canvas-путь (DrawAlertOverlay). Ломает альфу и
// режим доступа только в кадрах, где реально виден; после его canvas-
// операций восстанавливаем непрозрачность (пофреймовый OR-проход для
// обычных кадров удалён — Canvas на битмапе кадра больше не бывает).
if FADCOverloadVisible then
begin
DrawADCOverloadOverlay(C, W, H);
{$IFNDEF DARWIN}
FSpectrumBitmap.BeginUpdate(False);
for i := 0 to H - 1 do
begin
RowLW := PLongWord(FSpectrumBitmap.ScanLine[i]);
if RowLW = nil then Continue;
for Yp := 0 to W - 1 do
begin
RowLW^ := RowLW^ or $FF000000; // BGRA: альфа в байте 3
Inc(RowLW);
end;
end;
FSpectrumBitmap.EndUpdate(False);
{$ENDIF}
end;
end;
// ────────────────────────────────────────────────────────────────────────────