I did the convert on images using a shell script and the program convert, which is quite handy as a Swiss army knife of image functions. I then just did some simple OpenGL texture placement with relative addresses using a matrix of possible and solved elements. The graphic portion of the game is now scalable to a standard OpenGL window. The relative representation of the array in its state of partial solution is actually simple and only took a few minutes to program. The code is here as an example and it extends the "simple OpenGL window" that I posted the code for earlier.
glLoadIdentity(); glColor3f(1.0,1.0,1.0); glClearColor(0.50,0.80,1.0,1.0); glLoadIdentity(); glColor3f(1.0,1.0,1.0); glClearColor(0.50,0.80,1.0,1.0); glEnable(GL_TEXTURE_2D); glEnable(GL_CULL_FACE); glEnable(GL_DEPTH_TEST); glEnable(GL_NORMALIZE); glBlendFunc(GL_SRC_COLOR,GL_ONE_MINUS_SRC_COLOR); glDisable(GL_BLEND); for (i=0;i<6;i++) { for (j=0;j<6;j++) { k = (int)(puzzle[i][j][0][1]); if (puzzle[i][j][0][1] > 1) { glBindTexture(GL_TEXTURE_2D, texture[(k)+(i*6)]); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f); glVertex3f(posx,posy-(sizey), posz); glTexCoord2f(1.0f, 0.0f); glVertex3f(posx+(sizex),posy-(sizey), posz); glTexCoord2f(1.0f, 1.0f); glVertex3f(posx+(sizex),posy, posz); glTexCoord2f(0.0f, 1.0f); glVertex3f(posx,posy, posz); glEnd(); } if (puzzle[i][j][0][0] <= 1) { for (l=0;l<6;l++) { posx2=posx; posy2=posy; if( l > 2 ){ posy = posy-(sizey/2);} posx=posx+((l%3)*(sizex/3)); glBindTexture(GL_TEXTURE_2D, texture[(l)+(i*6)]); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f); glVertex3f(posx,(posy-(sizey/2)), posz); glTexCoord2f(1.0f, 0.0f); glVertex3f((posx+(sizex/3)),(posy-(sizey/2)), posz); glTexCoord2f(1.0f, 1.0f); glVertex3f((posx+(sizex/3)),posy, posz); glTexCoord2f(0.0f, 1.0f); glVertex3f(posx,posy, posz); glEnd(); posx=posx2; posy=posy2; } } posx+=sizex+spacing; k++; } posx=-1.0;posy=posy-sizey-spacing; } return;
When it is done I will create a zip of the final product with all the trappings that come with the original game including all the source, makefiles, debian install information, help file, desktop icon, and i18n methods. I will play with this on and off over the next few weeks and add some special effects. It is really simple to do graphical interfaces using OpenGL, once you get over the initial hurdles. Matrices and the order of action can be confusing, but once the methods become familiar it is a quick way to do all types of graphical applications that are compatible with many platforms. Another odd thing is that the vertical axis starts at 1 and goes down as you go down the screen, but I suppose that is just one of those standards that was adopted and now it couldn't be changed without changing about 100 billion terabytes of code to act with the opposite polarity. I find that properly structured C can be safer and if object orientation is considered in the design, it is better than C++ IMHO. The 36 textures are loaded with the following code:
void LoadGLTexture(char *filename, int texture[], int textureNum) { Image *image1; image1 = (Image *) malloc(sizeof(Image)); if (image1 == NULL) {printf("Error allocating space for image\n");exit(0);} if (!ImageLoad(filename, image1)) {printf("Error loading image.\n");exit(1);} glBindTexture(GL_TEXTURE_2D,texture[textureNum]); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, image1->sizeX, image1->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, image1->data); free(image1); free (image1->data); } void LoadGLTextures(int texture[], int texture_count) { glGenTextures(texture_count, &texture[0]); int i,j,k,textureNum; textureNum=0; char filename[] = "res/large2-A1.bmp"; for (i = 0; i<6;i++) { for (j = 0; j<6;j++) { filename[11] = (char)((int)('A')+i); filename[12] = (char)((int)('1')+j); LoadGLTexture(filename, texture, textureNum);textureNum++; }} } void UnloadGLTextures(int texture[], int texture_count){ glDeleteTextures(texture_count,&texture[0]); }
And here is the structure of the "Image" file for BMPs only.
struct Image { unsigned long sizeX; unsigned long sizeY; char *data; }; typedef struct Image Image;
I hope this helps someone else to understand how to program with OpenGL and C. I certainly have learned a lot from people on the web. (MIT, Stanford, Yale, Harvard UCLA, Berkeley) opencourseware, W3C, FSF, Wikipedia, YouTube, and many other places have great resources to learn many things. Below is also a sample script thta I made to test conversions and can be used as an example to manage a set of files. Check out the ImageMagick site for some good information on how to use convert.
for i in *large*.bmpdo x=`echo "$i"|sed s/large/large3/` convert -resize 16x16! "$i" "$x" done
0 comments:
Post a Comment