Re: [Matplotlib-users] How to make a grid of (plot) grids?
On Tue, Jan 4, 2011 at 6:17 PM, Paul Ivanov wrote: > Gf B, on 2011-01-04 12:31, wrote: > > On Mon, Jan 3, 2011 at 3:53 PM, Paul Ivanov > wrote: > > Gf B, on 2011-01-03 15:23, wrote: > > > > Can such a "grid of grids" be done with matplotlib? If so, could > someone > > > > show me how? > > > > > > You'll be able to group the inner grids visually by adjusting the > > > spacing. As far as getting the spines to only outline the outer > > > grid, and not the inner grid - I think you'll have to do it > > > manually by hiding the appropriate spines for the inner subplots. > > > > > > > This sort of ad-hoc manual tweaking is what I was hoping to avoid. > > > > What would it take to implement a "true" grid-of-grids function in > > matplotlib? What I mean by this is a function that can arrange in a grid > > not only plots but also other grids. (Is this a question for the devel > > group?) > > I think the true grid-of-grids functunality is already > implemented. Here's a replication of your Mathematica plots: > > > import numpy as np > import matplotlib.pyplot as plt > import matplotlib.gridspec as gridspec > from itertools import product > > def squiggle_xy(a, b, c, d, i=np.linspace(0.0, 2*np.pi, 200)): >return np.sin(i*a)*np.cos(i*b), np.sin(i*c)*np.cos(i*d) > > f = plt.figure(figsize=(8, 8)) > > # gridspec inside gridspec > outer_grid = gridspec.GridSpec(4, 4, wspace=0.0, hspace=0.0) > for i in xrange(16): >inner_grid = gridspec.GridSpecFromSubplotSpec(3, 3, >subplot_spec=outer_grid[i], wspace=0.0, hspace=0.0) >a, b = int(i/4)+1,i%4+1 > for j, (c, d) in enumerate(product(range(1, 4), repeat=2)): > ax = plt.Subplot(f, inner_grid[j]) >ax.plot(*squiggle_xy(a, b, c, d)) > ax.set_xticks([]) >ax.set_yticks([]) > f.add_subplot(ax) > > all_axes = f.get_axes() > > #show only the outside spines > for ax in all_axes: >for sp in ax.spines.values(): >sp.set_visible(False) >if ax.is_first_row(): >ax.spines['top'].set_visible(True) >if ax.is_last_row(): >ax.spines['bottom'].set_visible(True) >if ax.is_first_col(): >ax.spines['left'].set_visible(True) >if ax.is_last_col(): >ax.spines['right'].set_visible(True) > > plt.show() > > > It's a matter of taste, but I think you can get away hiding all > spines, and just setting the hspace and wspace for the outer_grid > to some small value (this is what I meant by 'adjusting the > spacing'). > > I'll send a patch to the devel list shortly adding this example > with the following documentation > > A Complex Nested GridSpec using SubplotSpec > === > Here's a more sophisticated example of nested gridspect where we put > a box around outer 4x4 grid, by hiding appropriate spines in each of the > inner 3x3 grids. > > it'll be placed on the gridspec page, after this section: > > http://matplotlib.sourceforge.net/users/gridspec.html#gridspec-using-subplotspec > > best, > -- > Paul Ivanov > 314 address only used for lists, off-list direct email at: > http://pirsquared.org | GPG/PGP key id: 0x0F3E28F7 > > Just to add, because it is related, another tool that gives you advanced control over your axes is the AxesGrid toolkit: http://matplotlib.sourceforge.net/mpl_toolkits/axes_grid/index.html#toolkit-axesgrid-index However, gridspec should be exactly what you need for this particular problem. Ben Root -- Learn how Oracle Real Application Clusters (RAC) One Node allows customers to consolidate database storage, standardize their database environment, and, should the need arise, upgrade to a full multi-node Oracle RAC database without downtime or disruption http://p.sf.net/sfu/oracle-sfdevnl___ Matplotlib-users mailing list Matplotlib-users@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-users
Re: [Matplotlib-users] How to make a grid of (plot) grids?
Gf B, on 2011-01-04 12:31, wrote: > On Mon, Jan 3, 2011 at 3:53 PM, Paul Ivanov wrote: > Gf B, on 2011-01-03 15:23, wrote: > > > Can such a "grid of grids" be done with matplotlib? If so, could someone > > > show me how? > > > > You'll be able to group the inner grids visually by adjusting the > > spacing. As far as getting the spines to only outline the outer > > grid, and not the inner grid - I think you'll have to do it > > manually by hiding the appropriate spines for the inner subplots. > > > > This sort of ad-hoc manual tweaking is what I was hoping to avoid. > > What would it take to implement a "true" grid-of-grids function in > matplotlib? What I mean by this is a function that can arrange in a grid > not only plots but also other grids. (Is this a question for the devel > group?) I think the true grid-of-grids functunality is already implemented. Here's a replication of your Mathematica plots: import numpy as np import matplotlib.pyplot as plt import matplotlib.gridspec as gridspec from itertools import product def squiggle_xy(a, b, c, d, i=np.linspace(0.0, 2*np.pi, 200)): return np.sin(i*a)*np.cos(i*b), np.sin(i*c)*np.cos(i*d) f = plt.figure(figsize=(8, 8)) # gridspec inside gridspec outer_grid = gridspec.GridSpec(4, 4, wspace=0.0, hspace=0.0) for i in xrange(16): inner_grid = gridspec.GridSpecFromSubplotSpec(3, 3, subplot_spec=outer_grid[i], wspace=0.0, hspace=0.0) a, b = int(i/4)+1,i%4+1 for j, (c, d) in enumerate(product(range(1, 4), repeat=2)): ax = plt.Subplot(f, inner_grid[j]) ax.plot(*squiggle_xy(a, b, c, d)) ax.set_xticks([]) ax.set_yticks([]) f.add_subplot(ax) all_axes = f.get_axes() #show only the outside spines for ax in all_axes: for sp in ax.spines.values(): sp.set_visible(False) if ax.is_first_row(): ax.spines['top'].set_visible(True) if ax.is_last_row(): ax.spines['bottom'].set_visible(True) if ax.is_first_col(): ax.spines['left'].set_visible(True) if ax.is_last_col(): ax.spines['right'].set_visible(True) plt.show() It's a matter of taste, but I think you can get away hiding all spines, and just setting the hspace and wspace for the outer_grid to some small value (this is what I meant by 'adjusting the spacing'). I'll send a patch to the devel list shortly adding this example with the following documentation A Complex Nested GridSpec using SubplotSpec === Here's a more sophisticated example of nested gridspect where we put a box around outer 4x4 grid, by hiding appropriate spines in each of the inner 3x3 grids. it'll be placed on the gridspec page, after this section: http://matplotlib.sourceforge.net/users/gridspec.html#gridspec-using-subplotspec best, -- Paul Ivanov 314 address only used for lists, off-list direct email at: http://pirsquared.org | GPG/PGP key id: 0x0F3E28F7 signature.asc Description: Digital signature -- Learn how Oracle Real Application Clusters (RAC) One Node allows customers to consolidate database storage, standardize their database environment, and, should the need arise, upgrade to a full multi-node Oracle RAC database without downtime or disruption http://p.sf.net/sfu/oracle-sfdevnl___ Matplotlib-users mailing list Matplotlib-users@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-users
[Matplotlib-users] whitespace around custom projection
Hi all, I've created a custom projection for drawing Lambert plots on two adjacent hemispheres, copied closely from the custom_projection_example [1], and attached here. The basics are working I think, but the axes objects have too much whitespace around them, and I can't immediately work out what approach to take to reduce it to something reasonable. Can anyone point me in the right direction? Ultimately I'm hoping to be able to put several of these plots together in a figure, which is currently not practical. (Also, pcolor doesn't work as I expect, but I need to play around with that a bit more before I know what question I need to ask of the list.) Thanks, Angus. [1] http://matplotlib.sourceforge.net/examples/api/custom_projection_example.html -- AJC McMorland Post-doctoral research fellow Neurobiology, University of Pittsburgh from matplotlib.axes import Axes from matplotlib import cbook, docstring from matplotlib.patches import Patch, cbook, transforms, artist from matplotlib.path import Path from matplotlib.ticker import Formatter, Locator, NullLocator, \ FixedLocator, NullFormatter from matplotlib.transforms import Affine2D, Affine2DBase, Bbox, \ BboxTransformTo, IdentityTransform, Transform, TransformWrapper from matplotlib.projections import register_projection, PolarAxes from matplotlib.projections.geo import GeoAxes, LambertAxes import matplotlib.spines as mspines import matplotlib.axis as maxis from copy import copy from split_lambert_transforms import SplitLambertTransform import numpy as np class TwoCircle(Patch): """ A scale-free ellipse. """ def __str__(self): return "TwoCircle(%s, %s; %s)" % (self.center[0], self.center[1], self.radius) @docstring.dedent_interpd def __init__(self, xy, radius, **kwargs): """ xy : array_like center of two circles radius : scalar size of each circle Valid kwargs are: %(Patch)s """ Patch.__init__(self, **kwargs) self.center = xy self.radius = radius self.width = 2 * radius self.height = 2. * radius path = copy(Path.unit_circle()) n_pts = path.vertices.shape[0] path.vertices = np.tile(path.vertices, [2,1]) path.vertices[:n_pts,0] -= 1 path.vertices[n_pts:,0] += 1 path.codes = np.tile(path.codes, [2]) self._path = path # Note: This cannot be calculated until this is added to an Axes self._patch_transform = transforms.IdentityTransform() def _recompute_transform(self): """NOTE: This cannot be called until after this has been added to an Axes, otherwise unit conversion will fail. This makes it very important to call the accessor method and not directly access the transformation member variable. """ center = (self.convert_xunits(self.center[0]), self.convert_yunits(self.center[1])) width = self.convert_xunits(self.width) height = self.convert_yunits(self.height) self._patch_transform = transforms.Affine2D() \ .scale(width * 0.5, height * 0.5) \ .translate(*center) def get_path(self): """ Return the vertices of the rectangle """ return self._path def get_patch_transform(self): self._recompute_transform() return self._patch_transform def contains(self,ev): if ev.x is None or ev.y is None: return False,{} x, y = self.get_transform().inverted().transform_point((ev.x, ev.y)) r = self.radius return (((x - r) * (x - r) + y * y) <= r*r) or \ (((x + r) * (x + r) + y * y) <= r*r), {} class SplitLambertAxes(Axes): """ A custom class for the split Lambert projection, an equal-area map projection using one circle for each hemisphere. """ name = 'split_lambert' resolution = 75 def __init__(self, *args, **kwargs): Axes.__init__(self, *args, **kwargs) self.set_aspect(1., adjustable='box', anchor='C') self.cla() def _init_axis(self): self.xaxis = maxis.XAxis(self) # xaxis == theta == latitude self.yaxis = maxis.YAxis(self) # yaxis == phi == longitude # Do not register xaxis or yaxis with spines -- as done in # Axes._init_axis() -- until SplitLambertAxes.xaxis.cla() works. # self.spines['split_lambert'].register_axis(self.yaxis) self._update_transScale() def cla(self): """ Override to set up some reasonable defaults. """ # Don't forget to call the base class Axes.cla(self) # Set up a default grid spacing self.set_theta_grid(np.pi/4.) self.set_phi_grid(np.pi/2.) self.set_phi_grid_ends(np.pi/8.) # Turn off minor ticking altogether self.xaxis.set_mino
Re: [Matplotlib-users] Bug in boxplot/mlab.prctile
2011/1/1 OKB (not okblacke) : > I noticed that the boxplot function incorrectly calculates the > location of the median line in each box. As a simple example, plotting > the dataset [1, 2, 3, 4] incorrectly plots the median line at 3. It seems to work fine in matplotlib 1.0.0: u...@host:~$ python Python 2.6.6 (r266:84292, Sep 15 2010, 16:22:56) [GCC 4.4.5] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> import matplotlib as mpl >>> mpl.__version__ '1.0.0' >>> import matplotlib.pyplot as plt >>> import matplotlib.mlab as mlab >>> plt.ion() >>> plt.boxplot([1, 2, 3, 4]) {'medians': [], 'fliers': [, ], 'whiskers': [, ], 'boxes': [], 'caps': [, ]} >>> plt.grid() >>> plt.boxplot([1, 2, 3, 4]) {'medians': [], 'fliers': [, ], 'whiskers': [, ], 'boxes': [], 'caps': [, ]} >>> plt.grid() >>> # See attached image. ... >>> mlab.prctile([1, 2, 3, 4]) array([ 1. , 1.75, 2.5 , 3.25, 4. ]) Goyo > > It also seems that the quartile calculations for the box are a > little peculiar. I have seen some discussion in old mailing list > postings about mlab.prctile and its ways of calculating percentiles, > which are different than those of some other software. > > I'm aware that there is legitimate disagreement about the "best" > way to calculate the quartiles. However, it seems to me that mlab's way > is still not any of these possibly-correct ways, because it uses int() > or nparray.astype(int) to coerce the percentile result to an integer > index. This TRUNCATES the floating-point result. No accepted quantile- > calculating method that I'm aware of does this; they all ROUND instead > of truncating (if they want to coerce to an integer index at all, in > order to produce a quantile value that is an element of the data set), > or in some cases they round uniformly up for the lower quartile and > down for the upper. You can see a summary of different methods at > http://www.amstat.org/publications/jse/v14n3/langford.html ; the method > used by mlab does not appear to agree with any of these. > > I would suggest that mlab.prctile be fixed to conform to some one > or other of these methods, rather than adding to the proliferation of > approaches to quantile-calculation. Is there any motivation for always > truncating to integer (other that "it's quicker to type" :-)? > > Also, regardless of these quartile issues, there is, as far as I'm > aware, no one who denies that the median of a (sorted) data set with an > even number of values is the mean of the middle two values. Since numpy > is already a dependency for matplotlib, boxplot shouldn't use > mlab.prctile at all to decide where to plot the median line -- just use > numpy.median. > > Thanks, > -- > --OKB (not okblacke) > Brendan Barnwell > "Do not follow where the path may lead. Go, instead, where there is > no path, and leave a trail." > --author unknown <>-- Learn how Oracle Real Application Clusters (RAC) One Node allows customers to consolidate database storage, standardize their database environment, and, should the need arise, upgrade to a full multi-node Oracle RAC database without downtime or disruption http://p.sf.net/sfu/oracle-sfdevnl___ Matplotlib-users mailing list Matplotlib-users@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-users
Re: [Matplotlib-users] How to make a grid of (plot) grids?
On Mon, Jan 3, 2011 at 3:53 PM, Paul Ivanov wrote: Hi, Paul. Thanks for the links! Gf B, on 2011-01-03 15:23, wrote: > > Can such a "grid of grids" be done with matplotlib? If so, could someone > > show me how? > > You'll be able to group the inner grids visually by adjusting the > spacing. As far as getting the spines to only outline the outer > grid, and not the inner grid - I think you'll have to do it > manually by hiding the appropriate spines for the inner subplots. > This sort of ad-hoc manual tweaking is what I was hoping to avoid. What would it take to implement a "true" grid-of-grids function in matplotlib? What I mean by this is a function that can arrange in a grid not only plots but also other grids. (Is this a question for the devel group?) G. -- Learn how Oracle Real Application Clusters (RAC) One Node allows customers to consolidate database storage, standardize their database environment, and, should the need arise, upgrade to a full multi-node Oracle RAC database without downtime or disruption http://p.sf.net/sfu/oracle-sfdevnl___ Matplotlib-users mailing list Matplotlib-users@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/matplotlib-users