added s11!

This commit is contained in:
Ayzen
2026-03-26 18:29:42 +03:00
parent 9ddbde22bd
commit 077542cbd0
43 changed files with 713 additions and 347 deletions
+28 -10
View File
@@ -8,6 +8,7 @@ from typing import Any, Protocol
import numpy as np
from python_app.hardware_full.librevna_driver.models import SweepResult
from python_app.models.run_config_model import RadarSweepModel
@@ -30,8 +31,8 @@ class LibreVnaBackend(Protocol):
def read_device_limits(self) -> dict[str, float | int]:
"""Query runtime device limits."""
def acquire_s21(self) -> tuple[np.ndarray, np.ndarray]:
"""Acquire one S21 trace."""
def acquire(self) -> SweepResult:
"""Acquire one sweep with all available traces."""
@dataclass(slots=True)
@@ -108,15 +109,21 @@ class NativeLibreVnaBackend:
"max_power_dbm": float(limits.max_power_dbm),
}
def acquire_s21(self) -> tuple[np.ndarray, np.ndarray]:
"""Acquire one S21 sweep from hardware."""
def acquire(self) -> SweepResult:
"""Acquire one sweep from hardware."""
if self._settings is None:
raise RuntimeError("Radar service is not configured")
if self._device is None:
raise RuntimeError("Device not found")
result = self._device.vna.acquire(expected_points=self._settings.points, timeout_s=20.0)
return np.asarray(result.x, dtype=np.float32), np.asarray(result.trace("s21"), dtype=np.complex64)
return SweepResult(
x=np.asarray(result.x, dtype=np.float32),
traces={
"s11": np.asarray(result.trace("s11"), dtype=np.complex64),
"s21": np.asarray(result.trace("s21"), dtype=np.complex64),
},
)
@dataclass(slots=True)
@@ -149,15 +156,26 @@ class MockLibreVnaBackend:
"""Mock backend does not support native device limits queries."""
raise RuntimeError("LibreVNA Python driver is not available")
def acquire_s21(self) -> tuple[np.ndarray, np.ndarray]:
"""Generate synthetic S21 values using deterministic phase envelope."""
def acquire(self) -> SweepResult:
"""Generate synthetic S11 and S21 values using deterministic envelopes."""
if self._settings is None:
raise RuntimeError("Radar service is not configured")
points = self._settings.points
freq = np.linspace(self._settings.start_hz, self._settings.stop_hz, points, dtype=np.float32)
phase = (2.0 * math.pi * np.linspace(0.0, 1.0, points, dtype=np.float32)) + self._mock_phase
envelope = 0.6 + 0.4 * np.sin(phase * 0.5)
s21 = (envelope * np.cos(phase) + 1j * envelope * np.sin(phase)).astype(np.complex64)
s21_envelope = 0.6 + 0.4 * np.sin(phase * 0.5)
s11_envelope = 0.25 + 0.15 * np.cos(phase * 0.75)
s21 = (s21_envelope * np.cos(phase) + 1j * s21_envelope * np.sin(phase)).astype(np.complex64)
reflected_phase = phase * 0.6 + 0.8
s11 = (
s11_envelope * np.cos(reflected_phase) + 1j * s11_envelope * np.sin(reflected_phase)
).astype(np.complex64)
self._mock_phase += 0.05
return freq, s21
return SweepResult(
x=freq,
traces={
"s11": s11,
"s21": s21,
},
)