def adjust_bbox_pdf(fig, bbox_inches): """ adjust_bbox for pdf & eps format """ if fig._cachedRenderer.__class__.__name__ == "RendererPgf": tr = Affine2D().scale(fig.dpi) f = 1. else: tr = Affine2D().scale(72) f = 72. / fig.dpi _bbox = TransformedBbox(bbox_inches, tr) fig.bbox_inches = Bbox.from_bounds(0, 0, bbox_inches.width, bbox_inches.height) x0, y0 = _bbox.x0, _bbox.y0 w1, h1 = fig.bbox.width * f, fig.bbox.height * f fig.transFigure._boxout = Bbox.from_bounds(-x0, -y0, w1, h1) fig.transFigure.invalidate() fig.bbox = TransformedBbox(fig.bbox_inches, tr) fig.patch.set_bounds(x0 / w1, y0 / h1, fig.bbox.width / w1, fig.bbox.height / h1)
def _find_best_position(self, width, height, renderer, 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 display coords. """ # should always hold because function is only called internally assert self.isaxes verts, bboxes, lines, offsets = self._auto_legend_data() bbox = Bbox.from_bounds(0, 0, width, height) if consider is None: consider = [self._get_anchored_bbox(x, bbox, self.get_bbox_to_anchor(), renderer) for x in range(1, len(self.codes))] # tx, ty = self.legendPatch.get_x(), self.legendPatch.get_y() candidates = [] for l, b in consider: legendBox = Bbox.from_bounds(l, b, width, height) badness = 0 # XXX TODO: If markers are present, it would be good to # take their into account when checking vertex overlaps in # the next line. badness = legendBox.count_contains(verts) badness += legendBox.count_contains(offsets) badness += legendBox.count_overlaps(bboxes) for line in lines: # FIXME: the following line is ill-suited for lines # that 'spiral' around the center, because the bbox # may intersect with the legend even if the line # itself doesn't. One solution would be to break up # the line into its straight-segment components, but # this may (or may not) result in a significant # slowdown if lines with many vertices are present. if line.intersects_bbox(legendBox): badness += 1 ox, oy = l, b if badness == 0: return ox, oy candidates.append((badness, (l, b))) # 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. # NOTE: list.sort() is stable.But leave as it is for now. -JJL 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, renderer, 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 display coords. """ assert self.isaxes # should always hold because function is only called internally verts, bboxes, lines = self._auto_legend_data() bbox = Bbox.from_bounds(0, 0, width, height) consider = [self._get_anchored_bbox(x, bbox, self.get_bbox_to_anchor(), renderer) for x in range(1, len(self.codes))] candidates = [] for l, b in consider: legendBox = Bbox.from_bounds(l, b, width, height) badness = 0 badness = legendBox.count_contains(verts) badness += legendBox.count_overlaps(bboxes) for line in lines: if line.intersects_bbox(legendBox): badness += 1 ox, oy = l, b if badness == 0: return ox, oy candidates.append((badness, (l, b))) minCandidate = candidates[0] for candidate in candidates: if candidate[0] < minCandidate[0]: minCandidate = candidate ox, oy = minCandidate[1] return ox, oy
def connect_bbox(bbox1, bbox2, loc1, loc2=None): """ Helper function to obtain a Path from one bbox to another. Parameters ---------- bbox1, bbox2 : `matplotlib.transforms.Bbox` Bounding boxes to connect. loc1 : {1, 2, 3, 4} Corner of *bbox1* to use. Valid values are:: 'upper right' : 1, 'upper left' : 2, 'lower left' : 3, 'lower right' : 4 loc2 : {1, 2, 3, 4}, optional Corner of *bbox2* to use. If None, defaults to *loc1*. Valid values are:: 'upper right' : 1, 'upper left' : 2, 'lower left' : 3, 'lower right' : 4 Returns ------- path : `matplotlib.path.Path` A line segment from the *loc1* corner of *bbox1* to the *loc2* corner of *bbox2*. """ if isinstance(bbox1, Rectangle): transform = bbox1.get_transform() bbox1 = Bbox.from_bounds(0, 0, 1, 1) bbox1 = TransformedBbox(bbox1, transform) if isinstance(bbox2, Rectangle): transform = bbox2.get_transform() bbox2 = Bbox.from_bounds(0, 0, 1, 1) bbox2 = TransformedBbox(bbox2, transform) if loc2 is None: loc2 = loc1 x1, y1 = BboxConnector.get_bbox_edge_pos(bbox1, loc1) x2, y2 = BboxConnector.get_bbox_edge_pos(bbox2, loc2) verts = [[x1, y1], [x2, y2]] codes = [Path.MOVETO, Path.LINETO] return Path(verts, codes)
def _find_best_position(self, width, height, renderer, 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 display coords. """ # should always hold because function is only called internally assert self.isaxes verts, bboxes, lines = self._auto_legend_data() bbox = Bbox.from_bounds(0, 0, width, height) consider = [self._get_anchored_bbox(x, bbox, self.get_bbox_to_anchor(), renderer) for x in range(1, len(self.codes))] #tx, ty = self.legendPatch.get_x(), self.legendPatch.get_y() candidates = [] for l, b in consider: legendBox = Bbox.from_bounds(l, b, width, height) badness = 0 badness = legendBox.count_contains(verts) badness += legendBox.count_overlaps(bboxes) for line in lines: if line.intersects_bbox(legendBox): badness += 1 ox, oy = l, b if badness == 0: return ox, oy candidates.append((badness, (l, b))) # 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. # NOTE: list.sort() is stable.But leave as it is for now. -JJL minCandidate = candidates[0] for candidate in candidates: if candidate[0] < minCandidate[0]: minCandidate = candidate ox, oy = minCandidate[1] return ox, oy
def __init__(self, width, height, dpi): if __debug__: verbose.report('RendererAgg.__init__', 'debug-annoying') RendererBase.__init__(self) self.texd = maxdict(50) # a cache of tex image rasters self._fontd = maxdict(50) self.dpi = dpi self.width = width self.height = height if __debug__: verbose.report('RendererAgg.__init__ width=%s, height=%s'%(width, height), 'debug-annoying') self._renderer = _RendererAgg(int(width), int(height), dpi, debug=False) if __debug__: verbose.report('RendererAgg.__init__ _RendererAgg done', 'debug-annoying') #self.draw_path = self._renderer.draw_path # see below self.draw_markers = self._renderer.draw_markers self.draw_path_collection = self._renderer.draw_path_collection self.draw_quad_mesh = self._renderer.draw_quad_mesh self.draw_image = self._renderer.draw_image self.copy_from_bbox = self._renderer.copy_from_bbox self.tostring_rgba_minimized = self._renderer.tostring_rgba_minimized self.mathtext_parser = MathTextParser('Agg') self.bbox = Bbox.from_bounds(0, 0, self.width, self.height) if __debug__: verbose.report('RendererAgg.__init__ done', 'debug-annoying')
def connect_bbox(bbox1, bbox2, loc1, loc2=None): if isinstance(bbox1, Rectangle): transform = bbox1.get_transfrom() bbox1 = Bbox.from_bounds(0, 0, 1, 1) bbox1 = TransformedBbox(bbox1, transform) if isinstance(bbox2, Rectangle): transform = bbox2.get_transform() bbox2 = Bbox.from_bounds(0, 0, 1, 1) bbox2 = TransformedBbox(bbox2, transform) if loc2 is None: loc2 = loc1 x1, y1 = BboxConnector.get_bbox_edge_pos(bbox1, loc1) x2, y2 = BboxConnector.get_bbox_edge_pos(bbox2, loc2) verts = [[x1, y1], [x2,y2]] codes = [Path.MOVETO, Path.LINETO] return Path(verts, codes)
def _offset(w, h, xd, yd, renderer, fontsize=fontsize, self=self): bbox = Bbox.from_bounds(0, 0, w, h) borderpad = self.borderpad * fontsize bbox_to_anchor = self.get_bbox_to_anchor() x0, y0 = self._get_anchored_bbox(self.loc, bbox, bbox_to_anchor, borderpad) return x0 + xd, y0 + yd
def set_bbox_to_anchor(self, bbox, transform=None): """ set the bbox that the legend will be anchored. *bbox* can be a BboxBase instance, a tuple of [left, bottom, width, height] in the given transform (normalized axes coordinate if None), or a tuple of [left, bottom] where the width and height will be assumed to be zero. """ if bbox is None: self._bbox_to_anchor = None return elif isinstance(bbox, BboxBase): self._bbox_to_anchor = bbox else: try: l = len(bbox) except TypeError: raise ValueError("Invalid argument for bbox : %s" % str(bbox)) if l == 2: bbox = [bbox[0], bbox[1], 0, 0] self._bbox_to_anchor = Bbox.from_bounds(*bbox) if transform is None: transform = BboxTransformTo(self.parent.bbox) self._bbox_to_anchor = TransformedBbox(self._bbox_to_anchor, transform)
def draw_plot(self): if self._doRePlot: self._resizeCreateContent() if self.background is None: self.background = self.canvas.copy_from_bbox(self.ax.bbox) self.foo += 1 #self.y = numpy.cos(numpy.arange(0.0,1.0,0.1)+self.foo*0.1) # Optimization on the blitting: we compute the box where the changes happen changes_box = None for i in range(len(self.lines)): data=self.channels[i].getNext() if len(data[1])>0: if self.autolim: print self.autolim[0], data[1], self.autolim[1] self.autolim = [ min(self.autolim[0], min(data[1])), \ max(self.autolim[1], max(data[1])) ] else: self.autolim = [ min(data[1]), min(data[1]) ] if changes_box is None: changes_box = Bbox.unit() print '>>>>>>>>' print data[0], data[1] changes_box.update_from_data(numpy.array(data[0]), \ numpy.array(data[1]), ignore=changes_box.is_unit()) if not self._doRePlot and len(data[0]) > 0 : end = data[0][-1] if end > self.begin+self.span: self.begin += self.span self._doRePlot = True print 'do replot' self.lines[i].set_data(data[0], data[1]) else: self.lines[i].set_data([], []) if not changes_box: return #self.canvas.restore_region(self.background) for line in self.lines: self.ax.draw_artist(line) #print line.get_transform() tr = line.get_transform() changes_box_inframe = changes_box.transformed(tr) box_padding = 5 (x,y,l,w) = changes_box_inframe.bounds changes_box_inframe = Bbox.from_bounds(x-box_padding, \ y-box_padding, l+2*box_padding, w+2*box_padding) #print t0 = time.time() self.canvas.blit(None) #self.canvas.blit(changes_box_inframe) self.blit_time += time.time() - t0
def get_window_extent(self, renderer): ''' get the bounding box in display space. ''' self._update_offset_func(renderer) w, h, xd, yd = self.get_extent(renderer) ox, oy = self.get_offset(w, h, xd, yd, renderer) return Bbox.from_bounds(ox-xd, oy-yd, w, h)
def _calculate_bbox(self): r = self.renderer bboxes = self.xaxis.get_window_extent(r), self.yaxis.get_window_extent(r), self.subplot.bbox all_bbox = Bbox.union(bboxes) (x0, y0), (x1, y1) = all_bbox.get_points() w = x1 - x0 h = y1 - y0 all_bbox = Bbox.from_bounds(x0, y0, w * 1.02, h * 1.02) return all_bbox
def adjust_bbox_pdf(fig, bbox_inches): """ adjust_bbox for pdf & eps format """ tr = Affine2D().scale(72) _bbox = TransformedBbox(bbox_inches, tr) fig.bbox_inches = Bbox.from_bounds(0, 0, bbox_inches.width, bbox_inches.height) x0, y0 = _bbox.x0, _bbox.y0 f = 72. / fig.dpi w1, h1 = fig.bbox.width*f, fig.bbox.height*f fig.transFigure._boxout = Bbox.from_bounds(-x0, -y0, w1, h1) fig.transFigure.invalidate() fig.bbox = TransformedBbox(fig.bbox_inches, tr) fig.patch.set_bounds(x0/w1, y0/h1, fig.bbox.width/w1, fig.bbox.height/h1)
def _find_best_position(self, width, height, renderer, 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 display coords. """ # should always hold because function is only called internally assert self.isaxes verts, bboxes, lines, offsets = self._auto_legend_data() if self._loc_used_default and verts.shape[0] > 200000: # this size results in a 3+ second render time on a good machine cbook._warn_external( 'Creating legend with loc="best" can be slow with large ' 'amounts of data.' ) bbox = Bbox.from_bounds(0, 0, width, height) if consider is None: consider = [self._get_anchored_bbox(x, bbox, self.get_bbox_to_anchor(), renderer) for x in range(1, len(self.codes))] candidates = [] for idx, (l, b) in enumerate(consider): legendBox = Bbox.from_bounds(l, b, width, height) badness = 0 # XXX TODO: If markers are present, it would be good to # take them into account when checking vertex overlaps in # the next line. badness = (legendBox.count_contains(verts) + legendBox.count_contains(offsets) + legendBox.count_overlaps(bboxes) + sum(line.intersects_bbox(legendBox, filled=False) for line in lines)) if badness == 0: return l, b # Include the index to favor lower codes in case of a tie. candidates.append((badness, idx, (l, b))) _, _, (l, b) = min(candidates) return l, b
def _findoffset_loc(self, width, height, xdescent, ydescent, renderer): "Heper function to locate the legend using the location code" if iterable(self._loc) and len(self._loc)==2: fx, fy = self._loc bbox = self.get_bbox_to_anchor() x, y = bbox.x0 + bbox.width * fx, bbox.y0 + bbox.height * fy else: bbox = Bbox.from_bounds(0, 0, width, height) x, y = self._get_anchored_bbox(self._loc, bbox, self.get_bbox_to_anchor(), renderer) return x+xdescent, y+ydescent
def adjust_bbox_png(fig, bbox_inches): """ adjust_bbox for png (Agg) format """ tr = fig.dpi_scale_trans _bbox = TransformedBbox(bbox_inches, tr) x0, y0 = _bbox.x0, _bbox.y0 fig.bbox_inches = Bbox.from_bounds(0, 0, bbox_inches.width, bbox_inches.height) x0, y0 = _bbox.x0, _bbox.y0 w1, h1 = fig.bbox.width, fig.bbox.height fig.transFigure._boxout = Bbox.from_bounds(-x0, -y0, w1, h1) fig.transFigure.invalidate() fig.bbox = TransformedBbox(fig.bbox_inches, tr) fig.patch.set_bounds(x0/w1, y0/h1, fig.bbox.width/w1, fig.bbox.height/h1)
def _translate_to(self, g, xvalue, yvalue): layout = self.layout (x0data, y0data, wdata, hdata) = g.dataLim.transformed(g.transData).bounds x0, y0, w, h = g.bbox.bounds x0_new = (xvalue * wdata + x0data) if xvalue is not None else x0 # Need to revert scroll bar to have minimum on bottom y0_new = (-yvalue * hdata + y0data - h) if yvalue is not None else y0 result = Bbox.from_bounds(x0_new, y0_new, w, h).transformed(g.transData.inverted()) g.set_xlim(*result.intervalx) g.set_ylim(*result.intervaly)
def __init__(self, width, height, dpi): RendererBase.__init__(self) self.dpi = dpi self.width = width self.height = height self._renderer = _RendererAgg(int(width), int(height), dpi) self._filter_renderers = [] self._update_methods() self.mathtext_parser = MathTextParser('Agg') self.bbox = Bbox.from_bounds(0, 0, self.width, self.height)
def test_updated(): # Copy this bbox, since we're going to modify it later. large = Bbox.from_bounds(*LARGE.bounds) small_to_medium = BboxTransform(SMALL, MEDIUM) small_to_large = BboxTransform(SMALL, large) # Sanity check before manipulating bounds. _test_transform_corners(small_to_large, SMALL, LARGE) _test_transform_corners(small_to_medium, SMALL, MEDIUM) # Update bounds of large bbox and test updated transform. large.bounds = MEDIUM.bounds _test_transform_corners(small_to_large, SMALL, MEDIUM)
def _findoffset_loc(self, width, height, xdescent, ydescent, renderer): "Heper function to locate the legend using the location code" if iterable(self._loc) and len(self._loc)==2: # when loc is a tuple of axes(or figure) coordinates. fx, fy = self._loc bbox = self.parent.bbox x, y = bbox.x0 + bbox.width * fx, bbox.y0 + bbox.height * fy else: bbox = Bbox.from_bounds(0, 0, width, height) x, y = self._get_anchored_bbox(self._loc, bbox, self.parent.bbox, renderer) return x+xdescent, y+ydescent
def plot_polygon(ax, fig): ymin, ymax = ax.get_ylim() xy = [[-1 * log2(50), 0], [5, ymax * 0.35], [20, ymax * 0.35], [0, 0]] poly = Polygon(xy, facecolor='#E6E6E6', edgecolor='none', zorder=1) ax.add_patch(poly) bb_data = Bbox.from_bounds(5, ymax * 0.35, 15, ymax * 0.55) disp_coords = ax.transData.transform(bb_data) fig_coords = fig.transFigure.inverted().transform(disp_coords) ax2 = fig.add_axes(Bbox(fig_coords), zorder=5) return ax, ax2
def __call__(self, ax, renderer): self.axes = ax fontsize = renderer.points_to_pixels(self.prop.get_size_in_points()) self._update_offset_func(renderer, fontsize) width, height, xdescent, ydescent = self.get_extent(renderer) px, py = self.get_offset(width, height, 0, 0, renderer) bbox_canvas = Bbox.from_bounds(px, py, width, height) tr = ax.figure.transFigure.inverted() bb = TransformedBbox(bbox_canvas, tr) return bb
def _findoffset(self, width, height, xdescent, ydescent, renderer): "Helper function to locate the legend" if self._loc == 0: # "best". x, y = self._find_best_position(width, height, renderer) elif self._loc in Legend.codes.values(): # Fixed location. bbox = Bbox.from_bounds(0, 0, width, height) x, y = self._get_anchored_bbox(self._loc, bbox, self.get_bbox_to_anchor(), renderer) else: # Axes or figure coordinates. fx, fy = self._loc bbox = self.get_bbox_to_anchor() x, y = bbox.x0 + bbox.width * fx, bbox.y0 + bbox.height * fy return x + xdescent, y + ydescent
def __init__(self, width, height, dpi): if __debug__: verbose.report('RendererAgg.__init__', 'debug-annoying') RendererBase.__init__(self) self.texd = maxdict(50) # a cache of tex image rasters self._fontd = maxdict(50) self.dpi = dpi self.width = width self.height = height if __debug__: verbose.report('RendererAgg.__init__ width=%s, height=%s'%(width, height), 'debug-annoying') self._renderer = _RendererAgg(int(width), int(height), dpi, debug=False) self._filter_renderers = [] if __debug__: verbose.report('RendererAgg.__init__ _RendererAgg done', 'debug-annoying') self._update_methods() self.mathtext_parser = MathTextParser('Agg') self.bbox = Bbox.from_bounds(0, 0, self.width, self.height) if __debug__: verbose.report('RendererAgg.__init__ done', 'debug-annoying')
def __init__(self, array, world): self.array = array self.x_0 = self.array[0] self.y_0 = self.array[1] self.x_f = self.array[2] self.y_f = self.array[3] self.world = world self.dist = 5 # self.Bbox = Bbox.from_bounds(self.x_0, self.y_0 , \ # (self.x_f - self.x_0), (self.y_f - self.y_0)) # for i in range(self.x_0, self.x_f): # for j in range(self.y_0, self.y_f): # self.world.world[i][j] = 1 self.Bbox = Bbox.from_bounds(self.x_0 - self.dist, self.y_0 - self.dist, \ (self.x_f - self.x_0 + self.dist), (self.y_f - self.y_0 + self.dist)) for i in range(self.x_0, self.x_f): for j in range(self.y_0, self.y_f): self.world.world[i][j] = 1
def set_bbox_to_anchor(self, bbox, transform=None): """ set the bbox that the child will be anchored. *bbox* can be a Bbox instance, a list of [left, bottom, width, height], or a list of [left, bottom] where the width and height will be assumed to be zero. The bbox will be transformed to display coordinate by the given transform. """ if bbox is None or isinstance(bbox, BboxBase): self._bbox_to_anchor = bbox else: try: l = len(bbox) except TypeError: raise ValueError("Invalid argument for bbox : %s" % str(bbox)) if l == 2: bbox = [bbox[0], bbox[1], 0, 0] self._bbox_to_anchor = Bbox.from_bounds(*bbox) self._bbox_to_anchor_transform = transform
def __call__(self, axes, renderer): """ Return the adjusted position of the axes """ bbox0 = self.get_original_position(axes, renderer) bbox = bbox0 x1, y1, w, h = bbox.bounds extesion_fraction = self.extesion_fraction dw, dh = w*extesion_fraction, h*extesion_fraction if self.extend in ["min", "both"]: if self.orientation == "horizontal": x1 = x1 + dw else: y1 = y1+dh if self.extend in ["max", "both"]: if self.orientation == "horizontal": w = w-2*dw else: h = h-2*dh return Bbox.from_bounds(x1, y1, w, h)
def __call__(self, axes, renderer): """Return the adjusted position of the axes.""" bbox0 = self.get_original_position(axes, renderer) bbox = bbox0 x1, y1, w, h = bbox.bounds extesion_fraction = self.extesion_fraction dw, dh = w * extesion_fraction, h * extesion_fraction if self.extend in ["min", "both"]: if self.orientation == "horizontal": x1 = x1 + dw else: y1 = y1 + dh if self.extend in ["max", "both"]: if self.orientation == "horizontal": w = w - 2 * dw else: h = h - 2 * dh return Bbox.from_bounds(x1, y1, w, h)
def __init__(self, width, height, dpi): if __debug__: verbose.report("RendererAgg.__init__", "debug-annoying") RendererBase.__init__(self) self.dpi = dpi self.width = width self.height = height if __debug__: verbose.report("RendererAgg.__init__ width=%s, height=%s" % (width, height), "debug-annoying") self._renderer = _RendererAgg(int(width), int(height), dpi, debug=False) self._filter_renderers = [] if __debug__: verbose.report("RendererAgg.__init__ _RendererAgg done", "debug-annoying") self._update_methods() self.mathtext_parser = MathTextParser("Agg") self.bbox = Bbox.from_bounds(0, 0, self.width, self.height) if __debug__: verbose.report("RendererAgg.__init__ done", "debug-annoying")
def create_artists(self, legend, orig_handle, xdescent, ydescent, width, height, fontsize, trans): # save original visibility and then make it visible orig_vis = orig_handle.get_visible() orig_handle.set_visible(1) # set correct state and image data if not orig_vis: image_data = VisibilityHandler._unchecked self.state = False else: image_data = VisibilityHandler._checked self.state = True # ratio for square checkbox image_ratio = image_data.shape[1] / image_data.shape[0] # create a checkbox artist bb = Bbox.from_bounds(xdescent, ydescent, height * image_ratio, height) tbb = TransformedBbox(bb, trans) image = BboxImage(tbb) image.set_data(image_data) # update self self.update_prop(image, orig_handle, legend) self.set_events(image, orig_handle) # artists to be returned artists = [image] # if a handler is given, create artists to be return if self.handler is not None: artists += self.handler.create_artists( legend, orig_handle, xdescent - (height * 2.), ydescent, width - (height * 2.), height, fontsize, trans) # revert visibility orig_handle.set_visible(orig_vis) return artists
def __init__(self, **kwargs): """ Init the base plot. The accepted keyword arguments are style configuration parameters with defaults in BasePlotBuilder.style_defaults. """ style = self._pop_style_kwargs(kwargs) super().__init__(**kwargs) fig, ax = self.make_axes() logger.debug("Initialize plot '%s'", self.title) self.fig = fig """The matplotlib figure""" self.ax = ax """The matplotlib axes""" self._patch_builders = [] """ List of tuples (dataset, [builders,...]) holding the registered patch builders for each dataset. """ self._legend_handles = [] """Legend handles created by the patch builders.""" self._xticks = SortedDict() """X axis ticks returned by patch builders""" self._yticks = SortedDict() """Y axis ticks returned by patch builders""" self._view_box = Bbox.from_bounds(0, 0, 0, 0) """The viewport bounding box in data coordinates.""" self._style = style """Style options."""
def scatter_image(feature_x, feature_y, image_paths, title, save=None, code_list=None): """ Args: feature_x: x座標 feature_y: y座標 image_paths: """ global Scale fig = plt.figure() ax = fig.add_subplot(111) xlim = [np.min(feature_x)-5, np.max(feature_x)+5] ylim = [feature_y.min()-5, feature_y.max()+5] for (x, y, path) in zip(feature_x, feature_y, image_paths): img = plt.imread(path) if EmpCode != "" and get_class ( path ) == EmpCode : img = frame_image ( img, 30, 0 ) elif code_list != None : idx = code_list.index ( get_class (path) ) img = frame_image ( img, 30, float(idx) / len(code_list), cmap=cm ) disp_size = max ( xlim[1]-xlim[0], ylim[1]-ylim[0] ) / Num bb = Bbox.from_bounds(x, y, disp_size*Scale, disp_size * Scale) bb2 = TransformedBbox(bb, ax.transData) bbox_image = BboxImage(bb2, cmap=None, norm=None, origin=None, clip_on=False) bbox_image.set_data(img) ax.add_artist(bbox_image) ax.set_ylim(*ylim) ax.set_xlim(*xlim) plt.title(title) if save is not None: plt.savefig(save, dpi=600) plt.show()
def __init__(self, width, height, dpi): if __debug__: verbose.report('RendererAgg.__init__', 'debug-annoying') RendererBase.__init__(self) self.dpi = dpi self.width = width self.height = height if __debug__: verbose.report('RendererAgg.__init__ width=%s, height=%s'%(width, height), 'debug-annoying') self._renderer = _RendererAgg(int(width), int(height), dpi, debug=False) if __debug__: verbose.report('RendererAgg.__init__ _RendererAgg done', 'debug-annoying') self.draw_path = self._renderer.draw_path self.draw_markers = self._renderer.draw_markers self.draw_path_collection = self._renderer.draw_path_collection self.draw_quad_mesh = self._renderer.draw_quad_mesh self.draw_image = self._renderer.draw_image self.copy_from_bbox = self._renderer.copy_from_bbox self.restore_region = self._renderer.restore_region self.tostring_rgba_minimized = self._renderer.tostring_rgba_minimized self.mathtext_parser = MathTextParser('Agg') self.bbox = Bbox.from_bounds(0, 0, self.width, self.height) if __debug__: verbose.report('RendererAgg.__init__ done', 'debug-annoying')
def ylow(ax=None, ylow=None): """ Set lower y limit to 0 if not data/errors go lower. Or set a specific value """ if ax is None: ax = plt.gca() if ylow is None: # Check full figsize below 0 bbox = Bbox.from_bounds(0, 0, ax.get_window_extent().width, -ax.get_window_extent().height) if overlap(ax, bbox) == 0: ax.set_ylim(0, None) else: ydata = overlap(ax, bbox, get_vertices=True)[1][:, 1] ax.set_ylim(np.min([np.min(ydata), ax.get_ylim()[0]]), None) else: ax.set_ylim(0, ax.get_ylim()[-1]) return ax
def create_artists(self, legend, orig_handle, xdescent, ydescent, width, height, fontsize, trans): l = Line2D([xdescent + self.offset], [ydescent + height / 2.], c=self.color, ls="", marker="o", mfc=self.color, mec=self.color) l.set_clip_on(False) bb = Bbox.from_bounds( xdescent + (width + self.space) / 3. + self.offset, ydescent, height * self.image_data.shape[1] / self.image_data.shape[0], height) tbb = TransformedBbox(bb, trans) image = BboxImage(tbb) image.set_data(self.image_data) image.set_alpha(1.0) legend.set_alpha(1.0) self.update_prop(image, orig_handle, legend) return [l, image]
def main(argv): parser = argparse.ArgumentParser(prog='VIZ') parser.add_argument('source', help='path to the source metadata file') args = parser.parse_args(argv[1:]) # read in the data file data = pandas.read_csv(args.source, sep='\t') # load up data vis_x = data['x'].tolist() vis_y = data['y'].tolist() img_data = data['filename'].tolist() # Create figure fig = plt.figure() ax = fig.add_subplot(111) for x, y, filepath in zip(vis_x, vis_y, img_data): im = plt.imread(filepath) bb = Bbox.from_bounds(x, y, 1, 1) bb2 = TransformedBbox(bb, ax.transData) bbox_image = BboxImage(bb2, norm=None, origin=None, clip_on=False) bbox_image.set_data(im) ax.add_artist(bbox_image) #plt.scatter(vis_x, vis_y, marker='s', c=vis_y) #plt.colorbar(ticks=range(10)) #plt.clim(-0.5, 9.5) # Set the x and y limits ax.set_ylim(-50, 50) ax.set_xlim(-50, 50) plt.show()
def plot_wind_data2(ax, so, time_nums): so.wind_speed = np.array(so.wind_speed) wind_speed_max = np.nanmax(so.wind_speed) print('max speed', wind_speed_max, len(so.wind_speed)) logo = image.imread('north.png', None) bbox2 = Bbox.from_bounds(210, 330, 30, 40) # trans_bbox2 = bbox2.transformed(ax.transData) bbox_image2 = BboxImage(bbox2) bbox_image2.set_data(logo) ax.add_image(bbox_image2) # for x in range(0,len(time_nums),100): U = so.u V = so.v # if x == max_index: Q = ax.quiver(time_nums, -.15, U, V, headlength=0, headwidth=0, headaxislength=0, alpha=1, color='#045a8d', width=.0015, scale=wind_speed_max*5) ax.quiverkey(Q, 0.44, 0.84, wind_speed_max * .6,labelpos='N',label = ' 0 mph %.2f mph' % wind_speed_max, # fontproperties={'weight': 'bold'} )
gs = gridspec.GridSpec(6,1) ax1 = fig.add_subplot(gs[:-1]) ax2 = fig.add_subplot(gs[-1], sharex=ax1) im = ax1.matshow(samples[::-1], aspect='auto') ax1.autoscale(False) ax1.set_xticks([]) ax1.set_yticks([]) xo, yo, w, ht = ax1.bbox.bounds h = ht / n_show ax2.matshow(labels[None,:], aspect='auto') ax2.set_xticks([]) ax2.set_yticks([]) plt.draw() plt.ion() plt.show() from itertools import count for itr in count(): model.resample_model() samples[itr % n_show] = model.stateseqs[0] im.set_array(samples[::-1]) ax1.draw_artist(im) fig.canvas.blit(ax1.bbox) fig.canvas.blit(Bbox.from_bounds(xo,yo+h*(itr % n_show)+h,w,h))
import matplotlib.pyplot as plt from matplotlib.transforms import Bbox, TransformedBbox from matplotlib.image import BboxImage from pathlib import Path c = Path.cwd() / "checked.png" # Create figure and axes fig, ax = plt.subplots() # Add the Bbox Image to add the checked.png image bb = Bbox.from_bounds(0.2, 0.2, 0.6, 0.6) image_data = plt.imread(c, 0) tbb = TransformedBbox(bb, ax.transData) bbox_image = BboxImage(tbb) bbox_image.set_data(image_data) ax.add_artist(bbox_image) plt.show()
def adjust_bbox(fig, bbox_inches, fixed_dpi=None): """ Temporarily adjust the figure so that only the specified area (bbox_inches) is saved. It modifies figure.bbox, figure.bbox_inches, figure.transFigure._boxout, and figure.patch. While the figure size changes, the scale of the original figure is conserved. A function which restores the original values are returned. """ origBbox = fig.bbox origBboxInches = fig.bbox_inches _boxout = fig.transFigure._boxout asp_list = [] locator_list = [] for ax in fig.axes: pos = ax.get_position(original=False).frozen() locator_list.append(ax.get_axes_locator()) asp_list.append(ax.get_aspect()) def _l(a, r, pos=pos): return pos ax.set_axes_locator(_l) ax.set_aspect("auto") def restore_bbox(): for ax, asp, loc in zip(fig.axes, asp_list, locator_list): ax.set_aspect(asp) ax.set_axes_locator(loc) fig.bbox = origBbox fig.bbox_inches = origBboxInches fig.transFigure._boxout = _boxout fig.transFigure.invalidate() fig.patch.set_bounds(0, 0, 1, 1) if fixed_dpi is not None: tr = Affine2D().scale(fixed_dpi) dpi_scale = fixed_dpi / fig.dpi else: tr = Affine2D().scale(fig.dpi) dpi_scale = 1. _bbox = TransformedBbox(bbox_inches, tr) fig.bbox_inches = Bbox.from_bounds(0, 0, bbox_inches.width, bbox_inches.height) x0, y0 = _bbox.x0, _bbox.y0 w1, h1 = fig.bbox.width * dpi_scale, fig.bbox.height * dpi_scale fig.transFigure._boxout = Bbox.from_bounds(-x0, -y0, w1, h1) fig.transFigure.invalidate() fig.bbox = TransformedBbox(fig.bbox_inches, tr) fig.patch.set_bounds(x0 / w1, y0 / h1, fig.bbox.width / w1, fig.bbox.height / h1) return restore_bbox
def plot_feature_map(axes, annotation, loc_range=None, multi_line=True, symbols_per_line=1000, show_numbers=False, number_size=None, line_width=0.05, show_line_position=False, spacing=0.25, feature_plotters=None, style_param=None): """ Plot a sequence annotation, by showing the range of each feature on one or multiple position depicting line(s). This function uses :class:`FeaturePlotter` objects to draw the features. This function internally uses a list of plotters, where the first plotter in the list, that supports a feature, is used to draw that feature. The amount of features that can be visualized by default is limited. Features, that are not supported otherwise, are visualized as simple rectangles. Additional :class:`FeaturePlotter` objects, that are supplied in the `feature_plotters` parameters, can be used to add support for further features or to customize the appearance of certain features. Parameters ---------- axes : Axes A *Matplotlib* axes, that is used as plotting area. annotation : Annotation The annotation to be visualized. loc_range : tuple (int, int), optional The start and exclusive stop location that is visualized. By default, the location range starts from the first base/residue and ends at the last base/residue of all features, ensuring that the entire annotation is drawn. multi_line : bool, optional If true, the annotation is segmented into multiple lines with a line break all `symbols_per_line` lines. Otherwise, the entire location range is put into a single line. symbols_per_line : int, optional The amount of Does not have an effect, if `multi_line` is false. show_numbers : bool, optional If true, the sequence position the base/residue of a line is shown on the right side of the plot. number_size : float, optional The font size of the position numbers line_width : float, optional The size of the continuous line as fraction of the height of the drawn features. show_line_position : bool, optional If true the position within a line is plotted. spacing : float, optional The size of the spacing between the lines as fraction of the height of the drawn features. feature_plotters : list of FeaturePlotter, optional Custom plotters for features. The list is iterated from the beginning until a :class:`FeaturePlotter` matches the respective feature (`FeaturePlotter.matches()` returns `True`). This :class:`FeaturePlotter` is then used to draw the feature. Therefore, the :class:`FeaturePlotter` instances in the list have descending priority. The default plotters are appended after this supplied list, i.e. the default plotters have a lower priority. style_param : dict Additional style parameters that are given to the :class:`FeaturePlotter` objects. Notes ----- Good visulation results are obtained only for non-overlapping features. When two features overlap, their drawing area does also overlap. """ from matplotlib.transforms import Bbox from matplotlib.patches import Rectangle if loc_range is None: loc_range = annotation.get_location_range() loc_range_length = loc_range[1] - loc_range[0] if multi_line: symbols_per_line = symbols_per_line else: # Line length covers the entire location range symbols_per_line = loc_range_length plotters = [ PromoterPlotter(), TerminatorPlotter(), RBSPlotter(), CodingPlotter(), MiscFeaturePlotter() ] if feature_plotters is not None: plotters = list(feature_plotters) + plotters style_param = {} if style_param is None else style_param line_count = loc_range_length // symbols_per_line # Only extend line count by 1 if there is a remainder if loc_range_length % symbols_per_line != 0: line_count += 1 ### Draw lines ### remaining_symbols = loc_range_length y = 0.5 while remaining_symbols > 0: if remaining_symbols > symbols_per_line: # Line spans the entire plot (horizontally) line_length = symbols_per_line else: # Last line -> Line spans to end of annotation line_length = remaining_symbols axes.add_patch( Rectangle((0, y - line_width / 2), line_length, line_width, color="gray", linewidth=0)) # Increment by spacing and width (=1) of feature y += spacing + 1 remaining_symbols -= symbols_per_line ### Draw features ### line_start_loc = loc_range[0] y = 0 while line_start_loc < loc_range[1]: annotation_for_line = annotation[line_start_loc:line_start_loc + symbols_per_line] for feature in annotation_for_line: plotter = None # Identify fitting plotter for potentail_plotter in plotters: if potentail_plotter.matches(feature): # Take first fitting plotter in list plotter = potentail_plotter break if plotter is not None: for loc in feature.locs: loc_len = loc.last - loc.first + 1 # Get start location realtive to start if line loc_in_line = loc.first - line_start_loc x = loc_in_line # Line width multiplied by percentage of line width = loc_len height = 1 bbox = Bbox.from_bounds(x, y, width, height) plotter.draw(axes, feature, bbox, loc, style_param=style_param) # Increment by spacing and width (=1) of feature y += spacing + 1 remaining_symbols += symbols_per_line line_start_loc += symbols_per_line ### Draw position numbers ### ticks = [] tick_labels = [] if show_numbers: # Numbers at center height of each feature line -> 0.5 y = 0.5 for i in range(line_count): if i == line_count - 1: # Last line -> get number of last column in trace loc = loc_range[1] - 1 else: loc = loc_range[0] + ((i + 1) * symbols_per_line) - 1 ticks.append(y) tick_labels.append(str(loc)) # Increment by spacing and width of feature (1) y += spacing + 1 axes.set_yticks(ticks) axes.set_yticklabels(tick_labels) axes.set_xlim(0, symbols_per_line) # Y-axis starts from top axes.set_ylim(1 * line_count + spacing * (line_count - 1), 0) axes.set_frame_on(False) # Draw location numbers on right side axes.get_yaxis().set_tick_params(left=False, right=False, labelleft=False, labelright=True) # Remove ticks and set number font size axes.yaxis.set_tick_params(left=False, right=False, labelsize=number_size) if show_line_position: axes.xaxis.set_tick_params(top=False, bottom=True, labeltop=False, labelbottom=True) else: axes.xaxis.set_tick_params(top=False, bottom=False, labeltop=False, labelbottom=False)
#------------------------------------------------------------------------------- import numpy as np import matplotlib.pyplot as plt from matplotlib.transforms import Bbox from matplotlib.path import Path # Fixing random state for reproducibility np.random.seed(19680801) left, bottom, width, height = (-1, -1, 2, 2) rect = plt.Rectangle((left, bottom), width, height, facecolor="#aaaaaa") fig, ax = plt.subplots() ax.add_patch(rect) bbox = Bbox.from_bounds(left, bottom, width, height) for i in range(12): vertices = (np.random.random((2, 2)) - 0.5) * 6.0 path = Path(vertices) if path.intersects_bbox(bbox): color = 'r' else: color = 'b' ax.plot(vertices[:, 0], vertices[:, 1], color=color) plt.show() def main(): pass
images = torch.from_numpy(raw_data.astype('float32')) images = [image.view(-1) for image in images] for image in images: state = vae_append(state, image) bb_ans_compressed = bytes_to_img(rans.flatten(state).tobytes()) raw_data = np.concatenate(~raw_data, axis=1) labels = ["BB-ANS", "bz2", "PNG", "MNIST"] data = [bb_ans_compressed, bz2_compressed, png_compressed, raw_data ] yticks = [] for i, d in enumerate(data): bbox = Bbox.from_bounds(0, 28 * (spacing + i * (h + spacing)), 28 * d.shape[1], 28 * h) bbox = TransformedBbox(bbox, ax.transData) bbox_image = BboxImage(bbox, cmap='gray', origin=None) bbox_image.set_data(d) ax.add_artist(bbox_image) yticks.append(28 * (spacing + i * (h + spacing) + h // 2)) ax.set_xlim(0, max(28 * d.shape[1] for d in data)) ax.set_yticks(yticks) ax.set_yticklabels(labels) ax.set_ylim(0, 28 * (spacing + (i + 1) * (h + spacing))) ax.set_xlabel('Size (bits)') ax.set_aspect('equal') plt.savefig('compression_plot.png', dpi=800, bbox_inches='tight')
pl = AX1.errorbar(xvalues[:len(plotdata[l])], plotdata[l], label=(l), lw=2, marker=markers[i], markersize=12, elinewidth=2,ls="--") else: pl = AX1.errorbar(xvalues[:len(plotdata[l])], plotdata[l], yerr=plotconfidence[l], label=(l), lw=2, marker=markers[i], markersize=12, elinewidth=2,ls="--") plotlines.append(pl[0]) plotlabels.append(labels[l[0]]) AX1.set_xlabel(x_label, fontproperties=font) AX1.set_ylabel(y_label, fontproperties=font) AX1.set_xlim(0, 52) if o == "rt": AX1.set_yscale('log') elif o == "sq": AX1.set_ylim(ymin=0.995) elif o == "fs": AX1.set_ylim(ymax=1.02,ymin=0.0) elif o == "tot": AX1.set_ylim(ymax=350) #plotlines.append(AX1.plot((0, 166), (52, 166), 'k-')) plotlines.append(AX1.axhline(y=166, xmin=0, xmax=1, color='r', linewidth=1.5, linestyle='-')) for tick in AX1.xaxis.get_major_ticks(): tick.label1.set_fontsize(18) for tick in AX1.yaxis.get_major_ticks(): tick.label1.set_fontsize(18) P.savefig('plots/plot_Test_' + str(test) + '_' + str(l[1]) + '.pdf', bbox_inches='tight') F = P.figure(2) F.legend(plotlines, plotlabels, loc='upper left', shadow=False, fancybox=True, prop=font_smaller, ncol=2) bb = Bbox.from_bounds(0, 0, 6.4, 4) P.savefig('plots/plot_legend.pdf', bbox_inches=bb)
# plots T-SNE embeddings as a scatter plot (for reference) plt.clf() plt.scatter(embedded[:, 0], embedded[:, 1], marker='.', color='blue') plt.savefig("tests/tsne_test.png") plt.clf() # generates 2d T-SNE visualization of image embeddings plt.clf() fig = plt.figure(figsize=(25, 25)) plt.xlim([-20, 20]) plt.ylim([-20, 20]) ax = fig.add_subplot(111) plt.axis('off') # adapted from https://stackoverflow.com/questions/25329583/matplotlib-using-image-for-points-on-plot for i in range(0, len(img_filepaths)): bb = Bbox.from_bounds(embedded[i][0], embedded[i][1], 1.0, 1.0) bb2 = TransformedBbox(bb, ax.transData) bbox_image = BboxImage(bb2, norm=None, origin=None, clip_on=False, cmap='gray') im = plt.imread(img_filepaths[i]) bbox_image.set_data(im) ax.add_artist(bbox_image) # saves figure plt.savefig("tests/testfig.png", dpi=500, bbox_inches='tight') plt.clf()
assert all(len(name_color.split('_')) == 2 for name_color in args.players_colors) players = [{'name': name_color.split('_')[0][:17].upper(), 'color': name_color.split('_')[1], 'wedges': set()} for name_color in args.players_colors] # rectangular axes for legend, die rolls, and key to topics fig, ax = plt.subplots(1, 1, figsize=(11, 9)) plt.subplots_adjust(left=-.15) ax.set_axis_off() # images for rolling die dice = {i: plt.imread(f'images/{i}.png') for i in range(7)} bb = Bbox.from_bounds(.84, .46, .065, .1) bb2 = TransformedBbox(bb, ax.transData) bbox_image = BboxImage(bb2) # perimiter spaces p_coords = [(6, i * (2 * np.pi / 42)) for i in range(42)] p_coords.append((0, 0)) # will plot 'wedge' spaces a second time with larger markers w_coords = [(6, i * (2 * np.pi / 42)) for i in range(42) if i % 7 == 0] # 'spoke' spaces s_coords = [(k, j * (2 * np.pi / 42)) for k in range(1, 6) for j in range(0, 42, 7)] # coordinates for plotting p_r, p_th = zip(*p_coords) p_r = np.asarray(p_r)
def _find_best_position(self, width, height, renderer, 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 display coords. """ # should always hold because function is only called internally assert self.isaxes verts, bboxes, lines, offsets = self._auto_legend_data() bbox = Bbox.from_bounds(0, 0, width, height) if consider is None: consider = [ self._get_anchored_bbox(x, bbox, self.get_bbox_to_anchor(), renderer) for x in range(1, len(self.codes)) ] # tx, ty = self.legendPatch.get_x(), self.legendPatch.get_y() candidates = [] for l, b in consider: legendBox = Bbox.from_bounds(l, b, width, height) badness = 0 # XXX TODO: If markers are present, it would be good to # take their into account when checking vertex overlaps in # the next line. badness = legendBox.count_contains(verts) badness += legendBox.count_contains(offsets) badness += legendBox.count_overlaps(bboxes) for line in lines: # FIXME: the following line is ill-suited for lines # that 'spiral' around the center, because the bbox # may intersect with the legend even if the line # itself doesn't. One solution would be to break up # the line into its straight-segment components, but # this may (or may not) result in a significant # slowdown if lines with many vertices are present. if line.intersects_bbox(legendBox): badness += 1 ox, oy = l, b if badness == 0: return ox, oy candidates.append((badness, (l, b))) # 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. # NOTE: list.sort() is stable.But leave as it is for now. -JJL minCandidate = candidates[0] for candidate in candidates: if candidate[0] < minCandidate[0]: minCandidate = candidate ox, oy = minCandidate[1] return ox, oy
def adjust_bbox(fig, bbox_inches, fixed_dpi=None): """ Temporarily adjust the figure so that only the specified area (bbox_inches) is saved. It modifies fig.bbox, fig.bbox_inches, fig.transFigure._boxout, and fig.patch. While the figure size changes, the scale of the original figure is conserved. A function which restores the original values are returned. """ def no_op_apply_aspect(position=None): return origBbox = fig.bbox origBboxInches = fig.bbox_inches orig_tight_layout = fig.get_tight_layout() _boxout = fig.transFigure._boxout fig.set_tight_layout(False) old_aspect = [] locator_list = [] sentinel = object() for ax in fig.axes: pos = ax.get_position(original=False).frozen() locator_list.append(ax.get_axes_locator()) def _l(a, r, pos=pos): return pos ax.set_axes_locator(_l) # override the method that enforces the aspect ratio # on the Axes if 'apply_aspect' in ax.__dict__: old_aspect.append(ax.apply_aspect) else: old_aspect.append(sentinel) ax.apply_aspect = no_op_apply_aspect def restore_bbox(): for ax, loc, aspect in zip(fig.axes, locator_list, old_aspect): ax.set_axes_locator(loc) if aspect is sentinel: # delete our no-op function which un-hides the # original method del ax.apply_aspect else: ax.apply_aspect = aspect fig.bbox = origBbox fig.bbox_inches = origBboxInches fig.set_tight_layout(orig_tight_layout) fig.transFigure._boxout = _boxout fig.transFigure.invalidate() fig.patch.set_bounds(0, 0, 1, 1) if fixed_dpi is not None: tr = Affine2D().scale(fixed_dpi) dpi_scale = fixed_dpi / fig.dpi else: tr = Affine2D().scale(fig.dpi) dpi_scale = 1. _bbox = TransformedBbox(bbox_inches, tr) fig.bbox_inches = Bbox.from_bounds(0, 0, bbox_inches.width, bbox_inches.height) x0, y0 = _bbox.x0, _bbox.y0 w1, h1 = fig.bbox.width * dpi_scale, fig.bbox.height * dpi_scale fig.transFigure._boxout = Bbox.from_bounds(-x0, -y0, w1, h1) fig.transFigure.invalidate() fig.bbox = TransformedBbox(fig.bbox_inches, tr) fig.patch.set_bounds(x0 / w1, y0 / h1, fig.bbox.width / w1, fig.bbox.height / h1) return restore_bbox
def detect_grid( self, image: np.ndarray, origin: tuple, nx: int, ny: int, ds: float, debug=False, ): """Detect a ``nx`` by ``ny`` circle grid centered around an origin. Parameters ---------- image: array A calibration image of maximum intensity 255. origin: tuple Origin / Principal point location in pixel coordinates nx, ny : int Shape of the grid, i.e. number of points ds : float Grid spacing in pixel coordinates debug : bool Plot the detected points and the bounding box """ keypoints = self.detect_all(image) # Add 1 so that the points at the edge of the bounding box are included w = (nx + 1) * ds h = (ny + 1) * ds originx, originy = origin bbox = Bbox.from_bounds(originx - w // 2, originy - h // 2, w, h) if debug: print(bbox) center_list = [] for k in keypoints: if bbox.contains(*k.pt): center_list.append(k.pt) centers = np.array(center_list) xround = np.round(centers[..., 0] / ds) yround = np.round(centers[..., 1] / ds) # Sort as a grid ind = np.lexsort((xround, yround)) # Add another dimension centers = np.array([centers[ind]], dtype=np.float32) if len(centers[0]) != nx * ny: raise AssertionError(f"Only {len(centers[0])} points were found") if debug: fig, ax = plt.subplots() ax.imshow(image, cmap="gray") ax.scatter(centers[..., 0], centers[..., 1]) l, b, w, h = bbox.bounds ax.add_patch( Rectangle(xy=(l, b), width=w, height=h, edgecolor="r", fill=False)) return centers
#all = plt.figure() #fig = all.add_subplot(111); #plot_opts = {'x_label': '$test x$', 'y_label': '$test y$', 'title': 'Generated Data in $x$ and $y$', 'y_lim': [np.min(Y)-0.5, np.max(Y)+0.5]} #plot_helpers.plot_data(X[:, 0], Y, fig=fig, options=plot_opts) #plt.show() #all.savefig('test.pdf', bbox_inches='tight') fig = plt.figure(figsize=(6,4)) ax = plt.subplot(111) plt.plot(X[:,0], Y, 'o', markersize=2, color='C1') plt.xlabel('test $x$') plt.title('Sumting') #plt.show() bbox = Bbox.from_bounds(0, 0, 6, 4) pos1 = ax.get_position() test = pos1.bounds fig.savefig('bb_test.pdf', bbox_inches=bbox) print(pos1) print(test) #new = fig.gca().get_anchor() #print(new)
def visualize(self): """Generate samples from a given fixed set of noise vectors and visualize them in a 2D plot along with contours of the discriminator, the norm of its gradient, and the target empirical distribution. """ target_dist = [] samples = [] block_stats = [] for _ in range(10): with torch.no_grad(): cx = self.P_eval.sample() cy = self.Q.sample() while cy.size(0) < cx.size(0): cy = torch.cat([cy, self.Q.sample()]) cy = cy[:cx.size(0)] target_dist.append(cx) samples.append(cy) stat = mmd2(*laplacian_mix_kernel(cx, cy)).sqrt() block_stats.append(stat.unsqueeze(-1)) target_dist = torch.cat(target_dist) samples = torch.cat(samples) block_stats = torch.cat(block_stats) N_POINTS = 256 RANGE = 3. fig, ax = plt.subplots(figsize=(FIG_X_SIZE_IN, FIG_Y_SIZE_IN), dpi=DPI) ax.set_xlim(-RANGE, RANGE) ax.set_ylim(-RANGE, RANGE) Xspace = np.linspace(-RANGE, RANGE, N_POINTS) x, y = np.meshgrid(Xspace, Xspace) points = np.concatenate( (x.reshape(len(Xspace), len(Xspace), 1), y.reshape(len(Xspace), len(Xspace), 1)), axis=2) points = torch.from_numpy(points).float() if self.args.cuda: points = points.cuda(device=self.device) outs = self.critic(points) disc_map = torch.sigmoid(outs).detach().cpu().numpy().squeeze() bot, top = Xspace[0], Xspace[-1] ax.imshow(disc_map, cmap=CMAP_DIVERGING, vmin=0.45, vmax=0.55, alpha=0.5, interpolation='lanczos', extent=(bot, top, bot, top), origin='lower') CS = ax.contour(disc_map, cmap=CMAP_SEQUENTIAL, alpha=0.6, extent=(bot, top, bot, top), origin='lower') ax.clabel(CS, inline=True, fmt='%.3f', colors='black', fontsize=MEDIUM_SIZE) ax.scatter(*target_dist.cpu().numpy().T, s=1, marker='o', facecolors='none', edgecolors='blue') ax.scatter(*samples.cpu().numpy().T, c='orange', s=1, marker='+') msg = "Eval Metric (×1e3) <mean±std>: {:4.4f}±{:4.4f} | Update Steps: {}" mmd_mean = block_stats.mean() * 1e3 mmd_std = block_stats.std() * 1e3 msg = msg.format(mmd_mean, mmd_std, self.iter) plt.title(msg, loc='left') image_path = os.path.join(self.logdir, 'step-' + str(self.iter) + '.png') bbox = Bbox.from_bounds(1.16, 1, 960 / DPI, 960 / DPI) fig.savefig(image_path, bbox_inches=bbox) self.log(viz=fig) plt.close(fig) return mmd_mean, mmd_std
############################################################################### # If you want an inset axes in data-space, you need to manually execute the # layout using ``fig.execute_constrained_layout()`` call. The inset figure # will then be properly positioned. However, it will not be properly # positioned if the size of the figure is subsequently changed. Similarly, # if the figure is printed to another backend, there may be slight changes # of location due to small differences in how the backends render fonts. from matplotlib.transforms import Bbox fig, axs = plt.subplots(1, 2) example_plot(axs[0], fontsize=12) fig.execute_constrained_layout() # put into data-space: bb_data_ax2 = Bbox.from_bounds(0.5, 1., 0.2, 0.4) disp_coords = axs[0].transData.transform(bb_data_ax2) fig_coords_ax2 = fig.transFigure.inverted().transform(disp_coords) bb_ax2 = Bbox(fig_coords_ax2) ax2 = fig.add_axes(bb_ax2) ############################################################################### # Manually turning off ``constrained_layout`` # =========================================== # # ``constrained_layout`` usually adjusts the axes positions on each draw # of the figure. If you want to get the spacing provided by # ``constrained_layout`` but not have it update, then do the initial # draw and then call ``fig.set_constrained_layout(False)``. # This is potentially useful for animations where the tick labels may # change length.
def plot_bars(ax, fig, data, xy, boxsize, xylims, leg_args, frac=True, alt_hatch=False, labels=[]): num_plots = len(data) fig.show() fig.canvas.draw() # Determine plot limits if frac: plot_range = [0., 1.] else: #plot_range = [0,np.amax(data[np.where(np.isfinite(xy[:,0]))])] plot_range = [0, leg_args['max']] ax.set_xlim(xylims[0], xylims[1]) ax.set_ylim(xylims[2], xylims[3]) ax.set_aspect('equal', adjustable='box-forced') ax.xaxis.set_visible(False) ax.yaxis.set_visible(False) #Plots bar plots at given locations (x centered over point, y bottom at point) for p in range(num_plots): if np.isfinite(xy[p, 0]): bb_data = Bbox.from_bounds(xy[p, 0] - boxsize[0] / 2., xy[p, 1], boxsize[0], boxsize[1]) disp_coords = ax.transData.transform(bb_data) # Ben - what is this doing? Why does it need fig and not ax? fig_coords = fig.transFigure.inverted().transform(disp_coords) if len(labels) > 1: plotBarGraph(fig_coords, data[p, :], fig, plot_range, alt_hatch=alt_hatch, labels=labels[p, :]) else: plotBarGraph(fig_coords, data[p, :], fig, plot_range, alt_hatch=alt_hatch) fig.canvas.draw() xy_leg = [589782.5317557553, 4187778.3682879894] # move to main mod = len(leg_args['bars']) / 4 if len(leg_args['bars']) % 4 != 0: mod += 1 # bb_data = Bbox.from_bounds(xy_leg[0]-boxsize[0]/2., xy_leg[1], # boxsize[0], boxsize[1]) bb_data = Bbox.from_bounds(xy_leg[0] - boxsize[0] / 2., xy_leg[1], boxsize[0] * mod, boxsize[1]) disp_coords = ax.transData.transform(bb_data) fig_coords = fig.transFigure.inverted().transform(disp_coords) if alt_hatch: bars = leg_args['bars'] * 2 else: bars = leg_args['bars'] plotBarGraph(fig_coords, [plot_range[1]] * len(bars), fig, plot_range, legend=True, alt_hatch=alt_hatch, xlabels=bars, ylabel=leg_args['ylabel']) return
# List of all colormaps; skip reversed colormaps. maps = sorted(m for m in plt.colormaps() if not m.endswith("_r")) ncol = 2 nrow = len(maps) // ncol + 1 xpad_fraction = 0.3 dx = 1. / (ncol + xpad_fraction * (ncol - 1)) ypad_fraction = 0.3 dy = 1. / (nrow + ypad_fraction * (nrow - 1)) for i, m in enumerate(maps): ix, iy = divmod(i, nrow) bbox0 = Bbox.from_bounds(ix * dx * (1 + xpad_fraction), 1. - iy * dy * (1 + ypad_fraction) - dy, dx, dy) bbox = TransformedBbox(bbox0, ax2.transAxes) bbox_image = BboxImage(bbox, cmap=plt.get_cmap(m), norm=None, origin=None, **kwargs) bbox_image.set_data(a) ax2.add_artist(bbox_image) plt.show() ############################################################################# #
from pylab import * import numpy as np from matplotlib.transforms import Bbox from matplotlib.path import Path from matplotlib.patches import Rectangle rect = Rectangle((-1, -1), 2, 2, facecolor="#aaaaaa") gca().add_patch(rect) bbox = Bbox.from_bounds(-1, -1, 2, 2) for i in range(12): vertices = (np.random.random((4, 2)) - 0.5) * 6.0 vertices = np.ma.masked_array(vertices, [[False, False], [True, True], [False, False], [False, False]]) path = Path(vertices) if path.intersects_bbox(bbox): color = 'r' else: color = 'b' plot(vertices[:,0], vertices[:,1], color=color) show()
def __call__(self, ax, renderer): bbox_parent = self.parent.get_position(original=False) trans = BboxTransformTo(bbox_parent) bbox_inset = Bbox.from_bounds(*self.lbwh) bb = TransformedBbox(bbox_inset, trans) return bb
def plot_boxes(ax, fig, data, xy, boxsize, xylims, leg_args, frac=True, alt_hatch=False, labels=[]): ''' Functions similar to the map_w_bars plot. Takes in the following arguments: ax: plot frame, should already exist from draw_water_and_polys() in Longfin bar. Be sure that gets called first. fig: Figure frame, same as ax. data: numpy array that contains all of the data for every bar plot. formatted as such: region -> Survey -> dict{med, q1, q3, whislo, whishi} 9 regions with 9 surveys will end up being 81 dictionaries! xy: xy locations dictionary for each bar plot. Comes from findSiteLoc() boxsize: size of the plots. 10,000x10,000 looks good. xylims: plot x and y limits for frame reference leg_args: arguments for the plot legend labels labels: array of labels for the bar plots, containing x's for areas with missing data. Array of lists, region -> surveys the script will iterate through each region and plot each bar graph separately. It will convert the coords into ratios of the plot window. The plot needs to redraw each time or else it gets confused and the plots will be offset. After all the bar plots are plotted, the legend is plotted below those. ''' num_plots = len(data) fig.show() fig.canvas.draw() # Determine plot limits if frac: plot_range = [0., 1.] else: #plot_range = [0,np.amax(data[np.where(np.isfinite(xy[:,0]))])] plot_range = [0, leg_args['max']] ax.set_xlim(xylims[0], xylims[1]) ax.set_ylim(xylims[2], xylims[3]) ax.set_aspect('equal', adjustable='box-forced') ax.xaxis.set_visible(False) ax.yaxis.set_visible(False) #Plots box plots at given locations (x centered over point, y bottom at point) for p in range(num_plots): if np.isfinite(xy[p, 0]): bb_data = Bbox.from_bounds(xy[p, 0] - boxsize[0] / 2., xy[p, 1], boxsize[0], boxsize[1]) disp_coords = ax.transData.transform(bb_data) fig_coords = fig.transFigure.inverted().transform( disp_coords) #convert coords into ratios if len(labels) > 1: plotBWPlot(fig_coords, data[p, :], fig, plot_range, alt_hatch=alt_hatch, labels=labels[p, :]) else: plotBWPlot(fig_coords, data[p, :], fig, plot_range, alt_hatch=alt_hatch) fig.canvas.draw() xy_leg = [589782.5317557553, 4187778.3682879894] # move to main, Legend coords mod = len( leg_args['boxes'] ) / 4 # figure out how long to make the legend, every 4 items make more room if len(leg_args['boxes']) % 4 != 0: mod += 1 bb_data = Bbox.from_bounds(xy_leg[0] - boxsize[0] / 2., xy_leg[1], boxsize[0] * mod, boxsize[1]) disp_coords = ax.transData.transform(bb_data) fig_coords = fig.transFigure.inverted().transform(disp_coords) if alt_hatch: boxes = leg_args['boxes'] * 2 else: boxes = leg_args['boxes'] legend_data = { "med": plot_range[1] * .5, #make a dummy legend with perfect data "q1": plot_range[1] * .25, "q3": plot_range[1] * .75, "whislo": plot_range[0], "whishi": plot_range[1] } legend_array = [] for i in range(len(boxes)): legend_array.append(legend_data) plotBWPlot(fig_coords, legend_array, fig, plot_range, legend=True, alt_hatch=alt_hatch, xlabels=boxes, ylabel=leg_args['ylabel']) return
def _make_patch(self): """ Returns an appropriately scaled patch object corresponding to the Glyph. """ # Set height height = self.ceiling - self.floor # If height is zero, set patch to None and return None if height == 0.0: self.patch = None return None # Set bounding box for character, # leaving requested amount of padding above and below the character char_xmin = self.p - self.width / 2.0 char_ymin = self.floor + self.vpad * height / 2.0 char_width = self.width char_height = height - self.vpad * height bbox = Bbox.from_bounds(char_xmin, char_ymin, char_width, char_height) # Set font properties of Glyph font_properties = FontProperties(family=self.font_name, weight=self.font_weight) # Create a path for Glyph that does not yet have the correct # position or scaling tmp_path = TextPath((0, 0), self.c, size=1, prop=font_properties) # Create create a corresponding path for a glyph representing # the max stretched character msc_path = TextPath((0, 0), self.dont_stretch_more_than, size=1, prop=font_properties) # If need to flip char, do it within tmp_path if self.flip: transformation = Affine2D().scale(sx=1, sy=-1) tmp_path = transformation.transform_path(tmp_path) # If need to mirror char, do it within tmp_path if self.mirror: transformation = Affine2D().scale(sx=-1, sy=1) tmp_path = transformation.transform_path(tmp_path) # Get bounding box for temporary character and max_stretched_character tmp_bbox = tmp_path.get_extents() msc_bbox = msc_path.get_extents() # Compute horizontal stretch factor needed for tmp_path hstretch_tmp = bbox.width / tmp_bbox.width # Compute horizontal stretch factor needed for msc_path hstretch_msc = bbox.width / msc_bbox.width # Choose the MINIMUM of these two horizontal stretch factors. # This prevents very narrow characters, such as 'I', from being # stretched too much. hstretch = min(hstretch_tmp, hstretch_msc) # Compute the new character width, accounting for the # limit placed on the stretching factor char_width = hstretch * tmp_bbox.width # Compute how much to horizontally shift the character path char_shift = (bbox.width - char_width) / 2.0 # Compute vertical stetch factor needed for tmp_path vstretch = bbox.height / tmp_bbox.height # THESE ARE THE ESSENTIAL TRANSFORMATIONS # 1. First, translate char path so that lower left corner is at origin # 2. Then scale char path to desired width and height # 3. Finally, translate char path to desired position # char_path is the resulting path used for the Glyph transformation = Affine2D() \ .translate(tx=-tmp_bbox.xmin, ty=-tmp_bbox.ymin) \ .scale(sx=hstretch, sy=vstretch) \ .translate(tx=bbox.xmin + char_shift, ty=bbox.ymin) char_path = transformation.transform_path(tmp_path) # Convert char_path to a patch, which can now be drawn on demand self.patch = PathPatch(char_path, facecolor=self.color, zorder=self.zorder, alpha=self.alpha, edgecolor=self.edgecolor, linewidth=self.edgewidth) # add patch to axes self.ax.add_patch(self.patch)
def _get_layout(self, renderer): """ return the extent (bbox) of the text together with multiple-alignment information. Note that it returns an extent of a rotated text when necessary. """ key = self.get_prop_tup(renderer=renderer) if key in self._cached: return self._cached[key] thisx, thisy = 0.0, 0.0 lines = self.get_text().split("\n") # Ensures lines is not empty. ws = [] hs = [] xs = [] ys = [] # Full vertical extent of font, including ascenders and descenders: _, lp_h, lp_d = renderer.get_text_width_height_descent( "lp", self._fontproperties, ismath="TeX" if self.get_usetex() else False) min_dy = (lp_h - lp_d) * self._linespacing # AG edit pixels_per_pt = 1/72*self.figure._dpi line_height = (pixels_per_pt * self.get_fontsize()) * self._linespacing for i, line in enumerate(lines): clean_line, ismath = self._preprocess_math(line) if clean_line: w, h, d = renderer.get_text_width_height_descent( clean_line, self._fontproperties, ismath=ismath) else: w = h = d = 0 # For multiline text, increase the line spacing when the text # net-height (excluding baseline) is larger than that of a "l" # (e.g., use of superscripts), which seems what TeX does. h = max(h, lp_h) d = max(d, lp_d) ws.append(w) hs.append(h) # Metrics of the last line that are needed later: baseline = (h - d) - thisy if i == 0: # position at baseline thisy = -(h - d) else: # put baseline a good distance from bottom of previous line # thisy -= max(min_dy, (h - d) * self._linespacing) # AG edit - define change in y independent of font dimensions thisy -= line_height - d # reduce by d, because d is minus'd 3 lines later anyway xs.append(thisx) # == 0. ys.append(thisy) thisy -= d # Metrics of the last line that are needed later: descent = d # Bounding box definition: width = max(ws) xmin = 0 xmax = width ymax = 0 ymin = ys[-1] - descent # baseline of last line minus its descent height = ymax - ymin yprop = (ys[0]-ymin) / height # AG edit # get the rotation matrix M = Affine2D().rotate_deg(self.get_rotation()) # now offset the individual text lines within the box malign = self._get_multialignment() if malign == 'left': offset_layout = [(x, y) for x, y in zip(xs, ys)] elif malign == 'center': offset_layout = [(x + width / 2 - w / 2, y) for x, y, w in zip(xs, ys, ws)] elif malign == 'right': offset_layout = [(x + width - w, y) for x, y, w in zip(xs, ys, ws)] # the corners of the unrotated bounding box corners_horiz = np.array( [(xmin, ymin), (xmin, ymax), (xmax, ymax), (xmax, ymin)]) # now rotate the bbox corners_rotated = M.transform(corners_horiz) # compute the bounds of the rotated box xmin = corners_rotated[:, 0].min() xmax = corners_rotated[:, 0].max() ymin = corners_rotated[:, 1].min() ymax = corners_rotated[:, 1].max() width = xmax - xmin height = ymax - ymin # Now move the box to the target position offset the display # bbox by alignment halign = self._horizontalalignment valign = self._verticalalignment rotation_mode = self.get_rotation_mode() if rotation_mode != "anchor": # compute the text location in display coords and the offsets # necessary to align the bbox with that location if halign == 'center': offsetx = (xmin + xmax) / 2 elif halign == 'right': offsetx = xmax else: offsetx = xmin if valign == 'center': offsety = (ymin + ymax) / 2 elif valign == 'top': offsety = ymax elif valign == 'baseline': offsety = ymin + descent elif valign == 'first_baseline': offsety = ymin + (yprop * height) elif valign == 'center_baseline': offsety = ymin + height - baseline / 2.0 else: offsety = ymin else: xmin1, ymin1 = corners_horiz[0] xmax1, ymax1 = corners_horiz[2] if halign == 'center': offsetx = (xmin1 + xmax1) / 2.0 elif halign == 'right': offsetx = xmax1 else: offsetx = xmin1 if valign == 'center': offsety = (ymin1 + ymax1) / 2.0 elif valign == 'top': offsety = ymax1 elif valign == 'baseline': offsety = ymax1 - baseline elif valign == 'center_baseline': offsety = ymax1 - baseline / 2.0 else: offsety = ymin1 offsetx, offsety = M.transform_point((offsetx, offsety)) xmin -= offsetx ymin -= offsety bbox = Bbox.from_bounds(xmin, ymin, width, height) # now rotate the positions around the first x,y position xys = M.transform(offset_layout) - (offsetx, offsety) ret = bbox, list(zip(lines, zip(ws, hs), *xys.T)), descent self._cached[key] = ret return ret