SOPHIA XT
Research · Spatial comprehension

Scene understanding from a cloud of points

How a system goes from raw 3D measurements to a description it can reason about: which surface is the floor, what stands on it, where each thing sits relative to the others, and what stays where when it goes out of view. Every figure on this page computes its answer in front of you.

Figures
Four, computed live in the browser
Methods
RANSAC, PCA, Kalman filtering, Euclidean clustering, ray casting
Author
Sophia, SOPHIA XT
The pipeline

From measurements to a map

A depth sensor returns points. Nothing in that list says which points belong together, which surface is the ground, or how many objects there are. Scene understanding is the chain of estimates that turns the list into a description: a dominant plane, the clusters that rise from it, a shape and an extent for each cluster, the relations between them, and a map of which cells of space are filled.

Each link in that chain is a small, well-posed estimation problem with a known answer. The four figures below run those problems on a synthetic scene whose ground truth is known, so every readout can be checked. The same routines run on real sensor data; the difference is the noise, which is why the open problems at the end are about noise.

Point cloud · RANSAC plane fit · Euclidean clustering
Finding the floor, then what stands on it
hypothesis inliers refined plane inliers clusters unassigned
Hypotheses
39
N for p = 0.99
154
Inlier ratio w
0.309
RMS residual
—
n̂
0.15, -0.10, 0.98
d (n̂·p + d = 0)
-0.002
Clusters
0
Phase
sampling
A few hundred points sampled from a tilted floor, a box, a sphere and a cylinder, with Gaussian noise σ on every coordinate and 2% uniform outliers. Each frame draws three random triples, fits a plane through each and counts points within τ of it; the best hypothesis is kept. Once the count passes twice the Fischler–Bolles bound N = log(1 − p) / log(1 − w³) for the measured inlier ratio w, the winner is refined by least squares (the smallest eigenvector of the inlier scatter matrix) and the remaining points are clustered by a 0.28 unit connectivity radius; a cluster that contains a horizontal planar patch with points above it is split there, since those points rest on a support. Each cluster is then labelled: a sphere when the residual of an algebraic sphere fit sits at the noise level, a cylinder when the radius of its side points depends on neither azimuth nor height, otherwise a box.

The plane model and the RANSAC bound

A plane is a unit normal and an offset. A point lies on it when

\hat{\mathbf{n}} \cdot \mathbf{p} + d = 0, \qquad \|\hat{\mathbf{n}}\| = 1

and its signed distance from the plane is \hat{\mathbf{n}} \cdot \mathbf{p} + d. Three points fix a plane, so each RANSAC hypothesis draws three at random and counts the points within \tau. If a fraction w of the points are inliers, the probability that a triple is all inliers is w^3, and the number of draws needed to see at least one clean triple with confidence p is

N = \frac{\log(1 - p)}{\log(1 - w^3)}

(Fischler & Bolles 1981). The figure reads w off its best hypothesis, evaluates this bound for p = 0.99, and stops after twice that many draws.

Least-squares refinement

The winning triple is only three noisy points. The refinement fits all the inliers at once: with centroid \bar{\mathbf{p}} and scatter matrix

S = \sum_{i \in \text{inliers}} (\mathbf{p}_i - \bar{\mathbf{p}})(\mathbf{p}_i - \bar{\mathbf{p}})^{\mathsf T}

the normal that minimises the sum of squared distances is the eigenvector of S with the smallest eigenvalue, and d = -\hat{\mathbf{n}} \cdot \bar{\mathbf{p}}. The figure computes it by Jacobi rotations on the 3 × 3 matrix. The remaining points are then linked whenever two lie within 0.28 units of each other, which is Euclidean clustering; each cluster is then labelled by two tests: a sphere when the residual of an algebraic sphere fit sits at the noise level, a cylinder when the radius of its side points about the footprint centre depends on neither azimuth nor height, and otherwise a box. A cluster that contains a horizontal patch with points resting on it is split at that patch first.

Object permanence

Holding an estimate through an occlusion

Object permanence · Kalman filter · constant-velocity model
Keeping the estimate while the object is hidden
truth measurement +estimate · 2σ ellipse
Innovation |y|
—px
NIS yᵀS⁻¹y
—
σ position (P)
—px
‖K‖ gain
—
Error vs truth
—px
State
—
Updates
0
Predictions
0
The white dot is the true target on a Lissajous path; amber dots are its position measured with noise σz at 30 Hz. The filter state is position and velocity with a white-noise acceleration model of strength σa, and the cyan cross is its estimate. While the target is behind the panel no measurement arrives, only the prediction x ← Fx, P ← FPFᵀ + Q runs, and the 2σ ellipse of the position covariance grows with the elapsed hidden time. When the target reappears the innovation y = z − Hx is large for one step, the gain K = PHᵀS⁻¹ pulls the estimate back, and the ellipse collapses. The NIS readout is the innovation normalised by its predicted covariance S; for a consistent filter it averages about 2, the measurement dimension.

