Skip to content

rwellinger/xp_streamdeck

Repository files navigation

xp_streamdeck

X-Plane 12 cockpit with Stream Deck XL configurator showing autopilot controls

Native Stream Deck plugin for X-Plane 12 on macOS, talking to the X-Plane Web API on localhost:8086.

Prerequisites

  • X-Plane 12.1.1 or newer — the built-in Web API was introduced in 12.1.1 and is enabled by default.
  • Node.js 24 (pinned via .nvmrc — run nvm use in this directory).
  • The Elgato Stream Deck CLI ships as a devDependency, so no global install is needed; invoke it via npx streamdeck … (or install globally with npm i -g @elgato/cli if you prefer the bare streamdeck command).

X-Plane Web API setup

X-Plane 12.1.1+ runs the Web API automatically on http://localhost:8086/api/v3no menu toggle is needed to turn it on. The toggles in Settings → Network labelled "iPhone, iPad and External Apps" are unrelated to the Web API; they control the legacy UDP interfaces.

The only relevant setting is opt-out:

  • Settings → Network → Disable Incoming Traffic — must remain unchecked, otherwise every Web API call returns 403 Forbidden.

If you launched X-Plane from the command line with --no_web_server, the API is off; restart without that flag. To use a non-default port, use --web_server_port=<N> — but note this plugin currently hard-codes 8086 (will be configurable in M03+).

Quick API smoke test

Before debugging the plugin, verify the API responds:

curl -i 'http://localhost:8086/api/v3/datarefs/count'
Response Meaning
HTTP/1.1 200 OK + JSON API healthy → if the plugin still fails, look at plugin logs
HTTP/1.1 403 Forbidden Disable Incoming Traffic is checked — uncheck and restart X-Plane
Connection refused Web API not running — check X-Plane version and that it wasn't started with --no_web_server

X-Plane's own log usually shows a line like Web server listening on port 8086 at startup; check Log.txt if in doubt:

grep -i "web" "$HOME/X-Plane 12/Log.txt"
# Mac App Store install instead:
# grep -i "web" "$HOME/Library/Containers/com.laminarresearch.X-Plane/Data/Log.txt"

Plugin-side logs

Once the API is up, plugin activity goes to:

tail -f ~/Library/Logs/ElgatoStreamDeck/com.robertw.xplane*.log

Each press should produce Resolved sim/operation/pause_toggle -> id=… and Activated …. If nothing appears on press, the plugin isn't loaded — re-run npx streamdeck restart com.robertw.xplane.

Build & install (development)

make setup                                    # npm install
make build                                    # rollup → bin/plugin.js
npx streamdeck link com.robertw.xplane.sdPlugin
npx streamdeck restart com.robertw.xplane

After this, the X-Plane → Pause action appears in the Stream Deck app's action list. Drop it onto a key, press it, and X-Plane toggles pause (sim/operation/pause_toggle).

Actions

Command

Triggers any X-Plane CommandRef on key press. Optional Hold Mode routes the press through the WebSocket command_set_is_active begin/end pair instead of a one-shot activate — useful for things that should keep firing while the key is held (e.g. spinning the heading bug).

Property Inspector fields:

  • Command Path — the X-Plane CommandRef, e.g. sim/operation/pause_toggle.
  • Hold Mode — when checked, sends begin on keyDown and end on keyUp.
  • Hide green confirmation icon — opt-out of the showOk() flash on success. Errors still always show the alert icon.

Example: toggle pause

Field Value
Command Path sim/operation/pause_toggle
Hold Mode (unchecked)

Press → X-Plane pauses; press again → resumes.

Example: spin the heading bug while held

Field Value
Command Path sim/autopilot/heading_up
Hold Mode (checked)

Press and hold → heading bug rotates continuously; release → stops. Pair with sim/autopilot/heading_down on a second key for the opposite direction.

Command + Display

Fires a CommandRef on key press while showing a live DataRef value as the button title. Designed for buttons that both trigger and report state — e.g. G1000 softkeys, autopilot mode buttons.

Property Inspector fields:

  • Command Path — the CommandRef fired on keyDown, e.g. sim/GPS/g1000n1_softkey1.
  • Hide green confirmation icon — opt-out of the showOk() flash on success. Errors still always show the alert icon.
  • DataRef Path — optional DataRef rendered as the live title. Supports array indexing (see Array DataRefs).
  • Live Value — read-only preview while editing the path.
  • Label — optional caption rendered above the live value.
  • Format / Unit Scale / Precision — printf-style formatting; see DataRef Display for details.

