Russian Qt Forum
Апрель 24, 2024, 21:28 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1] 2 3   Вниз
  Печать  
Автор Тема: Архитектура VBO  (Прочитано 17172 раз)
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« : Декабрь 17, 2014, 10:32 »

Добрый день

VBO (vertex buffer object) - это данные хранящиеся на видеокарте (напр вертексы, нормали, полигоны, цвет).  Использование VBO заметно ускоряет рисование. Приложение оперирует с индексами этих данных (фактически это хендлы).

Сделал просто - храню хендл вместе с массивом данных. Напр контейнер вертексов имеет хендл VBO и.т.д. Это кажется очевидным - ведь исходная геометрия не меняется. А если вертексы изменились - тогда и данные VBO пере-создаются.

Однако вылезла неприятная деталь - в одном из окон пользователь может указать так называемый "flat shading", в то время как в других должен показываться gourand, phong и др. К сожалению, для "flat" нужна др геометрия подаваемая в OpenGL, т.е. др полигоны, вертексы. Эту дыру я просто заткнул, для режима "flat" не использую VBO, а рисую по-старинке glBegin/glEnd. Это конечно позорно медленно, зато у меня нет никаких доп данных и минимум кода. Поскольку flat используется редко, в году раз - проконало.

Но появилась новая фича - пользователь хочет иметь возможность показа измельченной (грубо говоря триангулированной) модели, причем "виртуально", деталированная модель должна храниться на видео (а не занимать память приложения). И тут моя простая организация данных стала трещать по всем швам.

И почему-то вспомнилось: "кривая архитектура", "изменить архитектуру приложения" и.т.п. не раз звучавшие на этом форуме Улыбающийся  Поэтому внимательно слушаю Ваши рекомендации.

Спасибо
Записан
__Heaven__
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2130



Просмотр профиля
« Ответ #1 : Декабрь 17, 2014, 11:40 »

Буфер с продублированными нормалями так и не появилось желание использовать?
Записан
__Heaven__
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2130



Просмотр профиля
« Ответ #2 : Декабрь 17, 2014, 11:47 »

Ни разу не пробовал, но, возможно, прокатит следующее:
Хранить нормали к каждому треугольнику в текстуре. В вершинном шейдере смотреть id выводимой вершины, делить её на 3, тем самым получая id нормали в текстуре. Передавать этот id (нормали) в фрагментный шейдер. А в том извлекать нормаль и применять к цвету фрагмента.
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #3 : Декабрь 17, 2014, 12:26 »

Буфер с продублированными нормалями так и не появилось желание использовать?
Ну вот за это меня точно выгонят и больше не возьмут  Улыбающийся

Ни разу не пробовал, но, возможно, прокатит следующее:
Хранить нормали к каждому треугольнику в текстуре. В вершинном шейдере смотреть id выводимой вершины, делить её на 3, тем самым получая id нормали в текстуре. Передавать этот id (нормали) в фрагментный шейдер. А в том извлекать нормаль и применять к цвету фрагмента.
Утопия хотя бы потому что каждый фейсет может иметь любое вертексов от 1 до 4 включительно.

Не надо сваливаться с специфику OpenGL (все равно без толку), а посмотрим с точки зрения пресловутой архитектуры. Примерная схема

Исходные данные (RAM) ---> данные для "прямого" рисования (VBO)
-----------------------------> данные для "фейсетного" рисования (Непонимающий)
-----------------------------> данные для "детального" рисования (должны быть в VBO)

Понятно что я должен создать нужные буфера VBO, но где хранить их хендлы и как ими управлять?
Записан
__Heaven__
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2130



Просмотр профиля
« Ответ #4 : Декабрь 17, 2014, 13:51 »

У вас имеются точки и линии, которые нужно освещать?
Разбивать квадратики на треугольники тоже не вариант? (В 3.0 GL_QUADS deprecated).
Передавать id нормали в текстуре для каждой вершины через VBO? Но тут мало что сэкономим.

Буфер с продублированными нормалями так и не появилось желание использовать?
Ну вот за это меня точно выгонят и больше не возьмут  Улыбающийся

А чем это хуже, чем рисовать phong? Там такое же количество нормалей необходимо. Кстати, их можно подсчитать/продублировать налету (при включении режима flat) и засунуть в vbo, оставив только хэндл - данные из RAM можно удалить. Ну или рассчитывать нормали при каждой прорисовке и выводить их без участия VBO, по завершению прорисовки затирать.
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #5 : Декабрь 17, 2014, 16:18 »

У вас имеются точки и линии, которые нужно освещать?
Точки и линии могут освещаться, как и wireframe (аттач).

