【问题标题】:Tkinter not changing image on button pressTkinter 在按钮按下时没有改变图像
【发布时间】:2017-01-15 03:15:56
【问题描述】:

我已将图像加载到 tkinter 标签,并且该图像显示在该标签中。当我按下按钮时,我需要更改该图像。当按下按钮时,旧图像消失但新图像不显示 我的代码是

import Tkinter as tk
from PIL import Image, ImageTk
root = tk.Tk()

def change_pic(labelname):
 photo1 = ImageTk.PhotoImage(Image.open("demo.jpg"))
 labelname.configure(image=photo1)
 print "updated"

vlabel=tk.Label(root)
photo = ImageTk.PhotoImage(Image.open('cardframe.jpg'))
vlabel.configure(image=photo)
vlabel.pack()
b2=tk.Button(root,text="Capture",command=lambda:change_pic(vlabel))
b2.pack()
root.mainloop()

【问题讨论】:

  • 不知道PIL是不是和Tkinter的PhotoImage一样。在 Python 中,有垃圾收集,有时它不会做我们希望它做的事情。您需要做什么才能将图像作为单独的实例,然后将其应用于类,否则,Python 会收集您的图像实例。 image = Image.open("demo.jpg")photo = PhotoImage(image) 一起可能会起作用。
  • @PrestonHager 试过但没用

标签: python user-interface tkinter


【解决方案1】:

def change_pic(labelname) 中,您需要添加labelname.photo = photo1 以确保photo1 不会被垃圾回收。

def change_pic(labelname):
    photo1 = ImageTk.PhotoImage(Image.open("demo.jpg"))
    labelname.configure(image=photo1)
    labelname.photo = photo1
    print "updated"

P.S.看起来labelname.photo = photo1labelname.image = photo1 都可以工作。

查看更多详情:http://effbot.org/tkinterbook/label.htm

您可以使用标签来显示 PhotoImage 和 BitmapImage 对象。 执行此操作时,请确保保留对图像对象的引用, 防止它被 Python 的内存垃圾回收 分配器。您可以使用全局变量或实例属性,或者 更简单,只需向小部件实例添加一个属性。

【讨论】:

  • 我想知道是否有这样一个已知问题,为什么它没有在配置函数中完成?
【解决方案2】:

进行了以下修改:

  1. 我已经组织了您的代码布局并简化了它 尽可能的语法。这些是为了让您的代码更易于阅读。
  2. 通常我们将 PIL 对象设为 tk 的子集/子对象。 只要它是根的一部分(即它是根的孩子 或其任何子小部件),您的 PIL 对象将起作用。

您的工作代码如下所示:

import Tkinter as tk
from PIL import Image, ImageTk

def change_pic():
    vlabel.configure(image=root.photo1)
    print "updated"

root = tk.Tk()

photo = 'cardframe.jpg'
photo1 = "demo.jpg"
root.photo = ImageTk.PhotoImage(Image.open(photo))
root.photo1 = ImageTk.PhotoImage(Image.open(photo1))

vlabel=tk.Label(root,image=root.photo)
vlabel.pack()

b2=tk.Button(root,text="Capture",command=change_pic)
b2.pack()

root.mainloop()

【讨论】:

    【解决方案3】:

    我得到了它的另一行代码:

    import tkinter as tk                        # I am using python 3 on windows so the tkinter is lowercased
    from PIL import Image, ImageTk
    root = tk.Tk()
    
    def change_pic(labelname):
        global photo1                           # This is the only new line you need, I believe
        photo1 = ImageTk.PhotoImage(Image.open("demo.jpg"))
        labelname.configure(image=photo1)
        print("updated")                        # Again I'm using python 3 on windows so syntax may differ.
        root.update()                           # You don't need this statement in this case, but it never hurts
    
    vlabel=tk.Label(root)
    photo = ImageTk.PhotoImage(Image.open('cardframe.jpg'))
    vlabel.configure(image=photo)
    vlabel.pack()
    b2=tk.Button(root,text="Capture",command=lambda:change_pic(vlabel))
    b2.pack()
    root.mainloop()
    

    我相信代码在本地改变了图像,所以global语句会在项目范围上改变它。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-09-20
      • 1970-01-01
      • 2011-12-17
      • 2017-07-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多