Example: G1000 softkey 1 with live FMS frequency

Field Value
Command Path sim/GPS/g1000n1_softkey1
DataRef Path sim/cockpit2/radios/actuators/com1_frequency_hz_833
Label SK1
Format %.3f
Unit Scale 0.001

Rotary

Fires a CommandRef on press and shows a live DataRef as the title — for rotary-knob-style controls driven by step commands. Works in two Format Modes:

  • Numeric — for continuous setpoints (COM/NAV/FMS frequencies, heading bug, altitude target). Renders the live value via printf with an optional unit suffix.
  • Enum — for discrete enums (magneto positions, flap detents). Renders the value as a label from an index=label map, e.g. OFF/R/L/BOTH/START.

Optional HOLD on last position (enum mode only): when the DataRef sits one step before the last enum index and the user presses the key, the press fires a separate HOLD Command via the WebSocket begin/end pair instead of the regular step command. Designed for the Cessna starter: advancing BOTH → START should hold the starter engaged until the key is released, not click past it.

Property Inspector fields:

  • Command Path — the step command (e.g. sim/magnetos/magnetos_up).
  • Hide green confirmation icon — opt-out of the showOk() flash on success.
  • Direction — visual hint only (rendered as part of the title): Right (CW), Left (CCW), Up, Down.
  • DataRef Path — the live value displayed on the button. Supports array indexing.
  • Live Value — read-only preview while editing the path.
  • Label — optional caption rendered above the live value.
  • Format ModeNumeric or Enum.
  • Unit Scale — multiplier applied to the raw DataRef value before formatting (numeric) or before rounding to an enum index (enum). Useful for ratio DataRefs like flap_handle_request_ratio: scale by the number of detents.
  • Numeric mode: Format (printf) / Unit (suffix like MHz, ft, kt) / Precision.
  • Enum mode: Enum Map — comma-separated index=label pairs, e.g. 0=OFF,1=R,2=L,3=BOTH,4=START.
  • HOLD on last position (enum only) — checkbox to enable the begin/end behaviour described above.
  • HOLD Command — the separate CommandRef used during the hold (e.g. sim/starters/engage_starter).

Example: Cessna magneto switch (enum + HOLD)

Field Value
Command Path sim/magnetos/magnetos_up
Direction Right (CW)
DataRef Path sim/cockpit2/engine/actuators/ignition_key
Format Mode Enum
Enum Map 0=OFF,1=R,2=L,3=BOTH,4=START
HOLD on last position (checked)
HOLD Command sim/starters/engage_starter

Pressing the key cycles OFF → R → L → BOTH; pressing at BOTH instead holds the starter engaged (engage_starter begin) until release.

Example: COM1 frequency tuning (numeric)

Field Value
Command Path sim/COM1/coarse_up
Direction Right (CW)
DataRef Path sim/cockpit2/radios/actuators/com1_frequency_hz_833
Format Mode Numeric
Format %.3f
Unit MHz
Unit Scale 0.001

DataRef Display

Shows a live X-Plane DataRef value as the button title. Pure read-only — no click action.

Property Inspector fields:

  • DataRef Path — the X-Plane DataRef, e.g. sim/cockpit/autopilot/heading_mag. Supports array indexing (see Array DataRefs).
  • Live Value — read-only preview of the current value while editing the path. Without [N] an array DataRef shows its full contents (handy for picking the right index); with [N] only the indexed element is shown.
  • Label — optional caption rendered above the value (e.g. ALT).
  • Format — printf-style template (%s, %d, %f, %.Nf, %%). Default %s.
  • Unit Scale — optional multiplier applied before formatting (e.g. radians→degrees, m/s→kt, Pa→inHg).
  • Precision — optional decimals; only used when the format token has no explicit precision.

Example: QNH in inHg

X-Plane exposes sim/weather/aircraft/qnh_pas as a float in Pascal. To show it as 29.92 inHg on a button:

Field Value
DataRef Path sim/weather/aircraft/qnh_pas
Format %.2f inHg
Unit Scale 0.0002953
Precision (leave empty)

Background: 1 inHg = 3386.389 Pa, so the conversion factor is 1 / 3386.389 ≈ 0.0002953. Standard QNH 101325 Pa × 0.0002953 = 29.9213 → with %.2f29.92 inHg.

For hPa/mb (1013) instead:

