You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Tkinter类在函数内实例化时图片无法加载的问题排查

问题原因与解决方案

问题原因

函数open_GUI()内部创建的test = GUI()是局部变量,函数执行完毕后,Python的垃圾回收机制会销毁这个局部变量,连带销毁GUI实例及其内部的self.img(ImageTk.PhotoImage对象)。而Tkinter要求必须保持对PhotoImage对象的引用,才能让图片在窗口中正常显示,因此函数内实例化的窗口无法加载图片。

解决方案

只要让GUI实例或PhotoImage对象保持持久引用即可,以下是三种常用方法:

方法1:将实例保存为全局变量

修改open_GUI()函数,把GUI实例赋值给全局变量,避免被垃圾回收:

def open_GUI():
    global gui_instance  # 声明全局变量
    gui_instance = GUI()

方法2:将实例绑定到根窗口属性

把GUI实例挂载到root窗口的属性上,利用root窗口的持久存在性保留引用:

def open_GUI():
    root.gui_instance = GUI()

方法3:给Label额外绑定图片引用

在GUI类的__init__方法中,给Label对象添加对图片的引用,确保图片不会被提前回收:

class GUI:
    def __init__(self):
        self.toplevel = tk.Toplevel()
        
        self.img = ImageTk.PhotoImage(Image.open(IMAGE_PATH))
        self.img_label = tk.Label(self.toplevel,image=self.img)
        self.img_label.image = self.img  # 给Label绑定图片引用
        self.img_label.place(x=0,y=0)

这种方法即使GUI实例被局部变量销毁,只要Toplevel窗口还存在,Label就会保留对图片的引用,图片就能正常显示。

修改后的完整代码示例

import tkinter as tk
from PIL import Image,ImageTk

IMAGE_PATH = "your_image_path_here"  # 替换为你的图片路径

#GUI CLASS
class GUI:
    def __init__(self):
        self.toplevel = tk.Toplevel()
        
        self.img = ImageTk.PhotoImage(Image.open(IMAGE_PATH))
        self.img_label = tk.Label(self.toplevel,image=self.img)
        self.img_label.image = self.img  # 添加图片引用绑定
        self.img_label.place(x=0,y=0)

#open the gui with a FUNCTION --> image now opens
def open_GUI():
    root.gui_instance = GUI()  # 绑定到root属性

#root window
root = tk.Tk()
tk.Label(root,text="This is the root").pack()

#tests
test = GUI()
open_GUI()

root.mainloop()

内容的提问来源于stack exchange,提问作者Hunter Davies

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 09:42:12