Как определить идентификатор текущей вершины на этапе TES?

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

Во время контроля тесселяции я проверяю идентификатор 0-11 и сохраните положение вершины и цвет в позиции текущего идентификатора.

Я определяю glPatchParameteri(GL_PATCH_VERTICES, 3); а также layout(vertices = 12) out; для моего шейдера управления тесселяцией, поскольку я хочу, чтобы каждый треугольник тесселировался в 4 треугольника.

Похоже, что во время моей оценки шейдера тесселяции in vec3 tcPosition[]; а также in vec3 tcColor[]; массивы содержат правильные 12 значения в правильном порядке. Однако: как правильно связать их во время оценки? Есть что-нибудь подобное gl_primitiveID во время оценки тесселяции? Мне нужна замена для gl_primitiveID который 0 для всех сгенерированных вершин, поскольку они порождены из одного патча. В настоящее время я просто использую информацию первых трех вершин (0,1,2) но мне нужно будет сдвинуть эти индексы на 3 после каждого сгенерированного треугольника.

void main(){
    vec3 p0 = gl_TessCoord.x * tcPosition[0];
    vec3 p1 = gl_TessCoord.y * tcPosition[1];
    vec3 p2 = gl_TessCoord.z * tcPosition[2];
    tePosition = p0 + p1 + p2;
    teColor = gl_TessCoord.x * tcColor[0] + gl_TessCoord.y * tcColor[1] + gl_TessCoord.z * tcColor[2]; 
    gl_Position = mvp * vec4(tePosition, 1);
} 

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

1 ответ

Решение

Я посылаю треугольник вниз по трубопроводу и хочу тесселяции его в прокладку Серпинского.

Стоп. Тебе этого не сделать.

Тесселяция треугольника не делается таким образом, чтобы вы могли это сгенерировать. Конкретный алгоритм тесселяции, необходимый для тесселяции, разработан для облегчения соединения ребер. Он также предназначен для обеспечения адаптивной и плавной тесселяции.

Треугольники Серпинского не имеют этих свойств.

Если вам нужен такой строгий контроль над точными средствами тесселяции, я бы предложил выполнить тесселяцию на процессоре. GS был бы неспособен достаточно точно описать треугольник; большинство реализаций OpenGL не позволяют GS выводить столько треугольников, даже с использованием геометрических шейдеров.

Что касается подробностей вашего вопроса:

Я определяю glPatchParameteri(GL_PATCH_VERTICES, 3); и макет (вершины = 12) из; для моего шейдера управления тесселяцией, поскольку я хочу, чтобы каждый треугольник тесселировался в 4 треугольника.

Это не то, как работает тесселяция.

Каждый патч, который достигает генератора примитивов тесселяции (шаг после TCS), независимо от того, сколько у него вершин, считается одним примитивом для тесселяции. Ваш TCS здесь выводит 12 вершин в патче, но сам патч все равно будет одним треугольником.

Позволяя вам контролировать количество вершин, вы можете определить, что означает "вершина" для вашего алгоритма тесселяции. Например, поверхность Безье имеет 16 вершин контрольных точек, но все равно это четверка. Это позволяет основанной на Безье TES принимать все 16 контрольных точек в качестве входных данных при создании позиций вершин.

Кроме того, тесселяция не работает на основе вопроса о том, сколько треугольников вы получаете. Это работает в зависимости от того, сколько подразделений вы хотите. Это то, что определяют внешний и внутренний уровни тесселяции: количество сегментов, в которые будут переселены края треугольника.

Однако: как правильно связать их во время оценки?

Входы TES - это те же значения, что и TCS. В том же порядке.

Тесселяция работает так, что тесселяция - это не ваши вершины, написанные TCS. Тесселяция - это абстрактный патч. Генератор примитивов тесселяции генерирует "вершины" относительно абстрактного патча.

gl_TessCoord это то, что позволяет вам определить, где конкретный вызов TES находится в абстрактном патче. Затем вы комбинируете это с выходными данными TCS (которые являются входными данными для TES), чтобы сгенерировать значения для каждой вершины, необходимые для этой координаты.

Мне нужна замена для gl_primitiveID, который равен 0 для всех сгенерированных вершин, так как они создаются из одного и того же патча.

Это уже делает это. gl_PrimitiveID будет одинаковым для каждого вызова TES в одном патче.

Другие вопросы по тегам