fwt_software/docs/modules-reference.md

8.6 KiB
Raw Blame History

Module Reference

Per-file reference for the refactored tree, plus the shared data structures.

Core (fgc_core — SDK-independent, unit-tested)

File Contents
include/fgc/Config.h, src/core/Config.cpp Typed AppConfig (General/Network/Serial/Camera/Paths/Features/Logging/UI/Motor/Scan/IMU) + ConfigLoader (INI parse, env overrides, validation)
include/fgc/Paths.h, src/core/Paths.cpp ~/$ENV expansion, executable dir, config search order, default output dir
include/fgc/Logger.h, src/core/Logger.cpp Leveled, thread-safe logger + per-category wire trace; LOG_TRACE..LOG_ERROR, LOG_TRACE_CAT
include/fgc/Geometry.h, src/core/Geometry.cpp Per-axis degrees↔encoder-counts affine map ([Motor] calibration)
include/fgc/ScanGrid.h, src/core/ScanGrid.cpp Capture waypoints (CSV or generated) + ping-pong cursor ([Scan])
include/fgc/TelemetryParser.h, src/core/TelemetryParser.cpp parseTelemetryLine (firmware ST line) → std::optional<MotorTelemetry>
include/fgc/CommandParser.h, src/core/CommandParser.cpp parseCommand whitespace tokenizer → Command
include/fgc/HelpText.h, src/core/HelpText.cpp Operator command catalog (helpCatalog) + renderHelp (console & TUI help)
include/fgc/DumpParser.h, src/core/DumpParser.cpp parseDump firmware DUMP block → DumpData (per-axis state + decoded TMC registers/flags); formatDump
include/fgc/DiagParser.h, src/core/DiagParser.cpp parseDiag firmware DG self-test stream → DiagResult (per-axis tests, PASS/FAIL); formatDiag
include/fgc/Calibration.h, src/core/Calibration.cpp linearFit (least-squares, R²) + circularMeanDeg for the IMU-referenced calibration
include/fgc/CalibrationRoutine.h, src/core/CalibrationRoutine.cpp gimbal calib worker thread: sweeps each axis, dwells reading the IMU, fits degrees↔counts; exposes progress()/report()/takeResult()
include/fgc/MtiProtocol.h, src/core/MtiProtocol.cpp Xsens MTi binary protocol: MtiFramer (checksum framing), config-message builders, parseMTDataImuSample (temp/acc/gyr/mag/euler)
include/fgc/CaptureScheduler.h, src/core/CaptureScheduler.cpp Capture state machine over the interfaces; injectable clock; setGeometry adopts a recalibration
include/fgc/Application.h, src/core/Application.cpp Factory (real vs mock, headless vs TUI), wiring, control loop, gimbal … commands, background-result polling, buildSnapshot()
include/fgc/ui/UiSnapshot.h, src/ui/UiSnapshot.cpp Plain-data view model (incl. ImuView, ActivityView, CalibResultView, DumpView) + pure formatting helpers (state label/colour, degrees, time-ago, pending-sensors)
include/fgc/ui/HeadlessUi.h, src/ui/HeadlessUi.cpp Default line console: stdin → command sink; logs via the default stdout/stderr writer
ini.c, ini.h Bundled third-party inih INI parser

Interfaces

File Interface Shared structs
include/fgc/IMotorController.h IMotorController MotorTelemetry
include/fgc/IControlChannel.h IControlChannel ControlCommand, CamEvent
include/fgc/ICameraSource.h ICameraSource Frame
include/fgc/IImuSource.h IImuSource ImuSample (from MtiProtocol.h)
include/fgc/ui/IUserInterface.h IUserInterface UiSnapshot

Real implementations (SDK-gated)

File Implements Built when
src/serial/SerialMotorController.cpp IMotorController over Boost.Asio serial (pImpl) always
src/serial/MtiImuSource.cpp IImuSource over Boost.Asio serial: configures the MTi to Euler+calibrated, then frames the MTData stream always
src/mqtt/MqttControlChannel.cpp IControlChannel over Eclipse Paho WITH_MQTT
src/ui/TuiUi.cpp IUserInterface over FTXUI: panels, key bar, log pane WITH_TUI
src/camera/VimbaCameraSource.cpp ICameraSource over Vimba X (pImpl) WITH_VIMBA
src/camera/JpegXlEncoder.cpp libjxl encode-to-file always
src/camera/ImagePipeline.cpp frame → rotate → encode → write → CamEvent (worker thread) always

Mock / null implementations

File Implements
include/fgc/mock/MockMotorController.h Simulated sweeping gimbal (incl. canned DUMP)
include/fgc/mock/NullControlChannel.h No-op channel; auto-sweep
include/fgc/mock/MockCameraSource.h Synthetic gradient frames
include/fgc/mock/MockImuSource.h Synthetic IMU (sinusoidal orientation, gravity on accZ)

Entry point & scripts

File Role
main.cpp CLI parsing → AppConfig + RuntimeOptionsApplication::run()
scripts/run.sh Path-independent launcher
scripts/fire-gimbal-control.service systemd unit template

Data structures

MotorTelemetry / AxisTelemetry (IMotorController.h)

Per-axis yaw and pitch segments (pitch_present flag), each an AxisTelemetry: state (AxisState B/R/H/A/E), xactual, xenc (encoder counts), drv_status, sg/cs/pwm, and flags standstill/stall/overtemp/endstop_l/endstop_r, with moving()/ready() helpers. Parsed from the firmware ST Y:...[ P:...] line; degrees are derived via Geometry.

ControlCommand (IControlChannel.h)

control_code (0 = scan-grid sweep, 1 = directed to target_HDG) + target_heading, each with an *_available flag.

CamEvent (IControlChannel.h)

tower, camera (RGB/ACR/NIR), heading_decideg (yaw×10), pitch_decideg (pitch×10), timestamp_ms. Serialized to the CamEvent JSON payload (see mqtt-api.md).

Frame (ICameraSource.h)

Owned pixel buffer + width, height, channels (1 or 3), timestamp_ms, cam_id.

ImuSample (MtiProtocol.h)

One decoded Xsens MTi reading: temp_c (°C), acc[3] (m/s², incl. gravity), gyr[3] (rad/s), mag[3] (a.u., earth-normalized), roll_deg (180..180), pitch_deg (90..90), yaw_deg (0..360 heading — the MTi's native 180..180 is shifted by parseMTData), sample_counter. gimbal calib phase-unwraps the swept yaw (unwrapNear) so a sweep crossing 0/360 still fits a clean line.

On-disk artifacts

Artifact Path Format
Captured images <output_dir>/<RGB|ACR|NIR>/<unix_ms>.jxl JPEG XL, rotated 90° CCW
Demo placeholder bin/x64/Release/test_smoke.jxl copied verbatim in demo mode
Diagnostics log <data_dir>/fire_gimbal_control/logs/diag_<ts>.log raw DG stream + parsed summary
Calibration log <data_dir>/fire_gimbal_control/logs/calib_<ts>.log per-axis samples + the least-squares fit

Diagnostics/calibration results are also surfaced live in the TUI (activity strip + gimbal g view) and applied to the running session's geometry; other state lives in memory.