Field Value
Format %.0f hPa
Unit Scale 0.01

Multi DataRef Display

Shows up to three live DataRef values stacked on one button — for things like COM A/S (active + standby frequency), wind DIR/SPD/TEMP, or any other grouped readout that needs to share one key. Pure read-only — no click action.

Property Inspector fields:

  • Title — optional top-line caption rendered above all slots (e.g. COM1).
  • Slot 1 / Slot 2 / Slot 3 — each slot is collapsible and has its own:
    • Label — optional prefix (e.g. A:, S:).
    • DataRef Path — the DataRef to subscribe to. Supports array indexing.
    • Live Value — read-only preview while editing.
    • Format / Unit Scale / Precision — printf-style formatting per slot (see DataRef Display).
  • Slot 1 is required; slots 2 and 3 render only if their DataRef Path is set.

Example: COM1 active + standby

Field Value
Title COM1
Slot 1 Label A:
Slot 1 DataRef Path sim/cockpit2/radios/actuators/com1_frequency_hz_833
Slot 1 Format %.3f
Slot 1 Unit Scale 0.001
Slot 2 Label S:
Slot 2 DataRef Path sim/cockpit2/radios/actuators/com1_standby_frequency_hz_833
Slot 2 Format %.3f
Slot 2 Unit Scale 0.001

Wind Display

Specialised readout: renders wind direction as a rotating arrow icon plus the wind speed (and optionally OAT) underneath. Reads the direction and speed DataRefs continuously and rotates a built-in arrow image to match the wind heading.

Property Inspector fields:

  • Label — optional top-line caption; defaults to WIND.
  • Direction DataRef — wind heading in degrees, e.g. sim/cockpit2/gauges/indicators/wind_heading_deg_mag.
  • Speed DataRef — wind speed in the desired unit, e.g. sim/cockpit2/gauges/indicators/wind_speed_kts.
  • OAT DataRef (optional) — outside air temperature, e.g. sim/cockpit2/temperature/outside_air_temp_degc. Rendered as a third line if set.
  • Speed Unit — suffix appended to the speed value; defaults to kt.
  • Arrow Convention
    • Points where wind goes (PFD style) (default) — rotates the arrow 180° from the X-Plane heading, matching most glass cockpit PFDs.
    • Points where wind comes from (weather chart) — matches METAR / weather chart convention.

X-Plane's wind_heading_deg_mag reports the direction the wind comes from; the default convention flips this so the arrow points downwind.

DataRef Toggle

Two-state action that flips a DataRef value (or activates a CommandRef) on key press, and reflects the live state on the button by switching between two images. Use it for binary or near-binary controls (gear, flaps detents, lights, fuel pumps, …).

Property Inspector fields:

  • DataRef Path — the X-Plane DataRef to read for the visible state. Supports array indexing (see Array DataRefs).
  • Live Value — read-only preview of the current value while editing the path.
  • Value OFF / Value ON — the two values that map to the OFF / ON image. Defaults to 0 / 1. The visible state is chosen by closest distance to either value (or ≥ 0.5 for the default 0/1 case).
  • Strict ON Match — when checked, only value === Value ON (with float tolerance) counts as ON; everything else is OFF. Useful for multi-state enums where a single index is the "ON" state.
  • Trigger Mode
    • Write DataRef writes the opposite value on each press.
    • Activate Command fires a single CommandRef on press; the visible state still comes from the DataRef. Useful when the aircraft exposes a "toggle" command but the DataRef is the actual state.
    • On/Off Command fires one of two CommandRefs depending on the current DataRef state: at OFF the ON command fires, at ON the OFF command fires. For aircraft that expose separate …_on / …_off commands instead of a single toggle.
  • Command Path — only used when Trigger Mode is Activate Command.
  • Command Path ON / Command Path OFF — only used when Trigger Mode is On/Off Command.
  • Image OFF / Image ON — optional custom 144×144 PNG/JPG/SVG per state; uploads are downscaled to 144 px and persisted to disk so multi-state image switching stays reliable. Leave empty to use the default imgs/states/{off,on} images.

The Property Inspector hides the command-path fields that don't apply to the selected trigger mode, so only the relevant inputs are visible.

Example: gear handle

Field Value
DataRef Path sim/cockpit2/controls/gear_handle_down
Value OFF 0
Value ON 1
Trigger Mode Write DataRef

Press → toggles gear up/down; the button flips between OFF/ON image as the DataRef actually changes.

