@@ -1565,16 +1565,81 @@ def get_edgecolor(self):
1565
1565
1566
1566
class Bar3DCollection (Poly3DCollection ):
1567
1567
"""
1568
- Bars (rectangular prisms) with constant square cross section, bases located
1569
- on z-plane at *z0*, arranged in a regular grid at *x*, *y* locations and
1570
- with height *z - z0*.
1571
- """
1568
+ A collection of 3D bars.
1569
+
1570
+ The bars are rectangular prisms with constant square cross-section.
1572
1571
1572
+ Attributes
1573
+ ----------
1574
+ xyz : numpy.ndarray
1575
+ Array of bar positions and heights.
1576
+ x: numpy.ndarray
1577
+ The x-coordinates of the bar bases.
1578
+ y: numpy.ndarray
1579
+ The y-coordinates of the bar bases.
1580
+ xy: numpy.ndarray
1581
+ The x and y coordinates of the bar bases.
1582
+ dxy : tuple[float, float]
1583
+ The width (dx) and depth (dy) of the bars in data units.
1584
+ dx : float
1585
+ The width of the bars in data units.
1586
+ dy : float
1587
+ The depth of the bars in data units.
1588
+ z : numpy.ndarray
1589
+ The height of the bars.
1590
+ z0 : float
1591
+ The z-coordinate of the bar bases.
1592
+ n_bars
1593
+ The number of bars.
1594
+
1595
+ Methods
1596
+ -------
1597
+ set_data:
1598
+ Set the data for the bars. Can also be used to set the color limits
1599
+ for color mapped data.
1600
+ """
1573
1601
_n_faces_base = 6
1574
1602
1575
1603
def __init__ (self , x , y , z , dxy = '0.8' , z0 = 0 , shade = True , lightsource = None ,
1576
1604
cmap = None , ** kws ):
1577
- #
1605
+ """
1606
+ Create a collection of 3D bars.
1607
+
1608
+ Bars (rectangular prisms) with constant square cross section, bases
1609
+ located on z-plane at *z0*, arranged in a regular grid at *x*, *y*
1610
+ locations and with height *z - z0*.
1611
+
1612
+ Parameters
1613
+ ----------
1614
+ x, y, z : array-like
1615
+ The coordinates of the bar bases.
1616
+ dxy : float or str or tuple[float|str, float|str], default: '0.8'
1617
+ The width and depth of the bars:
1618
+ - float: *dxy* is the width and depth of the bars. The bars are
1619
+ scaled to the data with this value. If *dxy* is a string, it must
1620
+ be parsable as a float.
1621
+ - (float, float): *dxy* is the width and depth of the bars in
1622
+ data units.
1623
+ z0 : float, default: 0
1624
+ Z-coordinate of the bases.
1625
+ shade : bool, default: True
1626
+ When *True*, the faces of the bars are shaded.
1627
+ lightsource : `~matplotlib.colors.LightSource`, optional
1628
+ The lightsource to use when *shade* is True.
1629
+ cmap : `~matplotlib.colors.Colormap`, optional
1630
+ Colormap for the bars.
1631
+ **kws
1632
+ Additional keyword arguments are passed to `.Poly3DCollection`.
1633
+
1634
+ Raises
1635
+ ------
1636
+ ValueError:
1637
+ When arrays have inconsistent shapes.
1638
+ TypeError:
1639
+ If the provided lightsource is not a `matplotlib.colors.LightSource`
1640
+ object.
1641
+ """
1642
+
1578
1643
x , y , z , z0 = np .ma .atleast_1d (x , y , z , z0 )
1579
1644
assert x .shape == y .shape == z .shape
1580
1645
@@ -1677,6 +1742,7 @@ def set_z0(self, z0):
1677
1742
1678
1743
@property
1679
1744
def n_bars (self ):
1745
+ """The number of bars in the collection."""
1680
1746
return self .x .size
1681
1747
1682
1748
def set_data (self , x = None , y = None , z = None , z0 = None , clim = None ):
@@ -2071,6 +2137,31 @@ def _camera_position(ax):
2071
2137
2072
2138
2073
2139
def resolve_dxy (step , xy , axis ):
2140
+ """
2141
+ Resolve the bar size from input step size and xy-positions along an axis of
2142
+ the array.
2143
+
2144
+ Parameters
2145
+ ----------
2146
+ step : float or str
2147
+ The bar size. If the step input is float, it is returned unchanged. If
2148
+ it is a string, it is converted to a float and multiplied
2149
+ by the grid step size along the specified *axis*.
2150
+ xy : array-like
2151
+ The coordinates of the bar centers.
2152
+ axis : int
2153
+ The axis along which to calculate the grid step size.
2154
+
2155
+ Returns
2156
+ -------
2157
+ float
2158
+ The resolved bar size.
2159
+
2160
+ Raises
2161
+ ------
2162
+ TypeError
2163
+ If *step* is not a float or a string.
2164
+ """
2074
2165
if isinstance (step , str ):
2075
2166
return float (step ) * _resolve_grid_step (xy , axis )
2076
2167
@@ -2101,15 +2192,35 @@ def _resolve_grid_step(x, axis=0):
2101
2192
2102
2193
2103
2194
def get_prism_face_zorder (ax , mask_occluded = True , nfaces = 4 ):
2104
- # compute panel sequence based on camera position
2195
+ """
2196
+ Compute the zorder of prism faces based on camera position.
2197
+
2198
+ The zorder determines the order in which the faces are drawn. Faces further
2199
+ from the camera are drawn first.
2200
+
2201
+ Parameters
2202
+ ----------
2203
+ ax : Axes3D
2204
+ The 3D axes.
2205
+ mask_occluded : bool, default: True
2206
+ Whether to mask occluded faces.
2207
+ nfaces : int, default: 4
2208
+ The number of faces of the prism's base shape. Eg: 4 for square bars, 6
2209
+ for hexagonal bars.
2210
+
2211
+ Returns
2212
+ -------
2213
+ zorder : ndarray
2214
+ The zorder of the prism faces.
2215
+ """
2105
2216
2106
- # these index positions are determined by the order of the faces returned
2107
- # by `_compute_verts`
2217
+ # NOTE: these index positions are determined by the order of the faces
2218
+ # returned by `_compute_verts`
2108
2219
base , top = nfaces , nfaces + 1
2109
2220
if ax .elev < 0 :
2110
2221
base , top = top , base
2111
2222
2112
- # this is to figure out which of the vertical faces to draw first
2223
+ # This is to figure out which of the vertical faces to draw first
2113
2224
angle_step = 360 / nfaces
2114
2225
zero = - angle_step / 2
2115
2226
flip = (np .abs (ax .elev ) % 180 > 90 )
@@ -2125,7 +2236,7 @@ def get_prism_face_zorder(ax, mask_occluded=True, nfaces=4):
2125
2236
sequence = [base , first , second , third ]
2126
2237
sequence = [* sequence , * np .setdiff1d (np .arange (nfaces ), sequence ), top ]
2127
2238
2128
- # reverse the panel sequence if elevation has flipped the axes by 180 multiple
2239
+ # reverse panel sequence if elevation has flipped the axes by 180 multiple
2129
2240
if np .abs (ax .elev ) % 360 > 180 :
2130
2241
sequence = sequence [::- 1 ]
2131
2242
@@ -2145,7 +2256,7 @@ def get_prism_face_zorder(ax, mask_occluded=True, nfaces=4):
2145
2256
# f'{sequence = :}',
2146
2257
# f'names = {list(np.take(names, sequence))}',
2147
2258
# f'{zorder = :}',
2148
- # f'zorder = {pformat( dict(zip(*cosort( zorder, names)[::-1])) )}',
2259
+ # f'zorder = {dict(sorted( zip(zorder, names)) [::-1])}',
2149
2260
# sep='\n')
2150
2261
2151
2262
return zorder
0 commit comments