从另一个 python 脚本访问 tkinter GUI

Accessing tkinter GUI from another python script

假设我有一个带有三个按钮 TestA、TestB、TestC 的 tkinter 应用程序,按下这些按钮时会显示消息“测试状态:运行 测试 A”(或 ...B、...C)出于某种原因,我想从按下这些按钮的位置创建第二个脚本,将调用另一个脚本的三个函数,其中包括必须做的许多其他事情,最后应该更新第一个的配置栏( tkinter) 脚本。这是如何实现的,因为在任何试验中我都会收到如下错误:“AttributeError: module 'testsUnit' has no attribute 'runTestA'”

这里他们遵循上述问题的代码

首先是没有第二个脚本的 tkinter gui,它运行完美(脚本名称 gui_trial.py) (函数 runTestA|B|C)

from tkinter import *
from tkinter import ttk
from tkinter import scrolledtext
import time

#Constants
GUI_WIDTH = 300
GUI_HEIGHT = 200

def powerOn():
    statusBar.config(text='Test Status: powerOn')
def powerOff():
    statusBar.config(text='Test Status: powerOff')
def shutdown():
    statusBar.config(text='Test Status: shutDown')

def runTestA():
    statusBar.config(text='Test Status: Running Test A')
def runTestB():
    statusBar.config(text='Test Status: Running Test B')
def runTestC():
    statusBar.config(text='Test Status: Running Test C')

master = Tk()
gui_resolution = str(GUI_WIDTH)+'x'+str(GUI_HEIGHT)+'+0+0'
master.geometry(gui_resolution)
master.title("Trial GUI")

powerOnButton = Button(master, text="Power On", command=powerOn)
powerOnButton.grid(column=1, row=1, pady=5, ipadx=12)
powerOffButton = Button(master, text="Power Off", command=powerOff)
powerOffButton.grid(column=1, row=2, pady=5, ipadx=12)
newTestButton = Button(master, text="Shutdown", command=shutdown)  # showPassTestResult)
newTestButton.grid(column=1, row=3, pady=5, ipadx=12)

testAButton = Button(master, text="Test A", command=runTestA)
testAButton.grid(column=2, row=1, pady=5, ipadx=12)
testBButton = Button(master, text="Test B", command=runTestB)
testBButton.grid(column=2, row=2, pady=5, ipadx=12)
testCButton = Button(master, text="Test C", command=runTestC)
testCButton.grid(column=2, row=3, pady=5, ipadx=12)

statusBar = Label(master, width=25, relief=SUNKEN, text='Test Status: IDLE')
statusBar.grid(column=1, row=4, sticky=SW, padx=10, pady=20)

master.mainloop()

然后再次修改第一个脚本以调用第二个脚本(函数 runGuiTestA|B|C)

from tkinter import *
from tkinter import ttk
import testsUnit

#Constants
GUI_WIDTH = 300
GUI_HEIGHT = 200

def powerOn():
    statusBar.config(text='Test Status: powerOn')

def powerOff():
    statusBar.config(text='Test Status: powerOff')

def shutdown():
    statusBar.config(text='Test Status: shutDown')

def runGuiTestA():
    #statusBar.config(text='Test Status: Running Test A')
    testsUnit.runTestA()
def runGuiTestB():
    #statusBar.config(text='Test Status: Running Test B')
    testsUnit.runTestB()
def runGuiTestC():
    #statusBar.config(text='Test Status: Running Test C')
    testsUnit.runTestC()

master = Tk()
gui_resolution = str(GUI_WIDTH)+'x'+str(GUI_HEIGHT)+'+0+0'
master.geometry(gui_resolution)
#master.resizable(FALSE, FALSE)
master.title("Trial GUI")

powerOnButton = Button(master, text="Power On", command=powerOn)
powerOnButton.grid(column=1, row=1, pady=5, ipadx=12)
powerOffButton = Button(master, text="Power Off", command=powerOff)
powerOffButton.grid(column=1, row=2, pady=5, ipadx=12)
newTestButton = Button(master, text="Shutdown", command=shutdown)  # showPassTestResult)
newTestButton.grid(column=1, row=3, pady=5, ipadx=12)

testAButton = Button(master, text="Test A", command=runGuiTestA)
testAButton.grid(column=2, row=1, pady=5, ipadx=12)
testBButton = Button(master, text="Test B", command=runGuiTestB)
testBButton.grid(column=2, row=2, pady=5, ipadx=12)
testCButton = Button(master, text="Test C", command=runGuiTestC)
testCButton.grid(column=2, row=3, pady=5, ipadx=12)

statusBar = Label(master, width=25, relief=SUNKEN, text='Test Status: IDLE')
statusBar.grid(column=1, row=4, sticky=SW, padx=10, pady=20)

master.mainloop()

第二个名为 testsUnit.py(此处运行 runTestA|B|C)

import gui_trial

def runTestA():
    gui_trial.statusBar.config(text='Test Status: Running Test A')
def runTestB():
    gui_trial.statusBar.config(text='Test Status: Running Test B')
def runTestC():
    gui_trial.statusBar.config(text='Test Status: Running Test C')

存在循环导入问题。更好的设计是将 statusBar 作为 testsUnity.py:

中那些函数的参数传递
# no need to import gui_trial
#import gui_trial

def runTestA(statusBar):
    statusBar.config(text='Test Status: Running Test A')
def runTestB(statusBar):
    statusBar.config(text='Test Status: Running Test B')
def runTestC(statusBar):
    statusBar.config(text='Test Status: Running Test C')

然后修改gui_trial.py,将statusBar传递给上面的函数执行时:

...
def runGuiTestA():
    #statusBar.config(text='Test Status: Running Test A')
    testsUnit.runTestA(statusBar) # pass statusBar as an argument
def runGuiTestB():
    #statusBar.config(text='Test Status: Running Test B')
    testsUnit.runTestB(statusBar)
def runGuiTestC():
    #statusBar.config(text='Test Status: Running Test C')
    testsUnit.runTestC(statusBar)
...