2015-10-26 3 views
0

Ive закодированные тонны шейдеров, но Ive споткнулся во что-то, чего я никогда раньше не осознавал.ближние/дальние плоскости и z в орфографической растеризации

Мне нужен вершинный + фрагментарный шейдер с простой орфографической проекцией без проверки глубины.

Камера выровнена по Z с началом координат.

Я отключил GL_DEPTH_TEST и замаскировал записи глубины. Это было так просто, что я решил, что мне даже не нужна проекционная матрица. В моем полном невежестве и изобретательности я думал, что для любой вершины треугольника вершинный шейдер просто передаст x, y (, z = <whatever>, w = 1) в шейдер фрагмента.

Я действительно думал, что для фрагментарного шейдера просто нужны координаты x, y, потому что, поскольку мы говорим о орфографической проекции, w = 1 (без разделения перспективы), а так как буфер глубины бесполезен, а запись глубины отключена, z может буквально быть ничего, не имеет значения.

Конечно, я был неправ. Я быстро обнаружил, что компонент z довольно используется растеризатором, infact, у меня есть тонны треугольников, которые просто не растрируются.

Я также обнаружил, что настройка z-компонента резко изменит отображаемые треугольники. Поэтому я внедрил регулярную матрицу ортографических проекций и, конечно, решил проблему, теперь все правильно растрировано.

Теперь, из чистого любопытства, я начал играть с матрицей ортографических проекций и посмотреть, что действительно создано для разных входных векторов, с разными значениями для ближних и дальних обрезных плоскостей, и я действительно не могу понять. Хорошо, x, y и w все, как ожидалось, но я получаю совершенно разные значения z, основанные на моих плоскостях ближнего/дальнего клипа.

Вопрос: шейдер фрагмента не знает ничего о плоскостях клипов и матрицах проекций, он просто получает кучу x, y, z, w ... Какова роль компонента z в процессе растрирования? как он знает, что-то внутри просмотра или нет?

Я имею в виду, что для любой заданной ближней/дальней плоскости в матрице орфографических проекций я получаю значения z, которые действительны для данной матрицы проекций, и недопустимы для других. Поскольку шейдер фрагмента не имеет способа узнать, какие плоскости были использованы в матрице, как он может отбрасывать фрагменты? Существует ли связь между каждой вершиной того же примитива?

PS: Я знаю, что шейдер фрагмента даже не вызывается, поскольку я устанавливаю SSBO + Atomic Counter и проверял оба значения без изменений.

+3

Растеризация, выполняемая до этапа фрагмента шейдеров - это на самом деле то, что генерирует фрагменты. Znear/Zfar выравнивает ваши значения min/max в соответствии с z = 1 и z = -1 в пространстве клипа. Просто создайте клип, который не подходит в единичном кубе (в пространстве клипа - после проецирования и разделения перспективы), и все в порядке. – keltar

+0

Какова ваша итоговая матрица? Почему ваш Zfar больше, чем Znear? Ось Z от глубины до камеры в opengl.Быстрый расчет на бумаге дает мне ~ 0.7317 для z = 300 и задан znear/zfar (конечно, инвертирован). – keltar

+0

вы правы. Я удалил свой предыдущий пример, я пересчитал все, и у меня была ошибка знака .. вы правы ... он просто масштабирует все от -1 до +1, если внутри frustrum .. если вы публикуете ответ я его рассмотрю. Спасибо. – user815129

ответ

2

Vertex shader преобразует вершины из локальной системы координат модели в пространство для клипа. Если ваши координаты превышают единичный куб после разделения перспективы (куб с [-1; 1] размерами для каждого измерения или [-W; W] перед делением), то эти фрагменты будут обрезаны.

Если вы не заботитесь о Z и действительно не хотите устанавливать правильную ортопроекцию (например, вы не знаете диапазон значений Z и, следовательно, не можете устанавливать соответствующие плоскости клипов), вы можете исправить Z в вершинном шейдере зажав его до (-W; W) диапазона (или просто установив его 0).