From e3373669e5544c3f18cf1edcd8fcfff9c6222f5c Mon Sep 17 00:00:00 2001 From: Vaxry Date: Tue, 27 Feb 2024 23:14:56 +0000 Subject: [PATCH] wayland: implement keyboard_shortcuts_inhibit_v1 fixes #4568 --- src/Compositor.cpp | 2 ++ src/events/Events.hpp | 3 +++ src/events/Misc.cpp | 17 +++++++++++++++++ src/helpers/WLClasses.hpp | 10 ++++++++++ src/managers/KeybindManager.cpp | 9 +++++++++ src/managers/KeybindManager.hpp | 1 + 6 files changed, 42 insertions(+) diff --git a/src/Compositor.cpp b/src/Compositor.cpp index c290a49d8d7..f0d7ca0f562 100644 --- a/src/Compositor.cpp +++ b/src/Compositor.cpp @@ -307,6 +307,7 @@ void CCompositor::initAllSignals() { addWLSignal(&m_sWLRGammaCtrlMgr->events.set_gamma, &Events::listen_setGamma, m_sWLRGammaCtrlMgr, "GammaCtrlMgr"); addWLSignal(&m_sWLRCursorShapeMgr->events.request_set_shape, &Events::listen_setCursorShape, m_sWLRCursorShapeMgr, "CursorShapeMgr"); addWLSignal(&m_sWLRTearingControlMgr->events.new_object, &Events::listen_newTearingHint, m_sWLRTearingControlMgr, "TearingControlMgr"); + addWLSignal(&m_sWLRKbShInhibitMgr->events.new_inhibitor, &Events::listen_newShortcutInhibitor, m_sWLRKbShInhibitMgr, "ShortcutInhibitMgr"); if (m_sWRLDRMLeaseMgr) addWLSignal(&m_sWRLDRMLeaseMgr->events.request, &Events::listen_leaseRequest, &m_sWRLDRMLeaseMgr, "DRM"); @@ -360,6 +361,7 @@ void CCompositor::removeAllSignals() { removeWLSignal(&Events::listen_setGamma); removeWLSignal(&Events::listen_setCursorShape); removeWLSignal(&Events::listen_newTearingHint); + removeWLSignal(&Events::listen_newShortcutInhibitor); if (m_sWRLDRMLeaseMgr) removeWLSignal(&Events::listen_leaseRequest); diff --git a/src/events/Events.hpp b/src/events/Events.hpp index 777bdf9f88e..8b737f3212e 100644 --- a/src/events/Events.hpp +++ b/src/events/Events.hpp @@ -174,4 +174,7 @@ namespace Events { // Tearing hints LISTENER(newTearingHint); + + // Shortcut inhibitor + LISTENER(newShortcutInhibitor); }; diff --git a/src/events/Misc.cpp b/src/events/Misc.cpp index b77cf0389de..35721832d53 100644 --- a/src/events/Misc.cpp +++ b/src/events/Misc.cpp @@ -262,3 +262,20 @@ void Events::listener_newTearingHint(wl_listener* listener, void* data) { }, NEWCTRL, "TearingController"); } + +void Events::listener_newShortcutInhibitor(wl_listener* listener, void* data) { + const auto INHIBITOR = (wlr_keyboard_shortcuts_inhibitor_v1*)data; + + const auto PINH = &g_pKeybindManager->m_lShortcutInhibitors.emplace_back(); + PINH->hyprListener_destroy.initCallback( + &INHIBITOR->events.destroy, + [](void* owner, void* data) { + const auto OWNER = (SShortcutInhibitor*)owner; + g_pKeybindManager->m_lShortcutInhibitors.remove(*OWNER); + }, + PINH, "ShortcutInhibitor"); + + PINH->pWlrInhibitor = INHIBITOR; + + Debug::log(LOG, "New shortcut inhibitor for surface {:x}", (uintptr_t)INHIBITOR->surface); +} diff --git a/src/helpers/WLClasses.hpp b/src/helpers/WLClasses.hpp index 8cfee18a089..02681f485cb 100644 --- a/src/helpers/WLClasses.hpp +++ b/src/helpers/WLClasses.hpp @@ -412,3 +412,13 @@ struct STearingController { return pWlrHint == other.pWlrHint; } }; + +struct SShortcutInhibitor { + wlr_keyboard_shortcuts_inhibitor_v1* pWlrInhibitor = nullptr; + + DYNLISTENER(destroy); + + bool operator==(const SShortcutInhibitor& other) { + return pWlrInhibitor == other.pWlrInhibitor; + } +}; diff --git a/src/managers/KeybindManager.cpp b/src/managers/KeybindManager.cpp index 85598f204b7..198aa8f6d63 100644 --- a/src/managers/KeybindManager.cpp +++ b/src/managers/KeybindManager.cpp @@ -497,6 +497,15 @@ bool CKeybindManager::handleKeybinds(const uint32_t modmask, const SPressedKeyWi if (g_pCompositor->m_sSeat.exclusiveClient) Debug::log(LOG, "Keybind handling only locked (inhibitor)"); + if (!m_lShortcutInhibitors.empty()) { + for (auto& i : m_lShortcutInhibitors) { + if (i.pWlrInhibitor->surface == g_pCompositor->m_pLastFocus) { + Debug::log(LOG, "Keybind handling is disabled due to an inhibitor for surface {:x}", (uintptr_t)i.pWlrInhibitor->surface); + return false; + } + } + } + for (auto& k : m_lKeybinds) { const bool SPECIALDISPATCHER = k.handler == "global" || k.handler == "pass" || k.handler == "mouse"; const bool SPECIALTRIGGERED = diff --git a/src/managers/KeybindManager.hpp b/src/managers/KeybindManager.hpp index 7022593a054..edd9ede253d 100644 --- a/src/managers/KeybindManager.hpp +++ b/src/managers/KeybindManager.hpp @@ -70,6 +70,7 @@ class CKeybindManager { bool m_bGroupsLocked = false; std::list m_lKeybinds; + std::list m_lShortcutInhibitors; private: std::deque m_dPressedKeys;