seems to work
This commit is contained in:
parent
14d7ce1e91
commit
0a51536162
@ -16,6 +16,7 @@
|
|||||||
- rename VIPS_ANGLE_180 as VIPS_ANGLE_D180 etc. to help python
|
- rename VIPS_ANGLE_180 as VIPS_ANGLE_D180 etc. to help python
|
||||||
- remove cimg support, we have a gmic plugin now instead
|
- remove cimg support, we have a gmic plugin now instead
|
||||||
- add support for vips8 plugins
|
- add support for vips8 plugins
|
||||||
|
- added "autorotate" option to jpeg load
|
||||||
|
|
||||||
8/10/14 started 7.40.11
|
8/10/14 started 7.40.11
|
||||||
- rework extra band handling for colour functions
|
- rework extra band handling for colour functions
|
||||||
|
@ -1853,6 +1853,7 @@ vips_tiffsave( VipsImage *in, const char *filename, ... )
|
|||||||
*
|
*
|
||||||
* @shrink: shrink by this much on load
|
* @shrink: shrink by this much on load
|
||||||
* @fail: fail on warnings
|
* @fail: fail on warnings
|
||||||
|
* @autorotate: use exif Orientation tag to rotate the image during load
|
||||||
*
|
*
|
||||||
* Read a JPEG file into a VIPS image. It can read most 8-bit JPEG images,
|
* Read a JPEG file into a VIPS image. It can read most 8-bit JPEG images,
|
||||||
* including CMYK and YCbCr.
|
* including CMYK and YCbCr.
|
||||||
@ -1861,10 +1862,15 @@ vips_tiffsave( VipsImage *in, const char *filename, ... )
|
|||||||
* are 1, 2, 4 and 8. Shrinking during read is very much faster than
|
* are 1, 2, 4 and 8. Shrinking during read is very much faster than
|
||||||
* decompressing the whole image and then shrinking later.
|
* decompressing the whole image and then shrinking later.
|
||||||
*
|
*
|
||||||
* Setting @fail to true makes the JPEG reader fail on any warnings.
|
* Setting @fail to %TRUE makes the JPEG reader fail on any warnings.
|
||||||
* This can be useful for detecting truncated files, for example. Normally
|
* This can be useful for detecting truncated files, for example. Normally
|
||||||
* reading these produces a warning, but no fatal error.
|
* reading these produces a warning, but no fatal error.
|
||||||
*
|
*
|
||||||
|
* Setting @autorotate to %TRUE will make the loader interpret the EXIF
|
||||||
|
* Orientation field and automatically rotate the image appropriately during
|
||||||
|
* load. After rotation, the Orientation tag will be removed to prevent
|
||||||
|
* accidental double-rotation.
|
||||||
|
*
|
||||||
* Example:
|
* Example:
|
||||||
*
|
*
|
||||||
* |[
|
* |[
|
||||||
@ -1892,8 +1898,7 @@ vips_tiffsave( VipsImage *in, const char *filename, ... )
|
|||||||
* "jpeg-thumbnail-data". See vips_image_get_blob().
|
* "jpeg-thumbnail-data". See vips_image_get_blob().
|
||||||
*
|
*
|
||||||
* This function only reads the image header and does not decompress any pixel
|
* This function only reads the image header and does not decompress any pixel
|
||||||
* data. Decompression only occurs when pixels are accessed by some other
|
* data. Decompression only occurs when pixels are accessed.
|
||||||
* function.
|
|
||||||
*
|
*
|
||||||
* See also: vips_jpegload_buffer(), vips_image_new_from_file().
|
* See also: vips_jpegload_buffer(), vips_image_new_from_file().
|
||||||
*
|
*
|
||||||
|
@ -133,12 +133,6 @@
|
|||||||
typedef struct _ReadJpeg {
|
typedef struct _ReadJpeg {
|
||||||
VipsImage *out;
|
VipsImage *out;
|
||||||
|
|
||||||
/* The raw image size: out may have width and height swapped if we are
|
|
||||||
* autorotating.
|
|
||||||
*/
|
|
||||||
int width;
|
|
||||||
int height;
|
|
||||||
|
|
||||||
/* Shrink by this much during load. 1, 2, 4, 8.
|
/* Shrink by this much during load. 1, 2, 4, 8.
|
||||||
*/
|
*/
|
||||||
int shrink;
|
int shrink;
|
||||||
@ -167,7 +161,8 @@ typedef struct _ReadJpeg {
|
|||||||
*/
|
*/
|
||||||
int y_pos;
|
int y_pos;
|
||||||
|
|
||||||
/* Use exif tags to automatically rotate and flip image.
|
/* Use Orientation exif tag to automatically rotate and flip image
|
||||||
|
* during load.
|
||||||
*/
|
*/
|
||||||
gboolean autorotate;
|
gboolean autorotate;
|
||||||
} ReadJpeg;
|
} ReadJpeg;
|
||||||
@ -933,20 +928,6 @@ read_jpeg_header( ReadJpeg *jpeg, VipsImage *out )
|
|||||||
(VipsCallbackFn) vips_free, data, data_length );
|
(VipsCallbackFn) vips_free, data, data_length );
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Swap width and height if we're going to rotate this image. Keep the
|
|
||||||
* unrotated dimensions around too.
|
|
||||||
*/
|
|
||||||
jpeg->width = out->Xsize;
|
|
||||||
jpeg->height = out->Ysize;
|
|
||||||
|
|
||||||
if( jpeg->autorotate ) {
|
|
||||||
VipsAngle angle = get_angle( out );
|
|
||||||
|
|
||||||
if( angle == VIPS_ANGLE_D90 ||
|
|
||||||
angle == VIPS_ANGLE_D270 )
|
|
||||||
VIPS_SWAP( int, out->Xsize, out->Ysize )
|
|
||||||
}
|
|
||||||
|
|
||||||
return( 0 );
|
return( 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1101,36 +1082,11 @@ read_jpeg_image( ReadJpeg *jpeg, VipsImage *out )
|
|||||||
return( 0 );
|
return( 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Read a JPEG file into a VIPS image.
|
/* Read the jpeg from file or buffer.
|
||||||
*/
|
*/
|
||||||
int
|
static int
|
||||||
vips__jpeg_read_file( const char *filename, VipsImage *out,
|
vips__jpeg_read( ReadJpeg *jpeg, VipsImage *out, gboolean header_only )
|
||||||
gboolean header_only, int shrink, gboolean fail, gboolean readbehind,
|
|
||||||
gboolean autorotate )
|
|
||||||
{
|
{
|
||||||
ReadJpeg *jpeg;
|
|
||||||
int result;
|
|
||||||
|
|
||||||
if( !(jpeg = readjpeg_new( out,
|
|
||||||
shrink, fail, readbehind, autorotate )) )
|
|
||||||
return( -1 );
|
|
||||||
|
|
||||||
/* Here for longjmp() from vips__new_error_exit() during startup.
|
|
||||||
*/
|
|
||||||
if( setjmp( jpeg->eman.jmp ) ) {
|
|
||||||
(void) readjpeg_free( jpeg );
|
|
||||||
|
|
||||||
return( -1 );
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Set input to file.
|
|
||||||
*/
|
|
||||||
if( readjpeg_file( jpeg, filename ) ) {
|
|
||||||
(void) readjpeg_free( jpeg );
|
|
||||||
|
|
||||||
return( -1 );
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Need to read in APP1 (EXIF metadata), APP2 (ICC profile), APP13
|
/* Need to read in APP1 (EXIF metadata), APP2 (ICC profile), APP13
|
||||||
* (photoshop IPCT).
|
* (photoshop IPCT).
|
||||||
*/
|
*/
|
||||||
@ -1140,15 +1096,59 @@ vips__jpeg_read_file( const char *filename, VipsImage *out,
|
|||||||
|
|
||||||
/* Convert!
|
/* Convert!
|
||||||
*/
|
*/
|
||||||
if( header_only )
|
if( header_only ) {
|
||||||
result = read_jpeg_header( jpeg, out );
|
if( read_jpeg_header( jpeg, out ) )
|
||||||
else
|
return( -1 );
|
||||||
result = read_jpeg_image( jpeg, out );
|
|
||||||
|
|
||||||
/* Don't call readjpeg_free(), we're probably still live.
|
/* Swap width and height if we're going to rotate this image.
|
||||||
|
*/
|
||||||
|
if( jpeg->autorotate ) {
|
||||||
|
VipsAngle angle = get_angle( out );
|
||||||
|
|
||||||
|
if( angle == VIPS_ANGLE_D90 ||
|
||||||
|
angle == VIPS_ANGLE_D270 )
|
||||||
|
VIPS_SWAP( int, out->Xsize, out->Ysize );
|
||||||
|
|
||||||
|
/* We won't be returning an orientation tag.
|
||||||
|
*/
|
||||||
|
(void) vips_image_remove( out, ORIENTATION );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if( read_jpeg_image( jpeg, out ) )
|
||||||
|
return( -1 );
|
||||||
|
}
|
||||||
|
|
||||||
|
return( 0 );
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Read a JPEG file into a VIPS image.
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
vips__jpeg_read_file( const char *filename, VipsImage *out,
|
||||||
|
gboolean header_only, int shrink, gboolean fail, gboolean readbehind,
|
||||||
|
gboolean autorotate )
|
||||||
|
{
|
||||||
|
ReadJpeg *jpeg;
|
||||||
|
|
||||||
|
if( !(jpeg = readjpeg_new( out,
|
||||||
|
shrink, fail, readbehind, autorotate )) )
|
||||||
|
return( -1 );
|
||||||
|
|
||||||
|
/* Here for longjmp() from vips__new_error_exit() during startup.
|
||||||
*/
|
*/
|
||||||
|
if( setjmp( jpeg->eman.jmp ) )
|
||||||
|
return( -1 );
|
||||||
|
|
||||||
return( result );
|
/* Set input to file.
|
||||||
|
*/
|
||||||
|
if( readjpeg_file( jpeg, filename ) )
|
||||||
|
return( -1 );
|
||||||
|
|
||||||
|
if( vips__jpeg_read( jpeg, out, header_only ) )
|
||||||
|
return( -1 );
|
||||||
|
|
||||||
|
return( 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Just like the above, but we read from a memory buffer.
|
/* Just like the above, but we read from a memory buffer.
|
||||||
@ -1329,38 +1329,22 @@ vips__jpeg_read_buffer( void *buf, size_t len, VipsImage *out,
|
|||||||
gboolean autorotate )
|
gboolean autorotate )
|
||||||
{
|
{
|
||||||
ReadJpeg *jpeg;
|
ReadJpeg *jpeg;
|
||||||
int result;
|
|
||||||
|
|
||||||
if( !(jpeg = readjpeg_new( out,
|
if( !(jpeg = readjpeg_new( out,
|
||||||
shrink, fail, readbehind, autorotate )) )
|
shrink, fail, readbehind, autorotate )) )
|
||||||
return( -1 );
|
return( -1 );
|
||||||
|
|
||||||
if( setjmp( jpeg->eman.jmp ) ) {
|
if( setjmp( jpeg->eman.jmp ) )
|
||||||
(void) readjpeg_free( jpeg );
|
|
||||||
|
|
||||||
return( -1 );
|
return( -1 );
|
||||||
}
|
|
||||||
|
|
||||||
/* Set input to buffer.
|
/* Set input to buffer.
|
||||||
*/
|
*/
|
||||||
readjpeg_buffer( jpeg, buf, len );
|
readjpeg_buffer( jpeg, buf, len );
|
||||||
|
|
||||||
/* Need to read in APP1 (EXIF metadata) and APP2 (ICC profile).
|
if( vips__jpeg_read( jpeg, out, header_only ) )
|
||||||
*/
|
return( -1 );
|
||||||
jpeg_save_markers( &jpeg->cinfo, JPEG_APP0 + 1, 0xffff );
|
|
||||||
jpeg_save_markers( &jpeg->cinfo, JPEG_APP0 + 2, 0xffff );
|
|
||||||
|
|
||||||
/* Convert!
|
return( 0 );
|
||||||
*/
|
|
||||||
if( header_only )
|
|
||||||
result = read_jpeg_header( jpeg, out );
|
|
||||||
else
|
|
||||||
result = read_jpeg_image( jpeg, out );
|
|
||||||
|
|
||||||
/* Don't call readjpeg_free(), we're probably still live.
|
|
||||||
*/
|
|
||||||
|
|
||||||
return( result );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
Loading…
Reference in New Issue
Block a user