RadianceLab · Native implementation document

Projectors, phase & depth

Four-shot CW, multiple frequencies and off-axis carrier demodulation, including ambiguity resolution.

Key relationships · typeset equations
X=I0−I2,Y=I1−I3,ϕ^=atan2⁡(Y,X)X=I_0-I_2,\quad Y=I_1-I_3,\quad \widehat\phi=\operatorname{atan2}(Y,X)
The sign matches the native minus-phase acquisition convention given below; it is not interchangeable with a plus-phase convention.
kj=round⁡(fjℓcoarse−νj),ℓj=νj+kjfjk_j=\operatorname{round}(f_j\ell_{\mathrm{coarse}}-\nu_j),\qquad\ell_j=\frac{\nu_j+k_j}{f_j}
Frequency f is cycles per world-space path unit; measured phase ν is expressed in turns. A calibrated coarse path resolves the integer ambiguity.

Open Render → Projector imaging / depth capture. Position the main camera, select a measurement, and press Take four-shot depth capture (or Acquire + reconstruct off-axis). The measurement sensor uses a calibrated pinhole at that viewpoint. It owns its renderer and film, so the main camera, exposure, lens and render settings remain unchanged. Use internal measurement fixture provides two matte spheres in front of a wall when a clean first experiment is useful.

Interactive refresh after moving takes a new acquisition after the previous one finishes if the camera or scene changed. Show breakdown reveals the individual observations, phase and confidence. This is a sequence of native GPU passes; the four phase buckets are not four copies synthesized from a z-buffer. At one sample per bucket the minimum is four passes for single-frequency CW, twelve for three-frequency CW, and nine for the anchored off-axis experiment. Additional samples improve the estimates. Camera pose and scene geometry are held at capture time. Changing the live scene cancels an in-progress acquisition.

Six calibrated acquisitions

Measurement What is acquired Reconstruction
CW-ToF / four shots Four quadratures of the co-located point projector DC cancellation, wrapped phase, absolute range within the declared low-frequency interval
CW-ToF / three frequencies Four shots each at f, 4f, 16f Coarse-to-fine integer-turn resolution and amplitude-weighted refinement
Off-axis / rolling sensor Two four-shot coarse anchors, then one fine-frequency spatial-carrier interferogram FFT, isolate −K, recenter, IFFT, phase, absolute ambiguity resolution with the anchors
Off-axis / emitter delay ramp Same, with a calibrated angular delay ramp on the point projector The emitter ramp gives the same known sensor carrier, including its constant phase offset
CW-ToF / plane phase front Four shots at each of three frequencies with the existing idealized panel projector Invert path = radial distance + forward depth
CW-ToF / line emitter Four shots at each of three frequencies with the existing line projector Invert path = radial distance + perpendicular distance to the emitter line

The off-axis acquisition uses the native modulated-light envelope signal. It is a Fourier fringe-analysis experiment with the same demodulation geometry as off-axis interferometry. It does not claim that RGB radiance includes optical interference, speckle or coherent diffraction. The existing synthetic postprocess experiments remain available separately.

An arbitrary plane/line emission ramp generally depends on the unknown surface position. It cannot be separated with the same fixed FFT crop. The implemented emitter-ramp preset uses the co-located point projector, whose angular coordinates are known from the camera ray. Rolling the sensor makes the carrier independent of surface depth directly.

What was missing, and the sign that matters

The native shader measures

I[k] = B + A cos(phi_path - phi_emit - phi_sensor - k*pi/2)
X = I[0] - I[2]
Y = I[1] - I[3]
phi_measured = atan2(Y, X)
A = hypot(X, Y) / 2
B = (I[0] + I[1] + I[2] + I[3]) / 4

The old recovery shader used the opposite sine difference. Its sign is now corrected. Its explicitly named GT-guided diagnostic modes are still legacy diagnostics; the new pipeline never invokes them.

The opposed differences remove phase-independent illumination. Nonzero A/B is necessary for reliable phase. In addition to amplitude and modulation visibility, the new mask checks quadrature closure and disagreement between frequencies. These tests reject many failed pixels, but they are not a proof against all multipath, aliasing or low-signal failures.

Here f is cycles per world-space path unit, equivalent to physical modulation frequency divided by propagation speed. It is not a wavelength in nanometres. The longest monostatic direct path is 2*maximumRange; the default f = .45/maximumRange keeps it below one turn. This declared capture range is a calibration constraint supplied by the user, not a range read from scene depth. The single-frequency result has correspondingly coarser precision. These phase/range and ambiguity relations follow the four-quadrature sensor model described in Texas Instruments' ToF introduction.

