4
4
====
5
5
6
6
"""
7
- import numpy as np
8
- import matplotlib .colors as colors
7
+
8
+ import matplotlib .artist as artist
9
9
import matplotlib .patches as patches
10
- import matplotlib .mathtext as mathtext
11
10
import matplotlib .pyplot as plt
12
- import matplotlib .artist as artist
13
- import matplotlib .image as image
11
+ from matplotlib .transforms import IdentityTransform
14
12
15
13
16
14
class ItemProperties :
@@ -21,12 +19,8 @@ def __init__(self, fontsize=14, labelcolor='black', bgcolor='yellow',
21
19
self .bgcolor = bgcolor
22
20
self .alpha = alpha
23
21
24
- self .labelcolor_rgb = colors .to_rgba (labelcolor )[:3 ]
25
- self .bgcolor_rgb = colors .to_rgba (bgcolor )[:3 ]
26
-
27
22
28
23
class MenuItem (artist .Artist ):
29
- parser = mathtext .MathTextParser ("Bitmap" )
30
24
padx = 5
31
25
pady = 5
32
26
@@ -37,102 +31,70 @@ def __init__(self, fig, labelstr, props=None, hoverprops=None,
37
31
self .set_figure (fig )
38
32
self .labelstr = labelstr
39
33
40
- if props is None :
41
- props = ItemProperties ()
42
-
43
- if hoverprops is None :
44
- hoverprops = ItemProperties ()
45
-
46
- self .props = props
47
- self .hoverprops = hoverprops
48
-
49
- self .on_select = on_select
50
-
51
- x , self .depth = self .parser .to_mask (
52
- labelstr , fontsize = props .fontsize , dpi = fig .dpi )
53
-
54
- if props .fontsize != hoverprops .fontsize :
34
+ self .props = props if props is not None else ItemProperties ()
35
+ self .hoverprops = (
36
+ hoverprops if hoverprops is not None else ItemProperties ())
37
+ if self .props .fontsize != self .hoverprops .fontsize :
55
38
raise NotImplementedError (
56
39
'support for different font sizes not implemented' )
57
40
58
- self .labelwidth = x .shape [1 ]
59
- self .labelheight = x .shape [0 ]
60
-
61
- self .labelArray = np .zeros ((x .shape [0 ], x .shape [1 ], 4 ))
62
- self .labelArray [:, :, - 1 ] = x / 255.
41
+ self .on_select = on_select
63
42
64
- self .label = image .FigureImage (fig , origin = 'upper' )
65
- self .label .set_array (self .labelArray )
43
+ # Setting the transform to IdentityTransform() lets us specify
44
+ # coordinates directly in pixels.
45
+ self .label = fig .text (0 , 0 , labelstr , transform = IdentityTransform (),
46
+ size = props .fontsize )
47
+ self .text_bbox = self .label .get_window_extent (
48
+ fig .canvas .get_renderer ())
66
49
67
- # we'll update these later
68
- self .rect = patches .Rectangle ((0 , 0 ), 1 , 1 )
50
+ self .rect = patches .Rectangle ((0 , 0 ), 1 , 1 ) # Will be updated later.
69
51
70
52
self .set_hover_props (False )
71
53
72
54
fig .canvas .mpl_connect ('button_release_event' , self .check_select )
73
55
74
56
def check_select (self , event ):
75
- over , junk = self .rect .contains (event )
57
+ over , _ = self .rect .contains (event )
76
58
if not over :
77
59
return
78
-
79
60
if self .on_select is not None :
80
61
self .on_select (self )
81
62
82
- def set_extent (self , x , y , w , h ):
83
- print (x , y , w , h )
84
- self .rect .set_x (x )
85
- self .rect .set_y (y )
86
- self .rect .set_width (w )
87
- self .rect .set_height (h )
88
-
89
- self .label .ox = x + self .padx
90
- self .label .oy = y - self .depth + self .pady / 2.
91
-
63
+ def set_extent (self , x , y , w , h , depth ):
64
+ self .rect .set (x = x , y = y , width = w , height = h )
65
+ self .label .set (position = (x + self .padx , y + depth + self .pady / 2 ))
92
66
self .hover = False
93
67
94
68
def draw (self , renderer ):
95
69
self .rect .draw (renderer )
96
70
self .label .draw (renderer )
97
71
98
72
def set_hover_props (self , b ):
99
- if b :
100
- props = self .hoverprops
101
- else :
102
- props = self .props
103
-
104
- r , g , b = props .labelcolor_rgb
105
- self .labelArray [:, :, 0 ] = r
106
- self .labelArray [:, :, 1 ] = g
107
- self .labelArray [:, :, 2 ] = b
108
- self .label .set_array (self .labelArray )
73
+ props = self .hoverprops if b else self .props
74
+ self .label .set (color = props .labelcolor )
109
75
self .rect .set (facecolor = props .bgcolor , alpha = props .alpha )
110
76
111
77
def set_hover (self , event ):
112
78
"""
113
79
Update the hover status of event and return whether it was changed.
114
80
"""
115
- b , junk = self .rect .contains (event )
116
-
81
+ b , _ = self .rect .contains (event )
117
82
changed = (b != self .hover )
118
-
119
83
if changed :
120
84
self .set_hover_props (b )
121
-
122
85
self .hover = b
123
86
return changed
124
87
125
88
126
89
class Menu :
127
90
def __init__ (self , fig , menuitems ):
128
91
self .figure = fig
129
- fig .suppressComposite = True
130
92
131
93
self .menuitems = menuitems
132
- self .numitems = len (menuitems )
133
94
134
- maxw = max (item .labelwidth for item in menuitems )
135
- maxh = max (item .labelheight for item in menuitems )
95
+ maxw = max (item .text_bbox .width for item in menuitems )
96
+ maxh = max (item .text_bbox .height for item in menuitems )
97
+ depth = max (- item .text_bbox .y0 for item in menuitems )
136
98
137
99
x0 = 100
138
100
y0 = 400
@@ -144,20 +106,16 @@ def __init__(self, fig, menuitems):
144
106
left = x0
145
107
bottom = y0 - maxh - MenuItem .pady
146
108
147
- item .set_extent (left , bottom , width , height )
109
+ item .set_extent (left , bottom , width , height , depth )
148
110
149
111
fig .artists .append (item )
150
112
y0 -= maxh + MenuItem .pady
151
113
152
114
fig .canvas .mpl_connect ('motion_notify_event' , self .on_move )
153
115
154
116
def on_move (self , event ):
155
- draw = False
156
- for item in self .menuitems :
157
- draw = item .set_hover (event )
158
- if draw :
159
- self .figure .canvas .draw ()
160
- break
117
+ if any (item .set_hover (event ) for item in self .menuitems ):
118
+ self .figure .canvas .draw ()
161
119
162
120
163
121
fig = plt .figure ()
0 commit comments