Предыстория: В повседневной
Поэтому время от времени я возвращаюсь к написанию какого-нибудь простого и симпатичного, а также небольшого и абсолютно бесполезного, но крайне поучительного кода. На C++ такой тренировкой являются матрицы. А так как в эти зимние праздники я никуда не поехал, то и занялся вплотную этим вопросом.
В очередной раз мне захотелось написать такой класс матриц, чтобы он оказался бинарно-совместимым с четырехмерными матрицами OpenGL. Ну и заодно я решил поизучать плотнее тему под названием "специализации классов и функций C++". Однако - как выяснилось - в инете (ну, во всяком случае на русском) почему-то затруднительно найти подробное описание того, как именно OpenGL совершает внутри себя - при всей их очевидности - свои сакральные действия типа glRotate (а пионеры повсюду задают на эту тему одни и те же вопросы, т.к. матрицы там 4D, и действительно существуют некоторые хинты). Но все-таки пары найденных статей с кратко изложенной математикой хватило, чтобы написать код. Четырехмерные матрицы заработали, и пожалуй единственное, что меня в них не устраивало - это чисто софтверный код внутри их операторов умножения на векторы (и т.п. действия).
Ну а чтобы тестировать правильность работы библиотеки, пришлось создать небольшое приложение на OpenGL, которое, пользуясь этими матрицами, рисует призмы (нечто вроде "Quake Brushes") в небольшом окошке. И вот дальше началось самое интересное.
Куда ни сунься в инет на тему OpenGL - повсюду разложены красивые и подробные переводы на русский документации по функциям типа glTranslate() и уже давно доступные где угодно книжки, в которых повсеместно советуют написать несколько glVertex3f посреди между glBegin/glEnd. Все это нужно, что нарисовать чуть более, чем одну призму в чуть более, чем наипростейшей тривиальной модели геометрических объектов.
Углубление процесса Internet Data Mining обнаружило, что не более 10% от вышеуказанного массива информации составляет то, что на этом уровне (в самых лучших книгах и кое-где на форумах продвинутых перцев) подается как профессиональный уровень. Суть в том, что если не выводить точки за точкой, каждый раз делая вывод функции glVertex, а создать массив, то для массивов в OpenGL есть специальные вызовы массивного вывода. Ну и утверждается, что по сравнению с примитивным такой способ быстрее (кто бы сомневался) в 10 раз.
Но я не остановился на этом, и продолжая упорно серфить, таки пролез на внезапно обнаружившийся третий уровень, который - в свою очередь - тоже составлял всего 10% от предыдущего. Там было написано: вы что, массивы в обычной ОЗУ создаете? Их надо делать в видеопамяти! И это дает прирост скорости рендеринга сцены... еще в 100(!!!) раз.
При этом было замечено, что чем
И тут начались приколы, так сказать, "back to the universe". Дело в том, что с версии 2.0 в OpenGL появились шейдеры. Для тех кто не в танке (хотя я пишу этот пост скорее для тех, для кого как, для меня, OpenGL - пускай в силу причин малых - оказался в стадии изучения, а не пренебрежения или наоборот, полного знания) шейдеры -это маленькие программы, которыми можно стало делать что-то внутри самого OpenGL. Но вот что именно ими делать (и нужно ли это мне), как-то ускользало от понимания... Пока я не стал смотреть, что именно менялось от версии к версии.
Итак, изначально был glBegin/glEnd и между ними - рендеринг по одной точке функциями glVertex.
Потом добавили glVertexPointer (на буфер), и другие pointer-ы (на всякие там цвета, текстуры и нормали).
Закончилась эта стадия, как я писал чуть выше, функцией glInterleavedArrays и работой с буферами в видеопамяти (OpenGL 1.5).
В следующей версии (уже 2.0) буфера выкинули из основной памяти - они теперь только в video-RAM, и выкатили пробный шар - в виде чуточки шейдеров.
А дальше (по мере развития версий 2.x) Пятачку так понравились шейдеры, что он стал давить кнопку delete непрерывно.
Сначала убрали glInterleavedArrays: теперь стало надо заводить буфер в видеопамяти и вызывать не фиксированную (пусть и достаточно гибкую, но все же сильно ограниченную функцию), а вместо нее - свою, написанную на шейдерах.
А потом удалили... glRotate, glTranslate и вообще все те вещи, по которым неподготовленный программист узнает OpenGL на всех этих сайтах с документацией и книжками! Т.е. теперь чтобы умножить матрицы, надо тоже написать шейдерную функцию, которая это делает, скомпилировать ее, и дернуть откуда-то посередине из скоего кода (скажем, как у меня - внутри операторов матриц на C++).
В итоге к версии 3.3 сформировалось уже ДВА OpenGL'я: [модер]новый (где все исключительно на шейдерах плюс совсем немножко утилитных функций для их загрузки, вызова и компиляции) и специально оставленная дырка для новичков: compatibility+depricated режим.
Ну и окончательно это завершилось выходом OpenGL 4.0/4.1 в совсем недавно закончившемся 2010-том году, который соответствует видеокартам уровня "DirectX 10/11".
Получились занятными ровно три факта:
1. OpenGL надо изучать уже не так, как везде написано!
2. Если следовать классическим путем, то лишь одна тысячная доля информации в интернете по современному использованию OpenGL дает прирост производительности в тысячу раз!!! Надо сразу лезть изучать GLSL (The OpenGL Shading Language).
3. Мне чрезвычайно понравилось, что когда-нибудь в следующий раз я смогу доделать свои матрицы, оптимизируя их умножения и другие операции не на ассемблере, а на шейдерном языке.
Ну и наконец, никто не мешает реализовать на шейдерах скажем, функцию нейросети или обработку фильтров видео... что уж вам больше нравится.
January 8 2011, 03:28:03 UTC 1 year ago
January 8 2011, 14:34:05 UTC 1 year ago
July 5 2011, 01:27:40 UTC 10 months ago
July 5 2011, 19:11:32 UTC 10 months ago
Почему бы и нет?
Можно уже не только почитать или посмотреть, но уже и купить:http://nvworld.ru/files/old/docs/3d
http://www.hifi-install.ru/news/Kompani
http://old.osp.ru/text/print/302/3140.h