[vtkusers] Linear interpolation as implemented by vtkImageReslice

Luca Pamparana luca.pamparana at gmail.com
Wed Sep 19 10:47:05 EDT 2007


You are fantastic. Thanks for the explanation. I will try and work out these
values by hand using the explanation you gave me and hopefully make sense of
the result!

Thank you so much!

Luca

On 9/19/07, David Gobbi <david.gobbi at gmail.com> wrote:
>
> Hi Luca,
>
> The equations for bilinear interpolation are easy.  Let's say that you
> want to interpolate a value at (x,y).  First thing the algorithm does is
> calculate (i,j) = (floor(x), floor(y)) to find the indices of a pixel in
> the
> original image.  Then it calculates fx = x-i and fy = y-j, and uses these
> to
> compute interpolation weights for the four voxels surrounding (x,y),
> so that it can give you v(x,y) which is the value of the new pixel:
>
> v(x,y) = (1-fx)(1-fy)*v(i,j) + (1-fx)(fy)*v(i,j+1) +
> (fx)(1-fy)*v(i+1,j) + (fx)(fy)*v(i+1,j+1)
>
> The reason that your results are odd must be due to the way that (x,y)
> is calculated.  For the simple vtkImageReslice example that I gave in
> my previous email, the x values at which the new pixel are interpolated
> are
> x = [0, 0.5, 1, 1.5, 2, 2.5, 3, 3.5, 4]
>
> It's just my guess by looking at your numbers, that for you the x values
> are
> x = [-0.25, 0.25, 0.75, 1.25, 1.75, 2.25, 2.75, 3.25, 3.75, 4.25]
>
> I don't want to get too technical here, but both of the above sets of x
> values
> are correct if you want to get a zoom factor of 2.0.  Which of the two
> behaviours
> you want depends on how you want edges to be handled.
>
> The first behaviour (averaging the neighboring pixels) is what you want if
> you are expanding a 5x5 image to create a 9x9 image.  As for why you get
> a 9x9 image when you do averaging like this, instead of a 10x10 image,
> that should be obvious when you think about it.
>
> The second behaviour with all those 0.25's is what you use if you really
> need
> to expand your 5x5 image into a 10x10 image.  Again, let me be clear
> on this: both of these behaviours are giving you a zoom factor of 2.0.
> The difference lies in how you want the edges to be handled.
>
> So, now about edges.  The edge of the image is defined as the position
> of the center of the outermost pixels.  Please note that I said the CENTER
> of those pixels.  That is how VTK defines the edge, and this is the best
> definition in most circumstances, so please don't argue with that
> definition.
> When vtkImageReslice needs to interpolate beyond the edge of an image,
> (e.g. when x = -0.25) the rule that is applied is as follows
> 1) if the distance from x to the edge is less than half of the output
> pixel
>     spacing, then x is clamped to the edge before interpolation occurs
> 2) if the distance is greater than half of the output pixel spacing, then
>     the output pixel is set to the background color
> 3) In vtk 4 and earlier, this "half pixel" rule doesn't apply, all
> out-of-bounds
>     pixels were set to the background value until vtk 5.0
>
> So let me quickly summarize: I think that your results are following
> behaviour 2 as described above.  Whether or not this is what you want,
> well, that's up to you.  As for why vtkImageReslice is giving you these
> results, I can't tell you that unless you post your code.
>
> David
>
>
>
> On 9/19/07, Luca Pamparana <luca.pamparana at gmail.com> wrote:
> > Hi David,
> >
> > Many many thanks for answering my question! I am really grateful.
> >
> > Yes, you are right I see that the number of pixels generated are
> correct.
> > However, I am unable to figure out what the algorithms are doing to
> generate
> > the values.
> >
> > For example, I created a small synthetic image (unsigned char) type with
> the
> > following pattern. Origin is at lower left (image dimension 5 X 5):
> >
> > 2         3              4            5            0
> > 3         4              5            0            1
> > 4         5              0            1            2
> > 5         0              1            2            3
> > 0         1              2            3            4
> >
> > switched to linear interpolation with the image and on zooming by a
> factor
> > of 2, I get the following pixel blocks:
> >
> > 2        2      3         3         4       4      5          4       1
> >   0
> > 3        3      3         4         4       4      3          2       1
> >   1
> > 3        3      4         4         5       4      1          0       1
> >   1
> > 4        4      4         4         3       2      1          1       1
> >   2
> > 4        4      5         4         1       0      1          1       2
> >   2
> > 5        4      3         2         1       1      1          2       2
> >   3
> > 5        4      1         0         1       1      2          2       3
> >   3
> > 3        2      1         1         1       2      2          3       3
> >   4
> > 0        0      1         1         2       2      3          3       4
> >   4
> > 0        0      1         1         2       2      3          3       4
> >   4
> >
> > What I want to know is how this is calculated? Could you, by any chance,
> > tell me the formula and the process as which pixels are considered when
> > calculating the intermediate values and what happens with the edge
> pixels? I
> > see the first two rows are exactly the same.
> >
> > Also, what about cubic interpolation? Is it something similar as well?
> >
> > I am attaching an image of the output, so you can see the pixel blocks.
> If
> > you load it in GIMP than you can easily see each pixel and see the
> intensity
> > value with the color picker tool...
> >
> > Again, I will be really grateful for all your help.
> >
> > Thanks,
> >
> > Luca
> >
> >
> > On 9/19/07, David Gobbi < david.gobbi at gmail.com> wrote:
> > > Hi Luca,
> > >
> > > To see how vtkImageReslice zooms an image by a factor of 2, you
> > > should be doing something like this:
> > >
> > > vtkPNGReader *reader = vtkPNGReader::New();
> > > reader->SetFileName("myfile.png");
> > > reader->SetDataSpacing(1.0, 1.0, 1.0);  // tell VTK what pixel spacing
> to
> > use
> > >
> > > vtkImageReslice *reslice = vtkImageReslice::New();
> > > reslice->SetInput(reader->GetOutput());
> > > reslice->SetOutputSpacing(0.5, 0.5, 0.5);  // resample with zoom
> factor of
> > 2.0
> > >
> > > If you write the output of this reslice to a file, you will see
> > > exactly what you expect, i.e. a new pixel inserted between all
> > > the old pixels in both the vertical and horizontal directions.  So if
> > > the original image size was 100x100, the new image will be
> > > 199x199 because 99 new pixels have been inserted in the
> > > horizontal and vertical directions.
> > >
> > > Since this is not what you are seeing, then there might be something
> > > wrong with the way you are appying the zoom factor.  If you can send
> > > a few lines of code that show how you are using vtkImageReslice, that
> > > would help me to fully answer your question.
> > >
> > > Cheers,
> > >
> > >   David
> > >
> > >
> > > On 9/19/07, Luca Pamparana <luca.pamparana at gmail.com> wrote:
> > > > Hi everyone,
> > > >
> > > > I had asked this question a few days back but did not receive any
> help.
> > > > Asking it again hoping someone would answer my query!
> > > >
> > > > Just trying to understand the linear interpolation algorithm as
> > implemented
> > > > in the vtkImageReslice class. I tried looking at the source code but
> it
> > is
> > > >
> > > > really complicated and I could not understand much :(
> > > >
> > > > Anyway, I am zooming my image by a factor of 2. The image is a
> synthetic
> > > > image which has a thick edge going along its diagonal (the value is
> > changing
> > > > from 0 to 255) and I am trying to look at how the values are
> > interpolated in
> > > > that region.
> > > >
> > > >
> > > > One thing I noticed is that there are 2 pixels being inserted in the
> > > > horizontal direction. So, I get the values 255, 191, 64 and 0 (255
> and 0
> > are
> > > > the old values and the two new values are being generated by taking
> a
> > > > weighted average). Is this correct? I thought that if I zoom by a
> factor
> > of
> > > >
> > > > 2.0 than one pixel should be inserted between successive pixels. I
> am
> > not
> > > > sure what happens at the edge pixels though.
> > > >
> > > > Also, what happens in the vertical direction? I cannot really figure
> out
> > how
> > > > this works...
> > > >
> > > >
> > > > So if I have pixel values as follows:
> > > >
> > > > 255 0 1 2
> > > > 0 255 0 1
> > > >
> > > > How is the lienar interpolation being done on a zoom of 2.0?
> > > >
> > > > I would really appreciate it if someone can clarify these doubts for
> > me....
> > > > I have spend a lot of time trying to understand this but have not
> yet
> > been
> > > > able to comprehend this implementation.
> > > >
> > > >
> > > > Thanks,
> > > >
> > > > Luca
> > > >
> > > > _______________________________________________
> > > > This is the private VTK discussion list.
> > > > Please keep messages on-topic. Check the FAQ at:
> > > > http://www.vtk.org/Wiki/VTK_FAQ
> > > > Follow this link to subscribe/unsubscribe:
> > > > http://www.vtk.org/mailman/listinfo/vtkusers
> > > >
> > > >
> > >
> >
> >
> >
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.vtk.org/pipermail/vtkusers/attachments/20070919/82a4012f/attachment.htm>


More information about the vtkusers mailing list