繁体   English   中英

如何与另一个调度程序一起运行Tkinter GUI?

[英]How can I run Tkinter GUI with another scheduler program together?

我已将一个Tkinter GUI编码为控制台以控制某些内容。 而且,我还想从APScheduler模块运行一个调度程序来完成一项工作,该工作每20秒执行一次操作。 但是,这两个线程似乎无法一起运行。

我尝试使用multi-threading ,但似乎无法正常工作。

import tkinter as tk
from tkinter import *
import time
import pyHook
import winreg
import webbrowser
import os
import pyautogui
from apscheduler.schedulers.blocking import BlockingScheduler
from apscheduler.schedulers.background import  BackgroundScheduler
import threading

def initialization():
    webbrowser.open('AutoRefreshSCMOutbound.HTML', 1)
    time.sleep(2)


def autoClick():
    x, y = pyautogui.size()
    pyautogui.click(x/2, y/2, button='left')
    time.sleep(1)
    pyautogui.click(x/2, y/2, button='left')
    return True

root = tk.Tk()
root.geometry('700x100')
root.resizable(height = True, width = True)
root.overrideredirect(False)

OneBtn = Button(root, command = initialization, text = "One Button", width = '30')
OneBtn.grid(row = 1 ,column = 0)   

if __name__ == "__main__":
    th01 = threading.Thread(target=root.mainloop())
    scheduler = BackgroundScheduler
    scheduler.add_job(autoClick, 'interval', seconds=20)
    threads = []
    th01.start()
    scheduler.start()
    threads.append(th01)
    threads.append(scheduler)
    for t in threads:
        t.join()
    print("End all process")

这两个线程应该同时运行,但是调度程序总是需要等到Tkinter结束。

tkinter ,你可以使用root.after(time_in_millisecond, function_name)与延迟执行功能。 root.after仅执行一次函数,因此在此函数内部,您必须再次使用root.after

import tkinter as tk
import time
import webbrowser
import pyautogui

def initialization():
    webbrowser.open('AutoRefreshSCMOutbound.HTML', 1)
    time.sleep(2)

def autoClick():
    # run again after 20000ms (20s)
    root.after(20000, autoClick)

    x, y = pyautogui.size()
    pyautogui.click(x/2, y/2, button='left')
    time.sleep(1)
    pyautogui.click(x/2, y/2, button='left')

if __name__ == "__main__":
    root = tk.Tk()
    root.geometry('700x100')
    root.resizable(height = True, width = True)
    root.overrideredirect(False)

    OneBtn = tk.Button(root, command=initialization, text="One Button", width='30')
    OneBtn.grid(row=1, column=0)   

    # run first time after 20000ms (20s)
    root.after(20000, autoClick)

    root.mainloop() 

或将其他函数与after()一起使用以执行您不想修改的函数。

import tkinter as tk
import time
import webbrowser
import pyautogui

def initialization():
    webbrowser.open('AutoRefreshSCMOutbound.HTML', 1)
    time.sleep(2)

def autoClick():
    x, y = pyautogui.size()
    pyautogui.click(x/2, y/2, button='left')
    time.sleep(1)
    pyautogui.click(x/2, y/2, button='left')

def repeate():
    # run again after 20000ms (20s)
    root.after(20000, repeate)
    autoclick()

if __name__ == "__main__":
    root = tk.Tk()
    root.geometry('700x100')
    root.resizable(height = True, width = True)
    root.overrideredirect(False)

    OneBtn = tk.Button(root, command=initialization, text="One Button", width='30')
    OneBtn.grid(row=1, column=0)   

    # run first time after 20000ms (20s)
    root.after(20000, repeate)

    root.mainloop() 

但是after()仅在执行的函数不会运行太长时间时才有用,因为此时它仍然阻塞mainloop() (和程序的其余部分)。 由于autoClick使用sleep(1)因此它将停止所有程序1秒钟。

并且after()在其他函数运行时间不长的情况下很有用,因为它可能会阻塞mainloop()来执行after()添加的函数。 initialization使用sleep(2)因此可能会阻止autoClick执行2秒钟。


要在不运行sleep(1)情况下运行它,可以将函数分为两个函数,然后使用after(1000, second_part)执行第二部分

def repeate():
    # run again after 20000ms (20s)
    root.after(20000, repeate)
    autoclick()

def autoClick():
    x, y = pyautogui.size()
    pyautogui.click(x/2, y/2, button='left')

    root.after(1000, autoClick_second_part) # 1000ms (1s)

def autoClick_second_part():
    pyautogui.click(x/2, y/2, button='left')

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM