1

I want to move a button animated. For example it starts from x=0 and y=0, after 0.1 second x=1 and y=1 ... x=50 and y=50.

I tried this:

import tkinter
import time

b=tkinter.Button(text="Example")
for i in range(50): 
    i+=1
    b.place(x=i, y=i)
    time.sleep(0.1)

The window opened after all place commands were executed.

Tomdzsó
  • 25
  • 3
  • 5
  • Because tkinter is event based you end up freezing the main loop when using `sleep()` in it. The `after()` method works with the event manager so this does not happen. – Mike - SMT Nov 21 '18 at 20:15

1 Answers1

4

Do not pause/sleep your python program. As pointed out by @Mike-SMT, it may end up freezing up your mainloop. If you want to do animation, after is the way to go.

import tkinter as tk

root = tk.Tk()
b = tk.Button(root, text="Example")

def move(i):
    if i<=50:
        b.place(x=i, y=i)
        b.after(100, lambda: move(i)) #after every 100ms
        i = i+1

move(0) #Start animation instantly
root.mainloop()

enter image description here

Miraj50
  • 4,257
  • 1
  • 21
  • 34
  • Change this `root.after(0, lambda: move(0))` to `move(0)`. There is no point to doing a `lambda` or `after()` here. – Mike - SMT Nov 21 '18 at 20:13
  • @Mike-SMT: oh, I'm sorry. My mistake. You are correct that the use of after for the first step isn't necessary. I'll remove my comment. – Bryan Oakley Nov 21 '18 at 20:17
  • @BryanOakley Thanks. I was worried for a second. I was like "I am sure that after/lambda is overkill here." lol. – Mike - SMT Nov 21 '18 at 20:21
  • @Mike-SMT Yes, Sorry didn't realise that. Initially I wanted to start the animation after some time, so I had an after there as well. But it is not needed. – Miraj50 Nov 21 '18 at 21:13