Scenario
escort_transit
W-to-E Berlin transit, four waves. Three broken beyond the raiders’ own detection range; the fourth a terrain-masked pop-up fought with guns.
BRKMYR/ AI Builder Portfolio/ INTENT Operator Console
A manned-unmanned teaming (MUM-T) command console. One operator tasks several unmanned wingmen, authorizes engagements under a rules-of-engagement policy, and every decision the system and the operator make is written to an AI decision log. Built on a PettingZoo MARL testbed over Greater Berlin.
Sixty seconds of operation MULTI-SHIELD EUROPE, captured headlessly from the shipping app
(python main.py demo escort_transit --autopilot --record --headless).
Five unmanned CCAs screen the manned lead across Berlin against four waves of Su-57s, the last
converting astern inside minimum missile range. Every element on screen — map, aircraft,
mission goals, PHC authorization, AI decision log — is drawn by the same code that renders the
interactive window. Debrief: nothing ever fired at the human pilot. Five of five unmanned
aircraft came home. Seven of seven raiders stopped.
Problem
As MUM-T concepts move from slideware into procurement, the open question is not whether an unmanned wingman can fly the profile. It is whether one operator can task several of them at once, authorize weapon release in seconds, and leave behind a message trail that survives an after-action review. Existing MARL testbeds are built for training agents; the operator experience is an afterthought if it exists at all.
For a product team building the operator side of a MUM-T system, this means the console has to be prototyped on the same simulator that trains the autonomy, so scenario replays exercise both. That is what INTENT is.
Solution
INTENT is an operator console (tasking, PHC engagement authorization, ROE cycling, AI decision log) that sits on top of a PettingZoo ParallelEnv MARL environment. The console attaches only in main.py. Training code paths never touch it, so a policy learned in headless training is exercised against the same env the operator sees.
Three scripted demo scenarios ship in the box, each with a scripted ghost operator that drives the console on autopilot for replay. The --record flag streams frames straight into an H.264 encode — or an animated GIF where ffmpeg is absent — so the demo above is produced by the app itself, not by screen capture.
Scenario
escort_transit
W-to-E Berlin transit, four waves. Three broken beyond the raiders’ own detection range; the fourth a terrain-masked pop-up fought with guns.
Scenario
pincer
Two-axis pressure. Wingmen have to be re-tasked mid-mission; ROE cycling matters.
Scenario
saturation
Enough tracks to blow past a single-operator span-of-control. Stress test for the console.
Success criteria
main.py. Training code paths never import UI code. This is an invariant, not a convention.SDL_VIDEODRIVER=dummy.Metrics, KPIs, evals
| KPI | Value | What it tells the PM |
|---|---|---|
| Time to authorize | key press | From threat surfaced to Y/A/N. Single-keypress authorization is a policy choice: it is fast, and it makes the decision log entry unambiguous. |
| C2 message throughput | per-step JSONL | Every tasking, authorization, and state transition writes a line to the AI decision log. Throughput is bounded by scenario tempo, not by console latency. |
| Scenario reproducibility | byte-identical | Same seed, same scenario, same scripted operator timeline gives the same decision log. Regression testing works. |
| Headless recall | SDL dummy | Same code path renders the live window and the recording. The hero above is one such capture, unedited. |
| Span-of-control | 3 wingmen | Console tasks a five-ship CCA element plus the manned lead. Saturation scenario stress-tests the span-of-control limit. |
| Training decoupling | import boundary | Console only lives in main.py. RL training never imports UI. Enforced by convention and reviewed on every change. |