1 // Calls glDrawElements() the number of times specified by
2 // ITERATIONS. Should draw a checkerboard on the screen after
3 // a few seconds.
4 //
5 // Ported from a Java version by Google.
6
7 #include <EGL/egl.h>
8 #include <GLES/gl.h>
9 #include <GLES/glext.h>
10
11 #include <WindowSurface.h>
12 #include <EGLUtils.h>
13
14 #include <stdio.h>
15 #include <stdlib.h>
16 #include <math.h>
17
18 using namespace android;
19
20 EGLDisplay eglDisplay;
21 EGLSurface eglSurface;
22 EGLContext eglContext;
23 GLuint texture;
24
25 #define FIXED_ONE 0x10000
26 #define ITERATIONS 50
27
28 int init_gl_surface(const WindowSurface&);
29 void free_gl_surface(void);
30 void init_scene(void);
31 void render(int quads);
32 void create_texture(void);
33 int readTimer(void);
34
gluLookAt(float eyeX,float eyeY,float eyeZ,float centerX,float centerY,float centerZ,float upX,float upY,float upZ)35 static void gluLookAt(float eyeX, float eyeY, float eyeZ,
36 float centerX, float centerY, float centerZ, float upX, float upY,
37 float upZ)
38 {
39 // See the OpenGL GLUT documentation for gluLookAt for a description
40 // of the algorithm. We implement it in a straightforward way:
41
42 float fx = centerX - eyeX;
43 float fy = centerY - eyeY;
44 float fz = centerZ - eyeZ;
45
46 // Normalize f
47 float rlf = 1.0f / sqrtf(fx*fx + fy*fy + fz*fz);
48 fx *= rlf;
49 fy *= rlf;
50 fz *= rlf;
51
52 // Normalize up
53 float rlup = 1.0f / sqrtf(upX*upX + upY*upY + upZ*upZ);
54 upX *= rlup;
55 upY *= rlup;
56 upZ *= rlup;
57
58 // compute s = f x up (x means "cross product")
59
60 float sx = fy * upZ - fz * upY;
61 float sy = fz * upX - fx * upZ;
62 float sz = fx * upY - fy * upX;
63
64 // compute u = s x f
65 float ux = sy * fz - sz * fy;
66 float uy = sz * fx - sx * fz;
67 float uz = sx * fy - sy * fx;
68
69 float m[16] ;
70 m[0] = sx;
71 m[1] = ux;
72 m[2] = -fx;
73 m[3] = 0.0f;
74
75 m[4] = sy;
76 m[5] = uy;
77 m[6] = -fy;
78 m[7] = 0.0f;
79
80 m[8] = sz;
81 m[9] = uz;
82 m[10] = -fz;
83 m[11] = 0.0f;
84
85 m[12] = 0.0f;
86 m[13] = 0.0f;
87 m[14] = 0.0f;
88 m[15] = 1.0f;
89
90 glMultMatrixf(m);
91 glTranslatef(-eyeX, -eyeY, -eyeZ);
92 }
93
main(int argc,char ** argv)94 int main(int argc, char **argv)
95 {
96 int q;
97 int start, end;
98
99 printf("Initializing EGL...\n");
100
101 WindowSurface windowSurface;
102 if(!init_gl_surface(windowSurface))
103 {
104 printf("GL initialisation failed - exiting\n");
105 return 0;
106 }
107
108 init_scene();
109
110 create_texture();
111
112 printf("Start test...\n");
113
114 render(argc==2 ? atoi(argv[1]) : ITERATIONS);
115
116 free_gl_surface();
117
118 return 0;
119 }
120
init_gl_surface(const WindowSurface & windowSurface)121 int init_gl_surface(const WindowSurface& windowSurface)
122 {
123 EGLint numConfigs = 1;
124 EGLConfig myConfig = {0};
125 EGLint attrib[] =
126 {
127 EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
128 EGL_DEPTH_SIZE, 16,
129 EGL_NONE
130 };
131
132 if ( (eglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY)) == EGL_NO_DISPLAY )
133 {
134 printf("eglGetDisplay failed\n");
135 return 0;
136 }
137
138 if ( eglInitialize(eglDisplay, NULL, NULL) != EGL_TRUE )
139 {
140 printf("eglInitialize failed\n");
141 return 0;
142 }
143
144 EGLNativeWindowType window = windowSurface.getSurface();
145 EGLUtils::selectConfigForNativeWindow(eglDisplay, attrib, window, &myConfig);
146
147 if ( (eglSurface = eglCreateWindowSurface(eglDisplay, myConfig,
148 window, 0)) == EGL_NO_SURFACE )
149 {
150 printf("eglCreateWindowSurface failed\n");
151 return 0;
152 }
153
154 if ( (eglContext = eglCreateContext(eglDisplay, myConfig, 0, 0)) == EGL_NO_CONTEXT )
155 {
156 printf("eglCreateContext failed\n");
157 return 0;
158 }
159
160 if ( eglMakeCurrent(eglDisplay, eglSurface, eglSurface, eglContext) != EGL_TRUE )
161 {
162 printf("eglMakeCurrent failed\n");
163 return 0;
164 }
165
166 return 1;
167 }
168
free_gl_surface(void)169 void free_gl_surface(void)
170 {
171 if (eglDisplay != EGL_NO_DISPLAY)
172 {
173 eglMakeCurrent( EGL_NO_DISPLAY, EGL_NO_SURFACE,
174 EGL_NO_SURFACE, EGL_NO_CONTEXT );
175 eglDestroyContext( eglDisplay, eglContext );
176 eglDestroySurface( eglDisplay, eglSurface );
177 eglTerminate( eglDisplay );
178 eglDisplay = EGL_NO_DISPLAY;
179 }
180 }
181
init_scene(void)182 void init_scene(void)
183 {
184 glDisable(GL_DITHER);
185 glEnable(GL_CULL_FACE);
186
187 float ratio = 320.0f / 480.0f;
188 glViewport(0, 0, 320, 480);
189
190 glMatrixMode(GL_PROJECTION);
191 glLoadIdentity();
192 glFrustumf(-ratio, ratio, -1, 1, 1, 10);
193
194 glMatrixMode(GL_MODELVIEW);
195 glLoadIdentity();
196 gluLookAt(
197 0, 0, 3, // eye
198 0, 0, 0, // center
199 0, 1, 0); // up
200
201 glEnable(GL_TEXTURE_2D);
202 glEnableClientState(GL_VERTEX_ARRAY);
203 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
204 }
205
create_texture(void)206 void create_texture(void)
207 {
208 const unsigned int on = 0xff0000ff;
209 const unsigned int off = 0xffffffff;
210 const unsigned int pixels[] =
211 {
212 on, off, on, off, on, off, on, off,
213 off, on, off, on, off, on, off, on,
214 on, off, on, off, on, off, on, off,
215 off, on, off, on, off, on, off, on,
216 on, off, on, off, on, off, on, off,
217 off, on, off, on, off, on, off, on,
218 on, off, on, off, on, off, on, off,
219 off, on, off, on, off, on, off, on,
220 };
221 glGenTextures(1, &texture);
222 glBindTexture(GL_TEXTURE_2D, texture);
223 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 8, 8, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
224 glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
225 glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
226 glTexEnvx(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
227 }
228
render(int quads)229 void render(int quads)
230 {
231 int i, j;
232
233 const GLfloat vertices[] = {
234 -1, -1, 0,
235 1, -1, 0,
236 1, 1, 0,
237 -1, 1, 0
238 };
239
240 const GLfixed texCoords[] = {
241 0, 0,
242 FIXED_ONE, 0,
243 FIXED_ONE, FIXED_ONE,
244 0, FIXED_ONE
245 };
246
247 const GLushort quadIndices[] = { 0, 1, 2, 0, 2, 3 };
248
249
250 GLushort* indices = (GLushort*)malloc(quads*sizeof(quadIndices));
251 for (i=0 ; i<quads ; i++)
252 memcpy(indices+(sizeof(quadIndices)/sizeof(indices[0]))*i, quadIndices, sizeof(quadIndices));
253
254 glVertexPointer(3, GL_FLOAT, 0, vertices);
255 glTexCoordPointer(2, GL_FIXED, 0, texCoords);
256
257 // make sure to do a couple eglSwapBuffers to make sure there are
258 // no problems with the very first ones (who knows)
259 glClearColor(0.4, 0.4, 0.4, 0.4);
260 glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
261 eglSwapBuffers(eglDisplay, eglSurface);
262 glClearColor(0.6, 0.6, 0.6, 0.6);
263 glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
264 eglSwapBuffers(eglDisplay, eglSurface);
265 glClearColor(1.0, 1.0, 1.0, 1.0);
266
267 for (j=0 ; j<10 ; j++) {
268 printf("loop %d / 10 (%d quads / loop)\n", j, quads);
269
270 int nelem = sizeof(quadIndices)/sizeof(quadIndices[0]);
271 glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
272 glDrawElements(GL_TRIANGLES, nelem*quads, GL_UNSIGNED_SHORT, indices);
273 eglSwapBuffers(eglDisplay, eglSurface);
274 }
275
276 free(indices);
277 }
278
279