Прозрачность
Реалистическая графика предполагает использование эффекта прозрачности элементов наблюдаемой сцены, когда через одни фрагменты сцены можно видеть другие. Для этой цели введено понятие "альфа-канал" в характеристике цвета точки (RGBA), который и указывает на степень ее "прозрачности". При альфа, равном 1.0, фрагмент считается полностью непрозрачным, а при 0.0 - полностью прозрачным.
Тест на прозрачность разрешается и запрещается командами glEnable и glDisable с параметром GL_ALPHA_TEST.
Для управления тестом по альфа-каналу используется команда void glAlphaFunc(GLenum/wnc, GLclampf ref),
где параметр ref задает сравниваемое значение для альфа-параметра. Это значение находится в диапазоне [0, 1]. По умолчанию параметр ref равен 0. Параметр func задает функцию сравнения значений альфа и может принимать следующие символьные константы:
|
Параметр |
Тест завершается положительно в случае |
|
GL_NEVER GL_LESS GL.EQUAL GL.LEQUAL GL_GREATER GL.NOTEQUAL GL.GEQUAL GLALWAYS |
Никогда Если поступающее значение меньше, чем ref Если поступающее значение равно ref Если поступающее значение меньше или равно ref Если поступающее значение больше, чем ref Если поступающее значение не равно ref Если поступающее значение больше или равно ref Всегда. Установлено по умолчанию |
Данная команда позволяет принять или отклонить фрагмент, основываясь на сравнении заданного значения альфа-канала с реальным. Если результат сравнения положительный, то поступающий фрагмент рисуется в буфере кадра (в зависимости от условий тестов трафарета и глубины). В случае отрицательного результата - вывод фрагмента не осуществляется.
В данном примере выводится фрагмент объекта в буфер кадра, если его альфа-значение больше (0.4):
glEnable(GL_ALPHA_TEST);
glAlphaFunc(GL_GREATER, 0.4f);
Используя команду glAlphaFunc(), мы работаем с полностью прозрачным или полностью непрозрачным смешиванием, но при этом не возникает реального смешивания. Для определения метода реального смешивания выводимых фрагментов с изображением, существующим в буфере кадра, используется команда
void glBlendFunc(GLenum srcfactor,GLenum dstfactor)
Параметр srcfactor определяет метод обработки RGBA значений, поступающих от источника на смешивание (выводимый фрагмент), a dstfactor определяет метод обработки RGB А значений, находящихся в буфере кадра, с которыми будет осуществляться смешивание. Всего существует одиннадцать методов обработки RGBA значений. Девять из них предназначены для источника (srcfactor) и восемь для приемника (dstfactor).
|
Параметр |
Метод |
|
GL.ZERO |
(0, 0, 0 ,0) |
|
GL_ONE |
(1,1, 1,1) |
|
GL_SRC_COLOR |
(Rs/kR, Gs/kG, Bs/kB, As/kA) |
Продолжение табл.
|
Параметр |
Метод |
|
GL_ONE_MINUS_SRC_COLOR |
(1, 1,1,1)-(RslkR, Gs/kG, Bs/kB, As/kA) |
|
GL_DST_COLOR |
(Rd 1 kB, Gd 1 kG, BD / kB, Ad 1 kA) |
|
GL_ONE_MINUS_DST_COLOR |
(1, 1, 1, l)-(RD/kR, GDlkG,BD/kB, Ad 1 kA) |
|
GL_SRC_ALPHA |
(As / kA, As / kA, As / kA, As / kA) |
|
GL_ONE_MINUS_SRC_ALPHA |
(1, 1, 1, 1)-(As/*a, As/kA, As / kA, As / kA) |
|
GL_DST_ALPHA |
(Ad 1 kA, Ad 1 kA, Ad 1 kA, Ad 1 kA) |
|
GL_ONE_MINUS_DST_ALPHA |
(1, 1,1, l)-(AD/kA, AD/kA, AD/kA, AD/kA) |
|
GL_SRC_ALPHA_SATURATE |
(i, i, i, 1), где i = min (As, kA-AD!kA) |
В таблице приняты следующие условные обозначения: Rs, Gs, Bs, As определяют составляющие цвета источника; RD, GD, BD, AD определяют составляющие цвета приемника. Значение цвета изменяется в диапазоне [О, кс= 2тС - 1], где С означает составляющие цвета R, G, В и А, а т - количество битовых плоскостей видеопамяти, отведенных под R, G, В и А соответственно. Для определения итогового значения RGBA после смешивания используются следующие уравнения:
R(d) = пйп(&я, Rb-Sr + Ro dffr,
G(d) = min(?c, Gs-sg + GD-dGy, B(d) = min(?B, Bs-sB + BD-dBy A(d) = min(kA,As-sA +ADdA),
где sB, sg, sb, sa, dR, dG, dB, dA - соответствующие компоненты векторов методов из таблицы для источника и для приемника цвета.
По умолчанию смешивание заблокировано. Для его включения используется команда glEnable(GL_BLEND). Для отключения -glDesable(GL_BLEND).
Приведенные возможности смешивания цветов позволяют осуществить достаточно сложные замыслы разработчиков. На практике часто используют команду glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA) с примитивами, отсортированными по глубине от наиболее к наименее отдаленным и непрозрачным элементам в глубине. Последнее подсказано логикой визуализации "пакета" полупрозрачных графических примитивов.
Рассмотрим пример вывода трех примитивов: непрозрачного красного треугольника; полупрозрачного зеленого квадрата и полупрозрачного синего прямоугольника. Процедура вывода имеет вид:
GLvoid DrawPrimO
{
glClear( GL_COLOR_BUFFER_BIT);
// Непрозрачный красный треугольник
glColor4f(1.0f, O.Of, O.Of, 1 .Of);
glBegin(GL_TRI ANGLES);
glVertex3f( O.Of, 1.8f, l.Of);
glVertex3f(-1.4f, -1.5f, l.Of);
glVertex3f( 1.4f, -1.5f, l.Of);
glEnd();
glEnable(GL_BLEND); // Разрешаем смешивание цветов glBlendFunc(GL_SRC_ALPHA,GL_SRC_ALPHA); // Режим смешивания glColor4f(0.0f, l.Of, O.Of, 0.5f); // Полупрозрачный зеленый квадрат glBegin(GL_QUADS);
glVertex3f( l.Of, l.Of, 2.0f);
glVertex3f(-1.0f, 1.0f,2.0f);
glVertex3f(-1.0f, -l.Of, 2.0f);
glVertex3f( l.Of, -l.Of, 2.0f);
glEnd();
И Полупрозрачный синий прямоугольник
glColor4f(0.0f, O.Of, 1 .Of, 0.5f);
glBegin(GL_QUADS);
glVertex3f( 2.0f, 0.5f, O.Of);
glVertex3f(-2.0f, 0.5f, O.Of);
glVertex3f(-2.0f, -0.5f, O.Of);
glVertex3f( 2.0f, -0.5f, O.Of);
glEnd();
glDisable(GL_BLEND); И Запрещаем смешивание цветов
}
В результате работы данной процедуры мы можем видеть красный треугольник через полупрозрачный квадрат и прямоугольник.