hist hacking
This commit is contained in:
parent
81c6456b78
commit
05c5ae9734
@ -4,6 +4,7 @@
|
||||
- im_wbuffer2() renamed as vips_discsink(), some cleanups
|
||||
- im_gammacorrect() can do 16-bit images too
|
||||
- im_histplot() could fail for signed int histograms
|
||||
- im_fwfft() and im_invfft() could free their output image too early
|
||||
|
||||
16/1/10 started 7.21.2
|
||||
- "invalidate" is careful to keep images alive, so invalidate callbacks can do
|
||||
|
3
TODO
3
TODO
@ -2,6 +2,9 @@
|
||||
- lots of stupid little files in hist, eg. im_hsp.c ... paste them into larger
|
||||
modules
|
||||
|
||||
- quite a few hist operations have no GUI ... lhisteq, for example? or
|
||||
histspec?
|
||||
|
||||
- check the order of decls in hist.h, is it sensible?
|
||||
|
||||
check the order in freq_flt as well
|
||||
|
@ -30,6 +30,8 @@
|
||||
* 7/2/10
|
||||
* - cleanups
|
||||
* - gtkdoc
|
||||
* 25/3/10
|
||||
* - have a "t" image linked to out to keep the image alive for longer
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -573,6 +575,7 @@ im__fftproc( IMAGE *dummy, IMAGE *in, IMAGE *out, im__fftproc_fn fn )
|
||||
{
|
||||
IMAGE **bands;
|
||||
IMAGE **fft;
|
||||
IMAGE *t;
|
||||
int b;
|
||||
|
||||
if( in->Bands == 1 )
|
||||
@ -589,7 +592,12 @@ im__fftproc( IMAGE *dummy, IMAGE *in, IMAGE *out, im__fftproc_fn fn )
|
||||
fn( dummy, bands[b], fft[b] ) )
|
||||
return( -1 );
|
||||
|
||||
if( im_gbandjoin( fft, out, in->Bands ) )
|
||||
/* We need a "t" for the combined image that won't get freed too
|
||||
* quickly.
|
||||
*/
|
||||
if( !(t = im_open_local( out, "im__fftproc", "t" )) ||
|
||||
im_gbandjoin( fft, t, in->Bands ) ||
|
||||
im_copy( t, out ) )
|
||||
return( -1 );
|
||||
|
||||
return( 0 );
|
||||
|
@ -258,7 +258,6 @@ invfft1( IMAGE *dummy, IMAGE *in, IMAGE *out )
|
||||
#endif /*HAVE_FFTW3*/
|
||||
#endif /*HAVE_FFTW*/
|
||||
|
||||
|
||||
/**
|
||||
* im_invfft:
|
||||
* @in: input image
|
||||
|
@ -63,7 +63,7 @@
|
||||
* Histogram-equalise @in. Equalise using band @bandno, or if @bandno is -1,
|
||||
* equalise all bands.
|
||||
*
|
||||
* See also: im_histgr(), im_histeq().
|
||||
* See also: im_lhisteq(), im_histgr(), im_histeq().
|
||||
*
|
||||
* Returns: 0 on success, -1 on error
|
||||
*/
|
||||
|
@ -1,12 +1,4 @@
|
||||
/* @(#) Performs local histogram equalisation on an image using a
|
||||
* @(#) window of size xw by yw
|
||||
* @(#) Works only on monochrome images
|
||||
* @(#)
|
||||
* @(#) int im_lhisteq(in, out, xwin, ywin)
|
||||
* @(#) IMAGE *in, *out;
|
||||
* @(#) int xwin, ywin;
|
||||
* @(#)
|
||||
* @(#) Returns 0 on sucess and -1 on error
|
||||
/* local histogram equalisation
|
||||
*
|
||||
* Copyright: 1991, N. Dessipris
|
||||
*
|
||||
@ -22,6 +14,9 @@
|
||||
* - sets Xoffset/Yoffset
|
||||
* 23/6/08
|
||||
* - check for window too small as well
|
||||
* 25/3/10
|
||||
* - gtkdoc
|
||||
* - small cleanups
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -80,18 +75,12 @@ lhist_gen( REGION *or, void *seq, void *a, void *b )
|
||||
{
|
||||
REGION *ir = (REGION *) seq;
|
||||
LhistInfo *inf = (LhistInfo *) b;
|
||||
Rect irect;
|
||||
|
||||
Rect *r = &or->valid;
|
||||
int le = r->left;
|
||||
int to = r->top;
|
||||
int bo = IM_RECT_BOTTOM( r );
|
||||
int ri = IM_RECT_RIGHT( r );
|
||||
|
||||
Rect irect;
|
||||
int x, y, i, j;
|
||||
int lsk;
|
||||
|
||||
int coff; /* Offset to move to centre of window */
|
||||
int centre; /* Offset to move to centre of window */
|
||||
|
||||
/* What part of ir do we need?
|
||||
*/
|
||||
@ -99,49 +88,60 @@ lhist_gen( REGION *or, void *seq, void *a, void *b )
|
||||
irect.top = or->valid.top;
|
||||
irect.width = or->valid.width + inf->xwin;
|
||||
irect.height = or->valid.height + inf->ywin;
|
||||
|
||||
if( im_prepare( ir, &irect ) )
|
||||
return( -1 );
|
||||
lsk = IM_REGION_LSKIP( ir );
|
||||
coff = lsk * (inf->ywin / 2) + inf->xwin / 2;
|
||||
|
||||
for( y = to; y < bo; y++ ) {
|
||||
lsk = IM_REGION_LSKIP( ir );
|
||||
centre = lsk * (inf->ywin / 2) + inf->xwin / 2;
|
||||
|
||||
for( y = 0; y < r->height; y++ ) {
|
||||
/* Get input and output pointers for this line.
|
||||
*/
|
||||
PEL *p = (PEL *) IM_REGION_ADDR( ir, le, y );
|
||||
PEL *q = (PEL *) IM_REGION_ADDR( or, le, y );
|
||||
PEL *p1, *p2;
|
||||
PEL *p = (PEL *) IM_REGION_ADDR( ir, r->left, r->top + y );
|
||||
PEL *q = (PEL *) IM_REGION_ADDR( or, r->left, r->top + y );
|
||||
|
||||
PEL *p1;
|
||||
int hist[256];
|
||||
|
||||
/* Find histogram for start of this line.
|
||||
*/
|
||||
memset( hist, 0, 256 * sizeof( int ) );
|
||||
for( p1 = p, j = 0; j < inf->ywin; j++, p1 += lsk )
|
||||
for( p2 = p1, i = 0; i < inf->xwin; i++, p2++ )
|
||||
hist[*p2]++;
|
||||
p1 = p;
|
||||
for( j = 0; j < inf->ywin; j++ ) {
|
||||
for( i = 0; i < inf->xwin; i++ )
|
||||
hist[p1[i]] += 1;
|
||||
|
||||
p1 += lsk;
|
||||
}
|
||||
|
||||
/* Loop for output pels.
|
||||
*/
|
||||
for( x = le; x < ri; x++, p++ ) {
|
||||
for( x = 0; x < r->width; x++ ) {
|
||||
/* Sum histogram up to current pel.
|
||||
*/
|
||||
int target = p[coff];
|
||||
int sum = 0;
|
||||
int target = p[centre];
|
||||
int sum;
|
||||
|
||||
for( sum = 0, i = 0; i < target; i++ )
|
||||
sum = 0;
|
||||
for( i = 0; i < target; i++ )
|
||||
sum += hist[i];
|
||||
|
||||
/* Transform.
|
||||
*/
|
||||
*q++ = sum * 256 / inf->npels;
|
||||
q[x] = sum * 256 / inf->npels;
|
||||
|
||||
/* Adapt histogram - remove the pels from the left hand
|
||||
* column, add in pels for a new right-hand column.
|
||||
*/
|
||||
for( p1 = p, j = 0; j < inf->ywin; j++, p1 += lsk ) {
|
||||
hist[p1[0]]--;
|
||||
hist[p1[inf->xwin]]++;
|
||||
p1 = p;
|
||||
for( j = 0; j < inf->ywin; j++ ) {
|
||||
hist[p1[0]] -= 1;
|
||||
hist[p1[inf->xwin]] += 1;
|
||||
|
||||
p1 += lsk;
|
||||
}
|
||||
|
||||
p += 1;
|
||||
}
|
||||
}
|
||||
|
||||
@ -153,22 +153,22 @@ im_lhisteq_raw( IMAGE *in, IMAGE *out, int xwin, int ywin )
|
||||
{
|
||||
LhistInfo *inf;
|
||||
|
||||
if( im_piocheck( in, out ) )
|
||||
if( im_check_mono( "im_lhisteq", in ) ||
|
||||
im_check_uncoded( "im_lhisteq", in ) ||
|
||||
im_check_format( "im_lhisteq", in, IM_BANDFMT_UCHAR ) ||
|
||||
im_piocheck( in, out ) )
|
||||
return( -1 );
|
||||
if( in->BandFmt != IM_BANDFMT_UCHAR ||
|
||||
in->Bands != 1 || in->Coding != IM_CODING_NONE ) {
|
||||
im_error( "im_lhisteq",
|
||||
"%s", _( "one band uchar uncoded only" ) );
|
||||
return( -1 );
|
||||
}
|
||||
if( xwin > in->Xsize || ywin > in->Ysize ) {
|
||||
if( xwin > in->Xsize ||
|
||||
ywin > in->Ysize ) {
|
||||
im_error( "im_lhisteq", "%s", _( "window too large" ) );
|
||||
return( -1 );
|
||||
}
|
||||
if( xwin <= 0 || ywin <= 0 ) {
|
||||
if( xwin <= 0 ||
|
||||
ywin <= 0 ) {
|
||||
im_error( "im_lhisteq", "%s", _( "window too small" ) );
|
||||
return( -1 );
|
||||
}
|
||||
|
||||
if( im_cp_desc( out, in ) )
|
||||
return( -1 );
|
||||
out->Xsize -= xwin - 1;
|
||||
@ -188,8 +188,6 @@ im_lhisteq_raw( IMAGE *in, IMAGE *out, int xwin, int ywin )
|
||||
if( im_demand_hint( out, IM_FATSTRIP, in, NULL ) )
|
||||
return( -1 );
|
||||
|
||||
/* Write the hist.
|
||||
*/
|
||||
if( im_generate( out,
|
||||
im_start_one, lhist_gen, im_stop_one, in, inf ) )
|
||||
return( -1 );
|
||||
@ -200,14 +198,30 @@ im_lhisteq_raw( IMAGE *in, IMAGE *out, int xwin, int ywin )
|
||||
return( 0 );
|
||||
}
|
||||
|
||||
/* The above, with a border to make out the same size as in.
|
||||
/**
|
||||
* im_lhisteq:
|
||||
* @in: input image
|
||||
* @out: output image
|
||||
* @xwin: width of region
|
||||
* @hwin: height of region
|
||||
*
|
||||
* Performs local histogram equalisation on @in using a
|
||||
* window of size @xwin by @ywin centered on the input pixel. Works only on
|
||||
* monochrome images.
|
||||
*
|
||||
* The output image is the same size as the input image. The edge pixels are
|
||||
* created by copy edge pixels of the input image outwards.
|
||||
*
|
||||
* See also: im_heq().
|
||||
*
|
||||
* Returns: 0 on success, -1 on error
|
||||
*/
|
||||
int
|
||||
im_lhisteq( IMAGE *in, IMAGE *out, int xwin, int ywin )
|
||||
{
|
||||
IMAGE *t1 = im_open_local( out, "im_lhisteq:1", "p" );
|
||||
IMAGE *t1;
|
||||
|
||||
if( !t1 ||
|
||||
if( !(t1 = im_open_local( out, "im_lhisteq:1", "p" )) ||
|
||||
im_embed( in, t1, 1,
|
||||
xwin / 2, ywin / 2,
|
||||
in->Xsize + xwin - 1, in->Ysize + ywin - 1 ) ||
|
||||
|
@ -1,28 +1,4 @@
|
||||
/* @(#) 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 must be an unsigned integer types, that is, it must
|
||||
* @(#) be one of IM_BANDFMT_UCHAR, IM_BANDFMT_USHORT or IM_BANDFMT_UINT.
|
||||
* @(#)
|
||||
* @(#) If the input is IM_BANDFMT_UCHAR, then the LUT must have 256 elements,
|
||||
* @(#) in other words, lut->Xsize * lut->Ysize == 256.
|
||||
* @(#)
|
||||
* @(#) If the input is IM_BANDFMT_USHORT or IM_BANDFMT_UINT, then the lut
|
||||
* @(#) may have any number of elements, and input pels whose value is
|
||||
* @(#) greater than lut->Xsize * lut->Ysize are mapped with the last LUT
|
||||
* @(#) element.
|
||||
* @(#)
|
||||
* @(#) If LUT has one band, then all bands of input pass through it. If LUT
|
||||
* @(#) has same number of bands as input, then each band is LUTed
|
||||
* @(#) separately. If input has one band, then LUT may have many bands and
|
||||
* @(#) the output will have the same number of bands as the LUT.
|
||||
* @(#)
|
||||
* @(#) int
|
||||
* @(#) im_maplut( in, out, lut )
|
||||
* @(#) IMAGE *in, *out, *lut;
|
||||
* @(#)
|
||||
* @(#) Returns 0 on success and -1 on error
|
||||
* @(#)
|
||||
/* map though a LUT
|
||||
*
|
||||
* Modified:
|
||||
* 18/6/93 JC
|
||||
@ -50,6 +26,9 @@
|
||||
* years :-)
|
||||
* 7/11/07
|
||||
* - new eval start/end system
|
||||
* 25/3/10
|
||||
* - gtkdoc
|
||||
* - small cleanups
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -130,11 +109,11 @@ lut_end( LutInfo *st )
|
||||
static LutInfo *
|
||||
build_luts( IMAGE *out, IMAGE *lut )
|
||||
{
|
||||
LutInfo *st = IM_NEW( out, LutInfo );
|
||||
LutInfo *st;
|
||||
int i, x;
|
||||
PEL *q;
|
||||
|
||||
if( !st )
|
||||
if( !(st = IM_NEW( out, LutInfo )) )
|
||||
return( NULL );
|
||||
|
||||
/* Make luts. We unpack the LUT image into a C 2D array to speed
|
||||
@ -244,15 +223,15 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
for( y = to; y < bo; y++ ) { \
|
||||
for( z = 0; z < b; z++ ) { \
|
||||
PEL *p = (PEL *) IM_REGION_ADDR( ir, le, y ) + z; \
|
||||
OUT *q = (OUT *) IM_REGION_ADDR( or, le, y ) + z*2; \
|
||||
OUT *q = (OUT *) IM_REGION_ADDR( or, le, y ) + z * 2; \
|
||||
OUT *tlut = (OUT *) st->table[z]; \
|
||||
\
|
||||
for( x = 0; x < ne; x += b ) { \
|
||||
int n = p[x]*2; \
|
||||
int n = p[x] * 2; \
|
||||
\
|
||||
q[0] = tlut[n]; \
|
||||
q[1] = tlut[n + 1]; \
|
||||
q += b*2; \
|
||||
q += b * 2; \
|
||||
} \
|
||||
} \
|
||||
} \
|
||||
@ -287,7 +266,7 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
for( y = to; y < bo; y++ ) { \
|
||||
for( z = 0; z < b; z++ ) { \
|
||||
IN *p = (IN *) IM_REGION_ADDR( ir, le, y ) + z; \
|
||||
OUT *q = (OUT *) IM_REGION_ADDR( or, le, y ) + z*2; \
|
||||
OUT *q = (OUT *) IM_REGION_ADDR( or, le, y ) + z * 2; \
|
||||
OUT *tlut = (OUT *) st->table[z]; \
|
||||
\
|
||||
for( x = 0; x < ne; x += b ) { \
|
||||
@ -298,10 +277,10 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
seq->overflow++; \
|
||||
} \
|
||||
\
|
||||
q[0] = tlut[ index*2 ]; \
|
||||
q[1] = tlut[ index*2+1 ]; \
|
||||
q[0] = tlut[index * 2]; \
|
||||
q[1] = tlut[index * 2 + 1]; \
|
||||
\
|
||||
q += b*2; \
|
||||
q += b * 2; \
|
||||
} \
|
||||
} \
|
||||
} \
|
||||
@ -378,8 +357,8 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
seq->overflow++; \
|
||||
} \
|
||||
\
|
||||
q[0] = tlut[index*2]; \
|
||||
q[1] = tlut[index*2 + 1]; \
|
||||
q[0] = tlut[index * 2]; \
|
||||
q[1] = tlut[index * 2 + 1]; \
|
||||
q += 2; \
|
||||
} \
|
||||
} \
|
||||
@ -465,8 +444,8 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
} \
|
||||
\
|
||||
for( z = 0; z < st->nb; z++ ) { \
|
||||
q[0] = tlut[z][n*2]; \
|
||||
q[1] = tlut[z][n*2 + 1]; \
|
||||
q[0] = tlut[z][n * 2]; \
|
||||
q[1] = tlut[z][n * 2 + 1]; \
|
||||
q += 2; \
|
||||
} \
|
||||
} \
|
||||
@ -481,8 +460,7 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
case IM_BANDFMT_USHORT: GEN( unsigned short, OUT ); break; \
|
||||
case IM_BANDFMT_UINT: GEN( unsigned int, OUT ); break; \
|
||||
default: \
|
||||
im_error( "im_maplut", "%s", _( "bad input file" ) ); \
|
||||
return( -1 ); \
|
||||
g_assert( 0 ); \
|
||||
}
|
||||
|
||||
/* Switch for LUT types. One function for non-complex images, a
|
||||
@ -512,8 +490,7 @@ maplut_start( IMAGE *out, void *a, void *b )
|
||||
case IM_BANDFMT_DPCOMPLEX: inner_switch( UCHAR_FC, GEN_FC, \
|
||||
double ); break; \
|
||||
default: \
|
||||
im_error( "im_maplut", "%s", _( "bad lut file" ) ); \
|
||||
return( -1 ); \
|
||||
g_assert( 0 ); \
|
||||
}
|
||||
|
||||
/* Do a map.
|
||||
@ -529,8 +506,8 @@ maplut_gen( REGION *or, void *vseq, void *a, void *b )
|
||||
int le = r->left;
|
||||
int to = r->top;
|
||||
int bo = IM_RECT_BOTTOM(r);
|
||||
int np = r->width; /* Pels across region */
|
||||
int ne = IM_REGION_N_ELEMENTS( or ); /* Number of elements */
|
||||
int np = r->width; /* Pels across region */
|
||||
int ne = IM_REGION_N_ELEMENTS( or ); /* Number of elements */
|
||||
int x, y, z, i;
|
||||
|
||||
/* Get input ready.
|
||||
@ -557,51 +534,49 @@ maplut_gen( REGION *or, void *vseq, void *a, void *b )
|
||||
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 must be an unsigned integer types, that is, it must
|
||||
* be one of 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 )
|
||||
{
|
||||
LutInfo *st;
|
||||
|
||||
/* Check lut.
|
||||
*/
|
||||
if( lut->Coding != IM_CODING_NONE ) {
|
||||
im_error( "im_maplut", "%s", _( "lut is not uncoded" ) );
|
||||
return( -1 );
|
||||
}
|
||||
if( lut->Xsize * lut->Ysize > 100000 ) {
|
||||
im_error( "im_maplut", "%s", _( "lut seems very large!" ) );
|
||||
return( -1 );
|
||||
}
|
||||
|
||||
/* Check input output. Old-style IO from lut, for simplicity.
|
||||
*/
|
||||
if( im_piocheck( in, out ) || im_incheck( lut ) )
|
||||
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_check_uint( "im_maplut", in ) ||
|
||||
im_piocheck( in, out ) ||
|
||||
im_incheck( lut ) )
|
||||
return( -1 );
|
||||
|
||||
/* Check args.
|
||||
*/
|
||||
if( in->Coding != IM_CODING_NONE ) {
|
||||
im_error( "im_maplut", "%s", _( "input is not uncoded" ) );
|
||||
return( -1 );
|
||||
}
|
||||
if( !vips_bandfmt_isuint( in->BandFmt ) ) {
|
||||
im_error( "im_maplut", "%s",
|
||||
_( "input is not some unsigned integer type" ) );
|
||||
return( -1 );
|
||||
}
|
||||
if( in->Bands != 1 && lut->Bands != 1 && lut->Bands != in->Bands ) {
|
||||
im_error( "im_maplut", "%s", _( "lut should have 1 band, "
|
||||
"or same number of bands as input, "
|
||||
"or any number of bands if input has 1 band" ) );
|
||||
return( -1 );
|
||||
}
|
||||
if( in->BandFmt == IM_BANDFMT_UCHAR &&
|
||||
lut->Xsize * lut->Ysize != 256 ) {
|
||||
im_error( "im_maplut", "%s", _( "input is uchar and lut "
|
||||
"does not have 256 elements" ) );
|
||||
return( -1 );
|
||||
}
|
||||
|
||||
/* Prepare the output header.
|
||||
*/
|
||||
if( im_cp_descv( out, in, lut, NULL ) )
|
||||
|
@ -1,19 +1,4 @@
|
||||
/* @(#) Function which returns an int. This integer is the threshold
|
||||
* @(#) above which there are percent values of the input images
|
||||
* @(#) If for instance precent=.1, the number of pels of the input image
|
||||
* @(#) with values greater than the returned int will correspond to
|
||||
* @(#) 10% of all pels of the image.
|
||||
* @(#) One band IM_BANDFMT_UCHAR images only.
|
||||
* @(#)
|
||||
* @(#) Function im_mpercent() assumes that input
|
||||
* @(#) is either memory mapped or in a buffer.
|
||||
* @(#)
|
||||
* @(#) int im_percent(in, percent)
|
||||
* @(#) IMAGE *in;
|
||||
* @(#) double percent;
|
||||
* @(#)
|
||||
* @(#) Returns 0 on success and -1 on error
|
||||
*
|
||||
/* find percent of pixels
|
||||
* Copyright: 1990, N. Dessipris
|
||||
*
|
||||
* Author: N. Dessipris
|
||||
@ -24,6 +9,8 @@
|
||||
* - ANSIfied a little
|
||||
* 19/1/07
|
||||
* - redone with the vips hist operators
|
||||
* 25/3/10
|
||||
* - gtkdoc
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -66,8 +53,23 @@
|
||||
#include <dmalloc.h>
|
||||
#endif /*WITH_DMALLOC*/
|
||||
|
||||
/* What threshold will select a specified percentage of the pixels in the
|
||||
* image.
|
||||
/**
|
||||
* im_mpercent:
|
||||
* @in: input image
|
||||
* @percent: threshold percentage
|
||||
* @out: output threshold value
|
||||
*
|
||||
* im_mpercent() returns (through the @out parameter) the threshold above
|
||||
* which there are @percent values of @in. If for example percent=.1, the
|
||||
* number of pels of the input image with values greater than the returned
|
||||
* int will correspond to 10% of all pels of the image.
|
||||
*
|
||||
* The function works for uchar and ushort images only. It can be used
|
||||
* to threshold the scaled result of a filtering operation.
|
||||
*
|
||||
* See also: im_histgr(), im_profile().
|
||||
*
|
||||
* Returns: 0 on success, -1 on error
|
||||
*/
|
||||
int
|
||||
im_mpercent( IMAGE *in, double percent, int *out )
|
||||
|
Loading…
Reference in New Issue
Block a user