Skip to content

Curved-Ray Renderer Architecture Master Outline

1) Executive Summary

This document is the code-grounded master outline for the curved-ray renderer in this repository.

  • Current state: the runtime path is a Godot-driven renderer where curved rays are generated as bounded segment chains (RayBeamRenderer.RaySeg) and consumed by a two-pass film pipeline (GrinFilmCamera.RenderStep).
  • Current state: field and geometry broadphase data are snapshotted into RendererCore.SceneSnapshot.SceneSnapshot and shared via RendererCore.Common.FrameSnapshotBus.
  • Current state: pass-2 collision/narrowphase still uses Godot physics (IntersectRay, IntersectShape, CastMotion) with optional GeometryTLAS candidate pruning.
  • Planned / TODO: internal triangle-level intersection (BLAS + internal narrowphase) is not wired yet.

What this engine is:

  • A curved-ray film renderer embedded in Godot.
  • A hybrid architecture where RendererCore owns snapshot/field/TLAS data structures while final collision is still delegated to Godot physics.

What this engine is not (today):

  • Not yet a fully internal intersection stack.
  • Not yet an end-to-end task-graph scheduler in RendererCore/Scheduler.
  • Not yet a production "Core" backend that replaces the legacy film path.

What "curved rays are first-class" means in implementation terms:

  • Rays are explicitly represented as segment sequences (RaySeg) with: A, B, TraveledB, and RadiusBound.
  • RadiusBound is consumed by pass-2 envelope broadphase (Aabb3.FromSegment(...).Expand(...)).
  • Pass-1 integration can be physically-driven (UseIntegratedField) with adaptive step sizing, not just straight-line + post bend.

Source anchors:

  • GrinFilmCamera.cs
  • RayBeamRenderer.cs
  • RendererCore/SceneSnapshot/SceneSnapshot.cs
  • RendererCore/Common/FrameSnapshotBus.cs

Academic / PhD-Level Target (New)

This architecture is explicitly intended to scale from interactive GRIN ray bending to research-grade gravitational optics:

  • Baseline: GRIN-style curved-ray transport controlled by simple field parameters (what the engine already ships today).
  • Upgrade: null-geodesic integration in arbitrary spacetime metrics (Schwarzschild/Kerr/wormholes), with numerical controls and invariants aligned with academic gravitational optics software.

Key principle for correctness: scene geometry remains Euclidean, while curvature lives in the ray transport law (GRIN effective-medium or metric/geodesic ODE). This matches the standard GR rendering pattern: integrate rays in a curved manifold; intersect rays against embedded geometry surfaces.

2) Current Architecture at a Glance

Godot scene tree
  -> GodotAdapter.SnapshotBuilder.BuildFromGodotScene(...)
      -> SceneSnapshot { Fields, FieldParams, FieldTLAS, Geometry, GeometryTLAS }
      -> CurvatureBoundGrid (added by GrinFilmCamera.RenderFrameBackend)
      -> FrameSnapshotBus.Set(snapshot, frameId)

GrinFilmCamera backend dispatch (per _Process when UpdateEveryFrame=true)
  -> BackendMode.Legacy:
       LegacyBackend.RenderFrame(snapshot)
         -> GrinFilmCamera.RenderStep()
            Pass 1 (Parallel.For): segment integration + optional pass1 hit probes
            Pass 2 (Main thread): broadphase + Godot physics + shading + writeback
            Upload Image -> ImageTexture -> TextureRect/FilmOverlay2D

  -> BackendMode.Core:
       CoreBackend.RenderFrame(snapshot)   // snapshot summary print
       LegacyBackend.RenderFrame(snapshot) // still renders output

  -> BackendMode.Compare:
       LegacyBackend.RenderFrame(snapshot) // TODO compare mode

Current state:

  • Main entry is GrinFilmCamera._Process -> RenderFrameBackend.
  • Snapshot is rebuilt every frame from the live Godot scene.
  • Legacy film pipeline is still the output-producing path.

Source anchors:

  • GrinFilmCamera.cs
  • GodotAdapter/SnapshotBuilder.cs
  • RenderBackends/LegacyBackend.cs
  • RenderBackends/CoreBackend.cs

3) Core Design Principles (As Implemented)

Snapshot Immutability

  • Current state: SceneSnapshot properties are init-set and rebuilt each frame (SnapshotBuilder.BuildFromGodotScene).
  • Current state: consumers read snapshot arrays as immutable for the frame.
  • Current state: immutability is by discipline/convention; arrays are not deep read-only wrappers.

Data-Oriented Layout

  • Current state: field/geometry snapshot data are SOA arrays and packed buffers (FieldEntitySOA, GeometryEntitySOA, PackedParamBuffer).
  • Current state: TLAS node arrays are contiguous (FieldTLAS.Nodes, GeometryTLAS.Nodes) for stack-based traversal.

Determinism and Threading

  • Current state: snapshot extraction order is stabilized by sorting node paths (string.CompareOrdinal).
  • Current state: pass-1 is parallel per pixel; pass-2 remains main-thread due Godot physics API calls.
  • Current state: RenderStep has a re-entry guard (Interlocked).
  • Current state: optional SoftGate random probing uses _rng.Randf(), so deterministic replay is not guaranteed when randomness is enabled.

