X-Git-Url: http://git.xonotic.org/?a=blobdiff_plain;f=tools%2Fquake3%2Fq3map2%2Fimage.c;h=20ad90ff99d59350b5b58cf34982c7bea2ec5220;hb=90f54911568e6f9b47a5e7561665d92d36eaccfd;hp=16c3304a6386a1033e092ac1f8ad041bedb7b82e;hpb=e0b3d0ac5abc0cde0a74fadbd2aa4739b43b24a3;p=xonotic%2Fnetradiant.git diff --git a/tools/quake3/q3map2/image.c b/tools/quake3/q3map2/image.c index 16c3304a..20ad90ff 100644 --- a/tools/quake3/q3map2/image.c +++ b/tools/quake3/q3map2/image.c @@ -36,7 +36,7 @@ /* dependencies */ #include "q3map2.h" - +#include "webp/decode.h" /* ------------------------------------------------------------------------------- @@ -86,6 +86,28 @@ static void LoadDDSBuffer( byte *buffer, int size, byte **pixels, int *width, in DDSDecompress( (ddsBuffer_t*) buffer, *pixels ); } +#ifdef BUILD_CRUNCH +/* + LoadCRNBuffer + loads a crn image into a valid rgba image +*/ +void LoadCRNBuffer( byte *buffer, int size, byte **pixels, int *width, int *height) { + /* dummy check */ + if ( buffer == NULL || size <= 0 || pixels == NULL || width == NULL || height == NULL ) { + return; + } + if ( !GetCRNImageSize( buffer, size, width, height ) ) { + Sys_FPrintf( SYS_WRN, "WARNING: Error getting crn imag dimensions.\n");; + return; + } + int outBufSize = *width * *height * 4; + *pixels = safe_malloc( outBufSize ); + if ( !ConvertCRNtoRGBA( buffer, size, outBufSize, *pixels) ) { + Sys_FPrintf( SYS_WRN, "WARNING: Error decoding crn image.\n", 0 ); + return; + } +} +#endif // BUILD_CRUNCH /* @@ -123,7 +145,6 @@ static void LoadPNGBuffer( byte *buffer, int size, byte **pixels, int *width, in png_struct *png; png_info *info, *end; pngBuffer_t pb; - //pngBuffer_t *pb = (pngBuffer_t*) png_get_io_ptr( png ); int bitDepth, colorType; png_uint_32 w, h, i; byte **rowPointers; @@ -170,7 +191,6 @@ static void LoadPNGBuffer( byte *buffer, int size, byte **pixels, int *width, in pb.size = size; pb.offset = 0; png_set_read_fn( png, &pb, PNGReadData ); - //png->io_ptr = &pb; /* hack! */ /* set error longjmp */ if ( setjmp( png_jmpbuf(png) ) ) { @@ -210,7 +230,8 @@ static void LoadPNGBuffer( byte *buffer, int size, byte **pixels, int *width, in /* create image pixel buffer */ *width = w; *height = h; - *pixels = safe_malloc( w * h * 4 ); + /* initialize with zeros, this memory area may not be entirely rewritten */ + *pixels = safe_malloc0( w * h * 4 ); /* create row pointers */ rowPointers = safe_malloc( h * sizeof( byte* ) ); @@ -223,7 +244,34 @@ static void LoadPNGBuffer( byte *buffer, int size, byte **pixels, int *width, in /* clean up */ free( rowPointers ); png_destroy_read_struct( &png, &info, &end ); +} + + +static void LoadWEBPBuffer( byte *buffer, int size, byte **pixels, int *width, int *height ){ + + int image_width; + int image_height; + + if ( !WebPGetInfo( buffer, ( size_t) size, &image_width, &image_height ) ) + { + Sys_FPrintf( SYS_WRN, "WARNING: An error occurred reading WEBP image info\n" ); + return; + } + + /* create image pixel buffer */ + *pixels = safe_malloc( image_width * image_height * 4 ); + *width = image_width; + *height = image_height; + + int out_stride = image_width * 4; + int out_size = image_height * out_stride; + + if ( !WebPDecodeRGBAInto( buffer, (size_t) size, *pixels, out_size, out_stride ) ) + { + Sys_FPrintf( SYS_WRN, "WARNING: An error occurred reading WEBP image\n" ); + return; + } } @@ -384,66 +432,81 @@ image_t *ImageLoad( const char *filename ){ size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); if ( size > 0 ) { LoadTGABuffer( buffer, buffer + size, &image->pixels, &image->width, &image->height ); + goto image_load_success; } - else - { - /* attempt to load png */ + + /* attempt to load png */ + StripExtension( name ); + strcat( name, ".png" ); + size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); + if ( size > 0 ) { + LoadPNGBuffer( buffer, size, &image->pixels, &image->width, &image->height ); + goto image_load_success; + } + + /* attempt to load jpg */ + StripExtension( name ); + strcat( name, ".jpg" ); + size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); + if ( size > 0 ) { + if ( LoadJPGBuff( buffer, size, &image->pixels, &image->width, &image->height ) == -1 && image->pixels != NULL ) { + // On error, LoadJPGBuff might store a pointer to the error message in image->pixels + Sys_FPrintf( SYS_WRN, "WARNING: LoadJPGBuff: %s\n", (unsigned char*) image->pixels ); + } + alphaHack = qtrue; + goto image_load_success; + } + + /* attempt to load dds */ + StripExtension( name ); + strcat( name, ".dds" ); + size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); + + /* also look for .dds image in dds/ prefix like Doom3 or DarkPlaces */ + if ( size <= 0 ) { + strcpy( name, "dds/" ); + strcat( name, image->name ); StripExtension( name ); - strcat( name, ".png" ); + strcat( name, ".dds" ); size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); - if ( size > 0 ) { - LoadPNGBuffer( buffer, size, &image->pixels, &image->width, &image->height ); - } - else - { - /* attempt to load jpg */ - StripExtension( name ); - strcat( name, ".jpg" ); - size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); - if ( size > 0 ) { - if ( LoadJPGBuff( buffer, size, &image->pixels, &image->width, &image->height ) == -1 && image->pixels != NULL ) { - // On error, LoadJPGBuff might store a pointer to the error message in image->pixels - Sys_FPrintf( SYS_WRN, "WARNING: LoadJPGBuff: %s\n", (unsigned char*) image->pixels ); - } - alphaHack = qtrue; - } - else - { - /* attempt to load dds */ - StripExtension( name ); - strcat( name, ".dds" ); - size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); - if ( size > 0 ) { - LoadDDSBuffer( buffer, size, &image->pixels, &image->width, &image->height ); - - /* debug code */ - #if 1 - { - ddsPF_t pf; - DDSGetInfo( (ddsBuffer_t*) buffer, NULL, NULL, &pf ); - Sys_Printf( "pf = %d\n", pf ); - if ( image->width > 0 ) { - StripExtension( name ); - strcat( name, "_converted.tga" ); - WriteTGA( "C:\\games\\quake3\\baseq3\\textures\\rad\\dds_converted.tga", image->pixels, image->width, image->height ); - } - } - #endif - } - else - { - /* attempt to load ktx */ - StripExtension( name ); - strcat( name, ".ktx" ); - size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); - if ( size > 0 ) { - LoadKTXBufferFirstImage( buffer, size, &image->pixels, &image->width, &image->height ); - } - } - } - } } + if ( size > 0 ) { + LoadDDSBuffer( buffer, size, &image->pixels, &image->width, &image->height ); + goto image_load_success; + } + + /* attempt to load ktx */ + StripExtension( name ); + strcat( name, ".ktx" ); + size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); + if ( size > 0 ) { + LoadKTXBufferFirstImage( buffer, size, &image->pixels, &image->width, &image->height ); + goto image_load_success; + } + + #ifdef BUILD_CRUNCH + /* attempt to load crn */ + StripExtension( name ); + strcat( name, ".crn" ); + size = vfsLoadFile( ( const char* ) name, ( void** ) &buffer, 0 ); + if ( size > 0 ) { + LoadCRNBuffer( buffer, size, &image->pixels, &image->width, &image->height ); + goto image_load_success; + } + #endif // BUILD_CRUNCH + + /* attempt to load webp */ + StripExtension( name ); + strcat( name, ".webp" ); + size = vfsLoadFile( (const char*) name, (void**) &buffer, 0 ); + if ( size > 0 ) { + LoadWEBPBuffer( buffer, size, &image->pixels, &image->width, &image->height ); + goto image_load_success; + } + + image_load_success: + /* free file buffer */ free( buffer ); @@ -456,6 +519,9 @@ image_t *ImageLoad( const char *filename ){ return NULL; } + /* tell user which image file is found for the given texture path */ + Sys_FPrintf( SYS_VRB, "Loaded image: \"%s\"\n", name ); + /* set filename */ image->filename = safe_malloc( strlen( name ) + 1 ); strcpy( image->filename, name ); @@ -475,7 +541,7 @@ image_t *ImageLoad( const char *filename ){ if (pixels) { // On error, LoadJPGBuff might store a pointer to the error message in pixels Sys_FPrintf( SYS_WRN, "WARNING: LoadJPGBuff %s %s\n", name, (unsigned char*) pixels ); - } + } } else { if ( width == image->width && height == image->height ) { int i;