动态添加Tkinter小部件

时间:2016-02-23 16:55:15

标签: python tkinter

对于我的计算机科学课,我们被分配了制作电影亭的任务。用户将商品添加到购物车中,我以列表的形式存储。当加载结账屏幕时,我想添加标签,显示用户在购物车中有哪些商品。我有以下代码:

class CheckOut(tk.Frame): #check out page

def __init__(self, parent, controller):
    tk.Frame.__init__(self, parent)
    #create and place base widgets
    backGroundPicture = ImageTk.PhotoImage(Image.open("Background.jpg"))
    backGroundLabel = tk.Label(self, image=backGroundPicture, borderwidth=0)
    backGroundLabel.image = backGroundPicture
    backGroundLabel.place(x=0, y=0, anchor=tk.NW)

    checkOutLabel = tk.Label(self, text="Check Out", font=("Verdana", 48), bg="#001f33", fg="red")
    checkOutLabel.place(relx=0.5, rely=0, anchor=tk.N)

    returnButton = tk.Button(self, text="Return to Main Menu", bg="#4db8ff", fg="black",
                       command=lambda: controller.show_frame(StartPage))
    returnButton.place(relx=1, rely=1, anchor=tk.SE)

def update(): #add new widgets displaying items purchase
    print("debug")
    itemLists = []
    for each in movieTitles:
        i = movieTitles.index(each)
        if(adultTickets[i] != 0):
            tempLabel = tk.Label(self, text="Adult Ticket: " + str(adultTickets[i]) + " " + each)
            itemLists.append(tempLabel)
        if(childTickets[i] != 0):
            tempLabel = tk.Label(self, text="Child Ticket: " + str(childTickets[i]) + " " + each)
            itemLists.append(tempLabel)
    for i in itemLists:
        i.place(x=100, y=200, anchor=tk.CENTER)
    print(itemLists)

除非我尝试使用self的父级创建标签,否则一切正常。它未定义。我想将它们放在init方法使用的相同框架中。我怎样才能获得自我?我可以使用某种工作吗?

1 个答案:

答案 0 :(得分:1)

附注:StackOverflow期望代码示例有额外的4个空格缩进。如果您只是粘贴代码,请在文本框中选择它,然后点击"代码示例"编辑器中的按钮(标记为{}),它将添加缩进。

class CheckOut(tk.Frame): #check out page
    def __init__(self, parent, controller):
        tk.Frame.__init__(self, parent)
        #create and place base widgets
        backGroundPicture = ImageTk.PhotoImage(Image.open("Background.jpg"))
        backGroundLabel = tk.Label(self, image=backGroundPicture, borderwidth=0)
        backGroundLabel.image = backGroundPicture
        backGroundLabel.place(x=0, y=0, anchor=tk.NW)

        checkOutLabel = tk.Label(self, text="Check Out", font=("Verdana", 48), bg="#001f33", fg="red")
        checkOutLabel.place(relx=0.5, rely=0, anchor=tk.N)

        returnButton = tk.Button(self, text="Return to Main Menu", bg="#4db8ff", fg="black",
                           command=lambda: controller.show_frame(StartPage))
        returnButton.place(relx=1, rely=1, anchor=tk.SE)

    ...

Python中类的方法将对象作为方法的第一个参数传递。作为约定,此参数名为self,但实际上,您可以为其指定任何名称。*因此,请将self作为参数添加到update方法中。我想你也想把电影标题作为参数传递给update方法。

    ...

    def update(self, movieTitles): #add new widgets displaying items purchase
        print("debug")
        itemLists = []
        for each in movieTitles:
            i = movieTitles.index(each)
            if(adultTickets[i] != 0):
                tempLabel = tk.Label(self, text="Adult Ticket: " + str(adultTickets[i]) + " " + each)
                itemLists.append(tempLabel)
            if(childTickets[i] != 0):
                tempLabel = tk.Label(self, text="Child Ticket: " + str(childTickets[i]) + " " + each)
                itemLists.append(tempLabel)
        for i in itemLists:
            i.place(x=100, y=200, anchor=tk.CENTER)
        print(itemLists)

这样,在实例化对象后,您可以应用如下方法:

# instantiate object
my_frame = CheckOut(parent, controller)

# apply "update"
my_frame.update(my_movie_titles)

# The previous line has the same effect as this:
CheckOut.update(my_frame, my_movie_titles)

注意:我没有测试代码,我只修复了你在那里的一点语法错误。乍看之下,电影的标签似乎都具有相同的位置。

此外,作为用户" zondo"暗示,lambdas在这里和那里混乱了代码;摆脱它们可以使代码更容易阅读。像这样的简单事件可以用partial模块中的函数functools替换:

from functools import partial

returnButton = tk.Button(self, ..., 
    command=partial(controller.show_frame, StartPage))
  • 其他语言(如C ++ / Java和family)将保留关键字。 (this