Source anchors:

  • GodotAdapter/SnapshotBuilder.cs
  • RendererCore/SceneSnapshot/*.cs
  • RendererCore/Fields/FieldTLAS.cs
  • RendererCore/Geometry/GeometryTLAS.cs
  • GrinFilmCamera.cs

4) Module Map (Folders and Responsibilities)

RendererCore/*

  • SceneSnapshot/*: snapshot container and SOA/pod types.
  • Fields/*: field enums, field evaluation, field TLAS, curvature bound grid.
  • Geometry/*: geometry TLAS over world AABBs.
  • Integrators/*: currently only StepPolicy (dt helper).
  • Common/*: snapshot bus + debug overlay/log toggles.
  • Accel/: currently empty.
  • Scheduler/: currently empty.

Portability & Academic Upgrade Interfaces (New)

Goal: keep the current Godot integration working unchanged, while formalizing clear seams so the same core can run:

  • inside Godot (interactive),
  • in headless CLI regression tests,
  • in other host environments long-term.

This is achieved by making ray transport + stepping engine-agnostic and treating Godot as a geometry query backend, not as the owner of physics.

1) Ray Transport / Physics Core Interfaces (RendererCore-owned)

IRayTransport (planned): - Advances a ray state through a curvature model using a chosen integrator tier. - Responsible for: step size control, invariant tracking (GR mode), and producing a polyline/segment chain compatible with existing RaySeg consumption.

Ray state types (planned): - RayState3: position + direction + parameterization (GRIN / 3D optical form) - RayState4: spacetime position x^μ + wavevector/momentum k^μ + affine λ (GR / 4D form)

ITransportModel (planned) is the physics backend plugged into IRayTransport: - GRIN / optical medium backend (scalar/tensor IOR) - Metric / geodesic backend (Christoffel / Hamiltonian RHS) - Optional Gordon/effective-medium adapter backend

2) Metric Interface for GR Mode (Research-grade)

IMetricField (planned): - Metric(x) -> g_{μν}(x) (4x4 symmetric) - Either: - Christoffel(x) -> Γ^μ_{αβ}(x) - or GeodesicRhs(state) -> derivatives for the ODE integrator

Implementation targets (non-exhaustive): - Minkowski (flat) - Schwarzschild - Kerr (Interstellar tier) - Morris–Thorne wormhole (chart/atlas compatible)

This interface is explicitly designed so academics can contribute metric modules without touching renderer frontends or collision backends.

3) Integrator Interface (Tiered)

IIntegrator (planned): - Step(state, rhs, dt) with optional embedded error estimate - Supports integrator tiers: - Tier 0: heuristic adaptive (current behavior) - Tier 1: RK45 / embedded error estimate - Tier 2: symplectic/variational + constraint projection (GR null invariants)

IConstraintProjector (planned, GR-mode only): - enforces/bounds null constraint drift: g_{μν} k^μ k^ν = 0 within tolerance

4) Geometry Query Backend Interface (Host-owned)

IGeometryQueryProvider (planned): - Narrowphase: segment raycast or swept segment test (existing Pass2 concept) - Broadphase: overlap AABB / candidate ID collection (existing TLAS concept)

Godot provides one implementation: - GodotGeometryQueryProvider wraps DirectSpaceState calls

Future implementations: - BVHGeometryQueryProvider (internal triangle BVH / CPU) - OfflineMeshQueryProvider (headless validation / batch renders)

This preserves the core idea: curvature affects ray transport; geometry remains Euclidean.

5) Camera Model Provider (Host-owned, Physics-owned math)

ICameraModelProvider (planned): - returns camera rays in local frame - GR mode can optionally provide tetrad-based emission and frequency bookkeeping

Godot provides: - camera pose + projection + per-frame properties

RendererCore provides: - the math for mapping local camera frame -> initial ray state (3D or 4D).

6) Minimal Adoption Strategy (No Big Refactor)

To avoid a disruptive rewrite: - keep GrinFilmCamera.RenderStep() as orchestrator - carve out a RendererCore.RenderBand(...) call that accepts: - snapshot refs - IRayTransport - IGeometryQueryProvider - camera rays provider - output film buffer accessor

This can start as a thin wrapper around existing Pass1/Pass2 routines and gradually lift logic into RendererCore without breaking the Godot front-end.

Planned additions to support academic gravitational optics (without changing existing flow):

  • Relativity/* (planned): spacetime metric definitions and adapters.
  • IMetricField (metric + connection / RHS).
  • MetricAdapters (optional Gordon/effective-medium mapping where applicable).
  • Transport/* (planned): engine-agnostic ray transport layer.
  • IRayTransport that advances a ray state using chosen integrator tier.
  • CameraModel/* (planned): relativistic camera / tetrad frame support for correctness when rendering strong-field scenes.

Source anchors:

  • RendererCore/SceneSnapshot/SceneSnapshot.cs
  • RendererCore/Fields/FieldSystem.cs
  • RendererCore/Geometry/GeometryTLAS.cs
  • RendererCore/Integrators/StepPolicy.cs
  • RendererCore/Common/FrameSnapshotBus.cs

RenderBackends/*

  • Backend interface and mode enum.
  • LegacyBackend: drives GrinFilmCamera.RenderStep().
  • CoreBackend: currently logs snapshot summary.
  • BackendSelector: exists but is not the active dispatch path.

Source anchors:

  • RenderBackends/IRenderBackend.cs
  • RenderBackends/LegacyBackend.cs
  • RenderBackends/CoreBackend.cs
  • RenderBackends/BackendSelector.cs

GodotAdapter/*

  • Godot scene extraction into SceneSnapshot.
  • Field collection, parameter packing, TLAS builds.
  • Geometry collection as world AABBs + Godot instance IDs.

Source anchors:

  • GodotAdapter/SnapshotBuilder.cs

Root-level Orchestrators / Runtime Nodes

  • GrinFilmCamera: backend dispatch, frame snapshot publish, film render loop, pass-1/pass-2 pipeline, budgets/watchdogs, telemetry.
  • RayBeamRenderer: curved segment integration primitives and collision helper APIs used by film pass.
  • FieldSource3D: authoring/runtime field node definition.
  • FieldGrid3D: pass-1 acceleration cache (vector field grid).
  • FieldProbe3D: runtime probe of snapshot field system + debug overlay output.
  • FilmOverlay2D: 2D overlay renderer for debug rays/hit normals/bus items.
  • PerfScope / PerfStats: timing/counter aggregation and log output.

Source anchors:

  • GrinFilmCamera.cs
  • RayBeamRenderer.cs
  • FieldSource3D.cs
  • FieldGrid3D.cs
  • FieldProbe3D.cs
  • FilmOverlay2D.cs
  • PerfScope.cs
  • PerfStats.cs

5) Data Model and Memory Layout

SceneSnapshot Shape

Current state (RendererCore.SceneSnapshot.SceneSnapshot):

  • InstanceSOA Instances
  • FieldEntitySOA Fields
  • PackedParamBuffer FieldParams
  • FieldTLAS FieldTLAS
  • GeometryEntitySOA Geometry
  • GeometryTLAS GeometryTLAS
  • CurvatureBoundGrid CurvatureGrid

SOA Containers

Current state:

  • InstanceSOA: mesh/material IDs, object/world transforms, world bounds.
  • GeometryEntitySOA: world bounds + GodotInstanceIds.
  • FieldEntitySOA: metric/shape/curve enums, transforms, bounds, param offsets/lengths, flags.

Packed Parameters

Current state:

  • PackedParamBuffer.AppendBlock8(...) stores field params in blocks of 8: rInner, rOuter, amp, a, b, c, r0, r1.

TLAS Layers

Current state:

  • FieldTLAS built from FieldEntitySOA.WorldBounds.
  • GeometryTLAS built from GeometryEntitySOA.WorldBounds.

Frame Rebuild vs Reuse

Current state:

  • Rebuilt per frame: snapshot, field TLAS, geometry TLAS, curvature grid.
  • Reused across frames: camera-owned pass buffers (_segBuf, hit arrays, quick-ray caches, perf windows, optional field grid cache with cadence).

Important present limitation:

  • SnapshotBuilder currently sets Instances = InstanceSOA.Empty(); instance transform SOA is defined but not populated in this path.

Source anchors:

  • RendererCore/SceneSnapshot/SceneSnapshot.cs
  • RendererCore/SceneSnapshot/InstanceSOA.cs
  • RendererCore/SceneSnapshot/GeometryEntitySOA.cs
  • RendererCore/SceneSnapshot/FieldEntitySOA.cs
  • RendererCore/SceneSnapshot/PackedParamBuffer.cs
  • GodotAdapter/SnapshotBuilder.cs

6) Coordinate Spaces and Transforms

Current state:

  • Field evaluation is world-query driven: FieldSystem.AccelAt(Vector3 pWorld, SceneSnapshot snapshot).
  • Field transforms are explicit per entity: WorldFromLocal[] and LocalFromWorld[].
  • Field radius/shape tests are evaluated in field-local space and converted back to world contribution.
  • Geometry in snapshot is currently represented in world AABBs.
  • Camera convention follows Godot: forward is -Basis.Z.

Current state for instance transforms:

  • InstanceSOA.WorldFromObject and ObjectFromWorld are part of model but not currently populated by SnapshotBuilder.

Source anchors:

  • RendererCore/Fields/FieldSystem.cs
  • RendererCore/SceneSnapshot/FieldEntitySOA.cs
  • RendererCore/SceneSnapshot/InstanceSOA.cs
  • GodotAdapter/SnapshotBuilder.cs
  • RayBeamRenderer.cs

7) Fields and Metrics System

Field Entity Representation

Current state:

  • Authored by FieldSource3D with exported: MetricModel, FieldShapeType, FieldCurveType, radii, amplitude, flags, and curve coefficients.
  • Extracted by SnapshotBuilder into SOA arrays and PackedParamBuffer.

Metric Models

Current state (RendererCore.Fields.MetricModel):

  • GRIN = 0
  • GordonMetric = 1

Current behavior:

  • FieldSystem flips local direction sign for GordonMetric vs GRIN.

Academic Optics Contract (New)

This engine supports (and will more explicitly formalize) two physically grounded but operationally distinct formulations of curved light transport:

1) Optical Medium / GRIN (3D) - Rays follow stationary optical path (Fermat principle) through an index field n(x). - Current implementation already author-controls behavior via simple GRIN parameters (beta/gamma curves, radii, amplitude, per-field curve types). - Planned: allow scalar n(x) and later anisotropic/tensor forms n_ij(x) for higher fidelity mappings.

2) Spacetime Metric / Null Geodesics (4D) - Rays follow null geodesics of g_{μν}(x) governed by the geodesic ODE: d²x^μ/dλ² + Γ^μ_{αβ} dx^α/dλ dx^β/dλ = 0. - Planned: integrate either in second-order form or in first-order Hamiltonian form (recommended for invariant preservation).

Gordon / Effective-Medium Bridge (Clarification)

GordonMetric is treated as an adapter path: in some cases, spacetime curvature can be expressed as an effective optical medium. The architecture intends to support both:

  • Direct metric/geodesic stepping (exact within numeric tolerance).
  • Optional mapping to an equivalent GRIN-style transport model (for performance or authoring).

This preserves the existing “simple GRIN input parameters” workflow while enabling academic accuracy where required.

Shapes and Curves

Current state:

  • Shapes: SphereRadial, BoxVolume.
  • Curves: Linear, Power, Polynomial, Exponential.
  • FieldCurves.Eval(...) handles curve law evaluation.

Current limitations / TODO already in code:

  • FieldSystem: BoxVolume currently falls back to radial distance model.
  • FieldSystem: flags behavior includes TODO for 1/r^2 mode details.

Curvature Bounds and Grids

Current state:

  • CurvatureBoundGrid.BuildAroundCamera(...) computes per-cell Kmax using candidate fields via FieldTLAS.QueryAabb.
  • RayBeamRenderer.BuildRaySegmentsCamera_Pass1 converts local Kmax into segment envelope radius bound (RaySeg.RadiusBound).
  • StepPolicy.ComputeDt exists and is used by FieldProbe3D for probe readouts.

Field Cache (FieldGrid3D)

Current state:

  • Optional pass-1 vector field cache (UseFieldGrid) rebuilt on cadence or field cache refresh; sampled before source fallback.

Source anchors:

  • FieldSource3D.cs
  • RendererCore/Fields/FieldModels.cs
  • RendererCore/Fields/FieldCurves.cs
  • RendererCore/Fields/FieldSystem.cs
  • RendererCore/Fields/CurvatureBoundGrid.cs
  • FieldGrid3D.cs
  • FieldProbe3D.cs

8) Curved Ray Representation and Integration

Ray State in Code

Current state:

  • Segment struct: RayBeamRenderer.RaySeg (A, B, TraveledB, RadiusBound).
  • Hit payload: RayBeamRenderer.HitPayload.
  • Pass-1 hit metadata: RayBeamRenderer.Pass1HitInfo.

Integration Method

Current state:

  • Main pass-1 builder: RayBeamRenderer.BuildRaySegmentsCamera_Pass1(...).
  • Uses explicit stepping over StepsPerRay with two paths:
  • Integrated path (UseIntegratedField=true): update velocity by field acceleration and step adaptively.
  • Analytic bend path: parametric bend by beta * t^gamma * bendScale.
  • Adaptive step controls: StepLength, MinStepLength, MaxStepLength, StepAdaptGain, low-curvature boost controls.

Integrator Tiers (New; aligns with “PhD-grade” expectations)

The engine already uses curvature-aware adaptive stepping heuristics. The planned formalization is a tiered integrator system:

  • Tier 0 (Interactive/Preview): current heuristic adaptive stepping (fast).
  • Tier 1 (Research): embedded error-estimating integrators (e.g., RK45 / Dormand–Prince) with adaptive step based on local truncation error, not just |accel| heuristics.
  • Tier 2 (Invariant-Preserving): Hamiltonian geodesic integration with symplectic/variational methods + constraint projection where needed.

Physical Invariants / Constraints (New)

For academic GR mode, ray state must remain null: g_{μν} k^μ k^ν = 0 (within bounded tolerance).

The architecture will track and bound: - null constraint drift (and optionally project back onto constraint manifold) - monotonic affine parameter advance - error estimates and convergence (step-halving / tolerance sweeps)

“Interstellar-Class” Rendering Claim (Clarification)

Achieving Interstellar-style visuals requires: - accurate null geodesic integration in strong-field metrics (e.g., Kerr) - a physically correct camera model (observer frame / aberration / frequency shifts) - shading hooks for redshift and Doppler effects (can be incremental)

The current segment-chain pipeline (RaySeg) remains valid: geodesic transport changes the stepping law, not the downstream broadphase/narrowphase consumption.

Segment Cadence and Envelopes

Current state:

  • Segment emission cadence uses base CollisionEveryNSteps and optional screen-space cadence adaptation.
  • Envelope radius is computed from curvature grid when available.

Chunking and envelope status:

  • Current state: envelope-carrying segments are implemented (RadiusBound).
  • Planned / TODO: dedicated chunk system from Docs/spec_curved_ray_chunks.md is not yet materialized as separate runtime chunk types.

Source anchors:

  • RayBeamRenderer.cs
  • GrinFilmCamera.cs
  • Docs/spec_curved_ray_chunks.md

9) Acceleration Structures and Intersection

TLAS in Runtime

Current state:

  • FieldTLAS: BVH over field AABBs, used for field candidate queries.
  • GeometryTLAS: BVH over geometry AABBs, used as pass-2 candidate pruning.

BVH/BLAS Type Inventory

Current state:

  • RendererCore.Fields.BVHNode in FieldTLAS.
  • RendererCore.Geometry.GeometryBVHNode in GeometryTLAS.
  • No BLAS triangle BVH implementation in RendererCore/Accel yet.

Intersection API Boundary

Current state:

  • Pass-1 generates segments and optional probe hits.
  • Pass-2 performs broadphase + narrowphase using Godot physics: IntersectRay, IntersectShape, CastMotion, and helper wrappers (SubdividedRayHit, SweepSegmentHit).
  • When geometry TLAS pruning is enabled, narrowphase hits are accepted only if collider ID is in TLAS-derived candidate instance IDs.

Validation vs production status:

  • Current state: Godot physics is still production narrowphase.
  • Planned / TODO: internal triangle-level intersection path to replace this.

Source anchors:

  • RendererCore/Fields/FieldTLAS.cs
  • RendererCore/Geometry/GeometryTLAS.cs
  • GrinFilmCamera.cs
  • RayBeamRenderer.cs
  • RendererCore/SceneSnapshot/GeometryEntitySOA.cs

10) Scheduling and Concurrency

Current state work partition:

  • Frame is processed in row bands (RowsPerFrame and adaptive row sizing).
  • Pass-1: Parallel.For across pixels in current band.
  • Pass-2: sequential on main thread.

Current thread-safety strategy:

  • Snapshot is read-only during RenderStep.
  • Pass-1 writes per-pixel buffers (disjoint indices) and merges counters via Interlocked.
  • Re-entry guard prevents overlapping RenderStep invocations.

RenderStep orchestration note (New; matches code):

  • GrinFilmCamera.RenderStep() is treated as the primary frame render trigger point and must remain a clean boundary between:
  • engine-agnostic transport (ideally RendererCore owned), and
  • engine-specific collision/query backends (Godot today).

This supports long-term portability to non-Godot frontends while preserving current behavior.

Current watchdogs and budgets:

  • UpdateEveryFrameBudgetMs, UpdateEveryFrameMaxRowsPerStep.
  • RenderStepMaxMs, RenderStepMaxPixelsPerFrame, RenderStepMaxSegmentsPerFrame.
  • Multiple guard exits for stuck/no-progress/no-hit/no-candidate bands.
  • SoftGate budgets and watchdog (Pass2SoftGate* config set).

Planned / TODO:

  • RendererCore/Scheduler is currently empty; task-graph scheduler doc exists but is not the runtime backbone yet.

Source anchors:

  • GrinFilmCamera.cs
  • RenderBackends/LegacyBackend.cs
  • RendererCore/Scheduler/
  • Docs/spec_scheduler_task_graph.md

11) Rendering Backends and Output

Current backend reality:

  • LegacyBackend is the rendering backend that produces film output.
  • CoreBackend currently prints snapshot summary only.
  • BackendMode.Core currently executes both core summary and legacy render.
  • BackendMode.Compare currently falls back to legacy path.

Current output chain:

  • Film buffer (Image) updated to ImageTexture each render step.
  • Output to configured TextureRect (FilmViewPath) or auto-created overlay.
  • Optional FilmOverlay2D draws world ray/hit overlays + film gradient normals.
  • DebugOverlayBus items (for example from FieldProbe3D) are consumed by FilmOverlay2D.

Postprocess/shader note:

  • Shader files exist in repo, but this C# pipeline does not currently show a dedicated postprocess stage wiring them in runtime code.

Source anchors:

  • RenderBackends/LegacyBackend.cs
  • RenderBackends/CoreBackend.cs
  • RenderBackends/BackendMode.cs
  • GrinFilmCamera.cs
  • FilmOverlay2D.cs
  • RendererCore/Common/DebugOverlayBus.cs

12) Telemetry, Debugging, and Validation

Current telemetry:

  • XPrimeRay.Perf.FramePerf + PerfScope stage timing/counters.
  • PerfStats rolling-window frame summaries and invariant checks.
  • Frame/band render-health logging in GrinFilmCamera.

Current debugging and validation helpers:

  • FieldProbe3D evaluates FieldSystem.AccelAt against current snapshot bus state and draws overlay diagnostics.
  • Geometry prune audit and reject sampling instrumentation in pass-2.
  • FieldSource3D in-game debug shape rendering.
  • RayBeamRenderer debug overlay + GetDebugRayBundle handoff.
  • RayViz and CurvedCamera are auxiliary debug/visual tools.

Validation Suite (New; “PhD-grade” requirements)

Add a reproducible validation harness that can run in-engine and offline. Minimum target scenarios:

Flat-space baselines: - straight-line rays (no field) match analytic results - segment envelope bounds remain stable and conservative

GRIN baselines: - known radial GRIN profiles reproduce expected qualitative lensing - convergence tests vs tighter tolerances / higher tier integrators

Schwarzschild benchmarks: - weak-field deflection matches analytic approximation in far-field - photon sphere behavior appears at expected radius (qualitative + numeric checks)

Kerr benchmarks (Interstellar tier): - compare selected rays against published Kerr geodesic references / datasets - regression snapshots for key camera poses and spin parameters

Wormhole metrics: - Morris–Thorne style throat lensing cases - chart transition / portal remap correctness tests (no coordinate singularity artifacts)

Numerical verification: - step-halving convergence where expected - bounded null-constraint drift in GR mode - optional constraint projection tests

The outcome is a credible claim that the renderer’s transport matches academic gravitational optics expectations to within configured tolerances.

Source anchors:

  • PerfScope.cs
  • PerfStats.cs
  • GrinFilmCamera.cs
  • FieldProbe3D.cs
  • FieldSource3D.cs
  • RayBeamRenderer.cs
  • RayViz.cs
  • CurvedCamera.cs

13) Roadmap (Reconciled to Current Code)

Charter Reality Check

  • Previous charter said: renderer owns all production intersection.
  • Code shows: pass-2 still uses Godot physics; internal TLAS is currently pruning/filtering, not full internal narrowphase.
  • Update needed: add internal triangle acceleration + intersection path before claiming full ownership.

  • Previous charter said: full end-to-end multithreading.

  • Code shows: pass-1 is parallel, pass-2 is main-thread.
  • Update needed: move pass-2 off Godot physics dependency.

  • Previous charter said: scheduler/task graph subsystem.

  • Code shows: scheduler folder is empty; scheduling logic is embedded in GrinFilmCamera.
  • Update needed: migrate runtime scheduling to RendererCore/Scheduler.

Implemented

  • Scene snapshot extraction (SnapshotBuilder) with field/geometry SOA.
  • Field and geometry TLAS builds and queries.
  • Curvature bound grid creation around camera.
  • Pass-1 curved segment integration with adaptive stepping and optional probes.
  • Pass-2 broadphase policies + TLAS-gated Godot narrowphase.
  • Budget/watchdog/telemetry framework in the film renderer.

In Progress

  • Core backend migration (CoreBackend exists but is summary-only).
  • Geometry TLAS pruning quality instrumentation (audit/fn/fp/reject samples).
  • SoftGate policy tuning for quick-ray-miss recovery.

Planned Next

  • Internal BLAS/triangle intersection path and removal of Godot as production narrowphase.
  • RendererCore/Scheduler task graph implementation.
  • Real compare mode in backend dispatch.
  • Explicit runtime chunk system if needed beyond RaySeg envelope usage.

Related specialized docs:

  • Docs/architecture_overview.md
  • Docs/spec_scene_snapshot_data_layout.md
  • Docs/spec_bvh_acceleration.md
  • Docs/spec_metric_models_grin_vs_gordon.md
  • Docs/spec_curved_ray_chunks.md
  • Docs/spec_scheduler_task_graph.md

14) Glossary

  • SceneSnapshot: immutable-for-frame container passed into rendering stages.
  • SOA: struct-of-arrays data layout (FieldEntitySOA, GeometryEntitySOA).
  • PackedParamBuffer: contiguous float buffer for field parameter blocks.
  • TLAS: top-level AABB hierarchy over entities (FieldTLAS, GeometryTLAS).
  • BLAS: lower-level triangle hierarchy; planned, not implemented in code.
  • GRIN: metric model (MetricModel.GRIN) for optical gradient-index behavior.
  • GordonMetric: metric model variant currently implemented as direction-sign inversion in field contribution logic.
  • RaySeg: bounded curved segment used for pass-2 tests and envelopes.
  • RadiusBound: conservative segment envelope radius used for geometry pruning.
  • Pass-1: parallel segment integration stage.
  • Pass-2: main-thread collision + shading stage.
  • SoftGate: gated policy for extra subdivided checks on uncertain misses.
  • FieldGrid3D: optional cached vector field for pass-1 acceleration sampling.
  • CurvatureBoundGrid: camera-centered grid of Kmax upper bounds.
  • RenderHealth: rolling diagnostics for stalls, hit-rate, prune behavior.

4) Module Map (Folders and Responsibilities)

RendererCore/*

  • SceneSnapshot/*: snapshot container and SOA/pod types.
  • Fields/*: field enums, field evaluation, field TLAS, curvature bound grid.
  • Geometry/*: geometry TLAS over world AABBs.
  • Integrators/*: currently only StepPolicy (dt helper).
  • Common/*: snapshot bus + debug overlay/log toggles.
  • Accel/: currently empty.
  • Scheduler/: currently empty.

Source anchors:

  • RendererCore/SceneSnapshot/SceneSnapshot.cs
  • RendererCore/Fields/FieldSystem.cs
  • RendererCore/Geometry/GeometryTLAS.cs
  • RendererCore/Integrators/StepPolicy.cs
  • RendererCore/Common/FrameSnapshotBus.cs

RenderBackends/*

  • Backend interface and mode enum.
  • LegacyBackend: drives GrinFilmCamera.RenderStep().
  • CoreBackend: currently logs snapshot summary.
  • BackendSelector: exists but is not the active dispatch path.

Source anchors:

  • RenderBackends/IRenderBackend.cs
  • RenderBackends/LegacyBackend.cs
  • RenderBackends/CoreBackend.cs
  • RenderBackends/BackendSelector.cs

GodotAdapter/*

  • Godot scene extraction into SceneSnapshot.
  • Field collection, parameter packing, TLAS builds.
  • Geometry collection as world AABBs + Godot instance IDs.

Source anchors:

  • GodotAdapter/SnapshotBuilder.cs

Root-level Orchestrators / Runtime Nodes

  • GrinFilmCamera: backend dispatch, frame snapshot publish, film render loop, pass-1/pass-2 pipeline, budgets/watchdogs, telemetry.
  • RayBeamRenderer: curved segment integration primitives and collision helper APIs used by film pass.
  • FieldSource3D: authoring/runtime field node definition.
  • FieldGrid3D: pass-1 acceleration cache (vector field grid).
  • FieldProbe3D: runtime probe of snapshot field system + debug overlay output.
  • FilmOverlay2D: 2D overlay renderer for debug rays/hit normals/bus items.
  • PerfScope / PerfStats: timing/counter aggregation and log output.

Source anchors:

  • GrinFilmCamera.cs
  • RayBeamRenderer.cs
  • FieldSource3D.cs
  • FieldGrid3D.cs
  • FieldProbe3D.cs
  • FilmOverlay2D.cs
  • PerfScope.cs
  • PerfStats.cs

7) Fields and Metrics System

Field Entity Representation

Current state:

  • Authored by FieldSource3D with exported: MetricModel, FieldShapeType, FieldCurveType, radii, amplitude, flags, and curve coefficients.
  • Extracted by SnapshotBuilder into SOA arrays and PackedParamBuffer.

Metric Models

Current state (RendererCore.Fields.MetricModel):

  • GRIN = 0
  • GordonMetric = 1

Current behavior:

  • FieldSystem flips local direction sign for GordonMetric vs GRIN.

Shapes and Curves

Current state:

  • Shapes: SphereRadial, BoxVolume.
  • Curves: Linear, Power, Polynomial, Exponential.
  • FieldCurves.Eval(...) handles curve law evaluation.

Current limitations / TODO already in code:

  • FieldSystem: BoxVolume currently falls back to radial distance model.
  • FieldSystem: flags behavior includes TODO for 1/r^2 mode details.

Curvature Bounds and Grids

Current state:

  • CurvatureBoundGrid.BuildAroundCamera(...) computes per-cell Kmax using candidate fields via FieldTLAS.QueryAabb.
  • RayBeamRenderer.BuildRaySegmentsCamera_Pass1 converts local Kmax into segment envelope radius bound (RaySeg.RadiusBound).
  • StepPolicy.ComputeDt exists and is used by FieldProbe3D for probe readouts.

Field Cache (FieldGrid3D)

Current state:

  • Optional pass-1 vector field cache (UseFieldGrid) rebuilt on cadence or field cache refresh; sampled before source fallback.

Source anchors:

  • FieldSource3D.cs
  • RendererCore/Fields/FieldModels.cs
  • RendererCore/Fields/FieldCurves.cs
  • RendererCore/Fields/FieldSystem.cs
  • RendererCore/Fields/CurvatureBoundGrid.cs
  • FieldGrid3D.cs
  • FieldProbe3D.cs

8) Curved Ray Representation and Integration

Ray State in Code

Current state:

  • Segment struct: RayBeamRenderer.RaySeg (A, B, TraveledB, RadiusBound).
  • Hit payload: RayBeamRenderer.HitPayload.
  • Pass-1 hit metadata: RayBeamRenderer.Pass1HitInfo.

Integration Method

Current state:

  • Main pass-1 builder: RayBeamRenderer.BuildRaySegmentsCamera_Pass1(...).
  • Uses explicit stepping over StepsPerRay with two paths:
  • Integrated path (UseIntegratedField=true): update velocity by field acceleration and step adaptively.
  • Analytic bend path: parametric bend by beta * t^gamma * bendScale.
  • Adaptive step controls: StepLength, MinStepLength, MaxStepLength, StepAdaptGain, low-curvature boost controls.

Segment Cadence and Envelopes

Current state:

  • Segment emission cadence uses base CollisionEveryNSteps and optional screen-space cadence adaptation.
  • Envelope radius is computed from curvature grid when available.

Chunking and envelope status:

  • Current state: envelope-carrying segments are implemented (RadiusBound).
  • Planned / TODO: dedicated chunk system from Docs/spec_curved_ray_chunks.md is not yet materialized as separate runtime chunk types.

Source anchors:

  • RayBeamRenderer.cs
  • GrinFilmCamera.cs
  • Docs/spec_curved_ray_chunks.md

10) Scheduling and Concurrency

Current state work partition:

  • Frame is processed in row bands (RowsPerFrame and adaptive row sizing).
  • Pass-1: Parallel.For across pixels in current band.
  • Pass-2: sequential on main thread.

Current thread-safety strategy:

  • Snapshot is read-only during RenderStep.
  • Pass-1 writes per-pixel buffers (disjoint indices) and merges counters via Interlocked.
  • Re-entry guard prevents overlapping RenderStep invocations.

Current watchdogs and budgets:

  • UpdateEveryFrameBudgetMs, UpdateEveryFrameMaxRowsPerStep.
  • RenderStepMaxMs, RenderStepMaxPixelsPerFrame, RenderStepMaxSegmentsPerFrame.
  • Multiple guard exits for stuck/no-progress/no-hit/no-candidate bands.
  • SoftGate budgets and watchdog (Pass2SoftGate* config set).

Planned / TODO:

  • RendererCore/Scheduler is currently empty; task-graph scheduler doc exists but is not the runtime backbone yet.

Source anchors:

  • GrinFilmCamera.cs
  • RenderBackends/LegacyBackend.cs
  • RendererCore/Scheduler/
  • Docs/spec_scheduler_task_graph.md

12) Telemetry, Debugging, and Validation

Current telemetry:

  • XPrimeRay.Perf.FramePerf + PerfScope stage timing/counters.
  • PerfStats rolling-window frame summaries and invariant checks.
  • Frame/band render-health logging in GrinFilmCamera.

Current debugging and validation helpers:

  • FieldProbe3D evaluates FieldSystem.AccelAt against current snapshot bus state and draws overlay diagnostics.
  • Geometry prune audit and reject sampling instrumentation in pass-2.
  • FieldSource3D in-game debug shape rendering.
  • RayBeamRenderer debug overlay + GetDebugRayBundle handoff.
  • RayViz and CurvedCamera are auxiliary debug/visual tools.

Source anchors:

  • PerfScope.cs
  • PerfStats.cs
  • GrinFilmCamera.cs
  • FieldProbe3D.cs
  • FieldSource3D.cs
  • RayBeamRenderer.cs
  • RayViz.cs
  • CurvedCamera.cs

14) Relativistic Optics, Metrics, and Wormholes

Goal: make the engine academically credible for gravitational optics by defining a metric-first path for null geodesics, while retaining the existing GRIN/field pipeline as a practical/artist-friendly control layer.

14.1 Key Principle: “Euclidean scene, non‑Euclidean light”

  • Geometry/colliders can remain standard Euclidean meshes (for gameplay + authoring).
  • The light transport is governed by an effective spacetime / optical metric that bends rays (null curves) through the same Euclidean world positions.
  • This matches how most production GR lensing renderers work: they integrate geodesics in a chosen coordinate chart and sample scene content along the ray.

14.2 Physics alignment levels (Research Mode tiers)

Tier 0 (Current, “GRIN-Field”): - Rays bend under a configurable field rule (beta/gamma, integrated acceleration, step adapt). Good for art, intuition, and controllable DOEs.

Tier 1 (Optical Metric / Gordon Metric): - Interpret curvature field as a spatially varying refractive index and/or moving medium (Gordon metric). - Required: a canonical conversion contract: (field params) → (n(x), v(x)) → effective metric g_eff(x).

Tier 2 (Full GR Metric): - Integrate null geodesics from explicit g_{μν}(x) (Schwarzschild, Kerr, weak-field PN, custom numerically defined metrics). - Required: Christoffel symbols Γ^μ_{αβ}(x) and a null-constraint enforcement strategy.

Tier 3 (Exotic / Wormhole Metrics): - Implement a small library of wormhole metrics (e.g., Morris–Thorne-style spherically symmetric static wormhole) as coordinate charts. - Rendering does not require non-Euclidean meshes; it requires: - a coordinate mapping / chart definition, - geodesic integration through that chart, - and sampling content from one or more “regions” (mouth A / mouth B) via mapping.

14.3 Integrators: “PHD level” method inventory (engine should expose them)

Engine should provide a unified integrator interface with these options: - Fixed-step explicit integrators: Euler (debug), Midpoint, RK2, RK4. - Adaptive embedded Runge–Kutta: RKF45 / Dormand–Prince RK45 (error estimate + dt control). - Symplectic / geometric integrators (where applicable): Verlet / Stormer–Verlet, implicit midpoint (energy behavior). - Geodesic-specific forms: - Hamiltonian formulation for null geodesics (canonical momenta p_μ; integrate Hamilton’s equations). - First integrals for common metrics (Schwarzschild/Kerr constants of motion) to reduce drift. - Constraint handling: - null constraint g_{μν} u^μ u^ν = 0 enforced via projection, renormalization, or constrained integrator step.

Deliverable target: - A single “RayIntegrator” contract with: State, Step(dt), ErrorEstimate(dt), and optional ConstraintProject(). - Current “StepPolicy” becomes one implementation; GR integrators become additional implementations.

14.4 Wormhole modeling (what we need to add)

You do not need “non-Cartesian scene meshes.” You need non-trivial coordinate mapping and metric definitions: - Metric: pick a wormhole line element (static spherically symmetric is easiest). - Charts/Regions: define mouth A and mouth B as separate coordinate patches (or a single patch with mapping). - Ray transport: integrate geodesics through the metric; when the ray crosses the throat, map its coordinates to the other region. - Sampling: query fields/geometry in the appropriate region’s scene snapshot or via portal mapping.

Proposed engine abstraction: - IMetricField (returns g_{μν} and optionally Γ or ∂g). - IChartMap (maps between Euclidean world (x,y,z,t) and chart coordinates; supports portal crossings). - IRaySampler (samples scene content along a ray, including “which region” rules).

14.5 Twistor/spinor note (position in the roadmap)

  • Twistors/spinors can be treated as an alternative representation of rays and null directions (especially useful for Kerr and conformal structures).
  • They are not strictly required to render GR lensing, but they can improve stability/efficiency and connect to conformal compactifications (Penrose-style).
  • Roadmap: add a “representation layer” where a ray may be stored as (x^μ, p_μ) Hamiltonian state or a spinor/twistor state, while preserving the same integrator/sampler interfaces above.

15) Research Mode Toggle (spec)

Purpose: allow switching between production/gameplay constraints and research/validation constraints without touching gameplay-facing defaults.

Required components: - ResearchModeConfig (authoritative toggle + policy) - Enabled - Preset (e.g., Off / Validate / PaperMatch / StressTest) - LoggingVerbosity - DeterminismMode (seeded RNG, disable random probes, fixed dt, etc.) - ResearchModeOverrides (override values for EffectiveConfig) - strong typing, explicit “OverrideX” bool flags - override groups: Film, Broadphase, RayMarch, SoftGate, Budgets, Debug

Integration point (code): - GrinFilmCamera.ResolveEffectiveConfig(out EffectiveConfig cfg) must call: - ResearchModeOverrides.Apply(ref cfg, ResearchModeConfig cfgResearch, sourceContext: "GrinFilmCamera") - Must log a one-line “ResearchMode active” banner when enabled, with a stable hash of the override set.

Validation behaviors to include: - Option to disable all stochastic choices (SoftGate randomness) for repeatable runs. - Option to run a “truth pass” (full overlap + no pruning) on a sampled subset for FP/FN estimates. - Option to dump ray states for a small set of pixels for offline comparison.

15) Research Mode Toggle Spec

Goal

Research Mode is a configuration + validation contract that makes xPRIMEray suitable for academic / PhD-level gravitational optics workflows:

  • explicit numeric tolerances (step size, error bounds)
  • invariant tracking knobs (e.g., null constraint drift in metric mode)
  • reproducibility controls (deterministic scheduling, fixed seeds)
  • a test harness that can be compared against published results

Public Configuration

The portable config types live in:

  • RendererCore/Config/ResearchModeConfig.cs
  • RendererCore/Config/ResearchModeOverrides.cs

In Godot, the camera exposes inspector-facing overrides under Research Mode, then merges them into EffectiveConfig.Research inside GrinFilmCamera.ResolveEffectiveConfig(...).

Tiers

  • Tier0_Preview: current behavior; heuristic stepping; performance first.
  • Tier1_ErrorBounded: declares per-ray tolerance goals; enforces dt bounds and work caps; prepares the integrator upgrade path to embedded error estimation (RK45) while remaining backwards compatible.
  • Tier2_InvariantPreserving: adds invariant tracking + (optional) constraint projection for metric transport; target mode for “academically comparable” claims.

Determinism Rules

When DeterministicMode=true:

  • disable probabilistic probes (SoftGate.RandomProbeChance = 0)
  • process work in deterministic order (band/row order)
  • avoid nondeterministic reductions for metrics and validation

Minimal Runtime Application (current code)

Today (pre-RK45), Research Mode already applies conservative constraints without re-architecting:

  • clamps marcher step length using DtMin/DtMax
  • caps StepsPerRay via MaxStepsPerRay
  • disables probabilistic probes in deterministic mode

These guardrails let us start building reproducible benchmark suites immediately, then swap in stronger integrators later.

Validation Harness (planned)

Research Mode supports a validation suite selector (quick sanity → full regression → metric benchmarks) with a structured report output. Benchmarks should include:

  • Flat-space straight-ray tests
  • GRIN lens regressions (known profiles)
  • Schwarzschild lensing and photon-sphere qualitative behavior
  • Kerr lensing spot checks
  • Wormhole throat continuity tests