/* Call im_conv via arg vector. */ static int conv_vec( im_object *argv ) { im_mask_object *mo = argv[2]; return( im_conv( argv[0], argv[1], mo->mask ) ); }
int im_lindetect( IMAGE *in, IMAGE *out, INTMASK *mask ) { IMAGE *filtered[4]; IMAGE *absed[4]; int i; if( im_open_local_array( out, filtered, 4, "im_lindetect:1", "p" ) || im_open_local_array( out, absed, 4, "im_lindetect:2", "p" ) ) return( -1 ); for( i = 0; i < 4; i++ ) { if( im_conv( in, filtered[i], mask ) || !(mask = (INTMASK *) im_local( out, (im_construct_fn) im_rotate_imask45, (im_callback_fn) im_free_imask, mask, mask->filename, NULL )) ) return( -1 ); } for( i = 0; i < 4; i++ ) if( im_abs( filtered[i], absed[i] ) ) return( -1 ); return( im_maxvalue( absed, out, 4 ) ); }
/** * im_ismonotonic: * @lut: lookup-table to test * @out: set non-zero if @lut is monotonic * * Test @lut for monotonicity. @out is set non-zero if @lut is monotonic. * * See also: im_tone_build_range(). * * Returns: 0 on success, -1 on error */ int im_ismonotonic( IMAGE *lut, int *out ) { IMAGE *t[2]; INTMASK *mask; double m; if( im_check_hist( "im_ismonotonic", lut ) || im_open_local_array( lut, t, 2, "im_ismonotonic", "p" ) ) return( -1 ); if( lut->Xsize == 1 ) mask = im_create_imaskv( "im_ismonotonic", 1, 2, -1, 1 ); else mask = im_create_imaskv( "im_ismonotonic", 2, 1, -1, 1 ); if( !(mask = im_local_imask( lut, mask )) ) return( -1 ); mask->offset = 128; /* We want >=128 everywhere, ie. no -ve transitions. */ if( im_conv( lut, t[0], mask ) || im_moreeqconst( t[0], t[1], 128 ) || im_min( t[1], &m ) ) return( -1 ); *out = m; return( 0 ); }
/** * im_gradient: * @in: input image * @out: output image * @mask: convolution mask * * @in is convolved with @mask and with @mask after a 90 degree rotation. The * result is the sum of the absolute value of the two convolutions. * * See also: im_lindetect(), im_gradient(), im_conv(). * * Returns: 0 on success, -1 on error */ int im_gradient( IMAGE *in, IMAGE *out, INTMASK *mask ) { IMAGE *t[4]; INTMASK *rmask; if( im_open_local_array( out, t, 4, "im_gradient", "p" ) ) return( -1 ); if( !(rmask = im_local_imask( out, im_rotate_imask90( mask, mask->filename ) )) ) return( -1 ); if( im_conv( in, t[0], mask ) || im_conv( in, t[1], rmask ) || im_abs( t[0], t[2] ) || im_abs( t[1], t[3] ) || im_add( t[2], t[3], out ) ) return( -1 ); return( 0 ); }
int im_gradient( IMAGE *in, IMAGE *out, INTMASK *mask ) { IMAGE *t[GTEMPS]; INTMASK *rmask; if( im_open_local_array( out, t, GTEMPS, "im_gradient", "p" ) ) return( -1 ); if( !(rmask = (INTMASK *) im_local( out, (im_construct_fn) im_rotate_imask90, (im_callback_fn) im_free_imask, mask, mask->filename, NULL )) ) return( -1 ); if( im_conv( in, t[0], mask ) || im_conv( in, t[1], rmask ) || im_abs( t[0], t[2] ) || im_abs( t[1], t[3] ) || im_add( t[2], t[3], out ) ) return( -1 ); return( 0 ); }
VALUE img_conv(VALUE obj, VALUE m) { DOUBLEMASK *dmask; INTMASK *imask; GetImg(obj, data, im); OutImg2(obj, m, new, data_new, im_new); mask_arg2mask(m, &imask, &dmask); if (imask) { if (im_conv(im, im_new, imask)) vips_lib_error(); } else if (im_conv_f(im, im_new, dmask)) vips_lib_error(); return new; }
/** * im_compass: * @in: input image * @out: output image * @mask: convolution mask * * @in is convolved 8 times with @mask, each time @mask is rotated by 45 * degrees. Each output pixel is the largest absolute value of the 8 * convolutions. * * See also: im_lindetect(), im_gradient(), im_conv(). * * Returns: 0 on success, -1 on error */ int im_compass( IMAGE *in, IMAGE *out, INTMASK *mask ) { IMAGE *filtered[8]; IMAGE *absed[8]; int i; if( im_open_local_array( out, filtered, 8, "im_compass:1", "p" ) || im_open_local_array( out, absed, 8, "im_compass:2", "p" ) ) return( -1 ); for( i = 0; i < 8; i++ ) { if( im_conv( in, filtered[i], mask ) || !(mask = im_local_imask( out, im_rotate_imask45( mask, mask->filename ) )) ) return( -1 ); } for( i = 0; i < 8; i++ ) if( im_abs( filtered[i], absed[i] ) ) return( -1 ); return( im_maxvalue( absed, out, 8 ) ); }
int main (int argc, char **argv) { const int NTMPS = 3; VipsImage *in, *out; VipsImage *tmps[NTMPS]; INTMASK *mask; int stat; const char *ifile, *ofile; int extractTop = 100, extractBtm = 200; check(argc == 3, "Syntax: %s <input> <output>", argv[0]); ifile = argv[1]; ofile = argv[2]; timer_start(ifile, "Setup"); if (im_init_world (argv[0])) error_exit ("unable to start VIPS"); in = im_open( ifile, "r" ); if (!in) vips_error_exit( "unable to read %s", ifile ); check(in->Ysize > 5 && in->Xsize > 5, "Input image must be larger than 5 in both dimensions", extractBtm); stat = im_open_local_array(in, tmps, NTMPS, "tt", "p"); check(!stat, "Unable to create temps."); mask = mk_convmat(); timer_done(); /* Reduce the extraction size if it's bigger than the image. */ if (extractBtm + extractTop >= in->Ysize || extractBtm + extractTop >= in->Xsize) { extractTop = 2; extractBtm = 2; }/* if */ timer_start(ifile, "im_extract_area"); check( !im_extract_area(in, tmps[0], extractTop, extractTop, in->Xsize - extractBtm, in->Ysize - extractBtm), "extract failed."); timer_done(); timer_start(ifile, "im_affine"); check( !im_affine(tmps[0], tmps[1], 0.9, 0, 0, 0.9, 0, 0, 0, 0, in->Xsize * 0.9, in->Ysize * 0.9), "im_affine failed."); timer_done(); timer_start(ifile, "im_conv"); check( !im_conv (tmps[1], tmps[2], mask), "im_conv failed."); timer_done(); timer_start(ofile, "writing output"); out = im_open(ofile, "w"); check(!!out, "file output failed."); im_copy(tmps[2], out); timer_done(); timer_start(ofile, "teardown"); im_close(out); im_close(in); timer_done(); print_times(); return 0; }/* main */
static int shrink_factor( IMAGE *in, IMAGE *out, int shrink, double residual, VipsInterpolate *interp ) { IMAGE *t[9]; VipsImage **s = (VipsImage **) vips_object_local_array( VIPS_OBJECT( out ), 1 ); IMAGE *x; int tile_width; int tile_height; int nlines; if( im_open_local_array( out, t, 9, "thumbnail", "p" ) ) return( -1 ); x = in; /* Unpack the two coded formats we support to float for processing. */ if( x->Coding == IM_CODING_LABQ ) { if( verbose ) printf( "unpacking LAB to RGB\n" ); if( im_LabQ2disp( x, t[1], im_col_displays( 7 ) ) ) return( -1 ); x = t[1]; } else if( x->Coding == IM_CODING_RAD ) { if( verbose ) printf( "unpacking Rad to float\n" ); if( im_rad2float( x, t[1] ) ) return( -1 ); x = t[1]; } if( im_shrink( x, t[2], shrink, shrink ) ) return( -1 ); /* We want to make sure we read the image sequentially. * However, the convolution we may be doing later will force us * into SMALLTILE or maybe FATSTRIP mode and that will break * sequentiality. * * So ... read into a cache where tiles are scanlines, and make sure * we keep enough scanlines to be able to serve a line of tiles. */ vips_get_tile_size( t[2], &tile_width, &tile_height, &nlines ); if( vips_tilecache( t[2], &s[0], "tile_width", t[2]->Xsize, "tile_height", 10, "max_tiles", (nlines * 2) / 10, "strategy", VIPS_CACHE_SEQUENTIAL, NULL ) || im_affinei_all( s[0], t[4], interp, residual, 0, 0, residual, 0, 0 ) ) return( -1 ); x = t[4]; /* If we are upsampling, don't sharpen, since nearest looks dumb * sharpened. */ if( shrink > 1 && residual <= 1.0 && !nosharpen ) { if( verbose ) printf( "sharpening thumbnail\n" ); if( im_conv( x, t[5], sharpen_filter() ) ) return( -1 ); x = t[5]; } /* Colour management: we can transform the image if we have an output * profile and an input profile. The input profile can be in the * image, or if there is no profile there, supplied by the user. */ if( export_profile && (im_header_get_typeof( x, IM_META_ICC_NAME ) || import_profile) ) { if( im_header_get_typeof( x, IM_META_ICC_NAME ) ) { if( verbose ) printf( "importing with embedded profile\n" ); if( im_icc_import_embedded( x, t[6], IM_INTENT_RELATIVE_COLORIMETRIC ) ) return( -1 ); } else { if( verbose ) printf( "importing with profile %s\n", import_profile ); if( im_icc_import( x, t[6], import_profile, IM_INTENT_RELATIVE_COLORIMETRIC ) ) return( -1 ); } if( verbose ) printf( "exporting with profile %s\n", export_profile ); if( im_icc_export_depth( t[6], t[7], 8, export_profile, IM_INTENT_RELATIVE_COLORIMETRIC ) ) return( -1 ); x = t[7]; } if( delete_profile ) { if( verbose ) printf( "deleting profile from output image\n" ); if( im_meta_get_typeof( x, IM_META_ICC_NAME ) && !im_meta_remove( x, IM_META_ICC_NAME ) ) return( -1 ); } if( im_copy( x, out ) ) return( -1 ); return( 0 ); }