X-Git-Url: https://git.jsancho.org/?a=blobdiff_plain;f=Source%2FOpenGL_Windows.cpp;h=8ce1a4ce34e88a150d2c357054a4601a096d30e6;hb=d72054c5ab036810ee8a09ce57950aa977fcab06;hp=6535b95d1cd4065abccb9504883eaa5747d110cd;hpb=bcb5c54b2b6170c185583c18f5ec97b0bb813f0a;p=lugaru.git diff --git a/Source/OpenGL_Windows.cpp b/Source/OpenGL_Windows.cpp index 6535b95..8ce1a4c 100644 --- a/Source/OpenGL_Windows.cpp +++ b/Source/OpenGL_Windows.cpp @@ -4,9 +4,28 @@ #endif #include "Game.h" -#include "IL/il.h" -#include "IL/ilu.h" -#include "IL/ilut.h" + +#ifndef USE_DEVIL +# ifdef WIN32 +# define USE_DEVIL +# endif +#endif + +#if USE_DEVIL + #include "IL/il.h" + #include "IL/ilu.h" + #include "IL/ilut.h" +#else + // just use libpng and libjpg directly; it's lighter-weight and easier + // to manage the dependencies on Linux... + extern "C" { + #include "png.h" + #include "jpeglib.h" + } + static bool load_image(const char * fname, TGAImageRec & tex); + static bool load_png(const char * fname, TGAImageRec & tex); + static bool load_jpg(const char * fname, TGAImageRec & tex); +#endif // ADDED GWC #ifdef _MSC_VER @@ -940,6 +959,7 @@ Boolean SetUp (Game & game) glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glAlphaFunc( GL_GREATER, 0.5f); +#if USE_DEVIL if (ilGetInteger(IL_VERSION_NUM) < IL_VERSION || iluGetInteger(ILU_VERSION_NUM) < ILU_VERSION || ilutGetInteger(ILUT_VERSION_NUM) < ILUT_VERSION) @@ -956,6 +976,7 @@ Boolean SetUp (Game & game) ilEnable(IL_ORIGIN_SET); ilOriginFunc(IL_ORIGIN_LOWER_LEFT); +#endif GLint width = kContextWidth; GLint height = kContextHeight; @@ -1154,7 +1175,9 @@ void CleanUp (void) // game.Dispose(); +#if USE_DEVIL ilShutDown(); +#endif #if USE_SDL SDL_Quit(); @@ -2096,6 +2119,7 @@ int main (void) return false; } + #if USE_DEVIL ILstring f = strdup(ConvertFileName(fname)); if (!f) { @@ -2152,12 +2176,17 @@ int main (void) } */ free(f); + #else + res = load_image(fname, tex); + //if (!res) printf("failed to load %s\n", fname); + #endif return res; } void ScreenShot(const char * fname) { + #if USE_DEVIL ILstring f = strdup(fname); if (!f) { @@ -2174,6 +2203,220 @@ int main (void) ilDeleteImages(1, &iid); free(f); + #else + STUBBED("Non-DevIL screenshot"); + #endif } +#if !USE_DEVIL +static bool load_image(const char *file_name, TGAImageRec &tex) +{ + char *ptr = strrchr(file_name, '.'); + if (ptr) + { + if (stricmp(ptr+1, "png") == 0) + return load_png(file_name, tex); + else if (stricmp(ptr+1, "jpg") == 0) + return load_jpg(file_name, tex); + } + + STUBBED("Unsupported image type"); + return false; +} + + +struct my_error_mgr { + struct jpeg_error_mgr pub; /* "public" fields */ + jmp_buf setjmp_buffer; /* for return to caller */ +}; +typedef struct my_error_mgr * my_error_ptr; + + +static void my_error_exit(j_common_ptr cinfo) +{ + struct my_error_mgr *err = (struct my_error_mgr *)cinfo->err; + longjmp(err->setjmp_buffer, 1); +} + +/* stolen from public domain example.c code in libjpg distribution. */ +static bool load_jpg(const char *file_name, TGAImageRec &tex) +{ + struct jpeg_decompress_struct cinfo; + struct my_error_mgr jerr; + JSAMPROW buffer[1]; /* Output row buffer */ + int row_stride; /* physical row width in output buffer */ + FILE *infile = fopen(file_name, "rb") + + if (infile == NULL) + return false; + + cinfo.err = jpeg_std_error(&jerr.pub); + jerr.pub.error_exit = my_error_exit; + if (setjmp(jerr.setjmp_buffer)) { + jpeg_destroy_decompress(&cinfo); + fclose(infile); + return false; + } + + jpeg_create_decompress(&cinfo); + jpeg_stdio_src(&cinfo, infile); + (void) jpeg_read_header(&cinfo, TRUE); + + cinfo.out_color_space = JCS_RGB; + cinfo.quantize_colors = 0; + (void) jpeg_calc_output_dimensions(&cinfo); + (void) jpeg_start_decompress(&cinfo); + + row_stride = cinfo.output_width * cinfo.output_components; + tex.sizeX = cinfo.output_width; + tex.sizeY = cinfo.output_height; + tex.bpp = 24; + + while (cinfo.output_scanline < cinfo.output_height) { + buffer[0] = (JSAMPROW)(char *)tex.data + + ((cinfo.output_height-1) - cinfo.output_scanline) * row_stride; + (void) jpeg_read_scanlines(&cinfo, buffer, 1); + } + + (void) jpeg_finish_decompress(&cinfo); + jpeg_destroy_decompress(&cinfo); + fclose(infile); + + return true; +} + +/* stolen from public domain example.c code in libpng distribution. */ +static bool load_png(const char *file_name, TGAImageRec &tex) +{ + bool hasalpha = false; + png_structp png_ptr = NULL; + png_infop info_ptr = NULL; + png_uint_32 width, height; + int bit_depth, color_type, interlace_type; + png_byte **rows = NULL; + bool retval = false; + png_byte **row_pointers = NULL; + FILE *fp = fopen(file_name, "rb"); + + if (fp == NULL) + return(NULL); + + png_ptr = png_create_read_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL); + if (png_ptr == NULL) + goto png_done; + + info_ptr = png_create_info_struct(png_ptr); + if (info_ptr == NULL) + goto png_done; + + if (setjmp(png_jmpbuf(png_ptr))) + goto png_done; + + png_init_io(png_ptr, fp); + png_read_png(png_ptr, info_ptr, + PNG_TRANSFORM_STRIP_16 | PNG_TRANSFORM_PACKING, + png_voidp_NULL); + png_get_IHDR(png_ptr, info_ptr, &width, &height, + &bit_depth, &color_type, &interlace_type, NULL, NULL); + + if (bit_depth != 8) // transform SHOULD handle this... + goto png_done; + + if (color_type & PNG_COLOR_MASK_PALETTE) // !!! FIXME? + goto png_done; + + if ((color_type & PNG_COLOR_MASK_COLOR) == 0) // !!! FIXME? + goto png_done; + + hasalpha = ((color_type & PNG_COLOR_MASK_ALPHA) != 0); + row_pointers = png_get_rows(png_ptr, info_ptr); + if (!row_pointers) + goto png_done; + + retval = malloc(width * height * 4); + if (!retval) + goto png_done; + + if (!hasalpha) + { + png_byte *dst = tex.data; + for (int i = height-1; i >= 0; i--) + { + png_byte *src = row_pointers[i]; + for (int j = 0; j < width; j++) + { + dst[0] = src[0]; + dst[1] = src[1]; + dst[2] = src[2]; + dst[3] = 0xFF; + src += 3; + dst += 4; + } + } + } + + else + { + png_byte *dst = tex.data; + int pitch = width * 4; + for (int i = height-1; i >= 0; i--, dst += pitch) + memcpy(dst, row_pointers[i], pitch); + } + + tex.sizeX = width; + tex.sizeY = height; + tex.bpp = 32; + retval = true; + +png_done: + png_destroy_read_struct(&png_ptr, &info_ptr, png_infopp_NULL); + fclose(fp); + return (retval); +} + +#if 0 +void save_png(char *file_name /* , ... other image information ... */) +{ + FILE *fp; + png_structp png_ptr; + png_infop info_ptr; + + /* open the file */ + fp = fopen(file_name, "wb"); + if (fp == NULL) + return (ERROR); + + png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL); + if (png_ptr == NULL) + { + fclose(fp); + return (ERROR); + } + + info_ptr = png_create_info_struct(png_ptr); + if (info_ptr == NULL) + { + fclose(fp); + png_destroy_write_struct(&png_ptr, png_infopp_NULL); + return (ERROR); + } + + if (setjmp(png_jmpbuf(png_ptr))) + { + /* If we get here, we had a problem reading the file */ + fclose(fp); + png_destroy_write_struct(&png_ptr, &info_ptr); + return (ERROR); + } + + png_init_io(png_ptr, fp); + png_write_png(png_ptr, info_ptr, png_transforms, png_voidp_NULL); + png_destroy_write_struct(&png_ptr, &info_ptr); + fclose(fp); + return (OK); +} +#endif + +#endif +