removed hacked GL tokens, fixed a printf
[mesa.git] / progs / tests / osdemo16.c
1 /* $Id: osdemo16.c,v 1.1 2001/03/08 15:24:18 brianp Exp $ */
2
3 /*
4 * Demo of off-screen Mesa rendering
5 *
6 * See Mesa/include/GL/osmesa.h for documentation of the OSMesa functions.
7 *
8 * If you want to render BIG images you'll probably have to increase
9 * MAX_WIDTH and MAX_HEIGHT in src/config.h.
10 *
11 * This program is in the public domain.
12 *
13 * Brian Paul
14 *
15 * PPM output provided by Joerg Schmalzl.
16 * ASCII PPM output added by Brian Paul.
17 */
18
19
20 #include <stdio.h>
21 #include <stdlib.h>
22 #include "GL/osmesa.h"
23 #include "GL/glut.h"
24
25
26 #define SAVE_TARGA
27
28
29 #define WIDTH 400
30 #define HEIGHT 400
31
32
33
34 static void render_image( void )
35 {
36 GLfloat light_ambient[] = { 0.0, 0.0, 0.0, 1.0 };
37 GLfloat light_diffuse[] = { 1.0, 1.0, 1.0, 1.0 };
38 GLfloat light_specular[] = { 1.0, 1.0, 1.0, 1.0 };
39 GLfloat light_position[] = { 1.0, 1.0, 1.0, 0.0 };
40 GLfloat red_mat[] = { 1.0, 0.2, 0.2, 1.0 };
41 GLfloat green_mat[] = { 0.2, 1.0, 0.2, 0.5 };
42 GLfloat blue_mat[] = { 0.2, 0.2, 1.0, 1.0 };
43 GLfloat white_mat[] = { 1.0, 1.0, 1.0, 1.0 };
44 GLfloat purple_mat[] = { 1.0, 0.2, 1.0, 1.0 };
45 GLUquadricObj *qobj = gluNewQuadric();
46
47 glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient);
48 glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse);
49 glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular);
50 glLightfv(GL_LIGHT0, GL_POSITION, light_position);
51
52 glEnable(GL_LIGHTING);
53 glEnable(GL_LIGHT0);
54 glEnable(GL_DEPTH_TEST);
55
56 glMatrixMode(GL_PROJECTION);
57 glLoadIdentity();
58 glOrtho(-2.5, 2.5, -2.5, 2.5, -10.0, 10.0);
59 glMatrixMode(GL_MODELVIEW);
60
61 glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
62
63 glPushMatrix();
64 glRotatef(20.0, 1.0, 0.0, 0.0);
65
66 #if 0
67 glPushMatrix();
68 glTranslatef(-0.75, 0.5, 0.0);
69 glRotatef(90.0, 1.0, 0.0, 0.0);
70 glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, red_mat );
71 glutSolidTorus(0.275, 0.85, 20, 20);
72 glPopMatrix();
73 #endif
74
75 /* red square */
76 glPushMatrix();
77 glTranslatef(0.0, -0.5, 0.0);
78 glRotatef(90, 1, 0.5, 0);
79 glScalef(3, 3, 3);
80 glDisable(GL_LIGHTING);
81 glColor4f(1, 0, 0, 0.5);
82 glBegin(GL_POLYGON);
83 glVertex2f(-1, -1);
84 glVertex2f( 1, -1);
85 glVertex2f( 1, 1);
86 glVertex2f(-1, 1);
87 glEnd();
88 glEnable(GL_LIGHTING);
89 glPopMatrix();
90
91 #if 0
92 /* green square */
93 glPushMatrix();
94 glTranslatef(0.0, 0.5, 0.1);
95 glDisable(GL_LIGHTING);
96 glColor3f(0, 1, 0);
97 glBegin(GL_POLYGON);
98 glVertex2f(-1, -1);
99 glVertex2f( 1, -1);
100 glVertex2f( 1, 1);
101 glVertex2f(-1, 1);
102 glEnd();
103 glEnable(GL_LIGHTING);
104 glPopMatrix();
105
106 /* blue square */
107 glPushMatrix();
108 glTranslatef(0.75, 0.5, 0.3);
109 glDisable(GL_LIGHTING);
110 glColor3f(0, 0, 0.5);
111 glBegin(GL_POLYGON);
112 glVertex2f(-1, -1);
113 glVertex2f( 1, -1);
114 glVertex2f( 1, 1);
115 glVertex2f(-1, 1);
116 glEnd();
117 glEnable(GL_LIGHTING);
118 glPopMatrix();
119 #endif
120 glPushMatrix();
121 glTranslatef(-0.75, -0.5, 0.0);
122 glRotatef(270.0, 1.0, 0.0, 0.0);
123 glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, green_mat );
124 glColor4f(0,1,0,0.5);
125 glEnable(GL_BLEND);
126 glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
127 gluCylinder(qobj, 1.0, 0.0, 2.0, 16, 1);
128 glDisable(GL_BLEND);
129 glPopMatrix();
130
131 glPushMatrix();
132 glTranslatef(0.75, 1.0, 1.0);
133 glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, blue_mat );
134 gluSphere(qobj, 1.0, 20, 20);
135 glPopMatrix();
136
137 glPopMatrix();
138
139 gluDeleteQuadric(qobj);
140
141 {
142 GLint r, g, b, a;
143 glGetIntegerv(GL_RED_BITS, &r);
144 glGetIntegerv(GL_GREEN_BITS, &g);
145 glGetIntegerv(GL_BLUE_BITS, &b);
146 glGetIntegerv(GL_ALPHA_BITS, &a);
147 printf("channel sizes: %d %d %d %d\n", r, g, b, a);
148 }
149 }
150
151
152
153 static void
154 write_targa(const char *filename, const GLushort *buffer, int width, int height)
155 {
156 FILE *f = fopen( filename, "w" );
157 if (f) {
158 int i, x, y;
159 const GLushort *ptr = buffer;
160 printf ("osdemo, writing tga file \n");
161 fputc (0x00, f); /* ID Length, 0 => No ID */
162 fputc (0x00, f); /* Color Map Type, 0 => No color map included */
163 fputc (0x02, f); /* Image Type, 2 => Uncompressed, True-color Image */
164 fputc (0x00, f); /* Next five bytes are about the color map entries */
165 fputc (0x00, f); /* 2 bytes Index, 2 bytes length, 1 byte size */
166 fputc (0x00, f);
167 fputc (0x00, f);
168 fputc (0x00, f);
169 fputc (0x00, f); /* X-origin of Image */
170 fputc (0x00, f);
171 fputc (0x00, f); /* Y-origin of Image */
172 fputc (0x00, f);
173 fputc (WIDTH & 0xff, f); /* Image Width */
174 fputc ((WIDTH>>8) & 0xff, f);
175 fputc (HEIGHT & 0xff, f); /* Image Height */
176 fputc ((HEIGHT>>8) & 0xff, f);
177 fputc (0x18, f); /* Pixel Depth, 0x18 => 24 Bits */
178 fputc (0x20, f); /* Image Descriptor */
179 fclose(f);
180 f = fopen( filename, "ab" ); /* reopen in binary append mode */
181 for (y=height-1; y>=0; y--) {
182 for (x=0; x<width; x++) {
183 i = (y*width + x) * 4;
184 fputc(ptr[i+2] >> 8, f); /* write blue */
185 fputc(ptr[i+1] >> 8, f); /* write green */
186 fputc(ptr[i] >> 8, f); /* write red */
187 }
188 }
189 }
190 }
191
192
193 static void
194 write_ppm(const char *filename, const GLubyte *buffer, int width, int height)
195 {
196 const int binary = 0;
197 FILE *f = fopen( filename, "w" );
198 if (f) {
199 int i, x, y;
200 const GLubyte *ptr = buffer;
201 if (binary) {
202 fprintf(f,"P6\n");
203 fprintf(f,"# ppm-file created by osdemo.c\n");
204 fprintf(f,"%i %i\n", width,height);
205 fprintf(f,"255\n");
206 fclose(f);
207 f = fopen( filename, "ab" ); /* reopen in binary append mode */
208 for (y=height-1; y>=0; y--) {
209 for (x=0; x<width; x++) {
210 i = (y*width + x) * 4;
211 fputc(ptr[i], f); /* write red */
212 fputc(ptr[i+1], f); /* write green */
213 fputc(ptr[i+2], f); /* write blue */
214 }
215 }
216 }
217 else {
218 /*ASCII*/
219 int counter = 0;
220 fprintf(f,"P3\n");
221 fprintf(f,"# ascii ppm file created by osdemo.c\n");
222 fprintf(f,"%i %i\n", width, height);
223 fprintf(f,"255\n");
224 for (y=height-1; y>=0; y--) {
225 for (x=0; x<width; x++) {
226 i = (y*width + x) * 4;
227 fprintf(f, " %3d %3d %3d", ptr[i], ptr[i+1], ptr[i+2]);
228 counter++;
229 if (counter % 5 == 0)
230 fprintf(f, "\n");
231 }
232 }
233 }
234 fclose(f);
235 }
236 }
237
238
239
240 int main( int argc, char *argv[] )
241 {
242 void *buffer;
243
244 /* Create an RGBA-mode context */
245 #if OSMESA_MAJOR_VERSION * 100 + OSMESA_MINOR_VERSION >= 305
246 /* specify Z, stencil, accum sizes */
247 OSMesaContext ctx = OSMesaCreateContextExt( GL_RGBA, 16, 0, 0, NULL );
248 #else
249 OSMesaContext ctx = OSMesaCreateContext( GL_RGBA, NULL );
250 #endif
251 if (!ctx) {
252 printf("OSMesaCreateContext failed!\n");
253 return 0;
254 }
255
256 /* Allocate the image buffer */
257 buffer = malloc( WIDTH * HEIGHT * 4 * sizeof(GLushort));
258 if (!buffer) {
259 printf("Alloc image buffer failed!\n");
260 return 0;
261 }
262
263 /* Bind the buffer to the context and make it current */
264 if (!OSMesaMakeCurrent( ctx, buffer, GL_UNSIGNED_SHORT, WIDTH, HEIGHT )) {
265 printf("OSMesaMakeCurrent failed!\n");
266 return 0;
267 }
268
269 render_image();
270
271 if (argc>1) {
272 #ifdef SAVE_TARGA
273 write_targa(argv[1], buffer, WIDTH, HEIGHT);
274 #else
275 write_ppm(argv[1], buffer, WIDTH, HEIGHT);
276 #endif
277 }
278 else {
279 printf("Specify a filename if you want to make an image file\n");
280 }
281
282 printf("all done\n");
283
284 /* free the image buffer */
285 free( buffer );
286
287 /* destroy the context */
288 OSMesaDestroyContext( ctx );
289
290 return 0;
291 }