# [wxPython] new mandelbrot version Classic List Threaded 4 messages Open this post in threaded view
|

## [wxPython] new mandelbrot version

 Hi! The calculation time is now further reduced by 30%.  I found, that Mike put some redundant stuff in the mandelbrot function.  Although Mike used a wxTimer, the application isn't responsive during calculation, so I didn't include this approach. I will continue posting the mandelbrot program to this mailing list, because 1) The mandelbrot program was born here, 2) Some interested people read this mailing list (Ionel, Mike, ...) 3) I find it more interesting to do mandelbrot calculations when the output is shown on the screen 4) There was no response to Mikes posting on comp.lang.python (maybe because of the high traffic there). --- Have fun, Markus #! /usr/bin/env python #######################################################################################94x78## """ Mandelbrot program, for no particular reason.         John Farrell: initial version           Robin Dunn: introduced wxImage.SetData instead of wxBitmapFromData     Ionel Simionescu: used the Numeric package, and rewrote all of the                         computation and data displaying code Alexander Smishlajev: suggestions on optimising loops and drawing       Markus Gritsch: in-place calculation in the mandelbrot while loop        Mike Fletcher: Numeric.repeat instead of Numeric.compress """ from wxPython.wx import * import Numeric WIDTH = 200 HEIGHT = 200 #coords = ((-1.0, -1.5), (0.0, -0.5)) coords = ((-2.0, -1.5), (1.0, 1.5)) WEIGHTS = (16, 1, 32) MAX_ITERATIONS = 255 zero = complex(0.0, 0.0) def setup():     # we use a single array for the real values corresponding to the x coordinates     diff = coords - coords     xs = 0j + (coords + Numeric.arange(WIDTH).astype(Numeric.Float32) * diff / WIDTH )     # we use a single array for the imaginary values corresponding to the y coordinates     diff = coords - coords     ys = 1j * (coords + Numeric.arange(HEIGHT).astype(Numeric.Float32) * diff / HEIGHT )     # we build in direct correpondence with the pixels in the image     c = Numeric.add.outer(ys, xs)     z = Numeric.zeros((HEIGHT, WIDTH)).astype(Numeric.Complex32)     # use flattened representations for easier handling of array elements     c = Numeric.ravel(c)     z = Numeric.ravel(z)     return (c, z) def mandelbrot(progressMonitor):     import time     t = time.clock()     (c, z) = setup()     iterations = 0     size = WIDTH * HEIGHT     i_no = Numeric.arange(size)       # non-overflow indices     data = MAX_ITERATIONS + Numeric.zeros(size)     # initialize the "todo" arrays;     # they will contain just the spots where we still need to iterate     c_ = Numeric.array(c).astype(Numeric.Complex32)     z_ = Numeric.array(z).astype(Numeric.Complex32)     while (iterations < MAX_ITERATIONS) and len(i_no):         # do the calculations in-place         Numeric.multiply(z_, z_, z_)         Numeric.add(z_, c_, z_)         overflow = Numeric.greater_equal(abs(z_), 2.0)         not_overflow = Numeric.logical_not(overflow)         # get the indices where overflow occured         ####overflowIndices = Numeric.compress(overflow, i_no) # slower         overflowIndices = Numeric.repeat(i_no, overflow) # faster         # set the pixel indices there         for idx in overflowIndices:             data[idx] = iterations         # compute the new array of non-overflow indices         i_no = Numeric.repeat(i_no, not_overflow)         # update the todo arrays         c_ = Numeric.repeat(c_, not_overflow)         z_ = Numeric.repeat(z_, not_overflow)         iterations = iterations + 1         progressMonitor.progress(iterations, 100.0 * len(i_no) / size)     print time.clock() - t     return data class MandelCanvas(wxWindow):     def __init__(self, parent, id = -1):         wx.wxWindow.__init__(self, parent, id)         self.parent = parent         self.border = (1,1)         self.SetSize(wxSize(WIDTH, HEIGHT))         self.SetBackgroundColour(wx.wxNamedColour("black"))         self.bitmap = None         self.colours = Numeric.zeros( (MAX_ITERATIONS + 1, 3) )         arangeMax = Numeric.arange(0, MAX_ITERATIONS + 1)         self.colours[:,0] = Numeric.clip(arangeMax * WEIGHTS, 0, MAX_ITERATIONS)         self.colours[:,1] = Numeric.clip(arangeMax * WEIGHTS, 0, MAX_ITERATIONS)         self.colours[:,2] = Numeric.clip(arangeMax * WEIGHTS, 0, MAX_ITERATIONS)     def OnPaint(self, event):         if not self.bitmap:             data = mandelbrot(self.parent)             import time             t = time.clock()             data.shape = (HEIGHT, WIDTH)             # build the pixel values             pixels = Numeric.take(self.colours, data)             # create the image data             self.bitmap = pixels.astype(Numeric.UnsignedInt8).tostring()             # create the image itself             image = wxEmptyImage(WIDTH, HEIGHT)             image.SetData(self.bitmap)             self.bitmap = image.ConvertToBitmap()             print time.clock() - t         dc = wxPaintDC(self)         dc.BeginDrawing()         dc.DrawBitmap(self.bitmap, 0, 0, false)         dc.EndDrawing() class MyFrame(wxFrame):     def __init__(self, parent, ID, title):         wxFrame.__init__(self, parent, ID, title)         self.CreateStatusBar()         self.progress(0, 100)         self.Centre(wxBOTH)         mdb = MandelCanvas(self)         self.SetAutoLayout(true)         self.Layout()         self.Fit()         sz = self.GetClientSize()         self.SetClientSize(wxSize(sz.width-7, sz.height-14))     def progress(self, done, percent):         self.SetStatusText("%d/%d, %2.2f" % (done, MAX_ITERATIONS, percent) +                            "% of pixels left") class MyApp(wxApp):     def OnInit(self):         frame = MyFrame(NULL, -1, "Mandelbrot")         frame.Show(true)         self.SetTopWindow(frame)         return true app = MyApp(0) app.MainLoop() _______________________________________________ wxPython-users maillist  -  [hidden email] http://starship.python.net/mailman/listinfo/wxpython-users
Open this post in threaded view
|

## RE: [wxPython] new mandelbrot version

 Oh, fine, I'll post here :-P ;) , to justify myself I made changes which do have something to do with the GUI part :) --> this version uses threading module to do calculation, is slower than the non-threaded version, but does allow for GUI updates during calculation.  Also adds tiling display (i.e. you watch the solution "grow" on-screen in little pieces), and eliminates the global variables.  Still all sorts of rough edges :) . Cheers, Mike -----Original Message----- From: Markus Gritsch To: wxPython-users list Sent: 02/12/99 3:55 AM Subject: [wxPython] new mandelbrot version Hi! The calculation time is now further reduced by 30%.  I found, that Mike put some redundant stuff in the mandelbrot function.  Although Mike used a wxTimer, the application isn't responsive during calculation, so I didn't include this approach. I will continue posting the mandelbrot program to this mailing list, because 1) The mandelbrot program was born here, 2) Some interested people read this mailing list (Ionel, Mike, ...) 3) I find it more interesting to do mandelbrot calculations when the output is shown on the screen 4) There was no response to Mikes posting on comp.lang.python (maybe because of the high traffic there). --- Have fun, Markus ... mandelbrot3.py (8K) Download Attachment