15
15
16
16
from matplotlib import (
17
17
_api , artist , cbook , colors as mcolors , lines , text as mtext ,
18
- path as mpath , rcParams )
18
+ path as mpath , _val_or_rc )
19
19
from matplotlib .collections import (
20
20
Collection , LineCollection , PolyCollection , PatchCollection , PathCollection )
21
21
from matplotlib .patches import Patch
@@ -646,31 +646,36 @@ def __init__(
646
646
:class:`~matplotlib.collections.PatchCollection`. In addition,
647
647
keywords *zs=0* and *zdir='z'* are available.
648
648
649
- The keyword argument *depthshade* is available to
650
- indicate whether or not to shade the patches in order to
651
- give the appearance of depth (default is *True*).
652
- This is typically desired in scatter plots.
653
-
654
- *depthshade_minalpha* sets the minimum alpha value applied by
655
- depth-shading.
649
+ Parameters
650
+ ----------
651
+ zs : float or array of floats
652
+ The location or locations to place the patches in the collection
653
+ along the *zdir* axis.
654
+ zdir : {'x', 'y', 'z'}
655
+ Plane to plot patches orthogonal to.
656
+ All patches must have the same direction.
657
+ See `.get_dir_vector` for a description of the values.
658
+ depthshade : bool, default: :rc:`axes3d.depthshade`
659
+ Whether to shade the patches in order to give the appearance of
660
+ depth.
661
+ depthshade_minalpha : float, default: :rc:`axes3d.depthshade_minalpha`
662
+ Sets the minimum alpha value used by depth-shading.
663
+ axlim_clip : bool, default: False
664
+ Whether to hide patches with a vertex outside the axes view limits.
665
+ kwargs :
666
+ Additional keyword arguments are the same as for
667
+ :class:`~matplotlib.collections.PatchCollection`.
656
668
"""
657
- if depthshade is None :
658
- depthshade = rcParams ['axes3d.depthshade' ]
659
- if depthshade_minalpha is None :
660
- depthshade_minalpha = rcParams ['axes3d.depthshade_minalpha' ]
661
- self ._depthshade = depthshade
662
- self ._depthshade_minalpha = depthshade_minalpha
669
+ self ._depthshade = _val_or_rc (depthshade , 'axes3d.depthshade' )
670
+ self ._depthshade_minalpha = _val_or_rc (depthshade_minalpha ,
671
+ 'axes3d.depthshade_minalpha' )
663
672
super ().__init__ (* args , ** kwargs )
664
673
self .set_3d_properties (zs , zdir , axlim_clip )
665
674
666
675
def get_depthshade (self ):
667
676
return self ._depthshade
668
677
669
- def set_depthshade (
670
- self ,
671
- depthshade ,
672
- depthshade_minalpha = None ,
673
- ):
678
+ def set_depthshade (self , depthshade , depthshade_minalpha = None ):
674
679
"""
675
680
Set whether depth shading is performed on collection members.
676
681
@@ -679,14 +684,12 @@ def set_depthshade(
679
684
depthshade : bool
680
685
Whether to shade the patches in order to give the appearance of
681
686
depth.
682
- depthshade_minalpha : float, default: None
687
+ depthshade_minalpha : float, default: :rc:`axes3d.depthshade_minalpha`
683
688
Sets the minimum alpha value used by depth-shading.
684
- If None, use the value from rcParams['axes3d.depthshade_minalpha'].
685
689
"""
686
- if depthshade_minalpha is None :
687
- depthshade_minalpha = rcParams ['axes3d.depthshade_minalpha' ]
688
690
self ._depthshade = depthshade
689
- self ._depthshade_minalpha = depthshade_minalpha
691
+ self ._depthshade_minalpha = _val_or_rc (depthshade_minalpha ,
692
+ 'axes3d.depthshade_minalpha' )
690
693
self .stale = True
691
694
692
695
def set_sort_zpos (self , val ):
@@ -743,11 +746,7 @@ def do_3d_projection(self):
743
746
744
747
def _maybe_depth_shade_and_sort_colors (self , color_array ):
745
748
color_array = (
746
- _zalpha (
747
- color_array ,
748
- self ._vzs ,
749
- min_alpha = self ._depthshade_minalpha ,
750
- )
749
+ _zalpha (color_array , self ._vzs , min_alpha = self ._depthshade_minalpha )
751
750
if self ._vzs is not None and self ._depthshade
752
751
else color_array
753
752
)
@@ -776,18 +775,12 @@ def _get_data_scale(X, Y, Z):
776
775
X, Y, Z : masked arrays
777
776
The data to estimate the scale of.
778
777
"""
779
- # Account for empty datasets. Assume that X Y and Z have the same number
780
- # of elements.
781
- if not np .ma .count (X ):
778
+ # Account for empty datasets.
779
+ if not np .ma .count (X ) or not np .ma .count (Y ) or not np .ma .count (Z ):
782
780
return 0
783
781
784
782
# Estimate the scale using the RSS of the ranges of the dimensions
785
- # Note that we don't use np.ma.ptp() because we otherwise get a build
786
- # warning about handing empty arrays.
787
- ptp_x = X .max () - X .min ()
788
- ptp_y = Y .max () - Y .min ()
789
- ptp_z = Z .max () - Z .min ()
790
- return np .sqrt (ptp_x ** 2 + ptp_y ** 2 + ptp_z ** 2 )
783
+ return np .sqrt (np .ma .ptp (X ) ** 2 + np .ma .ptp (Y ) ** 2 + np .ma .ptp (Z ) ** 2 )
791
784
792
785
793
786
class Path3DCollection (PathCollection ):
@@ -815,20 +808,29 @@ def __init__(
815
808
:class:`~matplotlib.collections.PathCollection`. In addition,
816
809
keywords *zs=0* and *zdir='z'* are available.
817
810
818
- Also, the keyword argument *depthshade* is available to
819
- indicate whether or not to shade the patches in order to
820
- give the appearance of depth (default is *True*).
821
- This is typically desired in scatter plots.
822
-
823
- *depthshade_minalpha* sets the minimum alpha value applied by
824
- depth-shading.
811
+ Parameters
812
+ ----------
813
+ zs : float or array of floats
814
+ The location or locations to place the paths in the collection
815
+ along the *zdir* axis.
816
+ zdir : {'x', 'y', 'z'}
817
+ Vector to plot paths orthogonal to.
818
+ All paths must have the same direction.
819
+ See `.get_dir_vector` for a description of the values.
820
+ depthshade : bool, default: :rc:`axes3d.depthshade`
821
+ Whether to shade the paths in order to give the appearance of
822
+ depth.
823
+ depthshade_minalpha : float, default: :rc:`axes3d.depthshade_minalpha`
824
+ Sets the minimum alpha value used by depth-shading.
825
+ axlim_clip : bool, default: False
826
+ Whether to hide paths with a vertex outside the axes view limits.
827
+ kwargs :
828
+ Additional keyword arguments are the same as for
829
+ :class:`~matplotlib.collections.PathCollection`.
825
830
"""
826
- if depthshade is None :
827
- depthshade = rcParams ['axes3d.depthshade' ]
828
- if depthshade_minalpha is None :
829
- depthshade_minalpha = rcParams ['axes3d.depthshade_minalpha' ]
830
- self ._depthshade = depthshade
831
- self ._depthshade_minalpha = depthshade_minalpha
831
+ self ._depthshade = _val_or_rc (depthshade , 'axes3d.depthshade' )
832
+ self ._depthshade_minalpha = _val_or_rc (depthshade_minalpha ,
833
+ 'axes3d.depthshade_minalpha' )
832
834
self ._in_draw = False
833
835
super ().__init__ (* args , ** kwargs )
834
836
self .set_3d_properties (zs , zdir , axlim_clip )
@@ -854,7 +856,7 @@ def set_3d_properties(self, zs, zdir, axlim_clip=False):
854
856
The location or locations to place the paths in the collection
855
857
along the *zdir* axis.
856
858
zdir : {'x', 'y', 'z'}
857
- Plane to plot paths orthogonal to.
859
+ Vector to plot paths orthogonal to.
858
860
All paths must have the same direction.
859
861
See `.get_dir_vector` for a description of the values.
860
862
axlim_clip : bool, default: False
@@ -907,11 +909,7 @@ def set_linewidth(self, lw):
907
909
def get_depthshade (self ):
908
910
return self ._depthshade
909
911
910
- def set_depthshade (
911
- self ,
912
- depthshade ,
913
- depthshade_minalpha = None ,
914
- ):
912
+ def set_depthshade (self , depthshade , depthshade_minalpha = None ):
915
913
"""
916
914
Set whether depth shading is performed on collection members.
917
915
@@ -920,13 +918,12 @@ def set_depthshade(
920
918
depthshade : bool
921
919
Whether to shade the patches in order to give the appearance of
922
920
depth.
923
- depthshade_minalpha : float
921
+ depthshade_minalpha : float, default: :rc:`axes3d.depthshade_minalpha`
924
922
Sets the minimum alpha value used by depth-shading.
925
923
"""
926
- if depthshade_minalpha is None :
927
- depthshade_minalpha = rcParams ['axes3d.depthshade_minalpha' ]
928
924
self ._depthshade = depthshade
929
- self ._depthshade_minalpha = depthshade_minalpha
925
+ self ._depthshade_minalpha = _val_or_rc (depthshade_minalpha ,
926
+ 'axes3d.depthshade_minalpha' )
930
927
self .stale = True
931
928
932
929
def do_3d_projection (self ):
@@ -989,15 +986,15 @@ def _maybe_depth_shade_and_sort_colors(self, color_array):
989
986
color_array ,
990
987
self ._vzs ,
991
988
min_alpha = self ._depthshade_minalpha ,
992
- _data_scale = self ._data_scale ,
989
+ data_scale = self ._data_scale ,
993
990
)
994
991
995
992
# Adjust the order of the color_array using the _z_markers_idx,
996
993
# which has been sorted by z-depth
997
994
if len (color_array ) > 1 :
998
995
color_array = color_array [self ._z_markers_idx ]
999
996
1000
- return mcolors .to_rgba_array (color_array )
997
+ return mcolors .to_rgba_array (color_array , self . _alpha )
1001
998
1002
999
def get_facecolor (self ):
1003
1000
return self ._maybe_depth_shade_and_sort_colors (super ().get_facecolor ())
@@ -1017,7 +1014,7 @@ def patch_collection_2d_to_3d(
1017
1014
zdir = "z" ,
1018
1015
depthshade = None ,
1019
1016
axlim_clip = False ,
1020
- * args ,
1017
+ * ,
1021
1018
depthshade_minalpha = None ,
1022
1019
):
1023
1020
"""
@@ -1035,12 +1032,10 @@ def patch_collection_2d_to_3d(
1035
1032
zdir : {'x', 'y', 'z'}
1036
1033
The axis in which to place the patches. Default: "z".
1037
1034
See `.get_dir_vector` for a description of the values.
1038
- depthshade : bool, default: None
1035
+ depthshade : bool, default: :rc:`axes3d.depthshade`
1039
1036
Whether to shade the patches to give a sense of depth.
1040
- If None, use the value from rcParams['axes3d.depthshade'].
1041
- depthshade_minalpha : float, default: None
1037
+ depthshade_minalpha : float, default: :rc:`axes3d.depthshade_minalpha`
1042
1038
Sets the minimum alpha value used by depth-shading.
1043
- If None, use the value from rcParams['axes3d.depthshade_minalpha'].
1044
1039
axlim_clip : bool, default: False
1045
1040
Whether to hide patches with a vertex outside the axes view limits.
1046
1041
"""
@@ -1049,12 +1044,9 @@ def patch_collection_2d_to_3d(
1049
1044
col ._offset_zordered = None
1050
1045
elif isinstance (col , PatchCollection ):
1051
1046
col .__class__ = Patch3DCollection
1052
- if depthshade is None :
1053
- depthshade = rcParams ['axes3d.depthshade' ]
1054
- if depthshade_minalpha is None :
1055
- depthshade_minalpha = rcParams ['axes3d.depthshade_minalpha' ]
1056
1047
col ._depthshade = depthshade
1057
- col ._depthshade_minalpha = depthshade_minalpha
1048
+ col ._depthshade_minalpha = _val_or_rc (depthshade_minalpha ,
1049
+ 'axes3d.depthshade_minalpha' )
1058
1050
col ._in_draw = False
1059
1051
col .set_3d_properties (zs , zdir , axlim_clip )
1060
1052
@@ -1395,12 +1387,7 @@ def rotate_axes(xs, ys, zs, zdir):
1395
1387
return xs , ys , zs
1396
1388
1397
1389
1398
- def _zalpha (
1399
- colors ,
1400
- zs ,
1401
- min_alpha = 0.3 ,
1402
- _data_scale = None ,
1403
- ):
1390
+ def _zalpha (colors , zs , min_alpha = 0.3 , data_scale = None ):
1404
1391
"""Modify the alphas of the color list according to depth."""
1405
1392
1406
1393
if len (colors ) == 0 or len (zs ) == 0 :
@@ -1409,13 +1396,13 @@ def _zalpha(
1409
1396
# Alpha values beyond the range 0-1 inclusive make no sense, so clip them
1410
1397
min_alpha = np .clip (min_alpha , 0 , 1 )
1411
1398
1412
- if _data_scale is None or _data_scale == 0 :
1399
+ if data_scale is None or data_scale == 0 :
1413
1400
# Don't scale the alpha values since we have no valid data scale for reference
1414
1401
sats = np .ones_like (zs )
1415
1402
1416
1403
else :
1417
1404
# Deeper points have an increasingly transparent appearance
1418
- sats = np .clip (1 - (zs - min (zs )) / _data_scale , min_alpha , 1 )
1405
+ sats = np .clip (1 - (zs - min (zs )) / data_scale , min_alpha , 1 )
1419
1406
1420
1407
rgba = np .broadcast_to (mcolors .to_rgba_array (colors ), (len (zs ), 4 ))
1421
1408
0 commit comments