1919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich// OpenGL ES 1.0 code
2919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
3919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich#include <nativehelper/jni.h>
4919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich#define LOG_TAG "GLJNI gl_code.cpp"
5e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich#include <utils/Log.h>
6e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
7919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich#include <GLES/gl.h>
8919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
9e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich#include <stdio.h>
10e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
11919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich#include <stdlib.h>
12919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich#include <math.h>
13e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
14e5810d1f98557cbcf0f533215b1d76724b182e79Jack PalevichGLuint texture;
15e5810d1f98557cbcf0f533215b1d76724b182e79Jack PalevichGLfloat background;
16e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
17e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich#define FIXED_ONE 0x10000
18919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
19919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevichstatic void printGLString(const char *name, GLenum s) {
20919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    const char *v = (const char *) glGetString(s);
21a19954ab377b46dbcb9cbe8a6ab6d458f2e32bcaSteve Block    ALOGI("GL %s = %s\n", name, v);
22919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich}
23919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
24919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevichstatic void gluLookAt(float eyeX, float eyeY, float eyeZ,
25919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich        float centerX, float centerY, float centerZ, float upX, float upY,
26919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich        float upZ)
27919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich{
28919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    // See the OpenGL GLUT documentation for gluLookAt for a description
29919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    // of the algorithm. We implement it in a straightforward way:
30919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
31919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float fx = centerX - eyeX;
32919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float fy = centerY - eyeY;
33919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float fz = centerZ - eyeZ;
34919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
35919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    // Normalize f
36919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float rlf = 1.0f / sqrtf(fx*fx + fy*fy + fz*fz);
37919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    fx *= rlf;
38919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    fy *= rlf;
39919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    fz *= rlf;
40919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
41919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    // Normalize up
42919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float rlup = 1.0f / sqrtf(upX*upX + upY*upY + upZ*upZ);
43919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    upX *= rlup;
44919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    upY *= rlup;
45919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    upZ *= rlup;
46919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
47919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    // compute s = f x up (x means "cross product")
48919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
49919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float sx = fy * upZ - fz * upY;
50919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float sy = fz * upX - fx * upZ;
51919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float sz = fx * upY - fy * upX;
52919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
53919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    // compute u = s x f
54919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float ux = sy * fz - sz * fy;
55919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float uy = sz * fx - sx * fz;
56919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float uz = sx * fy - sy * fx;
57919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
58919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float m[16] ;
59919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[0] = sx;
60919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[1] = ux;
61919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[2] = -fx;
62919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[3] = 0.0f;
63919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
64919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[4] = sy;
65919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[5] = uy;
66919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[6] = -fy;
67919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[7] = 0.0f;
68919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
69919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[8] = sz;
70919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[9] = uz;
71919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[10] = -fz;
72919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[11] = 0.0f;
73919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
74919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[12] = 0.0f;
75919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[13] = 0.0f;
76919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[14] = 0.0f;
77919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    m[15] = 1.0f;
78919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
79919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glMultMatrixf(m);
80919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glTranslatef(-eyeX, -eyeY, -eyeZ);
81919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich}
82919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
83e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevichvoid init_scene(int width, int height)
84919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich{
85919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    printGLString("Version", GL_VERSION);
86919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    printGLString("Vendor", GL_VENDOR);
87919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    printGLString("Renderer", GL_RENDERER);
88e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    printGLString("Extensions", GL_EXTENSIONS);
89e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
90919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glDisable(GL_DITHER);
91919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glEnable(GL_CULL_FACE);
92919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
93919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    float ratio = width / height;
94919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glViewport(0, 0, width, height);
95919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
96919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glMatrixMode(GL_PROJECTION);
97919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glLoadIdentity();
98e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glFrustumf(-ratio, ratio, -1, 1, 1, 10);
99919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
100e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glMatrixMode(GL_MODELVIEW);
101919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
102919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glLoadIdentity();
103919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    gluLookAt(
104919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            0, 0, 3,  // eye
105919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            0, 0, 0,  // center
106919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            0, 1, 0); // up
107e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
108e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glEnable(GL_TEXTURE_2D);
109e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glEnableClientState(GL_VERTEX_ARRAY);
110919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
111e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich}
112e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
113e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevichvoid create_texture()
114e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich{
115919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    const unsigned int on = 0xff0000ff;
116919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    const unsigned int off = 0xffffffff;
117919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    const unsigned int pixels[] =
118919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    {
119919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            on, off, on, off, on, off, on, off,
120919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            off, on, off, on, off, on, off, on,
121919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            on, off, on, off, on, off, on, off,
122919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            off, on, off, on, off, on, off, on,
123919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            on, off, on, off, on, off, on, off,
124919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            off, on, off, on, off, on, off, on,
125919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            on, off, on, off, on, off, on, off,
126919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich            off, on, off, on, off, on, off, on,
127e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    };
128e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
129e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glGenTextures(1, &texture);
130e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glBindTexture(GL_TEXTURE_2D, texture);
131e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 8, 8, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
132e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
133e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glTexParameterx(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
134e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glTexEnvx(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
135919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich}
136919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
137919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevichextern "C" {
138919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    JNIEXPORT void JNICALL Java_com_android_gljni_GLJNILib_init(JNIEnv * env, jobject obj,  jint width, jint height);
139919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    JNIEXPORT void JNICALL Java_com_android_gljni_GLJNILib_step(JNIEnv * env, jobject obj);
140e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    JNIEXPORT void JNICALL Java_com_android_gljni_GLJNILib_changeBackground(JNIEnv * env, jobject obj);
141919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich};
142919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
143e5810d1f98557cbcf0f533215b1d76724b182e79Jack PalevichJNIEXPORT void JNICALL Java_com_android_gljni_GLJNILib_init(JNIEnv * env, jobject obj,  jint width, jint height)
144e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich{
145e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    init_scene(width, height);
146e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    create_texture();
147e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich}
148e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
149e5810d1f98557cbcf0f533215b1d76724b182e79Jack PalevichJNIEXPORT void JNICALL Java_com_android_gljni_GLJNILib_step(JNIEnv * env, jobject obj)
150e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich{
151e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    const GLfloat vertices[] = {
152e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich            -1,  -1,  0,
153e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich             1,  -1,  0,
154e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich             1,   1,  0,
155e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich            -1,   1,  0
156e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    };
157e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich
158e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    const GLfixed texCoords[] = {
159e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich            0,            0,
160e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich            FIXED_ONE,    0,
161e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich            FIXED_ONE,    FIXED_ONE,
162e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich            0,            FIXED_ONE
163e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    };
164919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
165e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    const GLushort quadIndices[] = { 0, 1, 2,  0, 2, 3 };
166e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glVertexPointer(3, GL_FLOAT, 0, vertices);
167e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glTexCoordPointer(2, GL_FIXED, 0, texCoords);
168919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
169919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    int nelem = sizeof(quadIndices)/sizeof(quadIndices[0]);
170919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    static float grey;
171919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    grey += 0.01f;
172919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    if (grey > 1.0f) {
173919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich        grey = 0.0f;
174919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    }
175e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glClearColor(background, grey, grey, 1.0f);
176919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich    glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
177e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    glDrawElements(GL_TRIANGLES, nelem, GL_UNSIGNED_SHORT, quadIndices);
178e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich}
179919583553781f1e1885fa17f76d54008ebeca3c1Jack Palevich
180e5810d1f98557cbcf0f533215b1d76724b182e79Jack PalevichJNIEXPORT void JNICALL Java_com_android_gljni_GLJNILib_changeBackground(JNIEnv * env, jobject obj)
181e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich{
182e5810d1f98557cbcf0f533215b1d76724b182e79Jack Palevich    background = 1.0f - background;
1837efc2fc955087663f17848913c93835634bc2de8Jae-Hyung Ahn}
184