mirror of
https://github.com/hyprwm/Hyprland
synced 2024-11-24 01:45:59 +01:00
keyboard mod fixes
This commit is contained in:
parent
12c5de14c8
commit
e1adef12f5
6 changed files with 49 additions and 53 deletions
|
@ -1114,7 +1114,7 @@ std::string switchXKBLayoutRequest(eHyprCtlOutputFormat format, std::string requ
|
||||||
const auto LAYOUTS = xkb_keymap_num_layouts(KEEB->xkbKeymap);
|
const auto LAYOUTS = xkb_keymap_num_layouts(KEEB->xkbKeymap);
|
||||||
xkb_layout_index_t activeLayout = 0;
|
xkb_layout_index_t activeLayout = 0;
|
||||||
while (activeLayout < LAYOUTS) {
|
while (activeLayout < LAYOUTS) {
|
||||||
if (xkb_state_layout_index_is_active(KEEB->xkbTranslationState, activeLayout, XKB_STATE_LAYOUT_EFFECTIVE) == 1)
|
if (xkb_state_layout_index_is_active(KEEB->xkbState, activeLayout, XKB_STATE_LAYOUT_EFFECTIVE) == 1)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
activeLayout++;
|
activeLayout++;
|
||||||
|
|
|
@ -27,11 +27,11 @@ IKeyboard::~IKeyboard() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void IKeyboard::clearManuallyAllocd() {
|
void IKeyboard::clearManuallyAllocd() {
|
||||||
if (xkbTranslationState)
|
if (xkbStaticState)
|
||||||
xkb_state_unref(xkbTranslationState);
|
xkb_state_unref(xkbStaticState);
|
||||||
|
|
||||||
if (xkbInternalTranslationState)
|
if (xkbState)
|
||||||
xkb_state_unref(xkbInternalTranslationState);
|
xkb_state_unref(xkbState);
|
||||||
|
|
||||||
if (xkbKeymap)
|
if (xkbKeymap)
|
||||||
xkb_keymap_unref(xkbKeymap);
|
xkb_keymap_unref(xkbKeymap);
|
||||||
|
@ -40,7 +40,8 @@ void IKeyboard::clearManuallyAllocd() {
|
||||||
close(xkbKeymapFD);
|
close(xkbKeymapFD);
|
||||||
|
|
||||||
xkbKeymap = nullptr;
|
xkbKeymap = nullptr;
|
||||||
xkbTranslationState = nullptr;
|
xkbState = nullptr;
|
||||||
|
xkbStaticState = nullptr;
|
||||||
xkbKeymapFD = -1;
|
xkbKeymapFD = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -99,9 +100,9 @@ void IKeyboard::setKeymap(const SStringRuleNames& rules) {
|
||||||
|
|
||||||
// set internal translation state
|
// set internal translation state
|
||||||
// demo sunao ni ienai
|
// demo sunao ni ienai
|
||||||
xkbInternalTranslationState = xkb_state_new(xkbKeymap);
|
xkbStaticState = xkb_state_new(xkbKeymap);
|
||||||
|
|
||||||
updateXKBTranslationState();
|
updateXKBTranslationState(xkbKeymap);
|
||||||
|
|
||||||
const auto NUMLOCKON = g_pConfigManager->getDeviceInt(hlName, "numlock_by_default", "input:numlock_by_default");
|
const auto NUMLOCKON = g_pConfigManager->getDeviceInt(hlName, "numlock_by_default", "input:numlock_by_default");
|
||||||
|
|
||||||
|
@ -151,17 +152,17 @@ void IKeyboard::setKeymap(const SStringRuleNames& rules) {
|
||||||
|
|
||||||
void IKeyboard::updateXKBTranslationState(xkb_keymap* const keymap) {
|
void IKeyboard::updateXKBTranslationState(xkb_keymap* const keymap) {
|
||||||
|
|
||||||
if (xkbTranslationState)
|
if (xkbState)
|
||||||
xkb_state_unref(xkbTranslationState);
|
xkb_state_unref(xkbState);
|
||||||
|
|
||||||
if (keymap) {
|
if (keymap) {
|
||||||
Debug::log(LOG, "Updating keyboard {:x}'s translation state from a provided keymap", (uintptr_t)this);
|
Debug::log(LOG, "Updating keyboard {:x}'s translation state from a provided keymap", (uintptr_t)this);
|
||||||
xkbTranslationState = xkb_state_new(keymap);
|
xkbState = xkb_state_new(keymap);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto KEYMAP = xkbKeymap;
|
const auto KEYMAP = xkbKeymap;
|
||||||
const auto STATE = xkbInternalTranslationState;
|
const auto STATE = xkbState;
|
||||||
const auto LAYOUTSNUM = xkb_keymap_num_layouts(KEYMAP);
|
const auto LAYOUTSNUM = xkb_keymap_num_layouts(KEYMAP);
|
||||||
|
|
||||||
const auto PCONTEXT = xkb_context_new(XKB_CONTEXT_NO_FLAGS);
|
const auto PCONTEXT = xkb_context_new(XKB_CONTEXT_NO_FLAGS);
|
||||||
|
@ -200,7 +201,7 @@ void IKeyboard::updateXKBTranslationState(xkb_keymap* const keymap) {
|
||||||
KEYMAP = xkb_keymap_new_from_names(PCONTEXT, &rules, XKB_KEYMAP_COMPILE_NO_FLAGS);
|
KEYMAP = xkb_keymap_new_from_names(PCONTEXT, &rules, XKB_KEYMAP_COMPILE_NO_FLAGS);
|
||||||
}
|
}
|
||||||
|
|
||||||
xkbTranslationState = xkb_state_new(KEYMAP);
|
xkbState = xkb_state_new(KEYMAP);
|
||||||
|
|
||||||
xkb_keymap_unref(KEYMAP);
|
xkb_keymap_unref(KEYMAP);
|
||||||
xkb_context_unref(PCONTEXT);
|
xkb_context_unref(PCONTEXT);
|
||||||
|
@ -221,7 +222,7 @@ void IKeyboard::updateXKBTranslationState(xkb_keymap* const keymap) {
|
||||||
|
|
||||||
const auto NEWKEYMAP = xkb_keymap_new_from_names(PCONTEXT, &rules, XKB_KEYMAP_COMPILE_NO_FLAGS);
|
const auto NEWKEYMAP = xkb_keymap_new_from_names(PCONTEXT, &rules, XKB_KEYMAP_COMPILE_NO_FLAGS);
|
||||||
|
|
||||||
xkbTranslationState = xkb_state_new(NEWKEYMAP);
|
xkbState = xkb_state_new(NEWKEYMAP);
|
||||||
|
|
||||||
xkb_keymap_unref(NEWKEYMAP);
|
xkb_keymap_unref(NEWKEYMAP);
|
||||||
xkb_context_unref(PCONTEXT);
|
xkb_context_unref(PCONTEXT);
|
||||||
|
@ -229,7 +230,7 @@ void IKeyboard::updateXKBTranslationState(xkb_keymap* const keymap) {
|
||||||
|
|
||||||
std::string IKeyboard::getActiveLayout() {
|
std::string IKeyboard::getActiveLayout() {
|
||||||
const auto KEYMAP = xkbKeymap;
|
const auto KEYMAP = xkbKeymap;
|
||||||
const auto STATE = xkbTranslationState;
|
const auto STATE = xkbState;
|
||||||
const auto LAYOUTSNUM = xkb_keymap_num_layouts(KEYMAP);
|
const auto LAYOUTSNUM = xkb_keymap_num_layouts(KEYMAP);
|
||||||
|
|
||||||
for (uint32_t i = 0; i < LAYOUTSNUM; ++i) {
|
for (uint32_t i = 0; i < LAYOUTSNUM; ++i) {
|
||||||
|
@ -246,12 +247,12 @@ std::string IKeyboard::getActiveLayout() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void IKeyboard::updateLEDs() {
|
void IKeyboard::updateLEDs() {
|
||||||
if (xkbTranslationState == nullptr)
|
if (xkbState == nullptr)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
uint32_t leds = 0;
|
uint32_t leds = 0;
|
||||||
for (uint32_t i = 0; i < WLR_LED_COUNT; ++i) {
|
for (uint32_t i = 0; i < WLR_LED_COUNT; ++i) {
|
||||||
if (xkb_state_led_index_is_active(xkbTranslationState, ledIndexes.at(i)))
|
if (xkb_state_led_index_is_active(xkbState, ledIndexes.at(i)))
|
||||||
leds |= (1 << i);
|
leds |= (1 << i);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -259,7 +260,7 @@ void IKeyboard::updateLEDs() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void IKeyboard::updateLEDs(uint32_t leds) {
|
void IKeyboard::updateLEDs(uint32_t leds) {
|
||||||
if (!xkbTranslationState)
|
if (!xkbState)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (isVirtual() && g_pInputManager->shouldIgnoreVirtualKeyboard(self.lock()))
|
if (isVirtual() && g_pInputManager->shouldIgnoreVirtualKeyboard(self.lock()))
|
||||||
|
@ -288,10 +289,10 @@ uint32_t IKeyboard::getModifiers() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void IKeyboard::updateModifiers(uint32_t depressed, uint32_t latched, uint32_t locked, uint32_t group) {
|
void IKeyboard::updateModifiers(uint32_t depressed, uint32_t latched, uint32_t locked, uint32_t group) {
|
||||||
if (!xkbTranslationState)
|
if (!xkbState)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
xkb_state_update_mask(xkbTranslationState, depressed, latched, locked, 0, 0, group);
|
xkb_state_update_mask(xkbState, depressed, latched, locked, 0, 0, group);
|
||||||
|
|
||||||
if (!updateModifiersState())
|
if (!updateModifiersState())
|
||||||
return;
|
return;
|
||||||
|
@ -300,13 +301,13 @@ void IKeyboard::updateModifiers(uint32_t depressed, uint32_t latched, uint32_t l
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IKeyboard::updateModifiersState() {
|
bool IKeyboard::updateModifiersState() {
|
||||||
if (!xkbTranslationState)
|
if (!xkbState)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
auto depressed = xkb_state_serialize_mods(xkbTranslationState, XKB_STATE_MODS_DEPRESSED);
|
auto depressed = xkb_state_serialize_mods(xkbState, XKB_STATE_MODS_DEPRESSED);
|
||||||
auto latched = xkb_state_serialize_mods(xkbTranslationState, XKB_STATE_MODS_LATCHED);
|
auto latched = xkb_state_serialize_mods(xkbState, XKB_STATE_MODS_LATCHED);
|
||||||
auto locked = xkb_state_serialize_mods(xkbTranslationState, XKB_STATE_MODS_LOCKED);
|
auto locked = xkb_state_serialize_mods(xkbState, XKB_STATE_MODS_LOCKED);
|
||||||
auto group = xkb_state_serialize_layout(xkbTranslationState, XKB_STATE_LAYOUT_EFFECTIVE);
|
auto group = xkb_state_serialize_layout(xkbState, XKB_STATE_LAYOUT_EFFECTIVE);
|
||||||
|
|
||||||
if (depressed == modifiersState.depressed && latched == modifiersState.latched && locked == modifiersState.locked && group == modifiersState.group)
|
if (depressed == modifiersState.depressed && latched == modifiersState.latched && locked == modifiersState.locked && group == modifiersState.group)
|
||||||
return false;
|
return false;
|
||||||
|
@ -318,3 +319,15 @@ bool IKeyboard::updateModifiersState() {
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void IKeyboard::updateXkbStateWithKey(uint32_t xkbKey, bool pressed) {
|
||||||
|
xkb_state_update_key(xkbState, xkbKey, pressed ? XKB_KEY_DOWN : XKB_KEY_UP);
|
||||||
|
if (updateModifiersState()) {
|
||||||
|
keyboardEvents.modifiers.emit(SModifiersEvent{
|
||||||
|
.depressed = modifiersState.depressed,
|
||||||
|
.latched = modifiersState.latched,
|
||||||
|
.locked = modifiersState.locked,
|
||||||
|
.group = modifiersState.group,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -58,12 +58,13 @@ class IKeyboard : public IHID {
|
||||||
uint32_t getModifiers();
|
uint32_t getModifiers();
|
||||||
void updateModifiers(uint32_t depressed, uint32_t latched, uint32_t locked, uint32_t group);
|
void updateModifiers(uint32_t depressed, uint32_t latched, uint32_t locked, uint32_t group);
|
||||||
bool updateModifiersState(); // rets whether changed
|
bool updateModifiersState(); // rets whether changed
|
||||||
|
void updateXkbStateWithKey(uint32_t xkbKey, bool pressed);
|
||||||
|
|
||||||
bool active = false;
|
bool active = false;
|
||||||
bool enabled = true;
|
bool enabled = true;
|
||||||
|
|
||||||
xkb_layout_index_t activeLayout = 0;
|
xkb_layout_index_t activeLayout = 0;
|
||||||
xkb_state * xkbTranslationState = nullptr, *xkbInternalTranslationState = nullptr;
|
xkb_state * xkbState = nullptr, *xkbStaticState /* Static state: never gets modifiers or layout changes sent, used for keybinds. */ = nullptr;
|
||||||
xkb_keymap* xkbKeymap = nullptr;
|
xkb_keymap* xkbKeymap = nullptr;
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
|
|
|
@ -32,12 +32,7 @@ CKeyboard::CKeyboard(SP<Aquamarine::IKeyboard> keeb) : keyboard(keeb) {
|
||||||
listeners.key = keeb->events.key.registerListener([this](std::any d) {
|
listeners.key = keeb->events.key.registerListener([this](std::any d) {
|
||||||
auto E = std::any_cast<Aquamarine::IKeyboard::SKeyEvent>(d);
|
auto E = std::any_cast<Aquamarine::IKeyboard::SKeyEvent>(d);
|
||||||
|
|
||||||
uint32_t xkbKeycode = E.key + 8;
|
updateXkbStateWithKey(E.key + 8, E.pressed);
|
||||||
xkb_state_update_key(xkbTranslationState, xkbKeycode, E.pressed ? XKB_KEY_DOWN : XKB_KEY_UP);
|
|
||||||
|
|
||||||
// we have to do this for DRM sessions, as they never send modifiers events
|
|
||||||
if (g_pCompositor->m_pAqBackend->hasSession())
|
|
||||||
updateModifiersState();
|
|
||||||
|
|
||||||
keyboardEvents.key.emit(SKeyEvent{
|
keyboardEvents.key.emit(SKeyEvent{
|
||||||
.timeMs = E.timeMs,
|
.timeMs = E.timeMs,
|
||||||
|
|
|
@ -366,8 +366,8 @@ bool CKeybindManager::onKeyEvent(std::any event, SP<IKeyboard> pKeyboard) {
|
||||||
|
|
||||||
const auto KEYCODE = e.keycode + 8; // Because to xkbcommon it's +8 from libinput
|
const auto KEYCODE = e.keycode + 8; // Because to xkbcommon it's +8 from libinput
|
||||||
|
|
||||||
const xkb_keysym_t keysym = xkb_state_key_get_one_sym(pKeyboard->resolveBindsBySym ? pKeyboard->xkbTranslationState : m_pXKBTranslationState, KEYCODE);
|
const xkb_keysym_t keysym = xkb_state_key_get_one_sym(pKeyboard->resolveBindsBySym ? pKeyboard->xkbStaticState : m_pXKBTranslationState, KEYCODE);
|
||||||
const xkb_keysym_t internalKeysym = xkb_state_key_get_one_sym(pKeyboard->xkbInternalTranslationState, KEYCODE);
|
const xkb_keysym_t internalKeysym = xkb_state_key_get_one_sym(pKeyboard->xkbState, KEYCODE);
|
||||||
|
|
||||||
if (handleInternalKeybinds(internalKeysym))
|
if (handleInternalKeybinds(internalKeysym))
|
||||||
return true;
|
return true;
|
||||||
|
@ -2121,7 +2121,7 @@ void CKeybindManager::sendshortcut(std::string args) {
|
||||||
|
|
||||||
if (!g_pKeybindManager->m_mKeyToCodeCache.contains(KEYPAIRSTRING)) {
|
if (!g_pKeybindManager->m_mKeyToCodeCache.contains(KEYPAIRSTRING)) {
|
||||||
xkb_keymap* km = KB->xkbKeymap;
|
xkb_keymap* km = KB->xkbKeymap;
|
||||||
xkb_state* ks = KB->xkbTranslationState;
|
xkb_state* ks = KB->xkbState;
|
||||||
|
|
||||||
xkb_keycode_t keycode_min, keycode_max;
|
xkb_keycode_t keycode_min, keycode_max;
|
||||||
keycode_min = xkb_keymap_min_keycode(km);
|
keycode_min = xkb_keymap_min_keycode(km);
|
||||||
|
|
|
@ -1156,10 +1156,6 @@ static void removeFromHIDs(WP<IHID> hid) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void CInputManager::destroyKeyboard(SP<IKeyboard> pKeyboard) {
|
void CInputManager::destroyKeyboard(SP<IKeyboard> pKeyboard) {
|
||||||
if (pKeyboard->xkbTranslationState)
|
|
||||||
xkb_state_unref(pKeyboard->xkbTranslationState);
|
|
||||||
pKeyboard->xkbTranslationState = nullptr;
|
|
||||||
|
|
||||||
std::erase_if(m_vKeyboards, [pKeyboard](const auto& other) { return other == pKeyboard; });
|
std::erase_if(m_vKeyboards, [pKeyboard](const auto& other) { return other == pKeyboard; });
|
||||||
|
|
||||||
if (m_vKeyboards.size() > 0) {
|
if (m_vKeyboards.size() > 0) {
|
||||||
|
@ -1225,19 +1221,10 @@ void CInputManager::destroyTabletPad(SP<CTabletPad> pad) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void CInputManager::updateKeyboardsLeds(SP<IKeyboard> pKeyboard) {
|
void CInputManager::updateKeyboardsLeds(SP<IKeyboard> pKeyboard) {
|
||||||
if (!pKeyboard || !pKeyboard->xkbTranslationState)
|
if (!pKeyboard)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// FIXME:
|
pKeyboard->updateLEDs();
|
||||||
// uint32_t leds = 0;
|
|
||||||
// for (uint32_t i = 0; i < WLR_LED_COUNT; ++i) {
|
|
||||||
// if (xkb_state_led_index_is_active(pKeyboard->xkbTranslationState, keyboard->led_indexes[i]))
|
|
||||||
// leds |= (1 << i);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// for (auto& k : m_vKeyboards) {
|
|
||||||
// k->updateLEDs(leds);
|
|
||||||
// }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void CInputManager::onKeyboardKey(std::any event, SP<IKeyboard> pKeyboard) {
|
void CInputManager::onKeyboardKey(std::any event, SP<IKeyboard> pKeyboard) {
|
||||||
|
|
Loading…
Reference in a new issue