Skip to main content

Overview

Atlas provides a comprehensive post-processing system with render targets and chainable effects.

Render Targets

Render targets capture scene output to textures for post-processing:
#include "atlas/texture.h"

// Create scene render target
RenderTarget renderTarget(window, RenderTargetType::Scene, 1024);

// Add to window rendering pipeline
window.addRenderTarget(&renderTarget);

// Display the render target
renderTarget.display(window, -1.0f);

Render Target Types

Scene
RenderTargetType
Standard scene rendering with color and depth
Multisampled
RenderTargetType
MSAA render target for anti-aliasing
Shadow
RenderTargetType
Shadow map rendering (depth only)
CubeShadow
RenderTargetType
Omnidirectional shadow cubemap
GBuffer
RenderTargetType
Deferred rendering geometry buffer
SSAO
RenderTargetType
Screen-space ambient occlusion
SSAOBlur
RenderTargetType
Blurred SSAO for smoothing

Post-Processing Effects

Add effects to render targets for screen-space processing:
#include "atlas/effect.h"

// Create render target
RenderTarget renderTarget(window);

// Add effects (applied in order)
renderTarget.addEffect(Blur::create(16.0f));
renderTarget.addEffect(ColorCorrection::create(params));
renderTarget.addEffect(Grayscale::create());

Available Effects

Inversion

Inverts all colors:
auto invert = Inversion::create();
renderTarget.addEffect(invert);

Grayscale

Converts to grayscale using luminance:
auto grayscale = Grayscale::create();
renderTarget.addEffect(grayscale);

Sharpen

Enhances edges and details:
auto sharpen = Sharpen::create();
renderTarget.addEffect(sharpen);

Blur

Gaussian blur with configurable radius:
auto blur = Blur::create(16.0f);  // Radius in pixels
renderTarget.addEffect(blur);
magnitude
float
default:"16.0f"
Blur radius in pixels (higher = stronger blur)

Edge Detection

Detects and highlights edges:
auto edgeDetect = EdgeDetection::create();
renderTarget.addEffect(edgeDetect);

Color Correction

Comprehensive color grading:
ColorCorrectionParameters params;
params.exposure = 0.5f;      // Brighten
params.contrast = 1.2f;      // Increase contrast
params.saturation = 1.1f;    // Boost saturation
params.gamma = 1.0f;         // Gamma correction
params.temperature = 0.1f;   // Add warmth (red)
params.tint = 0.0f;          // Green/magenta tint

auto colorCorrection = ColorCorrection::create(params);
renderTarget.addEffect(colorCorrection);
exposure
float
default:"0.0f"
Exposure adjustment (positive = brighter, negative = darker)
contrast
float
default:"1.0f"
Contrast multiplier (> 1.0 increases, < 1.0 decreases)
saturation
float
default:"1.0f"
Saturation level (0.0 = grayscale, 1.0 = normal, > 1.0 = oversaturated)
gamma
float
default:"1.0f"
Gamma correction value (typically 1.0 to 2.2)
temperature
float
default:"0.0f"
Color temperature (positive = warmer/red, negative = cooler/blue)
tint
float
default:"0.0f"
Tint adjustment (positive = green, negative = magenta)

Motion Blur

Simulates camera motion:
MotionBlurParameters params;
params.size = 12;          // Sample count
params.separation = 1.5f;  // Velocity scaling

auto motionBlur = MotionBlur::create(params);
renderTarget.addEffect(motionBlur);
size
int
default:"8"
Number of samples along motion vector
separation
float
default:"1.0f"
Scaling factor for velocity vector

Chromatic Aberration

Separates color channels for lens distortion:
ChromaticAberrationParameters params;
params.red = 0.01f;
params.green = 0.006f;
params.blue = -0.006f;
params.direction = {1.0f, 0.0f};  // Radial direction

auto chromaticAberration = ChromaticAberration::create(params);
renderTarget.addEffect(chromaticAberration);
red
float
default:"0.01f"
Red channel offset strength
green
float
default:"0.006f"
Green channel offset strength
blue
float
default:"-0.006f"
Blue channel offset strength
direction
Magnitude2d
Direction toward which channels shift

Posterization

Reduces color palette for stylized look:
PosterizationParameters params;
params.levels = 5.0f;  // Number of color levels

auto posterization = Posterization::create(params);
renderTarget.addEffect(posterization);
levels
float
default:"5.0f"
Number of discrete color levels to preserve

Pixelation

Retro-style large pixel blocks:
PixelationParameters params;
params.pixelSize = 5;  // Block size in pixels

auto pixelation = Pixelation::create(params);
renderTarget.addEffect(pixelation);
pixelSize
int
default:"5"
Size of pixelated blocks in screen pixels

Dilation

Expands bright regions for glow/bloom:
DilationParameters params;
params.size = 5.0f;      // Sample radius
params.separation = 2.0f; // Sample distance

