Different between canvas.draw() and canvas.restore_region()??

canvas.draw() is slow in animation, I have succeed in replacing it with
canvas.restore_region(). And it is wonderful.
    However, in the following, I fail to make it work the same as
canvas.draw().The following code can work. And creat a dynamic line. When I
work with the statement "#self.canvas.draw()" .The result is exactly what I
want.

However, canvas.restore_region() fail to do as canvas.draw() here. The
problem is when I refresh the line, the previous line is not clear as I want
to.Could anyone help me? Thanks.

import wx
from matplotlib.backends.backend_wxagg import FigureCanvasWxAgg
from matplotlib.figure import Figure

class Temp:
    
    def __init__(self):
        app = wx.PySimpleApp()
        frame=wx.Frame(None,size=(700,500))
        frame.Show(True)
        
        ##Creat figure , canvas , axe.
        fig = Figure((8.8,6),facecolor='w')
        self.canvas = FigureCanvasWxAgg(frame, -1, fig)
        self.ax=fig.add_axes([0.1,0.15,0.7,0.7],axisbg='#dedff7')
        
        ##Get background for OnTimer function.
        self.background=self.canvas.copy_from_bbox(self.ax.bbox)
        
        ##Create line on axe.
        self.y=[1,1]
        self.x=[0,10]
        self.line,=self.ax.plot(self.x,self.y)
        
        ##Bind timer to refresh line
        timer=wx.Timer()
        timer.Bind(wx.EVT_TIMER, self.OnTimer, timer)
        timer.Start(1000)
        app.MainLoop()
        
    def OnTimer(self,event):

        self.y=[self.y[0]+0.005,self.y[1]+0.005]
          
        self.line.set_data(self.x,self.y)
        self.canvas.restore_region(self.background)
             
        self.ax.draw_artist(self.line)
        self.canvas.blit(self.ax.bbox)
        self.canvas.gui_repaint()
        #self.canvas.draw()
Temp()

···


View this message in context: http://www.nabble.com/Different-between-canvas.draw()-and-canvas.restore_region()---tp16790656p16790656.html
Sent from the matplotlib - users mailing list archive at Nabble.com.

The basic idiom is show in the attached example animation_blit.py.
You create a line with the "amimated" property set True. Then calling
draw will draw everything but the animated objects

line, = p.plot(x, npy.sin(x), animated=True, lw=2)

Then you copy the drawn region minus the animated parts as a
background. On the first draw, do

.background = canvas.copy_from_bbox(ax.bbox)

Then to animate your line, restore the background, update your line
data, and blit the region:

canvas.restore_region(background)
line.set_ydata(ydata)
ax.draw_artist(line)
canvas.blit(ax.bbox)

There are animation blit examples for most GUI toolkits in the
examples directory.

JDH

animation_blit.py (1.32 KB)

···

On Sun, Apr 20, 2008 at 3:33 AM, hjc520070 <jiacong_huang@...1221...> wrote:

    canvas.draw() is slow in animation, I have succeed in replacing it with
canvas.restore_region(). And it is wonderful.
    However, in the following, I fail to make it work the same as
canvas.draw().The following code can work. And creat a dynamic line. When I
work with the statement "#self.canvas.draw()" .The result is exactly what I
want.

However, canvas.restore_region() fail to do as canvas.draw() here. The
problem is when I refresh the line, the previous line is not clear as I want
to.Could anyone help me? Thanks.

Thanks for your help. I get it work. However, an interesting thing appears.
The following two codes(code 1 and code 2) makes different result??? Only
set background in different place. Anyone can tell me why? I am eager to
know it.

##code 1
import wx
from matplotlib.backends.backend_wxagg import FigureCanvasWxAgg
from matplotlib.figure import Figure

class Temp:
    def __init__(self):
        
        self.step=0
        
        app = wx.PySimpleApp()
        frame=wx.Frame(None,size=(700,500))
        frame.Show(True)
        
        ##Creat figure , canvas , axe.
        fig = Figure((8.8,6),facecolor='w')
        self.canvas = FigureCanvasWxAgg(frame, -1, fig)
        self.ax=fig.add_axes([0.1,0.15,0.7,0.7],axisbg='#dedff7')
                
        ##Create line on axe.
        self.y=[1,1]
        self.x=[0,10]
        self.line,=self.ax.plot(self.x,self.y,animated=True)
        
        ##Bind timer to refresh line
        timer=wx.Timer()
        timer.Bind(wx.EVT_TIMER, self.OnTimer, timer)
        timer.Start(1000)

        app.MainLoop()
     
    def OnTimer(self,event):

        self.step=self.step+1
       
        if self.step==1:
            self.background=self.canvas.copy_from_bbox(self.ax.bbox)
            
        self.y=[self.y[0]+0.005,self.y[1]+0.005]
        self.canvas.restore_region(self.background)
        self.line.set_data(self.x,self.y)
        self.ax.draw_artist(self.line)
        self.canvas.blit(self.ax.bbox)
Temp()

##Code 2
import wx
from matplotlib.backends.backend_wxagg import FigureCanvasWxAgg
from matplotlib.figure import Figure

class Temp:
    
    def __init__(self):
        
        self.step=0
        
        app = wx.PySimpleApp()
        frame=wx.Frame(None,size=(700,500))
        frame.Show(True)
        
        ##Creat figure , canvas , axe.
        fig = Figure((8.8,6),facecolor='w')
        self.canvas = FigureCanvasWxAgg(frame, -1, fig)
        self.ax=fig.add_axes([0.1,0.15,0.7,0.7],axisbg='#dedff7')
                
        ##Create line on axe.
        self.y=[1,1]
        self.x=[0,10]
        self.line,=self.ax.plot(self.x,self.y,animated=True)
        
        self.background=self.canvas.copy_from_bbox(self.ax.bbox)

        ##Bind timer to refresh line
        timer=wx.Timer()
        timer.Bind(wx.EVT_TIMER, self.OnTimer, timer)
        timer.Start(1000)

        app.MainLoop()
     
    def OnTimer(self,event):

        self.step=self.step+1
                   
        self.y=[self.y[0]+0.005,self.y[1]+0.005]
        self.canvas.restore_region(self.background)
        self.line.set_data(self.x,self.y)
        self.ax.draw_artist(self.line)
        self.canvas.blit(self.ax.bbox)
Temp()

···


View this message in context: http://www.nabble.com/Different-between-canvas.draw()-and-canvas.restore_region()---tp16790656p16801603.html
Sent from the matplotlib - users mailing list archive at Nabble.com.

In code2, you copy the background before the canvas is drawn, which is
wrong. code 1 is the correct approach. Calling ax.plot is not enough
to cause the background to be drawn. You must call fig.canvas.draw
first.

JDH

···

On Sun, Apr 20, 2008 at 9:13 PM, hjc520070 <jiacong_huang@...1221...> wrote:

Thanks for your help. I get it work. However, an interesting thing appears.
The following two codes(code 1 and code 2) makes different result??? Only
set background in different place. Anyone can tell me why? I am eager to
know it.

I'm confused, because I don't see any place where self.canvas.draw is
called in the code1 version. Also, when I resize the figure, the
background region changes, so the plot gets messed up as I have
noticed before with this method. Does anyone know a good way to
recapture a clean background, in particular when the image is resized?
Thanks,
Glenn

···

On Mon, Apr 21, 2008 at 6:21 AM, John Hunter <jdh2358@...287...> wrote:

On Sun, Apr 20, 2008 at 9:13 PM, hjc520070 <jiacong_huang@...1221...> wrote:
>
> Thanks for your help. I get it work. However, an interesting thing appears.
> The following two codes(code 1 and code 2) makes different result??? Only
> set background in different place. Anyone can tell me why? I am eager to
> know it.

In code2, you copy the background before the canvas is drawn, which is
wrong. code 1 is the correct approach. Calling ax.plot is not enough
to cause the background to be drawn. You must call fig.canvas.draw
first.

JDH

-------------------------------------------------------------------------
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference
Don't miss this year's exciting event. There's still time to save $100.
Use priority code J8TL2D2.
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone
_______________________________________________
Matplotlib-users mailing list
Matplotlib-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/matplotlib-users

It's a good question. There is no explicit fig.canvas.draw in the
code1 example, but there is an implicit one, since the relevant
function calls ("draw_artist", "restore_region" and "blit") occur in
the wx OnTimer method. These things are GUI dependent, but stuff that
happens in the idle hander or timer handler of GUI toolkits often
happen after the initial mpl draw.

JDH

···

On Thu, Apr 24, 2008 at 2:43 AM, G Jones <glenn.caltech@...287...> wrote:

I'm confused, because I don't see any place where self.canvas.draw is
called in the code1 version. Also, when I resize the figure, the
background region changes, so the plot gets messed up as I have
noticed before with this method. Does anyone know a good way to
recapture a clean background, in particular when the image is resized?