Skip to content

Commit 020350d

Browse files
committed
3d in 2d back working
1 parent fdb7a45 commit 020350d

File tree

1 file changed

+63
-18
lines changed

1 file changed

+63
-18
lines changed

crates/store/re_tf/src/transform_forest.rs

Lines changed: 63 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -392,6 +392,9 @@ impl TransformForest {
392392
}
393393
};
394394

395+
// Query type of target's root for later.
396+
let target_root_info = self.roots.get(&target.root);
397+
395398
itertools::Either::Right(sources.map(move |source| {
396399
let Some(root_from_source) = self.root_from_entity.get(&source) else {
397400
return (
@@ -413,6 +416,11 @@ impl TransformForest {
413416
let target_from_source = root_from_source.left_multiply(target.target_from_root);
414417
Ok(target_from_source)
415418
}
419+
// There might be a connection via a pinhole making this 3D in 2D.
420+
else if let Some(TransformTreeRootInfo::Pinhole(pinhole_tree_root)) = target_root_info
421+
{
422+
from_3d_source_to_2d_target(&target, &source, pinhole_tree_root)
423+
}
416424
// There might be a connection via a pinhole making this 2D in 3D.
417425
else if let Some(TransformTreeRootInfo::Pinhole(pinhole_tree_root)) =
418426
self.roots.get(&source.root)
@@ -439,36 +447,81 @@ impl TransformForest {
439447
fn from_2d_source_to_3d_target(
440448
target: &TargetInfo,
441449
source: &SourceInfo<'_>,
442-
pinhole_tree_root: &PinholeTreeRoot,
450+
source_pinhole_tree_root: &PinholeTreeRoot,
443451
lookup_image_plane_distance: &dyn Fn(EntityPathHash) -> f32,
444452
) -> Result<TransformInfo, TransformFromToError> {
445453
let PinholeTreeRoot {
446454
parent_tree_root,
447455
pinhole_projection,
448456
parent_root_from_pinhole_root: root_from_pinhole3d,
449-
} = pinhole_tree_root;
457+
} = source_pinhole_tree_root;
450458

459+
// `root` here is the target's root!
460+
// We call the source's root `pinhole3d` to distinguish it.
451461
if *parent_tree_root != target.root {
452462
return Err(TransformFromToError::no_path_between_target_and_source(
453463
target, source,
454464
));
455465
}
456466

457467
// Rename for clarification:
458-
let pinhole2d_from_source = source.root_from_source;
468+
let image_plane_from_source = source.root_from_source;
459469

460470
// There's a connection via a pinhole making this 2D in 3D.
461471
// We can transform into the target space!
462472
let pinhole_image_plane_distance = lookup_image_plane_distance(source.root);
463473

464474
// TODO: Locally cache pinhole transform?
465-
let pinhole3d_from_pinhole2d =
466-
pinhole2d_image_plane_from_pinhole3d(pinhole_projection, pinhole_image_plane_distance);
467-
let target_from_pinhole2d =
468-
target.target_from_root * root_from_pinhole3d * pinhole3d_from_pinhole2d;
475+
let pinhole3d_from_image_plane =
476+
pinhole3d_from_image_plane(pinhole_projection, pinhole_image_plane_distance);
477+
let target_from_image_plane =
478+
target.target_from_root * root_from_pinhole3d * pinhole3d_from_image_plane;
469479

470-
// target_from_source = target_from_pinhole2d * pinhole2d_from_source
471-
Ok(pinhole2d_from_source.left_multiply(target_from_pinhole2d))
480+
// target_from_source = target_from_image_plane * image_plane_from_source
481+
Ok(image_plane_from_source.left_multiply(target_from_image_plane))
482+
}
483+
484+
fn from_3d_source_to_2d_target(
485+
target: &TargetInfo,
486+
source: &SourceInfo<'_>,
487+
target_pinhole_tree_root: &PinholeTreeRoot,
488+
) -> Result<TransformInfo, TransformFromToError> {
489+
let PinholeTreeRoot {
490+
parent_tree_root,
491+
pinhole_projection,
492+
parent_root_from_pinhole_root: root_from_pinhole3d,
493+
} = target_pinhole_tree_root;
494+
495+
// `root` here is the source's root!
496+
// We call the target's root `pinhole3d` to distinguish it.
497+
if *parent_tree_root != source.root {
498+
return Err(TransformFromToError::no_path_between_target_and_source(
499+
target, source,
500+
));
501+
}
502+
503+
// Rename for clarification:
504+
let target_from_image_plane = target.target_from_root;
505+
506+
// TODO(#1025):
507+
// There's no meaningful image plane distance for 3D->2D views.
508+
let pinhole_image_plane_distance = 500.0;
509+
// Currently our 2D views require us to invert the `pinhole2d_image_plane_from_pinhole3d` matrix.
510+
// This builds a relationship between the 2D plane and the 3D world, when actually the 2D plane
511+
// should have infinite depth!
512+
// The inverse of this matrix *is* working for this, but quickly runs into precision issues.
513+
// See also `ui_2d.rs#setup_target_config`
514+
515+
// TODO: Locally cache pinhole transform?
516+
let pinhole3d_from_image_plane =
517+
pinhole3d_from_image_plane(pinhole_projection, pinhole_image_plane_distance);
518+
let image_plane_from_pinhole3d = pinhole3d_from_image_plane.inverse();
519+
let pinhole3d_from_root = root_from_pinhole3d.inverse();
520+
let target_from_root =
521+
target_from_image_plane * image_plane_from_pinhole3d * pinhole3d_from_root;
522+
523+
// target_from_source = target_from_root * root_from_source
524+
Ok(source.root_from_source.left_multiply(target_from_root))
472525
}
473526

474527
fn left_multiply_smallvec1_of_transforms(
@@ -531,7 +584,7 @@ fn compute_root_from_archetype(
531584
.unwrap_or_default()
532585
}
533586

534-
fn pinhole2d_image_plane_from_pinhole3d(
587+
fn pinhole3d_from_image_plane(
535588
resolved_pinhole_projection: &ResolvedPinholeProjection,
536589
pinhole_image_plane_distance: f32,
537590
) -> glam::Affine3A {
@@ -567,14 +620,6 @@ fn pinhole2d_image_plane_from_pinhole3d(
567620

568621
// Above calculation is nice for a certain kind of visualizing a projected image plane,
569622
// but the image plane distance is arbitrary and there might be other, better visualizations!
570-
571-
// TODO(#1025):
572-
// As such we don't ever want to invert this matrix!
573-
// However, currently our 2D views require us to do exactly that since we're forced to
574-
// build a relationship between the 2D plane and the 3D world, when actually the 2D plane
575-
// should have infinite depth!
576-
// The inverse of this matrix *is* working for this, but quickly runs into precision issues.
577-
// See also `ui_2d.rs#setup_target_config`
578623
}
579624

580625
/// Resolved transforms at an entity.

0 commit comments

Comments
 (0)