Example: gear via command, state via DataRef

Field Value
DataRef Path sim/cockpit2/controls/gear_handle_down
Trigger Mode Activate Command
Command Path sim/flight_controls/landing_gear_toggle

Useful for aircraft where the gear command runs an animation/sound but the simple DataRef write would skip it.

Example: autopilot servos with separate On/Off commands

Field Value
DataRef Path sim/cockpit2/autopilot/servos_on
Value OFF 0
Value ON 1
Trigger Mode On/Off Command
Command Path ON sim/autopilot/servos_on
Command Path OFF sim/autopilot/servos_off

Press while OFF → fires servos_on; press while ON → fires servos_off. The button image follows the live DataRef.

Guarded Command

Two-stage button modeled on cockpit covers that protect dangerous switches. Short press fires shortPressCommand (e.g. flip the cover open); long press (≥ 500 ms) fires the protected longPressCommand (e.g. engage the starter). Optionally subscribes to a Guard DataRef and renders one of two images — locked (cover closed) or unlocked (cover open) — so the button reflects the actual cockpit state.

Designed primarily for the Piper PA-46 M500 by X-Aerodynamics — the Property Inspector placeholders use M500 DataRefs (sim/PA46/cover/starter_open, sim/PA46/cover/starter_toggle) — but works with any aircraft that exposes a guard DataRef plus open/close commands.

Property Inspector fields:

  • Short press → Command Path — CommandRef fired on quick release, e.g. the cover toggle.
  • Hide green OK after short press — opt-out of the showOk() flash on short press. Errors still always show the alert icon.
  • Long press → Command Path — CommandRef used when the key is held for at least 500 ms (e.g. engage starter).
  • Long press → Mode
    • Hold (begin / end while held) (default) — sends WebSocket command_set_is_active begin at the 500 ms threshold and end on release. Use for sustained actions like cranking a starter.
    • Auto-repeat 5 Hz while held — fires activate every 200 ms while held. Use for things that need repeated discrete activations.
    • Activate once at threshold — fires a single activate at 500 ms and ignores the rest of the hold.
  • Guard DataRef — optional DataRef that reports the cover/guard state; drives the visible locked/unlocked image. Leave blank to skip state display (the action still fires both commands).
  • Value Locked / Value Unlocked — numeric thresholds; default 0 / 1. Closest-distance match selects the image (or ≥ 0.5 for the default 0/1 case).
  • Strict Unlocked Match — when checked, only value === Value Unlocked (with float tolerance) counts as unlocked; everything else is locked. Useful for multi-state guards where one specific index is "open".
  • Image Locked / Image Unlocked — optional custom 144×144 PNG/JPG/SVG per state; uploads are downscaled to 144 px and persisted. Leave empty to use the bundled guarded icons (see Button icons).

Example: PA-46 M500 starter with cover

Field Value
Short press → Command Path sim/PA46/cover/starter_toggle
Long press → Command Path sim/starters/engage_starter_1
Long press → Mode Hold (begin / end while held)
Guard DataRef sim/PA46/cover/starter_open
Value Locked 0
Value Unlocked 1

Press once → cover flips open; the button image switches to unlocked. Press and hold → starter engages via begin/end and stays engaged until release. Press once again → cover flips closed.

DataRef Write

Single-press action that writes a fixed numeric value to a DataRef. Use it when you want a button that sets a specific value (e.g. flaps to detent 2, parking brake to 1) rather than toggling.

Property Inspector fields:

  • DataRef Path — the X-Plane DataRef to write. Supports array indexing (see Array DataRefs).
  • Live Value — read-only preview of the current value while editing the path.
  • Value — the numeric value written on press.
  • Label — optional caption rendered above the live value (only used when Show current value is checked).
  • Show current value — when checked, subscribes to the DataRef and renders its live value on the button title (same formatting pipeline as DataRef Display).
  • Format / Unit Scale / Precision — printf formatting, only used when Show current value is checked. See DataRef Display for details.
  • Hide green confirmation icon — opt-out of the showOk() flash on success. Errors still always show the alert icon.

Example: parking brake on

Field Value
DataRef Path sim/flightmodel/controls/parkbrake
Value 1

Example: flaps to detent 2

Field Value
DataRef Path sim/flightmodel/controls/flaprqst
Value 0.5
Show current value (checked)
Format FLP %.0f%%
Unit Scale 100

Background Tile

