Python:使用键盘按键启动和停止线程

2024-05-29 06:39:40 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在使用Python3.8,我正在尝试使用键盘快捷键打开和关闭线程

这是我的线程类:

import keyboard
from threading import Thread
import time

class PrintHi(Thread):
    def __init__(self):
        Thread.__init__(self)
        self.active = False

    def run(self):
        while True:
            if self.active:
                print("Hi,", time.time())
                time.sleep(1)

它似乎按预期工作,我可以启动线程,然后根据我是否要启用或禁用它,将“thread.active”更改为True或False

问题是,当我尝试将其与“键盘”模块一起使用时,它无法按预期工作:

class KeyboardHook(object):
    def __init__(self):
        self.thread = PrintHi()
        self.thread.start()
        self.set_keyboard_hotkeys()

    def toggle_print(self):
        print("Toggle Print")
        self.thread.active = not self.thread.active

    def set_keyboard_hotkeys(self):
        print("Setting hotkeys hooks")
        keyboard.add_hotkey('ctrl+c', self.toggle_print)
        keyboard.wait()


if __name__ == '__main__':
    hook = KeyboardHook()

以下是步骤:

  • 我首先创建线程,将其存储在“self.thread”中并启动它
  • 然后我设置键盘热键挂钩
  • 当我按下“ctrl+c”时,“toggle_print()”函数应该会执行
  • 这应该将线程的活动属性设置为True,从而启用打印

线程本身可以很好地工作,键盘挂钩本身也可以很好地工作,但是当我将两者结合起来时,它们就不工作了

有人知道我做错了什么吗?有没有一种方法可以通过使用键盘快捷键来打开和关闭线程?在我的应用程序中,我将有多个线程,我必须独立地打开和关闭它们

谢谢


Tags: importselftruetimeinitdef键盘线程
2条回答

KeyboardHook中的一些更改使其运行:

  1. 您不需要使用键盘。等待()
  2. 设置热键后启动线程
  3. 最好将热键从ctrl-c改为其他键
class KeyboardHook(object):
    def __init__(self):
        self.thread = PrintHi()
        self.set_keyboard_hotkeys()
        self.thread.start()

    def toggle_print(self):
        print("Toggle Print")
        self.thread.active = not self.thread.active

    def set_keyboard_hotkeys(self):
        print("Setting hotkeys hooks")
        keyboard.add_hotkey('ctrl+p', self.toggle_print)
        #keyboard.wait()

我建议您稍微重构一下代码,即在打印机线程中使用Event而不是bool变量来表示打印操作,并添加允许您在程序退出时停止打印机线程的逻辑:

import time
from threading import Thread, Event

import keyboard


class PrintThread(Thread):
    
    def __init__(self): 
        super().__init__() 
        self.stop = False 
        self.print = Event()

    def run(self): 
        while not self.stop: 
            if self.print.wait(1): 
                print('Hi,', time.time())
    
    def join(self, timeout=None): 
        self.stop = True 
        super().join(timeout)

另外,我建议将阻塞代码从KeyboadHook初始值设定项移到单独的start方法:

class KeyboardHook: 

    def __init__(self):
        self.printer = PrintThread()
        self.set_keyboard_hotkeys()

    def toggle_print(self): 
        print('Toggle the printer thread...')

        if self.printer.print.is_set():
            self.printer.print.clear()
        else:
            self.printer.print.set()

    def set_keyboard_hotkeys(self):
        print('Setting keyboard hotkeys...')
        keyboard.add_hotkey('ctrl+p', self.toggle_print)

    def start(self): 
        self.printer.start()

        try:
            keyboard.wait()
        except KeyboardInterrupt:
            pass
        finally:
            self.printer.join()

按如下方式运行:

hook = KeyboardHook()
hook.start()

这个密码对我来说很有用

相关问题 更多 >

    热门问题