For each higher frequency, lift the measured phase by the integer closest to the coarse estimate, then refine using the frequency and amplitude weights:

k[j] = round(f[j]*path_coarse - measured_turns[j])
path[j] = (measured_turns[j] + k[j]) / f[j]
weight[j] = (f[j]*A[j])^2

Finally compare every measured phase with the phase predicted by the recovered path. A poor coarse estimate can still select the wrong fine turn; the residual threshold controls which such results are accepted. The numerical tests cover crossing multiple wrap boundaries, rather than only one smooth unwrapped ramp.

Off-axis phase is not automatically absolute depth

The fine interferogram is B + A cos(phi_path - carrier). Its −K Fourier sideband contains the positive object phase. Selecting and moving that band to DC before the inverse FFT recovers a complex field. The implementation also corrects the constant difference between pixel-center sampling and FFT index coordinates. The phase sign and this half-pixel offset have an independent DFT test. The Fourier carrier method is the construction introduced by Takeda, Ina and Kobayashi.

Spatial phase unwrapping, already available in HoloDepthV2, gives a continuous relative phase on suitable connected regions. It does not determine the global integer turn or reconnect depth-discontinuous surfaces by itself. The new absolute result therefore uses the measured low/middle-frequency anchors. Neither the object depth texture nor its min/max is fed into this calculation.

FFT filtering trades resolution for sideband separation. A depth edge creates wide spatial frequencies; a finite crop mixes its two sides and can create a halo or invalid band. Strong albedo edges can also leak into the selected band. This is why a one-frame fringe can look smoother while losing details that four-shot demodulation preserves. See also the original reconstruction analysis in Verrier and Atlan.

Geometry, multipath and current scope

The native point projector is co-located with the camera. For a pinhole ray d=(dx,dy,dz) and radial range r, a direct point-light path has length 2r. The panel model has phase path r*(1+dz). A vertical line model has r*(1+sqrt(1-dy²)). Recovery uses these functions; simply dividing every path by two would be wrong off-axis for the panel and line. The line emitter's modulation helper now uses the same vertical-zero sweep convention as its actual illumination connection.

The panel is the existing idealized phase-front projector: its shading and visibility connection is not a complete extended-source optical model. The line likewise represents a closest-point connection. Those limitations are not hidden by the calibrated inverse.

By default acquisition uses a single surface interaction and no medium for a clean direct-range measurement. Include multipath + medium retains several surface and medium interactions. Then the observed complex value is a weighted sum of path phasors, and its phase is apparent range, not necessarily the nearest surface. Enabling this is a useful failure experiment; three frequencies do not constitute a general multipath separation algorithm. Frequency-diverse separation is a larger inverse problem, for example Bhandari et al.'s sparse multi-frequency reconstruction.

Promising additional pipelines include calibrated projector-camera triangulation (phase shifting plus Gray codes), pulsed transient ranging, and frequency-swept sparse path recovery. They require, respectively, a nonzero projector baseline and calibration, transient bins, or an explicit multipath inversion. The present plane/line presets are useful acquisition geometries; they are not marketed as three additional unrelated depth algorithms.

Export and validation

Exports include top-down range, forward depth, confidence and validity as RGBA32F; the native four-shot arrays; readable PNGs; and capture.json with frequency units, geometry, samples, source and limitations. The displayed RMSE is a separate diagnostic against the renderer's axial depth. That reference is read only after reconstruction has finished.

Headless native capture hooks:

PRISM_IMAGING_AUTORUN=0..5
PRISM_IMAGING_EXPORT=<output directory>
PRISM_IMAGING_SAMPLES=1..128

They select the internal matte fixture, acquire, and export once without closing the application. PrismProjectorDepthTest is the independent numerical test target (5,709 assertions in the initial validation).

The native validation record includes all six acquisitions, original buckets, recovered images, calibration and independent error analysis. The three-frequency CW fixture reaches median axial error 0.00076 world units; the two off-axis setups reach 0.00428 and 0.00626, with approximately 98% valid pixels. Silhouette mixing makes global RMS higher, so the record reports both global and smooth-region errors.

PrismProjectorDepthGPUTest additionally exercises the actual GPU inverse and FFT, including a rectangular sensor crossing phase branch cuts. Resampling interpolates complex values before extracting phase, and the sideband window tapers into its Gaussian tail; interpolating wrapped phase or abruptly clipping the Gaussian causes artificial depth streaks and ringing.