Decorative filler tile with no action — pressing it does nothing. Useful as a visual separator between functional clusters on the deck (e.g. a black or colored stripe between autopilot and lights groups).

There are no Property Inspector fields; set the image via Stream Deck's standard Icon field on the right-hand side. The bundled icon catalog produces solid-color tiles (bg_black, bg_white, bg_yellow, bg_red) via make icons — see Button icons.

Array DataRefs

Some X-Plane DataRefs are arrays — one value per engine, per cylinder, per aerodynamic surface, etc. Examples:

  • sim/cockpit/engine/fuel_pump_onint[16], one slot per engine.
  • sim/flightmodel/engine/ENGN_runningint[16], one per engine.
  • sim/cockpit2/switches/landing_lights_onint[10].

Append [N] to the DataRef path in any action that takes a DataRef path (Display, Toggle, Write, Command + Display, Rotary, Multi DataRef Display) to address a single element. Without [N], Display-style actions fall back to element [0] (legacy behaviour); Toggle and Write target the DataRef as a whole, which is fine for scalar DataRefs but unreliable for arrays — always use [N] when the DataRef is an array.

Example: fuel pump for engine 1

Field Value
DataRef Path sim/cockpit/engine/fuel_pump_on[0]
Value OFF 0
Value ON 1

The Toggle action reads only fuel_pump_on[0] for the visible state and writes only that index on press (via PATCH …/value?index=0); engines 2–16 stay untouched. To put each engine on its own key, drop the same action four times and change the index to [0] / [1] / [2] / [3]. All four share a single WebSocket subscription under the hood.

Live Value behaviour

In the Property Inspector's Live Value row:

  • Path without [N] on an array DataRef → shows the entire array (e.g. [0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0]). Useful for figuring out which index does what before committing to one.
  • Path with [N] → shows only that scalar.
  • Path with [N] but DataRef is not an array → shows not an array.
  • Path with [N] but N is out of range → shows index N out of bounds (length M).

In all error cases the action tile shows the standard ? not-found suffix at runtime, and Toggle/Write trigger showAlert() on press.

Button icons

Button images shown on the Stream Deck are generated locally by a small TypeScript pipeline so the whole set stays visually consistent (same font size, same baseline, same LED-bar geometry across every icon).

make icons

