更新

更新

问题摘要:我希望我的鼠标按钮之一能够被 X11 注册为 Windows 左键Super_L


在我的窗口管理器中,我可以通过按住“左 Windows 按钮”(左 Super)并用鼠标左键拖动窗口来移动窗口。我希望能够在不触摸键盘的情况下做到这一点,所以我想将左 Super 键映射到鼠标按钮 11,这样我就可以按住鼠标按钮 11 并单击并拖动窗口。

最明显的解决方案是使用 xbindkeys 和 xte,如下所示(.xbindkeysrc):

"xte 'keydown Super_L'"
  b:11

"xte 'keyup Super_L'"
  b:11 + release

它的工作原理如下:

  • 当我按下鼠标第 11 键时,Super_L也会按下
  • 当我释放鼠标第 11 键时,Super_L也会释放

但是有一个问题:如果我还按住另一个鼠标按钮(如鼠标按钮 11),则无法使用Super_L+移动窗口。使用上述解决方案,鼠标按钮 11 仍被注册为按下和释放,因此所有窗口管理器操作都不起作用。Mouse1

我已经尝试使用 Cinnamon 和 Awesome WM 来实现这一点,绝对没有Super_L当鼠标按钮 10 或 11 被按住时,键盘组合键可以起作用。

低于标准的黑客攻击

我目前正在解决这个问题,方法是让鼠标 11 单击以按住Super_L按钮一段时间。这样我就可以点击鼠标按钮,然后短暂地拖动内容:

"xte 'keydown Super_L' 'usleep 250000' 'keyup Super_L'"
  b:11

另一次尝试

按照 totti 的建议,我尝试了这种xbindkeys配置:

"xte 'mouseup 10' 'keydown Super_L'"
  b:10

"xte 'keyup Super_L'"
  b:10 + Release

它不起作用。似乎Super_L按键被按住了,因为一旦我释放按钮 10,它就会一直保持按住状态(直到我Super_L再次按下键盘上的按键),但鼠标按钮仍然被注册,因为我无法单击和拖动窗口。我不认为我能使用xbindkeys和来实现这一点xte

答案1

askubuntu 帖子包含一个答案下面我将进行总结。

问题是 xbindkeys 会抓取整个鼠标,导致修饰键 + 鼠标点击映射不确定。答案是使用 uinput 通过python-uinput脚本来监控/dev/my-mouse拇指按钮的点击并将Ctrl按键发送到虚拟键盘。以下是详细步骤:

1.制定udev规则

对于鼠标,文件/etc/udev/rules.d/93-mxmouse.conf.rules

KERNEL=="event[0-9]*", SUBSYSTEM=="input", SUBSYSTEMS=="input", 
ATTRS{name}=="Logitech Performance MX", SYMLINK+="my_mx_mouse", 
GROUP="mxgrabber", MODE="640"

Udev 将查找名称类似 event5 的内核设备。SYMLINK 用于查找 中的鼠标/dev/my_mx_mouse,可供 组读取mxgrabber

要查找硬件信息,请运行以下命令:

udevadm info -a -n /dev/input/eventX

对于 uinput,文件/etc/udev/rules.d/94-mxkey.rules

KERNEL=="uinput", GROUP="mxgrabber", MODE="660"

拔下并插入鼠标,或者强制 udev 触发规则udevadm trigger

2. 激活 UINPUT 模块

sudo modprobe uinput

并且/etc/modules-load.d/uinput.conf

uinput

3. 创建新组

sudo groupadd mxgrabber
sudo usermod -aG mxgrabber your_login

4.Python脚本

安装python-uinput librarypython-evdev library

下面的脚本需要识别按钮的event.code:

#!/usr/bin/python3.5
# -*- coding: utf-8 -*-

"""
Sort of mini driver.
Read a specific InputDevice (my_mx_mouse),
monitoring for special thumb button
Use uinput (virtual driver) to create a mini keyboard
Send ctrl keystroke on that keyboard
"""

from evdev import InputDevice, categorize, ecodes
import uinput

# Initialize keyboard, choosing used keys
ctrl_keyboard = uinput.Device([
    uinput.KEY_KEYBOARD,
    uinput.KEY_LEFTCTRL,
    uinput.KEY_F4,
    ])

# Sort of initialization click (not sure if mandatory)
# ( "I'm-a-keyboard key" )
ctrl_keyboard.emit_click(uinput.KEY_KEYBOARD)

# Useful to list input devices
#for i in range(0,15):
#    dev = InputDevice('/dev/input/event{}'.format(i))
#    print(dev)

# Declare device patch.
# I made a udev rule to assure it's always the same name
dev = InputDevice('/dev/my_mx_mouse')
#print(dev)
ctrlkey_on = False

# Infinite monitoring loop
for event in dev.read_loop():
    # My thumb button code (use "print(event)" to find)
    if event.code == 280 :
        # Button status, 1 is down, 0 is up
        if event.value == 1:
            ctrl_keyboard.emit(uinput.KEY_LEFTCTRL, 1)
            ctrlkey_on = True
        elif event.value == 0:
            ctrl_keyboard.emit(uinput.KEY_LEFTCTRL, 0)
            ctrlkey_on = False

5. 整理

使 python 文件可执行并确保它在启动时加载。

答案2

由于您可以通过鼠标单击来运行脚本,因此您可以使用以下技巧。
1. 按按钮 11抓住超级键。 (按钮 11触发脚本)
2.使用其他鼠标按钮移动窗口
3. 按鼠标按钮 11再次发布 超级键

脚本
使用xdotool容纳超级键
第一次单击按钮时,创建一个临时文件并按住键。下次单击删除临时文件并释放键,

更新

根据 ubuntu 帮助页面(多键鼠标如何使用)imwheel可以重新映射到一个键。

答案3

调试建议:我会尝试监视/dev/input/eventX文件以查看按下和释放该按钮时会生成什么事件,尤其是与 的组合BTN_LEFT这里这是帮助您入门的示例代码。显然,您必须对其进行修改,才能记录所有事件,而不仅仅是按键事件。

xev如果还没有,您可能还想检查一下输出。分析这两个日志应该能发现您遇到的确切问题。

您的鼠标在按下多个按钮时可能会生成额外的按钮释放事件。在这种情况下,您的选择是使用键绑定解决方法,或修改xf86-input-evdev库以过滤不需要的事件(或模拟丢失的事件)。不久前,我为触摸屏做了类似的事情,它在尝试拖放时生成了“点击”事件。这个想法是过滤几乎同时(在很短的时间窗口内)发生的“释放”事件和“点击”事件。如果我的猜测是正确的,您基本上需要实现类似的东西。

答案4

今天早些时候,我使用其他修饰键解决了这个问题。问题是,您必须在按钮组合中包含修饰键才能释放。假设您的 Super 键映射到 Mod4(据我所知,这应该是默认设置):

"xte 'keydown Super_L'"
  b:11

"xte 'keyup Super_L'"
  Mod4 + b:11 + release

编辑:刚刚意识到这并不能完全回答你的问题,因为你仍然无法在按住 b:11 时使用 LMB

相关内容