@@ -12,16 +12,58 @@ def __call__(self, ax):
1212 self .set_bounds (* ax .viewLim .bounds )
1313 ax .figure .canvas .draw_idle ()
1414
15- x = np .linspace (- 3. , 3. , 20 )
16- y = np .linspace (- 3. , 3. , 20 ).reshape (- 1 ,1 )
17- Z = (1 - x / 2 + x ** 5 + y ** 3 )* np .exp (- x ** 2 - y ** 2 )
15+ # A class that will regenerate a fractal set as we zoom in, so that you
16+ # can actually see the increasing detail. A box in the left panel will show
17+ # the area to which we are zoomed.
18+ class MandlebrotDisplay (object ):
19+ def __init__ (self , h = 500 , w = 500 , niter = 50 , radius = 2. , power = 2 ):
20+ self .height = h
21+ self .width = w
22+ self .niter = niter
23+ self .radius = radius
24+ self .power = power
25+
26+ def __call__ (self , xstart , xend , ystart , yend ):
27+ self .x = np .linspace (xstart , xend , self .width )
28+ self .y = np .linspace (ystart , yend , self .height ).reshape (- 1 ,1 )
29+ c = self .x + 1.0j * self .y
30+ threshold_time = np .zeros ((self .height , self .width ))
31+ z = np .zeros (threshold_time .shape , dtype = np .complex )
32+ mask = np .ones (threshold_time .shape , dtype = np .bool )
33+ for i in xrange (self .niter ):
34+ z [mask ] = z [mask ]** self .power + c [mask ]
35+ mask = (np .abs (z ) < self .radius )
36+ threshold_time += mask
37+ return threshold_time
38+
39+ def ax_update (self , ax ):
40+ ax .set_autoscale_on (False ) # Otherwise, infinite loop
41+
42+ #Get the number of points from the number of pixels in the window
43+ dims = ax .axesFrame .get_window_extent ().bounds
44+ self .width = int (dims [2 ] + 0.5 )
45+ self .height = int (dims [2 ] + 0.5 )
46+
47+ #Get the range for the new area
48+ xstart ,ystart ,xdelta ,ydelta = ax .viewLim .bounds
49+ xend = xstart + xdelta
50+ yend = ystart + ydelta
51+
52+ # Update the image object with our new data and extent
53+ im = ax .images [- 1 ]
54+ im .set_data (self .__call__ (xstart , xend , ystart , yend ))
55+ im .set_extent ((xstart , xend , ystart , yend ))
56+ ax .figure .canvas .draw_idle ()
57+
58+ md = MandlebrotDisplay ()
59+ Z = md (- 2. , 0.5 , - 1.25 , 1.25 )
1860
1961fig = plt .figure ()
2062ax1 = fig .add_subplot (1 , 2 , 1 )
21- ax1 .pcolor ( x , y , Z )
63+ ax1 .imshow ( Z , origin = 'lower' , extent = ( md . x . min (), md . x . max (), md . y . min (), md . y . max ()) )
2264
2365ax2 = fig .add_subplot (1 , 2 , 2 )
24- ax2 .pcolor ( x , y , Z )
66+ ax2 .imshow ( Z , origin = 'lower' , extent = ( md . x . min (), md . x . max (), md . y . min (), md . y . max ()) )
2567
2668rect = UpdatingRect ([0 , 0 ], 0 , 0 , facecolor = 'None' , edgecolor = 'black' )
2769rect .set_bounds (* ax2 .viewLim .bounds )
@@ -31,4 +73,7 @@ def __call__(self, ax):
3173ax2 .callbacks .connect ('xlim_changed' , rect )
3274ax2 .callbacks .connect ('ylim_changed' , rect )
3375
76+ ax2 .callbacks .connect ('xlim_changed' , md .ax_update )
77+ ax2 .callbacks .connect ('ylim_changed' , md .ax_update )
78+
3479plt .show ()
0 commit comments