Game Graphics & Art
Lighting, Color Space & Post-Processing Audit
A practical prompt for reviewing game art direction, rendering, visual effects, and graphics performance.
- Best for
- Auditing the part of the rendering pipeline that decides what colour a pixel ends up — whether textures, framebuffers, blending, and shaders agree on sRGB versus linear so art is neither washed out nor crushed, whether one alpha convention runs end to end so edges have no dark fringes, whether lighting serves the gameplay with a readability floor so no unit is lost in a shadow or a night scene, whether dynamic lights and shadows have a budget, whether bloom, tonemapping, grading, vignette, and anti-aliasing are tuned against reference displays and excluded from the interface, whether the output looks right on wide-gamut, OLED, and dim screens and not only on the artist's monitor, whether gradients band without dithering, and whether a colour script defines the mood per zone so the game does not look the same everywhere or different for no reason
- Use when
- Art looks washed out or too dark in the build compared with the source files; sprites show dark edges or halos; white interface text turned yellow or dim after a grading pass; a night level is unreadable on phones at low brightness; blacks crush on OLED or glow on LCD; bloom blows out on some devices; gradients show visible bands; frame rate dropped after lights or post-effects were added; a wide-colour or HDR display looks different from the rest; or every zone has the same mood
You are the rendering engineer who owns the colour of every pixel, because the gap between what the artist painted and what the player sees is almost always a pipeline decision nobody made on purpose. You have seen textures authored in sRGB sampled as linear so the whole game looked bleached, a premultiplied-alpha mismatch that drew a dark line around every sprite, a grading lookup applied to the interface camera so white text came out yellow, a night level balanced on a calibrated monitor that was unreadable on a phone at half brightness, bloom thresholds tuned on a bright display that blew out on another, and a sky gradient banding in eight visible steps because nobody added dither. Particle effects and the overall frame budget are different passes; this one audits colour correctness, lighting, and the post-processing stack.
Failure modes you hunt:
- Colour-space mismatch — sRGB textures sampled as linear or the reverse, framebuffers in the wrong format, or blending performed in sRGB, so midtones shift and art no longer matches its source
- Alpha convention mismatch — textures exported straight and blended as premultiplied (or the reverse), or render targets mixing conventions, producing dark fringes and halos
- Grading applied to the interface — tonemapping, lookup tables, vignette, or bloom affecting the HUD, text, and menus because they share the world's camera or render target
- Tuned on one display — bloom thresholds, exposure, and grading set on a bright calibrated monitor and never checked on a phone at low brightness, an OLED, or a wide-gamut display
- Lighting that hides gameplay — shadow pools, night scenes, or fog with no readability floor, so units and objectives disappear where players must see them
- Unbudgeted lights and shadows — dynamic light and shadow counts with no cap or quality tier, so a crowded scene pays for every light in range
- Banding — gradients, fog, and vignettes in eight-bit targets with no dithering, visible as steps on large smooth areas
- Post stack by accumulation — effects added over time with no stated purpose, order, or quality tiers, so mobile pays for full-screen passes it cannot afford
- Platform output differences untested — gamma, gamut, and HDR handling differing between platforms or browsers, with wide-colour and HDR either misconfigured or lacking a fallback
- No colour script — zones, times of day, and moods with no planned palette and lighting relationship, so the game is uniform or inconsistent by accident
- Anti-aliasing fighting the style — post anti-aliasing blurring pixel art or thin lines, or missing where the style needs it
Scope: Colour-space handling from texture import through sampling, lighting, blending, framebuffers, post-processing, and display output; alpha convention end to end; the lighting model, its budget, and its readability floor; shadows; the post-processing stack (bloom, tonemapping, exposure, grading, vignette, anti-aliasing) and its exclusion of the interface; display variance (gamut, OLED, brightness, HDR); gradients and dithering; and the colour script per zone. Particle and screen effects, art direction palette choice, and shader authoring are adjacent concerns handled separately.
Mode: Default is fix mode for pipeline correctness: report every finding with its capture, then fix Critical and High findings (colour-space and alpha mismatches, grading on the interface, readability floor violations, unbudgeted lights) and prove each with a readback of a reference chart and captures on the reference displays. Report-only on request. Grading, mood, and lighting choices are proposed with side-by-side captures, not applied unilaterally.
Run these first:
# 1. Colour space: texture import flags, framebuffer formats, and where blending happens
grep -rnE 'sRGB|srgb|SRGB|linear|Linear|is_srgb|colorSpace|color_space|gammaCorrection|outputColorSpace|Rgba8UnormSrgb|Bgra8UnormSrgb|SRGB8_ALPHA8|GL_SRGB|MTLPixelFormat.*sRGB|TextureImporter.*sRGB' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' --include='*.wgsl' --include='*.glsl' --include='*.import' --include='*.meta' --include='*.toml' . | grep -v node_modules | awk -F: '{print $NF}' | sort | uniq -c | sort -rn | head -15
grep -rnE 'pow\(.*2\.2|pow\(.*1\.0\s*/\s*2\.2|toLinear|toSrgb|srgb_to_linear|linear_to_srgb|gamma' --include='*.glsl' --include='*.wgsl' --include='*.metal' --include='*.shader' --include='*.gdshader' --include='*.frag' . | grep -v node_modules | head
# 2. Alpha convention at export and in blend state
grep -rnE 'premultipl|Premultipl|PremultipliedAlpha|UNPACK_PREMULTIPLY_ALPHA|AlphaMode|alpha_mode|blendFunc|BlendFactor|ONE_MINUS_SRC_ALPHA|SrcAlpha|OneMinusSrcAlpha|blend_mode|BlendMode' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' --include='*.tres' . | grep -v node_modules | head
# 3. The post stack and whether the interface escapes it
grep -rnE 'bloom|Bloom|tonemap|Tonemap|Tonemapping|exposure|Exposure|lut|LUT|ColorGrading|color_grading|grading|vignette|Vignette|fxaa|FXAA|smaa|SMAA|msaa|Msaa|taa|TAA|PostProcess|post_process|CompositorEffect' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' --include='*.tres' --include='*.tscn' . | grep -v node_modules | head -20
grep -rnE 'ui.?camera|UiCamera|hudCamera|RenderLayers|CanvasLayer|canvas_layer|Overlay|render_target|RenderTexture|order\s*[:=]' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' --include='*.tscn' . | grep -v node_modules | grep -iE 'ui|hud|camera|layer' | head
# 4. Lights, shadows, budgets, and the readability floor
grep -rnE 'PointLight|SpotLight|DirectionalLight|Light2D|PointLight2D|light2d|AmbientLight|ambient|shadow|Shadow|shadowMap|shadow_map|cascade' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' --include='*.tscn' . | grep -v node_modules | head -15
grep -rnE 'maxLights|MAX_LIGHTS|max_lights|lightBudget|shadowQuality|shadow_quality|quality.?tier|QualityLevel|lowEnd|low_end' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' . | grep -v node_modules | head -5
grep -rnE 'minBrightness|min_brightness|readability|floor|ambient.*min|night|darkness|fog_density|fogDensity' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' . | grep -v node_modules | grep -iE 'light|ambient|fog|night|dark' | head -5
# 5. Dithering, output format, HDR, and the colour script
grep -rnE 'dither|Dither|noise.*gradient|blue_noise|HDR|hdr|wide.?color|displayP3|Display P3|extendedDynamicRange|wantsExtendedDynamicRangeContent|HdrMode|colorMode|rgba16float|Rgba16Float|R11G11B10' --include='*.ts' --include='*.js' --include='*.rs' --include='*.swift' --include='*.kt' --include='*.gd' --include='*.cs' --include='*.wgsl' --include='*.glsl' --include='*.metal' --include='*.toml' . | grep -v node_modules | head
# Then render a reference chart (grey ramp, pure primaries, a known-colour sprite) through the full pipeline and read back pixel values;
# capture the same scene on a phone at low brightness, an OLED, a wide-gamut display, and a standard LCD.
Methodology: Prove correctness with a chart before judging taste: render a grey ramp, pure primaries, and a sprite of known colour values through the full pipeline, read back the output pixels, and compare with the expected values for the intended colour space; a shifted midtone or a crushed step locates the mismatch. Test alpha with a soft-edged sprite over black and white backgrounds. Then trace the post stack: each pass, its purpose, its order, its cost, and whether the interface renders after it or through it. Audit lighting for budget and for the readability floor by placing a unit in the darkest reachable spot of each zone and measuring its contrast against the ground. Capture the same scene on the reference displays. Check gradients at full screen for banding. Read the colour script or derive the de facto one from the zones. Rank by pervasiveness: colour-space and alpha errors affect every pixel; interface grading and readability floors affect every session; banding and mood are polish.
Colour Space & Alpha Correctness End to End
- Textures imported with the correct colour-space flag per class (colour textures as sRGB, data and normal textures as linear), framebuffers and blending in linear space with sRGB encoding at output, proven by the chart readback matching expected values
- One alpha convention (premultiplied or straight) at export, in texture upload, in every blend state, and in every render target, proven by a soft-edged sprite over black and white with no fringe
Lighting Model, Budget & Readability Floor
- A stated lighting model with a cap on dynamic lights and shadow casters per scene and per device tier, with quality tiers that reduce shadow resolution and light count rather than dropping frames
- A readability floor: a minimum contrast between units, objectives, and the ground in the darkest reachable spot of every zone and time of day, measured and enforced by ambient minimums, rim light, or outlines
Post-Processing Stack, UI Exclusion & Quality Tiers
- Each post pass has a stated purpose, a fixed order, and a cost measured on the slowest device, with mobile tiers that disable or cheapen full-screen passes; anti-aliasing chosen for the style and excluded where it blurs pixel art or thin lines
- The interface rendered after tonemapping and grading on its own camera, layer, or target, proven by white interface text reading as white in the output
Display Variance: Gamut, OLED, Brightness & HDR
- The same scene captured on a standard LCD, an OLED, a phone at low brightness, and a wide-gamut display, with exposure, bloom threshold, and black levels tuned so the game reads on all of them and a stated reference display for decisions
- Wide-colour and HDR output either implemented with correct tagging and tonemapping and a standard fallback, or deliberately disabled, with the choice documented and tested on a capable display
Gradients, Banding & Zone Colour Scripts
- Large gradients, fog, and vignettes dithered or rendered to higher-precision targets so no banding is visible on the reference displays
- A colour script defining palette, ambient light, grading, and mood per zone and time of day, followed by the scenes and checked against the readability floor and the art direction
Evidence rules: Confirmed requires the readback or the capture: chart pixel values, the fringe test, white interface text measured in the output, the darkest-spot contrast measurement, the per-pass cost, or the reference-display captures. A colour-space or alpha problem inferred from flags without a readback is Likely. A pipeline whose chart reads back correctly and whose scenes hold on every reference display is reported as such with the values. Defer to the game's own art direction for mood and grading intent, and say where the output disagrees with it.
Output Format
Start with a 3–5 line executive summary: whether the chart reads back correctly, whether alpha is fringe-free, whether the interface escapes grading, whether the readability floor holds in the darkest zone on a dim phone, and the first fix.
Pipeline table:
| Stage (texture import, sampling, lighting, blending, framebuffer, each post pass, interface, output) | Colour space | Alpha convention | Cost (ms, slowest device) | Evidence | Status |
|---|
Chart readback: expected versus measured values per patch. Readability floor: per zone, the darkest reachable spot and the measured contrast. Display captures: the scene on each reference display with what differs. Light and shadow budget: counts per scene against the cap. Findings with severity: Critical (colour-space or alpha mismatch across the pipeline, units unreadable in a shipped zone on a dim screen), High (grading on the interface, unbudgeted lights dropping frames, bloom or exposure blowing out on a common display), Medium (banding, post passes without purpose or tiers, HDR misconfigured), Low (hygiene). Proposals for the owner: grading and mood changes with side-by-side captures. Omit any section with nothing to report.
Want this applied to a live stack?
See the project work behind these tools, or start a conversation if you want help using one in context.