Five kinds of icons are produced from a single catalog (scripts/icons/catalog.ts):

  • toggle — for action buttons that flip a state (AP HDG mode, FD on/off, …). Generates an _on + _off pair: bold uppercase label centered, colored LED bar at the bottom (lit in the accent color when ON, dark grey when OFF, with a soft glow).
  • display — for the dataref-display action (live X-Plane readouts: current altitude, wind, AP setpoints, …). Generates a single PNG: small caption + thin accent line in the top third, rest of the key left empty so Stream Deck's title overlay can render the live value cleanly underneath.
  • nudge — for single-press command buttons that increment/decrement an AP setpoint (heading bug, altitude target, V/S, source). Generates a single PNG: bold label at the top, big filled triangle in the accent color pointing in the action direction. Pair with the command action (with Hold Mode for continuous spin).
  • background — solid-color filler tile (no label, no accent). Generates a single PNG with the entire 144×144 painted in the entry's color. Useful as visual separators between functional clusters on the deck. Bundled set: black, white, yellow, red.
  • guarded — pairs with the guarded-command action. Generates a _locked + _unlocked pair: yellow-and-black hazard stripe at the top (signals "guarded"), bold label centered, LED bar at the bottom (lit in the group's accent color when unlocked, dark when locked). Bundled set lives in the cockpit group: starter, starter_l / starter_r (twin-engine), fuel_cut, emer_gear.

Groups & color palette

Each catalog entry belongs to exactly one group. The group decides both the accent color and the output subdirectory — one color per group keeps the whole set visually calm and makes related buttons easy to find on disk.

Group Accent Hex Contents
autopilot yellow #eab308 AP/FD/YD mode toggles, AP setpoint readouts, HDG/ALT/VS/SRC nudges
lights green #22c55e BCN, LAND, TAXI, NAV, STROBE
cockpit green #22c55e PARK BRK, FUEL PUMP, MASTER BAT, AVIONICS, PITOT HEAT
readouts white #ffffff Live values: HDG, ALT, IAS, V/S, BARO, WIND, W SPD
backgrounds n/a per entry Solid-color filler tiles (bg_black, bg_white, bg_yellow, bg_red)

The mapping lives in GROUP_ACCENT at the top of scripts/icons/catalog.ts — change a hex there and every icon in that group updates after the next make icons.

Output goes into one subdirectory per group:

out/icons/
├── autopilot/   # ap, fd, hdg, …, ap_hdg, ap_alt, …, hdg_left, hdg_right, alt_up, …
├── lights/      # lt_bcn_on/off, lt_land_on/off, …
├── cockpit/     # parkbrake_on/off, fuelpump_on/off, …
└── readouts/    # cur_hdg, cur_alt, cur_ias, …

Toggles produce <name>_on.png + <name>_off.png; displays and nudges produce a single <name>.png. All 144×144. The out/ folder is gitignored and wiped by make clean.

Adding a new icon

  1. Open scripts/icons/catalog.ts.

  2. Append a single entry to the catalog array, picking the kind and the group:

    // toggle button — color and output dir come from the group
    { kind: 'toggle',  name: 'apu',     label: 'APU', group: 'cockpit' },
    
    // live readout (header for the dataref-display action)
    { kind: 'display', name: 'cur_oat', label: 'OAT', group: 'readouts' },
    
    // nudge button (single press → CommandRef; arrow indicates direction)
    { kind: 'nudge',   name: 'crs_left', label: 'CRS', direction: 'left',  group: 'autopilot' },
    { kind: 'nudge',   name: 'crs_x2',   label: 'CRS', direction: 'right', double: true, group: 'autopilot' },
    
    // solid-color filler tile (no label, no accent — color comes from `color`)
    { kind: 'background', name: 'bg_orange', color: '#f59e0b', group: 'backgrounds' },
    • kind'toggle' for on/off buttons, 'display' for live-readout headers, 'nudge' for single-press arrow buttons, 'background' for plain-color filler tiles, 'guarded' for two-stage cover-protected buttons.
    • name — file-name stem; must be unique within its group. Output: apu_on.png + apu_off.png (toggle) or cur_oat.png / crs_left.png (display, nudge), inside the group's subdirectory.
    • label — text shown on the icon. Toggle: ≤ 4 chars renders at 44px; longer labels auto-shrink in fixed steps (5→36, 6→30, 7→26, 8→22, 9→20, 10+→18). Display: ≤ 6 characters comfortably (AP HDG, W SPD). Nudge: ≤ 4 characters (HDG, SRC, ALT, VS); the arrow is the visual focus.
    • group — one of 'autopilot' / 'lights' / 'cockpit' / 'readouts'. Drives both the accent color (see the table above) and the output subdirectory. To add a new group, extend the IconGroup type and GROUP_ACCENT map at the top of catalog.ts.
    • direction (nudge only)'up' / 'down' / 'left' / 'right'. Arrow points this way.
    • double (nudge only, optional)true renders two stacked triangles for "coarse step" semantics (e.g. ALT ↑↑ for big increments).
    • color (background only) — hex fill for the entire tile. The group's accent is ignored for this kind.
  3. Run make icons. The new files appear in out/icons/<group>/.

  4. In the Stream Deck app: drag the PNG onto a key. For a display icon, configure the dataref-display action (DataRef path + format) on that key — the live value renders as the title in the empty zone of the icon.

To rename an icon, edit the catalog entry and re-run; the old PNGs stay until you run make clean.

Where to change the look

All visual decisions live in scripts/icons/template.ts (a single SVG renderer):

  • LABEL_FONT_SIZE, LABEL_BASELINE_Y — text size and vertical position.
  • BAR_HEIGHT, BAR_INSET_X, BAR_INSET_BOTTOM, BAR_RADIUS — LED bar geometry.
  • BG, BAR_OFF, LABEL_COLOR — base palette.
  • The <filter id="glow"> block — strength of the lit-bar glow.

Change once → re-run make icons → every icon updates with identical proportions.

Aircraft profiles

Ready-made Stream Deck XL profiles for several aircraft live in streamdeck-profiles/. The bundled set covers the X-Plane default Cessna 172 SP and G1000, Aerobask Diamond DA42 / DA62 / DV20, UL Shark, Aerobask Phenom 300, Pilatus PC12 by Thranda (G1000 version), and the Piper PA-46 M500 by X-Aerodynamics.

Each profile expects this plugin installed and the matching aircraft loaded in X-Plane.

Common Make targets

Run make help for the full list. Most-used: make build, make icons, make clean, make distclean, make setup, make package.