/** * im_mpercent_hist: * @hist: input histogram image * @percent: threshold percentage * @out: output threshold value * * Just like im_mpercent(), except it works on an image histogram. Handy if * you want to run im_mpercent() several times without having to recompute the * histogram each time. * * See also: im_mpercent(). * * Returns: 0 on success, -1 on error */ int im_mpercent_hist( IMAGE *hist, double percent, int *out ) { IMAGE *base; IMAGE *t[6]; double pos; if( im_check_hist( "im_mpercent", hist ) ) return( -1 ); if( !(base = im_open( "im_mpercent", "p" )) ) return( -1 ); if( im_open_local_array( base, t, 6, "im_mpercent", "p" ) ) { im_close( base ); return( -1 ); } if( im_histcum( hist, t[1] ) || im_histnorm( t[1], t[2] ) || im_lessconst( t[2], t[3], percent * t[2]->Xsize ) || im_fliphor( t[3], t[4] ) || im_profile( t[4], t[5], 1 ) || im_avg( t[5], &pos ) ) { im_close( base ); return( -1 ); } im_close( base ); *out = pos; return( 0 ); }
/** * 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_maplut: * @in: input image * @out: output image * @lut: look-up table * * Map an image through another image acting as a LUT (Look Up Table). * The lut may have any type, and the output image will be that type. * * The input image will be cast to one of the unsigned integer types, that is, * IM_BANDFMT_UCHAR, IM_BANDFMT_USHORT or IM_BANDFMT_UINT. * * If @lut is too small for the input type (for example, if @in is * IM_BANDFMT_UCHAR but @lut only has 100 elements), the lut is padded out * by copying the last element. Overflows are reported at the end of * computation. * If @lut is too large, extra values are ignored. * * If @lut has one band, then all bands of @in pass through it. If @lut * has same number of bands as @in, then each band is mapped * separately. If @in has one band, then @lut may have many bands and * the output will have the same number of bands as @lut. * * See also: im_histgr(), im_identity(). * * Returns: 0 on success, -1 on error */ int im_maplut( IMAGE *in, IMAGE *out, IMAGE *lut ) { IMAGE *t; LutInfo *st; /* Check input output. Old-style IO from lut, for simplicity. */ if( im_check_hist( "im_maplut", lut ) || im_check_uncoded( "im_maplut", lut ) || im_check_uncoded( "im_maplut", in ) || im_check_bands_1orn( "im_maplut", in, lut ) || im_piocheck( in, out ) || im_incheck( lut ) ) return( -1 ); /* Cast in to u8/u16/u32. */ if( !(t = im_open_local( out, "im_maplut", "p" )) || im_clip2fmt( in, t, bandfmt_maplut[in->BandFmt] ) ) return( -1 ); /* Prepare the output header. */ if( im_cp_descv( out, t, lut, NULL ) ) return( -1 ); /* Force output to be the same type as lut. */ out->BandFmt = lut->BandFmt; /* Output has same number of bands as LUT, unless LUT has 1 band, in * which case output has same number of bands as input. */ if( lut->Bands != 1 ) out->Bands = lut->Bands; /* Make tables. */ if( !(st = build_luts( out, lut )) ) return( -1 ); /* Set demand hints. */ if( im_demand_hint( out, IM_THINSTRIP, t, NULL ) ) return( -1 ); /* Process! */ if( im_generate( out, maplut_start, maplut_gen, maplut_stop, t, st ) ) return( -1 ); return( 0 ); }
/** * im_tone_map: * @in: input image * @out: output image * @lut: look-up table * * Map the first channel of @in through @lut. If @in is IM_CODING_LABQ, unpack * to LABS, map L and then repack. * * @in should be a LABS or LABQ image for this to work * sensibly. * * See also: im_maplut(). * * Returns: 0 on success, -1 on error */ int im_tone_map( IMAGE *in, IMAGE *out, IMAGE *lut ) { IMAGE *t[8]; if( im_check_hist( "im_tone_map", lut ) || im_open_local_array( out, t, 8, "im_tone_map", "p" ) ) return( -1 ); /* If in is IM_CODING_LABQ, unpack. */ if( in->Coding == IM_CODING_LABQ ) { if( im_LabQ2LabS( in, t[0] ) ) return( -1 ); } else t[0] = in; /* Split into bands. */ if( im_extract_band( t[0], t[1], 0 ) ) return( -1 ); if( t[0]->Bands > 1 ) { if( im_extract_bands( t[0], t[2], 1, t[0]->Bands - 1 ) ) return( -1 ); } /* Map L. */ if( im_maplut( t[1], t[3], lut ) ) return( -1 ); /* Recombine bands. */ if( t[0]->Bands > 1 ) { if( im_bandjoin( t[3], t[2], t[4] ) ) return( -1 ); } else t[4] = t[3]; /* If input was LabQ, repack. */ if( in->Coding == IM_CODING_LABQ ) { if( im_LabS2LabQ( t[4], t[5] ) ) return( -1 ); } else t[5] = t[4]; return( im_copy( t[4], out ) ); }
/** * im_histplot: * @in: input image * @out: output image * * Plot a 1 by any or any by 1 image file as a max by any or * any by max image using these rules: * * <emphasis>unsigned char</emphasis> max is always 256 * * <emphasis>other unsigned integer types</emphasis> output 0 - maxium * value of @in. * * <emphasis>signed int types</emphasis> min moved to 0, max moved to max + min. * * <emphasis>float types</emphasis> min moved to 0, max moved to any * (square output) * * See also: im_hist_indexed(), im_histeq(). * * Returns: 0 on success, -1 on error */ int im_histplot( IMAGE *in, IMAGE *out ) { IMAGE *t1; if( im_check_hist( "im_histplot", in ) ) return( -1 ); if( !(t1 = im_open_local( out, "im_histplot:1", "p" )) || normalise( in, t1 ) || plot( t1, out ) ) return( -1 ); return( 0 ); }