Программирование игр, создание игрового движка, OpenGL, DirectX, физика, форум
GameDev.ru / Программирование / Форум / OpenGL, VAO, VBO

OpenGL, VAO, VBO

Страницы: 1 2 Следующая »
AMM1AKПостоялецwww1 мар. 201816:27#0
Доброго дня!
В любом руководстве будет написано, что: "VAO хранит состояние, необходимое для переключения между различными конфигурациями вершинных массивов/буферов", или что-то вроде того.
То есть команда
glBindVertexArray
должна устанавливать сохраненные раннее в конкретный VAO буферы и состояния командами
glBindBuffer, glVertexAttrib*, glVertexAttribPointer, ...
Теперь расссмотрим следующий код
glBindVertexArray(vao1);
glBindBuffer(GL_ARRAY_BUFFER, vbo1);

glBindVertexArray(vao2);
glBindBuffer(GL_ARRAY_BUFFER, vbo2);

glBindVertexArray(0);

А дальше запишем следующий код.

glBindVertexArray(vao1);
glGetIntegerv(GL_ARRAY_BUFFER_BINDING, &currentVBO);

По логике, после установки vao1, она должна установить vbo1 в GL_ARRAY_BUFFER. Однако, в currentVBO останется vbo2, даже несмотря на то, что в предыдущем листинге было

glBindVertexArray(0);
Таким образом возникает вопрос:
Правильно ли я понимаю, что привязка VAO и VBO абсолютно независимы и никак не влияют на друг друга. Только лишь во время drawcall'а, текущий VAO неявно установит свои настройки касаемо конфигураций вершинных массивов/буферов, а после восстановит все как было?

PS: Хочу это знать, чтобы понимать, что происходит под коробкой. Это нужно для того, чтобы запилить кэширование текущих буферов и не вызывать glBindBuffer для уже установленного буфера.

Правка: 1 мар. 2018 16:29

DampireПостоялецwww1 мар. 201816:40#1
https://www.khronos.org/opengl/wiki/Vertex_Specification#Vertex_Array_Object
Think of it like this. glBindBuffer sets a global variable, then glVertexAttribPointer reads that global variable and stores it in the VAO. Changing that global variable after it's been read doesn't affect the VAO. You can think of it that way because that's exactly how it works.

P.S.
При этом ibo вполне себе сохраняется в vao.

Правка: 1 мар. 2018 16:44

AMM1AKПостоялецwww1 мар. 201816:49#2
Dampire
Спасибо, разобрался.
Действительно,
glBindBuffer
устанавливает глобальное состояние. Во время установленного VAO, такие команды как
glVertexAttrib*, glVertexAttribPointer
запоминают в указанный attributeIndex установленный раннее индекс VBO. Получить этот id можно следующим образом
glBindVertexArray(vao);
glGetVertexAttribiv(attribIndex, GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING, &vboId);

/A\Постоялецwww1 мар. 201820:18#3
AMM1AK
Смотри на расширение direct state access, там понятнее что к чему и когда привязывается
AMM1AKПостоялецwww12 мар. 201816:11#4
Доброго дня!
Подниму тему, так как возник еще один вопрос.
Dampire
> P.S.
> При этом ibo вполне себе сохраняется в vao.
В какой момент vao сохраняет себе идентификатор ibo? Для вершинного буфера, я так понял, это делалось в момент вызова glVertexAttribPointer или glVertexAttribIPointer. Как же обстоит дело с индексным буфером? Неужели это происходит прямо внутри glBindBuffer?(при условии что target == GL_ELEMENT_ARRAY_BUFFER)
Если да, то правильно ли я понимаю, что если я не отвяжу vao, то я могу его случайно испортить, если буду потом биндить что-то к  GL_ELEMENT_ARRAY_BUFFER?
DampireПостоялецwww12 мар. 201817:45#5
Да.
dayllengerПользовательwww12 мар. 201817:55#6
AMM1AK
> В какой момент vao сохраняет себе идентификатор ibo?
А если у вас OpenGL 4.5, то достаточно вызвать glVertexArrayElementBuffer и ничего байндить не нужно.
MrShoorУчастникwww12 мар. 201820:01#7
AMM1AK
> Если да, то правильно ли я понимаю, что если я не отвяжу vao, то я могу его
> случайно испортить, если буду потом биндить что-то к  GL_ELEMENT_ARRAY_BUFFER?
Именно так. Это OpenGL. Тут все на вот таких костылях. Привыкай.  :)
innuendoПостоялецwww12 мар. 201820:11#8
MrShoor
> Это OpenGL. Тут все на вот таких костылях. Привыкай.

Не забудь рассказать про DX12, всё круто, но нужно играть по правилам MS :)

DampireПостоялецwww12 мар. 201821:33#9
MrShoor
Забыл рассказать про default vao.
MrShoorУчастникwww12 мар. 201822:05#10
Dampire
> Забыл рассказать про default vao.
Что за default vao? 0 который? Не во всех реализациях OGL ES можно биндить ноль. Некоторые выдают INVALID_OPERATION если попытаться забиндить 0.
Daniil PetrovПостоялецwww12 мар. 201823:39#11
А есть пример использования glVertexArrayElementBuffer? А то кроме сухонькой http://docs.gl/gl4/glVertexArrayElementBuffer больше ничего не попалось :)
/A\Постоялецwww13 мар. 20182:27#12
Daniil Petrov
раньше было
glBindVertexArray(vao)
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ib)

теперь
glVertexArrayElementBuffer(vao, ib)

Daniil PetrovПостоялецwww13 мар. 20183:35#13
Запутался :) решил растащить загрузку VBO и их оборачивание в VAO, попутно использовал glVertexArrayElementBuffer.
Гружу VBOs:
+ Показать

Оборачиваю их в VAO:
+ Показать

Но приложение упорно вылетает на
glBindVertexArray(vao);
glDrawElements(GL_TRIANGLES, ElementCount, GL_UNSIGNED_INT, NULL);
glBindVertexArray(NULL);
так было и с простыми биндингами. Не подскажете, где я допустил ошибку?

Правка: 13 мар. 2018 3:56

war_zesПостоялецwww13 мар. 20185:33#14
Daniil Petrov
> glEnableVertexAttribArray(INDEX_BUFFER);
> glVertexAttribPointer(INDEX_BUFFER, 3, GL_UNSIGNED_INT, GL_FALSE, 0, NULL);
а зачем ты это делаешь для индексного буфера?

Здесь и ошибка. индексный буфер не имеет никакого отношения к атрибутам вершин

Правка: 13 мар. 2018 5:37

Страницы: 1 2 Следующая »

/ Форум / Программирование игр / Графика

2001—2018 © GameDev.ru — Разработка игр