void Image::LoadPNG(FILE *f, char *filename, Texture *tex) { png_structp png; png_infop pnginfo; byte ioBuffer[8192]; byte *raw; int filesize = SystemFileManager::FileLength(f); raw = (byte *) malloc(filesize + 1); if (raw == NULL) { Sys_Error("Out of memory to load PNG: %s\n", filename); return; } fread(raw, 1, filesize, f); fclose(f); if (!raw) { Con_Printf("Bad png file %s\n", filename); return; } if (png_sig_cmp(raw, 0, 4)) { free(raw); return; } png = png_create_read_struct(PNG_LIBPNG_VER_STRING, 0, 0, 0); if (!png) { free(raw); return; } pnginfo = png_create_info_struct(png); if (!pnginfo) { free(raw); png_destroy_read_struct(&png, &pnginfo, 0); return; } png_set_sig_bytes(png, 0/*sizeof( sig )*/); mypng_struct_create(); // creates the my_png struct my_png->tmpBuf = (char *) raw; //buf = whole file content my_png->tmpi = 0; png_set_read_fn(png, ioBuffer, fReadData); png_read_info(png, pnginfo); png_get_IHDR(png, pnginfo, &my_png->Width, &my_png->Height, &my_png->BitDepth, &my_png->ColorType, &my_png->Interlace, &my_png->Compression, &my_png->Filter); // ...removed bgColor code here... if (my_png->ColorType == PNG_COLOR_TYPE_PALETTE) png_set_palette_to_rgb(png); if (my_png->ColorType == PNG_COLOR_TYPE_GRAY && my_png->BitDepth < 8) png_set_expand_gray_1_2_4_to_8(png); // Add alpha channel if present if (png_get_valid(png, pnginfo, PNG_INFO_tRNS)) png_set_tRNS_to_alpha(png); // hax: expand 24bit to 32bit if (my_png->BitDepth == 8 && my_png->ColorType == PNG_COLOR_TYPE_RGB) png_set_filler(png, 255, PNG_FILLER_AFTER); if ((my_png->ColorType == PNG_COLOR_TYPE_GRAY) || (my_png->ColorType == PNG_COLOR_TYPE_GRAY_ALPHA)) { png_set_gray_to_rgb(png); png_set_add_alpha(png, 255, PNG_FILLER_AFTER); } if (my_png->BitDepth < 8) png_set_expand(png); // update the info structure png_read_update_info(png, pnginfo); my_png->FRowBytes = png_get_rowbytes(png, pnginfo); my_png->BytesPerPixel = png_get_channels(png, pnginfo); // DL Added 30/08/2000 InitializeDemData(); if ((my_png->Data) && (my_png->FRowPtrs)) png_read_image(png, (png_bytepp) my_png->FRowPtrs); png_read_end(png, pnginfo); // read last information chunks png_destroy_read_struct(&png, &pnginfo, 0); if (my_png->BitDepth == 8) { tex->width = my_png->Width; tex->height = my_png->Height; tex->bytesPerPixel = my_png->BytesPerPixel; tex->setData((byte *) my_png->Data); } else { Con_Printf("Bad png color depth: %s\n", filename); free(my_png->Data); } free(raw); mypng_struct_destroy(true); return; }
void LoadPNG (char *filename, byte **pic, int *width, int *height) { png_structp png; png_infop pnginfo; byte ioBuffer[8192]; int len; byte *raw; *pic=0; len = ri.FS_LoadFile (filename, (void **)&raw); if (!raw) { ri.Con_Printf (PRINT_DEVELOPER, "Bad png file %s\n", filename); return; } if( png_sig_cmp(raw,0,4)) return; png = png_create_read_struct(PNG_LIBPNG_VER_STRING,0,0,0); if(!png) return; pnginfo = png_create_info_struct( png ); if(!pnginfo) { png_destroy_read_struct(&png,&pnginfo,0); return; } png_set_sig_bytes(png,0/*sizeof( sig )*/); mypng_struct_create(); // creates the my_png struct my_png->tmpBuf = raw; //buf = whole file content my_png->tmpi=0; png_set_read_fn(png,ioBuffer,fReadData ); png_read_info( png, pnginfo ); png_get_IHDR(png, pnginfo, &my_png->Width, &my_png->Height,&my_png->BitDepth, &my_png->ColorType, &my_png->Interlace, &my_png->Compression, &my_png->Filter ); // ...removed bgColor code here... if (my_png->ColorType == PNG_COLOR_TYPE_PALETTE) png_set_palette_to_rgb(png); if (my_png->ColorType == PNG_COLOR_TYPE_GRAY && my_png->BitDepth < 8) png_set_gray_1_2_4_to_8(png); // Add alpha channel if present if(png_get_valid( png, pnginfo, PNG_INFO_tRNS )) png_set_tRNS_to_alpha(png); // hax: expand 24bit to 32bit if (my_png->BitDepth == 8 && my_png->ColorType == PNG_COLOR_TYPE_RGB) png_set_filler(png,255, PNG_FILLER_AFTER); if (( my_png->ColorType == PNG_COLOR_TYPE_GRAY) || (my_png->ColorType == PNG_COLOR_TYPE_GRAY_ALPHA )) png_set_gray_to_rgb( png ); if (my_png->BitDepth < 8) png_set_expand (png); // update the info structure png_read_update_info( png, pnginfo ); my_png->FRowBytes = png_get_rowbytes( png, pnginfo ); my_png->BytesPerPixel = png_get_channels( png, pnginfo ); // DL Added 30/08/2000 InitializeDemData(); if((my_png->Data)&&(my_png->FRowPtrs)) png_read_image(png, (png_bytepp)my_png->FRowPtrs); png_read_end(png, pnginfo); // read last information chunks png_destroy_read_struct(&png, &pnginfo, 0); //only load 32 bit by now... if (my_png->BitDepth == 8) { *pic= my_png->Data; *width = my_png->Width; *height = my_png->Height; } else { ri.Con_Printf (PRINT_DEVELOPER, "Bad png color depth: %s\n", filename); *pic = NULL; free(my_png->Data); } mypng_struct_destroy(true); ri.FS_FreeFile ((void *)raw); }