Шейдеры для тех, кто думал что это тени
Первый раз я услышал слово «шейдер» на девятом курсе и решил, что это какая-то надстройка над тенями. Оказалось, с точностью до наоборот: шейдер — это программа, которая решает, какого цвета будет пиксель. Тени, свет, отражения, вода, голограмма, тот самый лайм-эффект из Half-Life — всё это шейдеры. Просто разные.
Два вопроса, на которые отвечает любой шейдер
Любой шейдер в мире — от узловой сети в Blender до кода в Godot — отвечает на два вопроса:
- Где вершина? (vertex shader) — берёт точку модели и говорит, куда её спроецировать на экране. Сюда же летят вершинные цвета, нормали, UV.
- Какого цвета пиксель? (fragment/pixel shader) — вызывается для каждого пикселя отдельно и возвращает цвет, прозрачность, шероховатость.
Всё. Вся магия — это математика между этими двумя вызовами. Волна на воде — вершинный шейдер, который двигает вершины по синусу. Пульсирующая неоном вывеска — фрагментный, который меняет эмиссию по времени.
Узлы — это те же шейдеры, только без синтаксиса
В Blender я годами писал материалы через Shader Editor: Principled BSDF, Noise Texture, Mapping, ColorRamp. И не догадывался, что каждый клик мышкой — это строка GLSL/HLSL. Blender сам компилирует граф узлов в шейдер. Noise Texture — это не «картинка шума», это функция шума Перлина, посчитанная на лету для каждого пикселя.
Полезная проверка: если вы собирали в Blender материал с Musgrave или Noise и крутили Scale — вы уже программировали шейдер, просто переменные назывались ползунками.
Где шейдеры ломают мозг новичка
- Думают, что шейдер «применяется к объекту». Нет: шейдер выполняется для каждого пикселя, 60-144 раза в секунду. Поэтому тяжёлые математические навороты в фрагментном шейдере съедают FPS быстрее, чем лишние полигоны.
- Путают материал и шейдер. Материал — это данные (текстуры, параметры). Шейдер — код, который эти данные переваривает. Principled BSDF — один шейдер, тысяча материалов.
- Боятся кода зря. В Godot шейдерный язык — тот же GLSL, штук 20 строк на простой эффект. Вот весь скрин-шейдер, который я написал за вечер:
shader_type canvas_item;
void fragment() {
COLOR = texture(TEXTURE, UV);
COLOR.a *= step(0.5, fract(UV.y * 4.0 + TIME));
}
Четыре строки, и интерфейс мигает как старый монитор.
С чего начать, если интересно
Откройте Shader Editor в Blender, воткните ColorRamp между Noise и Base Color, покрутите Mapping Location. Измените одно число — посмотрите, что стало с картинкой. Это и есть обучение шейдерам: не зубрёжка синтаксиса, а понимание, что пиксель — это результат функции, а не заклинание.
Как только это щёлкнет, половина «магии» из туториалов станет очевидной механикой. Второй половины касаться рано — сначала первая.
Комментарии (0)
Форма для гостей комментариев пока не принимается — писать можно автору (expeot@outlook.com) или через владельца блога. Все записи выше настоящие, никто их не модерирует молча.