放置在框架中时,tkinter中的OptionMenu会保持崩溃

时间:2016-12-21 01:56:55

标签: python tkinter

我正在尝试将一个OptionMenu小部件放在一个框架内,该框架本身位于笔记本中。根据我在网上发现的内容,执行此操作的代码大致如下:

    # add a drop down menu
    hops = range(0,6)
    self.selectedHop = StringVar(frame2)
    self.selectedHop.set(hops[0])
    self.hopOptions = OptionMenu(frame2, self.selectedHop, *hops)
    self.hopOptions.grid(row=0, column=2, sticky=EW)

然而,当我把它放在我的代码中的下面的代码中(上面的块放在它的底部,并标记为“问题代码...”),我的应用程序只是冻结,我必须强行退出它,我没有要调试的错误消息。任何帮助将不胜感激。

#!/usr/bin/python3


from tkinter import *
from tkinter import ttk
from tkinter import messagebox
import subprocess
import sys

class ReportGUI:

    def __init__(self, master):

        self.master = master

        master.title('Reporting')
        master.resizable(True, True)
        master.configure(background = '#b3e6cc')
        master.minsize(width=800,height=700)

        textcolor = "#003399"

        self.style = ttk.Style()
        self.style.configure('TFrame', background = '#e1d8b9')
        self.style.configure('TButton', background = '#e1d8b9')
        self.style.configure('TLabel', background = '#e1d8b9', font = ('Arial', 40))
        self.style.configure('Header.TLabel', font = ('Arial', 30, 'bold'))      

        # step 1 - create notebook
        self.notebook = ttk.Notebook(master)
        self.notebook.pack()

        # step 2 - create first frame to add to notebook
        self.frame_logon = ttk.Frame(self.notebook)

        # step 3 - add first frame to notebook and style it
        self.notebook.add(self.frame_logon, text = 'Login')                
        self.frame_logon.config(padding = (20, 20, 20))
        self.frame_logon.config(relief = RIDGE)

        ######### --- (1) LOGIN TAB ----  #########
        label = ttk.Label(self.frame_logon, text = 'Administrative Reporting', 
            foreground=textcolor, style = 'Header.TLabel')
        label.grid(row = 1, columnspan = 2)

        # widget: username and password Label()
        label2 = ttk.Label(self.frame_logon, text = 'Username:',
            font = ('Arial', 17),foreground=textcolor)
        label2.grid(row = 3, column = 0, padx = 5, sticky = 'sw')

        label3 = ttk.Label(self.frame_logon, text = 'Password:',
            font = ('Arial', 17),foreground=textcolor)
        label3.grid(row = 3, column = 1, padx = 5, sticky = 'sw')

        # widget: entry boxes Entry()
        self.entry_name = ttk.Entry(self.frame_logon, width = 20, font = ('Arial', 15))
        self.entry_pw = ttk.Entry(self.frame_logon, width = 20, font = ('Arial', 15))

        # place the widgets
        self.entry_name.grid(row = 4, column = 0, padx = 5)
        self.entry_pw.grid(row = 4, column = 1, padx = 5)
        self.entry_pw.config(show = '*') # make password not show

        # widget: connect button Button()
        self.loginButton = ttk.Button(self.frame_logon, text = 'Connect',
                   command = self.login)
        self.loginButton.grid(row = 5, column = 1, columnspan = 2, padx = 1, pady = 1, sticky = 'e')

    ### COMMAND FUNCTIONS
    def login(self):
        # Make connections (TBA)
        # 1) log into app
        # 2) ssh into server port
        # 3) connect to database

        # if successful login and connection, launch reports tab

        self.reportTab()
        self.notebook.select(1) # switch tabs to reports tab
        self.loginButton.state(['disabled']) # disable login button

    # TAB 2: reporting tab
    def reportTab(self):

        # create report frame and add to notebook
        self.frame_report = ttk.Frame(self.notebook)
        self.notebook.add(self.frame_report, text = 'Report Options')

        ######### --- REPORT TAB ----  #########

        #--------- FILTER 1: -----------
        frame = ttk.Frame(self.frame_report)
        frame.grid(row=1,column=0)
        frame.config(height = 100, width = 200)
        frame.config(relief = RIDGE)
        ttk.LabelFrame(frame, height=100,width = 200,text = 'FILTER 1').pack()  

        #--------- FILTER 2: -----------
        frame2 = ttk.Frame(self.frame_report)
        frame2.grid(row=1,column=1)
        frame2.config(height = 100, width = 200)
        frame2.config(relief = RIDGE)
        ttk.LabelFrame(frame2, height=100,width = 200,text = 'FILTER 2').pack()

        #---------- PROBLEMATIC CODE: trying to add a drop down menu ----
        hops = range(0,6)
        self.selectedHop = StringVar(frame2)
        self.selectedHop.set(hops[0])
        self.hopOptions = OptionMenu(frame2, self.selectedHop, *hops)
        self.hopOptions.grid(row=0, column=2, sticky=EW)
        #----------------------------------------------------------------

        #--------- FILTER 3:  -----------
        frame3 = ttk.Frame(self.frame_report)
        frame3.grid(row=2,column=0)
        frame3.config(height = 100, width = 200)
        frame3.config(relief = RIDGE)
        lbf3 = ttk.LabelFrame(frame3, height=100,width = 200,text = 'FILTER 3')
        lbf3.pack()

        #--------- FILTER 4:  -----------
        frame4 = ttk.Frame(self.frame_report)
        frame4.grid(row=2,column=1)
        frame4.config(height = 100, width = 200)
        frame4.config(relief = RIDGE)
        ttk.LabelFrame(frame4, height=100,width = 200,text = 'FILTER 4').pack()

        # code for calling queries TBA

        # launch results tab if queries successful

        # self.resultsTab()

    def func(self,value):
        print(value)

    # TAB 3: results tab
    def resultsTab(self):

        # create results frame and add to notebook 
        self.frame_results = ttk.Frame(self.notebook)
        self.notebook.add(self.frame_results, text = 'Results')

    def clear(self):
        self.entry_name.delete(0, 'end')
        self.entry_pw.delete(0, 'end')
        self.text_comments.delete(1.0, 'end')

def main():            

    root = Tk()
    hccwgui = ReportGUI(root)
    root.mainloop()

if __name__ == "__main__": main()

提前致谢!

1 个答案:

答案 0 :(得分:0)

# ...
ttk.LabelFrame(frame2, height=100,width = 200,text = 'FILTER 2').pack()
# ...
self.hopOptions = OptionMenu(frame2, self.selectedHop, *hops)
self.hopOptions.grid(row=0, column=2, sticky=EW)

这是你的问题。你在frame2中打包LabelFrame,然后在frame2中尝试网格化。给定的容器只能使用grid()pack()中的一个 - 使用两者都不会导致错误,但两位经理将协商如何在您的余生中放置东西。

解决方案是确保给定容器的子容器是打包的还是网格化的,但绝不会同时放在同一个容器中(尽管你可以有一个结构parent->child->grandchild,其中子包装在父包装中,而孙子包装在网格中在孩子)。