[prev in list] [next in list] [prev in thread] [next in thread] 

List:       gimp-developer
Subject:    Re: [Gimp-developer] Re: Lanczos filter
From:       gg () catking ! net
Date:       2006-09-26 12:53:35
Message-ID: op.tghkrlk4txpshh () linbox ! localdomain
[Download RAW message or body]

On Sun, 24 Sep 2006 20:10:01 +0200, <gg@catking.net> wrote:

> Hi,
>
> I'm trying to iron out some of the anomolies here and there are several  
> interpolations using a frig factor I dont understand. I'm probably  
> missing the point but I get the feeling this has been done impirically  
> to overcome a problem that has not been identified and may well be the  
> root cause of some of the glitches that are being seen.
>
> If I'm just being dumb, please explain and accept my appologies.
>
>
>            src_col = ((gint) (x * ratio + 2.0 - 0.5)) - 2;
>            /* +2, -2 is there because (int) rounds towards 0 and we need
>               to round down */
>
> now it seems to me that
>
>            src_col = ((gint) (x * ratio + 2.0 - 0.5)) - 2;
> is no different to
>            src_col = ((gint) (x * ratio + 1.0 - 0.5)) - 1;
> which is the same as
>            src_col = ((gint) (x * ratio + 0.5)) - 1;
>
>
> now I would normally expect something like (gint) (x * ratio + 0.5) to  
> overcome the truncation error, so why is the -1 necessary afterwards.
>
> This occurs on linear , cubic and earlier lanczos ; this suggests to me  
> that there is a bug somewhere out side the unit where this code resides.
>
>
> Why is this adjustment needed?
>
> thx.

Reply to my own question.

I've rationalised the +2 -2 senario and added comments to clearly explain  
the -0.5 adjustment. Hopefully this will save the time I lost figuring all  
this out for any poor sole that needs to look at this code in the future.

The resulting code should be slightly more efficient as well.

I will shortly submit a patch for scale-funcs.c to include this in CVS.


I suggest a similar tidy up of any parallel uses of  
GIMP_INTERPOLATION_CUBIC et al. since this applies to all interpolation  
types.




     case GIMP_INTERPOLATION_CUBIC:
       for (x = 0; x < width; x++)
         {
           /* -0.5 is because cubic() interpolates a position between 2nd  
and 3rd data points
            * we are assigning to 2nd in dest, hence mean shift of +0.5
            * +1, -1 ensures we dont (int) a negative; first src col only.
            */
           gdouble xr = x * ratio - 0.5;
           if (xr<0)
             src_col = (gint) (xr+1) - 1;
           else
             src_col = (gint) xr;
           frac = xr - src_col;
           s = &src[src_col * bytes_pp];

           for (b = 0; b < bytes_pp; b++)
             dest[b] = cubic_spline_fit (frac, s[b - bytes_pp], s[b], s[b  
+ bytes_pp],
                              s[b + bytes_pp * 2]);

           dest += bytes_pp;
         }

       break;




static inline gdouble
cubic_spline_fit (gdouble dx,
        gint    pt0,
        gint    pt1,
        gint    pt2,
        gint    pt3)
{
   /* Catmull-Rom spline - not bad
    * basic intro http://www.mvps.org/directx/articles/catmull/
    * This formula will calculate an interpolated point between pt1 and pt2
    * dx=0 returns pt1; dx=1 returns pt2
    */

   return (gdouble) ((( ( - pt0 + 3 * pt1 - 3 * pt2 + pt3 ) * dx +
       ( 2 * pt0 - 5 * pt1 + 4 * pt2 - pt3 ) ) * dx +
       ( - pt0 + pt2 ) ) * dx + (pt1 + pt1) ) / 2.0;
}

_______________________________________________
Gimp-developer mailing list
Gimp-developer@lists.XCF.Berkeley.EDU
https://lists.XCF.Berkeley.EDU/mailman/listinfo/gimp-developer

[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic