12
12
import numpy as np
13
13
14
14
from matplotlib import (
15
- artist , colors as mcolors , lines , text as mtext , path as mpath )
15
+ artist , cbook , colors as mcolors , lines , text as mtext , path as mpath )
16
16
from matplotlib .collections import (
17
17
LineCollection , PolyCollection , PatchCollection , PathCollection )
18
18
from matplotlib .colors import Normalize
@@ -49,13 +49,12 @@ def get_dir_vector(zdir):
49
49
- 'y': equivalent to (0, 1, 0)
50
50
- 'z': equivalent to (0, 0, 1)
51
51
- *None*: equivalent to (0, 0, 0)
52
- - an iterable (x, y, z) is returned unchanged.
52
+ - an iterable (x, y, z) is converted to a NumPy array, if not already
53
53
54
54
Returns
55
55
-------
56
56
x, y, z : array-like
57
- The direction vector. This is either a numpy.array or *zdir* itself if
58
- *zdir* is already a length-3 iterable.
57
+ The direction vector.
59
58
"""
60
59
if zdir == 'x' :
61
60
return np .array ((1 , 0 , 0 ))
@@ -66,7 +65,7 @@ def get_dir_vector(zdir):
66
65
elif zdir is None :
67
66
return np .array ((0 , 0 , 0 ))
68
67
elif np .iterable (zdir ) and len (zdir ) == 3 :
69
- return zdir
68
+ return np . array ( zdir )
70
69
else :
71
70
raise ValueError ("'x', 'y', 'z', None or vector of length 3 expected" )
72
71
@@ -95,22 +94,55 @@ def __init__(self, x=0, y=0, z=0, text='', zdir='z', **kwargs):
95
94
mtext .Text .__init__ (self , x , y , text , ** kwargs )
96
95
self .set_3d_properties (z , zdir )
97
96
97
+ def get_position_3d (self ):
98
+ """Return the (x, y, z) position of the text."""
99
+ return self ._x , self ._y , self ._z
100
+
101
+ def set_position_3d (self , xyz , zdir = None ):
102
+ """
103
+ Set the (*x*, *y*, *z*) position of the text.
104
+
105
+ Parameters
106
+ ----------
107
+ xyz : (float, float, float)
108
+ The position in 3D space.
109
+ zdir : {'x', 'y', 'z', None, 3-tuple}
110
+ The direction of the text. If unspecified, the zdir will not be
111
+ changed.
112
+ """
113
+ super ().set_position (xyz [:2 ])
114
+ self .set_z (xyz [2 ])
115
+ if zdir is not None :
116
+ self ._dir_vec = get_dir_vector (zdir )
117
+
118
+ def set_z (self , z ):
119
+ """
120
+ Set the *z* position of the text.
121
+
122
+ Parameters
123
+ ----------
124
+ z : float
125
+ """
126
+ self ._z = z
127
+ self .stale = True
128
+
98
129
def set_3d_properties (self , z = 0 , zdir = 'z' ):
99
- x , y = self .get_position ()
100
- self ._position3d = np .array ((x , y , z ))
130
+ self ._z = z
101
131
self ._dir_vec = get_dir_vector (zdir )
102
132
self .stale = True
103
133
104
134
@artist .allow_rasterization
105
135
def draw (self , renderer ):
136
+ position3d = np .array ((self ._x , self ._y , self ._z ))
106
137
proj = proj3d .proj_trans_points (
107
- [self ._position3d , self ._position3d + self ._dir_vec ], renderer .M )
138
+ [position3d , position3d + self ._dir_vec ],
139
+ renderer .M )
108
140
dx = proj [0 ][1 ] - proj [0 ][0 ]
109
141
dy = proj [1 ][1 ] - proj [1 ][0 ]
110
142
angle = math .degrees (math .atan2 (dy , dx ))
111
- self . set_position (( proj [0 ][0 ], proj [1 ][0 ]))
112
- self . set_rotation ( _norm_text_angle (angle ))
113
- mtext .Text .draw (self , renderer )
143
+ with cbook . _setattr_cm ( self , _x = proj [0 ][0 ], _y = proj [1 ][0 ],
144
+ _rotation = _norm_text_angle (angle )):
145
+ mtext .Text .draw (self , renderer )
114
146
self .stale = False
115
147
116
148
def get_tightbbox (self , renderer ):
0 commit comments