Tkinter应用 - 我的Toplevel窗口不出现,应用卡在主循环中
我正在尝试制作一个工作日程跟踪器,现在先从标题部分开始。附上的图片展示了完成后设计的样子。
到目前为止,我有三个类:
- InputWindow:一个顶层窗口,用户可以从两个下拉框中选择月份和年份。
- App:主窗口,根据用户在InputWindow中的选择,App应该加载一个包含TitleFrame中元素的标题。
- TitleFrame:一个框架,左边有应用程序的标题、选定的月份和年份,第一行是这个月的星期几,第二行是这个月的日期,第三行是工作人员的班次,用“D”表示白班或“N”表示夜班。
以下是代码:
# PEP8 Compliant Guidance
# Standard Library Imports
import tkinter as tk
from tkinter import ttk
import datetime
# Third-Party Library Imports
# Local Application/Library Specific Imports
import functions
class InputWindow(tk.Toplevel):
def __init__(self, parent):
super().__init__(parent)
# Customize the top-level window as needed
self.title("Schedule Selection")
self.geometry("400x500")
# widgets, labels, and other elements for user selections
currentdate = datetime.datetime.now()
currentmonth = currentdate.strftime("%B")
currentyear = currentdate.strftime("%Y")
# Month Selection
self.select_schedule_month = ttk.Combobox(self, values=functions.months_list())
self.select_schedule_month.set(currentmonth)
self.select_schedule_month.pack()
# Year Selection
self.select_schedule_year = ttk.Combobox(self, values=functions.years_list())
self.select_schedule_year.set(currentyear)
self.select_schedule_year.pack()
# Button to confirm selections and open the main application window
sel_button = tk.Button(self, text="Confirm", command=self.confirm_selections)
sel_button.pack()
def confirm_selections(self):
# Perform validation and check if the proper selections are made
# If selections are valid, hide the top-level window and open the main application window
if self.selections_are_valid():
self.selected_month = self.select_schedule_month.get()
self.selected_year = self.select_schedule_year.get()
self.withdraw() # Hide the top-level window
self.master.deiconify() # Show the main application window
def selections_are_valid(self):
# Implement your logic to validate selections
# Return True if selections are valid, False otherwise
return True
# The Main App Window - 35 columns | 5 rows
class App(tk.Tk):
def __init__(self):
super().__init__()
self.title("Schedule Window")
self.geometry("1300x300")
self.open_input_window()
# title frame
self.title_frame = TitleFrame(self)
self.title_frame.grid(column=0, row=0, columnspan=35, padx=10, pady=10)
def open_input_window(self):
self.input_window = InputWindow(self)
# self.wait_window(self.input_window) # Wait for the top-level window to close
self.handle_input_window_selections()
def handle_input_window_selections(self):
if self.input_window is not None:
selected_month = self.input_window.selected_month
selected_year = self.input_window.selected_year
# Use the selected month and year to perform any necessary operations
print(selected_month, selected_year)
# title frame
self.title_frame = TitleFrame(self)
self.title_frame.grid(column=0, row=0, columnspan=35, padx=10, pady=10)
# Schedule Header: Includes - Title, Calendar, Shifts, Crew Name, and Crew ID
class TitleFrame(tk.Frame):
def __init__(self, parent):
super().__init__(parent)
self.config(borderwidth=1, relief="raised", width=1300)
self.grid(column=0, row=0, columnspan=35, padx=10, pady=10)
self.title_label = tk.Label(self, text="Overtime Schedule", font=("Calibri", 22))
self.title_label.config(padx=462)
self.title_label.grid(column=0, row=0, columnspan=24, sticky="w")
self.ID_detection_label = tk.Label(self, text=f"Current User: {functions.get_user_id()}",
font=("Calibri", 12))
# self.ID_detection_label.config(bg="black", fg="white")
self.ID_detection_label.grid(column=34, row=0, sticky="e")
self.Calendar_Month_hdr = tk.Label(self, text="Schedule Calendar", font=("Calibri", 12))
self.Calendar_Month_hdr.grid(column=0, row=1)
# self.Calendar_Month_hdr.configure(bg="black", fg="white")
"""Need to add a calendar widget for this feature"""
self.Calendar_Month_label = tk.Label(self, text="Selected Month", font=("Calibri", 12))
self.Calendar_Month_label.grid(column=0, row=2)
self.Calendar_Year_label = tk.Label(self, text="Selected year", font=("Calibri", 12))
self.Calendar_Year_label.grid(column=0, row=3)
# Top Level Selector
class SelectorFrame(tk.Toplevel):
def __init__(self, parent):
super().__init__(parent)
pass
app = App()
app.withdraw() # Hide the main application window
app.mainloop()
最开始这个应用运行得很好,直到我尝试从InputWindow的下拉框选择中创建变量,并在TitleFrame中用它们作为标签。因为我对Python和tkinter非常陌生,所以我想先试着从另一个类调用这些变量,然后再尝试更新类的标签。
InputWindow第42和43行 - 初始赋值
self.selected_month = self.select_schedule_month.get()
self.selected_year = self.select_schedule_year.get()
在App第71-75行调用,以打印在InputWindow中选择的值。
def handle_input_window_selections(self):
if self.input_window is not None:
selected_month = self.input_window.selected_month
selected_year = self.input_window.selected_year
# Use the selected month and year to perform any necessary operations
print(selected_month, selected_year)
所有本地导入的函数在测试时都能正常工作。
当我尝试调用selected_month和selected_year变量时,出现了一个AttributeError错误。我不太确定如何从类外部调用这些选择,所以我需要一些相关的知识,但即使把这些变量从方程中去掉,我仍然无法让顶层窗口出现。
Exception has occurred: AttributeError
'InputWindow' object has no attribute 'selected_month'
File "C:\Users\edit\OneDrive\Py Scripts\Tkinter GUI\Schedule App\Schedule_GUI.py", line 71, in handle_input_window_selections
selected_month = self.input_window.selected_month
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\edit\OneDrive\Py Scripts\Tkinter GUI\Schedule App\Schedule_GUI.py", line 67, in open_input_window
self.handle_input_window_selections()
File "C:\Users\edit\OneDrive\Py Scripts\Tkinter GUI\Schedule App\Schedule_GUI.py", line 58, in __init__
self.open_input_window()
File "C:\Users\edit\OneDrive\Py Scripts\Tkinter GUI\Schedule App\Schedule_GUI.py", line 116, in <module>
app = App()
^^^^^
AttributeError: 'InputWindow' object has no attribute 'selected_month'
谢谢你的帮助,我确实还有很多东西需要学习。
1 个回答
暂无回答