WIP - port to Mali EGL
[mesa-demos/mali.git] / src / demos / pixeltest.c
blobe9b95b8b88695f1e0d39f8a63ba28fab713470ca
2 /* Pixeltest for lines.
3 * Hui Qi Tay
5 * Modified from
6 * glReadPixels and glCopyPixels test by Brian Paul.
7 */
9 #include <assert.h>
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <math.h>
13 #include <string.h>
14 #include <GL/glew.h> /* for GL_UNSIGNED_SHORT_5_6_5 */
15 #include "glut_wrap.h"
18 static int ImgWidth, ImgHeight;
19 static int WinWidth, WinHeight;
21 static int APosX, APosY; /* simple drawpixels */
22 static int BPosX, BPosY; /* read/draw pixels */
23 int MouseButton, MouseY, MouseX; /* mouse control */
24 float x0offset = 0.0f; /* for line translation */
25 float y0offset = 0.0f;
26 float x1offset = 0.0f;
27 float y1offset = 0.0f;
28 float width = 1.0f;
30 struct Line{
31 float x0;
32 float y0;
33 float x1;
34 float y1;
37 #define STEP 16 /* subpixel resolution 1/STEP */
38 #define SIZE 128 /* of non-zoomed drawing region */
39 #define ZOOM 32 /* scale factor for zooming */
41 struct Line line;
42 static GLboolean DrawFront = GL_FALSE;
43 GLushort TempImage[SIZE][SIZE]; /* original 128 by 128 pixel image */
44 GLushort myImage[SIZE*ZOOM][SIZE*ZOOM]; /* zoom by a factor of 32 */
46 static GLenum ReadFormat = GL_RGB;
47 static GLenum ReadType = GL_UNSIGNED_SHORT_5_6_5;
49 static void
50 Reset( void )
52 APosX = 8; APosY = 24;
53 MouseX = 8; MouseY = 24;
54 BPosX = APosX + ImgWidth + 40; BPosY = 24;
58 static void
59 PrintString(const char *s)
61 while (*s) {
62 glutBitmapCharacter(GLUT_BITMAP_8_BY_13, (int) *s);
63 s++;
67 static void
68 drawzoomline(int x0, int y0, int x1, int y1, GLushort color)
70 /* Use the Bresenham Line Algorithm here. */
71 GLboolean steep = (abs(y1 - y0) > abs(x1 - x0));
73 int deltax;
74 int deltay;
75 float error;
76 float deltaerr;
77 int ystep;
78 int x, y;
80 if (steep) {
81 int temp0 = x0;
82 int temp1 = x1;
83 x0 = y0;
84 y0 = temp0;
85 x1 = y1;
86 y1 = temp1;
88 if (x0 > x1) {
89 int tem0 = x0;
90 int tem1 = y0;
91 x0 = x1;
92 x1 = tem0;
93 y0 = y1;
94 y1 = tem1;
97 deltax = x1 - x0;
98 deltay = abs(y1 - y0);
99 error = 0.0;
100 deltaerr = (float)deltay / (float)deltax;
101 y = y0;
103 if (y0 < y1)
104 ystep = 1;
105 else
106 ystep = -1;
108 for (x = x0; x < x1; x++) {
109 if (y>0 && x>0) {
110 if (!steep) {
111 myImage[y][x] = color;
112 myImage[y+1][x] = color;
114 else {
115 myImage[x][y] = color;
116 myImage[x+1][y] = color;
119 error = error + deltaerr;
120 if (error >= 0.5) {
121 y = y + ystep;
122 error = error - 1.0;
127 static void
128 drawline(float xf0, float yf0, float xf1, float yf1, GLushort color)
130 /* map line endpoints on to relevant pixel grids */
131 int x0 = xf0 * ZOOM;
132 int y0 = yf0 * ZOOM;
133 int x1 = xf1 * ZOOM;
134 int y1 = yf1 * ZOOM;
136 drawzoomline(x0, y0, x1, y1, color);
139 static void
140 plot(int x, int y, GLushort color)
142 int i, j;
144 for (i=0; i<ZOOM; i++) {
145 for (j=0; j<ZOOM; j++) {
146 if (i == 0 || j == 0) {
147 /* draws the gridlines, use top-left rule */
148 myImage[x*ZOOM+i][y*ZOOM+j] = 0;
150 else if ((i >= 13 && i <= 19 && j == 16 ) || (j >= 13 && j <= 19 && i == 16) ){
151 /* draws the pixel centre */
152 myImage[x*ZOOM+i][y*ZOOM+j] = 0;
154 else if ( (i + j == 15) || fabsf(i - j) == 16 || (i + j == 47) ){
155 /* draws the pixel diamond, to test diamond exit rule */
156 myImage[x*ZOOM+i][y*ZOOM+j] = 0;
158 else
159 myImage[x*ZOOM+i][y*ZOOM+j]= color;
165 static void
166 drawMagnifiedView(void)
168 float halfwidth = width/2;
169 int i, j;
171 /* Sets up pixel grid for each pixel
173 for (i=0; i<128; i++){
174 for (j=0; j<128; j++){
175 plot(i, j, TempImage[i][j]);
179 /* Draws the actual line on zoomed version */
180 drawline(line.x0+x0offset+APosX-MouseX, line.y0+y0offset+APosY-MouseY,
181 line.x1+x1offset+APosX-MouseX, line.y1+y1offset+APosY-MouseY, 0);
183 /* Draws bounding line area */
184 if (fabsf(line.x0 + x0offset - line.x1 - x1offset) >=
185 fabsf(line.y0 + y0offset - line.y1 - y1offset)) {
186 /* X-MAJOR line */
187 drawline(line.x0+x0offset+APosX-MouseX, line.y0+y0offset+APosY-MouseY+halfwidth,
188 line.x1+x1offset+APosX-MouseX, line.y1+y1offset+APosY-MouseY+halfwidth, 0xffff);
189 drawline(line.x0+x0offset+APosX-MouseX, line.y0+y0offset+APosY-MouseY-halfwidth,
190 line.x1+x1offset+APosX-MouseX, line.y1+y1offset+APosY-MouseY-halfwidth, 0xffff);
191 drawline(line.x0+x0offset+APosX-MouseX, line.y0+y0offset+APosY-MouseY+halfwidth,
192 line.x0+x0offset+APosX-MouseX, line.y0+y0offset+APosY-MouseY-halfwidth, 0xffff);
193 drawline(line.x1+x1offset+APosX-MouseX, line.y1+y1offset+APosY-MouseY+halfwidth,
194 line.x1+x1offset+APosX-MouseX, line.y1+y1offset+APosY-MouseY-halfwidth, 0xffff);
196 else {
197 /* Y-MAJOR line */
198 drawline(line.x0+x0offset+APosX-MouseX+halfwidth, line.y0+y0offset+APosY-MouseY,
199 line.x1+x1offset+APosX-MouseX+halfwidth, line.y1+y1offset+APosY-MouseY, 0xffff);
200 drawline(line.x0+x0offset+APosX-MouseX-halfwidth, line.y0+y0offset+APosY-MouseY,
201 line.x1+x1offset+APosX-MouseX-halfwidth, line.y1+y1offset+APosY-MouseY, 0xffff);
202 drawline(line.x0+x0offset+APosX-MouseX+halfwidth, line.y0+y0offset+APosY-MouseY,
203 line.x0+x0offset+APosX-MouseX-halfwidth, line.y0+y0offset+APosY-MouseY, 0xffff);
204 drawline(line.x1+x1offset+APosX-MouseX+halfwidth, line.y1+y1offset+APosY-MouseY,
205 line.x1+x1offset+APosX-MouseX-halfwidth, line.y1+y1offset+APosY-MouseY, 0xffff);
209 static void
210 Display( void )
212 float z = 0;
214 glClearColor(.3, .3, .3, 1);
215 glClear( GL_COLOR_BUFFER_BIT );
217 /* draw original image */
219 glViewport(APosX, APosY, ImgWidth, ImgHeight);
220 glMatrixMode( GL_PROJECTION );
221 glLoadIdentity();
222 /* transformation to match the pixel array */
223 glOrtho(0, ImgWidth, 0, ImgHeight, -1.0, 1.0);
224 glDisable(GL_CULL_FACE);
226 /* Blue background
228 glBegin(GL_POLYGON);
229 glColor3f(.5,.5,1);
230 glVertex3f(0, 0, z);
231 glVertex3f(0, 150, z);
232 glVertex3f(150, 150, z);
233 glVertex3f(150, 0, z);
234 glEnd();
236 /* Original line
238 glLineWidth(width);
239 glBegin(GL_LINES);
240 glColor3f(.8,0,0);
241 glVertex3f(line.x0+x0offset, line.y0+y0offset, z);
242 glColor3f(0,.9,0);
243 glVertex3f(line.x1+x1offset, line.y1+y1offset, z);
244 glEnd();
247 glColor3f(1,1,1);
248 glViewport( 0, 0, WinWidth, WinHeight );
249 glMatrixMode( GL_PROJECTION );
250 glLoadIdentity();
251 glOrtho( 0.0, WinWidth, 0.0, WinHeight, -1.0, 1.0 );
253 /* might try alignment=4 here for testing */
254 glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
255 glPixelStorei(GL_PACK_ALIGNMENT, 1);
257 /* Legend */
258 glLineWidth(1.0);
259 glBegin(GL_LINE_STRIP);
260 glVertex3f(590, 800, 0);
261 glVertex3f(590, 670, 0);
262 glVertex3f(990, 670, 0);
263 glVertex3f(990, 800, 0);
264 glVertex3f(590, 800, 0);
265 glEnd();
267 glRasterPos2i(600, 780);
268 PrintString("Key:");
269 glRasterPos2i(600, 760);
270 PrintString(" Change linewidth: v/b");
271 glRasterPos2i(600, 740);
272 PrintString(" Move whole line: UP/DOWN/LEFT/RIGHT arrow keys");
273 glRasterPos2i(600, 720);
274 PrintString(" Move endpoint: i/k/j/l");
275 glRasterPos2i(600, 700);
276 PrintString(" Move startpoint: w/s/a/d");
277 glRasterPos2i(600, 680);
278 PrintString(" Change view: drag/click mouse");
280 glRasterPos2i(8, ImgHeight+30);
281 PrintString("Zoom Pixel Test");
283 glRasterPos2i(APosX, 5);
284 PrintString("Original");
286 /* do readpixels, drawpixels */
287 glRasterPos2i(BPosX, 5);
288 PrintString("Read/DrawPixels");
290 /* clear the temporary image to white (helpful for debugging */
291 memset(TempImage, 255, sizeof TempImage);
293 /* Read pixels from the color buffer */
294 glReadPixels(MouseX, MouseY, ImgWidth, ImgHeight,
295 ReadFormat, ReadType, TempImage);
297 glRasterPos2i(BPosX, BPosY);
298 glDisable(GL_DITHER);
299 drawMagnifiedView();
301 /* Write pixels to the frame buffer */
302 glDrawPixels(ImgWidth*5, ImgHeight*5, ReadFormat, ReadType, myImage);
304 if (!DrawFront)
305 glutSwapBuffers();
306 else
307 glFinish();
311 static void
312 Reshape( int width, int height )
314 WinWidth = width;
315 WinHeight = height;
317 glViewport( 0, 0, width, height );
318 glMatrixMode( GL_PROJECTION );
319 glLoadIdentity();
320 glOrtho( 0.0, width, 0.0, height, -1.0, 1.0 );
321 glMatrixMode( GL_MODELVIEW );
322 glLoadIdentity();
326 static void
327 Key( unsigned char key, int x, int y)
329 switch (key) {
330 case 'w':
331 y0offset += 1.0/(float)STEP;
332 break;
333 case 's':
334 y0offset -= 1.0/(float)STEP;
335 break;
336 case 'd':
337 x0offset += 1.0/(float)STEP;
338 break;
339 case 'a':
340 x0offset -= 1.0/(float)STEP;
341 break;
342 case 'i':
343 y1offset += 1.0/(float)STEP;
344 break;
345 case 'k':
346 y1offset -= 1.0/(float)STEP;
347 break;
348 case 'l':
349 x1offset += 1.0/(float)STEP;
350 break;
351 case 'j':
352 x1offset -= 1.0/(float)STEP;
353 break;
354 case 'b':
355 width += 1.0/(float) STEP;
356 printf("width = %f\n", width);
357 break;
358 case 'v':
359 width -= 1.0/(float) STEP;
360 printf("width = %f\n", width);
361 break;
362 case 27:
363 exit(1);
364 break;
365 default:
366 return;
368 glutPostRedisplay();
371 static void
372 SpecialKey( int k, int x, int y)
374 switch (k) {
375 case GLUT_KEY_UP:
376 y0offset += 1.0/(float)STEP;
377 y1offset += 1.0/(float)STEP;
378 break;
379 case GLUT_KEY_DOWN:
380 y0offset -= 1.0/(float)STEP;
381 y1offset -= 1.0/(float)STEP;
382 break;
383 case GLUT_KEY_RIGHT:
384 x0offset += 1.0/(float)STEP;
385 x1offset += 1.0/(float)STEP;
386 break;
387 case GLUT_KEY_LEFT:
388 x0offset -= 1.0/(float)STEP;
389 x1offset -= 1.0/(float)STEP;
390 break;
391 default:
392 return;
394 glutPostRedisplay();
397 static void
398 Mouse(int button, int state, int x, int y)
400 /* if left mouse button is pressed and dragged
401 * then change screen view
403 if (state == GLUT_DOWN &&
404 button == GLUT_LEFT_BUTTON &&
405 x < 160 &&
406 y > WinHeight-180)
408 MouseX = x;
409 MouseY = WinHeight - y;
411 glutPostRedisplay();
414 static void
415 processMouseMotion(int x, int y)
417 MouseX = x;
418 MouseY = WinHeight - y;
419 glutPostRedisplay();
422 static void
423 Init(void)
425 printf("GL_VERSION = %s\n", (char *) glGetString(GL_VERSION));
426 printf("GL_RENDERER = %s\n", (char *) glGetString(GL_RENDERER));
428 ImgWidth=128;
429 ImgHeight=128;
430 x0offset = 0;
431 y0offset = 0;
432 x1offset = 0;
433 y1offset = 0;
435 line.x0 = 2;
436 line.y0 = 2;
437 line.x1 = 15;
438 line.y1 = 15;
439 glutSetCursor(GLUT_CURSOR_CROSSHAIR);
441 glPixelStorei(GL_UNPACK_ROW_LENGTH, ImgWidth*ZOOM);
442 glPixelStorei(GL_PACK_ROW_LENGTH, ImgWidth);
444 Reset();
449 main( int argc, char *argv[] )
451 glutInitWindowSize( 1000, 800 );
452 glutInit( &argc, argv );
454 glutInitDisplayMode( GLUT_RGB | GLUT_DOUBLE );
455 glutCreateWindow(argv[0]);
456 Init();
457 glutReshapeFunc( Reshape );
458 glutKeyboardFunc (Key);
459 glutSpecialFunc(SpecialKey);
460 glutDisplayFunc( Display );
462 glutMouseFunc(Mouse);
463 glutMotionFunc(processMouseMotion);
465 glutMainLoop();
466 return 0;