1 geometry

geometry

Shared prepared geometry kernels used across ARIA-NBV domains.

1.1 Package guide

aria_nbv.geometry owns shared coordinate and geometric computations whose meaning is independent of rendering, storage, or a particular learning workflow. The frame owner in frames.py implements Aria/EFM LUF conventions: world-up construction, pose-aware look-at axes, rig-to-camera composition, and the fixed CW90 display-basis transform.

1.2 Ownership and depth

frames.py is the single owner for these frame operations. Callers should import the named operation from aria_nbv.geometry.frames; they should not reconstruct the LUF basis or duplicate the CW90 matrix. Camera calibration, image sampling, renderer policy, voxel policy, and scientific target policy remain with their existing owners. This boundary keeps coordinate conventions in one place without making geometry depend on rendering.

The public operations are world_up_tensor, view_axes_from_poses, view_axes_from_points, world_from_camera, and rotate_yaw_cw90. Their tensor batch, dtype, device, and pose-frame behavior is documented in the source docstrings and guarded by the integration and pose-generation tests.

1.3 Usage

from aria_nbv.geometry.frames import world_up_tensor

up = world_up_tensor()  # tensor([0., 0., 1.])

Use rotate_yaw_cw90 only for the established display-basis correction. Keep world/rig/camera composition explicit at call sites so a display transform is not mistaken for a physical pose change.

point_mesh.py separately owns prepared mesh queries reused by pruning and RRI. Metric reductions and target/candidate policy remain with those domain owners; shared geometry provides their geometric computations.

1.4 Import migration

Use aria_nbv.geometry.frames in place of aria_nbv.utils.frames. Frame operations are not re-exported by the geometry root. The documented utils.frames leaf remains an identity-preserving compatibility alias, and utils.rotate_yaw_cw90 retains its existing export. Retire these paths only after an agreed deprecation release or an explicit breaking-import decision.

1.5 Proof

From the repository root:

cd aria_nbv
uv run pytest tests/integration/test_frames_real_data.py \
  tests/pose_generation/test_align_to_gravity.py \
  tests/pose_generation/test_candidate_mixture.py \
  tests/pose_generation/test_pose_generation.py \
  tests/pose_generation/test_target_shell.py

Real-data cases require the local ASE tar/mesh data and pinned EFM3D taxonomy.

The relocation preserves the implementation bodies. Focused proof is provided by tests/integration/test_frames_real_data.py, the pose-generation alignment, mixture, generation, and target-shell tests, plus import and Ruff checks. The geometry package does not import rendering or camera adapters.

1.6 Shared crop predicates

crops.py owns closed point membership, ANY_VERTEX face admission, conservative face-AABB overlap, deterministic whole-face remapping, and exact OBB triangle surface clipping. These predicates are distinct: overlap screening is not exact intersection and ANY_VERTEX can miss crossing faces. Oracle wrappers own policy identities and typed failures; rendering builds its camera-to-target region; trimesh adapters retain fallback, warnings and submesh handling.

face_aabb_overlap_mask(..., face_batch_size=None) uses vectorized scalar coordinate screening; positive batch sizes bound temporary memory. Exact clipping screens all faces first and batches only overlap survivors (default 32768), because pathological targets may intersect the entire mesh. Six clipping planes are sequential and fan triangulation is tensorized. No new cache or automatic batch selection is introduced; renderer screening defaults remain 200000 until real-mesh measurements justify a change.

1.7 Classes

Name Description
PreparedMeshQuery Prepare immutable mesh state once for repeated geometric queries.

1.7.1 PreparedMeshQuery

geometry.PreparedMeshQuery(verts, faces, *, device, dtype, mesh=None)

Prepare immutable mesh state once for repeated geometric queries.

The module lazily materializes normalized PyTorch3D tensors and Trimesh adapters behind one interface. A query is valid only while its source tensors and optional CPU mesh remain immutable. Inference-mode tensors are valid for one query but deliberately uncacheable because Torch does not expose their mutation counters.

