PixelTrace is not a rendering engine. It's a light simulation.
While traditional game engines and renderers use clever tricks to approximate what things look like, PixelTrace simulates how light actually behaves in the real world. This is the difference between painting a picture of reality and letting reality paint itself.
Most rendering engines use rasterization and a collection of hacks accumulated over decades:
| Technique | What It Fakes | The Problem |
|---|---|---|
| Shadow Maps | Shadows | Aliased edges, limited resolution, no soft shadows |
| Screen-Space Reflections | Reflections | Can't reflect objects outside the screen |
| Ambient Occlusion (SSAO) | Indirect shadows | Only approximates local occlusion |
| Light Probes | Global illumination | Static, pre-baked, doesn't react to changes |
| Reflection Probes | Environment reflections | Low resolution, parallax errors |
| Bloom | Light glow | Post-process effect, not real light scatter |
| Fake Subsurface Scattering | Light through skin | Shader trick, not actual light transport |
These tricks are fast, but they're fundamentally lies. They approximate what a human expects to see, not what physics dictates they would see.
PixelTrace uses Light Tracing (also called Photon Tracing) - a physically accurate simulation:
1. Light leaves the source (like a real photon)
2. Light travels through space
3. Light hits a surface
4. Light bounces (specular) or scatters (diffuse)
5. If the camera can see that illuminated point → pixel is colored
6. Repeat billions of times
This is exactly how your eyes work:
- You don't see objects. You see light that bounced off objects.
- PixelTrace simulates this directly.
Traditional ray tracing shoots rays from the camera into the scene. This is computationally efficient but backwards from reality.
In nature:
Sun → Surface → Surface → Surface → Eye
In traditional ray tracing:
Eye → Surface → Surface → Light (backwards!)
In PixelTrace:
Light → Surface → Surface → Camera (natural!)
By tracing light forward from sources, PixelTrace naturally captures phenomena that are extremely difficult to fake:
| Phenomenon | Traditional Engines | PixelTrace |
|---|---|---|
| Caustics (light focusing through glass) | Special case shaders | Emerges naturally |
| Color bleeding (light picks up surface color) | Fake with probes | Physically accurate |
| Soft shadows | Multiple shadow maps | Natural penumbra |
| Indirect illumination | Baked lightmaps | Real-time accurate |
| Multiple light bounces | Usually 1-2 max | Unlimited |
┌─────────────────────────────────────────────────────┐
│ Light Source │
│ (emits rays in all directions) │
└─────────────────────┬───────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────┐
│ Ray Tracing │
│ • Find intersection with scene geometry │
│ • Calculate surface properties │
│ • Determine energy transfer │
└─────────────────────┬───────────────────────────────┘
│
┌───────────┴───────────┐
▼ ▼
┌─────────────────┐ ┌─────────────────┐
│ Specular Bounce │ │ Diffuse Scatter │
│ (mirror reflect)│ │ (spread in │
│ │ │ hemisphere) │
└────────┬────────┘ └────────┬────────┘
│ │
└───────────┬───────────┘
│
▼
┌─────────────────────────────────────────────────────┐
│ Camera Visibility Test │
│ • Project hit point to screen coordinates │
│ • Check if camera can see the point │
│ • Check for occlusion │
└─────────────────────┬───────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────┐
│ ScreenStack │
│ (accumulates light contributions) │
└─────────────────────────────────────────────────────┘
- True Light Tracing: Light emanates from sources, not camera
- Spherical Light Emission: Configurable angular resolution
- Specular Reflection: Perfect mirror bounces
- Diffuse Scattering: Light spreads across surfaces realistically
- Energy Conservation: Light loses energy with each bounce
- Material System: Ambient, diffuse, specular, shininess properties
- JSON Scene Format: Easy to create and modify scenes
- Multi-bounce Illumination: Configurable bounce depth
| Feature | Unreal/Unity | Traditional Path Tracer | PixelTrace |
|---|---|---|---|
| Light direction | Camera→Scene | Camera→Light | Light→Camera |
| Real-time capable | Yes (with tricks) | No | Future goal |
| Physically accurate | No | Yes | Yes |
| Caustics | Fake/None | Difficult | Natural |
| Matches human vision | Approximation | Backwards | Exact model |
- Sphere primitive support
- Plane/ground support
- Multiple light sources
- Transparent materials (glass, water)
- Texture mapping
- Refraction (light bending through materials)
- Volumetric effects (fog, atmosphere)
- Area lights (soft shadows)
- Depth of field
- Motion blur
- GPU acceleration (CUDA/OpenCL)
- Real-time progressive rendering
- Spectral rendering (wavelength-accurate color)
- Polarization effects
- Fluorescence
"The goal is not to render images. The goal is to simulate reality and let images emerge."
Most engines ask: "How do I make this look right?"
PixelTrace asks: "How does light actually work?"
When you simulate physics correctly, correct images are the inevitable result. There are no edge cases to handle, no special shaders to write, no tricks to learn. Just physics.
This is the first step toward true visual simulation - rendering that works exactly like human vision, because it follows the same physical laws.
PixelTrace/
├── main.cpp # Application entry point
├── ScreenStack.h/cpp # Pixel buffer (virtual screen)
├── PixelTraceRenderer.h/cpp # Core light tracing engine
├── Scene.h/cpp # Scene loader (JSON)
├── Vec3.h # 3D vector mathematics
├── Ray.h # Light ray structure
├── HitResult.h # Intersection results
├── Intersect.h # Geometry intersection tests
├── CameraProjection.h # World-to-screen projection
├── Camera.h # Camera definition
├── Light.h # Light source definition
├── Material.h # Surface material properties
├── SceneObject.h # Scene object definition
└── scenes/
└── default_scene.json # Example scene
// Configure the renderer
PixelTraceRenderer renderer(screenStack);
renderer.SetAngleStep(0.1f); // Light ray density (smaller = more rays)
renderer.SetMaxBounces(3); // How many times light can bounce
// Load and render
renderer.LoadScene("scenes/default_scene.json");
renderer.Render();- CMake 3.16+
- GCC/G++ with C++17 support
- Make or Ninja
cmake -S . -B build
cmake --build build -j./build/PixelTraceBy default this renders PixelTrace/scenes/default_scene.json and writes a render.ppm image in the current working directory.
You can also pass custom paths:
./build/PixelTrace <scene.json> <output.ppm>- Linux (current path): the renderer writes a
.ppmfile. - Why PPM: it is intentionally simple and dependency-free, so output works reliably without adding extra image libraries.
- Windows: the Win32 entry point opens a real-time render window and displays pixels directly while rendering.
If needed, convert PPM to PNG after rendering:
convert render.ppm render.pngThis project is a proof-of-concept demonstrating physically-based light simulation.
"We don't see the world. We see the light that the world reflects into our eyes. PixelTrace simulates exactly that."