def get_window_extent(self, renderer): self._newstyle = hasattr(renderer, 'draw_markers') if self._newstyle: x = self._x y = self._y else: x, y = self._get_plottable() x, y = self._transform.numerix_x_y(x, y) #x, y = self._transform.seq_x_y(x, y) left = min(x) bottom = min(y) width = max(x) - left height = max(y) - bottom # correct for marker size, if any if self._marker is not None: ms = self._markersize/72.0*self.figure.dpi.get() left -= ms/2 bottom -= ms/2 width += ms height += ms return lbwh_to_bbox( left, bottom, width, height)
def _get_layout_super(self, renderer, m): """ a special case optimization if a log super and angle = 0 Basically, mathtext is slow and we can do simple superscript layout "by hand" """ key = self.get_prop_tup() if self.cached.has_key(key): return self.cached[key] base, exponent = m.group(1), m.group(2) size = self._fontproperties.get_size_in_points() fpexp = self._fontproperties.copy() fpexp.set_size(0.7*size) wb,hb = renderer.get_text_width_height(base, self._fontproperties, False) we,he = renderer.get_text_width_height(exponent, fpexp, False) w = wb+we xb, yb = self._transform.xy_tup((self._x, self._y)) xe = xb+1.1*wb ye = yb+0.5*hb h = ye+he-yb if self._horizontalalignment=='center': xo = -w/2. elif self._horizontalalignment=='right': xo = -w else: xo = 0 if self._verticalalignment=='center': yo = -hb/2. elif self._verticalalignment=='top': yo = -hb else: yo = 0 xb += xo yb += yo xe += xo ye += yo bbox = lbwh_to_bbox(xb, yb, w, h) if renderer.flipy(): canvasw, canvash = renderer.get_canvas_width_height() yb = canvash-yb ye = canvash-ye val = ( bbox, ((base, xb, yb), (exponent, xe, ye, fpexp))) self.cached[key] = val return val
def get_window_extent(self, renderer=None): #return _unit_box if not self.get_visible(): return _unit_box if self._text == '': tx, ty = self._get_xy_display() return lbwh_to_bbox(tx,ty,0,0) if renderer is not None: self._renderer = renderer if self._renderer is None: raise RuntimeError('Cannot get window extent w/o renderer') angle = self.get_rotation() bbox, info = self._get_layout(self._renderer) return bbox
def get_window_extent(self, renderer=None): #return _unit_box if not self.get_visible(): return _unit_box if self._text == '': tx, ty = self._get_xy_display() return lbwh_to_bbox(tx, ty, 0, 0) if renderer is not None: self._renderer = renderer if self._renderer is None: raise RuntimeError('Cannot get window extent w/o renderer') angle = self.get_rotation() bbox, info = self._get_layout(self._renderer) return bbox
def _find_best_position(self, width, height, consider=None): """Determine the best location to place the legend. `consider` is a list of (x, y) pairs to consider as a potential lower-left corner of the legend. All are axes coords. """ assert self.isaxes # should always hold because function is only called internally verts, bboxes, lines = self._auto_legend_data() consider = [ self._loc_to_axes_coords(x, width, height) for x in range(1, len(self.codes)) ] tx, ty = self.legendPatch.xy candidates = [] for l, b in consider: legendBox = lbwh_to_bbox(l, b, width, height) badness = 0 badness = legendBox.count_contains(verts) ox, oy = l - tx, b - ty for bbox in bboxes: if legendBox.overlaps(bbox): badness += 1 for line in lines: if line_cuts_bbox(line, legendBox): badness += 1 if badness == 0: return ox, oy candidates.append((badness, (ox, oy))) # rather than use min() or list.sort(), do this so that we are assured # that in the case of two equal badnesses, the one first considered is # returned. minCandidate = candidates[0] for candidate in candidates: if candidate[0] < minCandidate[0]: minCandidate = candidate ox, oy = minCandidate[1] return ox, oy
def _find_best_position(self, width, height, consider=None): """Determine the best location to place the legend. `consider` is a list of (x, y) pairs to consider as a potential lower-left corner of the legend. All are axes coords. """ assert self.isaxes # should always hold because function is only called internally verts, bboxes, lines = self._auto_legend_data() consider = [self._loc_to_axes_coords(x, width, height) for x in range(1, len(self.codes))] tx, ty = self.legendPatch.xy candidates = [] for l, b in consider: legendBox = lbwh_to_bbox(l, b, width, height) badness = 0 badness = legendBox.count_contains(verts) ox, oy = l-tx, b-ty for bbox in bboxes: if legendBox.overlaps(bbox): badness += 1 for line in lines: if line_cuts_bbox(line, legendBox): badness += 1 if badness == 0: return ox, oy candidates.append((badness, (ox, oy))) # rather than use min() or list.sort(), do this so that we are assured # that in the case of two equal badnesses, the one first considered is # returned. minCandidate = candidates[0] for candidate in candidates: if candidate[0] < minCandidate[0]: minCandidate = candidate ox, oy = minCandidate[1] return ox, oy
def get_window_extent(self, renderer=None): if self._text == '': tx, ty = self._transform.xy_tup( (self._x, self._y) ) return lbwh_to_bbox(tx,ty,0,0) if renderer is not None: self._renderer = renderer if self._renderer is None: raise RuntimeError('Cannot get window extent w/o renderer') angle = self.get_rotation() if angle==0: m = self._rgxsuper.match(self._text) if m is not None: bbox, tmp = self._get_layout_super(self._renderer, m) return bbox bbox, info = self._get_layout(self._renderer) return bbox
def get_window_extent(self, renderer): x, y = self._get_numeric_clipped_data_in_range() x, y = self._transform.numerix_x_y(x, y) #x, y = self._transform.seq_x_y(x, y) left = min(x) bottom = min(y) width = max(x) - left height = max(y) - bottom # correct for marker size, if any if self._marker is not None: ms = self._markersize / 72.0 * self.figure.dpi.get() left -= ms / 2 bottom -= ms / 2 width += ms height += ms return lbwh_to_bbox(left, bottom, width, height)
def get_window_extent(self, renderer): x, y = self._get_numeric_clipped_data_in_range() x, y = self._transform.numerix_x_y(x, y) #x, y = self._transform.seq_x_y(x, y) left = min(x) bottom = min(y) width = max(x) - left height = max(y) - bottom # correct for marker size, if any if self._marker is not None: ms = self._markersize/72.0*self.figure.dpi.get() left -= ms/2 bottom -= ms/2 width += ms height += ms return lbwh_to_bbox( left, bottom, width, height)
def get_text_extent(self, text): """ Get the text extent in window coords """ return lbwh_to_bbox(0, 0, 1, 1) # your values here
def _get_layout(self, renderer): # layout the xylocs in display coords as if angle = zero and # then rotate them around self._x, self._y key = self.get_prop_tup() if self.cached.has_key(key): return self.cached[key] horizLayout = [] pad =2 thisx, thisy = self._transform.xy_tup( (self._x, self._y) ) width = 0 height = 0 xmin, ymin = thisx, thisy if self.is_math_text(): lines = [self._text] else: lines = self._text.split('\n') whs = [] for line in lines: w,h = renderer.get_text_width_height( line, self._fontproperties, ismath=self.is_math_text()) if not len(line) and not self.is_math_text(): # approx the height of empty line with tall char tmp, h = renderer.get_text_width_height( 'T', self._fontproperties, ismath=False) whs.append( (w,h) ) offsety = h+pad horizLayout.append((line, thisx, thisy, w, h)) thisy -= offsety # now translate down by text height, window coords width = max(width, w) ymin = horizLayout[-1][2] ymax = horizLayout[0][2] + horizLayout[0][-1] height = ymax-ymin xmax = xmin + width # get the rotation matrix M = self.get_rotation_matrix(xmin, ymin) # the corners of the unrotated bounding box cornersHoriz = ( (xmin, ymin), (xmin, ymax), (xmax, ymax), (xmax, ymin) ) offsetLayout = [] # now offset the individual text lines within the box if len(lines)>1: # do the multiline aligment malign = self._get_multialignment() for line, thisx, thisy, w, h in horizLayout: if malign=='center': offsetx = width/2.0-w/2.0 elif malign=='right': offsetx = width-w else: offsetx = 0 thisx += offsetx offsetLayout.append( (thisx, thisy )) else: # no additional layout needed offsetLayout = [ (thisx, thisy) for line, thisx, thisy, w, h in horizLayout] # now rotate the bbox cornersRotated = [dot(M,array([[thisx],[thisy],[1]])) for thisx, thisy in cornersHoriz] txs = [float(v[0][0]) for v in cornersRotated] tys = [float(v[1][0]) for v in cornersRotated] # compute the bounds of the rotated box xmin, xmax = min(txs), max(txs) ymin, ymax = min(tys), max(tys) width = xmax - xmin height = ymax - ymin # Now move the box to the targe position offset the display bbox by alignment halign = self._horizontalalignment valign = self._verticalalignment # compute the text location in display coords and the offsets # necessary to align the bbox with that location tx, ty = self._transform.xy_tup( (self._x, self._y) ) if halign=='center': offsetx = tx - (xmin + width/2.0) elif halign=='right': offsetx = tx - (xmin + width) else: offsetx = tx - xmin if valign=='center': offsety = ty - (ymin + height/2.0) elif valign=='top': offsety = ty - (ymin + height) else: offsety = ty - ymin xmin += offsetx xmax += offsetx ymin += offsety ymax += offsety bbox = lbwh_to_bbox(xmin, ymin, width, height) # now rotate the positions around the first x,y position xys = [dot(M,array([[thisx],[thisy],[1]])) for thisx, thisy in offsetLayout] tx = [float(v[0][0])+offsetx for v in xys] ty = [float(v[1][0])+offsety for v in xys] # now inverse transform back to data coords xys = [self._transform.inverse_xy_tup( xy ) for xy in zip(tx, ty)] xs, ys = zip(*xys) ret = bbox, zip(lines, whs, xs, ys) self.cached[key] = ret return ret
def get_text_extent(self, text): # is not used, can be removed? """ Get the text extent in window coords """ return lbwh_to_bbox(0,0,1,1) # your values here
return override # Extracted from Text's method to serve as a function def get_rotation(rotation): 'return the text angle as float' if rotation in ('horizontal', None): angle = 0. elif rotation == 'vertical': angle = 90. else: angle = float(rotation) return angle % 360 _unit_box = lbwh_to_bbox(0, 0, 1, 1) class Text(Artist): """ Handle storing and drawing of text in window or data coordinates """ # special case superscripting to speedup logplots _rgxsuper = re.compile('\$([\-+0-9]+)\^\{(-?[0-9]+)\}\$') zorder = 3 def __init__( self, x=0,
def get_text_extent(self, text): """ Get the text extent in window coords """ return lbwh_to_bbox(0,0,1,1) # your values here
override.update(kwargs) return override # Extracted from Text's method to serve as a function def get_rotation(rotation): 'return the text angle as float' if rotation in ('horizontal', None): angle = 0. elif rotation == 'vertical': angle = 90. else: angle = float(rotation) return angle%360 _unit_box = lbwh_to_bbox(0,0,1,1) class Text(Artist): """ Handle storing and drawing of text in window or data coordinates """ # special case superscripting to speedup logplots _rgxsuper = re.compile('\$([\-+0-9]+)\^\{(-?[0-9]+)\}\$') zorder = 3 def __init__(self, x=0, y=0, text='', color=None, # defaults to rc params verticalalignment='bottom', horizontalalignment='left',
def get_text_extent(self, text): # is not used, can be removed? """ Get the text extent in window coords """ return lbwh_to_bbox(0, 0, 1, 1) # your values here