+#define glVertexPointerd(nc, s, p, nv) glVertexPointer(nc, GL_DOUBLE, s, p)
+#define glDrawElementsi(type, count, start) glDrawElements(type, count, GL_UNSIGNED_INT, start)
+
+#endif
+
+#if defined(__ANDROID__)
+ static EGLDisplay eglDisplay;
+ static EGLSurface eglSurface;
+ static EGLContext eglContext;
+ static int eglWidth, eglHeight;
+
+ static bool egl_init_display(ANativeWindow* window)
+ {
+ const EGLint attribs[] =
+ {
+ EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
+ EGL_BLUE_SIZE, 8,
+ EGL_GREEN_SIZE, 8,
+ EGL_RED_SIZE, 8,
+ EGL_DEPTH_SIZE, 16, //24,
+ /*EGL_SAMPLE_BUFFERS, 1,
+ EGL_SAMPLES, 0, //2,*/
+ EGL_NONE
+ };
+ EGLint w, h, format;
+ EGLint numConfigs;
+ EGLConfig config;
+ EGLSurface surface;
+ EGLContext context;
+
+ EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
+ eglInitialize(display, 0, 0);
+ eglChooseConfig(display, attribs, &config, 1, &numConfigs);
+ eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format);
+
+ surface = eglCreateWindowSurface(display, config, window, null);
+ context = eglCreateContext(display, config, null, null);
+
+ if(!eglMakeCurrent(display, surface, surface, context))
+ return false;
+
+ eglQuerySurface(display, surface, EGL_WIDTH, &w);
+ eglQuerySurface(display, surface, EGL_HEIGHT, &h);
+
+ eglDisplay = display;
+ eglContext = context;
+ eglSurface = surface;
+ eglWidth = w;
+ eglHeight = h;
+
+ glEnableClientState(GL_VERTEX_ARRAY);
+ /*
+ // Initialize GL state.
+ glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST);
+ glEnable(GL_CULL_FACE);
+ glShadeModel(GL_SMOOTH);
+ glDisable(GL_DEPTH_TEST);
+ */
+ glDisable(GL_CULL_FACE);
+ glDisable(GL_DEPTH_TEST);
+
+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+ glEnable(GL_BLEND);
+
+ matrixStack[0][0].Identity();
+ matrixStack[1][0].Identity();
+ matrixStack[2][0].Identity();
+
+ glesMatrixMode(GL_MODELVIEW);
+ glScaled(1.0, 1.0, -1.0);
+ glesMatrixMode(GL_PROJECTION);
+ glShadeModel(GL_FLAT);
+
+ glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL, GL_SEPARATE_SPECULAR_COLOR);
+ glFogi(GL_FOG_MODE, GL_EXP);
+ glFogf(GL_FOG_DENSITY, 0);
+ glEnable(GL_NORMALIZE);
+ glDepthFunc(GL_LESS);
+ glClearDepth(1.0);
+ glDisable(GL_MULTISAMPLE_ARB);
+
+ glViewport(0,0,w,h);
+ glesLoadIdentity();
+ glOrtho(0,w,h,0,0.0,1.0);
+
+ currentVertexBuffer = 0;
+ return true;
+ }
+
+ static void egl_term_display()
+ {
+ if(stippleTexture)
+ {
+ glDeleteTextures(1, &stippleTexture);
+ stippleTexture = 0;
+ }
+ if(eglDisplay != EGL_NO_DISPLAY)
+ {
+ eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
+ if(eglContext != EGL_NO_CONTEXT)
+ eglDestroyContext(eglDisplay, eglContext);
+ if(eglSurface != EGL_NO_SURFACE)
+ eglDestroySurface(eglDisplay, eglSurface);
+ eglTerminate(eglDisplay);
+ }
+ eglDisplay = EGL_NO_DISPLAY;
+ eglContext = EGL_NO_CONTEXT;
+ eglSurface = EGL_NO_SURFACE;
+ }
+
+#endif
+
+// OpenGL Immediate Mode Porting Kit
+static int beginCount;
+static int vertexCount;
+static int normalCount;
+static float *vertexPointer;
+static float *normalPointer;
+static GLenum beginMode = -1;
+static uint beginBufferSize, normalBufferSize;
+static int numVertexCoords = 2;
+static bool vertexColorValues = false;
+static int vertexStride = 4;
+static int vertexOffset = 2;
+
+public void glesRecti(int a, int b, int c, int d)
+{
+ glBegin(GL_QUADS);
+ glVertex2i(a, b);
+ glVertex2i(a, d);
+ glVertex2i(c, d);
+ glVertex2i(c, b);
+ glEnd();
+}
+
+public void glesBegin(GLenum mode)
+{
+ beginMode = mode;
+ beginCount = 0;
+ vertexCount = 0;
+ vertexColorValues = false;
+ vertexOffset = 2;
+ vertexStride = 4;
+ numVertexCoords = 2;
+
+ if(!vertexPointer)
+ {
+ normalBufferSize = beginBufferSize = 1024; // default number of vertices
+ vertexPointer = new float[beginBufferSize * vertexStride];
+ normalPointer = new float[normalBufferSize * 3];
+ }
+}
+
+public void glesTexCoord2f(float x, float y)
+{
+ int count = vertexCount;
+
+ if(vertexCount + numVertexCoords > beginBufferSize)
+ {
+ beginBufferSize = beginBufferSize + beginBufferSize/2;
+ vertexPointer = renew vertexPointer float[beginBufferSize * vertexStride];
+ }
+
+ vertexPointer[count*vertexStride ] = x;
+ vertexPointer[count*vertexStride+1] = y;
+ count++;
+
+ if(beginMode == GL_QUADS && ((beginCount % 4) == 3))
+ {
+ vertexPointer[count*vertexStride ] = vertexPointer[(count-4)*vertexStride];
+ vertexPointer[count*vertexStride+1] = vertexPointer[(count-4)*vertexStride+1];
+ count++;
+ vertexPointer[count*vertexStride ] = vertexPointer[(count-3)*vertexStride];
+ vertexPointer[count*vertexStride+1] = vertexPointer[(count-3)*vertexStride+1];
+ count++;
+ }
+}
+public void glesTexCoord2i(int x, int y) { glesTexCoord2f((float)x, (float)y); }
+public void glesTexCoord2d(double x, double y) { glesTexCoord2f((float)x, (float)y); }
+public void glesTexCoord2fv(float * a) { glesTexCoord2f(a[0], a[1]); }
+
+public void glesVertex2f(float x, float y)
+{
+ numVertexCoords = 2;
+ vertexStride = vertexOffset + numVertexCoords;
+
+ if(vertexCount + 4 > beginBufferSize)
+ {
+ beginBufferSize = beginBufferSize + beginBufferSize/2;
+ vertexPointer = renew vertexPointer float[beginBufferSize * vertexStride];
+ }
+
+ vertexPointer[vertexCount*vertexStride+vertexOffset] = x;
+ vertexPointer[vertexCount*vertexStride+vertexOffset + 1] = y;
+ vertexCount++;
+
+ if(beginMode == GL_QUADS && ((beginCount % 4) == 3))
+ {
+ vertexPointer[vertexCount*vertexStride+vertexOffset] = vertexPointer[(vertexCount-4)*vertexStride+vertexOffset];
+ vertexPointer[vertexCount*vertexStride+vertexOffset + 1] = vertexPointer[(vertexCount-4)*vertexStride+vertexOffset + 1];
+ vertexCount++;
+ vertexPointer[vertexCount*vertexStride+vertexOffset] = vertexPointer[(vertexCount-3)*vertexStride+vertexOffset];
+ vertexPointer[vertexCount*vertexStride+vertexOffset + 1] = vertexPointer[(vertexCount-3)*vertexStride+vertexOffset + 1];
+ vertexCount++;
+ }
+ beginCount++;
+}
+public void glesVertex2i(int x, int y) { glesVertex2f((float)x, (float)y); }
+public void glesVertex2d(double x, double y) { glesVertex2f((float)x, (float)y); }
+
+public void glesEnd(void)
+{
+ int mode = beginMode;
+ if(mode == GL_QUADS) mode = GL_TRIANGLES;
+ else if(mode == GL_POLYGON) mode = GL_TRIANGLE_FAN;
+
+ GLSelectVBO(0);
+ glEnableClientState(GL_TEXTURE_COORD_ARRAY);
+ glTexCoordPointer(2, GL_FLOAT, vertexStride * sizeof(float), vertexPointer);
+ if(vertexColorValues)
+ {
+ glEnableClientState(GL_COLOR_ARRAY);
+ glColorPointer(4, GL_FLOAT, vertexStride * sizeof(float), vertexPointer + 2);
+ }
+ glVertexPointer (numVertexCoords, GL_FLOAT, (vertexStride)*sizeof(float),vertexPointer+vertexOffset);
+ if(normalCount && normalCount == vertexCount)
+ {
+ glEnableClientState(GL_NORMAL_ARRAY);
+ glNormalPointer (GL_FLOAT, 3*sizeof(float),normalPointer);
+ }
+
+ glDrawArrays(mode, 0, vertexCount);
+ if(normalCount)
+ glDisableClientState(GL_NORMAL_ARRAY);
+ if(vertexColorValues)
+ glDisableClientState(GL_COLOR_ARRAY);
+ glDisableClientState(GL_TEXTURE_COORD_ARRAY);
+ normalCount = 0;
+ vertexColorValues = false;
+ numVertexCoords = 2;
+ beginMode = -1;
+}
+
+// Vertex Pointer
+static float *floatVPBuffer = null;
+static short *shortVPBuffer = null;
+static unsigned int shortVPSize = 0, floatVPSize = 0;
+
+// Buffer Data
+//static float *floatVPBuffer = null; // For floats we reuse floatVPBuffer
+static unsigned short *shortBDBuffer = null;
+static unsigned int shortBDSize = 0/*, floatVPSize = 0*/;
+
+public void glesVertexPointeri(int numCoords, int stride, int *pointer, int numVertices)
+{
+ if(pointer)
+ {
+ int i;
+ if(numVertices*numCoords > shortVPSize)
+ {
+ shortVPSize = numVertices*numCoords;
+ shortVPBuffer = renew shortVPBuffer short[shortVPSize];
+ }
+ for(i = 0; i < numVertices*numCoords; i++)
+ shortVPBuffer[i] = (short)pointer[i];
+ glVertexPointer(numCoords, GL_SHORT, stride, shortVPBuffer);
+ }
+ else
+ glVertexPointer(numCoords, GL_SHORT, stride, 0);
+}
+
+public void glesVertexPointerd(int numCoords, int stride, double *pointer, int numVertices)
+{
+ if(pointer)
+ {
+ int i;
+ if(numVertices*numCoords > floatVPSize)
+ {
+ floatVPSize = numVertices*numCoords;
+ floatVPBuffer = renew floatVPBuffer float[floatVPSize];
+ }
+ for(i = 0; i < numVertices*numCoords; i++)
+ floatVPBuffer[i] = (float)pointer[i];
+ glVertexPointer(numCoords, GL_FLOAT, stride, floatVPBuffer);
+ }
+ else
+ glVertexPointer(numCoords, GL_FLOAT, stride, 0);
+}
+
+public void glesTexReuseIntVP(int numCoords)
+{
+ glTexCoordPointer(numCoords, GL_SHORT, 0, floatVPBuffer);
+}
+
+public void glesTexReuseDoubleVP(int numCoords)
+{
+ glTexCoordPointer(numCoords, GL_FLOAT, 0, floatVPBuffer);
+}
+
+public void glesColor4f(float r, float g, float b, float a)
+{
+ if(beginMode != (GLenum)-1)
+ {
+ int count = vertexCount;
+
+ vertexColorValues = true;
+ vertexOffset = 6;
+ vertexStride = vertexOffset + numVertexCoords;
+
+ if(vertexCount + vertexStride > beginBufferSize)
+ {
+ beginBufferSize = beginBufferSize + beginBufferSize/2;
+ vertexPointer = renew vertexPointer float[beginBufferSize * vertexStride];
+ }
+
+ vertexPointer[count*vertexStride + 2] = r;
+ vertexPointer[count*vertexStride + 3] = g;
+ vertexPointer[count*vertexStride + 4] = b;
+ vertexPointer[count*vertexStride + 5] = a;
+ count++;
+
+ if(beginMode == GL_QUADS && ((beginCount % 4) == 3))
+ {
+ vertexPointer[count*vertexStride + 2] = vertexPointer[(count-4) * vertexStride + 2];
+ vertexPointer[count*vertexStride + 3] = vertexPointer[(count-4) * vertexStride + 3];
+ vertexPointer[count*vertexStride + 4] = vertexPointer[(count-4) * vertexStride + 4];
+ vertexPointer[count*vertexStride + 5] = vertexPointer[(count-4) * vertexStride + 5];
+ count++;
+ vertexPointer[count*vertexStride + 2] = vertexPointer[(count-3) * vertexStride + 2];
+ vertexPointer[count*vertexStride + 3] = vertexPointer[(count-3) * vertexStride + 3];
+ vertexPointer[count*vertexStride + 4] = vertexPointer[(count-3) * vertexStride + 4];
+ vertexPointer[count*vertexStride + 5] = vertexPointer[(count-3) * vertexStride + 5];
+ count++;
+ }
+ }
+ else
+ glColor4f(r, g, b, a);
+}
+
+public void glesColor3f( float r, float g, float b )
+{
+ glesColor4f(r, g, b, 1.0f);
+}
+
+public void glesColor4ub(unsigned char r, unsigned char g, unsigned char b, unsigned char a)
+{
+ glesColor4f(r/255.0f, g/255.0f, b/255.0f, a/255.0f);
+}
+
+public void glesColor4fv(float * a)
+{
+ glesColor4f(a[0], a[1], a[2], a[3]);
+}
+
+public void glesBufferDatad(int target, int size, void * data, int usage)
+{
+ int numElems = size/sizeof(double);
+ double * dblPtr = (double *)data;
+ int i;
+ if (numElems > floatVPSize)
+ {
+ floatVPSize = numElems;
+ floatVPBuffer = renew floatVPBuffer float[floatVPSize];
+ }
+ for (i=0; i< numElems; i++)
+ floatVPBuffer[i] = (float)dblPtr[i];
+
+ glBufferData(target, numElems*sizeof(float), floatVPBuffer, usage);
+}
+
+public void glesBufferDatai(int target, int size, void * data, int usage)
+{
+ int numElems = size/sizeof(unsigned int);
+ unsigned int * pointer = (unsigned int *)data;
+ int i;
+ if (numElems > shortBDSize)
+ {
+ shortBDSize = numElems;
+ shortBDBuffer = renew shortBDBuffer uint16[shortBDSize];
+ }
+ for (i=0; i< numElems; i++)
+ shortBDBuffer[i] = (unsigned short)pointer[i];
+
+ glBufferData(target, numElems*sizeof(unsigned short), shortBDBuffer, usage);
+}
+
+// *** Our Custom Matrix Stack ***
+
+static void LoadCurMatrix()
+{
+ double * i = matrixStack[curStack][matrixIndex[curStack]].array;
+ float m[16] =
+ {
+ (float)i[0],(float)i[1],(float)i[2],(float)i[3],
+ (float)i[4],(float)i[5],(float)i[6],(float)i[7],
+ (float)i[8],(float)i[9],(float)i[10],(float)i[11],
+ (float)i[12],(float)i[13],(float)i[14],(float)i[15]
+ };
+ glLoadMatrixf(m);
+}
+
+public void glesLoadIdentity()
+{
+ matrixStack[curStack][matrixIndex[curStack]].Identity();
+ LoadCurMatrix();
+}
+
+public void glesPushMatrix()
+{
+ if(matrixIndex[curStack] + 1 < sizeof(matrixStack[0]) / sizeof(Matrix))
+ {
+ matrixIndex[curStack]++;
+ memcpy(matrixStack[curStack][matrixIndex[curStack]].array, matrixStack[curStack][matrixIndex[curStack]-1].array, sizeof(Matrix));
+ }
+}
+
+public void glesPopMatrix()
+{
+ if(matrixIndex[curStack] > 0)
+ {
+ matrixIndex[curStack]--;
+ LoadCurMatrix();
+ }
+}
+
+public void glesLoadMatrixd(double * i)
+{
+ memcpy(matrixStack[curStack][matrixIndex[curStack]].array, i, sizeof(Matrix));
+ LoadCurMatrix();
+}
+
+public void glesOrtho( double l, double r, double b, double t, double n, double f )
+{
+ Matrix m
+ { {
+ (2 / (r - l)), 0, 0, 0,
+ 0, (2 / (t - b)), 0, 0,
+ 0, 0, (-2 / (f - n)), 0,
+ (-(r + l) / (r - l)), (-(t + b) / (t - b)), (-(f + n) / (f - n)), 1
+ } };
+ Matrix res;
+ res.Multiply(m, matrixStack[curStack][matrixIndex[curStack]]);
+ matrixStack[curStack][matrixIndex[curStack]] = res;
+ LoadCurMatrix();
+}
+
+public void glesFrustum( double l, double r, double b, double t, double n, double f )
+{
+ nearPlane = n;
+ n = 1;
+ l /= nearPlane;
+ r /= nearPlane;
+ b /= nearPlane;
+ t /= nearPlane;
+ f /= nearPlane;
+ {
+ double A = ((r + l) / (r - l));
+ double B = ((t + b) / (t - b));
+ double C = (-(f + n) / (f - n));
+ double D = (-2*f*n/(f-n));
+ Matrix m
+ { {
+ (2.0*n / (r - l)), 0, 0, 0,
+ 0, (2.0*n / (t - b)), 0, 0,
+ A, B, C,-1,
+ 0, 0, D, 0
+ } };
+ Matrix res;
+ res.Multiply(m, matrixStack[curStack][matrixIndex[curStack]]);
+ matrixStack[curStack][matrixIndex[curStack]] = res;
+ LoadCurMatrix();
+ }
+}
+
+#if !defined(ECERE_NO3D) && !defined(ECERE_VANILLA)
+public void glesRotated( double a, double b, double c, double d )
+{
+ Quaternion q;
+ Matrix m, r;
+
+ q.RotationAxis({(float)b,(float)c,(float)-d}, a );
+ m.RotationQuaternion(q);
+ r.Multiply(m, matrixStack[curStack][matrixIndex[curStack]]);
+ matrixStack[curStack][matrixIndex[curStack]] = r;
+ LoadCurMatrix();
+}
+public void glesScaled( double a, double b, double c )
+{
+ Matrix m, r;
+
+ m.Identity();
+ m.Scale(a,b,c);
+ r.Multiply(m, matrixStack[curStack][matrixIndex[curStack]]);
+ matrixStack[curStack][matrixIndex[curStack]] = r;
+ LoadCurMatrix();
+}
+
+public void glesTranslated( double a, double b, double c )
+{
+ Matrix m, r;
+
+ m.Identity();
+ m.Translate(a,b,c);
+ r.Multiply(m, matrixStack[curStack][matrixIndex[curStack]]);
+ matrixStack[curStack][matrixIndex[curStack]] = r;
+ LoadCurMatrix();
+}
+
+public void glesMultMatrixd( double * i )
+{
+ Matrix r;
+ r.Multiply((Matrix *)i, matrixStack[curStack][matrixIndex[curStack]]);
+ matrixStack[curStack][matrixIndex[curStack]] = r;
+ LoadCurMatrix();
+}
+#endif
+
+public void glesMatrixMode(int mode)
+{
+ curStack = (mode == GL_MODELVIEW) ? 0 : (mode == GL_PROJECTION) ? 1 : 2;
+ glMatrixMode(mode);
+}
+
+#if defined(_GLES)
+
+#define glPushMatrix glesPushMatrix
+#define glPopMatrix glesPopMatrix
+#define glLoadIdentity glesLoadIdentity
+#define glMatrixMode glesMatrixMode
+
+#endif
+
+/* Using the built-in matrix stack
+void glesLoadMatrixd( double * i )
+{
+ float m[16] =
+ {
+ (float)i[0],(float)i[1],(float)i[2],(float)i[3],
+ (float)i[4],(float)i[5],(float)i[6],(float)i[7],
+ (float)i[8],(float)i[9],(float)i[10],(float)i[11],
+ (float)i[12],(float)i[13],(float)i[14],(float)i[15]
+ };
+ glLoadMatrixf(m);
+}
+
+void glesOrtho( double l, double r, double b, double t, double n, double f )
+{
+ float matrix[4][4] =
+ {
+ { (float)(2 / (r - l)), 0, 0, 0 },
+ { 0, (float)(2 / (t - b)), 0, 0 },
+ { 0, 0, (float)(-2 / (f - n)), 0 },
+ { (float)(-(r + l) / (r - l)), (float)(-(t + b) / (t - b)), (float)(-(f + n) / (f - n)), 1 }
+ };
+ glMultMatrixf((float *)matrix);
+}
+
+void glesFrustum( double l, double r, double b, double t, double n, double f )
+{
+ float A = (float)((r + l) / (r - l));
+ float B = (float)((t + b) / (t - b));
+ float C = (float)(-(f + n) / (f - n));
+ float D = (float)(-2*f*n/(f-n));
+ float matrix[4][4] =
+ {
+ { (float)(2*n / (r - l)), 0, 0, 0 },
+ { 0, (float)(2*n / (t - b)), 0, 0 },
+ { A, B, C,-1 },
+ { 0, 0, D, 0 }
+ };
+ glMultMatrixf((float *)matrix);
+}
+
+void glesRotated( double a, double b, double c, double d ) { glRotatef((float)a, (float)b, (float)c, (float)d); }
+void glesScaled( double a, double b, double c ) { glScalef((float)a, (float)b, (float)c); }
+void glesTranslated( double a, double b, double c ) { glTranslatef((float)a, (float)b, (float)c); }
+
+void glesMultMatrixd( double * i )
+{
+ float m[16] =
+ {
+ (float)i[0], (float)i[1], (float)i[2], (float)i[3],
+ (float)i[4], (float)i[5], (float)i[6], (float)i[7],
+ (float)i[8], (float)i[9], (float)i[10], (float)i[11],
+ (float)i[12], (float)i[13], (float)i[14], (float)i[15]
+ };
+ glMultMatrixf(m);
+}
+*/
+
+// Need to do these...
+public void glesVertex3f( float x, float y, float z )
+{
+ numVertexCoords = 3;
+ vertexStride = vertexOffset + numVertexCoords;
+
+ if(vertexCount + vertexStride > beginBufferSize)
+ {
+ beginBufferSize = beginBufferSize + beginBufferSize/2;
+ vertexPointer = renew vertexPointer float[beginBufferSize * vertexStride];
+ }
+
+ vertexPointer[vertexCount*vertexStride+vertexOffset] = x;
+ vertexPointer[vertexCount*vertexStride+vertexOffset+1] = y;
+ vertexPointer[vertexCount*vertexStride+vertexOffset+2] = z;
+ vertexCount++;
+
+ if(beginMode == GL_QUADS && ((beginCount % 4) == 3))
+ {
+ vertexPointer[vertexCount*vertexStride+vertexOffset] = vertexPointer[(vertexCount-4)*vertexStride+vertexOffset];
+ vertexPointer[vertexCount*vertexStride+vertexOffset+1] = vertexPointer[(vertexCount-4)*vertexStride+vertexOffset+1];
+ vertexPointer[vertexCount*vertexStride+vertexOffset+2] = vertexPointer[(vertexCount-4)*vertexStride+vertexOffset+2];
+ vertexCount++;
+ vertexPointer[vertexCount*vertexStride+vertexOffset] = vertexPointer[(vertexCount-3)*vertexStride+vertexOffset];
+ vertexPointer[vertexCount*vertexStride+vertexOffset+1] = vertexPointer[(vertexCount-3)*vertexStride+vertexOffset+1];
+ vertexPointer[vertexCount*vertexStride+vertexOffset+2] = vertexPointer[(vertexCount-3)*vertexStride+vertexOffset+2];
+ vertexCount++;
+ }
+ beginCount++;
+}
+
+public void glesVertex3d( double x, double y, double z ) { glesVertex3f((float)x, (float)y, (float)z); }
+public void glesVertex3fv( float* coords ) { glesVertex3f(coords[0], coords[1], coords[2]); }
+public void glesVertex3dv( double* coords ) { glesVertex3f((float)coords[0], (float)coords[1], (float)coords[2]); }
+
+public void glesNormal3f(float x, float y, float z)
+{
+ normalCount = vertexCount;
+ if(vertexCount + 4 > normalBufferSize)
+ {
+ normalBufferSize = normalBufferSize + normalBufferSize/2;
+ normalPointer = renew normalPointer float[normalBufferSize * 2];
+ }
+
+ normalPointer[normalCount*3+0] = x;
+ normalPointer[normalCount*3+1] = y;
+ normalPointer[normalCount*3+2] = z;
+ normalCount++;
+
+ if(beginMode == GL_QUADS && ((beginCount % 4) == 3))
+ {
+ normalPointer[normalCount*3+0] = normalPointer[(normalCount-4)*3+0];
+ normalPointer[normalCount*3+1] = normalPointer[(normalCount-4)*3+1];
+ normalPointer[normalCount*3+2] = normalPointer[(normalCount-4)*3+2];
+ normalCount++;
+ normalPointer[normalCount*3+0] = normalPointer[(normalCount-3)*3+0];
+ normalPointer[normalCount*3+1] = normalPointer[(normalCount-3)*3+1];
+ normalPointer[normalCount*3+2] = normalPointer[(normalCount-3)*3+2];
+ normalCount++;
+ }
+}
+public void glesNormal3fd(double x, double y, double z) { glesNormal3f((float)x, (float)y, (float)z); }
+public void glesNormal3fv(float * coords) { glesNormal3f(coords[0], coords[1], coords[2]); }
+
+public void glesColorMaterial(int a, int b)
+{
+ PrintLn("glColorMaterial stub");
+}
+
+public void glesTerminate()
+{
+ delete vertexPointer;
+ delete normalPointer;
+ beginBufferSize = 0;
+
+ delete floatVPBuffer;
+ shortVPSize = 0;
+
+ delete shortVPBuffer;
+ floatVPSize = 0;
+
+ delete shortBDBuffer;
+ shortBDSize = 0;
+}
+
+static GLuint stippleTexture;
+#if defined(_GLES) || defined(EM_MODE)
+static bool stippleEnabled;
+#endif
+
+public void glesLineStipple( int i, unsigned short j )
+{
+ uint texture[1*16];
+ int x;
+ for(x = 0; x < 16; x++)
+ {
+ bool v = (j & (1 << x)) != 0;
+ texture[x] = v ? 0xFFFFFFFF : 0;
+ }
+ if(!stippleTexture)
+ glGenTextures(1, &stippleTexture);
+ glBindTexture(GL_TEXTURE_2D, stippleTexture);
+ glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 16, 1, 0, GL_RGBA, GL_UNSIGNED_BYTE, texture);
+ glEnable(GL_TEXTURE_2D);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+ glMatrixMode(GL_TEXTURE);
+ glLoadIdentity();
+ //glTranslated(1.0/backAttrib->texW/2.0f, 1.0/backAttrib->texH/2.0f, 0.0f);
+ glScaled(i/16.0, 1, 1.0f);
+ glTranslated(0.5, 0.5, 0);
+ glMatrixMode(GL_PROJECTION);
+}
+
+public void glesLightModeli( unsigned int pname, int param )
+{
+#if !defined(EM_MODE)
+ if(pname == GL_LIGHT_MODEL_TWO_SIDE)
+ glLightModelf(GL_LIGHT_MODEL_TWO_SIDE, param);
+#endif
+}
+
+#ifdef __ANDROID__
+void glClearDepth( double depth ) { glClearDepthf((float)depth); }
+void glFogi( unsigned int pname, int param ) { }
+void glPolygonMode( unsigned int i, unsigned int j ) { }
+
+
+// *** Picking won't be supported for now ***
+void glPushName( unsigned int i ) { }
+void glLoadName( unsigned int i ) { }
+void glPopName() { }
+
+// Probably replace by regular glBlendFunc ...
+void glBlendFuncSeparate(int a, int b, int c, int d)
+{
+ glBlendFunc(a, b);
+}
+
+// For direct pixel blitting...
+void glRasterPos2d(double a, double b) { }
+void glPixelZoom(float a, float b) { }
+void glDrawPixels(int a, int b, int c, int d, void * e) { }
+
+#endif
+
+#if !defined(__APPLE__) && !defined(__WIN32__)