Skip to content

[Feature] Implement per-keybind event detection sensitivity and change rate #2770

@oznogon

Description

@oznogon

The move from SFML to SDL2 changed the default behavior of events where a key is pressed and held.

On SFML, it defaulted to the same behavior as the system's (typically press once, pause for 250-500ms, and then repeat discrete short keypress events on an interval at a rate of 20-30/second).

If you pressed and held a key like this:

d|||||||||||||||||||||||||||U
key down                    key Up

SFML would interpret it as:

key down, key pressed (|), key Up
d|U   d|U d|U d|U d|U d|U d|U
      repeats

On SDL2, they're handled similarly to gamepad button presses, as one sustained event:

 <- one key pressed event ->
d|||||||||||||||||||||||||||U
key down                    key Up

When EE/SP moved from SFML to SDL2, this changed the behavior of controls that relied on pressing and holding a key, like dial controls (Helms rotation, AimLock) or slider controls (impulse, jump distance, Engineering/Power Management, scanning). Instead of them moving in a de facto stepwise manner as they did on SFML, changes are applied on every update.

In SFML, this was already problematic in places like Helms rotation, which on clients would send a new stepwise command every discrete key press, at 20-30 a second, flooding the network. Ships would also continue to turn after the key was released, as the final stepwise interval was applied.

In SDL2, since most of the sensitivity values for such controls weren't changed, changes to values became uncontrollably fast since they were now happening every frame. The Helms rotation network traffic issue was also carried forward into SDL2 and made worse.

This transition necessitated workarounds:

These "fixes" created new issues for non-keyboard inputs that send keyboard keypress events:

  • Several actions now have separate keybinds for joystick axes and keypresses, but the hotkey config doesn't differentiate in which inputs it accepts for these.
  • hotkeys for adjusting step-by-step #2769 suggests spreading stepwise hacks into scanning and AimLock in order to facilitate digital encoder knobs on macropads, which have the opposite problem of keyboard keypress events: some encoder steps are too small to effect change, and both the event detection and change rate sensitivity can't be tuned.

Each new workaround of this nature adds to the already confusing list of keybinds, creates new backward-compatibility issues if input behavior changes, and creates new issues for other types of hardware not yet tested against these keybind options.

For all keybinds, the hotkey system should have an awareness of whether a control has one or more of these input behaviors:

  • A step control, where one key/button press performs a binary (on/off) function once, regardless of key/button press length
  • A sustained control, where one key/button press performs a binary function every update until released
  • An axis control, and whether that axis reports from -1.0 to 1.0 (most joystick axes) or from 0.0 to 1.0 (many throttles, most A2D pots)

To support arbitrary or custom hardware, keybinds should allow setting:

  • The value at which the input is triggered. This would allow users to tune the sensitivity of:
    • Axis-based triggers and buttons common on many gamepads, which return an axis value instead of a binary event and typically have a dead zone at the center.
    • Analog potentiometer knobs or sliders converted to digital values, which send an axis-like absolute value within a range and typically have dead zones at their extremities.
    • Digital rotary encoders, which send a value relative to 0 per step and might send an arbitrary number of steps per detent (or at an arbitrary threshold if lacking detents).
    • Mappable mouse movement or wheel events, which send positive or negative values across one or more axes relative to 0.
    • SDL relative mouse and joystick axis movements, which send values relative to 0, if any are implemented in the future.
  • The rate at which the triggered input changes the bind's value. This would allow users to tune the sensitivity of:
    • Rotational controls, such as Helms steering and AimLock angle, where the input applies a relative change.
    • Float-based slider controls, such as impulse and jump controls, engineering power and coolant sliders, scanner minigame sliders, and zoom sliders.
    • Float-based panning controls, to facilitate keybinds or arbitrary controllers for Relay radar (including Spectate and GM screen) panning.
    • Mouselook and camera movement controls for cinematic view.

To set these, two optional values would need to be added to keybind objects and saved to the keybinds file. Ideally these would also be exposed in some manner on the hotkey binding menu, which already needs to be redesigned.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions