wxPython fast and slow

iu2 israelu at elbit.co.il
Mon Mar 9 00:45:00 CET 2009


On Mar 9, 12:44 am, Scott David Daniels <Scott.Dani... at Acm.Org> wrote:
> iu2 wrote:
> > Here is the timer version. It works even more slowly, even with
> > PyScripter active: ...
>
> > I actually tried this one first. Due to the slow speed I changed to
> > looping inside the event.
> > I don't understand why it takes so long to move that square with
> > wx.Timer set to 1 ms interval. Perhaps its minimum interval is
> > actually 10 ms (as in Windows) so 100 steps really take 1 second.
> > But in that case, I really want to move the square in a tight loop
> > inside the wx.EVT_BUTTON event.
>
> > So allow me to rephrase my question:
> > Is there a way to move that square quickly and smoothly? Should 400
> > one-pixel moves should take so long on a 2.8 GHz core duo?
>
> > There is certainly something wrong in the code I wrote which I need
> > your help to figure out.
> > Can it be related to recurring paint events? If so how should I change
> > the code?
>
> > Thanks
>
> Here is a too-fast version you could fiddle around with:
>
> import wx
>
> class My_frame(wx.Frame):
>      def __init__(self):
>          wx.Frame.__init__(self, None, -1, 'Moving panel')
>          self.surface = p = wx.Panel(self, size=(300, 130))
>          self.square = wx.Panel(p, -1, size=(100, 100), pos=(0, 30))
>          self.square.Bind(wx.EVT_PAINT, self.on_paint_square)
>
>          btn_move = wx.Button(p, -1, 'Move panel', pos=(0, 0))
>          self.Bind(wx.EVT_BUTTON, self.startcalls, btn_move)
>          self.Fit()
>
>      def startcalls(self, evt=None):
>          def gen():
>              for x in range(200):
>                  yield x
>              for x in range(200, 0, -1):
>                  yield x
>          self.track = gen().next
>          wx.CallAfter(self.stepcall)
>
>      def stepcall(self, evt=None):
>          try:
>              x = self.track()
>          except StopIteration:
>              pass
>          else:
>              self.square.SetPosition((x, 30))
>              wx.CallAfter(self.stepcall)
>
>      def on_paint_square(self, evt):
>          square = evt.GetEventObject()
>          dc = wx.BufferedPaintDC(square)
>          dc.Pen = wx.Pen('black', 2)
>          dc.Brush = wx.Brush('light blue')
>          dc.DrawRectangle(0, 0, *square.GetSize())
>
> if __name__ == '__main__':
>      app = wx.PySimpleApp()
>      My_frame().Show()
>      app.MainLoop()

Indeed, but I don't think the CallAfter is necessary. I could just as
well remove the time.sleep in the original code. I could also make a
tight loop to replace time.sleep
for i in range(1000000): pass
and tune it to fit the speed I need.

I haven't mention this, but I actually want something to be the same
speed on different PC-s. So a timer seems to fit in.

I just can't make it work.
Using wx.Timer is too slow.
Using time.sleep is fast with PyScripter active, and slow when it is
closed.



More information about the Python-list mailing list