Update Tkinter GUI

时间:2016-02-12 20:09:45

标签: python tkinter

For my computer class at school we have to create software for a movie kiosk. I have a class which outlines the basis for every screen, then from that class I make separate classes for each individual screen. When the user clicks a button I want a bunch of the widgets on the screen to update to display the relevant information. Here is the class for the screen that displays the movies.

class BrowseMovies(tk.Frame):

    def switchMovie():
        global movNum
        movNum += 1
        print(movNum)
        #update the gui

    def __init__(self, parent, controller):
        tk.Frame.__init__(self,parent)

        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)

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

        middleFrame = tk.Frame(self)
        middleFrame.place(relx=0.5, rely=0.5, anchor=tk.CENTER, height=470, width=750)

        movieImage = ImageTk.PhotoImage(Image.open(moviePosterLinks[movNum]))
        movieImageLabel = tk.Label(middleFrame, image=movieImage, borderwidth=0)
        movieImageLabel.image = movieImage
        movieImageLabel.place(x=0, rely=0.5, anchor=tk.W)

        movieTitleLabel = tk.Label(middleFrame, text=movieTitles[movNum], font=("Verdana", 20), borderwidth=0)
        movieTitleLabel.place(x=317, y=0, anchor=tk.NW)

        movieRatingsLabel = tk.Label(middleFrame, text="Rotten Tomatoes Rating: " + movieRatings[movNum], font=("Verdana", 20), borderwidth=0)
        movieRatingsLabel.place(x=317, y=30, anchor=tk.NW)

        movieRestrictionsLabel = tk.Label(middleFrame, text=movieRestrictions[movNum], font=("Verdana", 20), borderwidth=0)
        movieRestrictionsLabel.place(x=317, y=60, anchor=tk.NW)

        movieDirectorsLabel = tk.Label(middleFrame, text="Director: " + movieDirectors[movNum], font=("Verdana", 20), borderwidth=0)
        movieDirectorsLabel.place(x=317, y=90, anchor=tk.NW)

        movieGenresLabel = tk.Label(middleFrame, text="Genre: " + movieGenres[movNum], font=("Verdana", 20), borderwidth=0)
        movieGenresLabel.place(x=317, y=120, anchor=tk.NW)

        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)

        changeButton = tk.Button(self, text="Switch to next movie", command=lambda: BrowseMovies.switchMovie(controller))
        changeButton.place(relx=1, rely=0.5, anchor=tk.E)

When I call the switchMovies function, the movNum variables (which represents the current selected movie) does update, however the gui stays idle, How could I make it update to display the new information?

********/****Edit****/********

Now adding the code for template "Window" class as suggested.

class Window(tk.Tk):

def __init__(self):
    tk.Tk.__init__(self)

    self.title("Movie Kiosk")
    self.attributes("-fullscreen", True)
    self.resizable(width=False, height=False)

    container = tk.Frame(self)
    container.pack(side="top", fill="both", expand=1)
    container.grid_rowconfigure(0, weight=1)
    container.grid_columnconfigure(0, weight=1)

    self.frames = {}

    for f in (StartPage, CheckOut, BrowseMovies, BrowseSnacks):
        frame = f(container, self)
        self.frames[f] = frame
        frame.grid(row=0, column=0, sticky="nsew")

    self.show_frame(StartPage)

2 个答案:

答案 0 :(得分:1)

我建议使用更简单的名称,而不使用冗余的“电影”和“标签”。但无论如何,由于可以从电影号设置标签,因此定义更新标签的方法,并将其用于初始设置。我假设在您发布的代码之前,movNum被初始化为0。换句话说,

class BrowseMovies(tk.Frame):
    ...
    def __init__(self, parent, controller):
        ...
        title = tk.Label(middleFrame, font=("Verdana", 20), borderwidth=0)
        ...
        self.update_labels()  # after all labels defined
        ...
    def update_labels(self):
        self.title['text'] = movieTitles[movNum]
        ... # similar  for other titles

然后在更改movNum时调用update_labels。

答案 1 :(得分:1)

这可能是以下几点之一:

  1. 这可能取决于你如何召唤GUI。您是否已将所有必要变量全球化?见this。我认为您需要将global MovNum添加到__init__
  2. 的顶部
  3. 更新GUI可能需要dirty trick涉及在每次进程/方法调用后使用root.update()
  4. 你也可以尝试Tk.update()
  5. 这就是我认为基于experience with Tkinter的问题。没有看到你的其余代码就很难分辨。

    祝你好运,编码愉快!