New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Qt5Agg blitting issue with matplotlib 2.2.2 #10949
Comments
With class BlittedFigure(object):
def __init__(self):
self._background = None
def _set_background(self):
if self.figure:
canvas = self.figure.canvas
if canvas.supports_blit:
self._background = canvas.copy_from_bbox(self.figure.bbox)
def _on_draw(self, *args):
if self.figure:
canvas = self.figure.canvas
if canvas.supports_blit:
self._set_background()
self._draw_animated(do_blit=False)
def _draw_animated(self, do_blit=True):
if self.ax.figure and self.figure.axes:
canvas = self.ax.figure.canvas
if do_blit and canvas.supports_blit:
canvas.restore_region(self._background)
for ax in self.figure.axes:
artists = []
artists.extend(ax.images)
artists.extend(ax.collections)
artists.extend(ax.patches)
artists.extend(ax.lines)
artists.extend(ax.texts)
artists.extend(ax.artists)
artists.append(ax.get_yaxis())
artists.append(ax.get_xaxis())
for a in artists:
if a.get_animated():
ax.draw_artist(a)
if do_blit and canvas.supports_blit:
canvas.blit(self.figure.bbox) it behaves as expected on close-to-master. See warning https://matplotlib.org/api/backend_bases_api.html?highlight=draw_event#matplotlib.backend_bases.DrawEvent (which is probably not the best place for that warning) and discussion at #9406 I'm a bit confused by what version your using ,and which versions it works on. |
Thanks @tacaswell for the quick reply! It is useful and your fix seems work nicely even if I don't think that I understand the reason... Sorry for the confusion between the different versions, indeed I made a mistake in the title of the issue, which is corrected now. I also edited the first post to clarify the issue. I have been pulling my hair out for too many hours!! And thanks for pointing out to the relevant issue/documentation on this, we fixed this issue with disconnecting and re-connecting the Out of curiosity: why was it working before and it is broken with the last release? |
There were some tweaks all the way at the bottom of the Qt draw stack that changed exactly how the Qt level that shifted details of when the call to the base draw happened and unified the normal and blitting code paths. Before Agg would render, the draw_event would fire, and then the paint event would happen, now the paint event starts, if it has to re-render Agg renders, draw_event fires (with-in the paint event), and then the paint event exits. Moving the draw_event inside of the paint is what causes trouble for the blitting as it then recurses at the Qt level! I strongly suggest not doing things inside of |
What triggers a |
It is triggered in matplotlib/lib/matplotlib/figure.py Line 1480 in 02646cb
That method is called on your behalf via the matplotlib/lib/matplotlib/backends/backend_agg.py Lines 414 to 433 in 02646cb
It is best to think of the 'draw_event' subscription as "I have just redrawn the figure from scratch at the current DPI and size, but with out anything labeled 'animated' and have not yet put it on the screen" |
Closing since the issue has been fixed in hyperspy/hyperspy#1890. Thanks @tacaswell for the explanation. |
Bug report
Bug summary
Plotting is broken in hyperspy (1.3 and dev) following matplotlib 2.2.2 release: the animated artists are not drawn as expected. In the dev version of hyperspy, the recursive repaint issue (canvas.blit call in a
draw_event
callback) has been fixed.We used blitting and the plotting code is quite convolved (a bit messy) in hyperspy, I have been looking for the bug in hyperspy -typically not blitting correctly- but I couldn't find any mistake...
Code for reproduction
This is a minimal example to reproduce the issue without using hyperspy. This is designed to be run in interactive environment (ipython).
This is a minimal example to reproduce the issue using hyperspy in ipython.
Actual outcome
The animated are missing from the figure in the first draw. Once a
draw_event
is triggered, everything is plotted on the figure as expected. When resizing the figure, the animated artists are not plotted, triggering adraw_event
plots the them. This is working fine with matplotlib 2.1.2, including resizing the figure.Expected outcome
Plot everything, including the animated artists
Matplotlib version
print(matplotlib.get_backend())
): Qt5AggThe text was updated successfully, but these errors were encountered: