Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/294.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 第一次按键时,注册按键事件不起作用_Python_Pyqt_Pyqt5 - Fatal编程技术网

Python 第一次按键时,注册按键事件不起作用

Python 第一次按键时,注册按键事件不起作用,python,pyqt,pyqt5,Python,Pyqt,Pyqt5,我正在使用Qt5(具体来说是PyQt5)并想检查按键 我遇到的问题是第一次按下按钮时未注册Qt::Key\u acute事件 我使用德国键盘布局[1],也许这是一个我不知道的问题,但我仍然想工作,因为我知道它在其他程序(非Qt)中工作 当按下键\u acute键(在链接图像中,退格键左边的一个)时,第一次按下时不会发生任何事情,但当我再次按下它时,控制台会打印两个事件:180和0(180=0x0b4=Key\u acute) 如何捕获此键的第一个按键事件 PyQt5程序示例: import sy

我正在使用Qt5(具体来说是PyQt5)并想检查按键

我遇到的问题是第一次按下按钮时未注册
Qt::Key\u acute
事件

我使用德国键盘布局[1],也许这是一个我不知道的问题,但我仍然想工作,因为我知道它在其他程序(非Qt)中工作

当按下
键\u acute
键(在链接图像中,退格键左边的一个)时,第一次按下时不会发生任何事情,但当我再次按下它时,控制台会打印两个事件:
180
0
(180=0x0b4=Key\u acute)

如何捕获此键的第一个按键事件

PyQt5程序示例:

import sys
from PyQt5.QtWidgets import *


class App(QWidget):
    def __init__(self, argv):
        super().__init__()

        self.box = QLabel(self)
        self.show()


    def keyPressEvent(self, ev):
        print(ev.key())
        self.box.setText(str(ev.key()))
        self.box.adjustSize()

        super().keyPressEvent(ev)


if __name__ == '__main__':
    app = QApplication(sys.argv)
    ex = App(sys.argv)
    sys.exit(app.exec_())

[1]

大多数键盘中的['']键是一个“”,这是一种特殊的键,等待下面的字符“合成”实际字符

据我所知,您只能将这些按键作为释放事件获取,而不能作为按下事件获取

当某些死键被按下两次时,它们不会作为按键按下/释放事件发送,但您可以使用as
QEvent.InputMethod
类型截获它们

from PyQt5.QtCore import *
from PyQt5.QtGui import *
from PyQt5.QtWidgets import *

keyNameFromValue = {}
keyNameFromString = {}
for k, v in vars(Qt).items():
    if isinstance(v, Qt.Key):
        keyNameFromValue[v] = k
        keyNameFromString[QKeySequence(v).toString()] = k


class App(QWidget):
    def __init__(self, argv):
        super().__init__()
        layout = QVBoxLayout(self)
        self.box = QLabel(self)
        layout.addWidget(self.box)
        self.show()

    def event(self, ev):
        if ev.type() == QEvent.InputMethod:
            s = ev.commitString()
            if s:
                self.box.setText('InputMethod > {}: {}'.format(
                     keyNameFromString.get(s, '(Unknown)'), s))
                self.box.adjustSize()
        return super().event(ev)

    def keyPressEvent(self, ev):
        if not ev.isAutoRepeat():
            self.box.setText('KeyPress > {}: {}'.format(
                keyNameFromValue.get(ev.key()), ev.text()))
            self.box.adjustSize()
        super().keyPressEvent(ev)

    def keyReleaseEvent(self, ev):
        if not ev.isAutoRepeat():
            self.box.setText('KeyRelease > {}: {}'.format(
                keyNameFromValue.get(ev.key()), ev.text()))
            self.box.adjustSize()
        super().keyReleaseEvent(ev)


if __name__ == '__main__':
    import sys
    app = QApplication(sys.argv)
    ex = App(sys.argv)
    sys.exit(app.exec_())
在这种情况下,第一次按下[')键时,结果为
键死键急性
(不可直接打印),第二次为
键急性

如果需要显示可打印的死键应如何显示为字符串,可以为死键创建自己的基于dict的映射(不到50个)
不幸的是,没有编程的方法来实现这一点,因为即使对于“相同”字符,它们的字符串转换也不同,并且
Qt.Key\u Dead\u*
Qt.Key\u*
名称或值之间没有实际的相关性:例如,
Qt.Key\u Dead\u Acute
对应于
Qt.Key\u Acute
Qt.Key\u Dead\u Grave
变成
Qt.Key\u QuoteLeft

如果你在QLineEdit中写东西并只按一次,那么QLineEdit中写的东西?@eyllanesc否。但是在记事本中也是这样,因为``通常会等待,例如,一个“a”来完成。但无论如何,必须有一种方法来登记第一家媒体。至少我知道有一个不同的程序,它没有问题。你说的“不可直接打印”到底是什么意思?你是说标签上什么也看不出来?至少我可以证实,没有“钥匙死了”。有趣的是,另外两个能够很好地检测这些密钥的程序(MPC-HC和PotPlayer)将其检测为
]
(并且它们还检测到该区域中的其他密钥与QWERTZ完全不同(甚至不匹配US布局))。PyCharm可以将其检测为
死亡\u急性
。因此,我想这只是Qt问题,无法捕获此事件,因为在您的示例中,仅打印(“x”)不会在任何事件函数中显示任何内容。@user136036死键与修改键几乎相同:您不能“打印”移位键,而“死键”充当某种替代移位;唯一的区别是,正常的修改器需要同时按下,死区键和连续键。当您按下“shift+a”键时,操作系统“修改”键“a”的行为并使其成为“a”,当您按下“shift+a”键时,也会使其成为“a”。请记住,从低级的角度来看,按键事件只是从键盘发送的扫描码,这取决于操作系统是否“翻译”它们,以及程序是否需要将它们“转换”为字符串表示。每个框架都可以为程序员提供不同级别的“检测”,这也取决于操作系统API。还考虑到QT必须维护一个通用的跨平台层,这可能会变得稍微不一致,从OS到OS或有某种限制,以保持兼容性。然后,可能是由于某些原因,Qt没有/不能为按键提供事件(不过,通过在应用程序上安装QAbstractNativeEventFilter,它可能会被捕获),但我不认为这是一个实际问题。