Example #1
0
/* Transform a rect using a point transformer.
 */
static void
transform_rect( const Transformation *trn, transform_fn transform,
                const Rect *in,		/* In input space */
                Rect *out )		/* In output space */
{
    double x1, y1;		/* Map corners */
    double x2, y2;
    double x3, y3;
    double x4, y4;
    double left, right, top, bottom;

    /* Map input Rect.
     */
    transform( trn, in->left, in->top, &x1, &y1 );
    transform( trn, in->left, IM_RECT_BOTTOM( in ), &x3, &y3 );
    transform( trn, IM_RECT_RIGHT( in ), in->top, &x2, &y2 );
    transform( trn, IM_RECT_RIGHT( in ), IM_RECT_BOTTOM( in ), &x4, &y4 );

    /* Find bounding box for these four corners. Round-to-nearest to try
     * to stop rounding errors growing images.
     */
    left = IM_MIN( x1, IM_MIN( x2, IM_MIN( x3, x4 ) ) );
    right = IM_MAX( x1, IM_MAX( x2, IM_MAX( x3, x4 ) ) );
    top = IM_MIN( y1, IM_MIN( y2, IM_MIN( y3, y4 ) ) );
    bottom = IM_MAX( y1, IM_MAX( y2, IM_MAX( y3, y4 ) ) );

    out->left = IM_RINT( left );
    out->top = IM_RINT( top );
    out->width = IM_RINT( right - left );
    out->height = IM_RINT( bottom - top );
}
Example #2
0
int 
im__avgdxdy( TIE_POINTS *points, int *dx, int *dy )
{
	int sumdx, sumdy;
	int i;

	if( points->nopoints == 0 ) {
		im_error( "im_avgdxdy", "%s", _( "no points to average" ) );
		return( -1 );
	}

	/* Lots of points.
	 */
	sumdx = 0;
	sumdy = 0;
	for( i = 0; i < points->nopoints; i++ ) {
		sumdx += points->x_secondary[i] - points->x_reference[i];
		sumdy += points->y_secondary[i] - points->y_reference[i];
	}

	*dx =  IM_RINT( (double) sumdx / (double) points->nopoints );
	*dy =  IM_RINT( (double) sumdy / (double) points->nopoints );

	return( 0 );
}
Example #3
0
/**
 * im_scale_dmask:
 * @in: mask to scale
 * @filename: filename for returned mask
 *
 * Scale the dmask to make an imask with a maximum value of 20.
 *
 * See also: im_norm_dmask().
 *
 * Returns: the converted mask, or NULL on error.
 */
INTMASK *
im_scale_dmask( DOUBLEMASK *in, const char *filename )
{
	const int size = in->xsize * in->ysize;

	INTMASK *out;
	double maxval, dsum; 
	int i;
	int isum;

	if( im_check_dmask( "im_scale_dmask", in ) ||
		!(out = im_create_imask( filename, in->xsize, in->ysize )) )
		return( NULL );

	/* Find mask max.
	 */
	maxval = in->coeff[0];
	for( i = 0; i < size; i++ ) 
		if( in->coeff[i] > maxval )
			maxval = in->coeff[i];

	/* Copy and scale, setting max to 20.
	 */
	for( i = 0; i < size; i++ ) 
		out->coeff[i] = IM_RINT( in->coeff[i] * 20.0 / maxval );
	out->offset = in->offset;

	/* Set the scale to match the adjustment to max.
	 */
	isum = 0;
	dsum = 0.0;
	for( i = 0; i < size; i++ ) { 
		isum += out->coeff[i]; 
		dsum += in->coeff[i];
	}

	if( dsum == in->scale )
		out->scale = isum;
	else if( dsum == 0.0 )
		out->scale = 1.0;
	else
		out->scale = IM_RINT( in->scale * isum / dsum );

	return( out );	
}
Example #4
0
/**
 * im_dmask2imask:
 * @in: mask to convert
 * @filename: filename for returned mask
 *
 * Make an imask from the dmask, rounding to nearest. 
 *
 * See also: im_scale_dmask().
 *
 * Returns: the converted mask, or NULL on error.
 */
INTMASK *
im_dmask2imask( DOUBLEMASK *in, const char *filename )
{
	const int size = in->xsize * in->ysize;

	INTMASK *out;
	int i;

	if( im_check_dmask( "im_dmask2imask", in ) ||
		!(out = im_create_imask( filename, in->xsize, in->ysize )) )
		return( NULL );

	for( i = 0; i < size; i++ ) 
		out->coeff[i] = IM_RINT( in->coeff[i] );
	out->offset = IM_RINT( in->offset );
	out->scale = IM_RINT( in->scale );

	return( out );	
}
Example #5
0
int
im_stretch3( IMAGE *in, IMAGE *out, double dx, double dy )
{
	StretchInfo *sin;
	int i;
 
        /* Check our args. 
	 */
        if( in->Coding != IM_CODING_NONE || in->BandFmt != IM_BANDFMT_USHORT ) {
        	im_error( "im_stretch3", 
			"%s", _( "not uncoded unsigned short" ) );
        	return( -1 );
        }
	if( dx < 0 || dx >= 1.0 || dy < 0 || dy >= 1.0 ) {
		im_error( "im_stretch3", 
			"%s", _( "displacements out of range [0,1)" ) );
		return( -1 );
	}
	if( im_piocheck( in, out ) )
		return( -1 );

        /* Prepare the output image.
	 */
        if( im_cp_desc( out, in ) )
		return( -1 );
 	out->Xsize = 34*(in->Xsize / 33) + in->Xsize%33 - 3;
        out->Ysize = in->Ysize - 3;

        if( im_demand_hint( out, IM_FATSTRIP, in, NULL ) )
        	return( -1 );

        if( !(sin = IM_NEW( out, StretchInfo )) )
        	return( -1 );

	/* Save parameters.
	 */
	sin->in = in;
	sin->dx = dx;
	sin->dy = dy;

	/* Generate masks.
	 */
        for( i = 0; i < 34; i++ ) {
        	double d = (34.0 - i)/34.0;

		double y0 = 2.0*d*d - d - d*d*d;
		double y1 = 1.0 - 2.0*d*d + d*d*d;
		double y2 = d + d*d - d*d*d;
		double y3 = -d*d + d*d*d;

		sin->mask[i][0] = IM_RINT( y0 * 32768 );
		sin->mask[i][1] = IM_RINT( y1 * 32768 );
		sin->mask[i][2] = IM_RINT( y2 * 32768 );
		sin->mask[i][3] = IM_RINT( y3 * 32768 );
	}

	/* Which mask do we start with to apply these offsets?
	 */
	sin->xoff = (dx * 33.0) + 0.5;
	sin->yoff = (dy * 33.0) + 0.5;

        if( im_generate( out, 
		stretch_start, stretch_gen, stretch_stop, in, sin ) )
        	return( -1 );

	return( 0 );
}