Title: Tkagg event loop throws error on window close · Issue #19940 · matplotlib/matplotlib · GitHub
Open Graph Title: Tkagg event loop throws error on window close · Issue #19940 · matplotlib/matplotlib
X Title: Tkagg event loop throws error on window close · Issue #19940 · matplotlib/matplotlib
Description: I have some code that continuously updates an MPL plot, and used fig.canvas.start_event_loop(0.0001) to listen for keyboard input. As of MPL 3.4, this code is broken in two ways: Commit c53570d converts the timeout to int milliseconds. T...
Open Graph Description: I have some code that continuously updates an MPL plot, and used fig.canvas.start_event_loop(0.0001) to listen for keyboard input. As of MPL 3.4, this code is broken in two ways: Commit c53570d con...
X Description: I have some code that continuously updates an MPL plot, and used fig.canvas.start_event_loop(0.0001) to listen for keyboard input. As of MPL 3.4, this code is broken in two ways: Commit c53570d con...
Opengraph URL: https://github.com/matplotlib/matplotlib/issues/19940
X: @github
Domain: github.com
{"@context":"https://schema.org","@type":"DiscussionForumPosting","headline":"Tkagg event loop throws error on window close","articleBody":"I have some code that continuously updates an MPL plot, and used `fig.canvas.start_event_loop(0.0001)` to listen for keyboard input. As of MPL 3.4, this code is broken in two ways:\r\n\r\n1. [Commit c53570d](https://github.com/matplotlib/matplotlib/commit/c53570db3e602d2855813fa76a971ae3b62d361a) converts the timeout to int milliseconds. This rounds down 0.0001 to 0 and fails to display the window at all. I might suggest `math.ceil(1000*timeout)` instead of `int(1000*timeout)`?\r\n2. After changing 0.0001 to 0.001 in my code, [Commit 630e806](https://github.com/matplotlib/matplotlib/commit/630e806ef7dfd0520490eeb85d2c866d8f8dca94) causes MPL to throw an error `invalid command name \"140668474408832stop_event_loop\" while executing \"140668474408832stop_event_loop\" (\"after\" script)` when closing the window before pausing the loop. Expected behavior would be for it to simply terminate the loop. It's a harmless error in the minimal code below (you can still launch new runs), but my full code updates using an `asyncio` event loop, which this behavior fails to exit, so this error prevents launching new runs in that case (`asyncio.run() cannot be called from a running event loop`). Not sure how to fix this one, but I'll note that using `fig.canvas.flush_events()` in my code instead of `start_event_loop` produces the desired behavior.\r\n\r\nNot sure if #2 is worth fixing given that `flush_events()` restores the desired behavior, but @richardsheridan suggested I post an issue in my comment on that commit. Minimal example below. Launch an MPL window and then close it before pausing to trigger the error:\r\n\r\n```\r\nfrom random import randint\r\nimport matplotlib, matplotlib.pyplot as plt\r\nfrom tkinter import *\r\n\r\nclass Visual:\r\n\trunning = False\r\n\t\r\n\t#Construct a launch button\r\n\tdef __init__(self):\r\n\t\tself.parent = Tk()\r\n\t\t\r\n\t\tself.runButton = Button(self.parent, text='Run', command=self.launchVisual, padx=10, pady=10)\r\n\t\tself.runButton.pack(fill=\"x\", side=TOP)\r\n\t\t\t\t\t\r\n\tdef start(self):\r\n\t\tself.runButton['text'] = 'Pause'\r\n\t\tself.runButton['command'] = self.stop\r\n\t\tself.running = True\r\n\t\t\r\n\t\twhile self.running:\r\n\t\t\tself.data.append(randint(0,100))\r\n\t\t\r\n\t\t\tself.line.set_ydata(self.data)\r\n\t\t\tself.line.set_xdata(range(len(self.data)))\r\n\t\t\tself.axes.relim()\r\n\t\t\tself.axes.autoscale_view(tight=False)\r\n\t\t\r\n\t\t\tif self.fig.stale: self.fig.canvas.draw_idle()\r\n\t\t\t\r\n\t\t\t#This rounds down to 0 and doesn't draw the window at all\r\n\t\t\t#self.fig.canvas.start_event_loop(0.0001)\r\n\t\t\t\r\n\t\t\t#This throws an error and breaks asyncio if you close the window before pausing\r\n\t\t\tself.fig.canvas.start_event_loop(0.001)\r\n\t\t\r\n\t\t\t#This works\r\n\t\t\t#self.fig.canvas.flush_events()\r\n\t\r\n\tdef stop(self, *args):\r\n\t\tself.running = False\r\n\t\tself.runButton['text'] = 'Run'\r\n\t\tself.runButton['command'] = self.start\r\n\t\r\n\tdef terminate(self, evt=False):\r\n\t\tself.running = False\r\n\t\tself.runButton['text'] = 'New Model'\r\n\t\tself.runButton['command'] = self.launchVisual\r\n\t\t\r\n\tdef launchVisual(self):\r\n\t\tmatplotlib.use('TkAgg')\r\n\t\tself.fig, self.axes = plt.subplots()\r\n\t\tself.fig.canvas.mpl_connect('close_event', self.terminate)\r\n\t\t\r\n\t\t#Keyboard input\r\n\t\tdef pause(event):\r\n\t\t\tif event.key==' ' and event.canvas is self.fig.canvas:\r\n\t\t\t\tif self.running: self.stop()\r\n\t\t\t\telse: self.start()\r\n\t\tself.fig.canvas.mpl_connect('key_press_event', pause)\r\n\t\t\r\n\t\tself.data = []\r\n\t\tself.line, = self.axes.plot(self.data, color='#330099')\r\n\t\t\r\n\t\tself.fig.canvas.draw_idle()\r\n\t\tplt.show(block=False)\r\n\t\t\r\n\t\tself.start()\r\n\r\nviz = Visual()\r\nviz.parent.mainloop()\r\n```","author":{"url":"https://github.com/charwick","@type":"Person","name":"charwick"},"datePublished":"2021-04-11T19:15:10.000Z","interactionStatistic":{"@type":"InteractionCounter","interactionType":"https://schema.org/CommentAction","userInteractionCount":2},"url":"https://github.com/19940/matplotlib/issues/19940"}
| route-pattern | /_view_fragments/issues/show/:user_id/:repository/:id/issue_layout(.:format) |
| route-controller | voltron_issues_fragments |
| route-action | issue_layout |
| fetch-nonce | v2:058995e3-c7e6-858d-453a-c8baabfc41a9 |
| current-catalog-service-hash | 81bb79d38c15960b92d99bca9288a9108c7a47b18f2423d0f6438c5b7bcd2114 |
| request-id | 82EA:2442E4:20DFB:2C5E7:6A51C914 |
| html-safe-nonce | 73ee9478ba25dc132fb6761a830a6fd2718d934d2eb1a4e036dc243323cdcef4 |
| visitor-payload | eyJyZWZlcnJlciI6IiIsInJlcXVlc3RfaWQiOiI4MkVBOjI0NDJFNDoyMERGQjoyQzVFNzo2QTUxQzkxNCIsInZpc2l0b3JfaWQiOiI4OTE0MTE0MTIxMDgwODgzNDc2IiwicmVnaW9uX2VkZ2UiOiJpYWQiLCJyZWdpb25fcmVuZGVyIjoiaWFkIn0= |
| visitor-hmac | af4eaf787f7d287aa7d1f35541c12e42aec993dc22320eb687803d1602b13b0b |
| hovercard-subject-tag | issue:855385435 |
| github-keyboard-shortcuts | repository,issues,copilot |
| google-site-verification | Apib7-x98H0j5cPqHWwSMm6dNU4GmODRoqxLiDzdx9I |
| octolytics-url | https://collector.github.com/github/collect |
| analytics-location | / |
| fb:app_id | 1401488693436528 |
| apple-itunes-app | app-id=1477376905, app-argument=https://github.com/_view_fragments/issues/show/matplotlib/matplotlib/19940/issue_layout |
| twitter:image | https://opengraph.githubassets.com/c210624fcff83359badf00a2c81125e748c10060e25b7c83780434340d6811fc/matplotlib/matplotlib/issues/19940 |
| twitter:card | summary_large_image |
| og:image | https://opengraph.githubassets.com/c210624fcff83359badf00a2c81125e748c10060e25b7c83780434340d6811fc/matplotlib/matplotlib/issues/19940 |
| og:image:alt | I have some code that continuously updates an MPL plot, and used fig.canvas.start_event_loop(0.0001) to listen for keyboard input. As of MPL 3.4, this code is broken in two ways: Commit c53570d con... |
| og:image:width | 1200 |
| og:image:height | 600 |
| og:site_name | GitHub |
| og:type | object |
| og:author:username | charwick |
| hostname | github.com |
| expected-hostname | github.com |
| None | b9a586c06a05a7a86fc7e3f4dbd03e42f6869085879aa184aa6369456dbd50fb |
| turbo-cache-control | no-preview |
| go-import | github.com/matplotlib/matplotlib git https://github.com/matplotlib/matplotlib.git |
| octolytics-dimension-user_id | 215947 |
| octolytics-dimension-user_login | matplotlib |
| octolytics-dimension-repository_id | 1385122 |
| octolytics-dimension-repository_nwo | matplotlib/matplotlib |
| octolytics-dimension-repository_public | true |
| octolytics-dimension-repository_is_fork | false |
| octolytics-dimension-repository_network_root_id | 1385122 |
| octolytics-dimension-repository_network_root_nwo | matplotlib/matplotlib |
| turbo-body-classes | logged-out env-production page-responsive |
| disable-turbo | false |
| browser-stats-url | https://api.github.com/_private/browser/stats |
| browser-errors-url | https://api.github.com/_private/browser/errors |
| release | 7aed05249554b889eb33d002851a973eebcc7e91 |
| ui-target | full |
| theme-color | #1e2327 |
| color-scheme | light dark |
Links:
Viewport: width=device-width