2 ** blendeq.c - Demonstrates the use of the blend_minmax, blend_subtract,
3 ** and blend_logic_op extensions using glBlendEquationEXT.
5 ** Over a two-color backround, draw rectangles using twelve blend
6 ** options. The values are read back as UNSIGNED_BYTE and printed
7 ** in hex over each value. These values are useful for logic
8 ** op comparisons when channels are 8 bits deep.
17 #define GL_GLEXT_PROTOTYPES
21 static int dithering
= 0;
23 int supportlogops
= 0;
24 static int doPrint
= 1;
28 static void DrawString(const char *string
)
32 for (i
= 0; string
[i
]; i
++)
33 glutBitmapCharacter(GLUT_BITMAP_9_BY_15
, string
[i
]);
36 static void Init(void)
40 glShadeModel(GL_FLAT
);
43 static void Reshape(int width
, int height
)
47 windH
= (GLint
)height
;
49 glViewport(0, 0, (GLint
)width
, (GLint
)height
);
52 glMatrixMode(GL_PROJECTION
);
54 gluOrtho2D(0, windW
, 0, windH
);
55 glMatrixMode(GL_MODELVIEW
);
58 static void Key(unsigned char key
, int x
, int y
)
65 dithering
= !dithering
;
68 if (supportlogops
== 3)
69 use11ops
= (!use11ops
);
71 printf("Using GL 1.1 color logic ops.\n");
72 else printf("Using GL_EXT_blend_logic_op.\n");
81 static void PrintColorStrings( void )
90 for (i
= windH
- deltaY
+ 4; i
> 0; i
-=deltaY
) {
91 glReadPixels(xleft
, i
+10, 1, 1, GL_RGB
, GL_UNSIGNED_BYTE
, ubbuf
);
92 sprintf(colorString
, "(0x%x, 0x%x, 0x%x)",
93 ubbuf
[0], ubbuf
[1], ubbuf
[2]);
94 glRasterPos2f(xleft
, i
);
95 DrawString(colorString
);
96 glReadPixels(xright
, i
+10, 1, 1, GL_RGB
, GL_UNSIGNED_BYTE
, ubbuf
);
97 sprintf(colorString
, "(0x%x, 0x%x, 0x%x)",
98 ubbuf
[0], ubbuf
[1], ubbuf
[2]);
99 glRasterPos2f(xright
, i
);
100 DrawString(colorString
);
104 static void Draw(void)
106 int stringOffset
= 5, stringx
= 8;
107 int x1
, x2
, xleft
, xright
;
110 (dithering
) ? glEnable(GL_DITHER
) : glDisable(GL_DITHER
);
112 if (supportlogops
& 2)
113 glDisable(GL_COLOR_LOGIC_OP
);
115 glClearColor(0.5, 0.6, 0.1, 1.0);
116 glClear(GL_COLOR_BUFFER_BIT
);
118 /* Draw background */
119 glColor3f(0.1, 0.1, 1.0);
120 glRectf(0.0, 0.0, windW
/2, windH
);
123 glColor3f(0.8, 0.8, 0.0);
124 i
= windH
- deltaY
+ stringOffset
;
125 glRasterPos2f(stringx
, i
); i
-= deltaY
;
126 DrawString("SOURCE");
127 glRasterPos2f(stringx
, i
); i
-= deltaY
;
129 glRasterPos2f(stringx
, i
); i
-= deltaY
;
131 glRasterPos2f(stringx
, i
); i
-= deltaY
;
133 glRasterPos2f(stringx
, i
); i
-= deltaY
;
134 DrawString("subtract");
135 glRasterPos2f(stringx
, i
); i
-= deltaY
;
136 DrawString("reverse_subtract");
137 glRasterPos2f(stringx
, i
); i
-= deltaY
;
139 glRasterPos2f(stringx
, i
); i
-= deltaY
;
141 glRasterPos2f(stringx
, i
); i
-= deltaY
;
143 glRasterPos2f(stringx
, i
); i
-= deltaY
;
145 glRasterPos2f(stringx
, i
); i
-= deltaY
;
147 glRasterPos2f(stringx
, i
); i
-= deltaY
;
148 DrawString("invert");
149 glRasterPos2f(stringx
, i
); i
-= deltaY
;
151 glRasterPos2f(stringx
, i
); i
-= deltaY
;
159 xright
= 5 + windW
/2;
161 /* Draw foreground color for comparison */
162 glColor3f(0.9, 0.2, 0.8);
163 glRectf(x1
, i
, x2
, i
+deltaY
);
165 /* Leave one rectangle of background color */
167 /* Begin test cases */
169 glBlendFunc(GL_ONE
, GL_ONE
);
172 glBlendEquationEXT(GL_MIN_EXT
);
173 glRectf(x1
, i
, x2
, i
+deltaY
);
176 glBlendEquationEXT(GL_MAX_EXT
);
177 glRectf(x1
, i
, x2
, i
+deltaY
);
180 glBlendEquationEXT(GL_FUNC_SUBTRACT_EXT
);
181 glRectf(x1
, i
, x2
, i
+deltaY
);
184 glBlendEquationEXT(GL_FUNC_REVERSE_SUBTRACT_EXT
);
185 glRectf(x1
, i
, x2
, i
+deltaY
);
187 glBlendFunc(GL_ONE
, GL_ZERO
);
190 glBlendEquationEXT(GL_LOGIC_OP
);
192 glEnable(GL_COLOR_LOGIC_OP
);
194 glRectf(x1
, i
, x2
, i
+deltaY
);
198 glRectf(x1
, i
, x2
, i
+deltaY
);
202 glRectf(x1
, i
, x2
, i
+deltaY
);
206 glRectf(x1
, i
, x2
, i
+deltaY
);
210 glRectf(x1
, i
, x2
, i
+deltaY
);
213 glLogicOp(GL_INVERT
);
214 glRectf(x1
, i
, x2
, i
+deltaY
);
218 glRectf(x1
, i
, x2
, i
+deltaY
);
222 glRectf(x1
, i
, x2
, i
+deltaY
);
223 glRectf(x1
, i
+10, x2
, i
+5);
227 if (supportlogops
& 2)
228 glDisable(GL_COLOR_LOGIC_OP
);
229 glColor3f(1.0, 1.0, 1.0);
240 static GLenum
Args(int argc
, char **argv
)
244 doubleBuffer
= GL_FALSE
;
246 for (i
= 1; i
< argc
; i
++) {
247 if (strcmp(argv
[i
], "-sb") == 0) {
248 doubleBuffer
= GL_FALSE
;
249 } else if (strcmp(argv
[i
], "-db") == 0) {
250 doubleBuffer
= GL_TRUE
;
252 printf("%s (Bad option).\n", argv
[i
]);
259 int main(int argc
, char **argv
)
263 char *extName1
= "GL_EXT_blend_logic_op";
264 char *extName2
= "GL_EXT_blend_minmax";
265 char *extName3
= "GL_EXT_blend_subtract";
268 glutInit(&argc
, argv
);
270 if (Args(argc
, argv
) == GL_FALSE
) {
274 glutInitWindowPosition(0, 0); glutInitWindowSize( 800, 400);
277 type
|= (doubleBuffer
) ? GLUT_DOUBLE
: GLUT_SINGLE
;
278 glutInitDisplayMode(type
);
280 if (glutCreateWindow("Blend Equation") == GL_FALSE
) {
284 /* Make sure blend_logic_op extension is there. */
285 s
= (char *) glGetString(GL_EXTENSIONS
);
286 version
= (char*) glGetString(GL_VERSION
);
289 if (strstr(s
,extName1
)) {
292 printf("blend_logic_op extension available.\n");
294 if (strncmp(version
,"1.1",3)>=0) {
297 printf("1.1 color logic ops available.\n");
299 if (supportlogops
== 0) {
300 printf("Blend_logic_op extension and GL 1.1 not present.\n");
303 if (strstr(s
,extName2
) == 0) {
304 printf("Blend_minmax extension is not present.\n");
307 if (strstr(s
,extName3
) == 0) {
308 printf("Blend_subtract extension is not present.\n");
314 glutReshapeFunc(Reshape
);
315 glutKeyboardFunc(Key
);
316 glutDisplayFunc(Draw
);