class QuadsLayer(BaseLayer): def __init__(self, data, cmap='hot_r'): self.data = data if cmap is not None: self.cmap = geoplotlib.colors.ColorMap(cmap, alpha=196) else: self.cmap = None def invalidate(self, proj): self.painter = BatchPainter() x, y = proj.lonlat_to_screen(self.data['lon'], self.data['lat']) w = x.max() - x.min() h = y.max() - y.min() w = np.ceil(w / 2) * 2 h = np.ceil(h / 2) * 2 l = max(w, h) root = QuadTree(x.min(), x.min() + l, y.min() + l, y.min()) maxarea = (root.right - root.left) * (root.top - root.bottom) queue = [root] done = [] while len(queue) > 0: qt = queue.pop() if qt.can_split(x, y): queue.extend(qt.split()) else: done.append(qt) print len(queue), len(done) if self.cmap is not None: for qt in done: area = (qt.right - qt.left) * (qt.top - qt.bottom) self.painter.set_color(self.cmap.to_color(1 + area, 1 + maxarea, 'log')) self.painter.rect(qt.left, qt.top, qt.right, qt.bottom) else: for qt in done: self.painter.linestrip([qt.left, qt.right, qt.right, qt.left], [qt.top, qt.top, qt.bottom, qt.bottom], closed=True) def draw(self, proj, mouse_x, mouse_y, ui_manager): self.painter.batch_draw()
class QuadsLayer(BaseLayer): def __init__(self, data, cmap='hot_r'): self.data = data if cmap is not None: self.cmap = geoplotlib.colors.ColorMap(cmap, alpha=196) else: self.cmap = None def invalidate(self, proj): self.painter = BatchPainter() x, y = proj.lonlat_to_screen(self.data['lon'], self.data['lat']) w = x.max() - x.min() h = y.max() - y.min() w = np.ceil(w / 2) * 2 h = np.ceil(h / 2) * 2 l = max(w, h) root = QuadTree(x.min(), x.min() + l, y.min() + l, y.min()) maxarea = (root.right - root.left) * (root.top - root.bottom) queue = [root] done = [] while len(queue) > 0: qt = queue.pop() if qt.can_split(x, y): queue.extend(qt.split()) else: done.append(qt) print((len(queue), len(done))) if self.cmap is not None: for qt in done: area = (qt.right - qt.left) * (qt.top - qt.bottom) self.painter.set_color( self.cmap.to_color(1 + area, 1 + maxarea, 'log')) self.painter.rect(qt.left, qt.top, qt.right, qt.bottom) else: for qt in done: self.painter.linestrip([qt.left, qt.right, qt.right, qt.left], [qt.top, qt.top, qt.bottom, qt.bottom], closed=True) def draw(self, proj, mouse_x, mouse_y, ui_manager): self.painter.batch_draw()
class HistogramLayer(BaseLayer): def __init__(self, data, cmap='hot', alpha=220, colorscale='sqrt', binsize=16, show_tooltip=False, scalemin=0, scalemax=None, f_group=None, show_colorbar=True): """Create a 2D histogram :param data: data access object :param cmap: colormap name :param alpha: color alpha :param colorscale: scaling [lin, log, sqrt] :param binsize: size of the hist bins :param show_tooltip: if True, will show the value of bins on mouseover :param scalemin: min value for displaying a bin :param scalemax: max value for a bin :param f_group: function to apply to samples in the same bin. Default is to count :param show_colorbar: show colorbar :return: """ self.data = data self.cmap = colors.ColorMap(cmap, alpha=alpha) self.binsize = binsize self.show_tooltip = show_tooltip self.scalemin = scalemin self.scalemax = scalemax self.colorscale = colorscale self.f_group = f_group if self.f_group is None: self.f_group = lambda grp: len(grp) self.show_colorbar = show_colorbar def invalidate(self, proj): self.painter = BatchPainter() x, y = proj.lonlat_to_screen(self.data['lon'], self.data['lat']) self.data['_xbin'] = (x / self.binsize).astype(int) self.data['_ybin'] = (y / self.binsize).astype(int) uniquevalues = set([ tuple(row) for row in np.vstack([self.data['_xbin'], self.data['_ybin']]).T ]) results = {(v1,v2): self.f_group(self.data.where((self.data['_xbin'] == v1) & (self.data['_ybin'] == v2))) \ for v1, v2 in uniquevalues} del self.data['_xbin'] del self.data['_ybin'] self.hotspot = HotspotManager() if self.scalemax: self.vmax = self.scalemax else: self.vmax = max(results.values()) if len(results) > 0 else 0 if self.vmax >= 1: for (ix, iy), value in list(results.items()): if value > self.scalemin: self.painter.set_color( self.cmap.to_color(value, self.vmax, self.colorscale)) l = self.binsize rx = ix * self.binsize ry = iy * self.binsize self.painter.rect(rx, ry, rx + l, ry + l) if self.show_tooltip: self.hotspot.add_rect(rx, ry, l, l, 'Value: %d' % value) def draw(self, proj, mouse_x, mouse_y, ui_manager): self.painter.batch_draw() picked = self.hotspot.pick(mouse_x, mouse_y) if picked: ui_manager.tooltip(picked) if self.show_colorbar: ui_manager.add_colorbar(self.cmap, self.vmax, self.colorscale) def bbox(self): return BoundingBox.from_points(lons=self.data['lon'], lats=self.data['lat'])
class HistogramLayer(BaseLayer): def __init__(self, data, cmap='hot', alpha=220, colorscale='sqrt', binsize=16, show_tooltip=False, scalemin=0, scalemax=None, f_group=None): """Create a 2D histogram :param data: data access object :param cmap: colormap name :param alpha: color alpha :param colorscale: scaling [lin, log, sqrt] :param binsize: size of the hist bins :param show_tooltip: if True, will show the value of bins on mouseover :param scalemin: min value for displaying a bin :param scalemax: max value for a bin :param f_group: function to apply to samples in the same bin. Default is to count :return: """ self.data = data self.cmap = colors.ColorMap(cmap, alpha=alpha) self.binsize = binsize self.show_tooltip = show_tooltip self.scalemin = scalemin self.scalemax = scalemax self.colorscale = colorscale self.f_group = f_group if self.f_group is None: self.f_group = lambda grp: len(grp) def invalidate(self, proj): self.painter = BatchPainter() x, y = proj.lonlat_to_screen(self.data['lon'], self.data['lat']) self.data['_xbin'] = (x / self.binsize).astype(int) self.data['_ybin'] = (y / self.binsize).astype(int) uniquevalues = set([tuple(row) for row in np.vstack([self.data['_xbin'],self.data['_ybin']]).T]) results = {(v1,v2): self.f_group(self.data.where((self.data['_xbin'] == v1) & (self.data['_ybin'] == v2))) \ for v1, v2 in uniquevalues} del self.data['_xbin'] del self.data['_ybin'] self.hotspot = HotspotManager() if self.scalemax: vmax = self.scalemax else: vmax = max(results.values()) if len(results) > 0 else 0 if vmax >= 1: for (ix, iy), value in results.items(): if value > self.scalemin: self.painter.set_color(self.cmap.to_color(value, vmax, self.colorscale)) l = self.binsize rx = ix * self.binsize ry = iy * self.binsize self.painter.rect(rx, ry, rx+l, ry+l) if self.show_tooltip: self.hotspot.add_rect(rx, ry, l, l, 'Value: %d' % value) def draw(self, proj, mouse_x, mouse_y, ui_manager): self.painter.batch_draw() picked = self.hotspot.pick(mouse_x, mouse_y) if picked: ui_manager.tooltip(picked) def bbox(self): return BoundingBox.from_points(lons=self.data['lon'], lats=self.data['lat'])