Есть ли способ генерировать примитивы в геометрическом шейдере без входной геометрии?

17

Несколько лет назад я пытался внедрить этот Gem GeForce в OpenGL для генерации трехмерного процедурного ландшафта с использованием Marching Cubes . В статье предлагается реализовать Marching Cubes в геометрическом шейдере с максимальной эффективностью. Это означает, что мне нужно запустить шейдер один раз для каждого вокселя в домене, и он сгенерирует всю геометрию в этой ячейке.

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

Итак, есть ли способ сказать OpenGL начать передачу рендеринга из геометрического шейдера без какой-либо входной геометрии? Или мне всегда придется посылать какие-то фиктивные очки в GPU, чтобы все заработало.

Мартин Эндер
источник

Ответы:

15

Нет, на самом деле нет способа сделать это.

Для вызова геометрического шейдера требуется входной примитив и генерируется 0 или более выходных примитивов. Без входного примитива на самом деле не существует способа вызвать геометрический шейдер . Конечно, вы можете расширить пределы максимального количества выходных примитивов геометрического шейдера для каждого входного примитива (не знаю практических ограничений сейчас, может быть, порядка тысяч). Таким образом, вы можете генерировать 1024 треугольника для каждой точки, но у вас всегда должны быть некоторые входные примитивы.

Однако то, что вам не нужно, - это реальное понятие геометрии. На самом деле вам не нужно визуализировать трехмерные точки в каком-либо разумном месте, они также могут иметь только некоторый абстрактный индекс или координаты текстуры или что-то еще в качестве атрибутов и не обязательно значащую трехмерную позицию. Никто не диктует, какие атрибуты имеют ваши вершины. И вы даже можете визуализировать вершины без каких-либо атрибутов . Но вы должны визуализировать некоторые примитивы, чтобы вызвать на них геометрический шейдер, даже если эти примитивы не имеют каких-либо фактических атрибутов (однако вопрос о том, как вы потом вычисляете свою выходную геометрию в геометрическом шейдере, другой вопрос).

Но то, что вы на самом деле сделали, рендеринг точки для каждой ячейки сетки и генерация треугольников марширующих кубов для этой ячейки из нее, является именно прямым подходом. Конечно, какие атрибуты содержит эта ячейка, зависит от вас, это может быть трехмерная позиция, текстовая координата в трехмерной текстуре, что угодно, но это ячейки сетки, которые вы визуализируете. Говоря чисто семантически, вы на самом деле не «отбрасываете» эти точки, а затем «заменяете» их треугольниками, вы «конвертируете» каждую точку в набор треугольников. Это именно то, для чего предназначен геометрический шейдер, и в этом нет ничего «хакерского» или «неправильного». Никто не говорит, что геометрический шейдер должен генерировать тот же тип выходного примитива, который был введен, чтобы быть «правильным» .


То, что вы можете сделать, чтобы добиться в значительной степени не требующего ввода способа рендеринга вашей воксельной сетки (а это может быть тем, о чем вы на самом деле просили), это просто нарисовать набор точек без атрибутов. Это означает, что вам не нужны никакие массивы атрибутов, вы просто отключаете их все и вызываете простое glDrawArraysс количеством ячеек, которое вам нужно. Затем в вершинном шейдере или геометрическом шейдере вы можете сгенерировать необходимый индекс ячейки трехмерной сетки с небольшим магическим индексом из входного идентификатора вершины (т. gl_VertexIDЕ. Единственной имеющейся у вас информации), а затем вычислить геометрию марширующих кубов из поиска в объемная текстура 3D (или любая другая структура данных).

Итак, в ретроспективе я должен с самого начала релятивизировать свое утверждение: вы не можете генерировать примитивы без каких-либо входных примитивов , но вы можете генерировать их без какой-либо входной геометрии .

Крис говорит восстановить Монику
источник