3636from matplotlib .transforms import Bbox , TransformedBbox , Affine2D
3737import cStringIO
3838
39+ import matplotlib .tight_bbox as tight_bbox
40+
3941class RendererBase :
4042 """An abstract base class to handle drawing/rendering operations.
4143
@@ -271,7 +273,6 @@ def _iter_collection(self, path_ids, cliprect, clippath, clippath_trans,
271273 gc .set_alpha (rgbFace [- 1 ])
272274 rgbFace = rgbFace [:3 ]
273275 gc .set_antialiased (antialiaseds [i % Naa ])
274-
275276 if Nurls :
276277 gc .set_url (urls [i % Nurls ])
277278
@@ -1426,7 +1427,16 @@ def print_figure(self, filename, dpi=None, facecolor='w', edgecolor='w',
14261427 if bbox_inches :
14271428 # call adjust_bbox to save only the given area
14281429 if bbox_inches == "tight" :
1429- # save the figure to estimate the bounding box
1430+ # when bbox_inches == "tight", it saves the figure
1431+ # twice. The first save command is just to estimate
1432+ # the bounding box of the figure. A stringIO object is
1433+ # used as a temporary file object, but it causes a
1434+ # problem for some backends (ps backend with
1435+ # usetex=True) if they expect a filename, not a
1436+ # file-like object. As I think it is best to change
1437+ # the backend to support file-like object, i'm going
1438+ # to leave it as it is. However, a better solution
1439+ # than stringIO seems to be needed. -JJL
14301440 result = getattr (self , method_name )(
14311441 cStringIO .StringIO (),
14321442 dpi = dpi ,
@@ -1439,9 +1449,12 @@ def print_figure(self, filename, dpi=None, facecolor='w', edgecolor='w',
14391449 pad = kwargs .pop ("pad_inches" , 0.1 )
14401450 bbox_inches = bbox_inches .padded (pad )
14411451
1442- restore_bbox = self ._adjust_bbox (self .figure , format ,
1443- bbox_inches )
1444-
1452+ restore_bbox = tight_bbox .adjust_bbox (self .figure , format ,
1453+ bbox_inches )
1454+
1455+ _bbox_inches_restore = (bbox_inches , restore_bbox )
1456+ else :
1457+ _bbox_inches_restore = None
14451458
14461459 try :
14471460 result = getattr (self , method_name )(
@@ -1450,6 +1463,7 @@ def print_figure(self, filename, dpi=None, facecolor='w', edgecolor='w',
14501463 facecolor = facecolor ,
14511464 edgecolor = edgecolor ,
14521465 orientation = orientation ,
1466+ bbox_inches_restore = _bbox_inches_restore ,
14531467 ** kwargs )
14541468 finally :
14551469 if bbox_inches and restore_bbox :
@@ -1463,106 +1477,6 @@ def print_figure(self, filename, dpi=None, facecolor='w', edgecolor='w',
14631477 return result
14641478
14651479
1466- def _adjust_bbox (self , fig , format , bbox_inches ):
1467- """
1468- Temporarily adjust the figure so that only the specified area
1469- (bbox_inches) is saved.
1470-
1471- It modifies fig.bbox, fig.bbox_inches,
1472- fig.transFigure._boxout, and fig.patch. While the figure size
1473- changes, the scale of the original figure is conserved. A
1474- function whitch restores the original values are returned.
1475- """
1476-
1477- origBbox = fig .bbox
1478- origBboxInches = fig .bbox_inches
1479- _boxout = fig .transFigure ._boxout
1480-
1481- asp_list = []
1482- locator_list = []
1483- for ax in fig .axes :
1484- pos = ax .get_position (original = False ).frozen ()
1485- locator_list .append (ax .get_axes_locator ())
1486- asp_list .append (ax .get_aspect ())
1487-
1488- def _l (a , r , pos = pos ): return pos
1489- ax .set_axes_locator (_l )
1490- ax .set_aspect ("auto" )
1491-
1492-
1493-
1494- def restore_bbox ():
1495-
1496- for ax , asp , loc in zip (fig .axes , asp_list , locator_list ):
1497- ax .set_aspect (asp )
1498- ax .set_axes_locator (loc )
1499-
1500- fig .bbox = origBbox
1501- fig .bbox_inches = origBboxInches
1502- fig .transFigure ._boxout = _boxout
1503- fig .transFigure .invalidate ()
1504- fig .patch .set_bounds (0 , 0 , 1 , 1 )
1505-
1506- if format in ["png" , "raw" , "rgba" ]:
1507- self ._adjust_bbox_png (fig , bbox_inches )
1508- return restore_bbox
1509- elif format in ["pdf" , "eps" ]:
1510- self ._adjust_bbox_pdf (fig , bbox_inches )
1511- return restore_bbox
1512- else :
1513- warnings .warn ("bbox_inches option for %s backend is not implemented yet." % (format ))
1514- return None
1515-
1516-
1517- def _adjust_bbox_png (self , fig , bbox_inches ):
1518- """
1519- _adjust_bbox for png (Agg) format
1520- """
1521-
1522- tr = fig .dpi_scale_trans
1523-
1524- _bbox = TransformedBbox (bbox_inches ,
1525- tr )
1526- x0 , y0 = _bbox .x0 , _bbox .y0
1527- fig .bbox_inches = Bbox .from_bounds (0 , 0 ,
1528- bbox_inches .width ,
1529- bbox_inches .height )
1530-
1531- x0 , y0 = _bbox .x0 , _bbox .y0
1532- w1 , h1 = fig .bbox .width , fig .bbox .height
1533- self .figure .transFigure ._boxout = Bbox .from_bounds (- x0 , - y0 ,
1534- w1 , h1 )
1535- self .figure .transFigure .invalidate ()
1536-
1537- fig .bbox = TransformedBbox (fig .bbox_inches , tr )
1538-
1539- fig .patch .set_bounds (x0 / w1 , y0 / h1 ,
1540- fig .bbox .width / w1 , fig .bbox .height / h1 )
1541-
1542-
1543- def _adjust_bbox_pdf (self , fig , bbox_inches ):
1544- """
1545- _adjust_bbox for pdf & eps format
1546- """
1547-
1548- tr = Affine2D ().scale (72 )
1549-
1550- _bbox = TransformedBbox (bbox_inches , tr )
1551-
1552- fig .bbox_inches = Bbox .from_bounds (0 , 0 ,
1553- bbox_inches .width ,
1554- bbox_inches .height )
1555- x0 , y0 = _bbox .x0 , _bbox .y0
1556- f = 72. / fig .dpi
1557- w1 , h1 = fig .bbox .width * f , fig .bbox .height * f
1558- self .figure .transFigure ._boxout = Bbox .from_bounds (- x0 , - y0 ,
1559- w1 , h1 )
1560- self .figure .transFigure .invalidate ()
1561-
1562- fig .bbox = TransformedBbox (fig .bbox_inches , tr )
1563-
1564- fig .patch .set_bounds (x0 / w1 , y0 / h1 ,
1565- fig .bbox .width / w1 , fig .bbox .height / h1 )
15661480
15671481
15681482 def get_default_filetype (self ):
0 commit comments