TheLegendaryCoder
TheLegendaryCoder

Reputation: 3

unable to update image in tkinter using a function

I am trying to create a Tkinter to make a window that shows images using a label, then update the image using an update function, but the image that I am trying to show doesn't show up in the Tkinter window, instead, a black screen appears

I have two working code

  1. one that shows an image on the Tkinter window
  2. one what loops a GIF using an update function

I tried to combine them

the code I am working on that doesn't work

#import GUI
from tkinter import *

#change dir
import os
os.chdir("C:/Users/user/Desktop/test image folder/")

#add delay
import time

#import image
from PIL import Image, ImageTk

#set up the window
window = Tk()
#window.title("modify images")

#list of filename
filelist = []

#loop over all files in the working directory
for filename in os.listdir("."):
    if not (filename.endswith('.png') or filename.endswith('.jpg')):
        continue #skip non-image files and the logo file itself
    filelist = filelist + [filename]

#list of filename
print(filelist)

#show first pic
imagefile = filelist[0]
photo = ImageTk.PhotoImage(Image.open(imagefile))
label1 = Label(window, image = photo)
label1.pack()

#update image
def update(ind):
    imagefile = filelist[ind]
    im = ImageTk.PhotoImage(Image.open(imagefile))
    if ind < len(filelist):
        ind += 1
    else:
        ind = 0
    label1.configure(image=im)
    window.after(2000, update, ind)
window.after(2000, update, 0)

#run the main loop
window.mainloop()

the other code I am trying to combine

1:the one that shows image

import tkinter as tk
from tkinter import *
from PIL import Image, ImageTk  # Place this at the end (to avoid any conflicts/errors)


window = tk.Tk()
imagefile = "image.jpg"
img = ImageTk.PhotoImage(Image.open(imagefile))
lbl = tk.Label(window, image = img).pack()
window.mainloop()
print('hi')

2:updates gif

from tkinter import *

#change dir
import os
os.chdir("C:/Users/user/Desktop/Learn Python")

#add delay
import time

##### main:
window = Tk()

##### My Photo
photo1 = [PhotoImage(file="anime.gif", format="gif -index %i" %(i)) for i in range(85)]

#update image
def update(ind):
    frame = photo1[ind]
    if ind < 84:
        ind += 1
    else:
        ind = 0
    label.configure(image=frame)
    window.after(80, update, ind)
label = Label(window, bg="black")
label.pack()
window.after(0, update, 0)

#####run the main loop
window.mainloop()

I expect it to show all images in the file one by one

it instead shows only the first image, then the window goes blank

Upvotes: 0

Views: 890

Answers (1)

furas
furas

Reputation: 142631

You have problem because there is bug in PhotoImage. If you create it in function and assign to local variable then Garbage Collector removes image from memory and you see empty image. You have to create PhotoImages outside function or you have to assign it to some global variable.

Popular solution is to assign it to label which will display it.

label.im = im

Function:

def update(ind):
    imagefile = filelist[ind]
    im = ImageTk.PhotoImage(Image.open(imagefile))

    if ind < len(filelist):
        ind += 1
    else:
        ind = 0

    label1.configure(image=im)

    label1.im = im  # <-- solution

    window.after(2000, update, ind)

Doc: PhotoImage

Upvotes: 1

Related Questions