Розробка кастомних шейдерів постобробки графіки

Наша компанія з розробки відеоігор веде незалежні проекти, спільно з клієнтом створює ігри та надає додаткові операційні послуги. Досвід нашої команди дозволяє нам охопити всі ігрові платформи та розробити приголомшливий продукт, що відповідає баченню клієнта та перевагам гравців.

Від імерсивних застосунків до ігрових світів і 3D-сцен

Наша виділена команда для VR/AR/MR-розробки, Unity-продакшну і 3D-моделювання та анімації — з власними кейсами і презентаціями.

Відвідати персоналізований сайт
Показано 1 з 1 послугУсі 242 послуг
Розробка кастомних шейдерів постобробки графіки
Складна
від 2 робочих днів до 2 тижнів
Часті питання

Наші компетенції

Які етапи розробки гри?

Останні роботи

  • image_games_mortal_motors_495_0.webp
    Розробка гри для компанії Mortal Motors
    683
  • image_games_a_turnbased_strategy_game_set_in_a_fantasy_setting_with_fire_and_sword_603_0.webp
    Покрокова стратегія у фентезі сеттингу With Fire And Sword
    862
  • image_games_second_team_604_0.webp
    Розробка ігри для компанії Second term
    491
  • image_games_phoenix_ii_606_0.webp
    3D-анімація – тизер для гри phoenix 2.
    533

Розробка кастомних шейдерів постобробки графіки

Вбудовані Volume ефекти в URP та HDRP — Bloom, Color Grading, Vignette — закривають базові потреби, але як тільки потрібен нестандартний візуальний ефект (тепловий марево над асфальтом, хроматична аберація з кастомною кривою, pixel art posterization, outline detection по depth buffer) — починається територія кастомних Renderer Feature та повноекранних Blit Shader'ів.

У Unity 2022+ архітектура кастомного постпроцесу змінилася. Старий підхід через OnRenderImage та CommandBuffer.Blit застарів. Новий стандарт — ScriptableRendererFeature + ScriptableRenderPass з Blitter.BlitCameraTexture.

Як влаштований ScriptableRendererFeature в URP

ScriptableRendererFeature — це точка входу для додавання кастомного render pass в URP pipeline. Він реєструє ScriptableRenderPass, який виконується в заданому RenderPassEvent (BeforeRenderingPostProcessing, AfterRenderingPostProcessing тощо).

Усередині ScriptableRenderPass.Execute() правильний паттерн у Unity 6 / URP 17:

Blitter.BlitCameraTexture(cmd, source, destination, material, passIndex);

Це замінює старий cmd.Blit(src, dst, mat). Різниця не тільки синтаксична: Blitter.BlitCameraTexture правильно обробляє VR single-pass instanced rendering та уникає UV flip артефактів у WebGL.

Матеріал для Blit використовує Full Screen Shader Graph (тип графа Fullscreen Shader в URP ShaderGraph). У ньому доступна URP Sample Buffer нода — вона читає Color, Depth, Normal або Motion Vectors з G-Buffer. Це ключове: без цієї ноди неможливо зробити глибиноорієнтовані ефекти (outline по depth, custom depth of field) через ShaderGraph без написання HLSL.

Outline по Depth та Normal

Outline detection — частий запит для стилізованих ігор. Наївний підхід: обводка через другий pass з збільшеними вершинами — працює для solid об'єктів, ламається на складній геометрії та не дає outline по силуету сцени.

Правильний підхід — повноекранний edge detection через Depth та Normal buffers:

Depth-based edge: читаємо глибину в поточному пікселі та сусідніх (4 або 8 сусідів через Sample Texture 2D з offset). Якщо різниця глибини перевищує поріг — піксель на краю. Roberts Cross або Sobel operator — стандартні фільтри. У ShaderGraph: чотири Sample Texture ноди з ручними UV offset'ами (+1/-1 піксель через Texel Size ноду), обчислюємо gradient magnitude.

Normal-based edge: аналогічно по Normal buffer. Дає лінії там, де геометрія резко змінює напрямок нормалі — це ребра та складки поверхні, які depth edge не видить. Комбінація depth + normal edge — стандарт для cel-shading outline.

Проблема depth outline: глибина в буфері не лінійна, вона записана в logarithmic або reversed-Z форматі залежно від платформи. Пряме порівняння depth значень без linearization дає нерівномірну товщину лінії. Потрібно лінеаризувати через LinearEyeDepth(depth, _ZBufferParams) — у ShaderGraph це Linear Eye Depth нода.

Тепловий марево та distortion ефекти

Screen-space distortion для heatwave або magic portal: Blit шейдер, який зміщує UV поточного кадру по Normal map (flowing animated normal texture). Проста ідея, але в ній приховується проблема з render order.

Distortion шейдер повинен працювати з Opaque Texture (снімком екрана до прозорих об'єктів). У URP це _CameraOpaqueTexture. Якщо ефект застосовується як повноекранний pass — він видить весь екран. Якщо потрібен локалізований distortion (тільки над конкретним об'єктом, наприклад гарячим асфальтом) — потрібна Distortion Renderer Feature, яка рендерить distortion objects в окремий render texture, потім застосовує його як screen-space mask у фінальному Blit.

Для HDRP distortion — вбудований Distortion render queue (окремий від Transparent). Об'єкти з Distortion enabled автоматично потрапляють в distortion accumulation pass. Це простіше, ніж URP кастомний підхід.

Типичні помилки при розробці кастомних постефектів

Wrong RenderPassEvent. Постефект поставлений в BeforeRenderingPostProcessing — але повинен бути після Bloom, інакше Bloom застосовується поверх кастомного ефекту. Порядок подій в URP: Opaques → Skybox → Transparents → Post Processing → UI. Вибір RenderPassEvent визначає, де в цій черзі станеме кастомний pass.

Відсутність Depth Priming Mode. На деяких мобільних GPU (особливо Mali) глибинний буфер може бути недоступний при читанні в кастомному pass, якщо Depth Priming Mode в URP Renderer настроєна на Auto замість Forced. Це призводить до чорного екрана або некоректних значень глибини без будь-яких помилок в консолі.

VR incompatibility. Кастомний шейдер постобробки, написаний без підтримки XR, ламається в VR — відрисовується тільки для одного ока або створює double-vision артефакт. Blitter.BlitCameraTexture автоматично обробляє це, але Custom Function ноди з ручним UV розрахунком вимагають UNITY_STEREO_EYE_INDEX_POST_VERTEX macro.

Тип постефекту Строк
Простий fullscreen ефект (колірна корекція, blur) 1–3 дні
Outline по depth/normal + настройка 3–5 днів
Distortion ефект (heatwave, portal) 3–6 днів
Складний складений ефект (кілька passes) 1–2 тижні

Вартість розраховується індивідуально. Потрібно знати рендер-пайплайн, платформу та наявність VR підтримки.