You can subscribe to this list here.
2007 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
(115) |
Aug
(120) |
Sep
(137) |
Oct
(170) |
Nov
(461) |
Dec
(263) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2008 |
Jan
(120) |
Feb
(74) |
Mar
(35) |
Apr
(74) |
May
(245) |
Jun
(356) |
Jul
(240) |
Aug
(115) |
Sep
(78) |
Oct
(225) |
Nov
(98) |
Dec
(271) |
2009 |
Jan
(132) |
Feb
(84) |
Mar
(74) |
Apr
(56) |
May
(90) |
Jun
(79) |
Jul
(83) |
Aug
(296) |
Sep
(214) |
Oct
(76) |
Nov
(82) |
Dec
(66) |
2010 |
Jan
(46) |
Feb
(58) |
Mar
(51) |
Apr
(77) |
May
(58) |
Jun
(126) |
Jul
(128) |
Aug
(64) |
Sep
(50) |
Oct
(44) |
Nov
(48) |
Dec
(54) |
2011 |
Jan
(68) |
Feb
(52) |
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
(1) |
2018 |
Jan
|
Feb
|
Mar
|
Apr
|
May
(1) |
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
S | M | T | W | T | F | S |
---|---|---|---|---|---|---|
|
|
|
|
|
1
|
2
(4) |
3
(2) |
4
(9) |
5
|
6
|
7
|
8
|
9
|
10
|
11
(6) |
12
|
13
|
14
|
15
|
16
(10) |
17
(1) |
18
|
19
(1) |
20
|
21
|
22
(3) |
23
|
24
|
25
(2) |
26
|
27
|
28
(3) |
29
(5) |
30
|
31
|
|
|
|
|
|
|
Revision: 8105 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8105&view=rev Author: leejjoon Date: 2010年01月29日 18:03:13 +0000 (2010年1月29日) Log Message: ----------- draggable legend now optionally blitted Modified Paths: -------------- trunk/matplotlib/examples/animation/draggable_legend.py trunk/matplotlib/lib/matplotlib/legend.py trunk/matplotlib/lib/matplotlib/offsetbox.py trunk/matplotlib/lib/matplotlib/text.py Modified: trunk/matplotlib/examples/animation/draggable_legend.py =================================================================== --- trunk/matplotlib/examples/animation/draggable_legend.py 2010年01月29日 17:33:34 UTC (rev 8104) +++ trunk/matplotlib/examples/animation/draggable_legend.py 2010年01月29日 18:03:13 UTC (rev 8105) @@ -37,7 +37,7 @@ ax.add_artist(ab) -d3 = ab.draggable() +d3 = ab.draggable(use_blit=True) plt.show() Modified: trunk/matplotlib/lib/matplotlib/legend.py =================================================================== --- trunk/matplotlib/lib/matplotlib/legend.py 2010年01月29日 17:33:34 UTC (rev 8104) +++ trunk/matplotlib/lib/matplotlib/legend.py 2010年01月29日 18:03:13 UTC (rev 8105) @@ -39,9 +39,10 @@ class DraggableLegend(DraggableOffsetBox): - def __init__(self, legend): + def __init__(self, legend, use_blit=False): self.legend=legend - DraggableOffsetBox.__init__(self, legend, legend._legend_box) + DraggableOffsetBox.__init__(self, legend, legend._legend_box, + use_blit=use_blit) def artist_picker(self, legend, evt): return self.legend.legendPatch.contains(evt) @@ -917,7 +918,7 @@ return ox, oy - def draggable(self, state=None): + def draggable(self, state=None, use_blit=False): """ Set the draggable state -- if state is @@ -939,7 +940,7 @@ if state: if self._draggable is None: - self._draggable = DraggableLegend(self) + self._draggable = DraggableLegend(self, use_blit) else: if self._draggable is not None: self._draggable.disconnect() Modified: trunk/matplotlib/lib/matplotlib/offsetbox.py =================================================================== --- trunk/matplotlib/lib/matplotlib/offsetbox.py 2010年01月29日 17:33:34 UTC (rev 8104) +++ trunk/matplotlib/lib/matplotlib/offsetbox.py 2010年01月29日 18:03:13 UTC (rev 8105) @@ -1416,10 +1416,11 @@ the normalized axes coordinate and set a relavant attribute. """ - def __init__(self, ref_artist): + def __init__(self, ref_artist, use_blit=False): self.ref_artist = ref_artist self.got_artist = False - + self._use_blit = use_blit + self.canvas = self.ref_artist.figure.canvas c2 = self.canvas.mpl_connect('pick_event', self.on_pick) c3 = self.canvas.mpl_connect('button_release_event', self.on_release) @@ -1432,16 +1433,34 @@ dx = evt.x - self.mouse_x dy = evt.y - self.mouse_y self.update_offset(dx, dy) + self.canvas.draw() + def on_motion_blit(self, evt): + if self.got_artist: + dx = evt.x - self.mouse_x + dy = evt.y - self.mouse_y + self.update_offset(dx, dy) + self.canvas.restore_region(self.background) + self.ref_artist.draw(self.ref_artist.figure._cachedRenderer) + self.canvas.blit(self.ref_artist.figure.bbox) + def on_pick(self, evt): if evt.artist == self.ref_artist: - self.save_offset() self.mouse_x = evt.mouseevent.x self.mouse_y = evt.mouseevent.y self.got_artist = True - self._c1 = self.canvas.mpl_connect('motion_notify_event', self.on_motion) + if self._use_blit: + self.ref_artist.set_animated(True) + self.canvas.draw() + self.background = self.canvas.copy_from_bbox(self.ref_artist.figure.bbox) + self.ref_artist.draw(self.ref_artist.figure._cachedRenderer) + self.canvas.blit(self.ref_artist.figure.bbox) + self._c1 = self.canvas.mpl_connect('motion_notify_event', self.on_motion_blit) + else: + self._c1 = self.canvas.mpl_connect('motion_notify_event', self.on_motion) + self.save_offset() def on_release(self, event): if self.got_artist: @@ -1449,6 +1468,9 @@ self.got_artist = False self.canvas.mpl_disconnect(self._c1) + if self._use_blit: + self.ref_artist.set_animated(False) + def disconnect(self): 'disconnect the callbacks' for cid in self.cids: @@ -1468,8 +1490,8 @@ class DraggableOffsetBox(DraggableBase): - def __init__(self, ref_artist, offsetbox): - DraggableBase.__init__(self, ref_artist) + def __init__(self, ref_artist, offsetbox, use_blit=False): + DraggableBase.__init__(self, ref_artist, use_blit=use_blit) self.offsetbox = offsetbox def save_offset(self): @@ -1482,7 +1504,6 @@ def update_offset(self, dx, dy): loc_in_canvas = self.offsetbox_x + dx, self.offsetbox_y + dy self.offsetbox.set_offset(loc_in_canvas) - self.offsetbox.figure.canvas.draw() def get_loc_in_canvas(self): @@ -1496,8 +1517,8 @@ class DraggableAnnotation(DraggableBase): - def __init__(self, annotation): - DraggableBase.__init__(self, annotation) + def __init__(self, annotation, use_blit=False): + DraggableBase.__init__(self, annotation, use_blit=use_blit) self.annotation = annotation def save_offset(self): @@ -1519,7 +1540,6 @@ ann.xytext = self.ox + dx, self.oy + dy x, y = ann.xytext xy = ann._get_xy(x, y, ann.textcoords) - self.canvas.draw() def finalize_offset(self): loc_in_canvas = self.annotation.xytext Modified: trunk/matplotlib/lib/matplotlib/text.py =================================================================== --- trunk/matplotlib/lib/matplotlib/text.py 2010年01月29日 17:33:34 UTC (rev 8104) +++ trunk/matplotlib/lib/matplotlib/text.py 2010年01月29日 18:03:13 UTC (rev 8105) @@ -1537,7 +1537,7 @@ return True - def draggable(self, state=None): + def draggable(self, state=None, use_blit=False): """ Set the draggable state -- if state is @@ -1560,7 +1560,7 @@ if state: if self._draggable is None: - self._draggable = DraggableAnnotation(self) + self._draggable = DraggableAnnotation(self, use_blit) else: if self._draggable is not None: self._draggable.disconnect() This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8104 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8104&view=rev Author: leejjoon Date: 2010年01月29日 17:33:34 +0000 (2010年1月29日) Log Message: ----------- fix axes_grid for offsetbox api change Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/offsetbox.py trunk/matplotlib/lib/mpl_toolkits/axes_grid/inset_locator.py Modified: trunk/matplotlib/lib/matplotlib/offsetbox.py =================================================================== --- trunk/matplotlib/lib/matplotlib/offsetbox.py 2010年01月29日 17:33:21 UTC (rev 8103) +++ trunk/matplotlib/lib/matplotlib/offsetbox.py 2010年01月29日 17:33:34 UTC (rev 8104) @@ -958,7 +958,7 @@ if fontsize is None: fontsize = renderer.points_to_pixels(self.prop.get_size_in_points()) - def _offset(w, h, xd, yd, fontsize=fontsize, self=self): + def _offset(w, h, xd, yd, renderer, fontsize=fontsize, self=self): bbox = Bbox.from_bounds(0, 0, w, h) borderpad = self.borderpad*fontsize bbox_to_anchor = self.get_bbox_to_anchor() Modified: trunk/matplotlib/lib/mpl_toolkits/axes_grid/inset_locator.py =================================================================== --- trunk/matplotlib/lib/mpl_toolkits/axes_grid/inset_locator.py 2010年01月29日 17:33:21 UTC (rev 8103) +++ trunk/matplotlib/lib/mpl_toolkits/axes_grid/inset_locator.py 2010年01月29日 17:33:34 UTC (rev 8104) @@ -47,7 +47,7 @@ width, height, xdescent, ydescent = self.get_extent(renderer) - px, py = self.get_offset(width, height, 0, 0) + px, py = self.get_offset(width, height, 0, 0, renderer) bbox_canvas = mtrans.Bbox.from_bounds(px, py, width, height) tr = ax.figure.transFigure.inverted() bb = mtrans.TransformedBbox(bbox_canvas, tr) This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8103 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8103&view=rev Author: leejjoon Date: 2010年01月29日 17:33:21 +0000 (2010年1月29日) Log Message: ----------- refactor draggable legend to support annotation Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/legend.py trunk/matplotlib/lib/matplotlib/offsetbox.py trunk/matplotlib/lib/matplotlib/text.py Added Paths: ----------- trunk/matplotlib/examples/animation/draggable_legend.py Added: trunk/matplotlib/examples/animation/draggable_legend.py =================================================================== --- trunk/matplotlib/examples/animation/draggable_legend.py (rev 0) +++ trunk/matplotlib/examples/animation/draggable_legend.py 2010年01月29日 17:33:21 UTC (rev 8103) @@ -0,0 +1,43 @@ +import matplotlib.pyplot as plt + + +ax = plt.subplot(111) +ax.plot([1,2,3], label="test") + +l = ax.legend() +d1 = l.draggable() + +xy = 1, 2 +txt = ax.annotate("Test", xy, xytext=(-30, 30), + textcoords="offset points", + bbox=dict(boxstyle="round",fc=(0.2, 1, 1)), + arrowprops=dict(arrowstyle="->")) +d2 = txt.draggable() + + +from matplotlib._png import read_png +from matplotlib.cbook import get_sample_data + +from matplotlib.offsetbox import OffsetImage, AnnotationBbox + +fn = get_sample_data("lena.png", asfileobj=False) +arr_lena = read_png(fn) + +imagebox = OffsetImage(arr_lena, zoom=0.2) + +ab = AnnotationBbox(imagebox, xy, + xybox=(120., -80.), + xycoords='data', + boxcoords="offset points", + pad=0.5, + arrowprops=dict(arrowstyle="->", + connectionstyle="angle,angleA=0,angleB=90,rad=3") + ) + + +ax.add_artist(ab) + +d3 = ab.draggable() + + +plt.show() Modified: trunk/matplotlib/lib/matplotlib/legend.py =================================================================== --- trunk/matplotlib/lib/matplotlib/legend.py 2010年01月29日 16:22:51 UTC (rev 8102) +++ trunk/matplotlib/lib/matplotlib/legend.py 2010年01月29日 17:33:21 UTC (rev 8103) @@ -33,56 +33,28 @@ from matplotlib.patches import Patch, Rectangle, Shadow, FancyBboxPatch from matplotlib.collections import LineCollection, RegularPolyCollection, \ CircleCollection -from matplotlib.transforms import Bbox, BboxBase, TransformedBbox, BboxTransformTo +from matplotlib.transforms import Bbox, BboxBase, TransformedBbox, BboxTransformTo, BboxTransformFrom -from matplotlib.offsetbox import HPacker, VPacker, TextArea, DrawingArea +from matplotlib.offsetbox import HPacker, VPacker, TextArea, DrawingArea, DraggableOffsetBox -class DraggableLegend: - """helper code for a draggable legend -- see Legend.draggable""" - +class DraggableLegend(DraggableOffsetBox): def __init__(self, legend): - self.legend = legend - self.gotLegend = False + self.legend=legend + DraggableOffsetBox.__init__(self, legend, legend._legend_box) - c1 = legend.figure.canvas.mpl_connect('motion_notify_event', self.on_motion) - c2 = legend.figure.canvas.mpl_connect('pick_event', self.on_pick) - c3 = legend.figure.canvas.mpl_connect('button_release_event', self.on_release) - legend.set_picker(self.my_legend_picker) - self.cids = [c1, c2, c3] - - def on_motion(self, evt): - if self.gotLegend: - dx = evt.x - self.mouse_x - dy = evt.y - self.mouse_y - loc_in_canvas = self.legend_x + dx, self.legend_y + dy - loc_in_norm_axes = self.legend.parent.transAxes.inverted().transform_point(loc_in_canvas) - self.legend._loc = tuple(loc_in_norm_axes) - self.legend.figure.canvas.draw() - - def my_legend_picker(self, legend, evt): + def artist_picker(self, legend, evt): return self.legend.legendPatch.contains(evt) - def on_pick(self, evt): - legend = self.legend - if evt.artist == legend: - bbox = self.legend.get_window_extent() - self.mouse_x = evt.mouseevent.x - self.mouse_y = evt.mouseevent.y - self.legend_x = bbox.xmin - self.legend_y = bbox.ymin - self.gotLegend = 1 + def finalize_offset(self): + loc_in_canvas = self.get_loc_in_canvas() - def on_release(self, event): - if self.gotLegend: - self.gotLegend = False + bbox = self.legend.get_bbox_to_anchor() + _bbox_transform = BboxTransformFrom(bbox) + self.legend._loc = tuple(_bbox_transform.transform_point(loc_in_canvas)) + - def disconnect(self): - 'disconnect the callbacks' - for cid in self.cids: - self.legend.figure.canvas.mpl_disconnect(cid) - class Legend(Artist): """ Place a legend on the axes at location loc. Labels are a @@ -323,7 +295,6 @@ 'Falling back on "upper right".') loc = 1 - self._loc = loc self._mode = mode self.set_bbox_to_anchor(bbox_to_anchor, bbox_transform) @@ -357,6 +328,8 @@ # init with null renderer self._init_legend_box(handles, labels) + self._loc = loc + self.set_title(title) self._last_fontsize_points = self._fontsize @@ -373,6 +346,28 @@ a.set_transform(self.get_transform()) + def _set_loc(self, loc): + # find_offset function will be provided to _legend_box and + # _legend_box will draw itself at the location of the return + # value of the find_offset. + self._loc_real = loc + if loc == 0: + _findoffset = self._findoffset_best + else: + _findoffset = self._findoffset_loc + + #def findoffset(width, height, xdescent, ydescent): + # return _findoffset(width, height, xdescent, ydescent, renderer) + + self._legend_box.set_offset(_findoffset) + + self._loc_real = loc + + def _get_loc(self): + return self._loc_real + + _loc = property(_get_loc, _set_loc) + def _findoffset_best(self, width, height, xdescent, ydescent, renderer): "Helper function to locate the legend at its best position" ox, oy = self._find_best_position(width, height, renderer) @@ -401,19 +396,6 @@ renderer.open_group('legend') - # find_offset function will be provided to _legend_box and - # _legend_box will draw itself at the location of the return - # value of the find_offset. - if self._loc == 0: - _findoffset = self._findoffset_best - else: - _findoffset = self._findoffset_loc - - def findoffset(width, height, xdescent, ydescent): - return _findoffset(width, height, xdescent, ydescent, renderer) - - self._legend_box.set_offset(findoffset) - fontsize = renderer.points_to_pixels(self._fontsize) # if mode == fill, set the width of the legend_box to the Modified: trunk/matplotlib/lib/matplotlib/offsetbox.py =================================================================== --- trunk/matplotlib/lib/matplotlib/offsetbox.py 2010年01月29日 16:22:51 UTC (rev 8102) +++ trunk/matplotlib/lib/matplotlib/offsetbox.py 2010年01月29日 17:33:21 UTC (rev 8103) @@ -20,7 +20,7 @@ import matplotlib.text as mtext import numpy as np from matplotlib.transforms import Bbox, BboxBase, TransformedBbox, \ - IdentityTransform + IdentityTransform, BboxTransformFrom from matplotlib.font_manager import FontProperties from matplotlib.patches import FancyBboxPatch, FancyArrowPatch @@ -168,14 +168,14 @@ """ self._offset = xy - def get_offset(self, width, height, xdescent, ydescent): + def get_offset(self, width, height, xdescent, ydescent, renderer): """ Get the offset accepts extent of the box """ if callable(self._offset): - return self._offset(width, height, xdescent, ydescent) + return self._offset(width, height, xdescent, ydescent, renderer) else: return self._offset @@ -222,7 +222,7 @@ get the bounding box in display space. ''' w, h, xd, yd, offsets = self.get_extent_offsets(renderer) - px, py = self.get_offset(w, h, xd, yd) + px, py = self.get_offset(w, h, xd, yd, renderer) return mtransforms.Bbox.from_bounds(px-xd, py-yd, w, h) def draw(self, renderer): @@ -233,7 +233,7 @@ width, height, xdescent, ydescent, offsets = self.get_extent_offsets(renderer) - px, py = self.get_offset(width, height, xdescent, ydescent) + px, py = self.get_offset(width, height, xdescent, ydescent, renderer) for c, (ox, oy) in zip(self.get_visible_children(), offsets): c.set_offset((px+ox, py+oy)) @@ -946,7 +946,7 @@ ''' self._update_offset_func(renderer) w, h, xd, yd = self.get_extent(renderer) - ox, oy = self.get_offset(w, h, xd, yd) + ox, oy = self.get_offset(w, h, xd, yd, renderer) return Bbox.from_bounds(ox-xd, oy-yd, w, h) @@ -996,7 +996,7 @@ width, height, xdescent, ydescent = self.get_extent(renderer) - px, py = self.get_offset(width, height, xdescent, ydescent) + px, py = self.get_offset(width, height, xdescent, ydescent, renderer) self.get_child().set_offset((px, py)) self.get_child().draw(renderer) @@ -1121,12 +1121,15 @@ # self.offset_transform.translate(xy[0], xy[1]) + def get_offset(self): """ return offset of the container. """ return self._offset + def get_children(self): + return [self.image] def get_window_extent(self, renderer): ''' @@ -1243,9 +1246,9 @@ def contains(self,event): t,tinfo = self.offsetbox.contains(event) - if self.arrow is not None: - a,ainfo=self.arrow.contains(event) - t = t or a + #if self.arrow_patch is not None: + # a,ainfo=self.arrow_patch.contains(event) + # t = t or a # self.arrow_patch is currently not checked as this can be a line - JJ @@ -1380,7 +1383,151 @@ +class DraggableBase(object): + """ + helper code for a draggable artist (legend, offsetbox) + The derived class must override following two method. + def saveoffset(self): + pass + + def update_offset(self, dx, dy): + pass + + *saveoffset* is called when the object is picked for dragging and it is + meant to save reference position of the artist. + + *update_offset* is called during the dragging. dx and dy is the pixel + offset from the point where the mouse drag started. + + Optionally you may override following two methods. + + def artist_picker(self, artist, evt): + return self.ref_artist.contains(evt) + + def finalize_offset(self): + pass + + *artist_picker* is a picker method that will be + used. *finalize_offset* is called when the mouse is released. In + current implementaion of DraggableLegend and DraggableAnnotation, + *update_offset* places the artists simply in display + coordinates. And *finalize_offset* recalculate their position in + the normalized axes coordinate and set a relavant attribute. + + """ + def __init__(self, ref_artist): + self.ref_artist = ref_artist + self.got_artist = False + + self.canvas = self.ref_artist.figure.canvas + c2 = self.canvas.mpl_connect('pick_event', self.on_pick) + c3 = self.canvas.mpl_connect('button_release_event', self.on_release) + + ref_artist.set_picker(self.artist_picker) + self.cids = [c2, c3] + + def on_motion(self, evt): + if self.got_artist: + dx = evt.x - self.mouse_x + dy = evt.y - self.mouse_y + self.update_offset(dx, dy) + + def on_pick(self, evt): + if evt.artist == self.ref_artist: + + self.save_offset() + self.mouse_x = evt.mouseevent.x + self.mouse_y = evt.mouseevent.y + self.got_artist = True + + self._c1 = self.canvas.mpl_connect('motion_notify_event', self.on_motion) + + def on_release(self, event): + if self.got_artist: + self.finalize_offset() + self.got_artist = False + self.canvas.mpl_disconnect(self._c1) + + def disconnect(self): + 'disconnect the callbacks' + for cid in self.cids: + self.canvas.mpl_disconnect(cid) + + def artist_picker(self, artist, evt): + return self.ref_artist.contains(evt) + + def save_offset(self): + pass + + def update_offset(self, dx, dy): + pass + + def finalize_offset(self): + pass + + +class DraggableOffsetBox(DraggableBase): + def __init__(self, ref_artist, offsetbox): + DraggableBase.__init__(self, ref_artist) + self.offsetbox = offsetbox + + def save_offset(self): + offsetbox = self.offsetbox + renderer = offsetbox.figure._cachedRenderer + w, h, xd, yd = offsetbox.get_extent(renderer) + offset = offsetbox.get_offset(w, h, xd, yd, renderer) + self.offsetbox_x, self.offsetbox_y = offset + + def update_offset(self, dx, dy): + loc_in_canvas = self.offsetbox_x + dx, self.offsetbox_y + dy + self.offsetbox.set_offset(loc_in_canvas) + self.offsetbox.figure.canvas.draw() + + def get_loc_in_canvas(self): + + offsetbox=self.offsetbox + renderer = offsetbox.figure._cachedRenderer + w, h, xd, yd = offsetbox.get_extent(renderer) + ox, oy = offsetbox._offset + loc_in_canvas = (ox-xd, oy-yd) + + return loc_in_canvas + + +class DraggableAnnotation(DraggableBase): + def __init__(self, annotation): + DraggableBase.__init__(self, annotation) + self.annotation = annotation + + def save_offset(self): + ann = self.annotation + x, y = ann.xytext + if isinstance(ann.textcoords, tuple): + xcoord, ycoord = ann.textcoords + x1, y1 = ann._get_xy(x, y, xcoord) + x2, y2 = ann._get_xy(x, y, ycoord) + ox0, oy0 = x1, y2 + else: + ox0, oy0 = ann._get_xy(x, y, ann.textcoords) + + self.ox, self.oy = ox0, oy0 + self.annotation.textcoords = "figure pixels" + + def update_offset(self, dx, dy): + ann = self.annotation + ann.xytext = self.ox + dx, self.oy + dy + x, y = ann.xytext + xy = ann._get_xy(x, y, ann.textcoords) + self.canvas.draw() + + def finalize_offset(self): + loc_in_canvas = self.annotation.xytext + self.annotation.textcoords = "axes fraction" + pos_axes_fraction = self.annotation.axes.transAxes.inverted().transform_point(loc_in_canvas) + self.annotation.xytext = tuple(pos_axes_fraction) + + if __name__ == "__main__": fig = plt.figure(1) Modified: trunk/matplotlib/lib/matplotlib/text.py =================================================================== --- trunk/matplotlib/lib/matplotlib/text.py 2010年01月29日 16:22:51 UTC (rev 8102) +++ trunk/matplotlib/lib/matplotlib/text.py 2010年01月29日 17:33:21 UTC (rev 8103) @@ -1402,6 +1402,9 @@ self.textcoords = textcoords self.set_annotation_clip(annotation_clip) + self._draggable = None + + def _get_xy(self, x, y, s): if s=='data': trans = self.axes.transData @@ -1534,8 +1537,38 @@ return True + def draggable(self, state=None): + """ + Set the draggable state -- if state is + * None : toggle the current state + * True : turn draggable on + + * False : turn draggable off + + If draggable is on, you can drag the annotation on the canvas with + the mouse. The DraggableAnnotation helper instance is returned if + draggable is on. + """ + from matplotlib.offsetbox import DraggableAnnotation + is_draggable = self._draggable is not None + + # if state is None we'll toggle + if state is None: + state = not is_draggable + + if state: + if self._draggable is None: + self._draggable = DraggableAnnotation(self) + else: + if self._draggable is not None: + self._draggable.disconnect() + self._draggable = None + + return self._draggable + + class Annotation(Text, _AnnotationBase): """ A :class:`~matplotlib.text.Text` class to make annotating things @@ -1661,6 +1694,7 @@ else: self.arrow_patch = None + def contains(self,event): t,tinfo = Text.contains(self,event) if self.arrow is not None: @@ -1803,6 +1837,9 @@ Text.draw(self, renderer) + + + docstring.interpd.update(Annotation=Annotation.__init__.__doc__) This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8102 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8102&view=rev Author: leejjoon Date: 2010年01月29日 16:22:51 +0000 (2010年1月29日) Log Message: ----------- fix some issues in the bbox after the postscript distiller is run Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/backends/backend_ps.py trunk/matplotlib/lib/matplotlib/font_manager.py Modified: trunk/matplotlib/lib/matplotlib/backends/backend_ps.py =================================================================== --- trunk/matplotlib/lib/matplotlib/backends/backend_ps.py 2010年01月29日 15:27:54 UTC (rev 8101) +++ trunk/matplotlib/lib/matplotlib/backends/backend_ps.py 2010年01月29日 16:22:51 UTC (rev 8102) @@ -1383,14 +1383,17 @@ This yields smaller files without illegal encapsulated postscript operators. The output is low-level, converting text to outlines. """ - paper = '-sPAPERSIZE=%s'% ptype + + paper_option = "-sPAPERSIZE=%s" % ptype + psfile = tmpfile + '.ps' outfile = tmpfile + '.output' dpi = rcParams['ps.distiller.res'] if sys.platform == 'win32': gs_exe = 'gswin32c' else: gs_exe = 'gs' + command = '%s -dBATCH -dNOPAUSE -r%d -sDEVICE=pswrite %s -sOutputFile="%s" \ - "%s" > "%s"'% (gs_exe, dpi, paper, psfile, tmpfile, outfile) + "%s" > "%s"'% (gs_exe, dpi, paper_option, psfile, tmpfile, outfile) verbose.report(command, 'debug') exit_status = os.system(command) fh = file(outfile) @@ -1403,14 +1406,14 @@ shutil.move(psfile, tmpfile) + # While it is best if above steps preserve the original bounding + # box, it does not seems to be the case. pstoeps not only convert + # the input to eps format, but also restores the original bbox. - # Since the the paper size is set to the figure size for eps - # output (in '_print_figure_tex'), pstoeps call is not required. + if eps: + pstoeps(tmpfile, bbox) - #if eps: - # pstoeps(tmpfile, bbox) - def xpdf_distill(tmpfile, eps=False, ptype='letter', bbox=None): """ Use ghostscript's ps2pdf and xpdf's/poppler's pdftops to distill a file. @@ -1421,9 +1424,13 @@ pdffile = tmpfile + '.pdf' psfile = tmpfile + '.ps' outfile = tmpfile + '.output' + + if eps: paper_option = "-dEPSCrop" + else: paper_option = "-sPAPERSIZE=%s" % ptype + command = 'ps2pdf -dAutoFilterColorImages=false \ --sColorImageFilter=FlateEncode -sPAPERSIZE=%s "%s" "%s" > "%s"'% \ -(ptype, tmpfile, pdffile, outfile) +-sColorImageFilter=FlateEncode %s "%s" "%s" > "%s"'% \ +(paper_option, tmpfile, pdffile, outfile) if sys.platform == 'win32': command = command.replace('=', '#') verbose.report(command, 'debug') exit_status = os.system(command) @@ -1445,17 +1452,37 @@ os.remove(outfile) os.remove(tmpfile) shutil.move(psfile, tmpfile) + + + # Similar to the gs_distillier case, ps2pdf does not seem to + # preserve the bbox of the original file (at least w/ gs + # 8.61). Thus, the original bbox need to be resotred. + if eps: pstoeps(tmpfile, bbox) for fname in glob.glob(tmpfile+'.*'): os.remove(fname) +def get_bbox_header(l, b, r, t): + """ + return a postscript header stringfor the given bbox (l, b, r, t) + """ + + bbox_info = '%%%%BoundingBox: %d %d %d %d' % (l, b, npy.ceil(r), npy.ceil(t)) + hires_bbox_info = '%%%%HiResBoundingBox: %.6f %.6f %.6f %.6f' % (l, b, r, t) + + return '\n'.join([bbox_info, hires_bbox_info]) + + +# get_bbox is deprecated. I don't see any reason to use ghostscript to +# find the bounding box, as the required bounding box is alread known. def get_bbox(tmpfile, bbox): """ Use ghostscript's bbox device to find the center of the bounding box. Return an appropriately sized bbox centered around that point. A bit of a hack. """ + outfile = tmpfile + '.output' if sys.platform == 'win32': gs_exe = 'gswin32c' else: gs_exe = 'gs' @@ -1497,7 +1524,7 @@ """ Convert the postscript to encapsulated postscript. """ - bbox_info = get_bbox(tmpfile, bbox) + bbox_info = get_bbox_header(*bbox) epsfile = tmpfile + '.eps' epsh = file(epsfile, 'w') @@ -1552,6 +1579,7 @@ shutil.move(epsfile, tmpfile) + class FigureManagerPS(FigureManagerBase): pass Modified: trunk/matplotlib/lib/matplotlib/font_manager.py =================================================================== --- trunk/matplotlib/lib/matplotlib/font_manager.py 2010年01月29日 15:27:54 UTC (rev 8101) +++ trunk/matplotlib/lib/matplotlib/font_manager.py 2010年01月29日 16:22:51 UTC (rev 8102) @@ -1204,7 +1204,6 @@ for font in fontlist: if (directory is not None and os.path.commonprefix([font.fname, directory]) != directory): - print directory, font.fname, os.path.commonprefix([font.fname, directory]) continue # Matching family should have highest priority, so it is multiplied # by 10.0 This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8101 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8101&view=rev Author: jdh2358 Date: 2010年01月29日 15:27:54 +0000 (2010年1月29日) Log Message: ----------- added state to legend toggle Modified Paths: -------------- trunk/matplotlib/CHANGELOG trunk/matplotlib/lib/matplotlib/legend.py Modified: trunk/matplotlib/CHANGELOG =================================================================== --- trunk/matplotlib/CHANGELOG 2010年01月28日 21:46:12 UTC (rev 8100) +++ trunk/matplotlib/CHANGELOG 2010年01月29日 15:27:54 UTC (rev 8101) @@ -1,3 +1,6 @@ +2010年01月29日 Added draggable method to Legend to allow mouse drag +placement. Thanks Adam Fraser. JDH + 2010年01月25日 Fixed a bug reported by Olle Engdegard, when using histograms with stepfilled and log=True - MM Modified: trunk/matplotlib/lib/matplotlib/legend.py =================================================================== --- trunk/matplotlib/lib/matplotlib/legend.py 2010年01月28日 21:46:12 UTC (rev 8100) +++ trunk/matplotlib/lib/matplotlib/legend.py 2010年01月29日 15:27:54 UTC (rev 8101) @@ -935,16 +935,32 @@ return ox, oy - def draggable(self): + def draggable(self, state=None): """ - toggle the draggable state; if on, you can drag the legend on - the canvas. The DraggableLegend helper class is returned + Set the draggable state -- if state is + + * None : toggle the current state + + * True : turn draggable on + + * False : turn draggable off + + If draggable is on, you can drag the legend on the canvas with + the mouse. The DraggableLegend helper instance is returned if + draggable is on. """ - if self._draggable is not None: - self._draggable.disconnect() + is_draggable = self._draggable is not None + + # if state is None we'll toggle + if state is None: + state = not is_draggable + + if state: + if self._draggable is None: + self._draggable = DraggableLegend(self) + else: + if self._draggable is not None: + self._draggable.disconnect() self._draggable = None - else: - self._draggable = DraggableLegend(self) - return self._draggable This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8100 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8100&view=rev Author: jdh2358 Date: 2010年01月28日 21:46:12 +0000 (2010年1月28日) Log Message: ----------- added drabbable state to legend -- thanks Adam Fraser Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/legend.py Modified: trunk/matplotlib/lib/matplotlib/legend.py =================================================================== --- trunk/matplotlib/lib/matplotlib/legend.py 2010年01月28日 20:37:46 UTC (rev 8099) +++ trunk/matplotlib/lib/matplotlib/legend.py 2010年01月28日 21:46:12 UTC (rev 8100) @@ -38,6 +38,51 @@ from matplotlib.offsetbox import HPacker, VPacker, TextArea, DrawingArea +class DraggableLegend: + """helper code for a draggable legend -- see Legend.draggable""" + + def __init__(self, legend): + self.legend = legend + self.gotLegend = False + + c1 = legend.figure.canvas.mpl_connect('motion_notify_event', self.on_motion) + c2 = legend.figure.canvas.mpl_connect('pick_event', self.on_pick) + c3 = legend.figure.canvas.mpl_connect('button_release_event', self.on_release) + legend.set_picker(self.my_legend_picker) + self.cids = [c1, c2, c3] + + def on_motion(self, evt): + if self.gotLegend: + dx = evt.x - self.mouse_x + dy = evt.y - self.mouse_y + loc_in_canvas = self.legend_x + dx, self.legend_y + dy + loc_in_norm_axes = self.legend.parent.transAxes.inverted().transform_point(loc_in_canvas) + self.legend._loc = tuple(loc_in_norm_axes) + self.legend.figure.canvas.draw() + + def my_legend_picker(self, legend, evt): + return self.legend.legendPatch.contains(evt) + + def on_pick(self, evt): + legend = self.legend + if evt.artist == legend: + bbox = self.legend.get_window_extent() + self.mouse_x = evt.mouseevent.x + self.mouse_y = evt.mouseevent.y + self.legend_x = bbox.xmin + self.legend_y = bbox.ymin + self.gotLegend = 1 + + def on_release(self, event): + if self.gotLegend: + self.gotLegend = False + + def disconnect(self): + 'disconnect the callbacks' + for cid in self.cids: + self.legend.figure.canvas.mpl_disconnect(cid) + + class Legend(Artist): """ Place a legend on the axes at location loc. Labels are a @@ -182,7 +227,7 @@ self.texts = [] self.legendHandles = [] self._legend_title_box = None - + localdict = locals() for name in propnames: @@ -284,7 +329,7 @@ # We use FancyBboxPatch to draw a legend frame. The location # and size of the box will be updated during the drawing time. - + self.legendPatch = FancyBboxPatch( xy=(0.0, 0.0), width=1., height=1., facecolor=rcParams["axes.facecolor"], @@ -316,6 +361,7 @@ self._last_fontsize_points = self._fontsize + self._draggable = None def _set_artist_props(self, a): """ @@ -584,7 +630,7 @@ textbox = TextArea(lab, textprops=label_prop, multilinebaseline=True, minimumdescent=True) text_list.append(textbox._text) - + labelboxes.append(textbox) handlebox = DrawingArea(width=self.handlelength*fontsize, @@ -597,7 +643,7 @@ handleboxes.append(handlebox) - if len(handleboxes) > 0: + if len(handleboxes) > 0: # We calculate number of lows in each column. The first # (num_largecol) columns will have (nrows+1) rows, and remaing @@ -613,7 +659,7 @@ [nrows] * num_smallcol) else: largecol, smallcol = [], [] - + handle_label = safezip(handleboxes, labelboxes) columnbox = [] for i0, di in largecol+smallcol: @@ -889,3 +935,16 @@ return ox, oy + def draggable(self): + """ + toggle the draggable state; if on, you can drag the legend on + the canvas. The DraggableLegend helper class is returned + """ + if self._draggable is not None: + self._draggable.disconnect() + self._draggable = None + else: + + self._draggable = DraggableLegend(self) + + return self._draggable This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8099 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8099&view=rev Author: leejjoon Date: 2010年01月28日 20:37:46 +0000 (2010年1月28日) Log Message: ----------- experimental support of Image._image_skew_coordinate Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/image.py Added Paths: ----------- trunk/matplotlib/examples/api/demo_affine_image.py Added: trunk/matplotlib/examples/api/demo_affine_image.py =================================================================== --- trunk/matplotlib/examples/api/demo_affine_image.py (rev 0) +++ trunk/matplotlib/examples/api/demo_affine_image.py 2010年01月28日 20:37:46 UTC (rev 8099) @@ -0,0 +1,51 @@ +#!/usr/bin/env python + + +""" +For the backends that supports draw_image with optional affine +transform (e.g., ps backend), the image of the output should +have its boundary matches the red rectangles. +""" + +import numpy as np +import matplotlib.cm as cm +import matplotlib.mlab as mlab +import matplotlib.pyplot as plt +import matplotlib.transforms as mtransforms + +def get_image(): + delta = 0.25 + x = y = np.arange(-3.0, 3.0, delta) + X, Y = np.meshgrid(x, y) + Z1 = mlab.bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0) + Z2 = mlab.bivariate_normal(X, Y, 1.5, 0.5, 1, 1) + Z = Z2-Z1 # difference of Gaussians + return Z + +def imshow_affine(ax, z, *kl, **kwargs): + im = ax.imshow(z, *kl, **kwargs) + x1, x2, y1, y2 = im.get_extent() + im._image_skew_coordinate = (x2, y1) + return im + + +if 1: + ax = plt.subplot(111) + Z = get_image() + im = imshow_affine(ax, Z, interpolation='nearest', cmap=cm.jet, + origin='lower', extent=[-2, 4, -3, 2]) + + trans_data2 = mtransforms.Affine2D().rotate_deg(30) + ax.transData + im.set_transform(trans_data2) + + # display intended extent of the image + x1, x2, y1, y2 = im.get_extent() + x3, y3 = x2, y1 + + ax.plot([x1, x2, x2, x1, x1], [y1, y1, y2, y2, y1], "r--", lw=3, + transform=trans_data2) + + ax.set_xlim(-3, 5) + ax.set_ylim(-4, 4) + + plt.savefig("demo_affine_image") Modified: trunk/matplotlib/lib/matplotlib/image.py =================================================================== --- trunk/matplotlib/lib/matplotlib/image.py 2010年01月28日 19:09:20 UTC (rev 8098) +++ trunk/matplotlib/lib/matplotlib/image.py 2010年01月28日 20:37:46 UTC (rev 8099) @@ -25,6 +25,7 @@ from matplotlib._image import * from matplotlib.transforms import BboxBase +import matplotlib.transforms as mtransforms class _AxesImageBase(martist.Artist, cm.ScalarMappable): zorder = 0 @@ -96,6 +97,12 @@ self._imcache = None + # this is an expetimental attribute, if True, unsampled image + # will be drawn using the affine transform that are + # appropriately skewed so that the given postition + # corresponds to the actual position in the coordinate. -JJL + self._image_skew_coordinate = None + self.update(kwargs) def get_size(self): @@ -204,6 +211,36 @@ return im, xmin, ymin, dxintv, dyintv, sx, sy + @staticmethod + def _get_rotate_and_skew_transform(x1, y1, x2, y2, x3, y3): + """ + Retuen a transform that does + (x1, y1) -> (x1, y1) + (x2, y2) -> (x2, y2) + (x2, y1) -> (x3, y3) + + It was intended to derive a skew transform that preserve the + lower-left corner (x1, y1) and top-right corner(x2,y2), but + change the the lower-right-corner(x2, y1) to a new position + (x3, y3). + """ + tr1 = mtransforms.Affine2D() + tr1.translate(-x1, -y1) + x2a, y2a = tr1.transform_point((x2, y2)) + x3a, y3a = tr1.transform_point((x3, y3)) + + inv_mat = 1./(x2a*y3a-y2a*x3a) * np.mat([[y3a, -y2a],[-x3a, x2a]]) + + a, b = (inv_mat * np.mat([[x2a], [x2a]])).flat + c, d = (inv_mat * np.mat([[y2a], [0]])).flat + + tr2 = mtransforms.Affine2D.from_values(a, c, b, d, 0, 0) + + tr = (tr1 + tr2 + mtransforms.Affine2D().translate(x1, y1)).inverted().get_affine() + + return tr + + def _draw_unsampled_image(self, renderer, gc): """ draw unsampled image. The renderer should support a draw_image method @@ -227,13 +264,25 @@ im._url = self.get_url() trans = self.get_transform() #axes.transData - xx1, yy1 = trans.transform_non_affine((xmin, ymin)) - xx2, yy2 = trans.transform_non_affine((xmin+dxintv, ymin+dyintv)) + xy = trans.transform_non_affine([(xmin, ymin), + (xmin+dxintv, ymin+dyintv)]) + xx1, yy1 = xy[0] + xx2, yy2 = xy[1] - renderer.draw_image(gc, xx1, yy1, im, xx2-xx1, yy2-yy1, - trans.get_affine()) + if self._image_skew_coordinate: + # skew the image when required. + x_lrc, y_lrc = self._image_skew_coordinate + xy = trans.transform_non_affine([(x_lrc, y_lrc)]) + xx3, yy3 = xy[0] + tr_rotate_skew = self._get_rotate_and_skew_transform(xx1, yy1, xx2, yy2, xx3, yy3) + tr = tr_rotate_skew+trans.get_affine() + else: + tr = trans.get_affine() + renderer.draw_image(gc, xx1, yy1, im, xx2-xx1, yy2-yy1, tr) + + def _check_unsampled_image(self, renderer): """ return True if the image is better to be drawn unsampled. This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8098 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8098&view=rev Author: ryanmay Date: 2010年01月28日 19:09:20 +0000 (2010年1月28日) Log Message: ----------- Support setting zorder keyword for ContourSet. Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/contour.py Modified: trunk/matplotlib/lib/matplotlib/contour.py =================================================================== --- trunk/matplotlib/lib/matplotlib/contour.py 2010年01月25日 20:31:41 UTC (rev 8097) +++ trunk/matplotlib/lib/matplotlib/contour.py 2010年01月28日 19:09:20 UTC (rev 8098) @@ -695,10 +695,13 @@ paths = self._make_paths(segs, kinds) + # Default zorder taken from Collection + zorder = kwargs.get('zorder', 1) col = collections.PathCollection(paths, antialiaseds = (self.antialiased,), edgecolors= 'none', - alpha=self.alpha) + alpha=self.alpha, + zorder=zorder) self.ax.add_collection(col) self.collections.append(col) else: @@ -710,10 +713,14 @@ nseg = len(nlist)//2 segs = nlist[:nseg] #kinds = nlist[nseg:] + + # Default zorder taken from LineCollection + zorder = kwargs.get('zorder', 2) col = collections.LineCollection(segs, linewidths = width, linestyle = lstyle, - alpha=self.alpha) + alpha=self.alpha, + zorder=zorder) col.set_label('_nolegend_') self.ax.add_collection(col, False) @@ -1228,4 +1235,3 @@ ymin = lc[imin,1] return (conmin,segmin,imin,xmin,ymin,dmin) - This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8097 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8097&view=rev Author: mmetz_bn Date: 2010年01月25日 20:31:41 +0000 (2010年1月25日) Log Message: ----------- Fixed a bug in hist with stepfilled and log=True Modified Paths: -------------- trunk/matplotlib/CHANGELOG trunk/matplotlib/lib/matplotlib/axes.py Modified: trunk/matplotlib/CHANGELOG =================================================================== --- trunk/matplotlib/CHANGELOG 2010年01月25日 13:04:22 UTC (rev 8096) +++ trunk/matplotlib/CHANGELOG 2010年01月25日 20:31:41 UTC (rev 8097) @@ -1,3 +1,5 @@ +2010年01月25日 Fixed a bug reported by Olle Engdegard, when using + histograms with stepfilled and log=True - MM 2010年01月16日 Upgraded CXX to 6.1.1 - JDH Modified: trunk/matplotlib/lib/matplotlib/axes.py =================================================================== --- trunk/matplotlib/lib/matplotlib/axes.py 2010年01月25日 13:04:22 UTC (rev 8096) +++ trunk/matplotlib/lib/matplotlib/axes.py 2010年01月25日 20:31:41 UTC (rev 8097) @@ -7216,6 +7216,8 @@ for m in n: y[1:-1:2], y[2::2] = m, m + if log: + y[y<1e-100]=1e-100 if orientation == 'horizontal': x,y = y,x elif orientation != 'vertical': This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8096 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8096&view=rev Author: jswhit Date: 2010年01月25日 13:04:22 +0000 (2010年1月25日) Log Message: ----------- add more informative error message when lat_0 is nonzero for projection='geos' Modified Paths: -------------- trunk/toolkits/basemap/lib/mpl_toolkits/basemap/__init__.py Modified: trunk/toolkits/basemap/lib/mpl_toolkits/basemap/__init__.py =================================================================== --- trunk/toolkits/basemap/lib/mpl_toolkits/basemap/__init__.py 2010年01月22日 23:48:35 UTC (rev 8095) +++ trunk/toolkits/basemap/lib/mpl_toolkits/basemap/__init__.py 2010年01月25日 13:04:22 UTC (rev 8096) @@ -585,6 +585,8 @@ if np.abs(lat_0) < 1.e-2: lat_0 = 1.e-2 projparams['lat_0'] = lat_0 elif projection == 'geos': + if lat_0 is not None and lat_0 != 0: + raise ValueError, 'lat_0 must be zero for Geostationary basemap' if lon_0 is None: raise ValueError, 'must specify lon_0 for Geostationary basemap' if width is not None or height is not None: This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8095 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8095&view=rev Author: efiring Date: 2010年01月22日 23:48:35 +0000 (2010年1月22日) Log Message: ----------- Add units module to documentation Modified Paths: -------------- trunk/matplotlib/doc/api/index.rst Added Paths: ----------- trunk/matplotlib/doc/api/units_api.rst Modified: trunk/matplotlib/doc/api/index.rst =================================================================== --- trunk/matplotlib/doc/api/index.rst 2010年01月22日 23:47:14 UTC (rev 8094) +++ trunk/matplotlib/doc/api/index.rst 2010年01月22日 23:48:35 UTC (rev 8095) @@ -32,4 +32,5 @@ pyplot_api.rst spine_api.rst ticker_api.rst + units_api.rst index_backend_api.rst Added: trunk/matplotlib/doc/api/units_api.rst =================================================================== --- trunk/matplotlib/doc/api/units_api.rst (rev 0) +++ trunk/matplotlib/doc/api/units_api.rst 2010年01月22日 23:48:35 UTC (rev 8095) @@ -0,0 +1,12 @@ +***************** +matplotlib units +***************** + + +:mod:`matplotlib.units` +======================== + +.. automodule:: matplotlib.units + :members: + :undoc-members: + :show-inheritance: This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8094 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8094&view=rev Author: efiring Date: 2010年01月22日 23:47:14 +0000 (2010年1月22日) Log Message: ----------- Fix units support for contour and contourf Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/contour.py Modified: trunk/matplotlib/lib/matplotlib/contour.py =================================================================== --- trunk/matplotlib/lib/matplotlib/contour.py 2010年01月22日 02:18:13 UTC (rev 8093) +++ trunk/matplotlib/lib/matplotlib/contour.py 2010年01月22日 23:47:14 UTC (rev 8094) @@ -643,7 +643,7 @@ if self.levels is None: self.levels = args[0].levels else: - x, y, z = self._contour_args(*args) + x, y, z = self._contour_args(args, kwargs) x0 = ma.minimum(x) x1 = ma.maximum(x) @@ -808,7 +808,7 @@ y = y[::-1] return np.meshgrid(x,y) - def _check_xyz(self, args): + def _check_xyz(self, args, kwargs): ''' For functions like contour, check that the dimensions of the input arrays match; if x and y are 1D, convert @@ -817,9 +817,10 @@ Possible change: I think we should make and use an ArgumentError Exception class (here and elsewhere). ''' - # We can strip away the x and y units - x = self.ax.convert_xunits( args[0] ) - y = self.ax.convert_yunits( args[1] ) + x, y = args[:2] + self.ax._process_unit_info(xdata=x, ydata=y, kwargs=kwargs) + x = self.ax.convert_xunits(x) + y = self.ax.convert_yunits(y) x = np.asarray(x, dtype=np.float64) y = np.asarray(y, dtype=np.float64) @@ -840,8 +841,7 @@ return x,y,z - - def _contour_args(self, *args): + def _contour_args(self, args, kwargs): if self.filled: fn = 'contourf' else: fn = 'contour' Nargs = len(args) @@ -849,7 +849,7 @@ z = ma.asarray(args[0], dtype=np.float64) x, y = self._initialize_x_y(z) elif Nargs <=4: - x,y,z = self._check_xyz(args[:3]) + x,y,z = self._check_xyz(args[:3], kwargs) else: raise TypeError("Too many arguments to %s; see help(%s)" % (fn,fn)) z = ma.masked_invalid(z, copy=False) @@ -1103,9 +1103,14 @@ are included. These added ranges are then mapped to the special colormap values which default to the ends of the colormap range, but can be set via - :meth:`matplotlib.cm.Colormap.set_under` and - :meth:`matplotlib.cm.Colormap.set_over` methods. + :meth:`matplotlib.colors.Colormap.set_under` and + :meth:`matplotlib.colors.Colormap.set_over` methods. + *xunits*, *yunits*: [ None | registered units ] + Override axis units by specifying an instance of a + :class:`matplotlib.units.ConversionInterface`. + + contour-only keyword arguments: *linewidths*: [ None | number | tuple of numbers ] This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8093 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8093&view=rev Author: efiring Date: 2010年01月22日 02:18:13 +0000 (2010年1月22日) Log Message: ----------- Contourf: change method of making bottom bound include zmin. This avoids a problem in colorbar tick labeling when zmin is 0. Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/contour.py Modified: trunk/matplotlib/lib/matplotlib/contour.py =================================================================== --- trunk/matplotlib/lib/matplotlib/contour.py 2010年01月19日 00:26:16 UTC (rev 8092) +++ trunk/matplotlib/lib/matplotlib/contour.py 2010年01月22日 02:18:13 UTC (rev 8093) @@ -676,8 +676,17 @@ if self.filled: if self.linewidths is not None: warnings.warn('linewidths is ignored by contourf') + lowers = self._levels[:-1] + if self.zmin == lowers[0]: + # Include minimum values in lowest interval + lowers = lowers.copy() # so we don't change self._levels + if self.logscale: + lowers[0] = 0.99 * self.zmin + else: + lowers[0] -= 1 uppers = self._levels[1:] + for level, level_upper in zip(lowers, uppers): nlist = C.trace(level, level_upper, nchunk = self.nchunk) nseg = len(nlist)//2 @@ -756,14 +765,6 @@ zmin = self.zmin self.locator.set_bounds(zmin, zmax) lev = self.locator() - zmargin = (zmax - zmin) * 0.000001 # so z < (zmax + zmargin) - if zmax >= lev[-1]: - lev[-1] += zmargin - if zmin <= lev[0]: - if self.logscale: - lev[0] = 0.99 * zmin - else: - lev[0] -= zmargin self._auto = True if self.filled: return lev @@ -1141,6 +1142,15 @@ be removed. Chunking introduces artifacts at the chunk boundaries unless *antialiased* is *False*. + Note: contourf fills intervals that are closed at the top; that + is, for boundaries *z1* and *z2*, the filled region is:: + + z1 < z <= z2 + + There is one exception: if the lowest boundary coincides with + the minimum value of the *z* array, then that minimum value + will be included in the lowest interval. + **Examples:** .. plot:: mpl_examples/pylab_examples/contour_demo.py This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8092 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8092&view=rev Author: leejjoon Date: 2010年01月19日 00:26:16 +0000 (2010年1月19日) Log Message: ----------- update annotate documentation to explain *annotation_clip* parameter Modified Paths: -------------- branches/v0_99_maint/lib/matplotlib/text.py Modified: branches/v0_99_maint/lib/matplotlib/text.py =================================================================== --- branches/v0_99_maint/lib/matplotlib/text.py 2010年01月17日 01:42:30 UTC (rev 8091) +++ branches/v0_99_maint/lib/matplotlib/text.py 2010年01月19日 00:26:16 UTC (rev 8092) @@ -1438,6 +1438,14 @@ # 5 points below the top border xy=(10,-5), xycoords='axes points' + + The *annotation_clip* attribute contols the visibility of the + annotation when it goes outside the axes area. If True, the + annotation will only be drawn when the *xy* is inside the + axes. If False, the annotation will always be drawn regardless + of its position. The default is *None*, which behave as True + only if *xycoords* is"data". + Additional kwargs are Text properties: %(Text)s This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8091 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8091&view=rev Author: jdh2358 Date: 2010年01月17日 01:42:30 +0000 (2010年1月17日) Log Message: ----------- added Goekhan's apply patch to qt editor Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/backends/qt4_editor/figureoptions.py trunk/matplotlib/lib/matplotlib/backends/qt4_editor/formlayout.py Modified: trunk/matplotlib/lib/matplotlib/backends/qt4_editor/figureoptions.py =================================================================== --- trunk/matplotlib/lib/matplotlib/backends/qt4_editor/figureoptions.py 2010年01月16日 23:14:50 UTC (rev 8090) +++ trunk/matplotlib/lib/matplotlib/backends/qt4_editor/figureoptions.py 2010年01月17日 01:42:30 UTC (rev 8091) @@ -112,43 +112,46 @@ datalist = [(general, "Axes", "")] if has_curve: datalist.append((curves, "Curves", "")) - result = formlayout.fedit(datalist, title="Figure options", parent=parent, - icon=get_icon('qt4_editor_options.svg')) - if result is None: - return - - if has_curve: - general, curves = result - else: - general, = result - - # Set / General - title, xmin, xmax, xlabel, xscale, ymin, ymax, ylabel, yscale = general - axes.set_xscale(xscale) - axes.set_yscale(yscale) - axes.set_title(title) - axes.set_xlim(xmin, xmax) - axes.set_xlabel(xlabel) - axes.set_ylim(ymin, ymax) - axes.set_ylabel(ylabel) - - if has_curve: - # Set / Curves - for index, curve in enumerate(curves): - line = linedict[curvelabels[index]] - label, linestyle, linewidth, color, \ - marker, markersize, markerfacecolor, markeredgecolor = curve - line.set_label(label) - line.set_linestyle(linestyle) - line.set_linewidth(linewidth) - line.set_color(color) - if marker is not 'none': - line.set_marker(marker) - line.set_markersize(markersize) - line.set_markerfacecolor(markerfacecolor) - line.set_markeredgecolor(markeredgecolor) - - # Redraw - figure = axes.get_figure() - figure.canvas.draw() - + + def apply_callback(data): + """This function will be called to apply changes""" + if has_curve: + general, curves = data + else: + general, = data + + # Set / General + title, xmin, xmax, xlabel, xscale, ymin, ymax, ylabel, yscale = general + axes.set_xscale(xscale) + axes.set_yscale(yscale) + axes.set_title(title) + axes.set_xlim(xmin, xmax) + axes.set_xlabel(xlabel) + axes.set_ylim(ymin, ymax) + axes.set_ylabel(ylabel) + + if has_curve: + # Set / Curves + for index, curve in enumerate(curves): + line = linedict[curvelabels[index]] + label, linestyle, linewidth, color, \ + marker, markersize, markerfacecolor, markeredgecolor = curve + line.set_label(label) + line.set_linestyle(linestyle) + line.set_linewidth(linewidth) + line.set_color(color) + if marker is not 'none': + line.set_marker(marker) + line.set_markersize(markersize) + line.set_markerfacecolor(markerfacecolor) + line.set_markeredgecolor(markeredgecolor) + + # Redraw + figure = axes.get_figure() + figure.canvas.draw() + + data = formlayout.fedit(datalist, title="Figure options", parent=parent, + icon=get_icon('qt4_editor_options.svg'), apply=apply_callback) + if data is not None: + apply_callback(data) + Modified: trunk/matplotlib/lib/matplotlib/backends/qt4_editor/formlayout.py =================================================================== --- trunk/matplotlib/lib/matplotlib/backends/qt4_editor/formlayout.py 2010年01月16日 23:14:50 UTC (rev 8090) +++ trunk/matplotlib/lib/matplotlib/backends/qt4_editor/formlayout.py 2010年01月17日 01:42:30 UTC (rev 8091) @@ -33,7 +33,11 @@ OTHER DEALINGS IN THE SOFTWARE. """ -__version__ = '1.0.5' +# History: +# 1.0.7: added support for "Apply" button +# 1.0.6: code cleaning + +__version__ = '1.0.7' __license__ = __doc__ DEBUG = False @@ -67,21 +71,21 @@ QPushButton.__init__(self, parent) self.setFixedSize(20, 20) self.setIconSize(QSize(12, 12)) - self.connect(self, SIGNAL("clicked()"), self.chooseColor) + self.connect(self, SIGNAL("clicked()"), self.choose_color) self._color = QColor() - def chooseColor(self): + def choose_color(self): rgba, valid = QColorDialog.getRgba(self._color.rgba(), self.parentWidget()) if valid: color = QColor.fromRgba(rgba) - self.setColor(color) + self.set_color(color) - def color(self): + def get_color(self): return self._color @pyqtSignature("QColor") - def setColor(self, color): + def set_color(self, color): if color != self._color: self._color = color self.emit(SIGNAL("colorChanged(QColor)"), self._color) @@ -89,7 +93,7 @@ pixmap.fill(color) self.setIcon(QIcon(pixmap)) - color = pyqtProperty("QColor", color, setColor) + color = pyqtProperty("QColor", get_color, set_color) def text_to_qcolor(text): @@ -369,8 +373,10 @@ class FormDialog(QDialog): """Form Dialog""" def __init__(self, data, title="", comment="", - icon=None, parent=None): + icon=None, parent=None, apply=None): super(FormDialog, self).__init__(parent) + + self.apply_callback = apply # Form if isinstance(data[0][0], (list, tuple)): @@ -387,6 +393,9 @@ # Button box bbox = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel) + if self.apply_callback is not None: + apply_btn = bbox.addButton(QDialogButtonBox.Apply) + self.connect(apply_btn, SIGNAL("clicked()"), self.apply) self.connect(bbox, SIGNAL("accepted()"), SLOT("accept()")) self.connect(bbox, SIGNAL("rejected()"), SLOT("reject()")) layout.addWidget(bbox) @@ -406,17 +415,25 @@ self.data = None QDialog.reject(self) + def apply(self): + self.apply_callback(self.formwidget.get()) + def get(self): """Return form result""" return self.data -def fedit(data, title="", comment="", icon=None, parent=None): +def fedit(data, title="", comment="", icon=None, parent=None, apply=None): """ Create form dialog and return result (if Cancel button is pressed, return None) data: datalist, datagroup + title: string + comment: string + icon: QIcon instance + parent: parent QWidget + apply: apply callback (function) datalist: list/tuple of (field_name, field_value) datagroup: list/tuple of (datalist *or* datagroup, title, comment) @@ -440,7 +457,7 @@ if QApplication.startingUp(): QApplication([]) - dialog = FormDialog(data, title, comment, icon, parent) + dialog = FormDialog(data, title, comment, icon, parent, apply) if dialog.exec_(): return dialog.get() @@ -471,8 +488,11 @@ #--------- datalist example datalist = create_datalist_example() + def apply_test(data): + print "data:", data print "result:", fedit(datalist, title="Example", - comment="This is just an <b>example</b>.") + comment="This is just an <b>example</b>.", + apply=apply_test) #--------- datagroup example datagroup = create_datagroup_example() This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8090 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8090&view=rev Author: jdh2358 Date: 2010年01月16日 23:14:50 +0000 (2010年1月16日) Log Message: ----------- make CXX6 the default again Added Paths: ----------- trunk/matplotlib/CXX/ Removed Paths: ------------- trunk/matplotlib/CXX6/ This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8089 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8089&view=rev Author: jdh2358 Date: 2010年01月16日 23:14:11 +0000 (2010年1月16日) Log Message: ----------- move CXX to CXX5 Added Paths: ----------- trunk/matplotlib/CXX5/ Removed Paths: ------------- trunk/matplotlib/CXX/ This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8088 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8088&view=rev Author: jdh2358 Date: 2010年01月16日 23:07:42 +0000 (2010年1月16日) Log Message: ----------- rename CXX64 to CXX6 Added Paths: ----------- trunk/matplotlib/CXX6/ Removed Paths: ------------- trunk/matplotlib/CXX64/ This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8087 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8087&view=rev Author: jdh2358 Date: 2010年01月16日 23:01:21 +0000 (2010年1月16日) Log Message: ----------- restore cxx5 Added Paths: ----------- trunk/matplotlib/CXX/ trunk/matplotlib/CXX/Config.hxx trunk/matplotlib/CXX/Exception.hxx trunk/matplotlib/CXX/Extensions.hxx trunk/matplotlib/CXX/IndirectPythonInterface.cxx trunk/matplotlib/CXX/IndirectPythonInterface.hxx trunk/matplotlib/CXX/Objects.hxx trunk/matplotlib/CXX/Version.hxx trunk/matplotlib/CXX/WrapPython.h trunk/matplotlib/CXX/cxx_extensions.cxx trunk/matplotlib/CXX/cxxextensions.c trunk/matplotlib/CXX/cxxsupport.cxx Added: trunk/matplotlib/CXX/Config.hxx =================================================================== --- trunk/matplotlib/CXX/Config.hxx (rev 0) +++ trunk/matplotlib/CXX/Config.hxx 2010年01月16日 23:01:21 UTC (rev 8087) @@ -0,0 +1,134 @@ +//----------------------------------------------------------------------------- +// +// Copyright (c) 1998 - 2007, The Regents of the University of California +// Produced at the Lawrence Livermore National Laboratory +// All rights reserved. +// +// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The +// full copyright notice is contained in the file COPYRIGHT located at the root +// of the PyCXX distribution. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// - Redistributions of source code must retain the above copyright notice, +// this list of conditions and the disclaimer below. +// - Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the disclaimer (as noted below) in the +// documentation and/or materials provided with the distribution. +// - Neither the name of the UC/LLNL nor the names of its contributors may be +// used to endorse or promote products derived from this software without +// specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF +// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR +// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH +// DAMAGE. +// +//----------------------------------------------------------------------------- + +#ifndef __PyCXX_config_hh__ +#define __PyCXX_config_hh__ + +// +// Microsoft VC++ 6.0 has no traits +// +#if defined( _MSC_VER ) + +# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 1 + +#elif defined( __GNUC__ ) +# if __GNUC__ >= 3 +# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 1 +# else +# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 0 +#endif + +// +// Assume all other compilers do +// +#else + +// Macros to deal with deficiencies in compilers +# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 1 +#endif + +#if STANDARD_LIBRARY_HAS_ITERATOR_TRAITS +# define random_access_iterator_parent(itemtype) std::iterator<std::random_access_iterator_tag,itemtype,int> +#else +# define random_access_iterator_parent(itemtype) std::random_access_iterator<itemtype, int> +#endif + +// +// Which C++ standard is in use? +// +#if defined( _MSC_VER ) +# if _MSC_VER <= 1200 +// MSVC++ 6.0 +# define PYCXX_ISO_CPP_LIB 0 +# define STR_STREAM <strstream> +# define TEMPLATE_TYPENAME class +# else +# define PYCXX_ISO_CPP_LIB 1 +# define STR_STREAM <sstream> +# define TEMPLATE_TYPENAME typename +# endif +#elif defined( __GNUC__ ) +# if __GNUC__ >= 3 +# define PYCXX_ISO_CPP_LIB 1 +# define STR_STREAM <sstream> +# define TEMPLATE_TYPENAME typename +# else +# define PYCXX_ISO_CPP_LIB 0 +# define STR_STREAM <strstream> +# define TEMPLATE_TYPENAME class +# endif +#endif + +#if PYCXX_ISO_CPP_LIB +# define STR_STREAM <sstream> +# define OSTRSTREAM ostringstream +# define EXPLICIT_TYPENAME typename +# define EXPLICIT_CLASS class +# define TEMPLATE_TYPENAME typename +#else +# define STR_STREAM <strstream> +# define OSTRSTREAM ostrstream +# define EXPLICIT_TYPENAME +# define EXPLICIT_CLASS +# define TEMPLATE_TYPENAME class +#endif + +// before 2.5 Py_ssize_t was missing +#ifndef PY_MAJOR_VERSION +#error not defined PY_MAJOR_VERSION +#endif +#if PY_MAJOR_VERSION < 2 || (PY_MAJOR_VERSION == 2 && PY_MINOR_VERSION < 5) +typedef int Py_ssize_t; +#endif + +// hash_map container usage selection +// 1) if PYCXX_USING_STD_MAP is defined PyCXX will be using std::map<> container +// implementation only. +// 2) if compilers are used other than MS Visual Studio (7.1+) or GCC 3.x +// STANDARD_LIBRARY_HAS_HASH_MAP must be defined before compilation to +// make PyCXX using hash_map container. +#if !defined( PYCXX_USING_STD_MAP ) + #if defined( _MSC_VER ) || defined( __INTEL_COMPILER ) || defined ( __ICC ) || (defined( __GNUC__ ) && ( __GNUC__ > 3 )) + # define PYCXX_USING_HASH_MAP + #else + # if defined( STANDARD_LIBRARY_HAS_HASH_MAP ) && !defined( PYCXX_USING_HASH_MAP ) + # define PYCXX_USING_HASH_MAP + # endif + #endif +#endif + +#endif // __PyCXX_config_hh__ Added: trunk/matplotlib/CXX/Exception.hxx =================================================================== --- trunk/matplotlib/CXX/Exception.hxx (rev 0) +++ trunk/matplotlib/CXX/Exception.hxx 2010年01月16日 23:01:21 UTC (rev 8087) @@ -0,0 +1,249 @@ +//----------------------------------------------------------------------------- +// +// Copyright (c) 1998 - 2007, The Regents of the University of California +// Produced at the Lawrence Livermore National Laboratory +// All rights reserved. +// +// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The +// full copyright notice is contained in the file COPYRIGHT located at the root +// of the PyCXX distribution. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// - Redistributions of source code must retain the above copyright notice, +// this list of conditions and the disclaimer below. +// - Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the disclaimer (as noted below) in the +// documentation and/or materials provided with the distribution. +// - Neither the name of the UC/LLNL nor the names of its contributors may be +// used to endorse or promote products derived from this software without +// specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF +// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR +// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH +// DAMAGE. +// +//----------------------------------------------------------------------------- + +#ifndef __CXX_Exception_h +#define __CXX_Exception_h + +#include "CXX/WrapPython.h" +#include "CXX/Version.hxx" +#include "CXX/Config.hxx" +#include "CXX/IndirectPythonInterface.hxx" + +#include <string> +#include <iostream> + +// This mimics the Python structure, in order to minimize confusion +namespace Py +{ + class ExtensionExceptionType; + + class Object; + + class Exception + { + public: + Exception( ExtensionExceptionType &exception, const std::string& reason ); + Exception( ExtensionExceptionType &exception, Object &reason ); + + explicit Exception () + {} + + Exception (const std::string& reason) + { + PyErr_SetString (Py::_Exc_RuntimeError(), reason.c_str()); + } + + Exception (PyObject* exception, const std::string& reason) + { + PyErr_SetString (exception, reason.c_str()); + } + + Exception (PyObject* exception, Object &reason); + + void clear() // clear the error + // technically but not philosophically const + { + PyErr_Clear(); + } + }; + + + // Abstract + class StandardError: public Exception + { + protected: + explicit StandardError() + {} + }; + + class LookupError: public StandardError + { + protected: + explicit LookupError() + {} + }; + + class ArithmeticError: public StandardError + { + protected: + explicit ArithmeticError() + {} + }; + + class EnvironmentError: public StandardError + { + protected: + explicit EnvironmentError() + {} + }; + + // Concrete + + class TypeError: public StandardError + { + public: + TypeError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_TypeError(),reason.c_str()); + } + }; + + class IndexError: public LookupError + { + public: + IndexError (const std::string& reason) + : LookupError() + { + PyErr_SetString (Py::_Exc_IndexError(), reason.c_str()); + } + }; + + class AttributeError: public StandardError + { + public: + AttributeError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_AttributeError(), reason.c_str()); + } + }; + + class NameError: public StandardError + { + public: + NameError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_NameError(), reason.c_str()); + } + }; + + class RuntimeError: public StandardError + { + public: + RuntimeError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_RuntimeError(), reason.c_str()); + } + }; + + class SystemError: public StandardError + { + public: + SystemError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_SystemError(),reason.c_str()); + } + }; + + class KeyError: public LookupError + { + public: + KeyError (const std::string& reason) + : LookupError() + { + PyErr_SetString (Py::_Exc_KeyError(),reason.c_str()); + } + }; + + + class ValueError: public StandardError + { + public: + ValueError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_ValueError(), reason.c_str()); + } + }; + + class OverflowError: public ArithmeticError + { + public: + OverflowError (const std::string& reason) + : ArithmeticError() + { + PyErr_SetString (Py::_Exc_OverflowError(), reason.c_str()); + } + }; + + class ZeroDivisionError: public ArithmeticError + { + public: + ZeroDivisionError (const std::string& reason) + : ArithmeticError() + { + PyErr_SetString (Py::_Exc_ZeroDivisionError(), reason.c_str()); + } + }; + + class FloatingPointError: public ArithmeticError + { + public: + FloatingPointError (const std::string& reason) + : ArithmeticError() + { + PyErr_SetString (Py::_Exc_FloatingPointError(), reason.c_str()); + } + }; + + class MemoryError: public StandardError + { + public: + MemoryError (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_MemoryError(), reason.c_str()); + } + }; + + class SystemExit: public StandardError + { + public: + SystemExit (const std::string& reason) + : StandardError() + { + PyErr_SetString (Py::_Exc_SystemExit(),reason.c_str()); + } + }; + +}// Py + +#endif Added: trunk/matplotlib/CXX/Extensions.hxx =================================================================== --- trunk/matplotlib/CXX/Extensions.hxx (rev 0) +++ trunk/matplotlib/CXX/Extensions.hxx 2010年01月16日 23:01:21 UTC (rev 8087) @@ -0,0 +1,928 @@ +//----------------------------------------------------------------------------- +// +// Copyright (c) 1998 - 2007, The Regents of the University of California +// Produced at the Lawrence Livermore National Laboratory +// All rights reserved. +// +// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The +// full copyright notice is contained in the file COPYRIGHT located at the root +// of the PyCXX distribution. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// - Redistributions of source code must retain the above copyright notice, +// this list of conditions and the disclaimer below. +// - Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the disclaimer (as noted below) in the +// documentation and/or materials provided with the distribution. +// - Neither the name of the UC/LLNL nor the names of its contributors may be +// used to endorse or promote products derived from this software without +// specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF +// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR +// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH +// DAMAGE. +// +//----------------------------------------------------------------------------- + +#ifndef __CXX_Extensions__h +#define __CXX_Extensions__h + + +#ifdef _MSC_VER +// disable warning C4786: symbol greater than 255 character, +// okay to ignore +#pragma warning(disable: 4786) +#endif + +#include "CXX/WrapPython.h" +#include "CXX/Version.hxx" +#include "CXX/Config.hxx" +#include "CXX/Objects.hxx" + +extern "C" +{ + extern PyObject py_object_initializer; +} + +#include <vector> + +// std::map / hash_map selection and declarations ---------------------------- +#if !defined( PYCXX_USING_HASH_MAP ) + +#include <map> + +#else + +#if defined( __GNUC__) && !defined( _STLPORT_VERSION ) + #include <ext/hash_map> +#else + #include <hash_map> +#endif +#if defined( _STLPORT_VERSION ) + #define __PYCXX_HASHMAP_NAMESPACE std + using namespace std; +#elif defined ( _MSC_VER ) && !defined( __INTEL_COMPILER ) && !defined( __ICC ) && !defined( __ICL ) && !defined( __ECC ) + #define __PYCXX_HASHMAP_NAMESPACE stdext + using namespace stdext; +#elif defined( __INTEL_COMPILER ) || defined( __ICC ) || defined( __ICL ) || defined( __ECC ) + #define __PYCXX_HASHMAP_NAMESPACE stdext + using namespace stdext; +#elif defined( __GNUC__ ) + #define __PYCXX_HASHMAP_NAMESPACE __gnu_cxx + using namespace __gnu_cxx; +#else + #define __PYCXX_HASHMAP_NAMESPACE std + using namespace std; +#endif + +class __pycxx_str_hash_func +{ +public: + enum + { + // parameters for hash table + bucket_size = 4, // 0 < bucket_size + min_buckets = 8 // min_buckets = 2 ^^ N, 0 < N + }; + + // http://www.azillionmonkeys.com/qed/hash.html + size_t operator()( const std::string &str ) const + { + const unsigned char * data = reinterpret_cast<const unsigned char *>( str.c_str() ); + int len = (int)str.length(); + unsigned int hash = len; + unsigned int tmp; + int rem; + + if (len <= 0 || data == NULL) + return 0; + + rem = len & 3; + len >>= 2; + + /* Main loop */ + for (;len > 0; len--) + { + hash += (data[1] << 8) | data[0]; + tmp = (((data[3] << 8) | data[2]) << 11) ^ hash; + hash = (hash << 16) ^ tmp; + data += 2*sizeof (unsigned short); + hash += hash >> 11; + } + + /* Handle end cases */ + switch (rem) + { + case 3: hash += (data[1] << 8) | data[0]; + hash ^= hash << 16; + hash ^= data[sizeof (unsigned short)] << 18; + hash += hash >> 11; + break; + case 2: hash += (data[1] << 8) | data[0]; + hash ^= hash << 11; + hash += hash >> 17; + break; + case 1: hash += *data; + hash ^= hash << 10; + hash += hash >> 1; + } + + /* Force "avalanching" of final 127 bits */ + hash ^= hash << 3; + hash += hash >> 5; + hash ^= hash << 4; + hash += hash >> 17; + hash ^= hash << 25; + hash += hash >> 6; + + return hash; + } + + bool operator()(const std::string &str_1, const std::string &str_2) const + { + // test if str_1 ordered before str_2 + return str_1 < str_2; + } +}; +#endif // PYCXX_USING_HASH_MAP +// ---------------------------------------------------------------------- + +namespace Py +{ + class ExtensionModuleBase; + + // Make an Exception Type for use in raising custom exceptions + class ExtensionExceptionType : public Object + { + public: + ExtensionExceptionType(); + virtual ~ExtensionExceptionType(); + + // call init to create the type + void init( ExtensionModuleBase &module, const std::string& name, ExtensionExceptionType &parent ); + void init( ExtensionModuleBase &module, const std::string& name ); + }; + + + class MethodTable + { + public: + MethodTable(); + virtual ~MethodTable(); + + void add(const char* method_name, PyCFunction f, const char* doc="", int flag=1); + PyMethodDef* table(); + + protected: + std::vector<PyMethodDef> t; // accumulator of PyMethodDef's + PyMethodDef *mt; // Actual method table produced when full + + static PyMethodDef method (const char* method_name, PyCFunction f, int flags = 1, const char* doc=""); + + private: + // + // prevent the compiler generating these unwanted functions + // + MethodTable(const MethodTable& m); //unimplemented + void operator=(const MethodTable& m); //unimplemented + + }; // end class MethodTable + + extern "C" + { + typedef PyObject *(*method_varargs_call_handler_t)( PyObject *_self, PyObject *_args ); + typedef PyObject *(*method_keyword_call_handler_t)( PyObject *_self, PyObject *_args, PyObject *_dict ); + } + + template<class T> + class MethodDefExt : public PyMethodDef + { + public: + typedef Object (T::*method_varargs_function_t)( const Tuple &args ); + typedef Object (T::*method_keyword_function_t)( const Tuple &args, const Dict &kws ); + + MethodDefExt + ( + const char *_name, + method_varargs_function_t _function, + method_varargs_call_handler_t _handler, + const char *_doc + ) + { + ext_meth_def.ml_name = const_cast<char *>(_name); + ext_meth_def.ml_meth = _handler; + ext_meth_def.ml_flags = METH_VARARGS; + ext_meth_def.ml_doc = const_cast<char *>(_doc); + + ext_varargs_function = _function; + ext_keyword_function = NULL; + } + + MethodDefExt + ( + const char *_name, + method_keyword_function_t _function, + method_keyword_call_handler_t _handler, + const char *_doc + ) + { + ext_meth_def.ml_name = const_cast<char *>(_name); + ext_meth_def.ml_meth = method_varargs_call_handler_t( _handler ); + ext_meth_def.ml_flags = METH_VARARGS|METH_KEYWORDS; + ext_meth_def.ml_doc = const_cast<char *>(_doc); + + ext_varargs_function = NULL; + ext_keyword_function = _function; + } + + ~MethodDefExt() + {} + + PyMethodDef ext_meth_def; + method_varargs_function_t ext_varargs_function; + method_keyword_function_t ext_keyword_function; + }; + + class ExtensionModuleBase + { + public: + ExtensionModuleBase( const char *name ); + virtual ~ExtensionModuleBase(); + + Module module(void) const; // only valid after initialize() has been called + Dict moduleDictionary(void) const; // only valid after initialize() has been called + + virtual Object invoke_method_keyword( const std::string &_name, const Tuple &_args, const Dict &_keywords ) = 0; + virtual Object invoke_method_varargs( const std::string &_name, const Tuple &_args ) = 0; + + const std::string &name() const; + const std::string &fullName() const; + + protected: + // Initialize the module + void initialize( const char *module_doc ); + + const std::string module_name; + const std::string full_module_name; + MethodTable method_table; + + private: + + // + // prevent the compiler generating these unwanted functions + // + ExtensionModuleBase( const ExtensionModuleBase & ); //unimplemented + void operator=( const ExtensionModuleBase & ); //unimplemented + + }; + + extern "C" PyObject *method_keyword_call_handler( PyObject *_self_and_name_tuple, PyObject *_args, PyObject *_keywords ); + extern "C" PyObject *method_varargs_call_handler( PyObject *_self_and_name_tuple, PyObject *_args ); + extern "C" void do_not_dealloc( void * ); + + + template<TEMPLATE_TYPENAME T> + class ExtensionModule : public ExtensionModuleBase + { + public: + ExtensionModule( const char *name ) + : ExtensionModuleBase( name ) + {} + virtual ~ExtensionModule() + {} + + protected: + typedef Object (T::*method_varargs_function_t)( const Tuple &args ); + typedef Object (T::*method_keyword_function_t)( const Tuple &args, const Dict &kws ); + +#if defined( PYCXX_USING_HASH_MAP ) + typedef __PYCXX_HASHMAP_NAMESPACE::hash_map<std::string, MethodDefExt<T> *, __pycxx_str_hash_func> method_map_t; +#else + typedef std::map<std::string,MethodDefExt<T> *> method_map_t; +#endif + + static void add_varargs_method( const char *name, method_varargs_function_t function, const char *doc="" ) + { + method_map_t &mm = methods(); + + MethodDefExt<T> *method_definition = new MethodDefExt<T> + ( + name, + function, + method_varargs_call_handler, + doc + ); + + mm[std::string( name )] = method_definition; + } + + static void add_keyword_method( const char *name, method_keyword_function_t function, const char *doc="" ) + { + method_map_t &mm = methods(); + + MethodDefExt<T> *method_definition = new MethodDefExt<T> + ( + name, + function, + method_keyword_call_handler, + doc + ); + + mm[std::string( name )] = method_definition; + } + + void initialize( const char *module_doc="" ) + { + ExtensionModuleBase::initialize( module_doc ); + Dict dict( moduleDictionary() ); + + // + // put each of the methods into the modules dictionary + // so that we get called back at the function in T. + // + method_map_t &mm = methods(); + EXPLICIT_TYPENAME method_map_t::const_iterator i; + + for( i=mm.begin(); i != mm.end(); ++i ) + { + MethodDefExt<T> *method_definition = (*i).second; + + static PyObject *self = PyCObject_FromVoidPtr( this, do_not_dealloc ); + + Tuple args( 2 ); + args[0] = Object( self ); + args[1] = String( (*i).first ); + + PyObject *func = PyCFunction_New + ( + &method_definition->ext_meth_def, + new_reference_to( args ) + ); + + dict[ (*i).first ] = Object( func ); + } + } + + protected: // Tom Malcolmson reports that derived classes need access to these + + static method_map_t &methods(void) + { + static method_map_t *map_of_methods = NULL; + if( map_of_methods == NULL ) + map_of_methods = new method_map_t; + + return *map_of_methods; + } + + + // this invoke function must be called from within a try catch block + virtual Object invoke_method_keyword( const std::string &name, const Tuple &args, const Dict &keywords ) + { + method_map_t &mm = methods(); + MethodDefExt<T> *meth_def = mm[ name ]; + if( meth_def == NULL ) + { + std::string error_msg( "CXX - cannot invoke keyword method named " ); + error_msg += name; + throw RuntimeError( error_msg ); + } + + // cast up to the derived class + T *self = static_cast<T *>(this); + + return (self->*meth_def->ext_keyword_function)( args, keywords ); + } + + // this invoke function must be called from within a try catch block + virtual Object invoke_method_varargs( const std::string &name, const Tuple &args ) + { + method_map_t &mm = methods(); + MethodDefExt<T> *meth_def = mm[ name ]; + if( meth_def == NULL ) + { + std::string error_msg( "CXX - cannot invoke varargs method named " ); + error_msg += name; + throw RuntimeError( error_msg ); + } + + // cast up to the derived class + T *self = static_cast<T *>(this); + + return (self->*meth_def->ext_varargs_function)( args ); + } + + private: + // + // prevent the compiler generating these unwanted functions + // + ExtensionModule( const ExtensionModule<T> & ); //unimplemented + void operator=( const ExtensionModule<T> & ); //unimplemented + }; + + + class PythonType + { + public: + // if you define one sequence method you must define + // all of them except the assigns + + PythonType (size_t base_size, int itemsize, const char *default_name ); + virtual ~PythonType (); + + const char *getName () const; + const char *getDoc () const; + + PyTypeObject* type_object () const; + PythonType & name (const char* nam); + PythonType & doc (const char* d); + PythonType & dealloc(void (*f)(PyObject*)); + + PythonType & supportPrint(void); + PythonType & supportGetattr(void); + PythonType & supportSetattr(void); + PythonType & supportGetattro(void); + PythonType & supportSetattro(void); + PythonType & supportCompare(void); +#if PY_MAJOR_VERSION > 2 || (PY_MAJOR_VERSION == 2 && PY_MINOR_VERSION >= 1) + PythonType & supportRichCompare(void); +#endif + PythonType & supportRepr(void); + PythonType & supportStr(void); + PythonType & supportHash(void); + PythonType & supportCall(void); + PythonType & supportIter(void); + + PythonType & supportSequenceType(void); + PythonType & supportMappingType(void); + PythonType & supportNumberType(void); + PythonType & supportBufferType(void); + + protected: + PyTypeObject *table; + PySequenceMethods *sequence_table; + PyMappingMethods *mapping_table; + PyNumberMethods *number_table; + PyBufferProcs *buffer_table; + + void init_sequence(); + void init_mapping(); + void init_number(); + void init_buffer(); + + private: + // + // prevent the compiler generating these unwanted functions + // + PythonType (const PythonType& tb); // unimplemented + void operator=(const PythonType& t); // unimplemented + + }; // end of PythonType + + + + // Class PythonExtension is what you inherit from to create + // a new Python extension type. You give your class itself + // as the template paramter. + + // There are two ways that extension objects can get destroyed. + // 1. Their reference count goes to zero + // 2. Someone does an explicit delete on a pointer. + // In (1) the problem is to get the destructor called + // We register a special deallocator in the Python type object + // (see behaviors()) to do this. + // In (2) there is no problem, the dtor gets called. + + // PythonExtension does not use the usual Python heap allocator, + // instead using new/delete. We do the setting of the type object + // and reference count, usually done by PyObject_New, in the + // base class ctor. + + // This special deallocator does a delete on the pointer. + + + class PythonExtensionBase : public PyObject + { + public: + PythonExtensionBase(); + virtual ~PythonExtensionBase(); + + public: + virtual int print( FILE *, int ); + virtual Object getattr( const char * ) = 0; + virtual int setattr( const char *, const Object & ); + virtual Object getattro( const Object & ); + virtual int setattro( const Object &, const Object & ); + virtual int compare( const Object & ); + virtual Object rich_compare( const Object &, int op ); + virtual Object repr(); + virtual Object str(); + virtual long hash(); + virtual Object call( const Object &, const Object & ); + virtual Object iter(); + virtual PyObject* iternext(); + + // Sequence methods + virtual int sequence_length(); + virtual Object sequence_concat( const Object & ); + virtual Object sequence_repeat( Py_ssize_t ); + virtual Object sequence_item( Py_ssize_t ); + virtual Object sequence_slice( Py_ssize_t, Py_ssize_t ); + virtual int sequence_ass_item( Py_ssize_t, const Object & ); + virtual int sequence_ass_slice( Py_ssize_t, Py_ssize_t, const Object & ); + + // Mapping + virtual int mapping_length(); + virtual Object mapping_subscript( const Object & ); + virtual int mapping_ass_subscript( const Object &, const Object & ); + + // Number + virtual int number_nonzero(); + virtual Object number_negative(); + virtual Object number_positive(); + virtual Object number_absolute(); + virtual Object number_invert(); + virtual Object number_int(); + virtual Object number_float(); + virtual Object number_long(); + virtual Object number_oct(); + virtual Object number_hex(); + virtual Object number_add( const Object & ); + virtual Object number_subtract( const Object & ); + virtual Object number_multiply( const Object & ); + virtual Object number_divide( const Object & ); + virtual Object number_remainder( const Object & ); + virtual Object number_divmod( const Object & ); + virtual Object number_lshift( const Object & ); + virtual Object number_rshift( const Object & ); + virtual Object number_and( const Object & ); + virtual Object number_xor( const Object & ); + virtual Object number_or( const Object & ); + virtual Object number_power( const Object &, const Object & ); + + // Buffer + virtual Py_ssize_t buffer_getreadbuffer( Py_ssize_t, void** ); + virtual Py_ssize_t buffer_getwritebuffer( Py_ssize_t, void** ); + virtual Py_ssize_t buffer_getsegcount( Py_ssize_t* ); + + private: + void missing_method( void ); + static PyObject *method_call_handler( PyObject *self, PyObject *args ); + }; + + template<TEMPLATE_TYPENAME T> + class PythonExtension: public PythonExtensionBase + { + public: + static PyTypeObject* type_object() + { + return behaviors().type_object(); + } + + static int check( PyObject *p ) + { + // is p like me? + return p->ob_type == type_object(); + } + + static int check( const Object& ob ) + { + return check( ob.ptr()); + } + + + // + // every object needs getattr implemented + // to support methods + // + virtual Object getattr( const char *name ) + { + return getattr_methods( name ); + } + + protected: + explicit PythonExtension() + : PythonExtensionBase() + { + #ifdef PyObject_INIT + (void)PyObject_INIT( this, type_object() ); + #else + ob_refcnt = 1; + ob_type = type_object(); + #endif + + // every object must support getattr + behaviors().supportGetattr(); + } + + virtual ~PythonExtension() + {} + + static PythonType &behaviors() + { + static PythonType* p; + if( p == NULL ) + { +#if defined( _CPPRTTI ) || defined(__GNUG__) + const char *default_name = (typeid ( T )).name(); +#else + const char *default_name = "unknown"; +#endif + p = new PythonType( sizeof( T ), 0, default_name ); + p->dealloc( extension_object_deallocator ); + } + + return *p; + } + + + typedef Object (T::*method_varargs_function_t)( const Tuple &args ); + typedef Object (T::*method_keyword_function_t)( const Tuple &args, const Dict &kws ); + +#if defined( PYCXX_USING_HASH_MAP ) + typedef __PYCXX_HASHMAP_NAMESPACE::hash_map<std::string, MethodDefExt<T> *, __pycxx_str_hash_func> method_map_t; +#else + typedef std::map<std::string,MethodDefExt<T> *> method_map_t; +#endif + + // support the default attributes, __name__, __doc__ and methods + virtual Object getattr_default( const char *_name ) + { + std::string name( _name ); + + if( name == "__name__" && type_object()->tp_name != NULL ) + { + return Py::String( type_object()->tp_name ); + } + if( name == "__doc__" && type_object()->tp_doc != NULL ) + { + return Py::String( type_object()->tp_doc ); + } + +// trying to fake out being a class for help() +// else if( name == "__bases__" ) +// { +// return Py::Tuple(0); +// } +// else if( name == "__module__" ) +// { +// return Py::Nothing(); +// } +// else if( name == "__dict__" ) +// { +// return Py::Dict(); +// } + + return getattr_methods( _name ); + } + + // turn a name into function object + virtual Object getattr_methods( const char *_name ) + { + std::string name( _name ); + + method_map_t &mm = methods(); + + EXPLICIT_TYPENAME method_map_t::const_iterator i; + + if( name == "__methods__" ) + { + List methods; + + for( i = mm.begin(); i != mm.end(); ++i ) + methods.append( String( (*i).first ) ); + + return methods; + } + + // see if name exists and get entry with method + i = mm.find( name ); + if( i == mm.end() ) + throw AttributeError( name ); + + Tuple self( 2 ); + + self[0] = Object( this ); + self[1] = String( name ); + + MethodDefExt<T> *method_definition = i->second; + + PyObject *func = PyCFunction_New( &method_definition->ext_meth_def, self.ptr() ); + + return Object(func, true); + } + + static void add_varargs_method( const char *name, method_varargs_function_t function, const char *doc="" ) + { + method_map_t &mm = methods(); + + // check that all methods added are unique + EXPLICIT_TYPENAME method_map_t::const_iterator i; + i = mm.find( name ); + if( i != mm.end() ) + throw AttributeError( name ); + + MethodDefExt<T> *method_definition = new MethodDefExt<T> + ( + name, + function, + method_varargs_call_handler, + doc + ); + + mm[std::string( name )] = method_definition; + } + + static void add_keyword_method( const char *name, method_keyword_function_t function, const char *doc="" ) + { + method_map_t &mm = methods(); + + // check that all methods added are unique + EXPLICIT_TYPENAME method_map_t::const_iterator i; + i = mm.find( name ); + if( i != mm.end() ) + throw AttributeError( name ); + + MethodDefExt<T> *method_definition = new MethodDefExt<T> + ( + name, + function, + method_keyword_call_handler, + doc + ); + + mm[std::string( name )] = method_definition; + } + + private: + static method_map_t &methods(void) + { + static method_map_t *map_of_methods = NULL; + if( map_of_methods == NULL ) + map_of_methods = new method_map_t; + + return *map_of_methods; + } + + static PyObject *method_keyword_call_handler( PyObject *_self_and_name_tuple, PyObject *_args, PyObject *_keywords ) + { + try + { + Tuple self_and_name_tuple( _self_and_name_tuple ); + + PyObject *self_in_cobject = self_and_name_tuple[0].ptr(); + T *self = static_cast<T *>( self_in_cobject ); + + String name( self_and_name_tuple[1] ); + + method_map_t &mm = methods(); + + EXPLICIT_TYPENAME method_map_t::const_iterator i; + i = mm.find( name ); + if( i == mm.end() ) + return 0; + + MethodDefExt<T> *meth_def = i->second; + + Tuple args( _args ); + + // _keywords may be NULL so be careful about the way the dict is created + Dict keywords; + if( _keywords != NULL ) + keywords = Dict( _keywords ); + + Object result( (self->*meth_def->ext_keyword_function)( args, keywords ) ); + + return new_reference_to( result.ptr() ); + } + catch( Exception & ) + { + return 0; + } + } + + static PyObject *method_varargs_call_handler( PyObject *_self_and_name_tuple, PyObject *_args ) + { + try + { + Tuple self_and_name_tuple( _self_and_name_tuple ); + + PyObject *self_in_cobject = self_and_name_tuple[0].ptr(); + T *self = static_cast<T *>( self_in_cobject ); + + String name( self_and_name_tuple[1] ); + + method_map_t &mm = methods(); + + EXPLICIT_TYPENAME method_map_t::const_iterator i; + i = mm.find( name ); + if( i == mm.end() ) + return 0; + + MethodDefExt<T> *meth_def = i->second; + + Tuple args( _args ); + + Object result; + + // TMM: 7Jun'01 - Adding try & catch in case of STL debug-mode exceptions. + #ifdef _STLP_DEBUG + try + { + result = (self->*meth_def->ext_varargs_function)( args ); + } + catch (std::__stl_debug_exception) + { + // throw cxx::RuntimeError( sErrMsg ); + throw cxx::RuntimeError( "Error message not set yet." ); + } + #else + result = (self->*meth_def->ext_varargs_function)( args ); + #endif // _STLP_DEBUG + + return new_reference_to( result.ptr() ); + } + catch( Exception & ) + { + return 0; + } + } + + static void extension_object_deallocator ( PyObject* t ) + { + delete (T *)( t ); + } + + // + // prevent the compiler generating these unwanted functions + // + explicit PythonExtension( const PythonExtension<T>& other ); + void operator=( const PythonExtension<T>& rhs ); + }; + + // + // ExtensionObject<T> is an Object that will accept only T's. + // + template<TEMPLATE_TYPENAME T> + class ExtensionObject: public Object + { + public: + + explicit ExtensionObject ( PyObject *pyob ) + : Object( pyob ) + { + validate(); + } + + ExtensionObject( const ExtensionObject<T>& other ) + : Object( *other ) + { + validate(); + } + + ExtensionObject( const Object& other ) + : Object( *other ) + { + validate(); + } + + ExtensionObject& operator= ( const Object& rhs ) + { + return (*this = *rhs ); + } + + ExtensionObject& operator= ( PyObject* rhsp ) + { + if( ptr() == rhsp ) + return *this; + set( rhsp ); + return *this; + } + + virtual bool accepts ( PyObject *pyob ) const + { + return ( pyob && T::check( pyob )); + } + + // + // Obtain a pointer to the PythonExtension object + // + T *extensionObject(void) + { + return static_cast<T *>( ptr() ); + } + }; + +} // Namespace Py +// End of CXX_Extensions.h +#endif Added: trunk/matplotlib/CXX/IndirectPythonInterface.cxx =================================================================== --- trunk/matplotlib/CXX/IndirectPythonInterface.cxx (rev 0) +++ trunk/matplotlib/CXX/IndirectPythonInterface.cxx 2010年01月16日 23:01:21 UTC (rev 8087) @@ -0,0 +1,597 @@ +//----------------------------------------------------------------------------- +// +// Copyright (c) 1998 - 2007, The Regents of the University of California +// Produced at the Lawrence Livermore National Laboratory +// All rights reserved. +// +// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The +// full copyright notice is contained in the file COPYRIGHT located at the root +// of the PyCXX distribution. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// - Redistributions of source code must retain the above copyright notice, +// this list of conditions and the disclaimer below. +// - Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the disclaimer (as noted below) in the +// documentation and/or materials provided with the distribution. +// - Neither the name of the UC/LLNL nor the names of its contributors may be +// used to endorse or promote products derived from this software without +// specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF +// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR +// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH +// DAMAGE. +// +//----------------------------------------------------------------------------- + +#include "CXX/IndirectPythonInterface.hxx" + +namespace Py +{ +bool _Buffer_Check( PyObject *op ) { return (op)->ob_type == _Buffer_Type(); } +bool _CFunction_Check( PyObject *op ) { return (op)->ob_type == _CFunction_Type(); } +bool _Class_Check( PyObject *op ) { return (op)->ob_type == _Class_Type(); } +bool _CObject_Check( PyObject *op ) { return (op)->ob_type == _CObject_Type(); } +bool _Complex_Check( PyObject *op ) { return (op)->ob_type == _Complex_Type(); } +bool _Dict_Check( PyObject *op ) { return (op)->ob_type == _Dict_Type(); } +bool _File_Check( PyObject *op ) { return (op)->ob_type == _File_Type(); } +bool _Float_Check( PyObject *op ) { return (op)->ob_type == _Float_Type(); } +bool _Function_Check( PyObject *op ) { return (op)->ob_type == _Function_Type(); } +bool _Instance_Check( PyObject *op ) { return (op)->ob_type == _Instance_Type(); } +bool _Boolean_Check( PyObject *op ) { return (op)->ob_type == _Bool_Type(); } +bool _Int_Check( PyObject *op ) { return (op)->ob_type == _Int_Type(); } +bool _List_Check( PyObject *o ) { return o->ob_type == _List_Type(); } +bool _Long_Check( PyObject *op ) { return (op)->ob_type == _Long_Type(); } +bool _Method_Check( PyObject *op ) { return (op)->ob_type == _Method_Type(); } +bool _Module_Check( PyObject *op ) { return (op)->ob_type == _Module_Type(); } +bool _Range_Check( PyObject *op ) { return (op)->ob_type == _Range_Type(); } +bool _Slice_Check( PyObject *op ) { return (op)->ob_type == _Slice_Type(); } +bool _String_Check( PyObject *o ) { return o->ob_type == _String_Type(); } +bool _TraceBack_Check( PyObject *v ) { return (v)->ob_type == _TraceBack_Type(); } +bool _Tuple_Check( PyObject *op ) { return (op)->ob_type == _Tuple_Type(); } +bool _Type_Check( PyObject *op ) { return (op)->ob_type == _Type_Type(); } + +#if PY_MAJOR_VERSION >= 2 +bool _Unicode_Check( PyObject *op ) { return (op)->ob_type == _Unicode_Type(); } +#endif + + + +#if defined(PY_WIN32_DELAYLOAD_PYTHON_DLL) + +#if defined(MS_WINDOWS) +#include <windows.h> + + +static HMODULE python_dll; + +static PyObject *ptr__Exc_ArithmeticError = NULL; +static PyObject *ptr__Exc_AssertionError = NULL; +static PyObject *ptr__Exc_AttributeError = NULL; +static PyObject *ptr__Exc_EnvironmentError = NULL; +static PyObject *ptr__Exc_EOFError = NULL; +static PyObject *ptr__Exc_Exception = NULL; +static PyObject *ptr__Exc_FloatingPointError = NULL; +static PyObject *ptr__Exc_ImportError = NULL; +static PyObject *ptr__Exc_IndexError = NULL; +static PyObject *ptr__Exc_IOError = NULL; +static PyObject *ptr__Exc_KeyboardInterrupt = NULL; +static PyObject *ptr__Exc_KeyError = NULL; +static PyObject *ptr__Exc_LookupError = NULL; +static PyObject *ptr__Exc_MemoryError = NULL; +static PyObject *ptr__Exc_MemoryErrorInst = NULL; +static PyObject *ptr__Exc_NameError = NULL; +static PyObject *ptr__Exc_NotImplementedError = NULL; +static PyObject *ptr__Exc_OSError = NULL; +static PyObject *ptr__Exc_OverflowError = NULL; +static PyObject *ptr__Exc_RuntimeError = NULL; +static PyObject *ptr__Exc_StandardError = NULL; +static PyObject *ptr__Exc_SyntaxError = NULL; +static PyObject *ptr__Exc_SystemError = NULL; +static PyObject *ptr__Exc_SystemExit = NULL; +static PyObject *ptr__Exc_TypeError = NULL; +static PyObject *ptr__Exc_ValueError = NULL; +static PyObject *ptr__Exc_ZeroDivisionError = NULL; + +#ifdef MS_WINDOWS +static PyObject *ptr__Exc_WindowsError = NULL; +#endif + +#if PY_MAJOR_VERSION >= 2 +static PyObject *ptr__Exc_IndentationError = NULL; +static PyObject *ptr__Exc_TabError = NULL; +static PyObject *ptr__Exc_UnboundLocalError = NULL; +static PyObject *ptr__Exc_UnicodeError = NULL; +#endif + +static PyObject *ptr__PyNone = NULL; + +static PyObject *ptr__PyFalse = NULL; +static PyObject *ptr__PyTrue = NULL; + +static PyTypeObject *ptr__Buffer_Type = NULL; +static PyTypeObject *ptr__CFunction_Type = NULL; +static PyTypeObject *ptr__Class_Type = NULL; +static PyTypeObject *ptr__CObject_Type = NULL; +static PyTypeObject *ptr__Complex_Type = NULL; +static PyTypeObject *ptr__Dict_Type = NULL; +static PyTypeObject *ptr__File_Type = NULL; +static PyTypeObject *ptr__Float_Type = NULL; +static PyTypeObject *ptr__Function_Type = NULL; +static PyTypeObject *ptr__Instance_Type = NULL; +static PyTypeObject *ptr__Int_Type = NULL; +static PyTypeObject *ptr__List_Type = NULL; +static PyTypeObject *ptr__Long_Type = NULL; +static PyTypeObject *ptr__Method_Type = NULL; +static PyTypeObject *ptr__Module_Type = NULL; +static PyTypeObject *ptr__Range_Type = NULL; +static PyTypeObject *ptr__Slice_Type = NULL; +static PyTypeObject *ptr__String_Type = NULL; +static PyTypeObject *ptr__TraceBack_Type = NULL; +static PyTypeObject *ptr__Tuple_Type = NULL; +static PyTypeObject *ptr__Type_Type = NULL; + +#if PY_MAJOR_VERSION >= 2 +static PyTypeObject *ptr__Unicode_Type = NULL; +#endif + +static int *ptr_Py_DebugFlag = NULL; +static int *ptr_Py_InteractiveFlag = NULL; +static int *ptr_Py_OptimizeFlag = NULL; +static int *ptr_Py_NoSiteFlag = NULL; +static int *ptr_Py_TabcheckFlag = NULL; +static int *ptr_Py_VerboseFlag = NULL; + +#if PY_MAJOR_VERSION >= 2 +static int *ptr_Py_UnicodeFlag = NULL; +#endif + +static char **ptr__Py_PackageContext = NULL; + +#ifdef Py_REF_DEBUG +int *ptr_Py_RefTotal; +#endif + + +//-------------------------------------------------------------------------------- +class GetAddressException +{ +public: + GetAddressException( const char *_name ) + : name( _name ) + {} + virtual ~GetAddressException() {} + const char *name; +}; + + +//-------------------------------------------------------------------------------- +static PyObject *GetPyObjectPointer_As_PyObjectPointer( const char *name ) +{ + FARPROC addr = GetProcAddress( python_dll, name ); + if( addr == NULL ) + throw GetAddressException( name ); + + return *(PyObject **)addr; +} + +static PyObject *GetPyObject_As_PyObjectPointer( const char *name ) +{ + FARPROC addr = GetProcAddress( python_dll, name ); + if( addr == NULL ) + throw GetAddressException( name ); + + return (PyObject *)addr; +} + +static PyTypeObject *GetPyTypeObjectPointer_As_PyTypeObjectPointer( const char *name ) +{ + FARPROC addr = GetProcAddress( python_dll, name ); + if( addr == NULL ) + throw GetAddressException( name ); + + return *(PyTypeObject **)addr; +} + +static PyTypeObject *GetPyTypeObject_As_PyTypeObjectPointer( const char *name ) +{ + FARPROC addr = GetProcAddress( python_dll, name ); + if( addr == NULL ) + throw GetAddressException( name ); + + return (PyTypeObject *)addr; +} + +static int *GetInt_as_IntPointer( const char *name ) +{ + FARPROC addr = GetProcAddress( python_dll, name ); + if( addr == NULL ) + throw GetAddressException( name ); + + return (int *)addr; +} + +static char **GetCharPointer_as_CharPointerPointer( const char *name ) +{ + FARPROC addr = GetProcAddress( python_dll, name ); + if( addr == NULL ) + throw GetAddressException( name ); + + return (char **)addr; +} + + +#ifdef _DEBUG +static const char python_dll_name_format[] = "PYTHON%1.1d%1.1d_D.DLL"; +#else +static const char python_dll_name_format[] = "PYTHON%1.1d%1.1d.DLL"; +#endif + +//-------------------------------------------------------------------------------- +bool InitialisePythonIndirectInterface() +{ + char python_dll_name[sizeof(python_dll_name_format)]; + + sprintf( python_dll_name, python_dll_name_format, PY_MAJOR_VERSION, PY_MINOR_VERSION ); + + python_dll = LoadLibrary( python_dll_name ); + if( python_dll == NULL ) + return false; + + try +{ +#ifdef Py_REF_DEBUG + ptr_Py_RefTotal = GetInt_as_IntPointer( "_Py_RefTotal" ); +#endif + ptr_Py_DebugFlag = GetInt_as_IntPointer( "Py_DebugFlag" ); + ptr_Py_InteractiveFlag = GetInt_as_IntPointer( "Py_InteractiveFlag" ); + ptr_Py_OptimizeFlag = GetInt_as_IntPointer( "Py_OptimizeFlag" ); + ptr_Py_NoSiteFlag = GetInt_as_IntPointer( "Py_NoSiteFlag" ); + ptr_Py_TabcheckFlag = GetInt_as_IntPointer( "Py_TabcheckFlag" ); + ptr_Py_VerboseFlag = GetInt_as_IntPointer( "Py_VerboseFlag" ); +#if PY_MAJOR_VERSION >= 2 + ptr_Py_UnicodeFlag = GetInt_as_IntPointer( "Py_UnicodeFlag" ); +#endif + ptr__Py_PackageContext = GetCharPointer_as_CharPointerPointer( "_Py_PackageContext" ); + + ptr__Exc_ArithmeticError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ArithmeticError" ); + ptr__Exc_AssertionError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_AssertionError" ); + ptr__Exc_AttributeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_AttributeError" ); + ptr__Exc_EnvironmentError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_EnvironmentError" ); + ptr__Exc_EOFError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_EOFError" ); + ptr__Exc_Exception = GetPyObjectPointer_As_PyObjectPointer( "PyExc_Exception" ); + ptr__Exc_FloatingPointError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_FloatingPointError" ); + ptr__Exc_ImportError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ImportError" ); + ptr__Exc_IndexError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_IndexError" ); + ptr__Exc_IOError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_IOError" ); + ptr__Exc_KeyboardInterrupt = GetPyObjectPointer_As_PyObjectPointer( "PyExc_KeyboardInterrupt" ); + ptr__Exc_KeyError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_KeyError" ); + ptr__Exc_LookupError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_LookupError" ); + ptr__Exc_MemoryError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_MemoryError" ); + ptr__Exc_MemoryErrorInst = GetPyObjectPointer_As_PyObjectPointer( "PyExc_MemoryErrorInst" ); + ptr__Exc_NameError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_NameError" ); + ptr__Exc_NotImplementedError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_NotImplementedError" ); + ptr__Exc_OSError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_OSError" ); + ptr__Exc_OverflowError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_OverflowError" ); + ptr__Exc_RuntimeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_RuntimeError" ); + ptr__Exc_StandardError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_StandardError" ); + ptr__Exc_SyntaxError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_SyntaxError" ); + ptr__Exc_SystemError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_SystemError" ); + ptr__Exc_SystemExit = GetPyObjectPointer_As_PyObjectPointer( "PyExc_SystemExit" ); + ptr__Exc_TypeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_TypeError" ); + ptr__Exc_ValueError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ValueError" ); +#ifdef MS_WINDOWS + ptr__Exc_WindowsError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_WindowsError" ); +#endif + ptr__Exc_ZeroDivisionError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ZeroDivisionError" ); + +#if PY_MAJOR_VERSION >= 2 + ptr__Exc_IndentationError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_IndentationError" ); + ptr__Exc_TabError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_TabError" ); + ptr__Exc_UnboundLocalError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_UnboundLocalError" ); + ptr__Exc_UnicodeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_UnicodeError" ); +#endif + ptr__PyNone = GetPyObject_As_PyObjectPointer( "_Py_NoneStruct" ); + + ptr__PyFalse = GetPyObject_As_PyObjectPointer( "_Py_ZeroStruct" ); + ptr__PyTrue = GetPyObject_As_PyObjectPointer( "_Py_TrueStruct" ); + + ptr__Buffer_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyBuffer_Type" ); + ptr__CFunction_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyCFunction_Type" ); + ptr__Class_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyClass_Type" ); + ptr__CObject_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyCObject_Type" ); + ptr__Complex_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyComplex_Type" ); + ptr__Dict_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyDict_Type" ); + ptr__File_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyFile_Type" ); + ptr__Float_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyFloat_Type" ); + ptr__Function_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyFunction_Type" ); + ptr__Instance_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyInstance_Type" ); + ptr__Int_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyInt_Type" ); + ptr__List_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyList_Type" ); + ptr__Long_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyLong_Type" ); + ptr__Method_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyMethod_Type" ); + ptr__Module_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyModule_Type" ); + ptr__Range_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyRange_Type" ); + ptr__Slice_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PySlice_Type" ); + ptr__String_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyString_Type" ); + ptr__TraceBack_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyTraceBack_Type" ); + ptr__Tuple_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyTuple_Type" ); + ... [truncated message content]
Revision: 8086 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8086&view=rev Author: jdh2358 Date: 2010年01月16日 23:00:27 +0000 (2010年1月16日) Log Message: ----------- move cxx6 Added Paths: ----------- trunk/matplotlib/CXX64/ Removed Paths: ------------- trunk/matplotlib/CXX/ This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8085 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8085&view=rev Author: jdh2358 Date: 2010年01月16日 22:08:25 +0000 (2010年1月16日) Log Message: ----------- remove cxx emacs backupfiles Removed Paths: ------------- trunk/matplotlib/CXX/IndirectPythonInterface.cxx~ trunk/matplotlib/CXX/cxxextensions.c~ trunk/matplotlib/CXX/cxxsupport.cxx~ Deleted: trunk/matplotlib/CXX/IndirectPythonInterface.cxx~ =================================================================== --- trunk/matplotlib/CXX/IndirectPythonInterface.cxx~ 2010年01月16日 22:07:53 UTC (rev 8084) +++ trunk/matplotlib/CXX/IndirectPythonInterface.cxx~ 2010年01月16日 22:08:25 UTC (rev 8085) @@ -1,43 +0,0 @@ -//----------------------------------------------------------------------------- -// -// Copyright (c) 1998 - 2007, The Regents of the University of California -// Produced at the Lawrence Livermore National Laboratory -// All rights reserved. -// -// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The -// full copyright notice is contained in the file COPYRIGHT located at the root -// of the PyCXX distribution. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are met: -// -// - Redistributions of source code must retain the above copyright notice, -// this list of conditions and the disclaimer below. -// - Redistributions in binary form must reproduce the above copyright notice, -// this list of conditions and the disclaimer (as noted below) in the -// documentation and/or materials provided with the distribution. -// - Neither the name of the UC/LLNL nor the names of its contributors may be -// used to endorse or promote products derived from this software without -// specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" -// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF -// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR -// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR -// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER -// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH -// DAMAGE. -// -//----------------------------------------------------------------------------- -#include "CXX/WrapPython.h" - -#if PY_MAJOR_VERSION == 2 -#include "Src/Python2/IndirectPythonInterface.cxx" -#else -#include "Src/Python3/IndirectPythonInterface.cxx" -#endif Deleted: trunk/matplotlib/CXX/cxxextensions.c~ =================================================================== --- trunk/matplotlib/CXX/cxxextensions.c~ 2010年01月16日 22:07:53 UTC (rev 8084) +++ trunk/matplotlib/CXX/cxxextensions.c~ 2010年01月16日 22:08:25 UTC (rev 8085) @@ -1,43 +0,0 @@ -//----------------------------------------------------------------------------- -// -// Copyright (c) 1998 - 2007, The Regents of the University of California -// Produced at the Lawrence Livermore National Laboratory -// All rights reserved. -// -// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The -// full copyright notice is contained in the file COPYRIGHT located at the root -// of the PyCXX distribution. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are met: -// -// - Redistributions of source code must retain the above copyright notice, -// this list of conditions and the disclaimer below. -// - Redistributions in binary form must reproduce the above copyright notice, -// this list of conditions and the disclaimer (as noted below) in the -// documentation and/or materials provided with the distribution. -// - Neither the name of the UC/LLNL nor the names of its contributors may be -// used to endorse or promote products derived from this software without -// specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" -// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF -// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR -// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR -// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER -// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH -// DAMAGE. -// -//----------------------------------------------------------------------------- -#include "CXX/WrapPython.h" - -#if PY_MAJOR_VERSION == 2 -#include "Src/Python2/cxxextensions.c" -#else -#include "Src/Python3/cxxextensions.c" -#endif Deleted: trunk/matplotlib/CXX/cxxsupport.cxx~ =================================================================== --- trunk/matplotlib/CXX/cxxsupport.cxx~ 2010年01月16日 22:07:53 UTC (rev 8084) +++ trunk/matplotlib/CXX/cxxsupport.cxx~ 2010年01月16日 22:08:25 UTC (rev 8085) @@ -1,43 +0,0 @@ -//----------------------------------------------------------------------------- -// -// Copyright (c) 1998 - 2007, The Regents of the University of California -// Produced at the Lawrence Livermore National Laboratory -// All rights reserved. -// -// This file is part of PyCXX. For details,see http://cxx.sourceforge.net/. The -// full copyright notice is contained in the file COPYRIGHT located at the root -// of the PyCXX distribution. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are met: -// -// - Redistributions of source code must retain the above copyright notice, -// this list of conditions and the disclaimer below. -// - Redistributions in binary form must reproduce the above copyright notice, -// this list of conditions and the disclaimer (as noted below) in the -// documentation and/or materials provided with the distribution. -// - Neither the name of the UC/LLNL nor the names of its contributors may be -// used to endorse or promote products derived from this software without -// specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" -// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -// ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OF THE UNIVERSITY OF -// CALIFORNIA, THE U.S. DEPARTMENT OF ENERGY OR CONTRIBUTORS BE LIABLE FOR -// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR -// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER -// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH -// DAMAGE. -// -//----------------------------------------------------------------------------- -#include "CXX/WrapPython.h" - -#if PY_MAJOR_VERSION == 2 -#include "Src/Python2/cxxsupport.cxx" -#else -#include "Src/Python3/cxxsupport.cxx" -#endif This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8084 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8084&view=rev Author: jdh2358 Date: 2010年01月16日 22:07:53 +0000 (2010年1月16日) Log Message: ----------- upgraded CXX to 6.1.1 Modified Paths: -------------- trunk/matplotlib/CHANGELOG trunk/matplotlib/CXX/Config.hxx trunk/matplotlib/CXX/Exception.hxx trunk/matplotlib/CXX/Extensions.hxx trunk/matplotlib/CXX/IndirectPythonInterface.cxx trunk/matplotlib/CXX/IndirectPythonInterface.hxx trunk/matplotlib/CXX/Objects.hxx trunk/matplotlib/CXX/Version.hxx trunk/matplotlib/CXX/WrapPython.h trunk/matplotlib/CXX/cxx_extensions.cxx trunk/matplotlib/CXX/cxxextensions.c trunk/matplotlib/CXX/cxxsupport.cxx Added Paths: ----------- trunk/matplotlib/CXX/IndirectPythonInterface.cxx~ trunk/matplotlib/CXX/Python2/ trunk/matplotlib/CXX/Python2/Config.hxx trunk/matplotlib/CXX/Python2/CxxDebug.hxx trunk/matplotlib/CXX/Python2/Exception.hxx trunk/matplotlib/CXX/Python2/ExtensionModule.hxx trunk/matplotlib/CXX/Python2/ExtensionOldType.hxx trunk/matplotlib/CXX/Python2/ExtensionType.hxx trunk/matplotlib/CXX/Python2/ExtensionTypeBase.hxx trunk/matplotlib/CXX/Python2/Extensions.hxx trunk/matplotlib/CXX/Python2/IndirectPythonInterface.cxx trunk/matplotlib/CXX/Python2/IndirectPythonInterface.hxx trunk/matplotlib/CXX/Python2/Objects.hxx trunk/matplotlib/CXX/Python2/PythonType.hxx trunk/matplotlib/CXX/Python2/cxx_extensions.cxx trunk/matplotlib/CXX/Python2/cxxextensions.c trunk/matplotlib/CXX/Python2/cxxsupport.cxx trunk/matplotlib/CXX/Python3/ trunk/matplotlib/CXX/Python3/Config.hxx trunk/matplotlib/CXX/Python3/CxxDebug.hxx trunk/matplotlib/CXX/Python3/Exception.hxx trunk/matplotlib/CXX/Python3/ExtensionModule.hxx trunk/matplotlib/CXX/Python3/ExtensionOldType.hxx trunk/matplotlib/CXX/Python3/ExtensionType.hxx trunk/matplotlib/CXX/Python3/ExtensionTypeBase.hxx trunk/matplotlib/CXX/Python3/Extensions.hxx trunk/matplotlib/CXX/Python3/IndirectPythonInterface.cxx trunk/matplotlib/CXX/Python3/IndirectPythonInterface.hxx trunk/matplotlib/CXX/Python3/Objects.hxx trunk/matplotlib/CXX/Python3/PythonType.hxx trunk/matplotlib/CXX/Python3/cxx_extensions.cxx trunk/matplotlib/CXX/Python3/cxxextensions.c trunk/matplotlib/CXX/Python3/cxxsupport.cxx trunk/matplotlib/CXX/cxxextensions.c~ trunk/matplotlib/CXX/cxxsupport.cxx~ Modified: trunk/matplotlib/CHANGELOG =================================================================== --- trunk/matplotlib/CHANGELOG 2010年01月16日 19:20:03 UTC (rev 8083) +++ trunk/matplotlib/CHANGELOG 2010年01月16日 22:07:53 UTC (rev 8084) @@ -1,3 +1,6 @@ + +2010年01月16日 Upgraded CXX to 6.1.1 - JDH + 2009年01月16日 Don't create minor ticks on top of existing major ticks. Patch by Neil Crighton. -ADS @@ -17,6 +20,7 @@ 2009年01月11日 Add add_click and pop_click methods in BlockingContourLabeler. -JJL + 2010年01月03日 Added rcParams['axes.color_cycle'] - EF 2010年01月03日 Added Pierre's qt4 formlayout editor and toolbar button - JDH Modified: trunk/matplotlib/CXX/Config.hxx =================================================================== --- trunk/matplotlib/CXX/Config.hxx 2010年01月16日 19:20:03 UTC (rev 8083) +++ trunk/matplotlib/CXX/Config.hxx 2010年01月16日 22:07:53 UTC (rev 8084) @@ -34,101 +34,10 @@ // DAMAGE. // //----------------------------------------------------------------------------- +#include "CXX/WrapPython.h" -#ifndef __PyCXX_config_hh__ -#define __PyCXX_config_hh__ - -// -// Microsoft VC++ 6.0 has no traits -// -#if defined( _MSC_VER ) - -# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 1 - -#elif defined( __GNUC__ ) -# if __GNUC__ >= 3 -# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 1 -# else -# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 0 -#endif - -// -// Assume all other compilers do -// +#if PY_MAJOR_VERSION == 2 +#include "CXX/Python2/Config.hxx" #else - -// Macros to deal with deficiencies in compilers -# define STANDARD_LIBRARY_HAS_ITERATOR_TRAITS 1 +#include "CXX/Python3/Config.hxx" #endif - -#if STANDARD_LIBRARY_HAS_ITERATOR_TRAITS -# define random_access_iterator_parent(itemtype) std::iterator<std::random_access_iterator_tag,itemtype,int> -#else -# define random_access_iterator_parent(itemtype) std::random_access_iterator<itemtype, int> -#endif - -// -// Which C++ standard is in use? -// -#if defined( _MSC_VER ) -# if _MSC_VER <= 1200 -// MSVC++ 6.0 -# define PYCXX_ISO_CPP_LIB 0 -# define STR_STREAM <strstream> -# define TEMPLATE_TYPENAME class -# else -# define PYCXX_ISO_CPP_LIB 1 -# define STR_STREAM <sstream> -# define TEMPLATE_TYPENAME typename -# endif -#elif defined( __GNUC__ ) -# if __GNUC__ >= 3 -# define PYCXX_ISO_CPP_LIB 1 -# define STR_STREAM <sstream> -# define TEMPLATE_TYPENAME typename -# else -# define PYCXX_ISO_CPP_LIB 0 -# define STR_STREAM <strstream> -# define TEMPLATE_TYPENAME class -# endif -#endif - -#if PYCXX_ISO_CPP_LIB -# define STR_STREAM <sstream> -# define OSTRSTREAM ostringstream -# define EXPLICIT_TYPENAME typename -# define EXPLICIT_CLASS class -# define TEMPLATE_TYPENAME typename -#else -# define STR_STREAM <strstream> -# define OSTRSTREAM ostrstream -# define EXPLICIT_TYPENAME -# define EXPLICIT_CLASS -# define TEMPLATE_TYPENAME class -#endif - -// before 2.5 Py_ssize_t was missing -#ifndef PY_MAJOR_VERSION -#error not defined PY_MAJOR_VERSION -#endif -#if PY_MAJOR_VERSION < 2 || (PY_MAJOR_VERSION == 2 && PY_MINOR_VERSION < 5) -typedef int Py_ssize_t; -#endif - -// hash_map container usage selection -// 1) if PYCXX_USING_STD_MAP is defined PyCXX will be using std::map<> container -// implementation only. -// 2) if compilers are used other than MS Visual Studio (7.1+) or GCC 3.x -// STANDARD_LIBRARY_HAS_HASH_MAP must be defined before compilation to -// make PyCXX using hash_map container. -#if !defined( PYCXX_USING_STD_MAP ) - #if defined( _MSC_VER ) || defined( __INTEL_COMPILER ) || defined ( __ICC ) || (defined( __GNUC__ ) && ( __GNUC__ > 3 )) - # define PYCXX_USING_HASH_MAP - #else - # if defined( STANDARD_LIBRARY_HAS_HASH_MAP ) && !defined( PYCXX_USING_HASH_MAP ) - # define PYCXX_USING_HASH_MAP - # endif - #endif -#endif - -#endif // __PyCXX_config_hh__ Modified: trunk/matplotlib/CXX/Exception.hxx =================================================================== --- trunk/matplotlib/CXX/Exception.hxx 2010年01月16日 19:20:03 UTC (rev 8083) +++ trunk/matplotlib/CXX/Exception.hxx 2010年01月16日 22:07:53 UTC (rev 8084) @@ -34,216 +34,10 @@ // DAMAGE. // //----------------------------------------------------------------------------- - -#ifndef __CXX_Exception_h -#define __CXX_Exception_h - #include "CXX/WrapPython.h" -#include "CXX/Version.hxx" -#include "CXX/Config.hxx" -#include "CXX/IndirectPythonInterface.hxx" -#include <string> -#include <iostream> - -// This mimics the Python structure, in order to minimize confusion -namespace Py -{ - class ExtensionExceptionType; - - class Object; - - class Exception - { - public: - Exception( ExtensionExceptionType &exception, const std::string& reason ); - Exception( ExtensionExceptionType &exception, Object &reason ); - - explicit Exception () - {} - - Exception (const std::string& reason) - { - PyErr_SetString (Py::_Exc_RuntimeError(), reason.c_str()); - } - - Exception (PyObject* exception, const std::string& reason) - { - PyErr_SetString (exception, reason.c_str()); - } - - Exception (PyObject* exception, Object &reason); - - void clear() // clear the error - // technically but not philosophically const - { - PyErr_Clear(); - } - }; - - - // Abstract - class StandardError: public Exception - { - protected: - explicit StandardError() - {} - }; - - class LookupError: public StandardError - { - protected: - explicit LookupError() - {} - }; - - class ArithmeticError: public StandardError - { - protected: - explicit ArithmeticError() - {} - }; - - class EnvironmentError: public StandardError - { - protected: - explicit EnvironmentError() - {} - }; - - // Concrete - - class TypeError: public StandardError - { - public: - TypeError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_TypeError(),reason.c_str()); - } - }; - - class IndexError: public LookupError - { - public: - IndexError (const std::string& reason) - : LookupError() - { - PyErr_SetString (Py::_Exc_IndexError(), reason.c_str()); - } - }; - - class AttributeError: public StandardError - { - public: - AttributeError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_AttributeError(), reason.c_str()); - } - }; - - class NameError: public StandardError - { - public: - NameError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_NameError(), reason.c_str()); - } - }; - - class RuntimeError: public StandardError - { - public: - RuntimeError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_RuntimeError(), reason.c_str()); - } - }; - - class SystemError: public StandardError - { - public: - SystemError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_SystemError(),reason.c_str()); - } - }; - - class KeyError: public LookupError - { - public: - KeyError (const std::string& reason) - : LookupError() - { - PyErr_SetString (Py::_Exc_KeyError(),reason.c_str()); - } - }; - - - class ValueError: public StandardError - { - public: - ValueError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_ValueError(), reason.c_str()); - } - }; - - class OverflowError: public ArithmeticError - { - public: - OverflowError (const std::string& reason) - : ArithmeticError() - { - PyErr_SetString (Py::_Exc_OverflowError(), reason.c_str()); - } - }; - - class ZeroDivisionError: public ArithmeticError - { - public: - ZeroDivisionError (const std::string& reason) - : ArithmeticError() - { - PyErr_SetString (Py::_Exc_ZeroDivisionError(), reason.c_str()); - } - }; - - class FloatingPointError: public ArithmeticError - { - public: - FloatingPointError (const std::string& reason) - : ArithmeticError() - { - PyErr_SetString (Py::_Exc_FloatingPointError(), reason.c_str()); - } - }; - - class MemoryError: public StandardError - { - public: - MemoryError (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_MemoryError(), reason.c_str()); - } - }; - - class SystemExit: public StandardError - { - public: - SystemExit (const std::string& reason) - : StandardError() - { - PyErr_SetString (Py::_Exc_SystemExit(),reason.c_str()); - } - }; - -}// Py - +#if PY_MAJOR_VERSION == 2 +#include "CXX/Python2/Exception.hxx" +#else +#include "CXX/Python3/Exception.hxx" #endif Modified: trunk/matplotlib/CXX/Extensions.hxx =================================================================== --- trunk/matplotlib/CXX/Extensions.hxx 2010年01月16日 19:20:03 UTC (rev 8083) +++ trunk/matplotlib/CXX/Extensions.hxx 2010年01月16日 22:07:53 UTC (rev 8084) @@ -34,895 +34,10 @@ // DAMAGE. // //----------------------------------------------------------------------------- - -#ifndef __CXX_Extensions__h -#define __CXX_Extensions__h - - -#ifdef _MSC_VER -// disable warning C4786: symbol greater than 255 character, -// okay to ignore -#pragma warning(disable: 4786) -#endif - #include "CXX/WrapPython.h" -#include "CXX/Version.hxx" -#include "CXX/Config.hxx" -#include "CXX/Objects.hxx" -extern "C" -{ - extern PyObject py_object_initializer; -} - -#include <vector> - -// std::map / hash_map selection and declarations ---------------------------- -#if !defined( PYCXX_USING_HASH_MAP ) - -#include <map> - +#if PY_MAJOR_VERSION == 2 +#include "CXX/Python2/Extensions.hxx" #else - -#if defined( __GNUC__) && !defined( _STLPORT_VERSION ) - #include <ext/hash_map> -#else - #include <hash_map> +#include "CXX/Python3/Extensions.hxx" #endif -#if defined( _STLPORT_VERSION ) - #define __PYCXX_HASHMAP_NAMESPACE std - using namespace std; -#elif defined ( _MSC_VER ) && !defined( __INTEL_COMPILER ) && !defined( __ICC ) && !defined( __ICL ) && !defined( __ECC ) - #define __PYCXX_HASHMAP_NAMESPACE stdext - using namespace stdext; -#elif defined( __INTEL_COMPILER ) || defined( __ICC ) || defined( __ICL ) || defined( __ECC ) - #define __PYCXX_HASHMAP_NAMESPACE stdext - using namespace stdext; -#elif defined( __GNUC__ ) - #define __PYCXX_HASHMAP_NAMESPACE __gnu_cxx - using namespace __gnu_cxx; -#else - #define __PYCXX_HASHMAP_NAMESPACE std - using namespace std; -#endif - -class __pycxx_str_hash_func -{ -public: - enum - { - // parameters for hash table - bucket_size = 4, // 0 < bucket_size - min_buckets = 8 // min_buckets = 2 ^^ N, 0 < N - }; - - // http://www.azillionmonkeys.com/qed/hash.html - size_t operator()( const std::string &str ) const - { - const unsigned char * data = reinterpret_cast<const unsigned char *>( str.c_str() ); - int len = (int)str.length(); - unsigned int hash = len; - unsigned int tmp; - int rem; - - if (len <= 0 || data == NULL) - return 0; - - rem = len & 3; - len >>= 2; - - /* Main loop */ - for (;len > 0; len--) - { - hash += (data[1] << 8) | data[0]; - tmp = (((data[3] << 8) | data[2]) << 11) ^ hash; - hash = (hash << 16) ^ tmp; - data += 2*sizeof (unsigned short); - hash += hash >> 11; - } - - /* Handle end cases */ - switch (rem) - { - case 3: hash += (data[1] << 8) | data[0]; - hash ^= hash << 16; - hash ^= data[sizeof (unsigned short)] << 18; - hash += hash >> 11; - break; - case 2: hash += (data[1] << 8) | data[0]; - hash ^= hash << 11; - hash += hash >> 17; - break; - case 1: hash += *data; - hash ^= hash << 10; - hash += hash >> 1; - } - - /* Force "avalanching" of final 127 bits */ - hash ^= hash << 3; - hash += hash >> 5; - hash ^= hash << 4; - hash += hash >> 17; - hash ^= hash << 25; - hash += hash >> 6; - - return hash; - } - - bool operator()(const std::string &str_1, const std::string &str_2) const - { - // test if str_1 ordered before str_2 - return str_1 < str_2; - } -}; -#endif // PYCXX_USING_HASH_MAP -// ---------------------------------------------------------------------- - -namespace Py -{ - class ExtensionModuleBase; - - // Make an Exception Type for use in raising custom exceptions - class ExtensionExceptionType : public Object - { - public: - ExtensionExceptionType(); - virtual ~ExtensionExceptionType(); - - // call init to create the type - void init( ExtensionModuleBase &module, const std::string& name, ExtensionExceptionType &parent ); - void init( ExtensionModuleBase &module, const std::string& name ); - }; - - - class MethodTable - { - public: - MethodTable(); - virtual ~MethodTable(); - - void add(const char* method_name, PyCFunction f, const char* doc="", int flag=1); - PyMethodDef* table(); - - protected: - std::vector<PyMethodDef> t; // accumulator of PyMethodDef's - PyMethodDef *mt; // Actual method table produced when full - - static PyMethodDef method (const char* method_name, PyCFunction f, int flags = 1, const char* doc=""); - - private: - // - // prevent the compiler generating these unwanted functions - // - MethodTable(const MethodTable& m); //unimplemented - void operator=(const MethodTable& m); //unimplemented - - }; // end class MethodTable - - extern "C" - { - typedef PyObject *(*method_varargs_call_handler_t)( PyObject *_self, PyObject *_args ); - typedef PyObject *(*method_keyword_call_handler_t)( PyObject *_self, PyObject *_args, PyObject *_dict ); - } - - template<class T> - class MethodDefExt : public PyMethodDef - { - public: - typedef Object (T::*method_varargs_function_t)( const Tuple &args ); - typedef Object (T::*method_keyword_function_t)( const Tuple &args, const Dict &kws ); - - MethodDefExt - ( - const char *_name, - method_varargs_function_t _function, - method_varargs_call_handler_t _handler, - const char *_doc - ) - { - ext_meth_def.ml_name = const_cast<char *>(_name); - ext_meth_def.ml_meth = _handler; - ext_meth_def.ml_flags = METH_VARARGS; - ext_meth_def.ml_doc = const_cast<char *>(_doc); - - ext_varargs_function = _function; - ext_keyword_function = NULL; - } - - MethodDefExt - ( - const char *_name, - method_keyword_function_t _function, - method_keyword_call_handler_t _handler, - const char *_doc - ) - { - ext_meth_def.ml_name = const_cast<char *>(_name); - ext_meth_def.ml_meth = method_varargs_call_handler_t( _handler ); - ext_meth_def.ml_flags = METH_VARARGS|METH_KEYWORDS; - ext_meth_def.ml_doc = const_cast<char *>(_doc); - - ext_varargs_function = NULL; - ext_keyword_function = _function; - } - - ~MethodDefExt() - {} - - PyMethodDef ext_meth_def; - method_varargs_function_t ext_varargs_function; - method_keyword_function_t ext_keyword_function; - }; - - class ExtensionModuleBase - { - public: - ExtensionModuleBase( const char *name ); - virtual ~ExtensionModuleBase(); - - Module module(void) const; // only valid after initialize() has been called - Dict moduleDictionary(void) const; // only valid after initialize() has been called - - virtual Object invoke_method_keyword( const std::string &_name, const Tuple &_args, const Dict &_keywords ) = 0; - virtual Object invoke_method_varargs( const std::string &_name, const Tuple &_args ) = 0; - - const std::string &name() const; - const std::string &fullName() const; - - protected: - // Initialize the module - void initialize( const char *module_doc ); - - const std::string module_name; - const std::string full_module_name; - MethodTable method_table; - - private: - - // - // prevent the compiler generating these unwanted functions - // - ExtensionModuleBase( const ExtensionModuleBase & ); //unimplemented - void operator=( const ExtensionModuleBase & ); //unimplemented - - }; - - extern "C" PyObject *method_keyword_call_handler( PyObject *_self_and_name_tuple, PyObject *_args, PyObject *_keywords ); - extern "C" PyObject *method_varargs_call_handler( PyObject *_self_and_name_tuple, PyObject *_args ); - extern "C" void do_not_dealloc( void * ); - - - template<TEMPLATE_TYPENAME T> - class ExtensionModule : public ExtensionModuleBase - { - public: - ExtensionModule( const char *name ) - : ExtensionModuleBase( name ) - {} - virtual ~ExtensionModule() - {} - - protected: - typedef Object (T::*method_varargs_function_t)( const Tuple &args ); - typedef Object (T::*method_keyword_function_t)( const Tuple &args, const Dict &kws ); - -#if defined( PYCXX_USING_HASH_MAP ) - typedef __PYCXX_HASHMAP_NAMESPACE::hash_map<std::string, MethodDefExt<T> *, __pycxx_str_hash_func> method_map_t; -#else - typedef std::map<std::string,MethodDefExt<T> *> method_map_t; -#endif - - static void add_varargs_method( const char *name, method_varargs_function_t function, const char *doc="" ) - { - method_map_t &mm = methods(); - - MethodDefExt<T> *method_definition = new MethodDefExt<T> - ( - name, - function, - method_varargs_call_handler, - doc - ); - - mm[std::string( name )] = method_definition; - } - - static void add_keyword_method( const char *name, method_keyword_function_t function, const char *doc="" ) - { - method_map_t &mm = methods(); - - MethodDefExt<T> *method_definition = new MethodDefExt<T> - ( - name, - function, - method_keyword_call_handler, - doc - ); - - mm[std::string( name )] = method_definition; - } - - void initialize( const char *module_doc="" ) - { - ExtensionModuleBase::initialize( module_doc ); - Dict dict( moduleDictionary() ); - - // - // put each of the methods into the modules dictionary - // so that we get called back at the function in T. - // - method_map_t &mm = methods(); - EXPLICIT_TYPENAME method_map_t::const_iterator i; - - for( i=mm.begin(); i != mm.end(); ++i ) - { - MethodDefExt<T> *method_definition = (*i).second; - - static PyObject *self = PyCObject_FromVoidPtr( this, do_not_dealloc ); - - Tuple args( 2 ); - args[0] = Object( self ); - args[1] = String( (*i).first ); - - PyObject *func = PyCFunction_New - ( - &method_definition->ext_meth_def, - new_reference_to( args ) - ); - - dict[ (*i).first ] = Object( func ); - } - } - - protected: // Tom Malcolmson reports that derived classes need access to these - - static method_map_t &methods(void) - { - static method_map_t *map_of_methods = NULL; - if( map_of_methods == NULL ) - map_of_methods = new method_map_t; - - return *map_of_methods; - } - - - // this invoke function must be called from within a try catch block - virtual Object invoke_method_keyword( const std::string &name, const Tuple &args, const Dict &keywords ) - { - method_map_t &mm = methods(); - MethodDefExt<T> *meth_def = mm[ name ]; - if( meth_def == NULL ) - { - std::string error_msg( "CXX - cannot invoke keyword method named " ); - error_msg += name; - throw RuntimeError( error_msg ); - } - - // cast up to the derived class - T *self = static_cast<T *>(this); - - return (self->*meth_def->ext_keyword_function)( args, keywords ); - } - - // this invoke function must be called from within a try catch block - virtual Object invoke_method_varargs( const std::string &name, const Tuple &args ) - { - method_map_t &mm = methods(); - MethodDefExt<T> *meth_def = mm[ name ]; - if( meth_def == NULL ) - { - std::string error_msg( "CXX - cannot invoke varargs method named " ); - error_msg += name; - throw RuntimeError( error_msg ); - } - - // cast up to the derived class - T *self = static_cast<T *>(this); - - return (self->*meth_def->ext_varargs_function)( args ); - } - - private: - // - // prevent the compiler generating these unwanted functions - // - ExtensionModule( const ExtensionModule<T> & ); //unimplemented - void operator=( const ExtensionModule<T> & ); //unimplemented - }; - - - class PythonType - { - public: - // if you define one sequence method you must define - // all of them except the assigns - - PythonType (size_t base_size, int itemsize, const char *default_name ); - virtual ~PythonType (); - - const char *getName () const; - const char *getDoc () const; - - PyTypeObject* type_object () const; - PythonType & name (const char* nam); - PythonType & doc (const char* d); - PythonType & dealloc(void (*f)(PyObject*)); - - PythonType & supportPrint(void); - PythonType & supportGetattr(void); - PythonType & supportSetattr(void); - PythonType & supportGetattro(void); - PythonType & supportSetattro(void); - PythonType & supportCompare(void); -#if PY_MAJOR_VERSION > 2 || (PY_MAJOR_VERSION == 2 && PY_MINOR_VERSION >= 1) - PythonType & supportRichCompare(void); -#endif - PythonType & supportRepr(void); - PythonType & supportStr(void); - PythonType & supportHash(void); - PythonType & supportCall(void); - PythonType & supportIter(void); - - PythonType & supportSequenceType(void); - PythonType & supportMappingType(void); - PythonType & supportNumberType(void); - PythonType & supportBufferType(void); - - protected: - PyTypeObject *table; - PySequenceMethods *sequence_table; - PyMappingMethods *mapping_table; - PyNumberMethods *number_table; - PyBufferProcs *buffer_table; - - void init_sequence(); - void init_mapping(); - void init_number(); - void init_buffer(); - - private: - // - // prevent the compiler generating these unwanted functions - // - PythonType (const PythonType& tb); // unimplemented - void operator=(const PythonType& t); // unimplemented - - }; // end of PythonType - - - - // Class PythonExtension is what you inherit from to create - // a new Python extension type. You give your class itself - // as the template paramter. - - // There are two ways that extension objects can get destroyed. - // 1. Their reference count goes to zero - // 2. Someone does an explicit delete on a pointer. - // In (1) the problem is to get the destructor called - // We register a special deallocator in the Python type object - // (see behaviors()) to do this. - // In (2) there is no problem, the dtor gets called. - - // PythonExtension does not use the usual Python heap allocator, - // instead using new/delete. We do the setting of the type object - // and reference count, usually done by PyObject_New, in the - // base class ctor. - - // This special deallocator does a delete on the pointer. - - - class PythonExtensionBase : public PyObject - { - public: - PythonExtensionBase(); - virtual ~PythonExtensionBase(); - - public: - virtual int print( FILE *, int ); - virtual Object getattr( const char * ) = 0; - virtual int setattr( const char *, const Object & ); - virtual Object getattro( const Object & ); - virtual int setattro( const Object &, const Object & ); - virtual int compare( const Object & ); - virtual Object rich_compare( const Object &, int op ); - virtual Object repr(); - virtual Object str(); - virtual long hash(); - virtual Object call( const Object &, const Object & ); - virtual Object iter(); - virtual PyObject* iternext(); - - // Sequence methods - virtual int sequence_length(); - virtual Object sequence_concat( const Object & ); - virtual Object sequence_repeat( Py_ssize_t ); - virtual Object sequence_item( Py_ssize_t ); - virtual Object sequence_slice( Py_ssize_t, Py_ssize_t ); - virtual int sequence_ass_item( Py_ssize_t, const Object & ); - virtual int sequence_ass_slice( Py_ssize_t, Py_ssize_t, const Object & ); - - // Mapping - virtual int mapping_length(); - virtual Object mapping_subscript( const Object & ); - virtual int mapping_ass_subscript( const Object &, const Object & ); - - // Number - virtual int number_nonzero(); - virtual Object number_negative(); - virtual Object number_positive(); - virtual Object number_absolute(); - virtual Object number_invert(); - virtual Object number_int(); - virtual Object number_float(); - virtual Object number_long(); - virtual Object number_oct(); - virtual Object number_hex(); - virtual Object number_add( const Object & ); - virtual Object number_subtract( const Object & ); - virtual Object number_multiply( const Object & ); - virtual Object number_divide( const Object & ); - virtual Object number_remainder( const Object & ); - virtual Object number_divmod( const Object & ); - virtual Object number_lshift( const Object & ); - virtual Object number_rshift( const Object & ); - virtual Object number_and( const Object & ); - virtual Object number_xor( const Object & ); - virtual Object number_or( const Object & ); - virtual Object number_power( const Object &, const Object & ); - - // Buffer - virtual Py_ssize_t buffer_getreadbuffer( Py_ssize_t, void** ); - virtual Py_ssize_t buffer_getwritebuffer( Py_ssize_t, void** ); - virtual Py_ssize_t buffer_getsegcount( Py_ssize_t* ); - - private: - void missing_method( void ); - static PyObject *method_call_handler( PyObject *self, PyObject *args ); - }; - - template<TEMPLATE_TYPENAME T> - class PythonExtension: public PythonExtensionBase - { - public: - static PyTypeObject* type_object() - { - return behaviors().type_object(); - } - - static int check( PyObject *p ) - { - // is p like me? - return p->ob_type == type_object(); - } - - static int check( const Object& ob ) - { - return check( ob.ptr()); - } - - - // - // every object needs getattr implemented - // to support methods - // - virtual Object getattr( const char *name ) - { - return getattr_methods( name ); - } - - protected: - explicit PythonExtension() - : PythonExtensionBase() - { - #ifdef PyObject_INIT - (void)PyObject_INIT( this, type_object() ); - #else - ob_refcnt = 1; - ob_type = type_object(); - #endif - - // every object must support getattr - behaviors().supportGetattr(); - } - - virtual ~PythonExtension() - {} - - static PythonType &behaviors() - { - static PythonType* p; - if( p == NULL ) - { -#if defined( _CPPRTTI ) || defined(__GNUG__) - const char *default_name = (typeid ( T )).name(); -#else - const char *default_name = "unknown"; -#endif - p = new PythonType( sizeof( T ), 0, default_name ); - p->dealloc( extension_object_deallocator ); - } - - return *p; - } - - - typedef Object (T::*method_varargs_function_t)( const Tuple &args ); - typedef Object (T::*method_keyword_function_t)( const Tuple &args, const Dict &kws ); - -#if defined( PYCXX_USING_HASH_MAP ) - typedef __PYCXX_HASHMAP_NAMESPACE::hash_map<std::string, MethodDefExt<T> *, __pycxx_str_hash_func> method_map_t; -#else - typedef std::map<std::string,MethodDefExt<T> *> method_map_t; -#endif - - // support the default attributes, __name__, __doc__ and methods - virtual Object getattr_default( const char *_name ) - { - std::string name( _name ); - - if( name == "__name__" && type_object()->tp_name != NULL ) - { - return Py::String( type_object()->tp_name ); - } - if( name == "__doc__" && type_object()->tp_doc != NULL ) - { - return Py::String( type_object()->tp_doc ); - } - -// trying to fake out being a class for help() -// else if( name == "__bases__" ) -// { -// return Py::Tuple(0); -// } -// else if( name == "__module__" ) -// { -// return Py::Nothing(); -// } -// else if( name == "__dict__" ) -// { -// return Py::Dict(); -// } - - return getattr_methods( _name ); - } - - // turn a name into function object - virtual Object getattr_methods( const char *_name ) - { - std::string name( _name ); - - method_map_t &mm = methods(); - - EXPLICIT_TYPENAME method_map_t::const_iterator i; - - if( name == "__methods__" ) - { - List methods; - - for( i = mm.begin(); i != mm.end(); ++i ) - methods.append( String( (*i).first ) ); - - return methods; - } - - // see if name exists and get entry with method - i = mm.find( name ); - if( i == mm.end() ) - throw AttributeError( name ); - - Tuple self( 2 ); - - self[0] = Object( this ); - self[1] = String( name ); - - MethodDefExt<T> *method_definition = i->second; - - PyObject *func = PyCFunction_New( &method_definition->ext_meth_def, self.ptr() ); - - return Object(func, true); - } - - static void add_varargs_method( const char *name, method_varargs_function_t function, const char *doc="" ) - { - method_map_t &mm = methods(); - - // check that all methods added are unique - EXPLICIT_TYPENAME method_map_t::const_iterator i; - i = mm.find( name ); - if( i != mm.end() ) - throw AttributeError( name ); - - MethodDefExt<T> *method_definition = new MethodDefExt<T> - ( - name, - function, - method_varargs_call_handler, - doc - ); - - mm[std::string( name )] = method_definition; - } - - static void add_keyword_method( const char *name, method_keyword_function_t function, const char *doc="" ) - { - method_map_t &mm = methods(); - - // check that all methods added are unique - EXPLICIT_TYPENAME method_map_t::const_iterator i; - i = mm.find( name ); - if( i != mm.end() ) - throw AttributeError( name ); - - MethodDefExt<T> *method_definition = new MethodDefExt<T> - ( - name, - function, - method_keyword_call_handler, - doc - ); - - mm[std::string( name )] = method_definition; - } - - private: - static method_map_t &methods(void) - { - static method_map_t *map_of_methods = NULL; - if( map_of_methods == NULL ) - map_of_methods = new method_map_t; - - return *map_of_methods; - } - - static PyObject *method_keyword_call_handler( PyObject *_self_and_name_tuple, PyObject *_args, PyObject *_keywords ) - { - try - { - Tuple self_and_name_tuple( _self_and_name_tuple ); - - PyObject *self_in_cobject = self_and_name_tuple[0].ptr(); - T *self = static_cast<T *>( self_in_cobject ); - - String name( self_and_name_tuple[1] ); - - method_map_t &mm = methods(); - - EXPLICIT_TYPENAME method_map_t::const_iterator i; - i = mm.find( name ); - if( i == mm.end() ) - return 0; - - MethodDefExt<T> *meth_def = i->second; - - Tuple args( _args ); - - // _keywords may be NULL so be careful about the way the dict is created - Dict keywords; - if( _keywords != NULL ) - keywords = Dict( _keywords ); - - Object result( (self->*meth_def->ext_keyword_function)( args, keywords ) ); - - return new_reference_to( result.ptr() ); - } - catch( Exception & ) - { - return 0; - } - } - - static PyObject *method_varargs_call_handler( PyObject *_self_and_name_tuple, PyObject *_args ) - { - try - { - Tuple self_and_name_tuple( _self_and_name_tuple ); - - PyObject *self_in_cobject = self_and_name_tuple[0].ptr(); - T *self = static_cast<T *>( self_in_cobject ); - - String name( self_and_name_tuple[1] ); - - method_map_t &mm = methods(); - - EXPLICIT_TYPENAME method_map_t::const_iterator i; - i = mm.find( name ); - if( i == mm.end() ) - return 0; - - MethodDefExt<T> *meth_def = i->second; - - Tuple args( _args ); - - Object result; - - // TMM: 7Jun'01 - Adding try & catch in case of STL debug-mode exceptions. - #ifdef _STLP_DEBUG - try - { - result = (self->*meth_def->ext_varargs_function)( args ); - } - catch (std::__stl_debug_exception) - { - // throw cxx::RuntimeError( sErrMsg ); - throw cxx::RuntimeError( "Error message not set yet." ); - } - #else - result = (self->*meth_def->ext_varargs_function)( args ); - #endif // _STLP_DEBUG - - return new_reference_to( result.ptr() ); - } - catch( Exception & ) - { - return 0; - } - } - - static void extension_object_deallocator ( PyObject* t ) - { - delete (T *)( t ); - } - - // - // prevent the compiler generating these unwanted functions - // - explicit PythonExtension( const PythonExtension<T>& other ); - void operator=( const PythonExtension<T>& rhs ); - }; - - // - // ExtensionObject<T> is an Object that will accept only T's. - // - template<TEMPLATE_TYPENAME T> - class ExtensionObject: public Object - { - public: - - explicit ExtensionObject ( PyObject *pyob ) - : Object( pyob ) - { - validate(); - } - - ExtensionObject( const ExtensionObject<T>& other ) - : Object( *other ) - { - validate(); - } - - ExtensionObject( const Object& other ) - : Object( *other ) - { - validate(); - } - - ExtensionObject& operator= ( const Object& rhs ) - { - return (*this = *rhs ); - } - - ExtensionObject& operator= ( PyObject* rhsp ) - { - if( ptr() == rhsp ) - return *this; - set( rhsp ); - return *this; - } - - virtual bool accepts ( PyObject *pyob ) const - { - return ( pyob && T::check( pyob )); - } - - // - // Obtain a pointer to the PythonExtension object - // - T *extensionObject(void) - { - return static_cast<T *>( ptr() ); - } - }; - -} // Namespace Py -// End of CXX_Extensions.h -#endif Modified: trunk/matplotlib/CXX/IndirectPythonInterface.cxx =================================================================== --- trunk/matplotlib/CXX/IndirectPythonInterface.cxx 2010年01月16日 19:20:03 UTC (rev 8083) +++ trunk/matplotlib/CXX/IndirectPythonInterface.cxx 2010年01月16日 22:07:53 UTC (rev 8084) @@ -34,564 +34,10 @@ // DAMAGE. // //----------------------------------------------------------------------------- +#include "CXX/WrapPython.h" -#include "CXX/IndirectPythonInterface.hxx" - -namespace Py -{ -bool _Buffer_Check( PyObject *op ) { return (op)->ob_type == _Buffer_Type(); } -bool _CFunction_Check( PyObject *op ) { return (op)->ob_type == _CFunction_Type(); } -bool _Class_Check( PyObject *op ) { return (op)->ob_type == _Class_Type(); } -bool _CObject_Check( PyObject *op ) { return (op)->ob_type == _CObject_Type(); } -bool _Complex_Check( PyObject *op ) { return (op)->ob_type == _Complex_Type(); } -bool _Dict_Check( PyObject *op ) { return (op)->ob_type == _Dict_Type(); } -bool _File_Check( PyObject *op ) { return (op)->ob_type == _File_Type(); } -bool _Float_Check( PyObject *op ) { return (op)->ob_type == _Float_Type(); } -bool _Function_Check( PyObject *op ) { return (op)->ob_type == _Function_Type(); } -bool _Instance_Check( PyObject *op ) { return (op)->ob_type == _Instance_Type(); } -bool _Boolean_Check( PyObject *op ) { return (op)->ob_type == _Bool_Type(); } -bool _Int_Check( PyObject *op ) { return (op)->ob_type == _Int_Type(); } -bool _List_Check( PyObject *o ) { return o->ob_type == _List_Type(); } -bool _Long_Check( PyObject *op ) { return (op)->ob_type == _Long_Type(); } -bool _Method_Check( PyObject *op ) { return (op)->ob_type == _Method_Type(); } -bool _Module_Check( PyObject *op ) { return (op)->ob_type == _Module_Type(); } -bool _Range_Check( PyObject *op ) { return (op)->ob_type == _Range_Type(); } -bool _Slice_Check( PyObject *op ) { return (op)->ob_type == _Slice_Type(); } -bool _String_Check( PyObject *o ) { return o->ob_type == _String_Type(); } -bool _TraceBack_Check( PyObject *v ) { return (v)->ob_type == _TraceBack_Type(); } -bool _Tuple_Check( PyObject *op ) { return (op)->ob_type == _Tuple_Type(); } -bool _Type_Check( PyObject *op ) { return (op)->ob_type == _Type_Type(); } - -#if PY_MAJOR_VERSION >= 2 -bool _Unicode_Check( PyObject *op ) { return (op)->ob_type == _Unicode_Type(); } -#endif - - - -#if defined(PY_WIN32_DELAYLOAD_PYTHON_DLL) - -#if defined(MS_WINDOWS) -#include <windows.h> - - -static HMODULE python_dll; - -static PyObject *ptr__Exc_ArithmeticError = NULL; -static PyObject *ptr__Exc_AssertionError = NULL; -static PyObject *ptr__Exc_AttributeError = NULL; -static PyObject *ptr__Exc_EnvironmentError = NULL; -static PyObject *ptr__Exc_EOFError = NULL; -static PyObject *ptr__Exc_Exception = NULL; -static PyObject *ptr__Exc_FloatingPointError = NULL; -static PyObject *ptr__Exc_ImportError = NULL; -static PyObject *ptr__Exc_IndexError = NULL; -static PyObject *ptr__Exc_IOError = NULL; -static PyObject *ptr__Exc_KeyboardInterrupt = NULL; -static PyObject *ptr__Exc_KeyError = NULL; -static PyObject *ptr__Exc_LookupError = NULL; -static PyObject *ptr__Exc_MemoryError = NULL; -static PyObject *ptr__Exc_MemoryErrorInst = NULL; -static PyObject *ptr__Exc_NameError = NULL; -static PyObject *ptr__Exc_NotImplementedError = NULL; -static PyObject *ptr__Exc_OSError = NULL; -static PyObject *ptr__Exc_OverflowError = NULL; -static PyObject *ptr__Exc_RuntimeError = NULL; -static PyObject *ptr__Exc_StandardError = NULL; -static PyObject *ptr__Exc_SyntaxError = NULL; -static PyObject *ptr__Exc_SystemError = NULL; -static PyObject *ptr__Exc_SystemExit = NULL; -static PyObject *ptr__Exc_TypeError = NULL; -static PyObject *ptr__Exc_ValueError = NULL; -static PyObject *ptr__Exc_ZeroDivisionError = NULL; - -#ifdef MS_WINDOWS -static PyObject *ptr__Exc_WindowsError = NULL; -#endif - -#if PY_MAJOR_VERSION >= 2 -static PyObject *ptr__Exc_IndentationError = NULL; -static PyObject *ptr__Exc_TabError = NULL; -static PyObject *ptr__Exc_UnboundLocalError = NULL; -static PyObject *ptr__Exc_UnicodeError = NULL; -#endif - -static PyObject *ptr__PyNone = NULL; - -static PyObject *ptr__PyFalse = NULL; -static PyObject *ptr__PyTrue = NULL; - -static PyTypeObject *ptr__Buffer_Type = NULL; -static PyTypeObject *ptr__CFunction_Type = NULL; -static PyTypeObject *ptr__Class_Type = NULL; -static PyTypeObject *ptr__CObject_Type = NULL; -static PyTypeObject *ptr__Complex_Type = NULL; -static PyTypeObject *ptr__Dict_Type = NULL; -static PyTypeObject *ptr__File_Type = NULL; -static PyTypeObject *ptr__Float_Type = NULL; -static PyTypeObject *ptr__Function_Type = NULL; -static PyTypeObject *ptr__Instance_Type = NULL; -static PyTypeObject *ptr__Int_Type = NULL; -static PyTypeObject *ptr__List_Type = NULL; -static PyTypeObject *ptr__Long_Type = NULL; -static PyTypeObject *ptr__Method_Type = NULL; -static PyTypeObject *ptr__Module_Type = NULL; -static PyTypeObject *ptr__Range_Type = NULL; -static PyTypeObject *ptr__Slice_Type = NULL; -static PyTypeObject *ptr__String_Type = NULL; -static PyTypeObject *ptr__TraceBack_Type = NULL; -static PyTypeObject *ptr__Tuple_Type = NULL; -static PyTypeObject *ptr__Type_Type = NULL; - -#if PY_MAJOR_VERSION >= 2 -static PyTypeObject *ptr__Unicode_Type = NULL; -#endif - -static int *ptr_Py_DebugFlag = NULL; -static int *ptr_Py_InteractiveFlag = NULL; -static int *ptr_Py_OptimizeFlag = NULL; -static int *ptr_Py_NoSiteFlag = NULL; -static int *ptr_Py_TabcheckFlag = NULL; -static int *ptr_Py_VerboseFlag = NULL; - -#if PY_MAJOR_VERSION >= 2 -static int *ptr_Py_UnicodeFlag = NULL; -#endif - -static char **ptr__Py_PackageContext = NULL; - -#ifdef Py_REF_DEBUG -int *ptr_Py_RefTotal; -#endif - - -//-------------------------------------------------------------------------------- -class GetAddressException -{ -public: - GetAddressException( const char *_name ) - : name( _name ) - {} - virtual ~GetAddressException() {} - const char *name; -}; - - -//-------------------------------------------------------------------------------- -static PyObject *GetPyObjectPointer_As_PyObjectPointer( const char *name ) -{ - FARPROC addr = GetProcAddress( python_dll, name ); - if( addr == NULL ) - throw GetAddressException( name ); - - return *(PyObject **)addr; -} - -static PyObject *GetPyObject_As_PyObjectPointer( const char *name ) -{ - FARPROC addr = GetProcAddress( python_dll, name ); - if( addr == NULL ) - throw GetAddressException( name ); - - return (PyObject *)addr; -} - -static PyTypeObject *GetPyTypeObjectPointer_As_PyTypeObjectPointer( const char *name ) -{ - FARPROC addr = GetProcAddress( python_dll, name ); - if( addr == NULL ) - throw GetAddressException( name ); - - return *(PyTypeObject **)addr; -} - -static PyTypeObject *GetPyTypeObject_As_PyTypeObjectPointer( const char *name ) -{ - FARPROC addr = GetProcAddress( python_dll, name ); - if( addr == NULL ) - throw GetAddressException( name ); - - return (PyTypeObject *)addr; -} - -static int *GetInt_as_IntPointer( const char *name ) -{ - FARPROC addr = GetProcAddress( python_dll, name ); - if( addr == NULL ) - throw GetAddressException( name ); - - return (int *)addr; -} - -static char **GetCharPointer_as_CharPointerPointer( const char *name ) -{ - FARPROC addr = GetProcAddress( python_dll, name ); - if( addr == NULL ) - throw GetAddressException( name ); - - return (char **)addr; -} - - -#ifdef _DEBUG -static const char python_dll_name_format[] = "PYTHON%1.1d%1.1d_D.DLL"; +#if PY_MAJOR_VERSION == 2 +#include "Python2/IndirectPythonInterface.cxx" #else -static const char python_dll_name_format[] = "PYTHON%1.1d%1.1d.DLL"; +#include "Python3/IndirectPythonInterface.cxx" #endif - -//-------------------------------------------------------------------------------- -bool InitialisePythonIndirectInterface() -{ - char python_dll_name[sizeof(python_dll_name_format)]; - - sprintf( python_dll_name, python_dll_name_format, PY_MAJOR_VERSION, PY_MINOR_VERSION ); - - python_dll = LoadLibrary( python_dll_name ); - if( python_dll == NULL ) - return false; - - try -{ -#ifdef Py_REF_DEBUG - ptr_Py_RefTotal = GetInt_as_IntPointer( "_Py_RefTotal" ); -#endif - ptr_Py_DebugFlag = GetInt_as_IntPointer( "Py_DebugFlag" ); - ptr_Py_InteractiveFlag = GetInt_as_IntPointer( "Py_InteractiveFlag" ); - ptr_Py_OptimizeFlag = GetInt_as_IntPointer( "Py_OptimizeFlag" ); - ptr_Py_NoSiteFlag = GetInt_as_IntPointer( "Py_NoSiteFlag" ); - ptr_Py_TabcheckFlag = GetInt_as_IntPointer( "Py_TabcheckFlag" ); - ptr_Py_VerboseFlag = GetInt_as_IntPointer( "Py_VerboseFlag" ); -#if PY_MAJOR_VERSION >= 2 - ptr_Py_UnicodeFlag = GetInt_as_IntPointer( "Py_UnicodeFlag" ); -#endif - ptr__Py_PackageContext = GetCharPointer_as_CharPointerPointer( "_Py_PackageContext" ); - - ptr__Exc_ArithmeticError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ArithmeticError" ); - ptr__Exc_AssertionError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_AssertionError" ); - ptr__Exc_AttributeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_AttributeError" ); - ptr__Exc_EnvironmentError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_EnvironmentError" ); - ptr__Exc_EOFError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_EOFError" ); - ptr__Exc_Exception = GetPyObjectPointer_As_PyObjectPointer( "PyExc_Exception" ); - ptr__Exc_FloatingPointError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_FloatingPointError" ); - ptr__Exc_ImportError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ImportError" ); - ptr__Exc_IndexError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_IndexError" ); - ptr__Exc_IOError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_IOError" ); - ptr__Exc_KeyboardInterrupt = GetPyObjectPointer_As_PyObjectPointer( "PyExc_KeyboardInterrupt" ); - ptr__Exc_KeyError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_KeyError" ); - ptr__Exc_LookupError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_LookupError" ); - ptr__Exc_MemoryError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_MemoryError" ); - ptr__Exc_MemoryErrorInst = GetPyObjectPointer_As_PyObjectPointer( "PyExc_MemoryErrorInst" ); - ptr__Exc_NameError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_NameError" ); - ptr__Exc_NotImplementedError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_NotImplementedError" ); - ptr__Exc_OSError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_OSError" ); - ptr__Exc_OverflowError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_OverflowError" ); - ptr__Exc_RuntimeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_RuntimeError" ); - ptr__Exc_StandardError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_StandardError" ); - ptr__Exc_SyntaxError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_SyntaxError" ); - ptr__Exc_SystemError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_SystemError" ); - ptr__Exc_SystemExit = GetPyObjectPointer_As_PyObjectPointer( "PyExc_SystemExit" ); - ptr__Exc_TypeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_TypeError" ); - ptr__Exc_ValueError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ValueError" ); -#ifdef MS_WINDOWS - ptr__Exc_WindowsError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_WindowsError" ); -#endif - ptr__Exc_ZeroDivisionError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_ZeroDivisionError" ); - -#if PY_MAJOR_VERSION >= 2 - ptr__Exc_IndentationError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_IndentationError" ); - ptr__Exc_TabError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_TabError" ); - ptr__Exc_UnboundLocalError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_UnboundLocalError" ); - ptr__Exc_UnicodeError = GetPyObjectPointer_As_PyObjectPointer( "PyExc_UnicodeError" ); -#endif - ptr__PyNone = GetPyObject_As_PyObjectPointer( "_Py_NoneStruct" ); - - ptr__PyFalse = GetPyObject_As_PyObjectPointer( "_Py_ZeroStruct" ); - ptr__PyTrue = GetPyObject_As_PyObjectPointer( "_Py_TrueStruct" ); - - ptr__Buffer_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyBuffer_Type" ); - ptr__CFunction_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyCFunction_Type" ); - ptr__Class_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyClass_Type" ); - ptr__CObject_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyCObject_Type" ); - ptr__Complex_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyComplex_Type" ); - ptr__Dict_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyDict_Type" ); - ptr__File_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyFile_Type" ); - ptr__Float_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyFloat_Type" ); - ptr__Function_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyFunction_Type" ); - ptr__Instance_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyInstance_Type" ); - ptr__Int_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyInt_Type" ); - ptr__List_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyList_Type" ); - ptr__Long_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyLong_Type" ); - ptr__Method_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyMethod_Type" ); - ptr__Module_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyModule_Type" ); - ptr__Range_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyRange_Type" ); - ptr__Slice_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PySlice_Type" ); - ptr__String_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyString_Type" ); - ptr__TraceBack_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyTraceBack_Type" ); - ptr__Tuple_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyTuple_Type" ); - ptr__Type_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyType_Type" ); - -#if PY_MAJOR_VERSION >= 2 - ptr__Unicode_Type = GetPyTypeObject_As_PyTypeObjectPointer( "PyUnicode_Type" ); -#endif -} - catch( GetAddressException &e ) - { - OutputDebugString( python_dll_name ); - OutputDebugString( " does not contain symbol "); - OutputDebugString( e.name ); - OutputDebugString( "\n" ); - - return false; - } - - return true; -} - -// -// Wrap variables as function calls -// -PyObject * _Exc_ArithmeticError(){ return ptr__Exc_ArithmeticError; } -PyObject * _Exc_AssertionError(){ return ptr__Exc_AssertionError; } -PyObject * _Exc_AttributeError(){ return ptr__Exc_AttributeError; } -PyObject * _Exc_EnvironmentError(){ return ptr__Exc_EnvironmentError; } -PyObject * _Exc_EOFError() { return ptr__Exc_EOFError; } -PyObject * _Exc_Exception() { return ptr__Exc_Exception; } -PyObject * _Exc_FloatingPointError(){ return ptr__Exc_FloatingPointError; } -PyObject * _Exc_ImportError() { return ptr__Exc_ImportError; } -PyObject * _Exc_IndexError() { return ptr__Exc_IndexError; } -PyObject * _Exc_IOError() { return ptr__Exc_IOError; } -PyObject * _Exc_KeyboardInterrupt(){ return ptr__Exc_KeyboardInterrupt; } -PyObject * _Exc_KeyError() { return ptr__Exc_KeyError; } -PyObject * _Exc_LookupError() { return ptr__Exc_LookupError; } -PyObject * _Exc_MemoryError() { return ptr__Exc_MemoryError; } -PyObject * _Exc_MemoryErrorInst(){ return ptr__Exc_MemoryErrorInst; } -PyObject * _Exc_NameError() { return ptr__Exc_NameError; } -PyObject * _Exc_NotImplementedError(){ return ptr__Exc_NotImplementedError; } -PyObject * _Exc_OSError() { return ptr__Exc_OSError; } -PyObject * _Exc_OverflowError() { return ptr__Exc_OverflowError; } -PyObject * _Exc_RuntimeError() { return ptr__Exc_RuntimeError; } -PyObject * _Exc_StandardError() { return ptr__Exc_StandardError; } -PyObject * _Exc_SyntaxError() { return ptr__Exc_SyntaxError; } -PyObject * _Exc_SystemError() { return ptr__Exc_SystemError; } -PyObject * _Exc_SystemExit() { return ptr__Exc_SystemExit; } -PyObject * _Exc_TypeError() { return ptr__Exc_TypeError; } -PyObject * _Exc_ValueError() { return ptr__Exc_ValueError; } -#ifdef MS_WINDOWS -PyObject * _Exc_WindowsError() { return ptr__Exc_WindowsError; } -#endif -PyObject * _Exc_ZeroDivisionError(){ return ptr__Exc_ZeroDivisionError; } - -#if PY_MAJOR_VERSION >= 2 -PyObject * _Exc_IndentationError(){ return ptr__Exc_IndentationError; } -PyObject * _Exc_TabError() { return ptr__Exc_TabError; } -PyObject * _Exc_UnboundLocalError(){ return ptr__Exc_UnboundLocalError; } -PyObject * _Exc_UnicodeError() { return ptr__Exc_UnicodeError; } -#endif - -// -// wrap items in Object.h -// -PyObject * _None() { return ptr__PyNone; } - -PyObject * _False() { return ptr__PyFalse; } -PyObject * _True() { return ptr__PyTrue; } - -PyTypeObject * _Buffer_Type() { return ptr__Buffer_Type; } -PyTypeObject * _CFunction_Type(){ return ptr__CFunction_Type; } -PyTypeObject * _Class_Type() { return ptr__Class_Type; } -PyTypeObject * _CObject_Type() { return ptr__CObject_Type; } -PyTypeObject * _Complex_Type() { return ptr__Complex_Type; } -PyTypeObject * _Dict_Type() { return ptr__Dict_Type; } -PyTypeObject * _File_Type() { return ptr__File_Type; } -PyTypeObject * _Float_Type() { return ptr__Float_Type; } -PyTypeObject * _Function_Type() { return ptr__Function_Type; } -PyTypeObject * _Instance_Type() { return ptr__Instance_Type; } -PyTypeObject * _Bool_Type() { return ptr__Bool_Type; } -PyTypeObject * _Int_Type() { return ptr__Int_Type; } -PyTypeObject * _List_Type() { return ptr__List_Type; } -PyTypeObject * _Long_Type() { return ptr__Long_Type; } -PyTypeObject * _Method_Type() { return ptr__Method_Type; } -PyTypeObject * _Module_Type() { return ptr__Module_Type; } -PyTypeObject * _Range_Type() { return ptr__Range_Type; } -PyTypeObject * _Slice_Type() { return ptr__Slice_Type; } -PyTypeObject * _String_Type() { return ptr__String_Type; } -PyTypeObject * _TraceBack_Type(){ return ptr__TraceBack_Type; } -PyTypeObject * _Tuple_Type() { return ptr__Tuple_Type; } -PyTypeObject * _Type_Type() { return ptr__Type_Type; } - -#if PY_MAJOR_VERSION >= 2 -PyTypeObject * _Unicode_Type() { return ptr__Unicode_Type; } -#endif - -char *__Py_PackageContext() { return *ptr__Py_PackageContext; } - - -// -// wrap the Python Flag variables -// -int &_Py_DebugFlag() { return *ptr_Py_DebugFlag; } -int &_Py_InteractiveFlag() { return *ptr_Py_InteractiveFlag; } -int &_Py_OptimizeFlag() { return *ptr_Py_OptimizeFlag; } -int &_Py_NoSiteFlag() { return *ptr_Py_NoSiteFlag; } -int &_Py_TabcheckFlag() { return *ptr_Py_TabcheckFlag; } -int &_Py_VerboseFlag() { return *ptr_Py_VerboseFlag; } -#if PY_MAJOR_VERSION >= 2 -int &_Py_UnicodeFlag() { return *ptr_Py_UnicodeFlag; } -#endif - -void _XINCREF( PyObject *op ) -{ - // This function must match the contents of Py_XINCREF(op) - if( op == NULL ) - return; - -#ifdef Py_REF_DEBUG - (*ptr_Py_RefTotal)++; -#endif - (op)->ob_refcnt++; - -} - -void _XDECREF( PyObject *op ) -{ - // This function must match the contents of Py_XDECREF(op); - if( op == NULL ) - return; - -#ifdef P... [truncated message content]
Revision: 8083 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8083&view=rev Author: astraw Date: 2010年01月16日 19:20:03 +0000 (2010年1月16日) Log Message: ----------- Don't create minor ticks on top of existing major ticks (Neil Crighton). Modified Paths: -------------- trunk/matplotlib/CHANGELOG trunk/matplotlib/lib/matplotlib/ticker.py Modified: trunk/matplotlib/CHANGELOG =================================================================== --- trunk/matplotlib/CHANGELOG 2010年01月16日 19:19:14 UTC (rev 8082) +++ trunk/matplotlib/CHANGELOG 2010年01月16日 19:20:03 UTC (rev 8083) @@ -1,3 +1,6 @@ +2009年01月16日 Don't create minor ticks on top of existing major + ticks. Patch by Neil Crighton. -ADS + 2009年01月16日 Ensure three minor ticks always drawn (SF# 2924245). Patch by Neil Crighton. -ADS Modified: trunk/matplotlib/lib/matplotlib/ticker.py =================================================================== --- trunk/matplotlib/lib/matplotlib/ticker.py 2010年01月16日 19:19:14 UTC (rev 8082) +++ trunk/matplotlib/lib/matplotlib/ticker.py 2010年01月16日 19:20:03 UTC (rev 8083) @@ -1334,10 +1334,15 @@ vmin, vmax = self.axis.get_view_interval() if vmin > vmax: vmin,vmax = vmax,vmin + locs = locs[(vmin < locs) & (locs < vmax)] - return self.raise_if_exceeds(locs[(vmin < locs) & (locs < vmax)]) + # don't create minor ticks on top of existing major ticks + diff = 0.5 * abs(locs[1] - locs[0]) + locs = [l for l in locs if (np.abs(l - majorlocs) > diff).all()] + return self.raise_if_exceeds(np.array(locs)) + class OldAutoLocator(Locator): """ On autoscale this class picks the best MultipleLocator to set the This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8082 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8082&view=rev Author: astraw Date: 2010年01月16日 19:19:14 +0000 (2010年1月16日) Log Message: ----------- Ensure three minor ticks always drawn (SF# 2924245). Patch by Neil Crighton. Modified Paths: -------------- trunk/matplotlib/CHANGELOG trunk/matplotlib/lib/matplotlib/ticker.py Modified: trunk/matplotlib/CHANGELOG =================================================================== --- trunk/matplotlib/CHANGELOG 2010年01月16日 17:45:32 UTC (rev 8081) +++ trunk/matplotlib/CHANGELOG 2010年01月16日 19:19:14 UTC (rev 8082) @@ -1,3 +1,6 @@ +2009年01月16日 Ensure three minor ticks always drawn (SF# 2924245). Patch + by Neil Crighton. -ADS + 2010年01月16日 Applied patch by Ian Thomas to fix two contouring problems: now contourf handles interior masked regions, and the boundaries of line and filled contours coincide. - EF Modified: trunk/matplotlib/lib/matplotlib/ticker.py =================================================================== --- trunk/matplotlib/lib/matplotlib/ticker.py 2010年01月16日 17:45:32 UTC (rev 8081) +++ trunk/matplotlib/lib/matplotlib/ticker.py 2010年01月16日 19:19:14 UTC (rev 8082) @@ -1320,15 +1320,13 @@ except IndexError: raise ValueError('Need at least two major ticks to find minor ' 'tick locations') - # see whether major step should be divided by 5, 4 or 2. This + # see whether major step should be divided by 5, 4. This # should cover most cases. temp = float(('%e' % majorstep).split('e')[0]) if temp % 5 < 1e-10: minorstep = majorstep / 5. - elif temp % 2 < 1e-10: - minorstep = majorstep / 4. else: - minorstep = majorstep / 2. + minorstep = majorstep / 4. tmin = majorlocs[0] - majorstep tmax = majorlocs[-1] + majorstep This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
Revision: 8081 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=8081&view=rev Author: efiring Date: 2010年01月16日 17:45:32 +0000 (2010年1月16日) Log Message: ----------- Patch by Ian Thomas fixes 2 major cntr.c problems: Now line contours coincide with filled contour boundaries, and interior masked regions are handled correctly by contourf. Modified Paths: -------------- trunk/matplotlib/CHANGELOG trunk/matplotlib/examples/pylab_examples/contourf_demo.py trunk/matplotlib/src/cntr.c Modified: trunk/matplotlib/CHANGELOG =================================================================== --- trunk/matplotlib/CHANGELOG 2010年01月11日 19:55:26 UTC (rev 8080) +++ trunk/matplotlib/CHANGELOG 2010年01月16日 17:45:32 UTC (rev 8081) @@ -1,10 +1,14 @@ -2009年01月11日 The color of legend patch follows the rc parameters +2010年01月16日 Applied patch by Ian Thomas to fix two contouring + problems: now contourf handles interior masked regions, + and the boundaries of line and filled contours coincide. - EF + +2009年01月11日 The color of legend patch follows the rc parameters axes.facecolor and axes.edgecolor. -JJL -2009年01月11日 adjustable of Axes can be "box-forced" which allow +2009年01月11日 adjustable of Axes can be "box-forced" which allow sharing axes. -JJL -2009年01月11日 Add add_click and pop_click methods in +2009年01月11日 Add add_click and pop_click methods in BlockingContourLabeler. -JJL 2010年01月03日 Added rcParams['axes.color_cycle'] - EF Modified: trunk/matplotlib/examples/pylab_examples/contourf_demo.py =================================================================== --- trunk/matplotlib/examples/pylab_examples/contourf_demo.py 2010年01月11日 19:55:26 UTC (rev 8080) +++ trunk/matplotlib/examples/pylab_examples/contourf_demo.py 2010年01月16日 17:45:32 UTC (rev 8081) @@ -3,35 +3,14 @@ origin = 'lower' #origin = 'upper' -# The following controls only interior masking. -test_masking = False # There is a bug in filled contour masking with - # interior masks. +delta = 0.025 -if test_masking: - # Use a coarse grid so only a few masked points are needed. - delta = 0.5 -else: - delta = 0.025 - x = y = arange(-3.0, 3.01, delta) X, Y = meshgrid(x, y) Z1 = bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0) Z2 = bivariate_normal(X, Y, 1.5, 0.5, 1, 1) Z = 10 * (Z1 - Z2) -# interior badmask doesn't work yet for filled contours -if test_masking: - badmask = zeros(shape(Z)) - - badmask[5,5] = 1 - badmask[5,6] = 1 - Z[5,5] = 0 - Z[5,6] = 0 - - badmask[0,0] = 1 - Z[0,0] = 0 - Z = ma.array(Z, mask=badmask) - nr, nc = Z.shape # put NaNs in one corner: @@ -43,7 +22,11 @@ # mask another corner: Z[:nr//6, :nc//6] = ma.masked +# mask a circle in the middle: +interior = sqrt((X**2) + (Y**2)) < 0.5 +Z[interior] = ma.masked + # We are using automatic selection of contour levels; # this is usually not such a good idea, because they don't # occur on nice boundaries, but we do it here for purposes @@ -63,7 +46,7 @@ origin=origin, hold='on') -title('Nonsense (with 2 masked corners)') +title('Nonsense (3 masked regions)') xlabel('word length anomaly') ylabel('sentence length anomaly') @@ -87,7 +70,7 @@ colors = ('k',), linewidths = (3,), origin = origin) -title('Listed colors (with 2 masked corners)') +title('Listed colors (3 masked regions)') clabel(CS4, fmt = '%2.1f', colors = 'w', fontsize=14) colorbar(CS3) Modified: trunk/matplotlib/src/cntr.c =================================================================== --- trunk/matplotlib/src/cntr.c 2010年01月11日 19:55:26 UTC (rev 8080) +++ trunk/matplotlib/src/cntr.c 2010年01月16日 17:45:32 UTC (rev 8081) @@ -50,12 +50,14 @@ * The problem is that two disjoint curves cut through a saddle zone * (I reject the alternative of connecting the opposite points to make * a single self-intersecting curve, since those make ugly contour plots - * -- I've tried it). The real problem with saddle zones is that you - * need to communicate the connectivity decision you make back to the - * calling routine, since for the next contour level, we need to tell - * the contour tracer to make the same decision as on the previous - * level. The input/output triangulation array is the solution to this - * nasty problem. + * -- I've tried it). The solution is to determine the z value of the + * centre of the zone, which is the mean of the z values of the four + * corner points. If the centre z is higher than the contour level of + * interest and you are moving along the line with higher values on the + * left, turn right to leave the saddle zone. If the centre z is lower + * than the contour level turn left. Whether the centre z is higher + * than the 1 or 2 contour levels is stored in the saddle array so that + * it does not need to be recalculated in subsequent passes. * * Another complicating factor is that there may be logical holes in * the mesh -- zones which do not exist. We want our contours to stop @@ -175,6 +177,11 @@ * or not, z value 0, 1, or 2 -- is kept in a mesh sized data array */ typedef short Cdata; +/* information to decide on correct contour direction in saddle zones + * is stored in a mesh sized array. Only those entries corresponding + * to saddle zones have nonzero values in this array. */ +typedef char Saddle; + /* here is the minimum structure required to tell where we are in the * mesh sized data array */ typedef struct Csite Csite; @@ -189,8 +196,8 @@ long count; /* count of start markers visited */ double zlevel[2]; /* contour levels, zlevel[1]<=zlevel[0] * signals single level case */ - short *triangle; /* triangulation array for the mesh */ - char *reg; /* region array for the mesh (was int) */ + Saddle *saddle; /* saddle zone information for the mesh */ + char *reg; /* region array for the mesh (was int) */ Cdata *data; /* added by EF */ long edge0, left0; /* starting site on this curve for closure */ int level0; /* starting level for closure */ @@ -225,8 +232,6 @@ printf("\n"); } -/* triangle only takes values of -1, 0, 1, so it could be a signed char. */ -/* most or all of the longs probably could be converted to ints with no loss */ /* the Cdata array consists of the following bits: * Z_VALUE (2 bits) 0, 1, or 2 function value at point @@ -243,6 +248,7 @@ * OPEN_END marks an i-edge start point whose other endpoint is * on a boundary for the single level case * ALL_DONE marks final start point + * SLIT_DN_VISITED this slit downstroke hasn't/has been visited in pass 2 */ #define Z_VALUE 0x0003 #define ZONE_EX 0x0004 @@ -257,6 +263,7 @@ #define SLIT_DN 0x0800 #define OPEN_END 0x1000 #define ALL_DONE 0x2000 +#define SLIT_DN_VISITED 0x4000 /* some helpful macros to find points relative to a given directed * edge -- points are designated 0, 1, 2, 3 CCW around zone with 0 and @@ -272,6 +279,15 @@ enum {kind_zone, kind_edge1, kind_edge2, kind_slit_up, kind_slit_down, kind_start_slit=16} point_kinds; +/* Saddle zone array consists of the following bits: + * SADDLE_SET whether zone's saddle data has been set. + * SADDLE_GT0 whether z of centre of zone is higher than site->level[0]. + * SADDLE_GT1 whether z of centre of zone is higher than site->level[1]. + */ +#define SADDLE_SET 0x01 +#define SADDLE_GT0 0x02 +#define SADDLE_GT1 0x04 + /* ------------------------------------------------------------------------ */ /* these actually mark points */ @@ -313,18 +329,17 @@ long left0 = site->left0; int level0 = site->level0 == level; int two_levels = site->zlevel[1] > site->zlevel[0]; - short *triangle = site->triangle; + Saddle* saddle = site->saddle; const double *x = pass2 ? site->x : 0; const double *y = pass2 ? site->y : 0; - const double *z = pass2 ? site->z : 0; - double zlevel = pass2 ? site->zlevel[level] : 0.0; + const double *z = site->z; + double zlevel = site->zlevel[level]; double *xcp = pass2 ? site->xcp : 0; double *ycp = pass2 ? site->ycp : 0; short *kcp = pass2 ? site->kcp : 0; int z0, z1, z2, z3; - int keep_left = 0; /* flag to try to minimize curvature in saddles */ int done = 0; int n_kind; @@ -402,29 +417,28 @@ { if (z1 == z3) { - /* this is a saddle zone, need triangle to decide - * -- set triangle if not already decided for this zone */ + /* this is a saddle zone, determine whether to turn left or + * right depending on height of centre of zone relative to + * contour level. Set saddle[zone] if not already decided. */ long zone = edge + (left > 0 ? left : 0); - if (triangle) + if (!(saddle[zone] & SADDLE_SET)) { - if (!triangle[zone]) - { - if (keep_left) - triangle[zone] = jedge ? -1 : 1; - else - triangle[zone] = jedge ? 1 : -1; - } - if (triangle[zone] > 0 ? !jedge : jedge) - goto bkwd; + saddle[zone] = SADDLE_SET; + double zcentre = (z[p0] + z[p0+left] + z[p1] + z[p1+left])/4.0; + if (zcentre > site->zlevel[0]) + saddle[zone] |= + (two_levels && zcentre > site->zlevel[1]) + ? SADDLE_GT0 | SADDLE_GT1 : SADDLE_GT0; } - else - { - if (keep_left) - goto bkwd; - } + + int turnRight = level == 2 ? (saddle[zone] & SADDLE_GT1) + : (saddle[zone] & SADDLE_GT0); + if (z1 ^ (level == 2)) + turnRight = !turnRight; + if (!turnRight) + goto bkwd; } /* bend forward (right along curve) */ - keep_left = 1; jedge = !jedge; edge = p1 + (left > 0 ? left : 0); { @@ -437,7 +451,6 @@ { bkwd: /* bend backward (left along curve) */ - keep_left = 0; jedge = !jedge; edge = p0 + (left > 0 ? left : 0); { @@ -590,17 +603,27 @@ if (n_kind) kcp[n_kind] += kind_start_slit; return slit_cutter (site, 0, pass2); } + if (fwd < 0 && level0 && left < 0) + { + if (n_kind) kcp[n_kind] += kind_start_slit; + return slit_cutter (site, 0, pass2); + } return 3; } else if (pass2) { if (heads_up || (fwd < 0 && (data[edge] & SLIT_DN))) { - site->edge = edge; - site->left = left; - site->n = n + marked; - if (n_kind) kcp[n_kind] += kind_start_slit; - return slit_cutter (site, heads_up, pass2); + if (!heads_up && !(data[edge] & SLIT_DN_VISITED)) + data[edge] |= SLIT_DN_VISITED; + else + { + site->edge = edge; + site->left = left; + site->n = n + marked; + if (n_kind) kcp[n_kind] += kind_start_slit; + return slit_cutter (site, heads_up, pass2); + } } } else @@ -1181,6 +1204,8 @@ /* place immediate stop mark if nothing found */ if (!count) data[0] |= ALL_DONE; + else + for (i = 0; i < ijmax; ++i) site->saddle[i] = 0; /* initialize site */ site->edge0 = site->edge00 = site->edge = 0; @@ -1252,7 +1277,7 @@ if (site == NULL) return NULL; site->data = NULL; site->reg = NULL; - site->triangle = NULL; + site->saddle = NULL; site->xcp = NULL; site->ycp = NULL; site->kcp = NULL; @@ -1268,7 +1293,6 @@ { long ijmax = iMax * jMax; long nreg = iMax * jMax + iMax + 1; - long i; site->imax = iMax; site->jmax = jMax; @@ -1278,21 +1302,20 @@ PyMem_Free(site); return -1; } - site->triangle = (short *) PyMem_Malloc(sizeof(short) * ijmax); - if (site->triangle == NULL) + site->saddle = (Saddle*) PyMem_Malloc(sizeof(Saddle) * ijmax); + if (site->saddle == NULL) { PyMem_Free(site->data); PyMem_Free(site); return -1; } - for (i = 0; i < ijmax; i++) site->triangle[i] = 0; site->reg = NULL; if (mask != NULL) { site->reg = (char *) PyMem_Malloc(sizeof(char) * nreg); if (site->reg == NULL) { - PyMem_Free(site->triangle); + PyMem_Free(site->saddle); PyMem_Free(site->data); PyMem_Free(site); return -1; @@ -1311,7 +1334,7 @@ void cntr_del(Csite *site) { - PyMem_Free(site->triangle); + PyMem_Free(site->saddle); PyMem_Free(site->reg); PyMem_Free(site->data); PyMem_Free(site); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.