2013-09-26 4 views
9

В настоящее время я пытаюсь написать программу, которая принимает меш в качестве входных данных (состоящих из вершинных позиций и массива элементов) и выводит индексы для использования с glDrawElements() в режиме GL_TRIANGLES_ADJACENCY.Индексирование смежности треугольника OpenGL

Мне пришло время писать код, в котором не замкнутые сетки имеют треугольники, у которых может не быть трех соседей. Например, сетка, состоящая из одного треугольника, не имеет соседних треугольников.

Triangle adjacency diagram from OpenGL 4.3 spec.

В этом случае, что должно индексы 2, 4 и 6 быть? Похоже, что должен быть стандартный способ сказать геометрическому шейдеру, что один или несколько соседних треугольников не существуют. Однако я не мог найти информацию об этом в спецификации OpenGL (v4.3).

Единственный треугольник - примерный пример, но есть много сеток, где не все треугольники соединяются с тремя другими - например, с цилиндром с открытыми концами.

Есть ли стандартный способ обработки таких случаев? Извиняюсь, если я пропустил что-то очевидное в спецификации.

Выше изображения скопированы по спецификации OpenGL 4.3.

ответ

1

Это непростая задача. Вообще говоря, если GS нуждается в информации о смежности, то вы, вероятно, делаете что-то вроде тесселяции на основе GS, где вы используете информацию о соседних вершинах для генерации новых данных треугольника.

В тех случаях, когда информация о соседних вершинах отсутствует, вам необходимо обратиться к вашему алгоритму тесселяции для решений. Многие алгоритмы имеют способы иметь дело с случаями, когда соседний треугольник отсутствует. Некоторые алгоритмы тесселяции не; они работают только на совершенно регулярных сетках.

В таких случаях у вас есть проблема. Края, которые не имеют смежных треугольников, вероятно, должны быть острыми краями. Итак, если ваш алгоритм тесселяции не имеет возможности создавать острые края, тогда вам нужно будет изменить его, чтобы создать такую ​​вещь.

В противном случае вы всегда можете генерировать фантомные вершины. Например, предположим, что на вашей диаграмме нет вершины 6. Вы можете создать данные для вершины 6 путем зеркалирования/проецирования вершины 3 через середину линии, созданной вершинами 1 и 5. Это создает эффект обычная сетка.

Опять же, насколько это хорошо, зависит от вашего алгоритма тесселяции и желаемых результатов.

0

Ну, если вы не обеспечиваете достаточное количество вершин, то вы не получите ничего, что бы визуализировалось. Это означает, что если вы предоставите менее 6 вершин для GL_TRIANGLES_ADJACENCY, это не будет отображаться.

Простейшим критерием для этого является использование mode=GL_LINES и count=1.

+1

Спасибо за вашу помощь. Я понимаю, что, несмотря ни на что, я должен предоставить 6 индексов на треугольник. Я просто не знаю, какие индексы должны предоставить в случае, когда треугольник не имеет другого треугольника, прилегающего к нему. Как работает тест «GL_LINES», кстати? – Kaathe

+2

@ Kaathe: Это просто одна из тех вещей. Минимальное количество точек для описания строки равно 2; минимальное количество точек для описания треугольника равно 3. Хотя два предыдущих случая были простой геометрией, существуют также ограничения, наложенные на основании того, как вы передаете свой _list_ из примитивов - минимальное количество точек для описания смежности треугольника равно 6 Если вы действительно думаете об этом, какую цель вы бы описали примыкания треугольника только с одним треугольником? Хотя, если вы мертвы на этом, вы, вероятно, можете создать 3 вырожденных треугольника - я не знаю, что вы выиграете от этого? –

+0

@ Kaathe Если у вас есть только 3 индекса, вы не будете использовать 'GL_TRIANGLES_ADJACENCY'. Вместо этого вы должны использовать 'GL_TRIANGLES' –

6

После прочтения ваших комментариев к BЈовић, я думаю, ясно, что то, что вы ищете, является индексом примитивного перезапуска.

Вы можете зарезервировать произвольное значение индекса для представления примитивного перезапуска, используя следующий вызов API: glPrimitiveRestartIndex (...). Часто используется -1, как в вашем исходном вопросе.

Взгляните на: OpenGL 4.3 Core Specification - 10.3.5 Примитивный перезапуск - с. 301 для более подробной информации.

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

+0

Спасибо, я сейчас проверю эту часть спецификации. – Kaathe

+1

Спасибо за вашу помощь, но я думаю, что это немного другое - я действительно пытаюсь выяснить, есть ли способ сказать геометрическому шейдеру, что треугольник не имеет трех соседей. Извините - я не думаю, что я ясно дал понять исходный вопрос. Я попытался немного изменить его, чтобы сделать его более ясным. – Kaathe

+1

Это то, что делает примитивный перезапуск. Это более простой способ создания вырожденных примитивов (нулевой области), чем переход одного и того же индекса несколько раз в примитивных режимах, которые основаны на связности (например, полосы, смежность, петли и т. Д.). Так как информация о связности в списке смежности фактически не используется для примитивной сборки сама по себе (хотя вы можете использовать ее для такого в настраиваемом шейдере геометрии/тесселяции), вы можете зарезервировать любой индекс, который вы хотите обозначить не смежным примитивом - повторное использование примитивного перезапуска просто имеет смысл. –

Смежные вопросы