initial commit
[glpixels] / glpixels.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <math.h>
4 #include <assert.h>
5 #include <GL/glut.h>
6
7 enum {
8         MODE_VERTEX,
9         MODE_DRAWPIX,
10         MODE_TEXQUAD,
11         MODE_TEXTRI,
12
13         NUM_MODES
14 };
15
16 int init(void);
17 void display(void);
18 void idle(void);
19 void reshape(int x, int y);
20 void keyb(unsigned char key, int x, int y);
21
22 int win_width, win_height;
23 int max_xscroll, max_yscroll;
24
25 #define IMG_W   1024
26 #define IMG_H   1024
27 unsigned int img[IMG_W * IMG_H];
28
29 int mode = MODE_DRAWPIX;
30
31 int main(int argc, char **argv)
32 {
33         glutInit(&argc, argv);
34         glutInitWindowSize(800, 600);
35         glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
36         glutCreateWindow("GL pixel drawing methods");
37
38         glutDisplayFunc(display);
39         glutReshapeFunc(reshape);
40         glutKeyboardFunc(keyb);
41         glutIdleFunc(idle);
42
43         if(init() == -1) {
44                 return 1;
45         }
46         glutMainLoop();
47         return 0;
48 }
49
50
51 int init(void)
52 {
53         int i, j, xor, r, g, b;
54         unsigned int *ptr;
55         unsigned int tex;
56
57         ptr = img;
58         for(i=0; i<IMG_H; i++) {
59                 for(j=0; j<IMG_W; j++) {
60                         xor = i ^ j;
61                         r = (xor >> 1) & 0xff;
62                         g = xor & 0xff;
63                         b = (xor << 1) & 0xff;
64                         *ptr++ = r | (g << 8) | (b << 16);
65                 }
66         }
67
68         glPixelStorei(GL_UNPACK_ROW_LENGTH, IMG_W);
69
70         win_width = glutGet(GLUT_WINDOW_WIDTH);
71         win_height = glutGet(GLUT_WINDOW_HEIGHT);
72
73         glGenTextures(1, &tex);
74         glBindTexture(GL_TEXTURE_2D, tex);
75         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
76         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
77         glTexImage2D(GL_TEXTURE_2D, 1, GL_RGBA, win_width, win_height, 1, GL_RGBA, GL_UNSIGNED_BYTE, 0);
78
79         return 0;
80 }
81
82 void display(void)
83 {
84         unsigned int tm = glutGet(GLUT_ELAPSED_TIME);
85         float t = tm / 256.0f;
86         int xoffs = (int)((sin(t) * 0.5f + 0.5f) * max_xscroll);
87         int yoffs = (int)((cos(t) * 0.5f + 0.5f) * max_yscroll);
88         unsigned int *start;
89
90         switch(mode) {
91         case MODE_VERTEX:
92                 /* draw with points */
93                 break;
94
95         case MODE_DRAWPIX:
96                 /* draw with glDrawPixels */
97                 start = img + yoffs * IMG_W + xoffs;
98                 glDrawPixels(win_width, win_height, GL_RGBA, GL_UNSIGNED_BYTE, start);
99                 break;
100
101         case MODE_TEXQUAD:
102                 /* draw with textured quad */
103                 break;
104
105         case MODE_TEXTRI:
106                 /* draw with textured triangle */
107                 break;
108         }
109
110         glutSwapBuffers();
111         assert(glGetError() == GL_NO_ERROR);
112 }
113
114 void idle(void)
115 {
116         glutPostRedisplay();
117 }
118
119 void reshape(int x, int y)
120 {
121         glViewport(0, 0, x, y);
122
123         win_width = x;
124         win_height = y;
125         max_xscroll = IMG_W - win_width;
126         max_yscroll = IMG_H - win_height;
127         if(max_xscroll < 0) max_xscroll = 0;
128         if(max_yscroll < 0) max_yscroll = 0;
129 }
130
131 void keyb(unsigned char key, int x, int y)
132 {
133         switch(key) {
134         case 27:
135                 exit(0);
136
137         case ' ':
138                 mode = (mode + 1) % NUM_MODES;
139                 break;
140
141         default:
142                 break;
143         }
144 }