Predict

The state is position and velocity, \mathbf{x} = [p_x, p_y, v_x, v_y]^{\mathsf T}, and between frames it moves at constant velocity with an unknown acceleration of strength \sigma_a:

\hat{\mathbf{x}}^- = F\hat{\mathbf{x}}, \qquad P^- = F P F^{\mathsf T} + Q, \qquad F = \begin{bmatrix} I & \Delta t\, I \\ 0 & I \end{bmatrix}

with Q the discrete white-noise acceleration covariance, whose position block grows as \sigma_a^2 \Delta t^4 / 4. This step runs whether or not a measurement arrives. Behind the panel it is the only step that runs, and P grows every frame; the ellipse in the figure is the 2σ contour of its position block.

Update

When a measurement \mathbf{z} of the position arrives, the innovation and its covariance are

\mathbf{y} = \mathbf{z} - H\hat{\mathbf{x}}^-, \qquad S = H P^- H^{\mathsf T} + R

and the gain, state and covariance follow:

K = P^- H^{\mathsf T} S^{-1}, \quad \hat{\mathbf{x}} = \hat{\mathbf{x}}^- + K\mathbf{y}, \quad P = (I - KH)P^-(I - KH)^{\mathsf T} + K R K^{\mathsf T}

The figure uses the Joseph form for P so it stays symmetric. The normalised innovation squared, \mathbf{y}^{\mathsf T} S^{-1} \mathbf{y}, is what a filter uses to judge itself: for a consistent filter it is chi-squared with two degrees of freedom, so it averages about 2. The first update after the panel is where it spikes.

Relations

Reading a scene graph off the geometry

Spatial relations · interval tests in the plane frame
A scene graph computed from the fitted geometry
8 relations · plan view of the floor frameu →v ↑left ofin front ofin front ofleft ofleft ofin front ofin front ofonAbox · h 0.59Bcylinder · h 0.81Csphere · h 0.56Dbox · h 0.27
Aleft ofBgap 0.931
Bin front ofAgap 1.737
Cin front ofAgap 1.336
Cleft ofBgap 0.867
Dleft ofBgap 1.101
Bin front ofDgap 2.072
Cin front ofDgap 1.671
DonAgap 0.010
Objects
4
Relations
8
Pairs tested
12
Plane RMS
0.0121
Inliers
241/734
n̂
0.15, -0.12, 0.98
Left: the segmented scene with each object's extent box drawn in the plane frame (u, v along the fitted floor, n̂ its normal). Right: the relation graph as a plan view of the floor frame: each node sits at its object's footprint centroid, the dashed boxes are the footprints, and an object resting on another is lifted so the pair stays legible. For objects A and B, 'on' holds when their footprints overlap and A's lowest point sits within 0.12 units of B's highest; 'above' when the gap is larger; 'left of' and 'in front of' when the u or v intervals are disjoint; 'near' when the footprints do not overlap but the gap is under 0.35 units. Shuffle re-places the objects and the whole chain runs again: plane fit, clustering, shape tests, relations.

The plane frame

Relations need a frame, and the fitted floor supplies one. From \hat{\mathbf{n}} the figure builds two in-plane unit vectors and expresses every point as

u = \hat{\mathbf{u}} \cdot \mathbf{p}, \qquad v = \hat{\mathbf{v}} \cdot \mathbf{p}, \qquad h = \hat{\mathbf{n}} \cdot \mathbf{p} + d

so h is height above the floor and each cluster gets an axis-aligned extent [u_{\min}, u_{\max}] \times [v_{\min}, v_{\max}] \times [h_{\min}, h_{\max}]. The scene is generated with a tilt, so this frame is not the world frame; the relations come out right because they are computed in the fitted one.

Interval tests

Every relation is a test on two extents. With footprints that overlap in both u and v,

\text{on}(A, B): \; |h^A_{\min} - h^B_{\max}| < 2\varepsilon, \qquad \text{above}(A, B): \; h^A_{\min} - h^B_{\max} \ge 2\varepsilon

and with disjoint intervals along one axis,

\text{left of}(A, B): \; u^A_{\max} < u^B_{\min}, \qquad \text{in front of}(A, B): \; v^A_{\max} < v^B_{\min}

with \varepsilon set to about twice the point noise. This is the Allen interval algebra applied per axis; the graph is the list of tests that pass.

Occupancy

What is filled, what is free, what is unknown

