# Build & Setup

The project builds with **CMake** (≥ 3.20) and a C++17 compiler. The build is split so the SDK-independent
core and the development (mock) build work on any machine; the proprietary/heavy dependencies are optional.

## Build options

| Option | Default | Effect |
|--------|---------|--------|
| `WITH_VIMBA` | `ON` | Build the Allied Vision Vimba X camera source. `OFF` → mock cameras only (no SDK needed). |
| `WITH_MQTT` | `ON` | Build the Eclipse Paho MQTT channel (fetched via FetchContent). `OFF` → null channel only. |
| `BUILD_TESTING` | `OFF` | Build the doctest unit tests (fetches doctest). |

```bash
# Full build (requires Vimba X SDK installed + network for Paho)
cmake -B build
cmake --build build                    # -> build/fire_gimbal_control

# Development build: no proprietary SDKs, no broker
cmake -B build -DWITH_VIMBA=OFF -DWITH_MQTT=OFF
cmake --build build

# With tests
cmake -B build -DWITH_VIMBA=OFF -DWITH_MQTT=OFF -DBUILD_TESTING=ON
cmake --build build && ctest --test-dir build --output-on-failure
```

CMake exports `compile_commands.json` into the build dir for clangd/IDEs.

## Dependencies

| Dependency | Needed for | How it's provided |
|------------|-----------|-------------------|
| **CMake ≥ 3.20**, g++/clang with C++17 | always | system package (`cmake`, official repo) |
| **OpenCV** (`core`, `highgui`, `imgproc`) | image rotate/display | `find_package(OpenCV)` — system package |
| **libjxl** (`libjxl`, `libjxl_threads`) | JPEG XL encoding | pkg-config — system package |
| **Boost** (`program_options`; header-only Asio) | CLI parsing, serial I/O | `find_package(Boost CONFIG)` — system package |
| **Threads** | concurrency | system |
| **Eclipse Paho MQTT C/C++** | MQTT (`WITH_MQTT=ON`) | **FetchContent** from official upstream (no AUR / system install) |
| **Allied Vision Vimba X SDK** | cameras (`WITH_VIMBA=ON`) | **proprietary**, install manually (see below) |

On Arch/Manjaro the system deps are roughly:

```bash
sudo pacman -S cmake opencv libjxl boost
```

(Debian/Ubuntu equivalents: `cmake build-essential libopencv-dev libjxl-dev libboost-all-dev`.)

### Eclipse Paho MQTT (FetchContent, no AUR)

When `WITH_MQTT=ON`, CMake downloads and builds Paho MQTT C and C++ from the **official Eclipse repos**
([cmake/Paho.cmake](../cmake/Paho.cmake)), pinned by tag. This keeps the dependency off the AUR. For maximum
integrity, pin `PAHO_C_TAG`/`PAHO_CPP_TAG` to a commit SHA or switch to a hash-verified release tarball. The
first configure needs network access.

### Allied Vision Vimba X SDK (proprietary)

`VmbC`/`VmbCPP` are not in any package manager. Download the Vimba X SDK from Allied Vision
(<https://www.alliedvision.com/en/products/software/vimba-x-sdk/>) and point CMake at it:

```bash
cmake -B build -DVMB_HOME=/opt/VimbaX_2024-1
# or: export VIMBA_X_HOME=/opt/VimbaX_2024-1
```

[cmake/FindVmb.cmake](../cmake/FindVmb.cmake) locates the headers/libs and creates `Vmb::VmbC` / `Vmb::VmbCPP`.
If the SDK is absent, build with `-DWITH_VIMBA=OFF` to get a mock-only binary.

## Host setup (for a real run)

1. **Serial device** — the motor controller must appear at the configured `[Serial] device` (default
   `/dev/ttyACM0`) at the configured baud. Add your user to `dialout` for non-root access:
   ```bash
   sudo usermod -aG dialout "$USER"   # re-login afterwards
   ```
   If the port can't be opened the program logs an error and continues (degraded, no telemetry).
2. **Cameras** — connect the Allied Vision cameras and confirm Vimba X sees them. Camera IDs in `config.ini`
   must match (GigE IP like `192.168.11.101`, host NIC on that subnet; or USB `DEV_...`).
3. **MQTT broker** — reachable at `[Network] zkms_server_ip` with the credentials (from `$FGC_MQTT_USER`/
   `$FGC_MQTT_PW` or the config). Unlike the old version, the program **no longer exits** if MQTT is
   unavailable — it logs a warning and continues. Use `--no-mqtt` to skip MQTT entirely.

## Run

```bash
scripts/run.sh --start                                   # real deployment
scripts/run.sh --init --start                            # find endstops, then start
scripts/run.sh --mock-serial --mock-camera --no-mqtt --start   # dev, no hardware
```

[scripts/run.sh](../scripts/run.sh) locates the binary relative to itself, and
[scripts/fire-gimbal-control.service](../scripts/fire-gimbal-control.service) is a systemd unit template
(uses `WorkingDirectory` + `FGC_CONFIG`, so no paths are hardcoded in the binary).

## Directory layout

```
build/                 CMake build output (gitignored)
include/fgc/, src/     headers and implementations (see modules-reference.md)
tests/                 unit tests
config/config.example.ini   template (copy to config.ini)
```