1.7.1.1 Parameters

Name Type Description Default
verts Tensor["V 3", float] World-frame vertices in metres. required
faces Tensor["F 3", int] Triangle indices into verts. required
device torch.device | str Device used by point-distance kernels. required
dtype torch.dtype Floating-point dtype used by point-distance kernels. required
mesh 'trimesh.Trimesh | None' Optional CPU Trimesh adapter for signed-distance and ray queries. None

1.7.1.2 Attributes

Name Description
is_persistently_reusable Return whether sources are safe to retain across requests.
source_faces_dtype Return the original face dtype without changing historical materialization.

1.7.1.3 Methods

Name Description
acquire Reuse a matching query or prepare one for the supplied mesh contract.
matches Return whether this query can safely serve the supplied mesh inputs.
validate_source_face_indices Check original triangle indices before an evaluator materializes the mesh.
matches_request Validate immediate use against exact sources, including inference tensors.
pytorch3d_mesh Return normalized mesh tensors while caching only autograd-safe state.
point_distance Return point-to-mesh distances for matching device/dtype points.
signed_distance Return absolute Trimesh signed distances on the points’ device.
intersects_any Return whether each bounded ray intersects the prepared mesh.
1.7.1.3.1 acquire
geometry.PreparedMeshQuery.acquire(
    current,
    verts,
    faces,
    *,
    device,
    dtype,
    mesh=None,
)

Reuse a matching query or prepare one for the supplied mesh contract.

1.7.1.3.2 matches
geometry.PreparedMeshQuery.matches(verts, faces, *, device, dtype, mesh)

Return whether this query can safely serve the supplied mesh inputs.

1.7.1.3.3 validate_source_face_indices
geometry.PreparedMeshQuery.validate_source_face_indices()

Check original triangle indices before an evaluator materializes the mesh.

The historical prepared-mesh path retains its existing coercion behavior; stricter evaluators call this explicitly before PyTorch indexing can reinterpret a negative index or an out-of-range value.

1.7.1.3.4 matches_request
geometry.PreparedMeshQuery.matches_request(verts, faces, *, device, dtype, mesh)

Validate immediate use against exact sources, including inference tensors.

Matching unavailable mutation counters are safe only at this explicit request boundary. :meth:matches remains fail-closed for cross-request cache reuse.

1.7.1.3.5 pytorch3d_mesh
geometry.PreparedMeshQuery.pytorch3d_mesh()

Return normalized mesh tensors while caching only autograd-safe state.

1.7.1.3.6 point_distance
geometry.PreparedMeshQuery.point_distance(points, *, squared=False)

Return point-to-mesh distances for matching device/dtype points.

1.7.1.3.6.1 Parameters
Name Type Description Default
points Tensor["N 3", float] World-frame points in metres. required
squared bool Return squared distances when true. False
1.7.1.3.6.2 Returns
Name Type Description
torch.Tensor Tensor["N", float] distances in metres or square metres.
1.7.1.3.6.3 Raises
Name Type Description
ValueError If points do not match the prepared device and dtype.
1.7.1.3.7 signed_distance
geometry.PreparedMeshQuery.signed_distance(points)

Return absolute Trimesh signed distances on the points’ device.

1.7.1.3.8 intersects_any
geometry.PreparedMeshQuery.intersects_any(
    origins,
    directions,
    *,
    max_distance,
    use_pyembree,
)

Return whether each bounded ray intersects the prepared mesh.

1.8 Functions

Name Description
bounded_ray_intersects_any Return first-hit intersections bounded by each ray segment length.

1.8.1 bounded_ray_intersects_any

geometry.bounded_ray_intersects_any(
    engine,
    origins,
    directions,
    *,
    max_distance,
)

Return first-hit intersections bounded by each ray segment length.

Back to top