Input remap: CONTROLS.MAP binding engine + XInput gamepad support
The pod's controls reach the game through the RIO serial board; on a
desktop that hardware is a keyboard shim of hardcoded GetAsyncKeyState
reads. New binding engine (game/reconstructed/btinput.cpp) maps PC keys
and an XInput pad onto the authentic channels through a user-editable
file (content/CONTROLS.MAP, community-suggested grammar, corrected):
key/pad -> button <addr> real buttonGroup emissions, mirroring the
RIO convention exactly (press a+1 w/ mode
mask saved, release -a-1 w/ saved mask;
L4CTRL.cpp:2470-2520) -- aux/preset banks,
hotbox, panic, reverse thrust all reachable
key/pad -> axis Throttle rate (lever), pedals/JoystickX
deflect (turn/twist) into the existing
virtual-controls integrators (feel, gait
detent, spring-centering all unchanged)
keypad pilot|external <n> keyboardGroup key values ('0'-'F')
pckey <char> any authentic 1995 typed hotkey
action <name> port dev controls (view, all-stop, ...)
Keys claimed by a binding are SUPPRESSED from the legacy WM_CHAR/KEYUP
feed -- ends the historic double-dispatch ('w' drove AND selected pilot
0; F5's key-up value 0x74 aliased to the 't' hotkey; letter key-ups fed
the developer fake-event dispatcher). Unbound keys keep their authentic
meaning. The dual-use 'V' is split: V = view toggle, B = look behind.
Default profile = WASD classic (compiled-in twin; delete the file to
restore). CONTROLS_NUMPAD.MAP ships the corrected community layout
(keypads are NOT buttons 0x50-0x6F -- that space doesn't exist; no
clickable cockpit exists so everything needs a binding; keyboard fire
buttons added; 0x36/0x37 are hotbox not 'config'; missiles moved off
Ctrl). XInput loads dynamically (1_4 -> 9_1_0), disconnected-pad
probing rate-limited; pad sticks write the axes as absolute positions
(the spring is physical), triggers/buttons per the file.
Verified live: bindings load (43), W and NumPad8 drive (speedDemand 0 ->
61.5), X all-stop (spd -> 0), aux-bank emission (D1 -> [input] 0x2f
PRESS/release under the numpad profile), suppression both directions
(posted 'r' reaches [keych], posted 'w' swallowed), full-keyspace
WM_CHAR+WM_KEYUP fuzz x3 survived with sim advancing, XInput graceful
with no pad, 2-node relay session un-regressed (full ladder + UDP).
Pad-in-hand testing still needs a physical controller.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Fable 5
parent
0fcd0c3106
commit
980c9cd7e5
@@ -267,6 +267,7 @@ default-ON (`'0'` disables).
|
||||
| `BT_RELAY=<host:port\|auto>` | **D1 relay mode** — dial the relay/operator console instead of the P2P mesh; `auto` = LAN UDP-broadcast discovery on udp/15999 ([[multiplayer]] D1) |
|
||||
| `BT_SELF=<[pilots] tag>` | claim a specific roster seat in relay mode; absent/`auto` = the relay assigns one (SEAT_REQUEST) |
|
||||
| `BT_RELAY_TCP_ONLY=1` | disable the relay UDP channel (all unreliable traffic rides the TCP relay conn) |
|
||||
| `BT_INPUT_LOG` | binding-engine trace: CONTROLS.MAP load, button/keypad emissions, pad connect ([[pod-hardware]] §Desktop input remap) |
|
||||
|
||||
Full render/locomotion gates (BT_RAMP, BT_MATPRI, BT_CULL, BT_SHADOW_*, BT_LODSEL, BT_ADDLOD,
|
||||
BT_PUNCH, …) are catalogued in [[rendering]]. Warp visuals: [[translocation-warp]].
|
||||
|
||||
@@ -25,6 +25,38 @@ to keyboard/gamepad on a dev box; real wiring is a pod bring-up task (Phase 8).
|
||||
model — `LBE4ControlsManager` groups are fed by all devices (RIO on the pod, DirectInput on dev);
|
||||
the `MechControlsMapper` interprets them ([[locomotion]]). [T2]
|
||||
|
||||
### The button space + lamps [T0, L4CTRL.h enum]
|
||||
buttonGroup addresses 0x00-0x47: `AuxLowerRight/Left 1-8` (0x00-0x0F), `Secondary1-12` (0x10-0x1B),
|
||||
`AuxUpperCenter/Left/Right 1-8` (0x20-0x37 — the preset/eng "display eng data" banks; **0x30-0x37 =
|
||||
the target HOTBOX**, pilot select), icom/door 0x39-0x3C, `Panic` 0x3D (the config-mode lamp),
|
||||
`Throttle1` 0x3F (throttle-head = REVERSE THRUST), joystick cluster 0x40-0x47 (Main trigger 0x40,
|
||||
hat 0x41-0x44, Pinky/ThumbLow/ThumbHigh 0x45-0x47 — the four MAPPABLE fire buttons). "Lamp buttons"
|
||||
are literal: physical illuminated pushbuttons in panels around the screens; the RIO `LampRequest`
|
||||
protocol lights them (`MakeLinkedLamp`), reports burned-out bulbs (`RIODeadLamps` failure page,
|
||||
per-lamp names). A lit button = active. Keypads are NOT buttons: `keyboardGroup[KeyboardPilot/
|
||||
KeyboardExternal]` carry key VALUES ('0'-'9','A'-'F', L4CTRL.cpp:2526). RIO event convention:
|
||||
press = `buttonGroup[a].Update(a+1, modeMask)` (mask saved), release = `Update(-a-1, savedMask)`
|
||||
(L4CTRL.cpp:2470-2520).
|
||||
|
||||
### Desktop input remap — CONTROLS.MAP + XInput (2026-07-18) [T2 live]
|
||||
`game/reconstructed/btinput.cpp` + `content/CONTROLS.MAP` (WASD-classic default, compiled-in twin;
|
||||
`content/CONTROLS_NUMPAD.MAP` = the corrected community numpad profile). Grammar: `key <name>
|
||||
button <addr>|axis <axis> deflect|rate <n>|keypad pilot|external <0-15>|pckey <char>|action
|
||||
<name>`; `pad <button>` same targets; `padaxis <src> axis ... [invert] [deadzone d] [rate n]`.
|
||||
Axes: Throttle (lever, rate-walks + sticks), LeftPedal/RightPedal/Pedals (turn, springs),
|
||||
JoystickX (torso twist). Emissions mirror the RIO conventions above exactly; the four fire
|
||||
buttons (0x40/45/46/47) publish as levels to the bring-up fire channels instead of buttonGroup
|
||||
(avoids double-fire once the streamed ChooseButton mappings are exercised). XInput loads
|
||||
dynamically (xinput1_4 → 9_1_0; disconnected-pad probing rate-limited to 1 Hz). **Keys claimed by
|
||||
a binding are SUPPRESSED from the legacy WM_CHAR/KEYUP feed** (`BTInputSuppressKey`, hook at
|
||||
L4CTRL.cpp keyboard read) — this ended the historic DOUBLE-DISPATCH: 'w' drove AND selected pilot
|
||||
0; F5's key-up value 0x74 aliased to the 't' hotkey; letter key-ups (uppercase) fed the developer
|
||||
fake-event dispatcher. Unbound keys keep their authentic 1995 dispatcher meaning (reachable from
|
||||
any key via `pckey`). The old dual-use 'V' (view toggle + look-behind) is split: V = ViewToggle,
|
||||
B = LookBehind. Verified live: bindings load, W/NumPad8 drive (spd rises), X all-stop, aux-button
|
||||
emission ([input] 0x2f PRESS), suppression both directions ('r' delivered / 'w' swallowed),
|
||||
full-keyspace WM_CHAR+WM_KEYUP fuzz survived. Diag: `BT_INPUT_LOG`.
|
||||
|
||||
### The pod throttle is ANALOG-CONTINUOUS, not notched (verified end-to-end) [T1]
|
||||
The authentic pod throttle path — traced 2026-07 (task #50 throttle-fidelity question):
|
||||
1. **Hardware → RIO:** serial `AnalogReply` packet → `Ranger("Throttle", 0, 800, .05)` — raw counts
|
||||
|
||||
Reference in New Issue
Block a user