А чем это хуже, чем рисовать phong? Там такое же количество нормалей необходимо.
Возьмем грубую модель сферы, она имеет напр 144 полигона (для простоты - все треугольники) и 74 вертекса. Теперь мы хотим рисовать с фейсетными нормалями. Значит у каждого треугольника "свои" 3 вертекса, итого 144 * 3 = 432. Что Вы скажете о программисте который увеличил число базовых данных в 432 / 74 = 5.83 раза?  Улыбающийся

Не надо искать какие-то "железячные" решения, лезть в шейдеры, id и.т.п - все это мелко. Вопрос был об архитектуре. Поверьте, она есть даже с OpenGL  Улыбающийся
Записан
__Heaven__
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2130



Просмотр профиля
« Ответ #6 : Декабрь 17, 2014, 17:07 »

Может gl_InstanceID чем-то поможет. Только он доступен с OpenGL 3.1.
Записан
__Heaven__
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2130



Просмотр профиля
« Ответ #7 : Январь 31, 2016, 12:18 »

Нашлось ли решение?
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #8 : Январь 31, 2016, 12:35 »

Нашлось ли решение?
Для режима "flat" нет, так и рисую glBegin/glEnd. Для показа деталированной модели - да
Записан
Racheengel
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2679


Я работал с дискетам 5.25 :(


Просмотр профиля
« Ответ #9 : Январь 31, 2016, 15:31 »

Нашлось ли решение?
Для режима "flat" нет, так и рисую glBegin/glEnd. Для показа деталированной модели - да

вместо glBegin/glEnd можно хотя бы glDrawArrays заюзать, будет заметно быстее.
Записан

What is the 11 in the C++11? It’s the number of feet they glued to C++ trying to obtain a better octopus.

COVID не волк, в лес не уйдёт
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #10 : Январь 31, 2016, 15:54 »

вместо glBegin/glEnd можно хотя бы glDrawArrays заюзать, будет заметно быстее.
Ну вот такой я неграмотный, про glDrawArrays/glDrawElements мне ничего не известно  Плачущий
Вы тему-то читайте
Записан
Racheengel
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2679


Я работал с дискетам 5.25 :(


Просмотр профиля
« Ответ #11 : Январь 31, 2016, 23:48 »

Так а что надо пользователю? Видеть либо модель с текстурой, либо wireframe? Какая тогда разница в организации полигонов?
Записан

What is the 11 in the C++11? It’s the number of feet they glued to C++ trying to obtain a better octopus.

COVID не волк, в лес не уйдёт
__Heaven__
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2130



Просмотр профиля
« Ответ #12 : Февраль 01, 2016, 06:54 »

Racheengel, там проблема в нормалях. Требуется задавать нормаль для примитива, а не вершины. А opengl такого не позволяет сделать при glDrawArrays/glDrawElements не дублируя координаты, нормали.
Записан
Racheengel
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2679


Я работал с дискетам 5.25 :(


Просмотр профиля
« Ответ #13 : Февраль 01, 2016, 11:36 »

Racheengel, там проблема в нормалях. Требуется задавать нормаль для примитива, а не вершины. А opengl такого не позволяет сделать при glDrawArrays/glDrawElements не дублируя координаты, нормали.

То есть полигоны (их координаты) не меняются? Если да, то нормали я бы генерировал/хранил отдельно для каждого случая и переключался бы на нужные данные при смене view. Как вариант.
Записан

What is the 11 in the C++11? It’s the number of feet they glued to C++ trying to obtain a better octopus.

COVID не волк, в лес не уйдёт
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #14 : Февраль 01, 2016, 12:03 »

То есть полигоны (их координаты) не меняются? Если да, то нормали я бы генерировал/хранил отдельно для каждого случая и переключался бы на нужные данные при смене view. Как вариант.
Ладно, начнем "от печки". Сколько вертексов имеет простейший кубик? Человек знакомый с OpenGL ответит 24 (а не 8 как начинающий). Зачем 24 если углов-то всего 8? Потому что OpenGL рисует "по вертескам" (а не "по фейсам"). Один вертекс = одна нормаль и одна текстурная координата, счетчики должны совпадать во всех подаваемых рисованию массивах. Разные фейсы могут использовать разные вертексы, но при этом будут использовать и их нормали.  Если мы хотим видеть "грани" (как у кубика) то вынуждены создать вертексы для каждой фейсы (грани). Итого 6 * 4 = 24. В каждом углу будут 3 вертекса с разными нормалями. Как говорят "все расшарено"
Записан
Страниц: [1] 2 3   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.058 секунд. Запросов: 23.