
VA или делаем быстрее
Вы еще не используете VA? Тогда мы идем к вам!
[spoiler]
VA - VertexArray
Это некий массив где храняться параметры вершин. Что сокращает количество вызовов передоваемых видеокарте.
И так, вы решили нарисовать что либо с помощью VA, для этого выделяют 4 шага:
1) включить режим рисования VA
2) загрузить меш в огл
3) нарисовать
4) выключить режим рисования VA
И так погнали
Для Того что бы включить режим VA нужно написать следкющее
glEnableClientState(mode);
mode может принимать
из названия понятно какие опции они включают
Для того что бы выключить режим (после рисования) мы пишем
glDisableClientState(mode);
mode принимает тоже самое что и при enableclientstate (логично =))
после того как мы активировали VA надо передать параметры ему это делается с помощью gl * Pointer(argc);
* может принимать
параметры у каждого поинтера разные
теперь что делают параметры
size - это размерность, например если у нас вершины имеют 3 координаты (xyz) то требуется установить 3 на size
type - тип переменных лежащих в массиве, тут все ясно, главное, что бы они были переведены в gl'овские, например float - GL_FLOAT и тд
stride - смещение (в байтах) до следующего параметра (если массив с данными однородный то 0)
pointer - ссылка на первый элемент (0 если массив однородный)
Теперь перейдем к этапу отрисовки нашего массива
Есть несколько комманд для этого:
------glArrayElement(i);
С помощью ее мы может нарисовать какую нибуть(i) точку из массива
Внимание, команда не рисует точку, она просто возврощяет соотвецтвующий вызов glVertex glTexCoord glNormal и тд, для конкретного индекса, что бы нарисовать надо будет сделать цикл по всем элементам и обернуть в стандартный glBegin/glEnd
------glDrawRangeElements(mode, start, end, count, type, indices);
тоже что и glDrawElements только может выводиьт не с начала и не до конца
------glDrawElements(mode, count, type, indices);
с помощью этой команды мы можем рисовать по индексам передоваемым в indices, count и type должны быть понятны
все же напомню count - количество вершин которые нужно отрисовать, type - тип данных массива indices
mode - GL_POLYGON, GL_TRIANGLES, и тд
------glMultiDrawElements(mode, count, type, indices, pcount);
эта команда вызывает glDrawElements pcount раз
тут есть особенность в отличии от drawelements параметр count должен быть не числом а одномерным массивом размером pcount (от туда будут браться количество точек) и параметр indices должен быть массивом указателей на список вершин
------glDrawArrays(mode, first, count);
mode уже понятен, first - с какого элемента начинать, count сколько рисовать
эта команда выводит активированный массив (glEnable * State)
------glMultiDrawArrays(mode, first, count, pcount);
так же как и glMultiDrawElements только вызывает glDrawArrays
ну вот и все, комбинируйте параметрами что бы получить нужный результат
Пример использования
В следующей статье будет про использование VBO, а пока что отписывайте что не так написал, что исправить, комментарии да и вобще что хотите
[spoiler]
VA - VertexArray
Это некий массив где храняться параметры вершин. Что сокращает количество вызовов передоваемых видеокарте.
И так, вы решили нарисовать что либо с помощью VA, для этого выделяют 4 шага:
1) включить режим рисования VA
2) загрузить меш в огл
3) нарисовать
4) выключить режим рисования VA
И так погнали
Для Того что бы включить режим VA нужно написать следкющее
glEnableClientState(mode);
mode может принимать
|
из названия понятно какие опции они включают
Для того что бы выключить режим (после рисования) мы пишем
glDisableClientState(mode);
mode принимает тоже самое что и при enableclientstate (логично =))
после того как мы активировали VA надо передать параметры ему это делается с помощью gl * Pointer(argc);
* может принимать
|
параметры у каждого поинтера разные
|
теперь что делают параметры
size - это размерность, например если у нас вершины имеют 3 координаты (xyz) то требуется установить 3 на size
type - тип переменных лежащих в массиве, тут все ясно, главное, что бы они были переведены в gl'овские, например float - GL_FLOAT и тд
stride - смещение (в байтах) до следующего параметра (если массив с данными однородный то 0)
pointer - ссылка на первый элемент (0 если массив однородный)
Теперь перейдем к этапу отрисовки нашего массива
Есть несколько комманд для этого:
------glArrayElement(i);
С помощью ее мы может нарисовать какую нибуть(i) точку из массива
Внимание, команда не рисует точку, она просто возврощяет соотвецтвующий вызов glVertex glTexCoord glNormal и тд, для конкретного индекса, что бы нарисовать надо будет сделать цикл по всем элементам и обернуть в стандартный glBegin/glEnd
------glDrawRangeElements(mode, start, end, count, type, indices);
тоже что и glDrawElements только может выводиьт не с начала и не до конца
------glDrawElements(mode, count, type, indices);
с помощью этой команды мы можем рисовать по индексам передоваемым в indices, count и type должны быть понятны
все же напомню count - количество вершин которые нужно отрисовать, type - тип данных массива indices
mode - GL_POLYGON, GL_TRIANGLES, и тд
------glMultiDrawElements(mode, count, type, indices, pcount);
эта команда вызывает glDrawElements pcount раз
тут есть особенность в отличии от drawelements параметр count должен быть не числом а одномерным массивом размером pcount (от туда будут браться количество точек) и параметр indices должен быть массивом указателей на список вершин
------glDrawArrays(mode, first, count);
mode уже понятен, first - с какого элемента начинать, count сколько рисовать
эта команда выводит активированный массив (glEnable * State)
------glMultiDrawArrays(mode, first, count, pcount);
так же как и glMultiDrawElements только вызывает glDrawArrays
ну вот и все, комбинируйте параметрами что бы получить нужный результат
Пример использования
|
В следующей статье будет про использование VBO, а пока что отписывайте что не так написал, что исправить, комментарии да и вобще что хотите
glColorPointer(3, GL_FLOAT, 6*sizeof(float), &mesh2[3]);
а почему 6*sizeof(float) и там, и там?
static float mesh[] = {
-1, -1, 0, 1, 0, 0, 1, 0, 0, 0,
0, 1, 0, 1, 0, 1, 1, 0, 0, 0,
1, -1, 0, 1, 1, 0, 1, 0, 0, 0
};
glVertexPointer(3, GL_FLOAT, 10*sizeof(float), &mesh[0]);
glColorPointer(4, GL_FLOAT, 10*sizeof(float), &mesh[3]);
вершина начинается в mesh[0] и заканьчивается в mesh[2] потом идет цвет mesh[3] и конец в mesh[6] потом 3 ненужные ячейки, и в mesh[10] у тебя опять начало вершины и в nesh[13] начало цвета, смотрим mesh[10] — mesh[0] = 10 mesh[13] — mesh[3] = 10
и там и там смещение 10
забыл написать, он не рисует, он просто преобразовывает в соотвецтвующий вызов glVertex
те что бы с ним что нибуть нарисовать надо сделать вот так:
glBegin(GL_TRIANGLES);
for(int i = 0; i < 3; i++)
glArrayElement(i);
glEnd();
не особо крутой метод =)
А можно не отключать glDisableClientState, если у меня все через VA рисуется?
метод плохой потому что рисуется все тот же glBegin/glEnd VA не используется, просто тебе не приходится писать для каждой вершины по 150 команд для задания всего, текстурных координат, геом гоординат и тд, а все береться из твоих glVertexPoiter и тд