I want to call an asynchronous function from a tkinter button
import asyncio
import time
import tkinter as tk
async def gui():
root = tk.Tk()
timer = tk.Button(root, text='Timer', command=lambda: asyncio.run(wait()))
# timer = tk.Button(root, text='Timer', command=wait())
timer.pack()
root.mainloop()
async def sleep():
await asyncio.sleep(1)
async def wait():
start = time.time()
await sleep()
print(f'Elapsed: {time.time() - start}')
async def main():
await wait()
asyncio.run(main())
asyncio.run(gui())
If I use the line
timer = tk.Button(root, text='Timer', command=wait())
I get the error
coroutine 'wait' was never awaited
but if I use the line
timer = tk.Button(root, text='Timer', command=lambda: asyncio.run(wait()))
I get the error
asyncio.run() cannot be called from a running event loop
What's the resolution of this problem?
The essence of this is to understand which functions come under the async umbrella. This is simpler and resolves all the issues. Note that only the sleep function is asynchronous, and the wait function contains the async call
asyncio.run(sleep())
The code is now:
import asyncio
import time
import tkinter as tk
def gui():
root = tk.Tk()
timer = tk.Button(root, text="Timer", command=wait)
timer.pack()
root.mainloop()
def wait():
start = time.time()
asyncio.run(sleep())
print(f'Elapsed: {time.time() - start}')
async def sleep():
await asyncio.sleep(1)
def main():
wait()
main()
gui()