Occupancy grid · ray-cast visibility · log-odds mapping
What the sensor can see, and what it has mapped
Occupied voxels
—
Visible now
—
Mapped p > 0.7
—
Free p < 0.3
—
Unknown
—
Rays / pass
—
Hits this pass
—
Passes
0
The point cloud is binned into 0.125-unit voxels. A sensor orbits at radius 3.1 and casts 64 × 26 rays per pass through the grid; each ray is walked voxel by voxel with the Amanatides–Woo traversal until it hits an occupied cell. Cells crossed on the way add l_free = −0.4 to their log-odds, the hit cell adds l_occ = +0.85, and the probability is p = 1/(1 + e^−l). Bright cyan voxels are hit this pass, dim cyan were mapped on earlier passes, grey have never been seen; floor cells are drawn as flat tiles so the objects read above them. The slice on the right is the probability map at one height: cyan for occupied, navy for free, faint for unknown.

Walking a ray through the grid

The Amanatides–Woo traversal (1987) visits exactly the voxels a ray crosses, in order. For a ray \mathbf{o} + t\mathbf{d} it keeps, per axis, the parameter at which the ray next crosses a voxel boundary and the step between crossings:

t_{\max,x} = \frac{x_{\text{next}} - o_x}{d_x}, \qquad t_{\Delta x} = \left|\frac{\Delta}{d_x}\right|

and at each step advances along whichever axis has the smallest t_{\max}. The figure casts 64 × 26 rays per pass and stops each at the first occupied voxel.

Log-odds mapping

Each voxel keeps the log-odds of being occupied and adds a constant per observation:

l \leftarrow l + \begin{cases} l_{\text{occ}} & \text{ray ends here} \\ l_{\text{free}} & \text{ray passes through} \end{cases}, \qquad p = \frac{1}{1 + e^{-l}}

with l_{\text{occ}} = 0.85, l_{\text{free}} = -0.4 and l clamped to ±4 so a cell can change its mind. This is the occupancy-grid update of Moravec and Elfes (1985) in the form OctoMap uses (Hornung et al. 2013). A voxel the sensor has never looked at stays at l = 0, p = 0.5, which is the honest state for unknown space.

Rigid motion

The transforms under the figures

Rodrigues' rotation

R(\hat{\mathbf{k}}, \theta) = I + \sin\theta\, K + (1 - \cos\theta)\, K^2

K is the cross-product matrix of the unit axis \hat{\mathbf{k}}. The scene tilt and the orbiting cameras in every figure are this formula.

Rigid transform

T = \begin{bmatrix} R & \mathbf{t} \\ \mathbf{0}^{\mathsf T} & 1 \end{bmatrix} \in SE(3)

Rotation and translation in one 4 × 4 matrix, so a chain of frames composes by multiplication. Sensor-to-world and plane-to-world are both of this form.

Quaternion rotation

q = \cos\tfrac{\theta}{2} + \sin\tfrac{\theta}{2}\,(u_x \mathbf{i} + u_y \mathbf{j} + u_z \mathbf{k})

Four numbers for a rotation, no gimbal lock, and interpolation along the shortest arc. The representation of choice when orientations are estimated over time.

Where this goes

DiagBuddy.AI

DiagBuddy.AI, now ServiceLens, is the appliance-diagnosis product SOPHIA XT built and runs at diagbuddygo.com: field service and dispatch, with diagnostics grounded in a parts corpus we built rather than licensed.

A technician's photograph of an appliance interior is a scene of exactly the kind above: a few planar surfaces, boxes and cylinders, and components hidden behind others. The routines on this page, a dominant plane, clusters with shapes and extents, relations between them, and an estimate that survives an occlusion, are what a diagnostic model needs in order to read such a photograph as a layout rather than as pixels. That is the research track this page documents.

Open problems

What the synthetic scene hides

Noise that is not Gaussian

Real depth sensors have range-dependent, anisotropic error, dropouts on dark and specular surfaces, and flying pixels at edges. RANSAC's threshold \tau then has to vary with range, and the least-squares refinement needs a robust weighting. The figure's single \sigma is the simplest case.

More than one plane

Rooms have walls, tables and shelves. The fit has to be run sequentially, removing each plane's inliers before the next, and the relation frame has to be chosen from among them. Gravity from an inertial sensor settles which plane is the floor faster than geometry does.

Manoeuvring targets

The constant-velocity model is consistent until the target turns hard behind the panel. The standard answer is a bank of models with an interacting mixture (Blom & Bar-Shalom 1988); the price is several filters running at once.

Resolution and memory

A dense 0.125 unit grid over a room is a few hundred thousand voxels; a building at 5 cm is billions. Octrees with pruned uniform subtrees, the OctoMap design, keep the log-odds update while storing only what varies.