diff options
author | Ben Campbell <ben@scumways.com> | 2015-08-20 13:42:50 +1200 |
---|---|---|
committer | Ben Campbell <ben@scumways.com> | 2015-08-20 13:42:50 +1200 |
commit | c0e964dec6feec92ffbd7ab475793a86488b5f7e (patch) | |
tree | 3cd86554a100945375249d30b299ac37c0b69872 | |
parent | adc5d934ec56f9a1bcdf420286de82ec5a5b252e (diff) | |
download | devil-c0e964dec6feec92ffbd7ab475793a86488b5f7e.tar.gz |
png: add support for palettes with alpha values
-rw-r--r-- | DevIL/include/IL/il.h | 2 | ||||
-rw-r--r-- | DevIL/src-IL/src/il_png.c | 54 |
2 files changed, 33 insertions, 23 deletions
diff --git a/DevIL/include/IL/il.h b/DevIL/include/IL/il.h index 540a56eb..d8206cbb 100644 --- a/DevIL/include/IL/il.h +++ b/DevIL/include/IL/il.h @@ -374,7 +374,7 @@ typedef long long unsigned int ILuint64; #define IL_JPG_SAVE_FORMAT 0x0721 #define IL_CHEAD_HEADER_STRING 0x0722 #define IL_PCD_PICNUM 0x0723 -#define IL_PNG_ALPHA_INDEX 0x0724 //XIX : ILint : the color in the palette at this index value (0-255) is considered transparent, -1 for no trasparent color +#define IL_PNG_ALPHA_INDEX 0x0724 // currently has no effect! #define IL_JPG_PROGRESSIVE 0x0725 #define IL_VTF_COMP 0x0726 diff --git a/DevIL/src-IL/src/il_png.c b/DevIL/src-IL/src/il_png.c index 6234ca3a..830c9f9d 100644 --- a/DevIL/src-IL/src/il_png.c +++ b/DevIL/src-IL/src/il_png.c @@ -8,10 +8,6 @@ // // Description: Portable network graphics file (.png) functions // -// 20040223 XIX : now may spit out pngs with a transparent index, this is mostly a hack -// but the proper way of doing it would be to change the pal stuff to think in argb rather than rgb -// which is something of a bigger job. -// //----------------------------------------------------------------------------- // Most of the comments are left in this file from libpng's excellent example.c @@ -495,11 +491,6 @@ ILboolean iSavePngInternal() ILuint BitDepth, i, j; ILubyte **RowPtr = NULL; ILimage *Temp = NULL; - ILpal *TempPal = NULL; - -//XIX alpha - ILubyte transpart[1]; - ILint trans; if (iCurImage == NULL) { ilSetError(IL_ILLEGAL_OPERATION); @@ -603,19 +594,40 @@ ILboolean iSavePngInternal() PNG_INTERLACE_NONE, PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE); } + // set the palette if there is one. REQUIRED for indexed-color images. if (iCurImage->Format == IL_COLOUR_INDEX) { - // set the palette if there is one. REQUIRED for indexed-color images. + ILpal *TempPal = NULL; + ILint palType; + ILint numCols; + + numCols = ilGetInteger(IL_PALETTE_NUM_COLS); + if(numCols>256) { + numCols = 256; // png maximum + } + TempPal = iConvertPal(&iCurImage->Pal, IL_PAL_RGB24); - png_set_PLTE(png_ptr, info_ptr, (png_colorp)TempPal->Palette, - ilGetInteger(IL_PALETTE_NUM_COLS)); - -//XIX alpha - trans=iGetInt(IL_PNG_ALPHA_INDEX); - if ( trans>=0) - { - transpart[0]=(ILubyte)trans; - png_set_tRNS(png_ptr, info_ptr, transpart, 1, 0); - } + png_set_PLTE(png_ptr, info_ptr, (png_colorp)TempPal->Palette, numCols); + ilClosePal(TempPal); + + palType = ilGetInteger(IL_PALETTE_TYPE); + if( palType==IL_PAL_RGBA32 || palType==IL_PAL_BGRA32 ) { + // the palette has transparency, so we need a tRNS chunk. + png_byte trans[256]; // png supports up to 256 palette entries + int maxTrans = -1; + int i; + for(i=0; i<numCols; ++i) { + ILubyte alpha = iCurImage->Pal.Palette[(4*i) + 3]; + trans[i] = alpha; + if(alpha<255) { + // record the highest non-opaque index + maxTrans = i; + } + } + // only write tRNS chunk if we've got some non-opaque colours + if(maxTrans!=-1) { + png_set_tRNS(png_ptr, info_ptr, trans, maxTrans+1, 0); + } + } } /* @@ -711,7 +723,6 @@ ILboolean iSavePngInternal() if (Temp != iCurImage) ilCloseImage(Temp); - ilClosePal(TempPal); return IL_TRUE; @@ -720,7 +731,6 @@ error_label: ifree(RowPtr); if (Temp != iCurImage) ilCloseImage(Temp); - ilClosePal(TempPal); return IL_FALSE; } |