2014-12-27 3 views
2

Я прошел через существующие темы и немного проверил это, но я не совсем уверен, что делаю это правильно, поэтому я бы предпочел задать вопрос, чем быть застрял в течение нескольких часов, выясняя, что я неправильно понял, работая с несколькими учебниками OpenGL ES 2.0.OpenGL ES 2.0 и Dynamic VBO

Я реализовал VBO, как они представлены в «OpenGL ES 2 для Android - краткое руководство», и я пришел к моменту, что мне нужен динамический VBO, который обновляется каждый кадр с помощью некоторых матричных вычислений (это может быть точка, где я ошибаюсь) на вершинах модели. После этих расчетов, я хотел бы передать (обновление) те, уже выделены ВБО (с glBufferData) с этой частью кода/Java Android:

GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, this.id); 

    //GLES20.glBufferData(GLES20.GL_ARRAY_BUFFER, this.getLength() * Utils.BYTES_PER_FLOAT, null, GLES20.GL_DYNAMIC_DRAW); 

    /* CREATE BUFFER AND SET POSITION */ 
    FloatBuffer fBuffer = ByteBuffer.allocateDirect((this.length = vertices.length) * Utils.BYTES_PER_FLOAT) 
      .order(ByteOrder.nativeOrder()).asFloatBuffer().put(vertices); 
    fBuffer.position(0); 

    GLES20.glBufferSubData(GLES20.GL_ARRAY_BUFFER, 0, fBuffer.capacity(), fBuffer); 

    GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0); 
  • this.id - идентификатор ранее генерироваться буфер
  • this.getLength - длина первоначально выделено FloatBuffer

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

И вопрос - более или менее - это:

  • ли действительный подход к обновлению такого буфера или я могу получить совет, как сделать это правильно в этих условиях я обеспечил (OpenGL ES 2.0, Android 4+)?

A подвопросы являются:

  • Является ли подход с использованием VBO для динамических моделей лучше, чем использование ВАО для этих обстоятельств, или я должен скорее реализовать подход VBO для статики и динамики ВАО?
  • Когда мне следует беспокоиться о проблемах с памятью, глядя просто на GC_FOR_ALLOC Отладочная информация?
  • (Немного за пределами подтекста темы) Используя орто-изометрическую матрицу вида (орфографический + 2x поворота + Z-перевод), какой подход подходит для создания графического интерфейса для приложения?

EDIT (27.12):

Для достижения изометрической матрицы проекции Я просто использую эти строки:

Matrix.orthoM(this.orthoProjectionMatrix, 0, -screenAspect, screenAspect, -1.0f, 1.0f, -1.0f, 10.0f); 
    Matrix.translateM(this.viewProjectionMatrix, 0, this.orthoProjectionMatrix, 0, 0.0f, 0.0f, -5.0f); 
    Matrix.rotateM(this.viewProjectionMatrix, 0, 45, 1.0f, 0.0f, 0.0f); 
    Matrix.rotateM(this.viewProjectionMatrix, 0, 45, 0.0f, 1.0f, 0.0f); 

который просто:

  • создать проекцию орфографического, портрет в соответствии с аспектом экрана
  • переводить перемещение только по оси Z (так что сцена видна с расстояния)
  • вращать ось X на 45 градусов
  • вращаться по оси Y на 45 градусов

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

+2

То, что вы описали в своем вопросе, касается меня. Вы используете OpenGL ES 2.0, но вы говорите о применении матричных преобразований к вершинам, хранящимся в VBO. Обычно вы этого не делаете, если у вас есть доступ к шейдерам. Вы передадите матрицу, которую хотите преобразовать в вершины, в вершинный шейдер и применяете это преобразование каждый раз, когда вы рисуете. Буферные данные вершин будут фактически статичными, и именно вершинный шейдер выполняет всю работу (многократно). _ Из звуков вещей вы можете накапливать свои преобразования в своей матрице, а не в буфере вершин. –

+0

Я понял, что один из них. Проверьте один из моих комментариев ниже. Это был действительно недействительный подход. Теперь я переключаюсь между равномерными матрицами, которые привязаны к шейдеру при рендеринге сцены или HUD. Ссылаясь на то, что вы только что сказали - всякий раз, когда я применяю некоторые преобразования каждого кадра, должен ли я всегда работать с матрицей преобразования, которую я передаю в шейдер или операции над вершинами модели, и иметь более динамичный VBO? Я не могу получить информацию о любой книге/материале, которая относится к OpenGL ES 2.0 (Android), и описывает ее доступным способом. Я смущен. –

+1

Вы никогда не хотите менять вершины в буфере вершин, если только вам это не понадобится. Это может помочь, если вы считаете, что Vertex Buffers хранятся в памяти GPU, вы хотите перенести как можно меньше данных с CPU на GPU, как вы можете, каждый кадр. Обновление матрицы (16 поплавков) почти всегда меньше данных, чем обновление каждой вершины. Поэтому, если вы хотите повернуть одну и ту же модель в различной сумме каждого кадра, обновите матрицу и верните шейдеру фактическое преобразование. Динамические VBO лучше подходят для таких вещей, как «системы с сохранением состояния», которые будут опираться на предыдущие результаты шейдерного шейдера. –

ответ

3

(Предисловие:. Я не знаком с OpenGL ES, просто с регулярной OpenGL Однако, я не могу себе представить, что API-интерфейсы отличаются слишком много)

ли действительный подход к обновлению такого буфера

Если только fBuffer не будет меньше или равен размеру буфера OpenGL. glBufferSubData не изменяет размер буфера, и запись на внешний доступ выделенного диапазона не допускается. Вы можете использовать glBufferData для перераспределения буфера на новый размер. Также проверьте buffer object streaming.

Является ли подход с использованием VBO для динамических моделей лучше, чем использование VAO для этих обстоятельств, или я должен использовать метод VBO для статики и VAO для динамики?

VBOs и VAO являются ортогональными понятиями. VBOs хранят данные вершин; ВАО просто указывают, где и как получить вершины для рендеринга.

Использование орто-изометрической матрицы вида (орфографическая + 2x вращения + Z-перевод) Что такое подходящий подход для создания графического интерфейса для приложения?

Отбросьте перевод Z, и вместо этого визуализируйте GUI последним с отключенным буфером глубины. Кроме того, для чего нужны вращения?

+0

1) (в соответствии с размерами буфера) Я хотел бы избавиться от ВСЕХ предыдущих данных и отправить новую партию того же размера. Проще говоря - я хочу обновить старые данные буфера некоторыми вычислениями. Я чувствую, что создание нового буфера не требуется, но я не нашел ответа, который предоставляет мне другое решение. 2) (согласно VBO/VAO) ОК. Я прочитаю некоторые другие материалы по этой теме, потому что кажется, что я не понял это правильно. –

+0

3) (ссылаясь на изометрическую проекцию) Мне удалось понять гораздо лучший подход, который заключается в следующем: использовать изометрическую проекцию, нарисовать объекты сцены, переключиться на простую орфографическую проекцию, нарисовать HUD. И кажется, что он работает очень хорошо (HUD остается в том же месте, над сценой, пока сцена движется так, как должна, когда я перетаскиваю) –

+1

@ ŁukaszModliński Если загруженные данные имеют одинаковый размер, вы можете использовать 'glBufferSubData' написать ему. Вам нужно использовать 'glBufferData', если вам нужно изменить размер буфера (или оставить сироту старой, см. Ссылку на потоковое буферизацию). Подумайте о 'glBufferSubData' как' memcpy' и 'glBufferData' как' realloc'. –