fix GIF save change detector

We were only using the top 25% of the frame for GIF pallette change
detection.

Thanks TheEssem

See: https://github.com/libvips/libvips/issues/2622
This commit is contained in:
John Cupitt 2022-01-18 18:15:38 +00:00
parent 6b475c92a2
commit 774c969d43
2 changed files with 6 additions and 3 deletions

View File

@ -8,6 +8,7 @@
- fix TTF load [chregu] - fix TTF load [chregu]
- revise GIF save alpha threshold [jfcalvo] - revise GIF save alpha threshold [jfcalvo]
- raise libpng pixel size limit from 1m to 10m pixels [jskrzypek] - raise libpng pixel size limit from 1m to 10m pixels [jskrzypek]
- fix gif save change detector [TheEssem]
21/11/21 started 8.12.1 21/11/21 started 8.12.1
- fix insert [chregu] - fix insert [chregu]

View File

@ -1,6 +1,8 @@
/* save as GIF /* save as GIF
* *
* 22/8/21 lovell * 22/8/21 lovell
* 18/1/22 TheEssem
* - fix change detector
*/ */
/* /*
@ -162,7 +164,7 @@ vips_foreign_save_cgif_write_frame( VipsForeignSaveCgif *cgif )
/* We know this fits in an int since we limit frame size. /* We know this fits in an int since we limit frame size.
*/ */
int n_pels = frame_rect->height * frame_rect->width; int n_pels = frame_rect->height * frame_rect->width;
guint max_sum = 256 * n_pels * 3; guint max_sum = 256 * n_pels * 4;
VipsPel *frame_bytes = VipsPel *frame_bytes =
VIPS_REGION_ADDR( cgif->frame, 0, frame_rect->top ); VIPS_REGION_ADDR( cgif->frame, 0, frame_rect->top );
@ -199,7 +201,7 @@ vips_foreign_save_cgif_write_frame( VipsForeignSaveCgif *cgif )
*/ */
sum = 0; sum = 0;
p = frame_bytes; p = frame_bytes;
for( i = 0; i < n_pels; i++ ) for( i = 0; i < n_pels * 4; i++ )
sum += p[i]; sum += p[i];
percent_change = 100 * percent_change = 100 *
fabs( ((double) sum / max_sum) - fabs( ((double) sum / max_sum) -
@ -433,7 +435,7 @@ vips_foreign_save_cgif_build( VipsObject *object )
frame_rect.width = cgif->in->Xsize; frame_rect.width = cgif->in->Xsize;
frame_rect.height = page_height; frame_rect.height = page_height;
if( (guint64) frame_rect.width * frame_rect.height > 2000 * 2000 ) { if( (guint64) frame_rect.width * frame_rect.height > 2000 * 2000 ) {
/* RGB sum may overflow a 32-bit uint. /* RGBA sum may overflow a 32-bit uint.
*/ */
vips_error( class->nickname, "%s", _( "frame too large" ) ); vips_error( class->nickname, "%s", _( "frame too large" ) );
return( -1 ); return( -1 );