virtualkeyboard: Add options to skip releasing pressed keys on close and to skip sharing key states (#11214)
This commit is contained in:
parent
6491bb4fb7
commit
2be309de1d
23 changed files with 416 additions and 137 deletions
|
|
@ -378,19 +378,6 @@ bool IKeyboard::updateModifiersState() {
|
|||
}
|
||||
|
||||
void IKeyboard::updateXkbStateWithKey(uint32_t xkbKey, bool pressed) {
|
||||
|
||||
const auto contains = std::ranges::find(m_pressedXKB, xkbKey) != m_pressedXKB.end();
|
||||
|
||||
if (contains && pressed)
|
||||
return;
|
||||
if (!contains && !pressed)
|
||||
return;
|
||||
|
||||
if (contains)
|
||||
std::erase(m_pressedXKB, xkbKey);
|
||||
else
|
||||
m_pressedXKB.emplace_back(xkbKey);
|
||||
|
||||
xkb_state_update_key(m_xkbState, xkbKey, pressed ? XKB_KEY_DOWN : XKB_KEY_UP);
|
||||
|
||||
if (updateModifiersState()) {
|
||||
|
|
@ -405,3 +392,27 @@ void IKeyboard::updateXkbStateWithKey(uint32_t xkbKey, bool pressed) {
|
|||
});
|
||||
}
|
||||
}
|
||||
|
||||
bool IKeyboard::updatePressed(uint32_t key, bool pressed) {
|
||||
const auto contains = getPressed(key);
|
||||
|
||||
if (contains && pressed)
|
||||
return false;
|
||||
if (!contains && !pressed)
|
||||
return false;
|
||||
|
||||
if (contains)
|
||||
std::erase(m_pressed, key);
|
||||
else
|
||||
m_pressed.emplace_back(key);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool IKeyboard::getPressed(uint32_t key) {
|
||||
return std::ranges::contains(m_pressed, key);
|
||||
}
|
||||
|
||||
bool IKeyboard::shareStates() {
|
||||
return m_shareStates;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -24,10 +24,13 @@ enum eKeyboardModifiers {
|
|||
class IKeyboard : public IHID {
|
||||
public:
|
||||
virtual ~IKeyboard();
|
||||
virtual uint32_t getCapabilities();
|
||||
virtual eHIDType getType();
|
||||
virtual bool isVirtual() = 0;
|
||||
virtual SP<Aquamarine::IKeyboard> aq() = 0;
|
||||
virtual uint32_t getCapabilities();
|
||||
virtual eHIDType getType();
|
||||
virtual bool isVirtual() = 0;
|
||||
virtual wl_client* getClient() {
|
||||
return nullptr;
|
||||
};
|
||||
virtual SP<Aquamarine::IKeyboard> aq() = 0;
|
||||
|
||||
struct SKeyEvent {
|
||||
uint32_t timeMs = 0;
|
||||
|
|
@ -73,6 +76,8 @@ class IKeyboard : public IHID {
|
|||
bool updateModifiersState(); // rets whether changed
|
||||
void updateXkbStateWithKey(uint32_t xkbKey, bool pressed);
|
||||
void updateKeymapFD();
|
||||
bool getPressed(uint32_t key);
|
||||
bool shareStates();
|
||||
|
||||
bool m_active = false;
|
||||
bool m_enabled = true;
|
||||
|
|
@ -118,5 +123,9 @@ class IKeyboard : public IHID {
|
|||
private:
|
||||
void clearManuallyAllocd();
|
||||
|
||||
std::vector<uint32_t> m_pressedXKB;
|
||||
std::vector<uint32_t> m_pressed;
|
||||
|
||||
protected:
|
||||
bool updatePressed(uint32_t key, bool pressed);
|
||||
bool m_shareStates = true;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -29,13 +29,16 @@ CKeyboard::CKeyboard(SP<Aquamarine::IKeyboard> keeb) : m_keyboard(keeb) {
|
|||
});
|
||||
|
||||
m_listeners.key = keeb->events.key.listen([this](const Aquamarine::IKeyboard::SKeyEvent& event) {
|
||||
const auto UPDATED = updatePressed(event.key, event.pressed);
|
||||
|
||||
m_keyboardEvents.key.emit(SKeyEvent{
|
||||
.timeMs = event.timeMs,
|
||||
.keycode = event.key,
|
||||
.state = event.pressed ? WL_KEYBOARD_KEY_STATE_PRESSED : WL_KEYBOARD_KEY_STATE_RELEASED,
|
||||
});
|
||||
|
||||
updateXkbStateWithKey(event.key + 8, event.pressed);
|
||||
if (UPDATED)
|
||||
updateXkbStateWithKey(event.key + 8, event.pressed);
|
||||
});
|
||||
|
||||
m_listeners.modifiers = keeb->events.modifiers.listen([this] {
|
||||
|
|
|
|||
|
|
@ -1,6 +1,8 @@
|
|||
#include "VirtualKeyboard.hpp"
|
||||
#include "../defines.hpp"
|
||||
#include "../protocols/VirtualKeyboard.hpp"
|
||||
#include "../config/ConfigManager.hpp"
|
||||
#include <wayland-server-protocol.h>
|
||||
|
||||
SP<CVirtualKeyboard> CVirtualKeyboard::create(SP<CVirtualKeyboardV1Resource> keeb) {
|
||||
SP<CVirtualKeyboard> pKeeb = SP<CVirtualKeyboard>(new CVirtualKeyboard(keeb));
|
||||
|
|
@ -19,7 +21,10 @@ CVirtualKeyboard::CVirtualKeyboard(SP<CVirtualKeyboardV1Resource> keeb_) : m_key
|
|||
m_events.destroy.emit();
|
||||
});
|
||||
|
||||
m_listeners.key = keeb_->m_events.key.listen([this](const auto& event) { m_keyboardEvents.key.emit(event); });
|
||||
m_listeners.key = keeb_->m_events.key.listen([this](const auto& event) {
|
||||
updatePressed(event.keycode, event.state == WL_KEYBOARD_KEY_STATE_PRESSED);
|
||||
m_keyboardEvents.key.emit(event);
|
||||
});
|
||||
m_listeners.modifiers = keeb_->m_events.modifiers.listen([this](const SModifiersEvent& event) {
|
||||
updateModifiers(event.depressed, event.latched, event.locked, event.group);
|
||||
m_keyboardEvents.modifiers.emit(SModifiersEvent{
|
||||
|
|
@ -39,7 +44,8 @@ CVirtualKeyboard::CVirtualKeyboard(SP<CVirtualKeyboardV1Resource> keeb_) : m_key
|
|||
m_keyboardEvents.keymap.emit(event);
|
||||
});
|
||||
|
||||
m_deviceName = keeb_->m_name;
|
||||
m_deviceName = keeb_->m_name;
|
||||
m_shareStates = g_pConfigManager->getDeviceInt(m_deviceName, "share_states", "input:virtualkeyboard:share_states");
|
||||
}
|
||||
|
||||
bool CVirtualKeyboard::isVirtual() {
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ class CVirtualKeyboard : public IKeyboard {
|
|||
virtual bool isVirtual();
|
||||
virtual SP<Aquamarine::IKeyboard> aq();
|
||||
|
||||
wl_client* getClient();
|
||||
virtual wl_client* getClient();
|
||||
|
||||
private:
|
||||
CVirtualKeyboard(SP<CVirtualKeyboardV1Resource> keeb);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue