diff --git a/README.md b/README.md index 8dfa26ac..faa732bf 100644 --- a/README.md +++ b/README.md @@ -1,160 +1,116 @@ # EDControlRoom -Multiplatform Elite Dangerous command-and-routine tooling focused on a shared runtime across macOS, Windows, and Linux. The active runtime is live-validated on macOS with Elite running through CrossOver by myself, @NicholasClooney, and the Windows path is now also live-validated by community member CMDR VRYAE. Linux remains unvalidated. +[![Tests](https://github.com/TheClooneyCollection/EDControlRoom/actions/workflows/tests.yml/badge.svg)](https://github.com/TheClooneyCollection/EDControlRoom/actions/workflows/tests.yml) +[![Discord](https://img.shields.io/badge/Discord-join%20chat-5865F2?logo=discord&logoColor=white)](https://discord.gg/73YSUBhfRG) -The current operator surface is [`control_room.py`](control_room.py). The project is not a hands-off flight bot; it is a live runtime and routine stack built around journal parsing, bindings lookup, synthetic input, and early workflow automation. +Multiplatform Elite Dangerous command-and-routine tooling. It handles the repetitive station-side loop of trading and hauling so the commander can stay focused on the parts that still benefit from human attention. It is **not** a hands-off flight bot. -![ED Control Room](docs/assets/control-room.png) - -See [docs/status/README.md](docs/status/README.md) for the maintained status entrypoint, area handoff files, validation notes, and next recommended work. +Live-validated on **macOS** (Elite through CrossOver) and **Windows** (community-validated by CMDR VRYAE). **Linux** paths exist in the code but are not yet validated. ## Contents -- [Start Here](#start-here) -- [Control Room Highlights](#control-room-highlights) -- [Haul Workflow](#haul-workflow) -- [Current Surface](#current-surface) -- [Primary Entrypoints](#primary-entrypoints) -- [Platform Validation](#platform-validation) -- [Galaxy Map Binding Requirement](#galaxy-map-binding-requirement) -- [Bindings Utility](#bindings-utility) -- [Repo Layout](#repo-layout) -- [Docs Map](#docs-map) +- [The Idea](#the-idea) +- [What You Get](#what-you-get) +- [Quick Start](#quick-start) +- [Documentation](#documentation) - [Development](#development) +- [Repo Layout](#repo-layout) +- [Contributing](#contributing) +- [License](#license) -## Start Here - -- run `uv sync` -- run `uv run python3 control_room.py` -- Important Note: - - after you fire off a ship-affecting command, make sure to switch back to Elite Dangerous; EDControlRoom works by sending keyboard input to the game window - - those commands wait `5` seconds by default, so you have time to switch back to Elite before the first key press - - if you are remotely connected to the shell and do not need that safety pause, use `instant` in Control Room to toggle the delay off or back on - -Once you have control room up and running: -- use `haul` to haul from A <-> B as the main end-to-end workflow -- edit ignored local `haul.toml` and run `haul load` if you want one text-editable saved haul route instead of stepping through the prompt each time -- run `home set ` once if you want a one-word reusable route command later via `home`; if Control Room already knows your current system, bare `home set` also works -- for setup details, platform-specific notes, and more commands, continue to [docs/getting-started/quickstart.md](docs/getting-started/quickstart.md) -- use [docs/operators/control-room.md](docs/operators/control-room.md) for day-to-day operation -- use [docs/operators/bindings-files.md](docs/operators/bindings-files.md) for `.binds` backup / restore / preset apply - -## Control Room Highlights - -- `control_room.py` is the primary operator surface -- `haul` is the strongest current operator flow and runs the active two-way haul loop -- `replay` / `Ctrl-R` reopens recent commands, including haul setups -- one saved default haul setup persists across restarts -- Control Room mirrors consumed journal events into `artifacts/control-room.log` -- after you fire off a ship-affecting command, switch back to Elite while the default `5` second launch delay runs -- `instant` toggles that delay on or off for future commands when you are operating from a remote shell session or otherwise do not need the safety pause - -Interrupt behavior during `haul` is haul-aware: the first `Ctrl-C` or `Ctrl-D` queues a stop after the current station-1 return sale and before the next buy. A second interrupt cancels immediately. +## The Idea -## Haul Workflow +A co-pilot, not an autopilot. You stay focused on flying; EDControlRoom takes over anything that lives behind a game menu. -`haul` is the strongest current end-to-end routine and the clearest example of what the active runtime is for. +The flagship is the **two-way haul routine**. When your ship drops near a station, it handles the boring bits end to end: request docking, work through station services, sell, refuel and repair, buy the return cargo, set the next-leg route, undock, clear mass lock, and prime the FSD. When the drive is primed it uses TTS to call the commander by title or name and announce the ship is ready to jump — that is your cue to take over for alignment and the next jump. -It is built to take the boring bits off the commander: from the moment you drop near a station, it handles the repeatable station-side work for you, including requesting docking, working through station services, buying or selling cargo, refuel and repair steps, setting the route for the next leg, leaving the station, clearing mass lock, and then priming the FSD automatically. +That makes it a direct fit for high-volume A↔B cargo work like community goal loops or long chill hauls, where the station-to-station cycle is the part worth automating and human attention is better spent on flying. -There is no auto-alignment. Instead, once the ship is clear and the drive is primed, EDControlRoom uses TTS to call the commander by title or name and say the ship is ready to jump, which is the cue for commanders to take over for alignment and the next jump. +**See it in action:** [live stream demo — co-pilot handling a station cycle](https://www.youtube.com/live/YKbz7xtc22Q?t=6014s) -That makes it directly useful for high-volume A-to-B cargo work such as community goal hauling loops, where the repetitive station-to-station trading cycle is the part worth automating and the commander can stay focused on the parts that still benefit from human attention. +Hauling in VR with EDControlRoom's help — click to watch on YouTube -Around that primary flow, the active routine surface also includes `dock`, `undock`, `jump`, `buy`, `sell`, `dest`, and `home`. +## What You Get -If you want a reusable route without stepping through the interactive haul prompt each time, edit ignored local `haul.toml` in the repo root and run `haul load` from Control Room. The operator doc includes a concrete example profile. +A terminal Control Room with TTS callouts, a LAN web frontend for haul dashboard / search / Spansh routing, and journal-driven `dock`, `undock`, `jump`, `buy`, `sell`, `dest`, `home`. -These are built to be manually exercised against a live Elite session, not left unattended. +_(Expand / click the following sections to see the screenshots.)_ -## Current Surface +
+Terminal Control Room (TUI) — ship status, activity log, market, and haul session, with TTS callouts. -What works today: +- Live panels: SHIP STATUS (commander, system, station, fuel, cargo, FSD target), ACTIVITY log, and MARKET table from `Market.json`. +- Full command bar for `dock`, `undock`, `jump`, `buy`, `sell`, `dest`, `home`, `travel`, `market ...`. +- Start haul work from the command bar: `haul [commodity]`, `haul start`, `haul load`, `haul search [system]`, `haul search url `, `haul route `, `multi_leg_haul `. +- `pause` / `resume` an active two-way haul; `stop` and `new_session` control the persisted session timer / profit. +- `Ctrl-R` reopens replay / command history; `Ctrl-C` interrupts (haul-aware safe stop first, cancel on second). +- Speaks TTS callouts locally, e.g. "commander, ship ready to jump" at the end of a leg. -- shared journal parsing, bindings lookup, and platform input/runtime plumbing across supported targets -- live-validated operator paths on macOS via CrossOver and on Windows via community testing from CMDR VRYAE -- journal-driven `haul`, `jump`, `dock`, `undock`, `buy`, `sell`, and `dest` flows -- a standalone `multi_leg_haul` / `mult` flow for finite multi-hop trade routes from our JSON schema or Spansh results -- a live Control Room TUI with ship status, activity log, market panel, replay history, saved default haul setup, and repo-local journal-event logging +Terminal Control Room TUI +
-What is not done: +
+Web dashboard — two-way haul control with live session stats and routine progress. -- the legacy CV-driven align loop is still not ported into the active runtime +- Quick stats strip: home system, current system, destination, cargo, routine, completed runs, session profit. +- Active routine board with the five haul stages (Buy, Undock, Depart, Transit, Sell) plus elapsed, current / accumulated credits, and cargo moved. +- Active route panel: jumps remaining, LY remaining, boosts remaining for the dispatched Spansh route. +- Header controls: **Pause**, **Resume**, **Stop after run**, **Stop now**, **Save** the current haul as the default, **Reconnect**, and **Instant off** for the 5-second safety delay. -## Primary Entrypoints +Web dashboard with haul session stats +
-- `uv run python3 control_room.py` -- `uv run python3 tools/run_routine.py --routine haul_loop` - This is the two-way haul routine used by Control Room. -- `uv run python3 tools/diagnostics.py` -- `uv run python3 tools/ship_controls.py --action SetSpeedZero --delay-seconds 3` -- `uv run python3 tools/bindings_files.py` - Lists, backs up, restores, and can replace the active `.binds` file from shipped presets. +
+Haul search — Inara-backed profitable route finder with one-click dispatch. -## Platform Validation +- Filter by origin (and optional destination), max route distance with presets, station distance, cargo capacity, profit metric, and min supply / demand. +- Results sort by profit / hour or profit / trip and show cargo, both stations, distance, and route LY. +- **Start route** hands the selected pair to the two-way haul routine; **Set destination** just routes there; **Travel assist** flies to an arbitrary system + station without hauling. +- Same search is reachable from the TUI via `haul search [system]` and `haul search url `; `haul route ` picks a numbered result. +- Note: v1 excludes surface / land settlements — station and carrier routes only. -- macOS: live-validated with Elite running through CrossOver by myself, @NicholasClooney -- Windows: live-validated by community member CMDR VRYAE -- Linux: runtime paths exist, but no live validation yet +Web haul search with Inara route results +
-## Galaxy Map Binding Requirement +
+Spansh route — fetch a Spansh route and compare it side-by-side with the in-game route. -The current galaxy-map automation depends on Elite having arrow-key secondary -bindings on these four actions: +- Inputs: from / to system, jump range (LY, unladen), efficiency, supercharge mode, optional final station, all-in-one navroute wait, and compare retries. From, jump range, and supercharge mode auto-fill from live ship state (current system + Loadout event); wait / retries auto-fill from server config. +- **Fetch Spansh** to pull a route, **Set in-game route** to plot it in Elite via the galaxy map, **Compare** to diff Spansh vs the plotted route jump-by-jump, or **All in one** to run the full flow. +- **Switch to Spansh** starts the standalone Spansh route runner: it flies the fetched route waypoint by waypoint, and every time you arrive at a waypoint it automatically sets the galaxy map to the next one. +- Route detail table shows system, neutron flag, +LY per jump, and cumulative total for both routes side by side. Dashboard's Active route panel tracks jumps remaining / LY remaining / boosts while the runner is active. -- `UI_Up` -> `UpArrow` -- `UI_Down` -> `DownArrow` -- `UI_Left` -> `LeftArrow` -- `UI_Right` -> `RightArrow` +Spansh route fetch and comparison panel +
-Keep your normal primary bindings as needed, but make sure those arrow-key -secondaries are present in the live `.binds` file. On the current Elite setup, -`W/A/S/D` pans the galaxy map view, while arrow-key `UI_*` bindings move the -map/menu cursor. Without those secondary arrow bindings, `dest` / galaxy-map -automation will not navigate the map menus correctly. +## Quick Start -## Bindings Utility +```sh +uv sync +uv run python3 control_room.py lan +``` -`tools/bindings_files.py` is the operator helper for `.binds` file management. +`lan` starts a headless server and prints the bound URL on startup (e.g. `http://192.168.1.50:8765`). Open that URL in a browser to use the web frontend — ideally on a **secondary device** (tablet, phone, or another laptop) so Elite can stay the foreground application on the game machine. Routines drive Elite by key input, and alt-tabbing away from the game window will break them. -Examples: +`lan` does **not** run a TUI or speak TTS. For TTS callouts, attach a TUI client from another terminal (same machine or another LAN box). Paste the URL `lan` printed, or use the shorter `host:port` form: ```sh -uv run python3 tools/bindings_files.py -uv run python3 tools/bindings_files.py backup -uv run python3 tools/bindings_files.py restore -uv run python3 tools/bindings_files.py apply-default +uv run python3 control_room.py connect http://:8765/ --token edcr +uv run python3 control_room.py connect :8765 --token edcr ``` -See [docs/operators/bindings-files.md](docs/operators/bindings-files.md) for the full command surface. +Both the server and the web page default to token `edcr`, so no `--token` override is needed unless you want a different one. -Note: `apply-default` is implemented and covered by unit tests, but it has not yet been live-validated against a real Elite session. If it does not behave as expected on your setup, please open an issue or report the exact command and resulting file state. +**Before your first run:** set arrow-key secondaries on `UI_Up / UI_Down / UI_Left / UI_Right` in Elite. See [docs/user/bindings-setup.md](docs/user/bindings-setup.md). -## Repo Layout +Full walkthrough: [docs/user/getting-started.md](docs/user/getting-started.md). -- `control_room.py`: primary operator surface kept at the repo root -- `tools/`: supported auxiliary CLIs such as `run_routine.py`, `diagnostics.py`, `ship_controls.py`, and bindings helpers -- `edap/`: active runtime code -- `tools/scratch/`: exploratory probes and one-off validation helpers -- `archive/legacy-windows/`: Windows-era behavior reference code, kept for historical context only - -## Docs Map - -- [docs/getting-started/quickstart.md](docs/getting-started/quickstart.md) - Setup plus first commands. -- [docs/operators/control-room.md](docs/operators/control-room.md) - Main operator workflow, haul behavior, replay/history, and interrupt semantics. -- [docs/operators/bindings-files.md](docs/operators/bindings-files.md) - `.binds` backup, restore, and shipped preset apply flows. -- [docs/operators/input-timing.md](docs/operators/input-timing.md) - Human-style delay, hold, and typing randomization settings. -- [docs/operators/market-timing.md](docs/operators/market-timing.md) - Market `buy ... max` hold tuning and sell `MAX` rapid-tap configuration. -- [docs/operators/manual-journal-routine-testing.md](docs/operators/manual-journal-routine-testing.md) - Low-level routine validation outside Control Room. -- [docs/diagnostics/cli-reference.md](docs/diagnostics/cli-reference.md) -- [docs/diagnostics/bindings-reference.md](docs/diagnostics/bindings-reference.md) -- [docs/README.md](docs/README.md) +## Documentation + +- [docs/user/](docs/user/): install, bindings, getting started, haul workflow, commands, troubleshooting. +- [docs/operators/](docs/operators/): operator references (control room, remote / multi-client, bindings files, input and market timing). +- [docs/diagnostics/](docs/diagnostics/): CLI and bindings reference for diagnostics. +- [docs/status/README.md](docs/status/README.md): maintained project status entrypoint. ## Development @@ -164,15 +120,26 @@ Use the repo `uv` environment for tests: uv run python3 -m unittest discover -s tests ``` -Development now ships as rolling updates on `main` rather than through a long-lived `dev` branch. For a single-maintainer project, that keeps the workflow lighter and avoids the overhead of constantly promoting work between branches. The tradeoff is that `main` may sometimes include unfinished or unpolished changes between stability markers, so stable features and releases are communicated through tags plus clear notes about feature completeness and known issues. +`main` is the active rolling-update branch; stable features and releases are marked with semantic version tags like `v1.22.0`. Commits use Conventional Commits (`feat:`, `fix:`, `refactor:`, `docs:`, `chore:`). + +## Repo Layout + +- `control_room.py`: primary operator surface at the repo root. +- `tools/`: supported auxiliary CLIs (`run_routine.py`, `diagnostics.py`, `ship_controls.py`, bindings helpers). +- `edap/`: active runtime code. +- `tools/scratch/`: exploratory probes and one-off validation helpers. +- `archive/legacy-windows/`: historical Windows-era reference code. + +## Contributing + +Issues and PRs welcome. Before opening a PR: -Releases are cut manually. The release flow is: prepare the versioned release changeset on `main`, run the full test suite, create a semantic version tag like `v1.8.0`, push the tag, and then publish the GitHub release with concise operator-facing notes about the stable capabilities and known constraints in that version. +- Follow Conventional Commits for commit messages. +- Run the test suite: `uv run python3 -m unittest discover -s tests`. +- If your change touches user-visible behavior, update the relevant doc under [docs/user/](docs/user/) or [docs/operators/](docs/operators/). -For commits, use Conventional Commits. +Bug reports and feature ideas are best filed as GitHub issues with journal / config details when relevant. Chat and questions: [Discord](https://discord.gg/73YSUBhfRG). -Examples: +## License -- `feat: add config loader` -- `refactor: split platform adapters from autopilot logic` -- `docs: update macos roadmap` -- `fix: validate missing journal path` +MIT. See [LICENSE](LICENSE). This project traces back to the original ED autopilot work by SKai2 and is being maintained and reshaped for the macOS-first Control Room direction. diff --git a/docs/README.md b/docs/README.md index b0b4f009..78d3cd0d 100644 --- a/docs/README.md +++ b/docs/README.md @@ -1,33 +1,39 @@ # Docs Index -## Start Here +## Start Here (Users) -- [getting-started/quickstart.md](getting-started/quickstart.md): setup, first checks, and first runtime commands -- [operators/control-room.md](operators/control-room.md): primary day-to-day operator guide -- [operators/bindings-files.md](operators/bindings-files.md): `.binds` backup, restore, and preset apply +- [user/install.md](user/install.md): install Python, `uv`, platform prerequisites. +- [user/bindings-setup.md](user/bindings-setup.md): Elite bindings required before first run. +- [user/getting-started.md](user/getting-started.md): recommended TUI + web LAN setup. +- [user/haul-workflow.md](user/haul-workflow.md): end-to-end haul walkthrough plus `haul.toml`. +- [user/commands-reference.md](user/commands-reference.md): every Control Room command. +- [user/troubleshooting.md](user/troubleshooting.md): input, journal, and bindings checks. -## Operator Guides +## Operator Reference -- [operators/input-timing.md](operators/input-timing.md): human-style delay, hold, and typing randomization settings -- [operators/market-timing.md](operators/market-timing.md): market buy-hold tuning and sell max rapid-tap settings -- [operators/manual-journal-routine-testing.md](operators/manual-journal-routine-testing.md): low-level manual validation outside Control Room +- [operators/control-room.md](operators/control-room.md): run modes, panels, and haul behavior specifics. +- [operators/control-room-remote.md](operators/control-room-remote.md): multi-client / observer semantics. +- [operators/bindings-files.md](operators/bindings-files.md): `.binds` backup, restore, and shipped preset apply. +- [operators/input-timing.md](operators/input-timing.md): human-style delay, hold, and typing randomization. +- [operators/market-timing.md](operators/market-timing.md): market buy-hold and sell-max tuning. +- [operators/manual-journal-routine-testing.md](operators/manual-journal-routine-testing.md): low-level manual validation outside Control Room. ## Diagnostics -- [diagnostics/cli-reference.md](diagnostics/cli-reference.md): utility and diagnostics commands -- [diagnostics/bindings-reference.md](diagnostics/bindings-reference.md): Elite binding names that matter to this runtime +- [diagnostics/cli-reference.md](diagnostics/cli-reference.md) +- [diagnostics/bindings-reference.md](diagnostics/bindings-reference.md) ## Maintainer Handoff -- [status/README.md](status/README.md): maintained status entrypoint and area map -- [status/](status/): split current-state handoff files by durable area -- [iteration-logs/](iteration-logs/): per-iteration maintained notes, one file per substantive work session -- [iteration-archive.md](iteration-archive.md): generated archive of iteration logs, refreshed whenever iteration-log changes are being committed, pushed, or sent for review -- [status-archive.md](status-archive.md): legacy archived validation and older pre-migration handoff notes +- [status/README.md](status/README.md): maintained status entrypoint and area map. +- [status/](status/): split current-state handoff files by durable area. +- [iteration-logs/](iteration-logs/): maintained per-session notes. +- [iteration-archive.md](iteration-archive.md): generated archive, refreshed alongside iteration-log changes. +- [status-archive.md](status-archive.md): legacy archived validation and pre-migration handoff notes. ## Deep Reference -- [plans/](plans/): implementation plans -- [research/](research/): deeper research and behavior-reference material -- [design/](design/): design notes -- [devlog/](devlog/): older session-style notes +- [plans/](plans/): implementation plans. +- [research/](research/): deeper research and behavior-reference material. +- [design/](design/): design notes. +- [devlog/](devlog/): older session-style notes. diff --git a/docs/assets/haul-search.png b/docs/assets/haul-search.png new file mode 100644 index 00000000..cf9ca76b --- /dev/null +++ b/docs/assets/haul-search.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:28561c11d208bdf2f3448d4e913d1868ddcd653f9c7cab1a196a0d53a345fd40 +size 702043 diff --git a/docs/assets/haul-vr.png b/docs/assets/haul-vr.png new file mode 100644 index 00000000..ea1bb455 --- /dev/null +++ b/docs/assets/haul-vr.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:feeb4c75e12a3ff9b6fba7fb589bc554bc86302fbde4780b084051d4df142c21 +size 1987847 diff --git a/docs/assets/quick-stats.png b/docs/assets/quick-stats.png new file mode 100644 index 00000000..def63049 --- /dev/null +++ b/docs/assets/quick-stats.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:30e4b1916eb1c09cb202920ad491652ce3ed0df1bb7e48f362db785cbf0a9252 +size 271672 diff --git a/docs/assets/spansh-routes.png b/docs/assets/spansh-routes.png new file mode 100644 index 00000000..cd988eba --- /dev/null +++ b/docs/assets/spansh-routes.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8c37358c2809c84bcc80f12adce98d6bb5df96ca30adca5d061ec88776571a88 +size 166321 diff --git a/docs/assets/tui-control-room.png b/docs/assets/tui-control-room.png new file mode 100644 index 00000000..b844d1b7 --- /dev/null +++ b/docs/assets/tui-control-room.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:d52eedac70451d3bbc3f20d4f08e26ef1805be51a3cf180d3507f38cbeede069 +size 412209 diff --git a/docs/getting-started/quickstart.md b/docs/getting-started/quickstart.md deleted file mode 100644 index e81381a7..00000000 --- a/docs/getting-started/quickstart.md +++ /dev/null @@ -1,142 +0,0 @@ -# Quickstart - -## Setup - -Shipped defaults live in `defaults/*.toml`. `config.example.toml` is an override skeleton. Create a local `config.toml` only if you want overrides; EDControlRoom auto-loads it when present, and otherwise falls back to shipped defaults plus auto-detection. - -When you do create `config.toml`, keep it minimal: - -- Set `paths.journal_dir` and `paths.bindings_file` only if auto-detection is not enough on this machine. -- Leave `runtime.platform` unset unless you want to make the backend choice explicit in a shared config. When omitted, it defaults to the host OS. - -### macOS + CrossOver - -1. Make sure Terminal has macOS Accessibility permission, and Screen Recording permission if you plan to use capture-based diagnostics. -2. Start Elite Dangerous through CrossOver. - -### Windows with `uv` - -1. Install Python 3.12 and `uv`. -2. Run `uv sync`. -3. Start Elite Dangerous. - -### Windows without `uv` - -1. Install Python 3.12. -2. Create a virtual environment: - -```sh -python -m venv .venv -``` - -3. Activate it: - -```sh -.venv\Scripts\activate -``` - -4. Install runtime deps: - -```sh -pip install -r requirements.txt -``` - -5. Start Elite Dangerous. - -### Linux - -1. Install Python 3.12 and `uv`. -2. Install `xdotool` if you want synthetic key input support. -3. Start Elite Dangerous through Steam/Proton. - -On Linux, prefer explicit `paths.journal_dir` and `paths.bindings_file` only when the built-in Steam Proton probing for app ID `359320` is not enough on this machine. - -Minimal example: - -```toml -[paths] -journal_dir = "" -bindings_file = "" - -[tts] -title_mode = "custom" -title = "captain" -``` - -Linux input is currently implemented through `xdotool`, so treat it as X11-oriented and verify it locally before relying on routines. Wayland behavior is unverified. - -## Start Control Room - -Control Room is the primary operator surface for current routine work, so start there first after installation. - -With `uv`: - -```sh -uv run python3 control_room.py -``` - -If your Windows shell does not provide `python3`, use `uv run python ...` instead. - -Without `uv`: - -```sh -python control_room.py -``` - -For day-to-day usage, haul behavior, replay/history, and interrupt semantics, see [../operators/control-room.md](../operators/control-room.md). - -If you want a reusable two-station haul setup in a text file, edit ignored repo-root `haul.toml` and use `haul load` in Control Room. See the example in [../operators/control-room.md](../operators/control-room.md). - -If you want a reusable destination, run `home set ` once in Control Room. If the current system is already known, bare `home set` also works. Either form writes `control_room.home_system` into config so later you can route with plain `home`. - -## If Something Is Not Working - -Use these checks only when you need to troubleshoot input, journal detection, or game integration. - -With `uv`: - -```sh -uv run python3 tools/watch_journal.py -uv run python3 tools/ship_controls.py --action SetSpeedZero --delay-seconds 3 -``` - -If your Windows shell does not provide `python3`, use `uv run python ...` instead. - -Without `uv`: - -```sh -python tools/watch_journal.py -python tools/ship_controls.py --action SetSpeedZero --delay-seconds 3 -``` - -- `tools/watch_journal.py` tails the Elite journal and prints events as they arrive. Run it only while the game is open, otherwise nothing new will appear. -- `tools/ship_controls.py --action SetSpeedZero --delay-seconds 3` waits three seconds, then presses the key currently bound to Elite's `SetSpeedZero` action. Expect your throttle-zero keybind to fire in game. - -If journal or bindings auto-detection still looks wrong after that, add explicit `paths.journal_dir` and `paths.bindings_file` overrides in `config.toml`. - -## Routine Harness - -```sh -uv run python3 tools/run_routine.py --routine jump --delay-seconds 5 -uv run python3 tools/run_routine.py --routine dock --delay-seconds 5 --log-events -uv run python3 tools/run_routine.py --routine haul_loop -``` - -`haul_loop` is the current two-way haul routine and matches the Control Room haul path. - -Windows equivalents: - -```sh -uv run python tools/run_routine.py --routine jump --delay-seconds 5 -python tools/run_routine.py --routine jump --delay-seconds 5 -``` - -Linux equivalent: - -```sh -uv run python3 tools/run_routine.py --routine jump --delay-seconds 5 -``` - -For current supported manual validation flows, see [../operators/manual-journal-routine-testing.md](../operators/manual-journal-routine-testing.md). - -For `.binds` backup, restore, or shipped preset apply, see [../operators/bindings-files.md](../operators/bindings-files.md). diff --git a/docs/operators/control-room-remote.md b/docs/operators/control-room-remote.md index 177a16b2..891bffe3 100644 --- a/docs/operators/control-room-remote.md +++ b/docs/operators/control-room-remote.md @@ -1,12 +1,12 @@ -# Control Room Remote Observer Mode +# Control Room Multi-Client Mode -This document covers the current `serve` / `connect` split for Control Room. +This document covers the `serve` / `connect` model when **more than one client** connects to the same Control Room server (e.g. TUI on the runtime host plus a browser plus a second TUI on another laptop). -For normal embedded local use, start with [control-room.md](control-room.md). +For the recommended single-user LAN setup (one `lan` server + one browser + local TUI for TTS), see [../user/getting-started.md](../user/getting-started.md). For the operator reference on run modes, see [control-room.md](control-room.md). ## Purpose -Use remote observer mode when one machine should own the runtime and one or more other clients should watch or operate it over the LAN. +Use multi-client mode when one machine owns the runtime and one or more additional clients should watch or take over control over the LAN. Current model: @@ -20,17 +20,14 @@ Current model: ## Commands -Start a server on the machine that owns the Elite runtime: +Server run modes are documented in [control-room.md](control-room.md#run-modes). A quick summary for multi-client setups: ```sh -uv run python3 control_room.py serve --token 1001 -uv run python3 control_room.py local --token 1001 -uv run python3 control_room.py lan --port 8765 --token 1001 -uv run python3 control_room.py serve --lan --port 8765 --token 1001 +uv run python3 control_room.py lan --token 1001 uv run python3 control_room.py serve --host 0.0.0.0 --port 8765 --token 1001 ``` -Use `local` to bind loopback (`127.0.0.1`) explicitly. Use `lan` or `serve --lan` when clients should connect from the same network and you want Control Room to bind to the detected non-loopback IPv4 address, preferring RFC1918 addresses and skipping VPN-owned ranges like `198.18/15` (Cloudflare WARP) and `100.64/10` (CGNAT). Use `--host` for an explicit bind address, including `0.0.0.0` for all interfaces. +Pass an explicit `--token` when you want to override the default `edcr`. All clients must use the same token. Connect from a client: diff --git a/docs/operators/control-room.md b/docs/operators/control-room.md index 7db6d42e..9ff0149a 100644 --- a/docs/operators/control-room.md +++ b/docs/operators/control-room.md @@ -1,141 +1,63 @@ -# Control Room +# Control Room (Operator Reference) -`control_room.py` is the main live operator surface. +`control_room.py` is the main live operator surface. For the recommended day-to-day setup (TUI + web frontend on the LAN), see [../user/getting-started.md](../user/getting-started.md). For the haul workflow, see [../user/haul-workflow.md](../user/haul-workflow.md). For the full command list, see [../user/commands-reference.md](../user/commands-reference.md). -Run it with: +This page is the operator-reference view: run modes, panels, and the specifics of how Control Room behaves in a live session. + +## Run Modes ```sh -uv run python3 control_room.py -uv run python3 control_room.py --market aluminium -uv run python3 control_room.py serve --token 1001 -uv run python3 control_room.py local --token 1001 -uv run python3 control_room.py lan --token 1001 -uv run python3 control_room.py connect 192.168.1.50:8765 --token 1001 +uv run python3 control_room.py # embedded local TUI only +uv run python3 control_room.py --market aluminium # embedded local, pre-focused market +uv run python3 control_room.py local # server bound to 127.0.0.1 +uv run python3 control_room.py lan # server bound to detected LAN IPv4 (recommended) +uv run python3 control_room.py serve --host 0.0.0.0 --port 8765 +uv run python3 control_room.py connect 192.168.1.50:8765 --token edcr ``` -If `config.toml` exists in the repo root, EDControlRoom loads it automatically. Create one only when you need explicit overrides beyond the built-in auto-detection. - -EDControlRoom works by sending keyboard input to Elite Dangerous. After you fire off any command that should affect the ship or UI, switch back to the game window before the delay expires. +`lan` autodetects a non-loopback IPv4, preferring RFC1918 addresses and skipping VPN-owned ranges like `198.18/15` (Cloudflare WARP) and `100.64/10` (CGNAT). Use `--host` for an explicit bind, `0.0.0.0` for all interfaces. -![Control Room screenshot](../assets/control-room.png) +Access token defaults to `edcr` when `--token` is omitted; the built-in web page auto-fills the same default. Override on both ends if you want a different token. The TUI `connect` client requires an explicit `--token`. -## What It Is +If `config.toml` exists in the repo root, EDControlRoom loads it automatically. -- primary operator surface for current routine work -- best-supported end-to-end path is `haul` -- one routine runs at a time -- can also run as a LAN observer server or remote client; see [control-room-remote.md](control-room-remote.md) +For multi-client / operator-vs-observer semantics, see [control-room-remote.md](control-room-remote.md). ## Panels -- `SHIP STATUS`: commander, system, station, flight state, fuel, credits, cargo, `Destination` from `Status.json` (`system/body/name`), and journal `FSD target` -- `ACTIVITY`: live event log plus routine progress lines -- `MARKET`: commodity table from `Market.json`, with filtering and lock/unlock controls - -## Main Commands - -- `dock` -- `undock` -- `jump` -- `buy [N|max]` -- `sell` -- `sell [N|max]` -- `haul [commodity]` -- `multi_leg_haul ` -- `dest ` -- `set_dest ` -- `home` -- `home set ` - -## Haul +- `SHIP STATUS`: commander, system, station, flight state, fuel, credits, cargo, `Destination` from `Status.json` (`system/body/name`), and journal FSD target. +- `ACTIVITY`: live event log and routine progress lines. Startup writes version info; if update checks are enabled, so do release notifications. +- `MARKET`: commodity table from `Market.json` with filter and lock/unlock. -- `haul [commodity]` runs the active two-way haul loop used by `tools/run_routine.py --routine haul_loop` -- `haul load [path]` loads ignored repo-root `haul.toml` by default, or a custom TOML path if you provide one -- haul is aimed at commanders who want the station-side repetition handled for them: after a drop near station it requests docking, runs station services, buys or sells cargo, refuels, repairs, routes the next leg, launches, clears mass lock, and primes the FSD -- haul does not auto-align for the next jump; after station clearance it uses TTS to call the commander by title or name and announce that the ship is ready to jump as the handoff cue -- haul resumes from current journal and sidecar state rather than assuming a fresh start -- one default haul setup can be saved and reused across restarts -- `replay` / `Ctrl-R` is the quickest way to relaunch recent haul commands or rerun a saved pattern without retyping it +## Ship-Affecting Delay -### `haul.toml` Example +Commands that press keys into Elite wait `5` seconds before the first press so you can focus the game window. `instant`, `instant on`, `instant off` toggle that delay for future commands. Useful when you are remoted in and do not need the pause. -If you want one text-editable haul profile instead of walking through the interactive prompt each time, edit ignored repo-root `haul.toml` and run: +## Haul Behavior -```sh -haul load -``` - -Example: +For the workflow story, see [../user/haul-workflow.md](../user/haul-workflow.md). Behavior specifics: -```toml -[haul] -galaxy_map_settle = 2.0 -dock_timeout = 1200.0 - -[haul.station_1] -buying = "Aluminium" -name = "Pawelczyk Dock" -system = "Sol" -on_land = false - -[haul.station_2] -buying = "Bertrandite" -name = "Trevithick Dock" -system = "Achenar" -on_land = false -``` - -Notes: - -- `buying` is optional on either side, but at least one station must have a buy cargo configured. -- `on_land = true` tells haul to hand off after destination-system `SupercruiseExit` so you can finish a surface approach and resume after landing. -- `haul load some-other-file.toml` works if you want multiple named route files. +- `haul [commodity]` runs the two-way loop used by `tools/run_routine.py --routine haul_loop`. +- `haul load [path]` loads repo-root `haul.toml` by default. +- Resume is journal + sidecar based; no clean-state assumption. +- One default haul setup persists across restarts. +- `replay` / `Ctrl-R` relaunches recent haul commands. +- Interrupt: first `Ctrl-C` / `Ctrl-D` queues a stop at the next station-1 boundary after the return sale; second cancels immediately. ## Multi-Leg Haul -- `multi_leg_haul ` (alias `mult`) runs a standalone finite multi-leg haul route -- the route can come from our normalized JSON schema or directly from a Spansh trade-result payload / URL -- resume is still state-based: rerun the command and EDControlRoom re-derives the current stop/phase from journal, `Cargo.json`, `Market.json`, and the route definition -- the public schema intentionally excludes plan or execution state; see `docs/schemas/multi_leg_haul.schema.json` and `templates/multi_leg_haul.example.json` - -Interrupt behavior during `haul` is special: - -- first `Ctrl-C` or `Ctrl-D`: finish the current run and stop at station 1 after the return sale, before the next buy -- second `Ctrl-C` or `Ctrl-D`: cancel immediately - -## Other Commands - -- `market filter ` -- `market` -- `market clear` -- `market lock` -- `market unlock` -- `replay` -- `commands` -- `help [command]` -- `q`, `quit`, `exit` - -## Home Routing - -- `home` reuses the saved `control_room.home_system` value and then runs the normal `dest` flow, including the galaxy-map settle prompt. -- `dest home` is accepted as a destination alias for the saved home system. -- `home set ` updates that setting in the active config file so the next `home` command is one word. -- Bare `home set` uses the current ship system when Control Room already knows it from live journal/status state. -- `haul search home` uses the saved home system as the Inara search center. -- If Control Room started from the default `config.example.toml` fallback because repo-root `config.toml` did not exist yet, `home set` creates a minimal repo-root `config.toml` instead of editing the shipped example file. +`multi_leg_haul ` (alias `mult`) runs a standalone finite multi-leg route. Route input can come from the normalized JSON at `docs/schemas/multi_leg_haul.schema.json` (see `templates/multi_leg_haul.example.json`) or from a Spansh trade-result URL / payload. Resume state is re-derived from journal, `Cargo.json`, `Market.json`, and the route definition. The public schema intentionally excludes plan / execution state. -## Keybinds +## Persistence -- `Ctrl-R` opens replay/history from the command bar. -- `Ctrl-C` stops the app when idle. During `haul`, the first press requests a safe stop at the next station-1 boundary after the return sale, and the second press cancels immediately. -- `Ctrl-D` behaves the same as `Ctrl-C`. +- `.control_room_state.json`: cross-session command history and the saved default haul profile. +- `artifacts/control-room.log`: mirror of consumed journal events. -## Useful Behavior +## Related -- Ship-affecting commands wait `5` seconds before starting by default, so you have time to switch back to Elite before EDControlRoom sends any key presses. -- `instant`, `instant on`, and `instant off` control that default launch delay for future commands. This is mainly useful when you are remotely connected to the shell and do not need the normal safety pause. -- Startup writes version information into `ACTIVITY`, and when update checks are enabled it also tells you if a newer EDControlRoom release is available. -- In replay/history, typing applies a simple prefix filter and `Backspace` removes characters from that filter. -- `sell` with no explicit item falls back to `Cargo.json` if the in-memory cargo manifest is empty. -- Cross-session command history and one saved default haul profile are persisted in `.control_room_state.json` by default. -- Consumed journal events are mirrored into `artifacts/control-room.log`, so you can inspect what Control Room saw during a run. +- [../user/commands-reference.md](../user/commands-reference.md) +- [bindings-files.md](bindings-files.md) +- [input-timing.md](input-timing.md) +- [market-timing.md](market-timing.md) +- [manual-journal-routine-testing.md](manual-journal-routine-testing.md) +- [control-room-remote.md](control-room-remote.md) diff --git a/docs/user/README.md b/docs/user/README.md new file mode 100644 index 00000000..105f5e49 --- /dev/null +++ b/docs/user/README.md @@ -0,0 +1,12 @@ +# User Docs + +Start here if you want to run EDControlRoom. + +1. [install.md](install.md): install Python, `uv`, and platform prerequisites. +2. [bindings-setup.md](bindings-setup.md): required Elite Dangerous key bindings. Do this once before your first run. +3. [getting-started.md](getting-started.md): the recommended way to run EDControlRoom, using the TUI plus web frontend together. +4. [haul-workflow.md](haul-workflow.md): the end-to-end `haul` workflow, including `haul.toml`. +5. [commands-reference.md](commands-reference.md): every Control Room command in one place. +6. [troubleshooting.md](troubleshooting.md): what to check when input, journal, or bindings do not behave. + +Deeper operator references (input timing, market timing, `.binds` file management, remote/multi-client mode) live under [../operators/](../operators/). diff --git a/docs/user/bindings-setup.md b/docs/user/bindings-setup.md new file mode 100644 index 00000000..99bfcf30 --- /dev/null +++ b/docs/user/bindings-setup.md @@ -0,0 +1,33 @@ +# Elite Dangerous Bindings Setup + +EDControlRoom drives Elite by looking up your live `.binds` file and pressing whatever keys those actions are bound to. Two things need to be true before your first run. + +## Contents + +- [1. Arrow-Key Secondaries on the Menu Cursor (Required)](#1-arrow-key-secondaries-on-the-menu-cursor-required) +- [2. A Complete `.binds` File](#2-a-complete-binds-file) + +## 1. Arrow-Key Secondaries on the Menu Cursor (Required) + +Elite's galaxy map and menu navigation must have **arrow-key secondary bindings** on these four actions: + +| Action | Secondary key | +|------------|---------------| +| `UI_Up` | Up Arrow | +| `UI_Down` | Down Arrow | +| `UI_Left` | Left Arrow | +| `UI_Right` | Right Arrow | + +**Why:** on the default Elite bindings, `W A S D` is bound to pan the galaxy map view, not to move the menu cursor. If EDControlRoom uses `W A S D` for menu nav it will scroll the map instead of picking items, so it needs a separate arrow-key path that only moves the cursor. + +**How to set it:** in Elite go to Options -> Controls -> UI Mode. For each of the four actions above, click the empty **secondary** slot and press the matching arrow key. Keep whatever you have on the primary slot. + +Without these secondaries, `dest`, `home`, and the galaxy-map portion of `haul` will misnavigate the menus. + +## 2. A Complete `.binds` File + +EDControlRoom needs to find your active bindings file so it can look up action keys. Auto-detection covers standard installs (macOS CrossOver, Windows Frontier launcher, Steam / Proton). If it does not find yours, set `paths.bindings_file` explicitly in a repo-root `config.toml`. + +To inspect, back up, or apply a shipped bindings preset, see [../operators/bindings-files.md](../operators/bindings-files.md). + +Next: [getting-started.md](getting-started.md). diff --git a/docs/user/commands-reference.md b/docs/user/commands-reference.md new file mode 100644 index 00000000..546bc288 --- /dev/null +++ b/docs/user/commands-reference.md @@ -0,0 +1,75 @@ +# Control Room Command Reference + +Every command you can type in the TUI or web command bar. For the haul flow specifically, see [haul-workflow.md](haul-workflow.md). + +## Contents + +- [Movement and Routing](#movement-and-routing) +- [Cargo](#cargo) +- [Haul](#haul) +- [Market](#market) +- [Session](#session) +- [Key Bindings in the TUI](#key-bindings-in-the-tui) +- [Panels](#panels) +- [Files EDControlRoom Writes](#files-edcontrolroom-writes) + +## Movement and Routing + +- `dock` +- `undock` +- `jump` +- `dest ` — set destination via the galaxy map +- `set_dest ` — explicit form +- `home` — route to the saved home system +- `home set ` — save a home system +- `home set` — save the current system + +## Cargo + +- `buy [N|max]` +- `sell` +- `sell [N|max]` + +`sell` with no explicit item falls back to `Cargo.json` if the in-memory cargo manifest is empty. + +## Haul + +- `haul [commodity]` — the two-way haul loop. +- `haul load [path]` — load `haul.toml` from the repo root by default, or a custom path. +- `haul search home` — search Inara using the saved home system as origin. +- `multi_leg_haul ` (alias `mult`) — finite multi-leg route. + +## Market + +- `market` — show the market panel. +- `market filter ` — filter to a commodity. +- `market clear` — clear the filter. +- `market lock` / `market unlock` — hold or release the current view. + +## Session + +- `replay` (or `Ctrl-R`) — recent-command history with prefix filter. +- `commands` — list commands. +- `help [command]` — inline help. +- `instant`, `instant on`, `instant off` — toggle the 5-second safety delay for future commands. +- `q`, `quit`, `exit`. + +## Key Bindings in the TUI + +- `Ctrl-R` — open replay / history. +- `Ctrl-C` / `Ctrl-D` when idle — exit. During `haul`, first press queues a safe stop at the next station-1 boundary, second press cancels immediately. + +## Panels + +The TUI shows three panels driven by journal + status files: + +- **SHIP STATUS**: commander, system, station, flight state, fuel, credits, cargo, `Destination` from `Status.json`, and journal FSD target. +- **ACTIVITY**: live event log and routine progress lines. Startup writes version info here; if update checks are enabled, so do release notifications. +- **MARKET**: commodity table from `Market.json` with filter and lock/unlock. + +The web frontend shows the equivalent state plus the haul search and Spansh route panels described in [getting-started.md](getting-started.md). + +## Files EDControlRoom Writes + +- `.control_room_state.json` — cross-session command history and one saved default haul profile. +- `artifacts/control-room.log` — mirror of consumed journal events. diff --git a/docs/user/getting-started.md b/docs/user/getting-started.md new file mode 100644 index 00000000..ed09eb71 --- /dev/null +++ b/docs/user/getting-started.md @@ -0,0 +1,104 @@ +# Getting Started + +This is the recommended way to run EDControlRoom day to day: one process serves the runtime, you keep the terminal TUI open for TTS callouts, and you drive it from your browser. + +## Contents + +- [Before You Start](#before-you-start) +- [Start Control Room in LAN Mode](#start-control-room-in-lan-mode) +- [Open the Web Frontend](#open-the-web-frontend) +- [Attach a TUI for TTS](#attach-a-tui-for-tts) +- [The Five-Second Safety Delay](#the-five-second-safety-delay) +- [First Haul](#first-haul) +- [Stopping](#stopping) +- [Where To Go Next](#where-to-go-next) + +## Before You Start + +- Finished [install.md](install.md). +- Set the arrow-key secondaries described in [bindings-setup.md](bindings-setup.md). This is easy to skip and will silently break galaxy-map automation. +- Elite Dangerous is running. + +## Start Control Room in LAN Mode + +From the repo root: + +```sh +uv run python3 control_room.py lan +``` + +`lan` starts a headless server. Uvicorn logs the bound URL as it starts, something like: + +``` +Uvicorn running on http://192.168.1.50:8765 +``` + +That address is the web frontend. + +**Token.** With no `--token`, both the server and the built-in web page default to `edcr`, so the browser connects without you typing anything. Pass `--token ` on both ends if you want a different one. + +## Open the Web Frontend + +On any device on the same LAN, open the URL from the startup log in a browser (or `http://localhost:8765` from the same machine). This is the main operator surface. + +> **Recommended:** open the web frontend on a **secondary device** (second laptop, tablet, phone) rather than the machine running Elite. EDControlRoom drives Elite by sending key input to the game window, so **Elite must be the foreground application** while a routine runs. Alt-tabbing to a browser on the same machine steals focus and breaks the routine. A tablet or second monitor / device sidesteps that entirely. + +![Web quick stats](../assets/quick-stats.png) + +Top of the page is the two-way haul dashboard: home / current system, destination, cargo, session profit, and the five stages of the active haul routine (Buy, Undock, Depart, Transit, Sell). Header controls let you pause / resume / stop the routine and toggle the pre-command safety delay (**Instant off**). + +### Web Haul Search + +The `/haul` view searches Inara for profitable station-to-station routes near your origin and lets you dispatch one straight into the two-way haul routine. + +![Haul search](../assets/haul-search.png) + +Fill in the origin (and optionally destination), max route distance, cargo capacity, min supply / demand, then **Search routes**. Click a result and use **Set destination** or **Start route** to dispatch it. Land settlements are excluded for now; only station and carrier routes are returned. + +### Spansh Route Fetch and Comparison + +The route comparison panel fetches a Spansh route between two systems and lays it out beside the in-game route. + +![Spansh route fetch and comparison](../assets/spansh-routes.png) + +From, jump range, and supercharge mode auto-fill from live ship state (current system + Loadout event). Set To, adjust efficiency and any other fields, and optionally a final station. **Fetch Spansh**, **Compare**, or **All in one** to run the full flow, then **Switch to Spansh** to start the Spansh route runner — it flies the route waypoint by waypoint and auto-sets the galaxy map for the next waypoint every time you arrive. + +## Attach a TUI for TTS + +`lan` is headless, so it does not speak TTS on its own. Open a TUI client in a separate terminal to get the "commander, ship ready to jump" callouts and a live activity log. Paste the URL `lan` printed, or use the shorter `host:port` form: + +```sh +uv run python3 control_room.py connect http://:8765/ --token edcr +uv run python3 control_room.py connect :8765 --token edcr +``` + +Swap `edcr` for your token if you overrode it. TTS is client-local; the browser will not speak. + +Typical setup: one machine runs `control_room.py lan`, a second terminal (same machine or a second monitor / LAN box) runs `connect ...` for TTS + activity log, iPad or another window drives the browser UI. + +## The Five-Second Safety Delay + +Ship-affecting commands wait **5 seconds** before pressing any keys, so you have time to click back into Elite. Do that as soon as you fire a command from the browser or TUI. + +If you are already remote and do not need the pause, type `instant` in the TUI command bar to toggle it off. `instant on` and `instant off` are explicit forms. + +## First Haul + +1. In Elite, dock at a station you want to buy from. +2. In the browser, either search routes (haul search panel) or type `haul ` in the TUI command bar. +3. Switch to Elite. The routine handles docking, station services, buy, undock, depart, transit, and sell. +4. When the ship is clear and the drive is primed for the next jump, TTS calls out that the ship is ready. Take over for alignment and jump. + +For the full workflow, `haul.toml` profiles, and multi-leg routes, see [haul-workflow.md](haul-workflow.md). + +## Stopping + +- `Ctrl-C` or `Ctrl-D` while `haul` is running: first press queues a safe stop at station 1 after the return sale, second press cancels immediately. +- `q`, `quit`, or `exit` in the TUI when idle. + +## Where To Go Next + +- [haul-workflow.md](haul-workflow.md): the full haul story. +- [commands-reference.md](commands-reference.md): every Control Room command. +- [troubleshooting.md](troubleshooting.md): when input, journal, or bindings misbehave. +- [../operators/control-room-remote.md](../operators/control-room-remote.md): multi-client / observer semantics if more than one person connects at once. diff --git a/docs/user/haul-workflow.md b/docs/user/haul-workflow.md new file mode 100644 index 00000000..1895a096 --- /dev/null +++ b/docs/user/haul-workflow.md @@ -0,0 +1,125 @@ +# Haul Workflow + +`haul` is the strongest end-to-end routine and the clearest example of what EDControlRoom is for. It handles the boring station-side loop so you can stay focused on the parts that still benefit from a human pilot. + +## Contents + +- [What Haul Does](#what-haul-does) +- [The Simple Path](#the-simple-path) +- [Reusable Setup: `haul.toml`](#reusable-setup-haultoml) +- [Saved Default](#saved-default) +- [Home Routing](#home-routing) +- [Resume Semantics](#resume-semantics) +- [Multi-Leg Haul](#multi-leg-haul) +- [Interrupt Behavior](#interrupt-behavior) +- [Related](#related) + +## What Haul Does + +`haul` can be started from anywhere in the loop — whether you're docked, in supercruise near a station, mid-transit between systems, or just launched. It reads the journal, `Cargo.json`, and `Market.json` to figure out which phase you're in and picks up from there. Starting from the TUI or the web frontend behaves the same way. + +The phases in a full station-side cycle are: + +- request docking +- work through station services +- buy or sell cargo +- refuel and repair +- set the route for the next leg +- leave the station +- clear mass lock and prime the FSD + +`haul` decides which phase is next from your live state and jumps in there — you do not have to start at "request docking." + +There is no auto-align. When the ship is clear and the drive is primed, TTS calls the commander by title or name and says the ship is ready to jump. That is your cue to take over alignment and the next jump. + +This makes it directly useful for high-volume A-to-B cargo work such as community goal loops, where the repetitive trading cycle is the part worth automating. + +## The Simple Path + +From the TUI command bar or the web command bar: + +``` +haul # walks you through an interactive prompt +haul # skips the buy-commodity question +``` + +Or use the web **Haul search** panel to pick a route from Inara results and click **Start route**. See [getting-started.md](getting-started.md#web-haul-search). + +## Reusable Setup: `haul.toml` + +If you want the same two-station loop each time without stepping through the prompt, edit a repo-root `haul.toml` (git-ignored) and run: + +``` +haul load +``` + +Example `haul.toml`: + +```toml +[haul] +galaxy_map_settle = 2.0 +dock_timeout = 1200.0 + +[haul.station_1] +buying = "Aluminium" +name = "Pawelczyk Dock" +system = "Sol" +on_land = false + +[haul.station_2] +buying = "Bertrandite" +name = "Trevithick Dock" +system = "Achenar" +on_land = false +``` + +Notes: + +- `buying` is optional on either side, but at least one station must have a buy cargo. +- `on_land = true` hands off after `SupercruiseExit` in the destination system so you can do a surface approach and resume after landing. +- `haul load some-other-file.toml` if you keep multiple named profiles. + +## Saved Default + +Control Room persists one saved default haul setup across restarts. `replay` or `Ctrl-R` reopens recent commands, including that saved setup. + +## Home Routing + +Setting a home system gives you one-word routing later. + +``` +home set # save a home system +home set # save the current system if Control Room knows it +home # route to the saved home system +dest home # same, as a dest alias +haul search home # use home as the Inara search center +``` + +`home set` updates the active config. If Control Room started from the shipped example fallback (no repo-root `config.toml` yet), it creates a minimal `config.toml` rather than editing the shipped example. + +## Resume Semantics + +Haul is state-aware. If you cancel or crash mid-run and start it again, it re-derives the current stop and phase from the journal, `Cargo.json`, `Market.json`, and its sidecar state. You do not need to start from a clean station. + +## Multi-Leg Haul + +For a finite multi-hop route rather than a two-station loop: + +``` +multi_leg_haul +multi_leg_haul +mult ... # short alias +``` + +The route can come from the normalized JSON schema at `docs/schemas/multi_leg_haul.schema.json` (see `templates/multi_leg_haul.example.json`) or directly from a Spansh trade-result URL / payload. Resume is state-based; rerun and EDControlRoom figures out where you are. + +## Interrupt Behavior + +- First `Ctrl-C` or `Ctrl-D`: finish the current run, stop at station 1 after the return sale, before the next buy. +- Second `Ctrl-C` or `Ctrl-D`: cancel immediately. + +## Related + +- [commands-reference.md](commands-reference.md) for every command. +- [../operators/control-room.md](../operators/control-room.md) for the operator-reference view. +- [../operators/market-timing.md](../operators/market-timing.md) if you need to tune the market buy-hold or sell-max timings. diff --git a/docs/user/install.md b/docs/user/install.md new file mode 100644 index 00000000..6bf29a47 --- /dev/null +++ b/docs/user/install.md @@ -0,0 +1,71 @@ +# Install + +EDControlRoom needs Python 3.12 and, on macOS/Linux, the `uv` package manager. + +## Contents + +- [Platform Status](#platform-status) +- [macOS](#macos) +- [Windows](#windows) +- [Linux (untested)](#linux-untested) +- [Config Overrides](#config-overrides) + +## Platform Status + +- **macOS**: fully supported and actively used. Elite runs through CrossOver. +- **Windows**: fully supported and live-validated by community member CMDR VRYAE. +- **Linux**: runtime paths exist but are not live-validated. Expect small adjustments (paths, input backend) before it works end to end. See the note at the bottom of this page. + +## macOS + +1. Install `uv` if you do not have it: . +2. Clone this repo and `cd` into it. +3. Run `uv sync`. +4. Grant your terminal **Accessibility** permission in System Settings so it can send key input to Elite. Grant **Screen Recording** as well if you plan to use capture-based diagnostics. +5. Start Elite Dangerous through CrossOver. + +## Windows + +With `uv` (recommended): + +1. Install Python 3.12. +2. Install `uv`. +3. Clone this repo and `cd` into it. +4. Run `uv sync`. +5. Start Elite Dangerous. + +Without `uv`: + +```powershell +python -m venv .venv +.venv\Scripts\activate +pip install -r requirements.txt +``` + +Then start Elite Dangerous. + +## Linux (untested) + +1. Install Python 3.12 and `uv`. +2. Install `xdotool` for synthetic key input. The Linux input path is X11-oriented; Wayland is unverified. +3. Start Elite Dangerous through Steam / Proton. + +If auto-detection does not find the Proton journal directory, set `paths.journal_dir` and `paths.bindings_file` explicitly in a repo-root `config.toml`. Minimal example: + +```toml +[paths] +journal_dir = "" +bindings_file = "" + +[tts] +title_mode = "custom" +title = "captain" +``` + +Linux input is currently implemented through `xdotool`. Wayland behavior is unverified. + +## Config Overrides + +Shipped defaults in `defaults/*.toml` cover most cases. Create a repo-root `config.toml` only if you need overrides. When you do, keep it minimal. Set `paths.journal_dir` and `paths.bindings_file` only if auto-detection is not enough. Leave `runtime.platform` unset unless you want to pin the backend explicitly. + +Next: [bindings-setup.md](bindings-setup.md). diff --git a/docs/user/troubleshooting.md b/docs/user/troubleshooting.md new file mode 100644 index 00000000..3e685be3 --- /dev/null +++ b/docs/user/troubleshooting.md @@ -0,0 +1,70 @@ +# Troubleshooting + +Quick checks for when input, journal detection, or bindings look wrong. + +## Contents + +- [Nothing Happens When I Fire a Command](#nothing-happens-when-i-fire-a-command) +- [Galaxy Map / `dest` Navigates Incorrectly](#galaxy-map--dest-navigates-incorrectly) +- [Tail the Journal Live](#tail-the-journal-live) +- [Confirm Key Injection Works End To End](#confirm-key-injection-works-end-to-end) +- [Journal or Bindings Not Auto-Detected](#journal-or-bindings-not-auto-detected) +- [`.binds` Backup, Restore, and Presets](#binds-backup-restore-and-presets) +- [Deeper Diagnostics](#deeper-diagnostics) + +## Nothing Happens When I Fire a Command + +EDControlRoom sends key input to whatever window is focused. If Elite is not focused when the safety delay expires, the key presses go nowhere (or into your terminal). + +- Ship-affecting commands wait **5 seconds** by default so you can click back into Elite. Switch focus in that window. +- Type `instant` in the TUI to toggle the delay off if you are operating remotely and do not need it. +- On macOS, confirm your terminal has **Accessibility** permission in System Settings. + +## Galaxy Map / `dest` Navigates Incorrectly + +Almost always missing arrow-key secondaries on `UI_Up / UI_Down / UI_Left / UI_Right`. See [bindings-setup.md](bindings-setup.md). + +## Tail the Journal Live + +```sh +uv run python3 tools/watch_journal.py +``` + +Prints Elite journal events as they arrive. Only useful while the game is open. + +## Confirm Key Injection Works End To End + +```sh +uv run python3 tools/ship_controls.py --action SetSpeedZero --delay-seconds 3 +``` + +Waits 3 seconds, then presses the key currently bound to Elite's `SetSpeedZero` action. Focus Elite before the delay expires and expect throttle-zero to fire. + +## Journal or Bindings Not Auto-Detected + +Add explicit overrides in a repo-root `config.toml`: + +```toml +[paths] +journal_dir = "/absolute/path/to/Journal" +bindings_file = "/absolute/path/to/Custom.4.0.binds" +``` + +Windows shells without `python3` on PATH: replace `uv run python3 ...` with `uv run python ...` throughout. + +## `.binds` Backup, Restore, and Presets + +```sh +uv run python3 tools/bindings_files.py # inspect +uv run python3 tools/bindings_files.py backup +uv run python3 tools/bindings_files.py restore +uv run python3 tools/bindings_files.py apply-default +``` + +Full reference: [../operators/bindings-files.md](../operators/bindings-files.md). `apply-default` is unit-tested but not live-validated; report unexpected behavior with an issue. + +## Deeper Diagnostics + +- [../diagnostics/cli-reference.md](../diagnostics/cli-reference.md) +- [../diagnostics/bindings-reference.md](../diagnostics/bindings-reference.md) +- [../operators/manual-journal-routine-testing.md](../operators/manual-journal-routine-testing.md) for low-level routine validation outside Control Room.