如何在 Tkinter Frame 上淡入淡出 in/out

How to fade in/out on a Tkinter Frame

如何在 Tkinter.Frame 或与此相关的任何其他小部件上淡入 and/or 淡出。我看到的所有示例都是针对 root (Tkinter.Tk) 或 Toplevel 设置 alpha,例如

是否可以将其应用于单个小部件?

您不能对单个小部件执行此操作。 Tkinter 中的透明度仅适用于 TkToplevel.

的实例

根据 Bryan 的回答,我想出了这个解决方案,他无意中也提供了大部分代码。

需要注意的一件事是,如果您移动主 window,顶层不会随之移动...

import Tkinter
import Queue

class Flash(Tkinter.Toplevel):
    def __init__(self, root, **options):
        Tkinter.Toplevel.__init__(self, root, width=100, height=20, **options)

        self.overrideredirect(True) # remove header from toplevel
        self.root = root

        self.attributes("-alpha", 0.0) # set transparency to 100%

        self.queue = Queue.Queue()
        self.update_me()

    def write(self, message):
        self.queue.put(message) # insert message into the queue

    def update_me(self):
        #This makes our tkinter widget threadsafe
        # http://effbot.org/zone/tkinter-threads.htm
        try:
            while 1:
                message = self.queue.get_nowait() # get message from the queue

                # if a message is received code will execute from here otherwise exception
                # 
                x = root.winfo_rootx() # set x coordinate of root
                y = root.winfo_rooty() # set y coordinate of root
                width = root.winfo_width() # get the width of root
                self.geometry("+%d+%d" % (x+width-self.winfo_width() ,y)) # place in the top right cornder of root

                self.fade_in() # fade in when a message is received
                label_flash = Tkinter.Label(self, text=message, bg='black', fg='white', padx=5, pady=5)
                label_flash.pack(anchor='e')
                self.lift(self.root)

                def callback():
                    label_flash.after(2000, label_flash.destroy) # destroy the label after 5 seconds
                    self.fade_away() # fade away after 3 seconds
                label_flash.after(3000, callback)

        except Queue.Empty:
            pass
        self.after(100, self.update_me) # check queue every 100th of a second

    # 
    def fade_in(self):
        alpha = self.attributes("-alpha")
        alpha = min(alpha + .01, 1.0)
        self.attributes("-alpha", alpha)
        if alpha < 1.0:
            self.after(10, self.fade_in)

    # 
    def fade_away(self):
        alpha = self.attributes("-alpha")
        if alpha > 0:
            alpha -= .1
            self.attributes("-alpha", alpha)
            self.after(10, self.fade_away)

if __name__ == '__main__':
    root = Tkinter.Tk()
    root.minsize(700, 300)
    root.geometry("700x500")

    flash = Flash(root) # create toplevel instance

    def callback():
        # put a delay between each message so we can check the behaviour depending on the lenght of the delay between messages
        import time
        flash.write('Hello World')
        time.sleep(1)
        flash.write('Ready!')
        time.sleep(2)
        flash.write('Steady!')
        time.sleep(4)
        flash.write('Go!')

    # create a thread to prevent the delays from blocking our GUI
    import threading
    t = threading.Thread(target=callback)
    t.daemon = True
    t.start()
    root.mainloop()
    exit()