Fired when a controller connects.
Fired when a controller disconnects.
All currently tracked controllers (order is not stable; use handedness).
The left-hand controller, if connected.
The right-hand controller, if connected.
Refresh every controller's poses and button/axis state for this frame.
Call once per XRFrame, before reading controllers.
Detach the inputsourceschange listener.
Tracks the XR session's input sources (controllers, hands) and refreshes their grip / target-ray poses and gamepad button/axis state each frame.
Deliberately decoupled from rendering: construct one alongside an XrSession and call update once per
XRFrame(e.g. from anengine.beforeFramehook). Read controllers / left / right to drive interaction, locomotion, or held viewmodels. This is the controller half of the WebXR integration — see TODO/webxr-integration.md.