mirror of
https://github.com/hyprwm/Hyprland
synced 2024-11-22 16:05:58 +01:00
input: Emulate discrete scrolling from v120 events (#6881)
* seat: avoid sending axis_stop() when source is wheel * fix rounding for absolute discrete values greater than 1 Co-authored-by: Agent_00Ming <agent00ming9366@gmail.com>
This commit is contained in:
parent
300228b503
commit
8e15f91c24
4 changed files with 49 additions and 6 deletions
|
@ -472,6 +472,7 @@ CConfigManager::CConfigManager() {
|
||||||
m_pConfig->addConfigValue("input:scroll_button_lock", Hyprlang::INT{0});
|
m_pConfig->addConfigValue("input:scroll_button_lock", Hyprlang::INT{0});
|
||||||
m_pConfig->addConfigValue("input:scroll_factor", {1.f});
|
m_pConfig->addConfigValue("input:scroll_factor", {1.f});
|
||||||
m_pConfig->addConfigValue("input:scroll_points", {STRVAL_EMPTY});
|
m_pConfig->addConfigValue("input:scroll_points", {STRVAL_EMPTY});
|
||||||
|
m_pConfig->addConfigValue("input:emulate_discrete_scroll", Hyprlang::INT{1});
|
||||||
m_pConfig->addConfigValue("input:touchpad:natural_scroll", Hyprlang::INT{0});
|
m_pConfig->addConfigValue("input:touchpad:natural_scroll", Hyprlang::INT{0});
|
||||||
m_pConfig->addConfigValue("input:touchpad:disable_while_typing", Hyprlang::INT{1});
|
m_pConfig->addConfigValue("input:touchpad:disable_while_typing", Hyprlang::INT{1});
|
||||||
m_pConfig->addConfigValue("input:touchpad:clickfinger_behavior", Hyprlang::INT{0});
|
m_pConfig->addConfigValue("input:touchpad:clickfinger_behavior", Hyprlang::INT{0});
|
||||||
|
|
|
@ -333,9 +333,7 @@ void CSeatManager::sendPointerAxis(uint32_t timeMs, wl_pointer_axis axis, double
|
||||||
if (source == 0) {
|
if (source == 0) {
|
||||||
p->sendAxisValue120(axis, value120);
|
p->sendAxisValue120(axis, value120);
|
||||||
p->sendAxisDiscrete(axis, discrete);
|
p->sendAxisDiscrete(axis, discrete);
|
||||||
}
|
} else if (value == 0)
|
||||||
|
|
||||||
if (value == 0)
|
|
||||||
p->sendAxisStop(timeMs, axis);
|
p->sendAxisStop(timeMs, axis);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -760,6 +760,7 @@ void CInputManager::onMouseWheel(IPointer::SAxisEvent e) {
|
||||||
static auto POFFWINDOWAXIS = CConfigValue<Hyprlang::INT>("input:off_window_axis_events");
|
static auto POFFWINDOWAXIS = CConfigValue<Hyprlang::INT>("input:off_window_axis_events");
|
||||||
static auto PINPUTSCROLLFACTOR = CConfigValue<Hyprlang::FLOAT>("input:scroll_factor");
|
static auto PINPUTSCROLLFACTOR = CConfigValue<Hyprlang::FLOAT>("input:scroll_factor");
|
||||||
static auto PTOUCHPADSCROLLFACTOR = CConfigValue<Hyprlang::FLOAT>("input:touchpad:scroll_factor");
|
static auto PTOUCHPADSCROLLFACTOR = CConfigValue<Hyprlang::FLOAT>("input:touchpad:scroll_factor");
|
||||||
|
static auto PEMULATEDISCRETE = CConfigValue<Hyprlang::INT>("input:emulate_discrete_scroll");
|
||||||
|
|
||||||
auto factor = (*PTOUCHPADSCROLLFACTOR <= 0.f || e.source == WL_POINTER_AXIS_SOURCE_FINGER ? *PTOUCHPADSCROLLFACTOR : *PINPUTSCROLLFACTOR);
|
auto factor = (*PTOUCHPADSCROLLFACTOR <= 0.f || e.source == WL_POINTER_AXIS_SOURCE_FINGER ? *PTOUCHPADSCROLLFACTOR : *PINPUTSCROLLFACTOR);
|
||||||
|
|
||||||
|
@ -798,9 +799,44 @@ void CInputManager::onMouseWheel(IPointer::SAxisEvent e) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
double deltaDiscrete = (e.deltaDiscrete != 0) ? (factor * e.deltaDiscrete / std::abs(e.deltaDiscrete)) : 0;
|
|
||||||
g_pSeatManager->sendPointerAxis(e.timeMs, e.axis, factor * e.delta, deltaDiscrete > 0 ? std::ceil(deltaDiscrete) : std::floor(deltaDiscrete),
|
double discrete = (e.deltaDiscrete != 0) ? (factor * e.deltaDiscrete / std::abs(e.deltaDiscrete)) : 0;
|
||||||
std::round(factor * e.deltaDiscrete), e.source, WL_POINTER_AXIS_RELATIVE_DIRECTION_IDENTICAL);
|
double delta = e.delta * factor;
|
||||||
|
|
||||||
|
if (e.source == 0) {
|
||||||
|
// if an application supports v120, it should ignore discrete anyways
|
||||||
|
if ((*PEMULATEDISCRETE >= 1 && std::abs(e.deltaDiscrete) != 120) || *PEMULATEDISCRETE >= 2) {
|
||||||
|
|
||||||
|
const int interval = factor != 0 ? std::round(120 * (1 / factor)) : 120;
|
||||||
|
|
||||||
|
// reset the accumulator when timeout is reached or direction/axis has changed
|
||||||
|
if (std::signbit(e.deltaDiscrete) != m_ScrollWheelState.lastEventSign || e.axis != m_ScrollWheelState.lastEventAxis ||
|
||||||
|
e.timeMs - m_ScrollWheelState.lastEventTime > 500 /* 500ms taken from libinput default timeout */) {
|
||||||
|
|
||||||
|
m_ScrollWheelState.accumulatedScroll = 0;
|
||||||
|
// send 1 discrete on first event for responsiveness
|
||||||
|
discrete = std::copysign(1, e.deltaDiscrete);
|
||||||
|
} else
|
||||||
|
discrete = 0;
|
||||||
|
|
||||||
|
for (int ac = m_ScrollWheelState.accumulatedScroll; ac >= interval; ac -= interval) {
|
||||||
|
discrete += std::copysign(1, e.deltaDiscrete);
|
||||||
|
m_ScrollWheelState.accumulatedScroll -= interval;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_ScrollWheelState.lastEventSign = std::signbit(e.deltaDiscrete);
|
||||||
|
m_ScrollWheelState.lastEventAxis = e.axis;
|
||||||
|
m_ScrollWheelState.lastEventTime = e.timeMs;
|
||||||
|
m_ScrollWheelState.accumulatedScroll += std::abs(e.deltaDiscrete);
|
||||||
|
|
||||||
|
delta = 15.0 * discrete * factor;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t value120 = std::round(factor * e.deltaDiscrete);
|
||||||
|
int32_t deltaDiscrete = std::abs(discrete) != 0 && std::abs(discrete) < 1 ? std::copysign(1, discrete) : std::round(discrete);
|
||||||
|
|
||||||
|
g_pSeatManager->sendPointerAxis(e.timeMs, e.axis, delta, deltaDiscrete, value120, e.source, WL_POINTER_AXIS_RELATIVE_DIRECTION_IDENTICAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
Vector2D CInputManager::getMouseCoordsInternal() {
|
Vector2D CInputManager::getMouseCoordsInternal() {
|
||||||
|
|
|
@ -278,6 +278,14 @@ class CInputManager {
|
||||||
|
|
||||||
void restoreCursorIconToApp(); // no-op if restored
|
void restoreCursorIconToApp(); // no-op if restored
|
||||||
|
|
||||||
|
// discrete scrolling emulation using v120 data
|
||||||
|
struct {
|
||||||
|
bool lastEventSign = 0;
|
||||||
|
bool lastEventAxis = 0;
|
||||||
|
uint32_t lastEventTime = 0;
|
||||||
|
uint32_t accumulatedScroll = 0;
|
||||||
|
} m_ScrollWheelState;
|
||||||
|
|
||||||
friend class CKeybindManager;
|
friend class CKeybindManager;
|
||||||
friend class CWLSurface;
|
friend class CWLSurface;
|
||||||
};
|
};
|
||||||
|
|
Loading…
Reference in a new issue