def update(self, data): self.frame_scatter.setData( np.tile(self.depths, self.sensor_config.sweeps_per_frame), data["frame"].flatten(), ) self.fast_scatter.setData(self.depths, data["fast"]) self.slow_scatter.setData(self.depths, data["slow"]) self.data_plot.setYRange( *self.frame_smooth_limits.update(data["frame"])) noise = data["noise"] self.noise_curve.setData(self.depths, noise) self.noise_plot.setYRange(0, self.noise_smooth_max.update(noise)) movement_x = data["presence_distance"] move_ys = data["depthwise_presence"] self.inter_curve.setData(self.depths, data["inter"]) self.total_curve.setData(self.depths, move_ys) m = self.move_smooth_max.update(np.max(move_ys)) m = max(m, 2 * self.processing_config.detection_threshold) self.move_plot.setYRange(0, m) self.move_depth_line.setPos(movement_x) self.move_depth_line.setVisible(bool(data["presence_detected"])) move_hist_ys = data["presence_history"] move_hist_xs = np.linspace(-self.history_length_s, 0, len(move_hist_ys)) self.move_hist_curve.setData(move_hist_xs, np.minimum(move_hist_ys, OUTPUT_MAX)) if data["presence_detected"]: present_text = "Presence detected at {:.0f} cm".format(movement_x * 100) present_html = self.present_html_format.format(present_text) self.present_text_item.setHtml(present_html) self.present_text_item.show() self.not_present_text_item.hide() else: self.present_text_item.hide() self.not_present_text_item.show() brush = utils.pg_brush_cycler(0) for sector in self.sectors: sector.setBrush(brush) if data["presence_detected"]: index = (data["presence_distance_index"] + self.sector_offset) // self.sector_size self.sectors[index].setBrush(utils.pg_brush_cycler(1))
def update(self, data): # Data plots for i, ys in enumerate(data["frame"].T): self.data_curves[i].setData(ys) # Spectral density plot psd_db = 20 * np.log10(data["nasd_temporal_max"]) psd_threshold_db = 20 * np.log10(data["temporal_max_threshold"]) m = self.smooth_max.update(max(2 * psd_threshold_db, np.max(psd_db))) self.sd_plot.setYRange(0, m) self.sd_curve.setData(self.bin_vs * self.unit.scale, psd_db) self.sd_threshold_line.setPos(psd_threshold_db) # Rolling speed plot vs = data["vel_history"] * self.unit.scale mask = ~np.isnan(vs) ts = -np.flip(np.arange(vs.size)) * self.dt bs = data["belongs_to_last_sequence"] brushes = [utils.pg_brush_cycler(int(b)) for b in bs[mask]] self.vel_scatter.setData(ts[mask], vs[mask], brush=brushes) v = data["vel"] if v: html = self.vel_html_fmt.format(v * self.unit.scale, self.unit.label) self.vel_text_item.setHtml(html) self.vel_text_item.show() self.vel_max_line.setPos(v * self.unit.scale) self.vel_max_line.show() else: self.vel_text_item.hide() self.vel_max_line.hide() # Sequence speed plot hs = data["sequence_vels"] * self.unit.scale self.bar_graph.setOpts(height=hs) if hs[-1] > 1e-3: html = self.vel_html_fmt.format(hs[-1], self.unit.label) self.sequences_text_item.setHtml(html)
def setup(self, win): win.setWindowTitle("Acconeer presence detection example") self.limit_lines = [] dashed_pen = pg.mkPen("k", width=2.5, style=QtCore.Qt.DashLine) # Data plot self.data_plot = win.addPlot( row=0, col=0, title="Frame (blue), fast (orange), and slow (green)", ) self.data_plot.setMenuEnabled(False) self.data_plot.setMouseEnabled(x=False, y=False) self.data_plot.hideButtons() self.data_plot.showGrid(x=True, y=True) self.data_plot.setLabel("bottom", "Depth (m)") self.data_plot.setLabel("left", "Amplitude") self.data_plot.setYRange(0, 2**16) self.frame_scatter = pg.ScatterPlotItem( size=10, brush=utils.pg_brush_cycler(0), ) self.fast_scatter = pg.ScatterPlotItem( size=10, brush=utils.pg_brush_cycler(1), ) self.slow_scatter = pg.ScatterPlotItem( size=10, brush=utils.pg_brush_cycler(2), ) self.data_plot.addItem(self.frame_scatter) self.data_plot.addItem(self.fast_scatter) self.data_plot.addItem(self.slow_scatter) self.frame_smooth_limits = utils.SmoothLimits( self.sensor_config.update_rate) # Noise estimation plot self.noise_plot = win.addPlot( row=1, col=0, title="Noise", ) self.noise_plot.setMenuEnabled(False) self.noise_plot.setMouseEnabled(x=False, y=False) self.noise_plot.hideButtons() self.noise_plot.showGrid(x=True, y=True) self.noise_plot.setLabel("bottom", "Depth (m)") self.noise_plot.setLabel("left", "Amplitude") self.noise_curve = self.noise_plot.plot(pen=utils.pg_pen_cycler()) self.noise_smooth_max = utils.SmoothMax(self.sensor_config.update_rate) # Depthwise presence plot self.move_plot = win.addPlot( row=2, col=0, title="Depthwise presence", ) self.move_plot.setMenuEnabled(False) self.move_plot.setMouseEnabled(x=False, y=False) self.move_plot.hideButtons() self.move_plot.showGrid(x=True, y=True) self.move_plot.setLabel("bottom", "Depth (m)") self.move_plot.setLabel("left", "Norm. ampl.") zero_curve = self.move_plot.plot(self.depths, np.zeros_like(self.depths)) self.inter_curve = self.move_plot.plot() self.total_curve = self.move_plot.plot() self.move_smooth_max = utils.SmoothMax( self.sensor_config.update_rate, tau_decay=1.0, tau_grow=0.25, ) self.move_depth_line = pg.InfiniteLine(pen=pg.mkPen("k", width=1.5)) self.move_depth_line.hide() self.move_plot.addItem(self.move_depth_line) limit_line = pg.InfiniteLine(angle=0, pen=dashed_pen) self.move_plot.addItem(limit_line) self.limit_lines.append(limit_line) fbi = pg.FillBetweenItem( zero_curve, self.inter_curve, brush=utils.pg_brush_cycler(0), ) self.move_plot.addItem(fbi) fbi = pg.FillBetweenItem( self.inter_curve, self.total_curve, brush=utils.pg_brush_cycler(1), ) self.move_plot.addItem(fbi) # Presence history plot self.move_hist_plot = pg.PlotItem(title="Presence history") self.move_hist_plot.setMenuEnabled(False) self.move_hist_plot.setMouseEnabled(x=False, y=False) self.move_hist_plot.hideButtons() self.move_hist_plot.showGrid(x=True, y=True) self.move_hist_plot.setLabel("bottom", "Time (s)") self.move_hist_plot.setLabel( "left", "Score (limited to {})".format(OUTPUT_MAX)) self.move_hist_plot.setXRange(-self.history_length_s, 0) self.move_hist_plot.setYRange(0, OUTPUT_MAX) self.move_hist_curve = self.move_hist_plot.plot( pen=utils.pg_pen_cycler()) limit_line = pg.InfiniteLine(angle=0, pen=dashed_pen) self.move_hist_plot.addItem(limit_line) self.limit_lines.append(limit_line) self.present_html_format = '<div style="text-align: center">' \ '<span style="color: #FFFFFF;font-size:15pt;">' \ "{}</span></div>" not_present_html = '<div style="text-align: center">' \ '<span style="color: #FFFFFF;font-size:15pt;">' \ "{}</span></div>".format("No presence detected") self.present_text_item = pg.TextItem( fill=pg.mkColor(0xff, 0x7f, 0x0e, 200), anchor=(0.5, 0), ) self.not_present_text_item = pg.TextItem( html=not_present_html, fill=pg.mkColor(0x1f, 0x77, 0xb4, 180), anchor=(0.5, 0), ) pos = (-self.history_length_s / 2, 0.95 * OUTPUT_MAX) self.present_text_item.setPos(*pos) self.not_present_text_item.setPos(*pos) self.move_hist_plot.addItem(self.present_text_item) self.move_hist_plot.addItem(self.not_present_text_item) self.present_text_item.hide() # Sector plot self.sector_plot = pg.PlotItem() self.sector_plot.setAspectLocked() self.sector_plot.hideAxis("left") self.sector_plot.hideAxis("bottom") self.sectors = [] pen = pg.mkPen("k", width=1) span_deg = 25 for r in np.flip(np.arange(self.num_sectors) + 1): sector = pg.QtGui.QGraphicsEllipseItem(-r, -r, r * 2, r * 2) sector.setStartAngle(-16 * span_deg) sector.setSpanAngle(16 * span_deg * 2) sector.setPen(pen) self.sector_plot.addItem(sector) self.sectors.append(sector) self.sectors.reverse() sublayout = win.addLayout(row=3, col=0) sublayout.layout.setColumnStretchFactor(0, 2) sublayout.addItem(self.move_hist_plot, col=0) sublayout.addItem(self.sector_plot, col=1) self.setup_is_done = True self.update_processing_config()