auto dilation = Dilation::create(params);
renderTarget.addEffect(dilation);
size
int
default:"5"
Radius in pixels for neighbor sampling
separation
float
default:"2.0f"
Distance multiplier for sample stepping

Film Grain

Adds animated noise for cinematic feel:
FilmGrainParameters params;
params.amount = 0.1f;  // Noise intensity

auto filmGrain = FilmGrain::create(params);
renderTarget.addEffect(filmGrain);
amount
float
default:"0.1f"
Intensity of noise pattern (0.0 = none, 1.0 = maximum)

Bloom

Atlas includes a specialized bloom system:
// Configure environment bloom
Environment env;
env.lightBloom.radius = 0.008f;  // Bloom spread
env.lightBloom.maxSamples = 5;   // Quality (mip levels)
scene.setEnvironment(env);
Bloom is handled by BloomRenderTarget internally:
BloomRenderTarget bloomRT;
bloomRT.init(1920, 1080, 5);  // Width, height, chain length
bloomRT.renderBloomTexture(brightTexture, 0.008f, commandBuffer);
unsigned int bloomResult = bloomRT.getBloomTexture();

Render Target Textures

Access internal textures for custom processing:
RenderTarget renderTarget(window, RenderTargetType::Scene);

// Main color output
Texture colorTexture = renderTarget.texture;

// Bright areas (for bloom)
Texture brightTexture = renderTarget.brightTexture;

// Depth buffer
Texture depthTexture = renderTarget.depthTexture;

// Blurred version
Texture blurredTexture = renderTarget.blurredTexture;

// For deferred rendering
Texture gPosition = renderTarget.gPosition;    // World-space positions
Texture gNormal = renderTarget.gNormal;        // Normals
Texture gAlbedoSpec = renderTarget.gAlbedoSpec; // Albedo + Specular
Texture gMaterial = renderTarget.gMaterial;    // Material properties

Multisampling (MSAA)

Enable anti-aliasing with multisampled render targets:
RenderTarget msTarget(window, RenderTargetType::Multisampled);

// MSAA textures
Texture msTexture = msTarget.msTexture;           // Color (4x)
Texture msDepthTexture = msTarget.msDepthTexture; // Depth (4x)
Texture msBrightTexture = msTarget.msBrightTexture; // Bright (4x)

// Resolve to regular texture
msTarget.resolve();
Or configure window-wide MSAA:
Window window({
    .title = "MSAA Demo",
    .width = 1920,
    .height = 1080,
    .multisampling = true  // Enable 4x MSAA
});

Screen Space Reflections (SSR)

Enable real-time reflections:
window.enableSSR(true);
Access SSR texture:
Texture ssrTexture = renderTarget.ssrTexture;

Complete Example

class MainScene : public Scene {
    RenderTarget frameBuffer;

public:
    void initialize(Window &window) override {
        // Create render target
        frameBuffer = RenderTarget(window, RenderTargetType::Scene);
        window.addRenderTarget(&frameBuffer);
        frameBuffer.display(window);

        // Add post-processing effects
        ColorCorrectionParameters ccParams;
        ccParams.exposure = 0.3f;
        ccParams.contrast = 1.1f;
        ccParams.saturation = 1.05f;
        frameBuffer.addEffect(ColorCorrection::create(ccParams));

        // Add subtle film grain
        FilmGrainParameters grainParams;
        grainParams.amount = 0.05f;
        frameBuffer.addEffect(FilmGrain::create(grainParams));

        // Configure bloom
        Environment env;
        env.lightBloom.radius = 0.008f;
        env.lightBloom.maxSamples = 5;
        this->setEnvironment(env);

        // Enable SSR
        window.enableSSR(true);
    }
};

Environment Effects

Configure global rendering effects:
Environment env;

// Fog
env.fog.intensity = 0.5f;
env.fog.color = Color(0.7f, 0.7f, 0.8f, 1.0f);

// Volumetric lighting
env.volumetricLighting.enabled = true;

// Bloom
env.lightBloom.radius = 0.008f;
env.lightBloom.maxSamples = 5;

scene.setEnvironment(env);

Performance Considerations

Effect Order

Apply effects in order of cost. Cheap effects (color correction) first, expensive effects (blur) last.

Resolution

Lower render target resolution for better performance:
RenderTarget rt(window, RenderTargetType::Scene, 512);  // 512x512

Effect Chaining

Each effect adds a full-screen pass. Limit to 3-5 effects for optimal performance.

Best Practices

Apply color correction before other effects to work with properly exposed images.
Use small bloom radius values (0.005 - 0.01) for subtle, realistic glow.
Keep grain amount low (0.05 - 0.15) to avoid overwhelming the image.
Use pixelation sparingly for retro effects or transitions.
Use MSAA (4x) for good quality with minimal performance cost. Avoid SSAA unless targeting high-end hardware.

See Also

Build docs developers (and LLMs) love