Skip to content

Commit

Permalink
Unified visualizer & override ui, enabled on all entities (#6599)
Browse files Browse the repository at this point in the history
### What

Previously, we had ui for adding component overrides, under an
experimental feature everywhere except the time series view + some
hardcoded ui for manipulating overrides (those that were
`EntityProperties` in 0.16).

This PR removes both the component override ui and the hardcoded
property ui in favor of a new overview + override ui showing all
currently used values by all active visualizers + ability to add/remove
visualizers.


https://github.com/rerun-io/rerun/assets/1220815/425a9406-9eb2-4319-846b-fe0d0eee1a42

---

Noteworthy "sideeffects":
* `ComponentUiCallback` now uses raw arrow arrays, allowing it to show
fallbacks
* kills lots'a old code :)
* `VisualizerQueryInfo::queried` keeps now archetype component ordering
instead of alphabetical (not in above video yet)
* lots of inconsistency in our data flow are now visible

---

Planned direct follow-ups:
* allow various reset / override menus 
* particularly important: remove override, add (single) override on
multi-value
* Would be great to do this with a menu button, will have to be a
context menu until emilk/egui#4607 is handled
* allow expanding to see the override/store/default/fallback stack
* original plan was to skip on this, but the method has all the data
layed out neatly now, so might as well!
* get the "Add" button integrated into the top (unless this is hard?)
*  show better docs: #6556
* Find a better name for the "blueprint section" below

---

Also needed but not planned short term:
* inspect multivalues
* we could do so for store multivalues already, but everything else we
can't yet select, so let's tackle this later
* ui polish

---

Part of:
* #4888

### Checklist
* [x] I have read and agree to [Contributor
Guide](https://github.com/rerun-io/rerun/blob/main/CONTRIBUTING.md) and
the [Code of
Conduct](https://github.com/rerun-io/rerun/blob/main/CODE_OF_CONDUCT.md)
* [x] I've included a screenshot or gif (if applicable)
* [x] I have tested the web demo (if applicable):
* Using examples from latest `main` build:
[rerun.io/viewer](https://rerun.io/viewer/pr/6599?manifest_url=https://app.rerun.io/version/main/examples_manifest.json)
* Using full set of examples from `nightly` build:
[rerun.io/viewer](https://rerun.io/viewer/pr/6599?manifest_url=https://app.rerun.io/version/nightly/examples_manifest.json)
* [x] The PR title and labels are set such as to maximize their
usefulness for the next release's CHANGELOG
* [x] If applicable, add a new check to the [release
checklist](https://github.com/rerun-io/rerun/blob/main/tests/python/release_checklist)!

- [PR Build Summary](https://build.rerun.io/pr/6599)
- [Recent benchmark results](https://build.rerun.io/graphs/crates.html)
- [Wasm size tracking](https://build.rerun.io/graphs/sizes.html)

To run all checks from `main`, comment on the PR with `@rerun-bot
full-check`.
  • Loading branch information
Wumpf authored Jun 20, 2024
1 parent c0bd16a commit 4b6bc9e
Show file tree
Hide file tree
Showing 26 changed files with 561 additions and 881 deletions.
1 change: 1 addition & 0 deletions Cargo.lock
Original file line number Diff line number Diff line change
Expand Up @@ -5266,6 +5266,7 @@ dependencies = [
"half 2.3.1",
"indexmap 2.1.0",
"itertools 0.13.0",
"linked-hash-map",
"macaw",
"ndarray",
"nohash-hasher",
Expand Down
27 changes: 14 additions & 13 deletions crates/re_data_ui/src/component.rs
Original file line number Diff line number Diff line change
@@ -1,24 +1,20 @@
use std::sync::Arc;

use egui::NumExt;

use re_entity_db::{external::re_query::LatestAtComponentResults, EntityPath, InstancePath};
use re_log_types::Instance;
use re_types::ComponentName;
use re_ui::{ContextExt as _, SyntaxHighlighting as _};
use re_viewer_context::{UiLayout, ViewerContext};

use super::DataUi;
use crate::item_ui;

/// All the values of a specific [`re_log_types::ComponentPath`].
pub struct EntityLatestAtResults {
pub struct EntityLatestAtResults<'a> {
pub entity_path: EntityPath,
pub component_name: ComponentName,
pub results: Arc<LatestAtComponentResults>,
pub results: &'a LatestAtComponentResults,
}

impl DataUi for EntityLatestAtResults {
impl<'a> DataUi for EntityLatestAtResults<'a> {
fn data_ui(
&self,
ctx: &ViewerContext<'_>,
Expand All @@ -27,12 +23,17 @@ impl DataUi for EntityLatestAtResults {
query: &re_data_store::LatestAtQuery,
db: &re_entity_db::EntityDb,
) {
re_tracing::profile_function!(self.component_name);
let Some(component_name) = self.results.component_name(db.resolver()) else {
// TODO(#5607): what should happen if the promise is still pending?
return;
};

re_tracing::profile_function!(component_name);

// TODO(#5607): what should happen if the promise is still pending?
let Some(num_instances) = self
.results
.raw(db.resolver(), self.component_name)
.raw(db.resolver(), component_name)
.map(|data| data.len())
else {
ui.weak("<pending>");
Expand Down Expand Up @@ -74,7 +75,7 @@ impl DataUi for EntityLatestAtResults {
if let Some(histogram) = db
.tree()
.subtree(&self.entity_path)
.and_then(|tree| tree.entity.components.get(&self.component_name))
.and_then(|tree| tree.entity.components.get(&component_name))
{
if histogram.num_static_messages() > 1 {
ui.label(ui.ctx().warning_text(format!(
Expand Down Expand Up @@ -139,7 +140,7 @@ impl DataUi for EntityLatestAtResults {
query,
db,
&self.entity_path,
&self.results,
self.results,
&Instance::from(0),
);
} else if one_line {
Expand All @@ -157,7 +158,7 @@ impl DataUi for EntityLatestAtResults {
ui.label("Index");
});
header.col(|ui| {
ui.label(self.component_name.short_name());
ui.label(component_name.short_name());
});
})
.body(|mut body| {
Expand Down Expand Up @@ -186,7 +187,7 @@ impl DataUi for EntityLatestAtResults {
query,
db,
&self.entity_path,
&self.results,
self.results,
&instance,
);
});
Expand Down
5 changes: 1 addition & 4 deletions crates/re_data_ui/src/component_path.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
use std::sync::Arc;

use re_log_types::ComponentPath;
use re_ui::ContextExt as _;
use re_viewer_context::{UiLayout, ViewerContext};
Expand Down Expand Up @@ -31,8 +29,7 @@ impl DataUi for ComponentPath {
if let Some(results) = results.components.get(component_name) {
crate::EntityLatestAtResults {
entity_path: entity_path.clone(),
component_name: *component_name,
results: Arc::clone(results),
results: results.as_ref(),
}
.data_ui(ctx, ui, ui_layout, query, db);
} else if let Some(entity_tree) = ctx.recording().tree().subtree(entity_path) {
Expand Down
49 changes: 23 additions & 26 deletions crates/re_data_ui/src/component_ui_registry.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use re_data_store::LatestAtQuery;
use re_entity_db::{external::re_query::LatestAtComponentResults, EntityDb};
use re_log_types::{external::arrow2, EntityPath, Instance};
use re_entity_db::EntityDb;
use re_log_types::{external::arrow2, EntityPath};
use re_types::external::arrow2::array::Utf8Array;
use re_ui::UiExt;
use re_viewer_context::{ComponentUiRegistry, UiLayout, ViewerContext};

use super::EntityDataUi;
Expand Down Expand Up @@ -39,43 +40,39 @@ pub fn add_to_registry<C: EntityDataUi + re_types::Component>(registry: &mut Com
registry.add_display_ui(
C::name(),
Box::new(
|ctx, ui, ui_layout, query, db, entity_path, component, instance| {
// TODO(#5607): what should happen if the promise is still pending?
if let Some(component) = component.instance::<C>(db.resolver(), instance.get() as _)
{
component.entity_data_ui(ctx, ui, ui_layout, entity_path, query, db);
} else {
ui.weak("(not found)");
|ctx, ui, ui_layout, query, db, entity_path, component_raw| match C::from_arrow(
component_raw,
) {
Ok(components) => match components.len() {
0 => {
ui.weak("(empty)");
}
1 => {
components[0].entity_data_ui(ctx, ui, ui_layout, entity_path, query, db);
}
i => {
ui.label(format!("{} values", re_format::format_uint(i)));
}
},
Err(err) => {
ui.error_label("(failed to deserialize)")
.on_hover_text(err.to_string());
}
},
),
);
}

#[allow(clippy::too_many_arguments)]
fn fallback_component_ui(
_ctx: &ViewerContext<'_>,
ui: &mut egui::Ui,
ui_layout: UiLayout,
_query: &LatestAtQuery,
db: &EntityDb,
_db: &EntityDb,
_entity_path: &EntityPath,
component: &LatestAtComponentResults,
instance: &Instance,
component: &dyn arrow2::array::Array,
) {
// TODO(#5607): what should happen if the promise is still pending?
let value = component
.component_name(db.resolver())
.and_then(|component_name| {
component.instance_raw(db.resolver(), component_name, instance.get() as _)
});

// No special ui implementation - use a generic one:
if let Some(value) = value {
arrow_ui(ui, ui_layout, &*value);
} else {
ui.weak("(null)");
}
arrow_ui(ui, ui_layout, component);
}

fn arrow_ui(ui: &mut egui::Ui, ui_layout: UiLayout, array: &dyn arrow2::array::Array) {
Expand Down
3 changes: 1 addition & 2 deletions crates/re_data_ui/src/instance_path.rs
Original file line number Diff line number Diff line change
Expand Up @@ -121,8 +121,7 @@ impl DataUi for InstancePath {
if instance.is_all() {
crate::EntityLatestAtResults {
entity_path: entity_path.clone(),
component_name,
results: std::sync::Arc::clone(results),
results: results.as_ref(),
}
.data_ui(
ctx,
Expand Down
3 changes: 2 additions & 1 deletion crates/re_edit_ui/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ use datatype_editors::{
use re_types::{
blueprint::components::{BackgroundKind, Corner2D, LockRangeDuringZoom, ViewFit, Visible},
components::{
AggregationPolicy, AxisLength, Color, Colormap, FillRatio, GammaCorrection,
AggregationPolicy, AxisLength, Color, Colormap, DepthMeter, FillRatio, GammaCorrection,
ImagePlaneDistance, MagnificationFilter, MarkerSize, Name, Radius, StrokeWidth, Text,
},
};
Expand Down Expand Up @@ -59,6 +59,7 @@ pub fn register_editors(registry: &mut re_viewer_context::ComponentUiRegistry) {
registry.add_singleline_editor_ui::<Text>(edit_singleline_string);
registry.add_singleline_editor_ui::<Name>(edit_singleline_string);

registry.add_singleline_editor_ui::<DepthMeter>(edit_f32_zero_to_max_float_raw);
registry.add_singleline_editor_ui::<MarkerSize>(edit_f32_zero_to_max_float_raw);
registry.add_singleline_editor_ui::<Radius>(edit_f32_zero_to_max_float_raw);
registry.add_singleline_editor_ui::<StrokeWidth>(edit_f32_zero_to_max_float_raw);
Expand Down
11 changes: 11 additions & 0 deletions crates/re_query/src/latest_at/helpers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,17 @@ impl LatestAtComponentResults {
}
}

/// Tries to return the component data as an arrow array.
///
/// Logs a warning and returns `None` if the component is missing or cannot be deserialized.
#[inline]
pub fn try_raw(&self, resolver: &PromiseResolver) -> Option<Box<dyn Array>> {
match self.resolved(resolver) {
PromiseResult::Pending | PromiseResult::Error(_) => None,
PromiseResult::Ready(cell) => Some(cell.to_arrow()),
}
}

/// Returns true if the component is missing, an empty array or still pending.
pub fn is_empty(&self, resolver: &PromiseResolver) -> bool {
match self.resolved(resolver) {
Expand Down
2 changes: 1 addition & 1 deletion crates/re_selection_panel/src/defaults_ui.rs
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ pub fn defaults_ui(ctx: &ViewContext<'_>, space_view: &SpaceViewBlueprint, ui: &
// TODO(jleibs): We can do something fancier in the future such as presenting both
// options once we have a motivating use-case.
for (id, vis) in ctx.visualizer_collection.iter_with_identifiers() {
for component in vis.visualizer_query_info().queried {
for &component in vis.visualizer_query_info().queried.iter() {
component_to_vis.entry(component).or_insert_with(|| id);
}
}
Expand Down
2 changes: 1 addition & 1 deletion crates/re_selection_panel/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
//! The UI for the selection panel.
mod defaults_ui;
mod override_ui;
mod query_range_ui;
mod selection_history_ui;
mod selection_panel;
mod space_view_entity_picker;
mod space_view_space_origin_ui;
mod visualizer_ui;

pub use selection_panel::SelectionPanel;

Expand Down
Loading

0 comments on commit 4b6bc9e

Please sign in to comment.