1

While my code is running after click run button in tkinter's window,it will show "not responding" when i click it . How to make it not respond when click and show loading progress? This is loading code that i use.

from tkinter import *
from tkinter.ttk import *
import time
window = Tk()
window.geometry("400x200")
percent = StringVar()
text = StringVar()
def start():
    def task():
        bar['value']=0
        GB = 100
        download = 0
        speed = 1
        while(download<GB):
            time.sleep(0.05)
            bar['value']+=(speed/GB)*100
            download+=speed
            percent.set(str(int((download/GB)*100))+"%")
            text.set(str(download)+"/"+str(GB)+" GB completed")
            window.after(2000, None)
            window.update_idletasks()
        window.after(1, task)
    window.after(100, task)

bar = Progressbar(window,orient=HORIZONTAL,length=300)
bar.pack(pady=10)
percentLabel = Label(window,textvariable=percent).pack()
taskLabel = Label(window,textvariable=text).pack()
button = Button(window,text="download",command=start).pack()
window.mainloop()    
test only
  • 13
  • 2

2 Answers2

0

Try this:

import tkinter as tk
from tkinter import ttk

window = tk.Tk()
window.geometry("400x200")
percent = tk.StringVar(master=window)
text = tk.StringVar(master=window)

def start():
    download = 0
    def task(download):
        bar["value"] = download
        GB = 100
        speed = 1
        if download <= GB:
            bar["value"] += (speed/GB)*100
            percent.set(str(int((download/GB)*100))+"%")
            text.set(str(download)+"/"+str(GB)+" GB completed")
        window.after(1000, task, download+1)
    window.after(1000, task, 0)

bar = ttk.Progressbar(window,orient="horizontal", length=300)
bar.pack(pady=10)
percentLabel = tk.Label(window, textvariable=percent)
percentLabel.pack()
taskLabel = tk.Label(window, textvariable=text)
taskLabel.pack()
button = tk.Button(window, text="download", command=start)
button.pack()
window.mainloop()  
TheLizzard
  • 7,248
  • 2
  • 11
  • 31
  • 1
    Instead of `window.after(100, lambda: task(download+1))` it's better to use `window.after(100, task, download+1)`. Same goes for `window.after(1000, lambda: task(0))` – TheLizzard Jul 14 '21 at 11:13
0

I've taken function task out of start and implemented a Button disable in order to prevent multiple button presses.

Also made the update percent and download output code for version 2.x and 3.x

try:
    import tkinter as tk
    from tkinter import ttk
except ImportError:
    # Can't test it but according to this: https://stackoverflow.com/a/23984633/11106801
    import Tkinter as tk
    import ttk

window = tk.Tk()
window.geometry("400x200")
percent = tk.StringVar(master=window)
text = tk.StringVar(master=window)

def task(download):
    bar['value'] = download
    GB = 100
    speed = 1
    if GB >= download:
        bar['value'] += speed/GB*100
        percent.set("{} %".format(int(download/GB*100)))
        text.set("{} / {}  GB completed".format(download, GB))
    window.after(100, task, download+1)

def start():
    button.config(state="disabled")
    task(0)

bar = ttk.Progressbar(window, orient="horizontal", length=300)
bar.pack(pady=10)

percentLabel = tk.Label(window, textvariable=percent)
percentLabel.pack()

taskLabel = tk.Label(window, textvariable=text)
taskLabel.pack()

button = tk.Button(window, text="download", command=start)
button.pack()

window.mainloop()
TheLizzard
  • 7,248
  • 2
  • 11
  • 31
Derek
  • 1,916
  • 2
  • 5
  • 15