From 0803de07e7586ea3127f9f2b71710ab065f43f53 Mon Sep 17 00:00:00 2001 From: John Cupitt Date: Wed, 1 Jul 2020 17:31:25 +0100 Subject: [PATCH] move vips__lr|tbmerge to private API --- libvips/deprecated/mosaicing_dispatch.c | 4 +- libvips/deprecated/vips7compat.c | 38 ++++++ libvips/include/vips/vips7compat.h | 4 + libvips/mosaicing/Makefile.am | 4 +- libvips/mosaicing/global_balance.c | 43 ++++--- libvips/mosaicing/im_lrmosaic.c | 10 +- libvips/mosaicing/im_tbmosaic.c | 10 +- libvips/mosaicing/{im_lrmerge.c => lrmerge.c} | 115 +++++++++--------- libvips/mosaicing/merge.c | 17 ++- libvips/mosaicing/mosaic1.c | 2 +- libvips/mosaicing/{im_tbmerge.c => tbmerge.c} | 33 +++-- test/test-suite/test_mosaicing.py | 17 +-- 12 files changed, 182 insertions(+), 115 deletions(-) rename libvips/mosaicing/{im_lrmerge.c => lrmerge.c} (90%) rename libvips/mosaicing/{im_tbmerge.c => tbmerge.c} (96%) diff --git a/libvips/deprecated/mosaicing_dispatch.c b/libvips/deprecated/mosaicing_dispatch.c index ab70f938..b8f7b121 100644 --- a/libvips/deprecated/mosaicing_dispatch.c +++ b/libvips/deprecated/mosaicing_dispatch.c @@ -367,7 +367,7 @@ lrmerge_vec( im_object *argv ) int dy = *((int *) argv[4]); int mwidth = *((int *) argv[5]); - return( vips_lrmerge( argv[0], argv[1], argv[2], dx, dy, mwidth ) ); + return( im_lrmerge( argv[0], argv[1], argv[2], dx, dy, mwidth ) ); } /* Call im_lrmerge1 via arg vector. @@ -421,7 +421,7 @@ tbmerge_vec( im_object *argv ) int dy = *((int *) argv[4]); int mwidth = *((int *) argv[5]); - return( vips_tbmerge( argv[0], argv[1], argv[2], dx, dy, mwidth ) ); + return( im_tbmerge( argv[0], argv[1], argv[2], dx, dy, mwidth ) ); } /* Call im_tbmerge1 via arg vector. diff --git a/libvips/deprecated/vips7compat.c b/libvips/deprecated/vips7compat.c index dd01f70c..f0a8f2fc 100644 --- a/libvips/deprecated/vips7compat.c +++ b/libvips/deprecated/vips7compat.c @@ -5367,6 +5367,25 @@ im_tbmosaic1( IMAGE *ref, IMAGE *sec, IMAGE *out, return( 0 ); } +int +im_lrmerge( IMAGE *ref, IMAGE *sec, IMAGE *out, + int dx, int dy, int mwidth ) +{ + VipsImage *x; + + if( vips_merge( ref, sec, &x, VIPS_DIRECTION_HORIZONTAL, dx, dy, + "mblend", mwidth, + NULL ) ) + return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); + } + g_object_unref( x ); + + return( 0 ); +} + int im_lrmerge1( IMAGE *ref, IMAGE *sec, IMAGE *out, int xr1, int yr1, int xs1, int ys1, @@ -5389,6 +5408,25 @@ im_lrmerge1( IMAGE *ref, IMAGE *sec, IMAGE *out, return( 0 ); } +int +im_tbmerge( IMAGE *ref, IMAGE *sec, IMAGE *out, + int dx, int dy, int mwidth ) +{ + VipsImage *x; + + if( vips_merge( ref, sec, &x, VIPS_DIRECTION_VERTICAL, dx, dy, + "mblend", mwidth, + NULL ) ) + return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); + } + g_object_unref( x ); + + return( 0 ); +} + int im_tbmerge1( IMAGE *ref, IMAGE *sec, IMAGE *out, int xr1, int yr1, int xs1, int ys1, diff --git a/libvips/include/vips/vips7compat.h b/libvips/include/vips/vips7compat.h index 7c1f01d0..460eab0c 100644 --- a/libvips/include/vips/vips7compat.h +++ b/libvips/include/vips/vips7compat.h @@ -1065,10 +1065,14 @@ int im_global_balancef( VipsImage *in, VipsImage *out, double gamma ); int im_remosaic( VipsImage *in, VipsImage *out, const char *old_str, const char *new_str ); +int im_lrmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, + int dx, int dy, int mwidth ); int im_lrmerge1( VipsImage *ref, VipsImage *sec, VipsImage *out, int xr1, int yr1, int xs1, int ys1, int xr2, int yr2, int xs2, int ys2, int mwidth ); +int im_tbmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, + int dx, int dy, int mwidth ); int im_tbmerge1( VipsImage *ref, VipsImage *sec, VipsImage *out, int xr1, int yr1, int xs1, int ys1, int xr2, int yr2, int xs2, int ys2, diff --git a/libvips/mosaicing/Makefile.am b/libvips/mosaicing/Makefile.am index d7da3b87..9d7b4035 100644 --- a/libvips/mosaicing/Makefile.am +++ b/libvips/mosaicing/Makefile.am @@ -8,16 +8,16 @@ libmosaicing_la_SOURCES = \ mosaic1.c \ matrixinvert.c \ global_balance.c \ + lrmerge.c \ + tbmerge.c \ im_avgdxdy.c \ im_chkpair.c \ im_clinear.c \ im_improve.c \ im_initialize.c \ im_lrcalcon.c \ - im_lrmerge.c \ im_lrmosaic.c \ im_tbcalcon.c \ - im_tbmerge.c \ im_remosaic.c \ im_tbmosaic.c \ global_balance.h \ diff --git a/libvips/mosaicing/global_balance.c b/libvips/mosaicing/global_balance.c index ba45d395..3089cebf 100644 --- a/libvips/mosaicing/global_balance.c +++ b/libvips/mosaicing/global_balance.c @@ -1340,22 +1340,17 @@ make_mos_image( SymbolTable *st, JoinNode *node, transform_fn tfn, void *a ) !(im2 = make_mos_image( st, node->arg2, tfn, a )) ) return( NULL ); - out = vips_image_new(); + if( vips_merge( im1, im2, &out, + node->type == JOIN_LR ? + VIPS_DIRECTION_HORIZONTAL : + VIPS_DIRECTION_VERTICAL, + -node->dx, -node->dy, + "mblend", node->mwidth, + NULL ) ) + return( NULL ); vips_object_local( st->im, out ); - vips_image_set_string( out, "mosaic-name", node->name ); - if( node->type == JOIN_LR ) { - if( vips_lrmerge( im1, im2, out, - -node->dx, -node->dy, node->mwidth ) ) - return( NULL ); - } - else { - if( vips_tbmerge( im1, im2, out, - -node->dx, -node->dy, node->mwidth ) ) - return( NULL ); - } - break; case JOIN_LRROTSCALE: @@ -1415,6 +1410,7 @@ vips__build_mosaic( SymbolTable *st, VipsImage *out, transform_fn tfn, void *a ) { JoinNode *root = st->root; VipsImage *im1, *im2; + VipsImage *x; switch( root->type ) { case JOIN_LR: @@ -1423,16 +1419,19 @@ vips__build_mosaic( SymbolTable *st, VipsImage *out, transform_fn tfn, void *a ) !(im2 = make_mos_image( st, root->arg2, tfn, a )) ) return( -1 ); - if( root->type == JOIN_LR ) { - if( vips_lrmerge( im1, im2, out, - -root->dx, -root->dy, root->mwidth ) ) - return( -1 ); - } - else { - if( vips_tbmerge( im1, im2, out, - -root->dx, -root->dy, root->mwidth ) ) - return( -1 ); + if( vips_merge( im1, im2, &x, + root->type == JOIN_LR ? + VIPS_DIRECTION_HORIZONTAL : + VIPS_DIRECTION_VERTICAL, + -root->dx, -root->dy, + "mblend", root->mwidth, + NULL ) ) + return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); } + g_object_unref( x ); break; diff --git a/libvips/mosaicing/im_lrmosaic.c b/libvips/mosaicing/im_lrmosaic.c index 5832897a..975a062e 100644 --- a/libvips/mosaicing/im_lrmosaic.c +++ b/libvips/mosaicing/im_lrmosaic.c @@ -252,6 +252,7 @@ vips_lrmosaic( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx0, dy0; double scale1, angle1, dx1, dy1; VipsImage *dummy; + VipsImage *x; /* Correct overlap. dummy is just a placeholder used to ensure that * memory used by the analysis phase is freed as soon as possible. @@ -270,8 +271,15 @@ vips_lrmosaic( VipsImage *ref, VipsImage *sec, VipsImage *out, /* Merge left right. */ - if( vips_lrmerge( ref, sec, out, dx0, dy0, mwidth ) ) + if( vips_merge( ref, sec, &x, VIPS_DIRECTION_HORIZONTAL, dx0, dy0, + "mblend", mwidth, + NULL ) ) return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); + } + g_object_unref( x ); return( 0 ); } diff --git a/libvips/mosaicing/im_tbmosaic.c b/libvips/mosaicing/im_tbmosaic.c index 61d8364b..2d3a85ee 100644 --- a/libvips/mosaicing/im_tbmosaic.c +++ b/libvips/mosaicing/im_tbmosaic.c @@ -223,6 +223,7 @@ vips_tbmosaic( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx0, dy0; double scale1, angle1, dx1, dy1; VipsImage *dummy; + VipsImage *x; /* Correct overlap. dummy is just a placeholder used to ensure that * memory used by the analysis phase is freed as soon as possible. @@ -241,8 +242,15 @@ vips_tbmosaic( VipsImage *ref, VipsImage *sec, VipsImage *out, /* Merge top-bottom. */ - if( vips_tbmerge( ref, sec, out, dx0, dy0, mwidth ) ) + if( vips_merge( ref, sec, &x, VIPS_DIRECTION_VERTICAL, dx0, dy0, + "mblend", mwidth, + NULL ) ) return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); + } + g_object_unref( x ); return( 0 ); } diff --git a/libvips/mosaicing/im_lrmerge.c b/libvips/mosaicing/lrmerge.c similarity index 90% rename from libvips/mosaicing/im_lrmerge.c rename to libvips/mosaicing/lrmerge.c index 4bbe31f2..8bb6f9dc 100644 --- a/libvips/mosaicing/im_lrmerge.c +++ b/libvips/mosaicing/lrmerge.c @@ -203,19 +203,19 @@ find_first( VipsRegion *ir, int *pos, int x, int y, int w ) } switch( im->BandFmt ) { - case VIPS_FORMAT_UCHAR: lsearch( unsigned char ); break; - case VIPS_FORMAT_CHAR: lsearch( signed char ); break; + case VIPS_FORMAT_UCHAR: lsearch( unsigned char ); break; + case VIPS_FORMAT_CHAR: lsearch( signed char ); break; case VIPS_FORMAT_USHORT: lsearch( unsigned short ); break; - case VIPS_FORMAT_SHORT: lsearch( signed short ); break; - case VIPS_FORMAT_UINT: lsearch( unsigned int ); break; - case VIPS_FORMAT_INT: lsearch( signed int ); break; - case VIPS_FORMAT_FLOAT: lsearch( float ); break; + case VIPS_FORMAT_SHORT: lsearch( signed short ); break; + case VIPS_FORMAT_UINT: lsearch( unsigned int ); break; + case VIPS_FORMAT_INT: lsearch( signed int ); break; + case VIPS_FORMAT_FLOAT: lsearch( float ); break; case VIPS_FORMAT_DOUBLE: lsearch( double ); break; case VIPS_FORMAT_COMPLEX: lsearch( float ); break; case VIPS_FORMAT_DPCOMPLEX: lsearch( double ); break; default: - vips_error( "vips_lrmerge", "%s", _( "internal error" ) ); + g_assert_not_reached(); return( -1 ); } @@ -252,19 +252,19 @@ find_last( VipsRegion *ir, int *pos, int x, int y, int w ) } switch( im->BandFmt ) { - case VIPS_FORMAT_UCHAR: rsearch( unsigned char ); break; - case VIPS_FORMAT_CHAR: rsearch( signed char ); break; + case VIPS_FORMAT_UCHAR: rsearch( unsigned char ); break; + case VIPS_FORMAT_CHAR: rsearch( signed char ); break; case VIPS_FORMAT_USHORT: rsearch( unsigned short ); break; - case VIPS_FORMAT_SHORT: rsearch( signed short ); break; - case VIPS_FORMAT_UINT: rsearch( unsigned int ); break; - case VIPS_FORMAT_INT: rsearch( signed int ); break; - case VIPS_FORMAT_FLOAT: rsearch( float ); break; + case VIPS_FORMAT_SHORT: rsearch( signed short ); break; + case VIPS_FORMAT_UINT: rsearch( unsigned int ); break; + case VIPS_FORMAT_INT: rsearch( signed int ); break; + case VIPS_FORMAT_FLOAT: rsearch( float ); break; case VIPS_FORMAT_DOUBLE: rsearch( double ); break; case VIPS_FORMAT_COMPLEX: rsearch( float ); break; case VIPS_FORMAT_DPCOMPLEX: rsearch( double ); break; default: - vips_error( "vipslrmerge", "%s", _( "internal error" ) ); + vips_error( "lrmerge", "%s", _( "internal error" ) ); return( -1 ); } @@ -330,7 +330,7 @@ make_firstlast( MergeInfo *inf, Overlapping *ovlap, VipsRect *oreg ) sr.top -= ovlap->sarea.top; #ifdef DEBUG - printf( "vips__lrmerge: making first/last for areas:\n" ); + printf( "lrmerge: making first/last for areas:\n" ); printf( "ref: left = %d, top = %d, width = %d, height = %d\n", rr.left, rr.top, rr.width, rr.height ); printf( "sec: left = %d, top = %d, width = %d, height = %d\n", @@ -605,7 +605,7 @@ lr_blend( VipsRegion *or, MergeInfo *inf, Overlapping *ovlap, VipsRect *oreg ) fblend( double, im->Bands * 2, pr, ps, q ); break; default: - vips_error( "vips_lrmerge", "%s", _( "internal error" ) ); + g_assert_not_reached(); return( -1 ); } } @@ -616,7 +616,8 @@ lr_blend( VipsRegion *or, MergeInfo *inf, Overlapping *ovlap, VipsRect *oreg ) /* Left-right blend function for VIPS_CODING_LABQ images. */ static int -lr_blend_labpack( VipsRegion *or, MergeInfo *inf, Overlapping *ovlap, VipsRect *oreg ) +lr_blend_labpack( VipsRegion *or, MergeInfo *inf, Overlapping *ovlap, + VipsRect *oreg ) { VipsRegion *rir = inf->rir; VipsRegion *sir = inf->sir; @@ -688,11 +689,12 @@ lock_free( VipsImage *image, GMutex *lock ) } /* Build basic per-call state and do some geometry calculations. Shared with - * vips_tbmerge, so not static. + * tbmerge, so not static. */ Overlapping * vips__build_mergestate( const char *domain, - VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, int mwidth ) + VipsImage *ref, VipsImage *sec, VipsImage *out, + int dx, int dy, int mwidth ) { VipsImage **t = (VipsImage **) vips_object_local_array( VIPS_OBJECT( out ), 4 ); @@ -703,14 +705,13 @@ vips__build_mergestate( const char *domain, /* TODO(kleisauke): Copied from vips_insert, perhaps we * need a separate function for this? - * (just like im__insert_base) */ + * (just like im__insert_base) + */ if( vips_image_pio_input( ref ) || vips_image_pio_input( sec ) || - vips_check_bands_1orn( domain, - ref, sec ) || + vips_check_bands_1orn( domain, ref, sec ) || vips_check_coding_known( domain, ref ) || - vips_check_coding_same( domain, - ref, sec ) ) + vips_check_coding_same( domain, ref, sec ) ) return( NULL ); /* Cast our input images up to a common format and bands. @@ -809,11 +810,12 @@ vips__build_mergestate( const char *domain, /* Build per-call state. */ static Overlapping * -build_lrstate( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, int mwidth ) +build_lrstate( VipsImage *ref, VipsImage *sec, VipsImage *out, + int dx, int dy, int mwidth ) { Overlapping *ovlap; - if( !(ovlap = vips__build_mergestate( "vips_lrmerge", + if( !(ovlap = vips__build_mergestate( "lrmerge", ref, sec, out, dx, dy, mwidth )) ) return( NULL ); @@ -829,7 +831,7 @@ build_lrstate( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i break; default: - vips_error( "vips_lrmerge", "%s", _( "unknown coding type" ) ); + vips_error( "lrmerge", "%s", _( "unknown coding type" ) ); return( NULL ); } @@ -844,9 +846,10 @@ build_lrstate( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i /* Is there too much overlap? ie. right edge of ref image is greater * than right edge of sec image, or left > left. */ - if( VIPS_RECT_RIGHT( &ovlap->rarea ) > VIPS_RECT_RIGHT( &ovlap->sarea ) || + if( VIPS_RECT_RIGHT( &ovlap->rarea ) > + VIPS_RECT_RIGHT( &ovlap->sarea ) || ovlap->rarea.left > ovlap->sarea.left ) { - vips_error( "vips_lrmerge", "%s", _( "too much overlap" ) ); + vips_error( "lrmerge", "%s", _( "too much overlap" ) ); return( NULL ); } @@ -861,7 +864,7 @@ build_lrstate( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i * or the sec images. Attach output to the appropriate part of the input image. * area is the position that ir->im occupies in the output image. * - * Shared with vips_tbmerge(), so not static. + * Shared with tbmerge, so not static. */ int vips__attach_input( VipsRegion *or, VipsRegion *ir, VipsRect *area ) @@ -890,10 +893,11 @@ vips__attach_input( VipsRegion *or, VipsRegion *ir, VipsRect *area ) * above, but just do a sub-area of the output, and make sure we copy rather * than just pointer-fiddling. reg is the sub-area of or->valid we should do. * - * Shared with vips_tbmerge(), so not static. + * Shared with tbmerge, so not static. */ int -vips__copy_input( VipsRegion *or, VipsRegion *ir, VipsRect *area, VipsRect *reg ) +vips__copy_input( VipsRegion *or, VipsRegion *ir, + VipsRect *area, VipsRect *reg ) { VipsRect r = *reg; @@ -910,8 +914,8 @@ vips__copy_input( VipsRegion *or, VipsRegion *ir, VipsRect *area, VipsRect *reg return( 0 ); } -/* Generate function for merge. This is shared between vips_lrmerge() and - * vips_tbmerge(). +/* Generate function for merge. This is shared between lrmerge and + * tbmerge. */ int vips__merge_gen( VipsRegion *or, void *seq, void *a, void *b, @@ -981,7 +985,7 @@ vips__merge_gen( VipsRegion *or, void *seq, void *a, void *b, return( 0 ); } -/* Stop function. Shared with vips_tbmerge(). Free explicitly to reduce mem +/* Stop function. Shared with tbmerge. Free explicitly to reduce mem * requirements quickly for large mosaics. */ int @@ -999,7 +1003,7 @@ vips__stop_merge( void *seq, void *a, void *b ) return( 0 ); } -/* Start function. Shared with vips_tbmerge(). +/* Start function. Shared with tbmerge. */ void * vips__start_merge( VipsImage *out, void *a, void *b ) @@ -1041,12 +1045,13 @@ vips__start_merge( VipsImage *out, void *a, void *b ) } int -vips__lrmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, int mwidth ) +vips__lrmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, + int dx, int dy, int mwidth ) { Overlapping *ovlap; #ifdef DEBUG - printf( "vips__lrmerge %s %s %s %d %d %d\n", + printf( "lrmerge %s %s %s %d %d %d\n", ref->filename, sec->filename, out->filename, dx, dy, mwidth ); printf( "ref is %d x %d pixels\n", ref->Xsize, ref->Ysize ); @@ -1054,16 +1059,24 @@ vips__lrmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i #endif if( dx > 0 || dx < 1 - ref->Xsize ) { + VipsImage *x; + #ifdef DEBUG - printf( "vips__lrmerge: no overlap, using insert\n" ); + printf( "lrmerge: no overlap, using insert\n" ); #endif /* No overlap, use insert instead. */ - if( vips_insert( ref, sec, &out, -dx, -dy, + if( vips_insert( ref, sec, &x, -dx, -dy, "expand", TRUE, NULL ) ) return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); + } + g_object_unref( x ); + out->Xoffset = -dx; out->Yoffset = -dy; @@ -1083,7 +1096,8 @@ vips__lrmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i out->Yoffset = -dy; if( vips_image_generate( out, - vips__start_merge, vips__merge_gen, vips__stop_merge, ovlap, NULL ) ) + vips__start_merge, vips__merge_gen, vips__stop_merge, + ovlap, NULL ) ) return( -1 ); return ( 0 ); @@ -1109,8 +1123,9 @@ vips__add_mosaic_name( VipsImage *image ) { static int global_serial = 0; - /* TODO(kleisauke): Could we call vips_image_temp_name instead? */ /* Old glibs named this differently. + * + * TODO(kleisauke): Could we call vips_image_temp_name instead? */ int serial = #if GLIB_CHECK_VERSION( 2, 30, 0 ) @@ -1128,19 +1143,3 @@ vips__add_mosaic_name( VipsImage *image ) vips_image_set_string( image, "mosaic-name", name ); } -int -vips_lrmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, int mwidth ) -{ - if( vips__lrmerge( ref, sec, out, dx, dy, mwidth ) ) - return( -1 ); - - vips__add_mosaic_name( out ); - if( vips_image_history_printf( out, "#LRJOIN <%s> <%s> <%s> <%d> <%d> <%d>", - vips__get_mosaic_name( ref ), - vips__get_mosaic_name( sec ), - vips__get_mosaic_name( out ), - -dx, -dy, mwidth ) ) - return( -1 ); - - return( 0 ); -} diff --git a/libvips/mosaicing/merge.c b/libvips/mosaicing/merge.c index e2f33118..3f0b419d 100644 --- a/libvips/mosaicing/merge.c +++ b/libvips/mosaicing/merge.c @@ -41,7 +41,7 @@ #include #include -#include +#include "pmosaicing.h" typedef struct { VipsOperation parent_instance; @@ -72,13 +72,13 @@ vips_merge_build( VipsObject *object ) switch( merge->direction ) { case VIPS_DIRECTION_HORIZONTAL: - if( vips_lrmerge( merge->ref, merge->sec, merge->out, + if( vips__lrmerge( merge->ref, merge->sec, merge->out, merge->dx, merge->dy, merge->mblend ) ) return( -1 ); break; case VIPS_DIRECTION_VERTICAL: - if( vips_tbmerge( merge->ref, merge->sec, merge->out, + if( vips__tbmerge( merge->ref, merge->sec, merge->out, merge->dx, merge->dy, merge->mblend ) ) return( -1 ); break; @@ -87,6 +87,17 @@ vips_merge_build( VipsObject *object ) g_assert_not_reached(); } + vips__add_mosaic_name( merge->out ); + if( vips_image_history_printf( merge->out, + "#%s <%s> <%s> <%s> <%d> <%d> <%d>", + merge->direction == VIPS_DIRECTION_HORIZONTAL ? + "LRJOIN" : "TBJOIN", + vips__get_mosaic_name( merge->ref ), + vips__get_mosaic_name( merge->sec ), + vips__get_mosaic_name( merge->out ), + -merge->dx, -merge->dy, merge->mblend ) ) + return( -1 ); + return( 0 ); } diff --git a/libvips/mosaicing/mosaic1.c b/libvips/mosaicing/mosaic1.c index 8cebcb2b..379ed5ec 100644 --- a/libvips/mosaicing/mosaic1.c +++ b/libvips/mosaicing/mosaic1.c @@ -394,7 +394,7 @@ old_lrmosaic1( VipsImage *ref, VipsImage *sec, VipsImage *out, /* And join to ref. */ - if( vips_lrmerge( ref, t[1], out, + if( vips_merge( ref, t[1], out, VIPS_DIRECtION_HORIZONTAL, -trn2.area.left, -trn2.area.top, mwidth ) ) return( -1 ); diff --git a/libvips/mosaicing/im_tbmerge.c b/libvips/mosaicing/tbmerge.c similarity index 96% rename from libvips/mosaicing/im_tbmerge.c rename to libvips/mosaicing/tbmerge.c index 8600f25e..6959878f 100644 --- a/libvips/mosaicing/im_tbmerge.c +++ b/libvips/mosaicing/tbmerge.c @@ -663,17 +663,30 @@ build_tbstate( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i } int -vips__tbmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, int mwidth ) +vips__tbmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, + int dx, int dy, int mwidth ) { Overlapping *ovlap; if( dy > 0 || dy < 1 - ref->Ysize ) { + VipsImage *x; + +#ifdef DEBUG + printf( "vips__tbmerge: no overlap, using insert\n" ); +#endif + /* No overlap, use insert instead. */ - if( vips_insert( ref, sec, &out, -dx, -dy, + if( vips_insert( ref, sec, &x, -dx, -dy, "expand", TRUE, NULL ) ) return( -1 ); + if( vips_image_write( x, out ) ) { + g_object_unref( x ); + return( -1 ); + } + g_object_unref( x ); + out->Xoffset = -dx; out->Yoffset = -dy; @@ -699,19 +712,3 @@ vips__tbmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, i return ( 0 ); } -int -vips_tbmerge( VipsImage *ref, VipsImage *sec, VipsImage *out, int dx, int dy, int mwidth ) -{ - if( vips__tbmerge( ref, sec, out, dx, dy, mwidth ) ) - return( -1 ); - - vips__add_mosaic_name( out ); - if( vips_image_history_printf( out, "#TBJOIN <%s> <%s> <%s> <%d> <%d> <%d>", - vips__get_mosaic_name( ref ), - vips__get_mosaic_name( sec ), - vips__get_mosaic_name( out ), - -dx, -dy, mwidth ) ) - return( -1 ); - - return( 0 ); -} diff --git a/test/test-suite/test_mosaicing.py b/test/test-suite/test_mosaicing.py index f9e85be5..7d79fcb1 100644 --- a/test/test-suite/test_mosaicing.py +++ b/test/test-suite/test_mosaicing.py @@ -16,21 +16,24 @@ class TestMosaicing: im = pyvips.Image.new_from_file(files[0]) sec_im = pyvips.Image.new_from_file(files[1]) - horizontal_part = im.mosaic(sec_im, pyvips.Direction.HORIZONTAL, - marks[0][0], marks[0][1], marks[1][0], marks[1][1]) + horizontal_part = im.mosaic(sec_im, + pyvips.Direction.HORIZONTAL, + marks[0][0], marks[0][1], + marks[1][0], marks[1][1]) if mosaiced_image is None: mosaiced_image = horizontal_part else: vertical_marks = MOSAIC_VERTICAL_MARKS[i - 2:i] - mosaiced_image = mosaiced_image.mosaic(horizontal_part, pyvips.Direction.VERTICAL, - vertical_marks[1][0], vertical_marks[1][1], - vertical_marks[0][0], vertical_marks[0][1]) + mosaiced_image = mosaiced_image.mosaic(horizontal_part, + pyvips.Direction.VERTICAL, + vertical_marks[1][0], vertical_marks[1][1], + vertical_marks[0][0], vertical_marks[0][1]) - mosaiced_image = mosaiced_image.globalbalance() + mosaiced_image = mosaiced_image.globalbalance() # Uncomment to see output file - # mosaiced_image.write_to_file('1-pt-mosaic.jpg') + #mosaiced_image.write_to_file('after.jpg') # hard to test much more than this assert mosaiced_image.width == 1005