diff --git a/ChangeLog b/ChangeLog index 4358e66b..278bc7a8 100644 --- a/ChangeLog +++ b/ChangeLog @@ -12,7 +12,8 @@ im_rint(), im_equal*(), im_notequal*(), im_less*(), im_lesseq*(), im_more*(), im_moreeq*(), im_remainder*(), im_and*(), im_or*(), im_eor*(), im_shift*(), im_pow*(), im_exp*(), im_ifthenelse(), im_blend(), im_c2amph(), im_c2rect(), - im_bandmean(), im_c2real(), im_c2imag(), im_ri2c() + im_bandmean(), im_c2real(), im_c2imag(), im_ri2c(), im_jpeg*2vips(), + im_vips2jpeg*(), im_tiff2vips(), im_vips2tiff(), redone as classes - added argument priorites to help control arg ordering - generate has a 'stop' param to signal successful early termination diff --git a/TODO b/TODO index 0d3bc8d8..48d8211f 100644 --- a/TODO +++ b/TODO @@ -1,10 +1,6 @@ - still some size_t that should be guint64, search for all use of VIPS_IMAGE_SIZEOF_IMAGE(), vips__parse_size() -- some mysterious error in tilecahce for new-style openslide read - - - - how about @@ -18,12 +14,6 @@ -- add ".ndpi" to openslide suffs? though we don't really use suffs for loaders - -- check lazy load hint bug in format-hacking branch - -- everywhere must set dhint in header load - - openslide sets a g_log() handler, argh, must just set temp - make an argb coding type, add to nip2 and known coding diff --git a/libvips/conversion/tilecache.c b/libvips/conversion/tilecache.c index bd0f7789..1f277396 100644 --- a/libvips/conversion/tilecache.c +++ b/libvips/conversion/tilecache.c @@ -207,9 +207,7 @@ tile_fill( Tile *tile, VipsRegion *in ) { VipsRect area; -#ifdef DEBUG - printf( "im_tile_cache: filling tile %d x %d\n", tile->x, tile->y ); -#endif /*DEBUG*/ + VIPS_DEBUG_MSG( "tilecache: filling tile %d x %d\n", tile->x, tile->y ); area.left = tile->x; area.top = tile->y; @@ -270,9 +268,7 @@ tile_find( VipsTileCache *cache, VipsRegion *in, int x, int y ) g_assert( tile ); -#ifdef DEBUG - printf( "im_tile_cache: reusing tile %d x %d\n", tile->x, tile->y ); -#endif /*DEBUG*/ + VIPS_DEBUG_MSG( "tilecache: reusing tile %d x %d\n", tile->x, tile->y ); if( tile_move( tile, x, y ) || tile_fill( tile, in ) ) @@ -360,6 +356,8 @@ vips_tile_cache_build( VipsObject *object ) VipsConversion *conversion = VIPS_CONVERSION( object ); VipsTileCache *cache = (VipsTileCache *) object; + VIPS_DEBUG_MSG( "vips_tile_cache_build\n" ); + if( VIPS_OBJECT_CLASS( vips_tile_cache_parent_class )->build( object ) ) return( -1 ); @@ -457,7 +455,7 @@ vips_tile_cache_init( VipsTileCache *cache ) * will cache up to 1,000 tiles. * * This is a lower-level operation than vips_image_cache() since it does no - * subdivision and it single-threads it's callee. It is suitable for caching + * subdivision and it single-threads its callee. It is suitable for caching * the output of operations like exr2vips() on tiled images. * * See also: vips_image_cache(). diff --git a/libvips/foreign/Makefile.am b/libvips/foreign/Makefile.am index c376ff32..4931aa0d 100644 --- a/libvips/foreign/Makefile.am +++ b/libvips/foreign/Makefile.am @@ -1,8 +1,8 @@ noinst_LTLIBRARIES = libforeign.la libforeign_la_SOURCES = \ - vipsopenslide.h \ - vipsopenslide.c \ + openslide2vips.h \ + openslide2vips.c \ openslideload.c \ tiff.h \ vips2tiff.c \ diff --git a/libvips/foreign/jpeg2vips.c b/libvips/foreign/jpeg2vips.c index ce1c8ddf..041a648e 100644 --- a/libvips/foreign/jpeg2vips.c +++ b/libvips/foreign/jpeg2vips.c @@ -573,6 +573,10 @@ read_jpeg_header( struct jpeg_decompress_struct *cinfo, interpretation, 1.0, 1.0 ); + /* Best for us, probably. + */ + vips_demand_hint( out, VIPS_DEMAND_STYLE_FATSTRIP, NULL ); + /* Interlaced jpegs need lots of memory to read, so our caller needs * to know. */ diff --git a/libvips/foreign/vipsopenslide.c b/libvips/foreign/openslide2vips.c similarity index 88% rename from libvips/foreign/vipsopenslide.c rename to libvips/foreign/openslide2vips.c index a951f244..04ef3aa4 100644 --- a/libvips/foreign/vipsopenslide.c +++ b/libvips/foreign/openslide2vips.c @@ -65,7 +65,7 @@ #include -#include "vipsopenslide.h" +#include "openslide2vips.h" /* We run our own tile cache. The OpenSlide one can't always keep enough for a * complete lines of pixels. @@ -90,21 +90,19 @@ vips__openslide_isslide( const char *filename ) const char *vendor; int ok; - ok = 1; - osr = openslide_open( filename ); - if( osr != NULL ) { - /* If this is a generic tiled TIFF image, decline to support - * it, since im_tiff2vips can do better. + ok = 0; + if( (osr = openslide_open( filename )) ) { + /* Generic tiled tiff images can be opened by openslide as + * well. Only offer to load this file if it's not a generic + * tiff since we want vips_tiffload() to handle these. */ vendor = openslide_get_property_value( osr, OPENSLIDE_PROPERTY_NAME_VENDOR ); - if( vendor == NULL || - strcmp( vendor, "generic-tiff" ) == 0 ) - ok = 0; + if( vendor && + strcmp( vendor, "generic-tiff" ) != 0 ) + ok = 1; openslide_close( osr ); } - else - ok = 0; VIPS_DEBUG_MSG( "vips__openslide_isslide: %s - %d\n", filename, ok ); @@ -128,7 +126,7 @@ check_associated_image( openslide_t *osr, const char *name ) if( strcmp( *associated, name ) == 0 ) return( 0 ); - vips_error( "im_openslide2vips", + vips_error( "openslide2vips", "%s", _( "invalid associated image name" ) ); return( -1 ); @@ -153,21 +151,21 @@ readslide_new( const char *filename, VipsImage *out, rslide->osr = openslide_open( filename ); if( rslide->osr == NULL ) { - vips_error( "im_openslide2vips", + vips_error( "openslide2vips", "%s", _( "failure opening slide" ) ); return( NULL ); } if( layer < 0 || layer >= openslide_get_layer_count( rslide->osr ) ) { - vips_error( "im_openslide2vips", + vips_error( "openslide2vips", "%s", _( "invalid slide layer" ) ); return( NULL ); } if( associated && check_associated_image( rslide->osr, associated ) ) - return( NULL ); + return( NULL ); if( associated ) { openslide_get_associated_image_dimensions( rslide->osr, @@ -190,24 +188,24 @@ readslide_new( const char *filename, VipsImage *out, background = openslide_get_property_value( rslide->osr, OPENSLIDE_PROPERTY_NAME_BACKGROUND_COLOR ); if( background != NULL ) - im_meta_set_int( out, + vips_image_set_int( out, "background-rgb", strtoul( background, NULL, 16 ) ); else - im_meta_set_int( out, "background-rgb", 0xffffff ); + vips_image_set_int( out, "background-rgb", 0xffffff ); if( w < 0 || h < 0 || rslide->downsample < 0 ) { - vips_error( "im_openslide2vips", _( "getting dimensions: %s" ), + vips_error( "openslide2vips", _( "getting dimensions: %s" ), openslide_get_error( rslide->osr ) ); return( NULL ); } if( w > INT_MAX || h > INT_MAX ) { - vips_error( "im_openslide2vips", + vips_error( "openslide2vips", "%s", _( "image dimensions overflow int" ) ); return( NULL ); } - vips_image_init_fields( out, (int) w, (int) h, 4, VIPS_FORMAT_UCHAR, + vips_image_init_fields( out, w, h, 4, VIPS_FORMAT_UCHAR, VIPS_CODING_NONE, VIPS_INTERPRETATION_RGB, 1.0, 1.0 ); for( properties = openslide_get_property_names( rslide->osr ); @@ -245,11 +243,11 @@ vips__openslide_generate( VipsRegion *out, const char *error; int x, y; - VIPS_DEBUG_MSG( "fill_region: %dx%d @ %dx%d\n", + VIPS_DEBUG_MSG( "vips__openslide_generate: %dx%d @ %dx%d\n", r->width, r->height, r->left, r->top ); /* Fill in tile-sized chunks. Some versions of OpenSlide can fail for - * very large dimensions. + * very large requests. */ for( y = 0; y < r->height; y += TILE_HEIGHT ) for( x = 0; x < r->width; x += TILE_WIDTH ) { @@ -267,7 +265,7 @@ vips__openslide_generate( VipsRegion *out, error = openslide_get_error( rslide->osr ); if( error ) { - vips_error( "im_openslide2vips", + vips_error( "openslide2vips", _( "reading region: %s" ), error ); return( -1 ); @@ -286,9 +284,9 @@ vips__openslide_read( const char *filename, VipsImage *out, int layer ) VIPS_DEBUG_MSG( "vips__openslide_read: %s %d\n", filename, layer ); - /* Tile cache: keep enough for two complete rows of tiles. - * This lets us do (smallish) area ops, like im_conv(), while - * still only hitting each tile once. + /* Tile cache: keep enough for two complete rows of tiles. OpenSlide + * has its own tile cache, but it's not large enough for a complete + * scan line. */ raw = vips_image_new(); vips_object_local( out, raw ); @@ -307,7 +305,7 @@ vips__openslide_read( const char *filename, VipsImage *out, int layer ) if( vips_tilecache( raw, &t, "tile_width", TILE_WIDTH, "tile_height", TILE_WIDTH, - "max_tiles", 1.5 * (1 + raw->Xsize / TILE_WIDTH), + "max_tiles", (int) (1.5 * (1 + raw->Xsize / TILE_WIDTH)), NULL ) ) return( -1 ); if( vips_image_write( t, out ) ) { @@ -344,7 +342,7 @@ vips__openslide_read_associated( const char *filename, VipsImage *out, (uint32_t *) VIPS_IMAGE_ADDR( raw, 0, 0 ) ); error = openslide_get_error( rslide->osr ); if( error ) { - vips_error( "im_openslide2vips", + vips_error( "openslide2vips", _( "reading associated image: %s" ), error ); return( -1 ); } diff --git a/libvips/foreign/vipsopenslide.h b/libvips/foreign/openslide2vips.h similarity index 93% rename from libvips/foreign/vipsopenslide.h rename to libvips/foreign/openslide2vips.h index b66b121d..8fc6cdec 100644 --- a/libvips/foreign/vipsopenslide.h +++ b/libvips/foreign/openslide2vips.h @@ -27,8 +27,8 @@ */ -#ifndef VIPS_OPENSLIDE_H -#define VIPS_OPENSLIDE_H +#ifndef VIPS_OPENSLIDE2VIPS_H +#define VIPS_OPENSLIDE2VIPS_H #ifdef __cplusplus extern "C" { @@ -46,4 +46,4 @@ int vips__openslide_read_associated( const char *filename, VipsImage *out, } #endif /*__cplusplus*/ -#endif /*VIPS_OPENSLIDE_H*/ +#endif /*VIPS_OPENSLIDE2VIPS_H*/ diff --git a/libvips/foreign/openslideload.c b/libvips/foreign/openslideload.c index 17ec670b..7ad03ade 100644 --- a/libvips/foreign/openslideload.c +++ b/libvips/foreign/openslideload.c @@ -47,7 +47,7 @@ #include #include -#include "vipsopenslide.h" +#include "openslide2vips.h" typedef struct _VipsForeignLoadOpenslide { VipsForeignLoad parent_object; diff --git a/libvips/include/vips/foreign.h b/libvips/include/vips/foreign.h index aa1bf961..6f03b8d5 100644 --- a/libvips/include/vips/foreign.h +++ b/libvips/include/vips/foreign.h @@ -146,6 +146,9 @@ typedef struct _VipsForeignLoadClass { /* Set the header fields in @out from @filename. If you can read the * whole image as well with no performance cost (as with vipsload), * leave ->load() NULL and only @header will be used. + * + * ->header() needs to set the dhint on the image .. otherwise you get + * the default SMALLTILE. */ int (*header)( VipsForeignLoad * ); diff --git a/libvips/iofuncs/operation.c b/libvips/iofuncs/operation.c index 782d2327..8f65080d 100644 --- a/libvips/iofuncs/operation.c +++ b/libvips/iofuncs/operation.c @@ -28,8 +28,8 @@ */ /* - */ #define VIPS_DEBUG + */ #ifdef HAVE_CONFIG_H #include