OpenLogi Long-Press and Short-Press Binding Semantics: The 500ms SOOM Threshold Model
OpenLogi distinguishes between short-press and long-press bindings using a 500ms threshold where short-press actions fire immediately upon button activation while long-press actions only dispatch after the button is held longer than the configured LONG_PRESS_THRESHOLD.
OpenLogi implements a sophisticated input handling system called the SOOM (Smart Shift) threshold model that allows a single physical button to trigger different logical actions based on press duration. Understanding the long-press and short-press binding semantics is essential for configuring advanced workflows that distinguish between quick taps and deliberate holds. The system uses the LONG_PRESS_THRESHOLD defined in the core binding module to determine which action executes.
The SOOM Threshold Model Fundamentals
The SOOM threshold model enables a single physical button to expose two distinct logical actions through temporal differentiation.
- Short-press bindings dispatch immediately when the button is pressed (or released for toggle-type actions), requiring no additional timing checks.
- Long-press bindings only activate after the button is held continuously for longer than the 500ms threshold, preventing accidental triggers from brief contacts.
When a button-down event occurs, OpenLogi's input layer records the timestamp and monitors elapsed time on each subsequent tick. If the button releases before exceeding the threshold, the system processes any configured short-press binding and discards the long-press candidate.
Short-Press Binding Implementation
Short-press represents the default binding mode in OpenLogi, optimized for responsiveness and immediate feedback.
According to the OpenLogi source code in crates/openlogi-core/src/binding.rs, short-press actions commit to the state machine without wrapping in duration-tracking types. These bindings execute as soon as the input layer registers the button event, making them ideal for high-frequency operations like copy, undo, or paste that must respond instantly to user input.
The dispatch logic bypasses the threshold checking mechanism entirely, ensuring zero latency beyond the hardware's native report rate.
Long-Press Binding Implementation
Long-press bindings introduce deliberate latency to prevent accidental activation of secondary functions.
The LONG_PRESS_THRESHOLD Constant
The threshold value resides in crates/openlogi-core/src/binding.rs at line 43, where LONG_PRESS_THRESHOLD defines the default 500ms duration that distinguishes long-press from short-press events. This constant is wrapped by the LongPressBinding type defined in crates/openlogi-core/src/value.rs.
When the input subsystem receives a button event, it calculates elapsed time against this threshold. Once the duration exceeds 500ms, the LongPressBinding becomes active and dispatches the associated action to the device or GUI.
Fallback Behavior
If the user releases the button before the 500ms threshold elapses, OpenLogi discards the long-press binding and falls back to any configured short-press binding for that button. This creates a hierarchical input system where brief interactions trigger primary actions while sustained holds access secondary functions like custom scripts or mode switches.
Practical Code Implementation
The binding system distinguishes these modes through type wrapping and module organization.
use openlogi_core::binding::{Action, LongPressBinding, LONG_PRESS_THRESHOLD};
// Short-press binding: fires immediately on button press
state.commit_binding(ButtonId::Back, Action::Undo);
// Long-press binding: fires only after exceeding the 500ms threshold
state.commit_binding(
ButtonId::Back,
Action::LongPress(LongPressBinding::new(Action::Copy)),
);
In this example, quickly pressing the Back button triggers Undo immediately. Holding Back for longer than LONG_PRESS_THRESHOLD (500ms) suppresses the undo action and instead triggers Copy.
Key Source Files and Architecture
Understanding the file organization clarifies how these semantics propagate through the system:
crates/openlogi-core/src/binding.rs– DefinesLONG_PRESS_THRESHOLDat line 43 and exports the core binding types includingLongPressBinding.crates/openlogi-core/src/value.rs– Contains the concrete implementation ofLongPressBindingand the threshold value storage.crates/openlogi-device/src/session/gesture.rs– Implements gesture recognition logic that respects press-duration semantics for wheel-based actions while holding buttons.crates/openlogi-desktop/src/state/bindings.rs– Manages per-application and global binding tables that store both short-press and long-press entries, handling the dispatch logic based on elapsed time calculations.
Summary
- Short-press bindings in OpenLogi fire immediately upon button activation without checking timing thresholds, making them suitable for primary, high-frequency actions.
- Long-press bindings wrap actions in the
LongPressBindingtype and only execute after the button is held longer than the 500msLONG_PRESS_THRESHOLDdefined incrates/openlogi-core/src/binding.rs. - The input layer timestamps button-down events and monitors elapsed time; if the button releases before the threshold, the system falls back to short-press behavior.
- This SOOM threshold model allows single buttons to multiplex two distinct actions based purely on press duration, implemented across the core, device, and desktop crates.
Frequently Asked Questions
What is the default long-press threshold in OpenLogi?
OpenLogi uses a default 500ms threshold defined by the LONG_PRESS_THRESHOLD constant located at line 43 of crates/openlogi-core/src/binding.rs. This value determines how long a button must be held to trigger a long-press binding instead of a short-press action.
How does OpenLogi handle conflicting short-press and long-press bindings on the same button?
OpenLogi processes these bindings hierarchically. When a button is pressed, the system waits to see if the hold duration exceeds LONG_PRESS_THRESHOLD. If the user releases the button before 500ms elapse, the long-press binding is discarded and the short-press binding fires. If the threshold is exceeded, the long-press binding activates and the short-press action is suppressed.
Where is the long-press timing logic implemented in the source code?
The timing logic spans multiple crates. The threshold constant and LongPressBinding wrapper are defined in crates/openlogi-core/src/binding.rs and crates/openlogi-core/src/value.rs. The actual dispatch and fallback logic is implemented in crates/openlogi-desktop/src/state/bindings.rs, while gesture-specific timing is handled in crates/openlogi-device/src/session/gesture.rs.
Can the long-press threshold duration be customized?
Yes, the threshold is configurable through the LONG_PRESS_THRESHOLD constant. Developers can modify this value in crates/openlogi-core/src/binding.rs to adjust the sensitivity of long-press detection, though the default 500ms provides a balanced trade-off between responsiveness and accidental trigger prevention for most use cases.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →