如何正确将键盘键映射到鼠标按钮?


14

问题摘要:我希望Super_LX11 将我的鼠标按钮之一注册为Windows左按钮。


在我的窗口管理器中,可以通过按住“ Windows左键”(Left 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+ 来移动窗口Mouse1。使用上述解决方案,鼠标按钮11仍被注册为按下和释放状态,因此没有一个窗口管理器操作工作。

我一直在使用这两种桂皮和真棒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
不用重新将鼠标按钮绑定到超级键。为此,请使用xmodmap。有关完整设置,请参见Arch Wiki xmodmap页面。
托蒂

@totti:arch wiki xmodmap页面描述了如何将键映射到其他键,如何交换修饰键以及如何反向滚动,但是没有提到将键盘键映射到鼠标按钮
Hubro

@totti:使用xmodmap可以将键映射到其他键,并且使用X(和xkbset)的XKB扩展名可以将鼠标按钮映射到键盘键,但是我试图将键盘键映射到鼠标键。我仍然没有找到一种方法来做到这一点。
Hubro

尝试:在按住鼠标按钮11时,模拟超级按住+释放鼠标按钮11。窗口管理器现在可以检测超和鼠标1不鼠标11
托蒂

@totti:尝试过并编辑过的问题
Hubro

Answers:


5

Askubuntu帖子包含一个答案,我将在下面总结。

问题是xbindkeys会抓住整个鼠标,从而使修饰符+鼠标单击映射变得不确定。答案通过python-uinput脚本使用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文件可执行,并确保在启动时加载该文件。


我已经更新脚本分配一个未使用的键码的鼠标按键(我设置它们F13F14F15和使用禁用鼠标功能xinput,然后到任何我需要用一个简单的我可以简单地重新分配这些密钥xmodmap。主要思想是起草在一个要点(有一些硬编码值,我不恢复xinput后鼠标功能)在这里时,会做,我将做一个博客帖子就这个问题与剧本的最终版本(和共享的链接。谢谢for♥
zmo

还要在另一个线程上检查我的新答案,以获得基于x11的解决方案askubuntu.com/a/903389/269589
Maxim

1

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

脚本
使用xdotool持有超键
在第一个按钮点击,创建一个临时文件和HOLD键。在下一个单击删除tmp文件并释放密钥,

更新

根据ubuntu帮助页面(很多按钮鼠标如何操作)imwheel可以重新映射到一个键。


与此相关的几个问题:#1这仍然只是另一种破解/解决方法,无法回答问题。#2 xbindkeys在按住超级键时不起作用。就像xbindkeys暂停了一样,直到超键释放之前,它都没有注册任何东西。
Hubro

好的,经过大约5分钟的研究,我收回了第二点。我显然必须添加+ Mod4我的xbindkeys配置,以解决被按住的超级键的问题。您建议的解决方法比我的更好,我将其转换为:-)但它仍然不能解决问题。
Hubro

1

调试建议:我将尝试监视/dev/input/eventX文件以查看按下和释放该按钮时产生的事件,尤其是与组合使用时BTN_LEFT是一个示例代码,可以帮助您入门。显然,您必须修改它才能记录所有事件,而不仅仅是按键。

您可能还需要检出xev输出(如果尚未输出)。分析两个日志应该可以发现您遇到的确切问题。

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


1

我今天早些时候用其他修改键弄清楚了。问题是您必须在发布的按钮组合中包含修饰符。假设您的超级密钥已映射到Mod4(应为默认值afaik):

"xte 'keydown Super_L'"
  b:11

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

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

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.