Revision: 5786
http://matplotlib.svn.sourceforge.net/matplotlib/?rev=5786&view=rev
Author: dmkaplan
Date: 2008-07-18 08:43:03 +0000 (Fri, 18 Jul 2008)
Log Message:
-----------
Making a number of changes related to "blocking" stuff:
1) Adding to cbook.py a method is_sequence_of_strings that is then used in
BlockingInput to test for a tuple-like sequence of event names
2) Modified the use of *fmt* in clabel so that it an also be a
dictionary matching contour levels to arbitrary strings.
3) Removing the extraneous np.array or np.asarray commands in ContourLabeler
as they were forcing linecontour to array, but linecontour should already
be an array.
4) In blocking_input.py replacing all print commands with calls to
matplotlib.verbose.report
5) Removing extra cleanup call from BlockingInput as finally is always
executed, regardless of exception status.
6) Removing what appears to be a "patch" command screwup - there were two
versions of several of the Blocking* classes in blocking_input.py
Modified Paths:
--------------
trunk/matplotlib/lib/matplotlib/blocking_input.py
trunk/matplotlib/lib/matplotlib/cbook.py
trunk/matplotlib/lib/matplotlib/contour.py
trunk/matplotlib/lib/matplotlib/figure.py
Modified: trunk/matplotlib/lib/matplotlib/blocking_input.py
===================================================================
--- trunk/matplotlib/lib/matplotlib/blocking_input.py 2008-07-17 21:06:17 UTC
(rev 5785)
+++ trunk/matplotlib/lib/matplotlib/blocking_input.py 2008-07-18 08:43:03 UTC
(rev 5786)
@@ -19,7 +19,8 @@
import time
import numpy as np
-import matplotlib.path as path
+from matplotlib import path, verbose
+from cbook import is_sequence_of_strings
class BlockingInput(object):
"""
@@ -28,7 +29,7 @@
"""
def __init__(self, fig, eventslist=()):
self.fig = fig
- assert isinstance(eventslist, tuple), "Requires a tuple of event name
strings"
+ assert is_sequence_of_strings(eventslist), "Requires a sequence of
event name strings"
self.eventslist = eventslist
def on_event(self, event):
@@ -41,8 +42,7 @@
# subclasses
self.add_event(event)
- if self.verbose:
- print "Event %i" % len(self.events)
+ verbose.report("Event %i" % len(self.events))
# This will extract info from events
self.post_event()
@@ -80,7 +80,7 @@
self.pop_event(index)
pop.__doc__=pop_event.__doc__
- def __call__(self, n=1, timeout=30, verbose=False ):
+ def __call__(self, n=1, timeout=30 ):
"""
Blocking call to retrieve n events
"""
@@ -90,7 +90,6 @@
self.events = []
self.done = False
- self.verbose = verbose
self.callbacks = []
# Ensure that the figure is shown
@@ -112,12 +111,10 @@
if timeout > 0 and counter > timeout/0.01:
print "Timeout reached";
break;
- finally: # Activated on exception like ctrl-c
+ finally: # Run even on exception like ctrl-c
+ # Disconnect the callbacks
self.cleanup()
- # Disconnect the callbacks
- self.cleanup()
-
# Return the events in this case
return self.events
@@ -196,10 +193,10 @@
This add the coordinates of an event to the list of clicks
"""
self.clicks.append((event.xdata,event.ydata))
- if self.verbose:
- print "input %i: %f,%f" % (len(self.clicks),
- event.xdata, event.ydata)
+ verbose.report("input %i: %f,%f" %
+ (len(self.clicks),event.xdata, event.ydata))
+
# If desired plot up click
if self.show_clicks:
self.marks.extend(
@@ -238,7 +235,7 @@
# Call base class to remove callbacks
BlockingInput.cleanup(self)
- def __call__(self, n=1, timeout=30, verbose=False, show_clicks=True):
+ def __call__(self, n=1, timeout=30, show_clicks=True):
"""
Blocking call to retrieve n coordinate pairs through mouse
clicks.
@@ -246,7 +243,7 @@
self.show_clicks = show_clicks
self.clicks = []
self.marks = []
- BlockingInput.__call__(self,n=n,timeout=timeout,verbose=verbose)
+ BlockingInput.__call__(self,n=n,timeout=timeout)
return self.clicks
@@ -324,7 +321,7 @@
def __call__(self,inline,n=-1,timeout=-1):
self.inline=inline
- BlockingMouseInput.__call__(self,n=n,timeout=timeout,verbose=False,
+ BlockingMouseInput.__call__(self,n=n,timeout=timeout,
show_clicks=False)
class BlockingKeyMouseInput(BlockingInput):
@@ -343,198 +340,13 @@
self.keyormouse = self.events[-1].name == 'key_press_event'
- def __call__(self, timeout=30, verbose=False):
+ def __call__(self, timeout=30):
"""
Blocking call to retrieve a single mouse or key click
Returns True if key click, False if mouse, or None if timeout
"""
self.keyormouse = None
- BlockingInput.__call__(self,n=1,timeout=timeout,verbose=verbose)
+ BlockingInput.__call__(self,n=1,timeout=timeout)
return self.keyormouse
-"""
-This provides several classes used for interaction with figure windows:
-
-:class:`BlockingInput`
- creates a callable object to retrieve events in a blocking way for
interactive sessions
-
-:class:`BlockingKeyMouseInput`
- creates a callable object to retrieve key or mouse clicks in a blocking
way for interactive sessions.
- Note: Subclass of BlockingInput. Used by waitforbuttonpress
-
-:class:`BlockingMouseInput`
- creates a callable object to retrieve mouse clicks in a blocking way for
interactive sessions.
- Note: Subclass of BlockingInput. Used by ginput
-"""
-
-import time
-
-class BlockingInput(object):
- """
- Class that creates a callable object to retrieve events in a
- blocking way.
- """
- def __init__(self, fig, eventslist=()):
- self.fig = fig
- assert isinstance(eventslist, tuple), \
- "Requires a tuple of event name strings"
- self.eventslist = eventslist
-
- def on_event(self, event):
- """
- Event handler that will be passed to the current figure to
- retrieve events.
- """
- self.events.append(event)
-
- if self.verbose:
- print "Event %i" % len(self.events)
-
- # This will extract info from events
- self.post_event()
-
- if len(self.events) >= self.n and self.n > 0:
- self.done = True
-
- def post_event(self):
- """For baseclass, do nothing but collect events"""
- pass
-
- def cleanup(self):
- """Remove callbacks"""
- for cb in self.callbacks:
- self.fig.canvas.mpl_disconnect(cb)
-
- self.callbacks=[]
-
- def __call__(self, n=1, timeout=30, verbose=False ):
- """
- Blocking call to retrieve n events
- """
-
- assert isinstance(n, int), "Requires an integer argument"
- self.n = n
-
- self.events = []
- self.done = False
- self.verbose = verbose
- self.callbacks = []
-
- # Ensure that the figure is shown
- self.fig.show()
-
- # connect the events to the on_event function call
- for n in self.eventslist:
- self.callbacks.append( self.fig.canvas.mpl_connect(n,
self.on_event) )
-
- try:
- # wait for n clicks
- counter = 0
- while not self.done:
- self.fig.canvas.flush_events()
- time.sleep(0.01)
-
- # check for a timeout
- counter += 1
- if timeout > 0 and counter > timeout/0.01:
- print "Timeout reached";
- break;
- finally: # Activated on exception like ctrl-c
- self.cleanup()
-
- # Disconnect the callbacks
- self.cleanup()
-
- # Return the events in this case
- return self.events
-
-class BlockingMouseInput(BlockingInput):
- """
- Class that creates a callable object to retrieve mouse clicks in a
- blocking way.
- """
- def __init__(self, fig):
- BlockingInput.__init__(self, fig=fig,
eventslist=('button_press_event',) )
-
- def post_event(self):
- """
- This will be called to process events
- """
- assert len(self.events)>0, "No events yet"
-
- event = self.events[-1]
-
- if event.button == 3:
- # If it's a right click, pop the last coordinates.
- if len(self.clicks) > 0:
- self.clicks.pop()
- del self.events[-2:] # Remove button=3 event and previous event
-
- if self.show_clicks:
- mark = self.marks.pop()
- mark.remove()
- self.fig.canvas.draw()
- elif event.button == 2 and self.n < 0:
- # If it's a middle click, and we are in infinite mode, finish
- self.done = True
- elif event.inaxes:
- # If it's a valid click, append the coordinates to the list
- self.clicks.append((event.xdata, event.ydata))
- if self.verbose:
- print "input %i: %f,%f" % (len(self.clicks),
- event.xdata, event.ydata)
- if self.show_clicks:
- self.marks.extend(
- event.inaxes.plot([event.xdata,], [event.ydata,], 'r+') )
- self.fig.canvas.draw()
-
- def cleanup(self):
- # clean the figure
- if self.show_clicks:
- for mark in self.marks:
- mark.remove()
- self.marks = []
- self.fig.canvas.draw()
-
- # Call base class to remove callbacks
- BlockingInput.cleanup(self)
-
- def __call__(self, n=1, timeout=30, verbose=False, show_clicks=True):
- """
- Blocking call to retrieve n coordinate pairs through mouse
- clicks.
- """
- self.show_clicks = show_clicks
- self.clicks = []
- self.marks = []
- BlockingInput.__call__(self,n=n,timeout=timeout,verbose=verbose)
-
- return self.clicks
-
-class BlockingKeyMouseInput(BlockingInput):
- """
- Class that creates a callable object to retrieve a single mouse or
- keyboard click
- """
- def __init__(self, fig):
- BlockingInput.__init__(self, fig=fig,
eventslist=('button_press_event','key_press_event') )
-
- def post_event(self):
- """
- Determines if it is a key event
- """
- assert len(self.events)>0, "No events yet"
-
- self.keyormouse = self.events[-1].name == 'key_press_event'
-
- def __call__(self, timeout=30, verbose=False):
- """
- Blocking call to retrieve a single mouse or key click
- Returns True if key click, False if mouse, or None if timeout
- """
- self.keyormouse = None
- BlockingInput.__call__(self,n=1,timeout=timeout,verbose=verbose)
-
- return self.keyormouse
-
Modified: trunk/matplotlib/lib/matplotlib/cbook.py
===================================================================
--- trunk/matplotlib/lib/matplotlib/cbook.py 2008-07-17 21:06:17 UTC (rev
5785)
+++ trunk/matplotlib/lib/matplotlib/cbook.py 2008-07-18 08:43:03 UTC (rev
5786)
@@ -270,6 +270,15 @@
except (TypeError, ValueError): return 0
return 1
+def is_sequence_of_strings(obj):
+ """
+ Returns true if *obj* is iterable and contains strings
+ """
+ if not iterable(obj): return False
+ for o in obj:
+ if not is_string_like(o): return False
+ return True
+
def is_writable_file_like(obj):
'return true if *obj* looks like a file object with a *write* method'
return hasattr(obj, 'write') and callable(obj.write)
Modified: trunk/matplotlib/lib/matplotlib/contour.py
===================================================================
--- trunk/matplotlib/lib/matplotlib/contour.py 2008-07-17 21:06:17 UTC (rev
5785)
+++ trunk/matplotlib/lib/matplotlib/contour.py 2008-07-18 08:43:03 UTC (rev
5786)
@@ -71,6 +71,9 @@
*fmt*:
a format string for the label. Default is '%1.3f'
+ Alternatively, this can be a dictionary matching contour
+ levels with arbitrary strings to use for each contour level
+ (i.e., fmt[level]=string)
*manual*:
if *True*, contour labels will be placed manually using
@@ -158,10 +161,10 @@
if lcsize > 10 * labelwidth:
return 1
- xmax = np.amax(np.array(linecontour)[:,0])
- xmin = np.amin(np.array(linecontour)[:,0])
- ymax = np.amax(np.array(linecontour)[:,1])
- ymin = np.amin(np.array(linecontour)[:,1])
+ xmax = np.amax(linecontour[:,0])
+ xmin = np.amin(linecontour[:,0])
+ ymax = np.amax(linecontour[:,1])
+ ymin = np.amin(linecontour[:,1])
lw = labelwidth
if (xmax - xmin) > 1.2* lw or (ymax - ymin) > 1.2 * lw:
@@ -210,7 +213,7 @@
if cbook.is_string_like(lev):
lw = (len(lev)) * fsize
else:
- lw = (len(fmt%lev)) * fsize
+ lw = (len(self.get_text(lev,fmt))) * fsize
return lw
@@ -227,9 +230,11 @@
if cbook.is_string_like(lev):
return lev
else:
- return fmt%lev
+ if isinstance(fmt,dict):
+ return fmt[lev]
+ else:
+ return fmt%lev
-
def break_linecontour(self, linecontour, rot, labelwidth, ind):
"break a contour in two contours at the location of the label"
lcsize = len(linecontour)
@@ -243,8 +248,8 @@
slc = trans.transform(linecontour)
x,y = slc[ind]
- xx= np.asarray(slc)[:,0].copy()
- yy=np.asarray(slc)[:,1].copy()
+ xx=slc[:,0].copy()
+ yy=slc[:,1].copy()
#indices which are under the label
inds, = np.nonzero(((xx < x+xlabel) & (xx > x-xlabel)) &
@@ -325,8 +330,8 @@
else:
ysize = labelwidth
- XX = np.resize(np.asarray(linecontour)[:,0],(xsize, ysize))
- YY = np.resize(np.asarray(linecontour)[:,1],(xsize, ysize))
+ XX = np.resize(linecontour[:,0],(xsize, ysize))
+ YY = np.resize(linecontour[:,1],(xsize, ysize))
#I might have fouled up the following:
yfirst = YY[:,0].reshape(xsize, 1)
ylast = YY[:,-1].reshape(xsize, 1)
Modified: trunk/matplotlib/lib/matplotlib/figure.py
===================================================================
--- trunk/matplotlib/lib/matplotlib/figure.py 2008-07-17 21:06:17 UTC (rev
5785)
+++ trunk/matplotlib/lib/matplotlib/figure.py 2008-07-18 08:43:03 UTC (rev
5786)
@@ -1017,11 +1017,11 @@
ax.update_params()
ax.set_position(ax.figbox)
- def ginput(self, n=1, timeout=30, verbose=False, show_clicks=True):
+ def ginput(self, n=1, timeout=30, show_clicks=True):
"""
call signature::
- ginput(self, n=1, timeout=30, verbose=False, show_clicks=True)
+ ginput(self, n=1, timeout=30, show_clicks=True)
Blocking call to interact with the figure.
@@ -1038,7 +1038,7 @@
blocking_mouse_input = BlockingMouseInput(self)
return blocking_mouse_input(n=n, timeout=timeout,
- verbose=verbose,
show_clicks=show_clicks)
+ show_clicks=show_clicks)
def waitforbuttonpress(self, timeout=-1):
"""
This was sent by the SourceForge.net collaborative development platform, the
world's largest Open Source development site.
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
_______________________________________________
Matplotlib-checkins mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/matplotlib-checkins