激活窗口停止主循环

时间:2019-03-14 18:37:00

标签: python pyqt5

我有一个简单的GUI应用程序,我想连接Alt+M以便在最小化窗口时恢复该窗口。相关代码如下:

from pynput import keyboard
import sys, os, _thread
from PyQt5 import QtCore
from PyQt5.QtWidgets import QApplication, QWidget

class MainWindow(QWidget):
    def __init__(self):
        super().__init__()
        _thread.start_new_thread(self.hotkeyLoop, (self,))

        self.setWindowFlags(self.windowFlags() | QtCore.Qt.CustomizeWindowHint)
        self.setWindowFlags(self.windowFlags() & ~QtCore.Qt.WindowCloseButtonHint)

        self.show()

    def hotkeyLoop(self, window):
        COMBINATIONS = [
            {keyboard.Key.alt_l, keyboard.KeyCode(char='m')},
            {keyboard.Key.alt_l, keyboard.KeyCode(char='M')}
        ]

        # The currently active modifiers
        current = set()

        def execute():
            print('alt+m')
            self.setWindowState(QtCore.Qt.WindowActive)

        def on_press(key):
            if any([key in COMBO for COMBO in COMBINATIONS]):
                current.add(key)
                if any(all(k in current for k in COMBO) for COMBO in COMBINATIONS):
                    execute()

        def on_release(key):
            if any([key in COMBO for COMBO in COMBINATIONS]):
                current.remove(key)

        with keyboard.Listener(on_press=on_press, on_release=on_release) as listener:
            listener.join()

if __name__ == '__main__':
    app = QApplication(sys.argv)
    mainWindow = MainWindow()
    sys.exit(app.exec_())

hotkeyLoop中的代码实际上是我用来捕获热键的复制粘贴代码。我知道这段代码实际上是有效的,因为在关闭窗口时,我在同一应用中将其用于window.show()窗口。完美。但是我决定使窗口无法关闭,并在最小化窗口时使用热键显示它。但是每当我按下热键组合时,窗口就会出现,但它是完全白色的,并且停止响应。那么我别无选择,只能终止它。

赞:

为什么会发生这种情况,我该如何解决?

1 个答案:

答案 0 :(得分:0)

通常来说,如果您的代码具有除GUI主循环之外的无限循环,则GUI将停止响应。 keyboard.Listener.join()实际上是一个无限循环-只要侦听器还活着,它就会无限期地阻塞。

您无法调用join,在这种情况下,主线程将继续根据需要执行GUI mainloop。只需确保对侦听器线程保持永久引用,以免过早地收集到垃圾。

更改:

with keyboard.Listener(on_press=on_press, on_release=on_release) as listener:
    listener.join()

收件人:

self.listener = keyboard.Listener(on_press=on_press, on_release=on_release)