Читал пару дней назад книгу про шейдеры на OpenGL. Там описывалась проблема, связанная с использованием графических ускорителей на разных платформах. Оригинальное решение - разработчики написали отдельный язык шейдеров на основе ANSI C и встроили его не куда-нибудь, а прямо в драйвер OpenGL. Другими словами, внутри драйвера сидит компилятор и компоновщик, которые могут зохавывать код на языке шейдеров; а т.к. это - составляющие драйвера, то код может подаваться на компиляцию даже в время работы проектируемого приложения. Оригинальный подход, блин - я б до такого в жизни не додумался бы.
Теперь - о главном. Вообще, граф. ускоритель состоит из 2 основных составляющих - вершинный процессор и фрагментный процессор. В вершинном процессоре происходит обработка модели в обьектном пространстве, т.е. точки модели рассматриваются в 3-х и 4-х мерные. Соответственно, верш. процессор может выполнять операции поворота модели, расчета нормалей к поверхности, расчета цвета, определения координат текстуры и др. операций, связанных с объектным пространством. Фрагментный процессор работает уже в пространстве изображения. Он выполняет операции проецирования фрагмента, обработки изображения наложением различных эффектов (например, дымки или размытости), смешиванием цветов или наложением текстуры.
Саму работу всей этой конструкции можно охарактеризовать, если вспонить, что такое конечный автомат или, хотя бы, машина Тьюринга. По сути - разработчики OpenGL сделали драйвер, являющийся конечным автоматом с офигенным количеством состояний. На вход подается исходная модель в виде массива полигонов и пр. , которая обрабатывается в зависимости от заданных параметров (т.е. от заданного начального состояния) и на выходе получаем изображение на экране. Внутри драйвера происходит повершинная(!) обработка каждого из полигонов сначала вершинным процессором, а затем - результат работы передается во фрагментный процессор, который генерирует фрагмент изображения и лепит его в буфер кадра. Можно заметить, что такой принцип работы (процессоры работают независимо друг от друга) ускоряет работу с графикой, т.к. позволяет обрабатывать данные параллельно, в отличиее от реализации на WinAPI.
Я пока что не упоминал, что такое шейдеры и каким боком они прилеплены к этой схеме - а прилеплены они самым прямым образом: шейдер - это программа, которая выполняется на графическом процессоре, с возможностью перегрузки. Т.о. есть вершинные шейдеры, есть фрагментные шейдеры, выполняемые на соответствующих процессорах.
Это была преамбула, амбула только теперь. Как известно, алгоритм отображения с прозрачностью в исходном его виде не реализуем для z-буфера. Вместо этого используется его модификация. В самом же OpenGL вообще отсутствует алгоритм прозрачности - там полигоны перед отображением еще и отсортировывать надо. А всяким извращенцам вроде меня, которые ценят системное время и добивающимся большой скорости работы кода, становится как-то не по себе, когда прикидывают размеры массива и сколько времени этот массив будет сортироваться. И ладно, если один раз - а то пересортировку нужно делать при каждом малом изменении положения модели или ее геометрических параметров - это уж вообще ахтунг с процом получается. Непорядок.
Хорошее решение предлагает использование шейдеров - можно перегрузить фрагментный шейдер своим, в котором реализуется алгоритм прозрачности с двойной буферизацией. Т.к. OpenGL поддерживается на большинстве ОС (хоть WinOS, хоть Linux) и имеет собственный компилятор, то проблем с совместимостью возникать не должно. (разве только интерфейсная часть). Единственное требование к этому подходу - аппаратная часть должна поддерживать шейдеры хотя бы первую версию. Однако, с учетом того, что нынешние видео-карты поддерживают 3ю версию, то проблем с этим возникать не должно.