blob: af8cc95449440a1805606a20e803cf1553f28282 [file] [log] [blame]
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
//#define GL_API
//#define GL_APIENTRY
#undef ANDROID
#include <EGL/egl.h>
#include <GLES/gl.h>
#undef HAVE_MALLOC_H
#include <SDL.h>
#include <SDL_syswm.h>
#define WINDOW_WIDTH 500
#define WINDOW_HEIGHT 500
#define TEX_WIDTH 256
#define TEX_HEIGHT 256
#define F_to_X(d) ((d) > 32767.65535 ? 32767 * 65536 + 65535 : \
(d) < -32768.65535 ? -32768 * 65536 + 65535 : \
((GLfixed) ((d) * 65536)))
#define X_to_F(x) ((float)(x))/65536.0f
static EGLint const attribute_list[] = {
EGL_RED_SIZE, 1,
EGL_GREEN_SIZE, 1,
EGL_BLUE_SIZE, 1,
EGL_NONE
};
unsigned char *genTexture(int width, int height, int comp)
{
unsigned char *img = new unsigned char[width * height * comp];
unsigned char *ptr = img;
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
unsigned char col = ((i / 8 + j / 8) % 2) * 255 ;
for (int c = 0; c < comp; c++) {
*ptr = col; ptr++;
}
}
}
return img;
}
unsigned char *genRedTexture(int width, int height, int comp)
{
unsigned char *img = new unsigned char[width * height * comp];
memset(img,0,width*height*comp);
unsigned char *ptr = img;
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
unsigned char col = ((i / 8 + j / 8) % 2) * 255 ;
*ptr = col;
ptr+=comp;
}
}
return img;
}
//mip 0;
unsigned char *genPalette4_rgb8(int width, int height,int color)
{
int size = width*height/2 + 16*3/*palette size*/;
unsigned char *img = new unsigned char[size];
memset(img,0,size);
img[0] = 255; img[1] = 0; img[2] = 0; // red
img[3] = 0; img[4] = 0; img[5] = 255; //blue
img[7] = 128; img[8] = 0; img[9] = 128; //fucsia
//rest of the palette is empty
unsigned char *ptr = img+(16*3);
for (int i = 0; i < (height*width/2); i++) {
ptr[i] = (i%2)?0x0|color:0x11|color;
}
return img;
}
void usage(const char *progname)
{
fprintf(stderr, "usage: %s [-n <nframes> -i -h]\n", progname);
fprintf(stderr, "\t-h: this message\n");
fprintf(stderr, "\t-i: immidate mode\n");
fprintf(stderr, "\t-n nframes: generate nframes\n");
fprintf(stderr, "\t-e: use index arrays\n");
fprintf(stderr, "\t-t: use texture\n");
fprintf(stderr, "\t-f: use fixed points\n");
fprintf(stderr, "\t-p: use point size OES extention\n");
}
#ifdef _WIN32
int WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd)
#else
int main(int argc, char **argv)
#endif
{
GLuint ui32Vbo = 0; // Vertex buffer object handle
GLuint ui32IndexVbo;
GLuint ui32Texture;
int nframes = 100;
bool immidateMode = true;
bool useIndices = false;
bool useTexture = false;
bool useCompTexture = false;
bool useFixed = false;
bool usePoints = true;
bool useCopy = false;
bool useSubCopy = false;
int c;
extern char *optarg;
#ifdef _WIN32
HWND windowId = NULL;
#else
Window windowId = NULL;
#endif
// // Inialize SDL window
//
if (SDL_Init(SDL_INIT_NOPARACHUTE | SDL_INIT_VIDEO)) {
fprintf(stderr,"SDL init failed: %s\n", SDL_GetError());
return -1;
}
SDL_Surface *surface = SDL_SetVideoMode(WINDOW_WIDTH,WINDOW_HEIGHT, 32, SDL_HWSURFACE);
if (surface == NULL) {
fprintf(stderr,"Failed to set video mode: %s\n", SDL_GetError());
return -1;
}
SDL_SysWMinfo wminfo;
memset(&wminfo, 0, sizeof(wminfo));
SDL_GetWMInfo(&wminfo);
#ifdef _WIN32
windowId = wminfo.window;
#else
windowId = wminfo.info.x11.window;
#endif
int major,minor,num_config;
EGLConfig configs[150];
EGLSurface egl_surface;
EGLContext ctx;
EGLDisplay d = eglGetDisplay(EGL_DEFAULT_DISPLAY);
eglInitialize(d,&major,&minor);
printf("DISPLAY == %p major =%d minor = %d\n",d,major,minor);
eglChooseConfig(d, attribute_list, configs, 150, &num_config);
printf("config returned %d\n",num_config);
egl_surface = eglCreateWindowSurface(d,configs[0],windowId,NULL);
ctx = eglCreateContext(d,configs[0],EGL_NO_CONTEXT,NULL);
printf("SURFACE == %p CONTEXT == %p\n",egl_surface,ctx);
if(eglMakeCurrent(d,egl_surface,egl_surface,ctx)!= EGL_TRUE){
printf("make current failed\n");
return false;
}
printf("after make current\n");
GLenum err = glGetError();
if(err != GL_NO_ERROR) {
printf("error before drawing ->>> %d \n",err);
} else {
printf("no error before drawing\n");
}
if (useTexture) {
glEnable(GL_TEXTURE_2D);
ui32Texture = 1;
glBindTexture(GL_TEXTURE_2D, ui32Texture);
GLenum err = glGetError();
unsigned char *pixels = NULL;
if(useCompTexture) {
pixels = genPalette4_rgb8(TEX_WIDTH,TEX_HEIGHT,3);
glCompressedTexImage2D(GL_TEXTURE_2D,0,GL_PALETTE4_RGB8_OES,TEX_WIDTH,TEX_HEIGHT,0,3*16+TEX_WIDTH*TEX_HEIGHT/2,pixels);
} else {
pixels = genTexture(TEX_WIDTH, TEX_HEIGHT, 4);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, TEX_WIDTH, TEX_HEIGHT, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
}
delete pixels;
err = glGetError();
if(err != GL_NO_ERROR)
printf("error %d after image \n",err);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
err = glGetError();
if(err != GL_NO_ERROR)
printf("error after min filter \n");
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
err = glGetError();
if(err != GL_NO_ERROR)
printf("error after mag filter \n");
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
err = glGetError();
if(err != GL_NO_ERROR)
printf("error after env mode \n");
if(useCompTexture) {
pixels = genPalette4_rgb8(TEX_WIDTH,TEX_HEIGHT,1);
glCompressedTexSubImage2D(GL_TEXTURE_2D,0,TEX_WIDTH/4,TEX_HEIGHT/4,TEX_WIDTH/8,TEX_HEIGHT/8,GL_PALETTE4_RGB8_OES,3*16+(TEX_WIDTH*TEX_HEIGHT/128),pixels);
} else {
pixels = genRedTexture(TEX_WIDTH/8, TEX_HEIGHT/8, 4);
glTexSubImage2D(GL_TEXTURE_2D,0,TEX_WIDTH/4,TEX_HEIGHT/4,TEX_WIDTH/8,TEX_HEIGHT/8,GL_RGBA,GL_UNSIGNED_BYTE,pixels);
}
err = glGetError();
if(err != GL_NO_ERROR)
printf("error %d after subimage \n",err);
delete pixels;
}
glClearColor(0.6f, 0.8f, 1.0f, 1.0f); // clear blue
float afVertices[] = { -0.4f,-0.4f,0.0f, // Position
1.0f,0.0f,0.0f,1.0f, // Color
0.0f, 0.0f, // texture
12.f, //point size
0.4f,-0.4f,0.0f,
0.0f,1.0f,0.0f,1.0f,
1.0f, 0.0f,
47.0f,
0.0f,0.4f,0.0f,
0.0f,0.0f,1.0f,1.0f,
0.5f, 1.0f,
14.0f
};
GLfixed fixedVertices[] = { F_to_X(-0.4f),F_to_X(-0.4f),F_to_X(0.0f), // Position
F_to_X(1.0f),F_to_X(0.0f),F_to_X(0.0f),F_to_X(1.0f), // Color
F_to_X(0.0f),F_to_X(0.0f), // texture
F_to_X(12.0f),//points size
F_to_X(0.4f),F_to_X(-0.4f),F_to_X(0.0f),
F_to_X(0.0f),F_to_X(1.0f),F_to_X(0.0f),F_to_X(1.0f),
F_to_X(1.0f),F_to_X( 0.0f),
F_to_X(30.0f),
F_to_X(0.0f),F_to_X(0.4f),F_to_X(0.0f),
F_to_X(0.0f),F_to_X(0.0f),F_to_X(1.0f),F_to_X(1.0f),
F_to_X(0.5f), F_to_X(1.0f),
F_to_X(30.0)
};
unsigned short indices[] = { 2, 1, 0 };
if (!immidateMode) {
glGenBuffers(1, &ui32Vbo);
ui32Vbo = 1;
printf("ui32Vbo = %d\n", ui32Vbo);
glBindBuffer(GL_ARRAY_BUFFER, ui32Vbo);
unsigned int uiSize = 3 * (sizeof(float) * 10);
glBufferData(GL_ARRAY_BUFFER, uiSize, useFixed?(void *)fixedVertices:(void*)afVertices, GL_STATIC_DRAW);
ui32IndexVbo = 2;
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ui32IndexVbo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);
}
// Draws a triangle for 800 frames
float angle = 0.0;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
GLvoid* arr = NULL;
GLenum type;
GLenum drawType;
int size_of;
if(useFixed)
{
arr = fixedVertices;
type = GL_FIXED;
size_of = sizeof(GLfixed);
}
else
{
arr = afVertices;
type = GL_FLOAT;
size_of = sizeof(float);
}
if(usePoints)
{
drawType = GL_POINTS;
}
else
drawType = GL_TRIANGLES;
for (int i = 0; i < 10000; i++) {
glClear(GL_COLOR_BUFFER_BIT);
glPushMatrix();
glRotatef(angle, 0.0, 0.0, 1.0);
angle += 360.0 / nframes;
// Enable vertex arrays
glEnableClientState(GL_VERTEX_ARRAY);
if (immidateMode) {
glVertexPointer(3,type, size_of * 10, arr);
} else {
glVertexPointer(3,type, size_of * 10, 0);
}
// Set color data in the same way
glEnableClientState(GL_COLOR_ARRAY);
if (immidateMode) {
glColorPointer(4, type, size_of * 10, useFixed?(GLvoid*)(fixedVertices+3):(GLvoid*)(afVertices+3));
} else {
glColorPointer(4,type,size_of * 10, (GLvoid*) (size_of * 3) );
}
if (useTexture) {
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
if (immidateMode) {
glTexCoordPointer(2, type, size_of * 10, useFixed?(GLvoid*)(fixedVertices + 7):(GLvoid*)(afVertices+7));
} else {
glTexCoordPointer(2, type, size_of * 10, (GLvoid*)(size_of * 7));
}
}
if(usePoints)
{
glEnableClientState(GL_POINT_SIZE_ARRAY_OES);
if (immidateMode) {
glPointSizePointerOES(type,size_of * 10,useFixed?(GLvoid*)(fixedVertices + 9):(GLvoid*)(afVertices+9));
} else {
glPointSizePointerOES(type,size_of * 10,(GLvoid*)(size_of * 9));
}
}
if (useIndices) {
if (immidateMode) {
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
glDrawElements(drawType, 3, GL_UNSIGNED_SHORT, indices);
} else {
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ui32IndexVbo);
glDrawElements(drawType, 3, GL_UNSIGNED_SHORT, 0);
}
} else {
glDrawArrays(drawType, 0, 3);
}
GLenum err = glGetError();
if(err != GL_NO_ERROR)
printf(" error %d has occured while drawing\n",err);
glPopMatrix();
eglSwapBuffers(d,egl_surface);
if(useTexture && useCopy)
glCopyTexImage2D(GL_TEXTURE_2D,0,GL_RGBA,0,0,256,256,0);
else if(useTexture && useSubCopy)
glCopyTexSubImage2D(GL_TEXTURE_2D,0,100,100,WINDOW_WIDTH/2,WINDOW_HEIGHT/2,50,50);
}
err = glGetError();
if(err != GL_NO_ERROR)
printf("error ->>> %d \n",err);
eglDestroySurface(d,egl_surface);
eglDestroyContext(d,ctx);
// Just wait until the window is closed
SDL_Event ev;
while( SDL_WaitEvent(&ev) ) {
if (ev.type == SDL_QUIT) {
break;
}
}
return 0;
}