[ VIGRA Homepage | Function Index | Class Index | Namespaces | File List | Main Page ]

Image Registration VIGRA

Functions

template<class SrcIterator , class DestIterator >
linalg::TemporaryMatrix< double > affineMatrix2DFromCorrespondingPoints (SrcIterator s, SrcIterator send, DestIterator d)
 Create homogeneous matrix that maps corresponding points onto each other.
 doxygen_overloaded_function (template<...> void estimateTranslation) template< class SrcIterator
 Estimate the optical flow between two images according to a translation model.


Function Documentation

linalg::TemporaryMatrix<double> vigra::affineMatrix2DFromCorrespondingPoints ( SrcIterator  s,
SrcIterator  send,
DestIterator  d 
)

Create homogeneous matrix that maps corresponding points onto each other.

For use with affineWarpImage(). Since only two corresponding points are given, the matrix will not use a full affine transform, but only a similarity transform (translation, rotation, and uniform scaling). See \

doxygen_overloaded_function ( template<...> void  combineThreeImages  ) 

Estimate the optical flow between two images according to a translation model.

Combine three source images into destination image.

Combine ROI of two source images into destination image.

Combine two source images into destination image.

Boundary tensor variant.

Calculate the boundary tensor for a scalar valued image.

Calculate Riesz transforms of the Laplacian of Gaussian.

Resample image by a given factor.

Transpose an image over the major or minor diagonal.

Reflect image horizontally or vertically.

Rotate image by a multiple of 90 degrees.

Warp an image according to an affine transformation.

Rotate image by an arbitrary angle.

Estimate the optical flow between two images according to an affine transform model (e.g. translation, rotation, non-uniform scaling, and shearing).

Estimate the optical flow between two images according to a similarity transform model (e.g. translation, rotation, and uniform scaling).

Sorry, no detailedDocumentation() available yet.

Declarations:

#include <vigra/affine_registration.hxx>
Namespace: vigra

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor,
                  int SPLINEORDER = 2>
        void
        estimateTranslation(SrcIterator sul, SrcIterator slr, SrcAccessor src,
                            DestIterator dul, DestIterator dlr, DestAccessor dest,
                            Matrix<double> & affineMatrix,
                            AffineMotionEstimationOptions<SPLINEORDER> const & options = 
                                                        AffineMotionEstimationOptions<>())
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor,
                  int SPLINEORDER = 2>
        void
        estimateTranslation(triple<SrcIterator, SrcIterator, SrcAccessor> src,
                            triple<DestIterator, DestIterator, DestAccessor> dest,
                            Matrix<double> & affineMatrix,
                            AffineMotionEstimationOptions<SPLINEORDER> const & options =
                                                        AffineMotionEstimationOptions<>())
    }

Sorry, no detailedDocumentation() available yet.

Declarations:

#include <vigra/affine_registration.hxx>
Namespace: vigra

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor,
                  int SPLINEORDER = 2>
        void
        estimateSimilarityTransform(SrcIterator sul, SrcIterator slr, SrcAccessor src,
                            DestIterator dul, DestIterator dlr, DestAccessor dest,
                            Matrix<double> & affineMatrix,
                            AffineMotionEstimationOptions<SPLINEORDER> const & options = 
                                                        AffineMotionEstimationOptions<>())
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor,
                  int SPLINEORDER = 2>
        void
        estimateSimilarityTransform(triple<SrcIterator, SrcIterator, SrcAccessor> src,
                            triple<DestIterator, DestIterator, DestAccessor> dest,
                            Matrix<double> & affineMatrix,
                            AffineMotionEstimationOptions<SPLINEORDER> const & options =
                                                        AffineMotionEstimationOptions<>())
    }

Sorry, no detailedDocumentation() available yet.

Declarations:

#include <vigra/affine_registration.hxx>
Namespace: vigra

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor,
                  int SPLINEORDER = 2>
        void
        estimateAffineTransform(SrcIterator sul, SrcIterator slr, SrcAccessor src,
                            DestIterator dul, DestIterator dlr, DestAccessor dest,
                            Matrix<double> & affineMatrix,
                            AffineMotionEstimationOptions<SPLINEORDER> const & options = 
                                                        AffineMotionEstimationOptions<>())
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor,
                  int SPLINEORDER = 2>
        void
        estimateAffineTransform(triple<SrcIterator, SrcIterator, SrcAccessor> src,
                            triple<DestIterator, DestIterator, DestAccessor> dest,
                            Matrix<double> & affineMatrix,
                            AffineMotionEstimationOptions<SPLINEORDER> const & options =
                                                        AffineMotionEstimationOptions<>())
    }

The algorithm performs a rotation about the given center point (the image center by default) using the given SplineImageView for interpolation. The destination image must have the same size as the source SplineImageView. The rotation is counter-clockwise, and the angle must be given in degrees.

Declarations:

pass arguments explicitly:

    namespace vigra {
        // rotate about given center point
        template <int ORDER, class T, 
                  class DestIterator, class DestAccessor>
        void rotateImage(SplineImageView<ORDER, T> const & src,
                         DestIterator id, DestAccessor dest, 
                         double angleInDegree, TinyVector<double, 2> const & center);
                         
        // rotate about image center
        template <int ORDER, class T, 
                  class DestIterator, class DestAccessor>
        void 
        rotateImage(SplineImageView<ORDER, T> const & src,
                    DestIterator id, DestAccessor dest, 
                    double angleInDegree)
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        // rotate about given center point
        template <int ORDER, class T, 
                  class DestIterator, class DestAccessor>
        void 
        rotateImage(SplineImageView<ORDER, T> const & src,
                    pair<DestImageIterator, DestAccessor> dest, 
                    double angleInDegree, TinyVector<double, 2> const & center);

        // rotate about image center
        template <int ORDER, class T, 
                  class DestIterator, class DestAccessor>
        void 
        rotateImage(SplineImageView<ORDER, T> const & src,
                    pair<DestImageIterator, DestAccessor> dest, 
                    double angleInDegree);
    }

Usage:

#include <vigra/affinegeometry.hxx>
Namespace: vigra

    Image src(width, height);
    vigra::SplineImageView<3, Image::value_type> spline(srcImageRange(src));
    
    Image dest(width, height);
    
    vigra::rotateImage(spline, destImage(dest), 38.5);

Required Interface:

    DestImageIterator dest_upperleft;
    
    double x = ..., y = ...;
    
    if (spline.isInside(x,y))
        dest_accessor.set(spline(x, y), dest_upperleft);

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <int ORDER, class T, 
                class DestIterator, class DestAccessor,
                class C>
        void affineWarpImage(SplineImageView<ORDER, T> const & src,
                            DestIterator dul, DestIterator dlr, DestAccessor dest, 
                            MultiArrayView<2, double, C> const & affineMatrix);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <int ORDER, class T, 
                class DestIterator, class DestAccessor,
                class C>
        void affineWarpImage(SplineImageView<ORDER, T> const & src,
                            triple<DestIterator, DestIterator, DestAccessor> dest, 
                            MultiArrayView<2, double, C> const & affineMatrix);
    }

The algorithm applies the given affineMatrix to the destination coordinates and copies the image value from the resulting source coordinates, using the given SplineImageView src for interpolation. If the resulting coordinate is outside the source image, nothing will be writen at that destination point.

        for all dest pixels:
            currentSrcCoordinate = affineMatrix * currentDestCoordinate;
            if src.isInside(currentSrcCoordinate):
                dest[currentDestCoordinate] = src[currentSrcCoordinate]; // copy an interpolated value

The matrix represent a 2-dimensional affine transform by means of homogeneous coordinates, i.e. it must be a 3x3 matrix whose last row is (0,0,1).

Usage:

#include <vigra/affinegeometry.hxx>
Namespace: vigra

    Image src(width, height);
    vigra::SplineImageView<3, Image::value_type> spline(srcImageRange(src));
    
    Image dest1(width, height);
    
    // equivalent (up to round-off errors) with 
    //     rotateImage(spline, destImage(dest1), 45.0);
    TinyVector<double, 2> center((width-1.0)/2.0, (height-1.0)/2.0);
    affineWarpImage(spline, destImageRange(dest1), rotationMatrix2DDegrees(45.0, center));
    
    Image dest2(2*width-1, 2*height-1);
    
    // equivalent (up to round-off errors) with 
    //     resizeImageSplineInterpolation(srcImageRange(img), destImageRange(dest2));
    // note that scaleFactor = 0.5, because we must pass the transformation from destination to source
    affineWarpImage(spline, destImageRange(dest2), scalingMatrix2D(0.5));

Required Interface:

    DestImageIterator dest_upperleft;
    
    double x = ..., y = ...;
    
    if (spline.isInside(x,y))
        dest_accessor.set(spline(x, y), dest_upperleft);

See also: Functions to specify affine transformation: translationMatrix2D(), scalingMatrix2D(), shearMatrix2D(), rotationMatrix2DRadians(), rotationMatrix2DDegrees()

This algorithm just copies the pixels in the appropriate new order. It expects the destination image to have the correct shape for the desired rotation.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void 
        rotateImage(SrcIterator is, SrcIterator end, SrcAccessor as,
                    DestIterator id, DestAccessor ad, int rotation);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator, class SrcAccessor,
              class DestImageIterator, class DestAccessor>
        inline void 
        rotateImage(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
                    pair<DestImageIterator, DestAccessor> dest, int rotation);
    }

Usage:

#include <vigra/basicgeometry.hxx>
Namespace: vigra

    Image dest(src.height(), src.width()); // note that width and height are exchanged
    
    vigra::rotateImage(srcImageRange(src), destImage(dest), 90);

Required Interface:

    SrcImageIterator src_upperleft, src_lowerright;
    DestImageIterator dest_upperleft;
    
    SrcAccessor src_accessor;
    
    dest_accessor.set(src_accessor(src_upperleft), dest_upperleft);

Preconditions:

    src_lowerright.x - src_upperleft.x > 1
    src_lowerright.y - src_upperleft.y > 1

The reflection direction refers to the reflection axis, i.e. horizontal reflection turns the image upside down, vertical reflection changes left for right. The directions are selected by the enum values vigra::horizontal and vigra::vertical. The two directions can also be "or"ed together to perform both reflections simultaneously (see example below) -- this is the same as a 180 degree rotation.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void 
        reflectImage(SrcIterator is, SrcIterator end, SrcAccessor as,
                     DestIterator id, DestAccessor ad, Reflect axis);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator, class SrcAccessor,
              class DestImageIterator, class DestAccessor>
        inline void 
        reflectImage(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
                     pair<DestImageIterator, DestAccessor> dest, Reflect axis);
    }

Usage:

#include <vigra/basicgeometry.hxx>
Namespace: vigra

    Image dest(src.width(), src.height());
    
    vigra::reflectImage(srcImageRange(src), destImage(dest), vigra::horizontal | vigra::vertical);

Required Interface:

    SrcImageIterator src_upperleft, src_lowerright;
    DestImageIterator dest_upperleft;
    
    SrcAccessor src_accessor;
    
    dest_accessor.set(src_accessor(src_upperleft), dest_upperleft);

Preconditions:

    src_lowerright.x - src_upperleft.x > 1
    src_lowerright.y - src_upperleft.y > 1

The transposition direction refers to the axis, i.e. major transposition turns the upper right corner into the lower left one, whereas minor transposition changes the upper left corner into the lower right one. The directions are selected by the enum values vigra::major and vigra::minor. The two directions can also be "or"ed together to perform both reflections simultaneously (see example below) -- this is the same as a 180 degree rotation.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void 
        transposeImage(SrcIterator is, SrcIterator end, SrcAccessor as,
                       DestIterator id, DestAccessor ad, Transpose axis);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator, class SrcAccessor,
              class DestImageIterator, class DestAccessor>
        inline void 
        transposeImage(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
                       pair<DestImageIterator, DestAccessor> dest, Transpose axis);
    }

Usage:

#include <vigra/basicgeometry.hxx>
Namespace: vigra

    Image dest(src.width(), src.height());
    
    vigra::transposeImage(srcImageRange(src), destImage(dest), vigra::major | vigra::minor);

Required Interface:

    SrcImageIterator src_upperleft, src_lowerright;
    DestImageIterator dest_upperleft;
    
    SrcAccessor src_accessor;
    
    dest_accessor.set(src_accessor(src_upperleft), dest_upperleft);

Preconditions:

    src_lowerright.x - src_upperleft.x > 1
    src_lowerright.y - src_upperleft.y > 1

This algorithm is very fast and does not require any arithmetic on the pixel types. The input image must have a size of at least 2x2. Destiniation pixels are directly copied from the appropriate source pixels. The size of the result image is the product of factor and the original size, where we round up if factor < 1.0 and down otherwise. This size calculation is the main difference to the convention used in the similar function resizeImageNoInterpolation(): there, the result size is calculated as n*(old_width-1)+1 and n*(old_height-1)+1. This is because resizeImageNoInterpolation() does not replicate the last pixel in every row/column in order to make it compatible with the other functions of the resizeImage... family.

The function can be called with different resampling factors for x and y, or with a single factor to be used for both directions.

It should also be noted that resampleImage() is implemented so that an enlargement followed by the corresponding shrinking reproduces the original image. The function uses accessors.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void 
        resampleImage(SrcIterator is, SrcIterator iend, SrcAccessor sa,
                      DestIterator id, DestAccessor ad, double factor);
                      
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void 
        resampleImage(SrcIterator is, SrcIterator iend, SrcAccessor sa,
                      DestIterator id, DestAccessor ad, double xfactor, double yfactor);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator, class SrcAccessor,
              class DestImageIterator, class DestAccessor>
        inline void 
        resampleImage(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
                      pair<DestImageIterator, DestAccessor> dest, double factor);
                      
        template <class SrcImageIterator, class SrcAccessor,
              class DestImageIterator, class DestAccessor>
        inline void 
        resampleImage(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
                      pair<DestImageIterator, DestAccessor> dest, double xfactor, double yfactor);
    }

Usage:

#include <vigra/basicgeometry.hxx>
Namespace: vigra

    double factor = 2.0;
    Image dest((int)(factor*src.width()), (int)(factor*src.height()));
    
    vigra::resampleImage(srcImageRange(src), destImage(dest), factor);

Required Interface:

    SrcImageIterator src_upperleft, src_lowerright;
    DestImageIterator dest_upperleft;
    
    SrcAccessor src_accessor;
    
    dest_accessor.set(src_accessor(src_upperleft), dest_upperleft);

Preconditions:

    src_lowerright.x - src_upperleft.x > 1
    src_lowerright.y - src_upperleft.y > 1

The Riesz transforms of the Laplacian of Gaussian have the following transfer functions (defined in a polar coordinate representation of the frequency domain):

\[ F_{\sigma}(r, \phi)=(i \cos \phi)^n (i \sin \phi)^m r^2 e^{-r^2 \sigma^2 / 2} \]

where n = xorder and m = yorder determine th e order of the transform, and sigma > 0 is the scale of the Laplacian of Gaussian. This function computes a good spatial domain approximation of these transforms for xorder + yorder <= 2. The filter responses may be used to calculate the monogenic signal or the boundary tensor.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                class DestIterator, class DestAccessor>
        void rieszTransformOfLOG(SrcIterator supperleft, SrcIterator slowerright, SrcAccessor src,
                                 DestIterator dupperleft, DestAccessor dest,
                                 double scale, unsigned int xorder, unsigned int yorder);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                class DestIterator, class DestAccessor>
        void rieszTransformOfLOG(triple<SrcIterator, SrcIterator, SrcAccessor> src,
                                 pair<DestIterator, DestAccessor> dest,
                                 double scale, unsigned int xorder, unsigned int yorder);
    }

Usage:

#include <vigra/boundarytensor.hxx>

    FImage impulse(17,17), res(17, 17);
    impulse(8,8) = 1.0;

    // calculate the impulse response of the first order Riesz transform in x-direction
    rieszTransformOfLOG(srcImageRange(impulse), destImage(res), 2.0, 1, 0);

These functions calculate a spatial domain approximation of the boundary tensor as described in

U. Köthe: "Integrated Edge and Junction Detection with the Boundary Tensor", in: ICCV 03, Proc. of 9th Intl. Conf. on Computer Vision, Nice 2003, vol. 1, pp. 424-431, Los Alamitos: IEEE Computer Society, 2003

with the Laplacian of Gaussian as the underlying bandpass filter (see rieszTransformOfLOG()). The output image must have 3 bands which will hold the tensor components in the order t11, t12 (== t21), t22. The function boundaryTensor1() with the same interface implements a variant of the boundary tensor where the 0th-order Riesz transform has been dropped, so that the tensor is no longer sensitive to blobs.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void boundaryTensor(SrcIterator supperleft, SrcIterator slowerright, SrcAccessor src,
                            DestIterator dupperleft, DestAccessor dest,
                            double scale);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void boundaryTensor(triple<SrcIterator, SrcIterator, SrcAccessor> src,
                            pair<DestIterator, DestAccessor> dest,
                            double scale);
    }

Usage:

#include <vigra/boundarytensor.hxx>

    FImage img(w,h);
    FVector3Image bt(w,h);
    ...
    boundaryTensor(srcImageRange(img), destImage(bt), 2.0);

This function implements a variant of the boundary tensor where the 0th-order Riesz transform has been dropped, so that the tensor is no longer sensitive to blobs. See boundaryTensor() for more detailed documentation.

Declarations:

#include <vigra/boundarytensor.hxx>

pass arguments explicitly:

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void boundaryTensor1(SrcIterator supperleft, SrcIterator slowerright, SrcAccessor src,
                             DestIterator dupperleft, DestAccessor dest,
                             double scale);
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcIterator, class SrcAccessor,
                  class DestIterator, class DestAccessor>
        void boundaryTensor1(triple<SrcIterator, SrcIterator, SrcAccessor> src,
                             pair<DestIterator, DestAccessor> dest,
                             double scale);
    }

The transformation given by the functor is applied to the source pixels and the result written into the corresponding destination pixel. This is typically used for operations like add and subtract. The function uses accessors to access the pixel data. Note that the binary functors of the STL can be used in addition to the functors specifically defined in Functors to Combine Images. Creation of new functors is easiest by using Functor Expressions.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcImageIterator1, class SrcAccessor1,
              class SrcImageIterator2, class SrcAccessor2,
              class DestImageIterator, class DestAccessor,
              class Functor>
        void
        combineTwoImages(SrcImageIterator1 src1_upperleft, 
                 SrcImageIterator1 src1_lowerright, SrcAccessor1 sa1,
                 SrcImageIterator2 src2_upperleft, SrcAccessor2 sa2,
                 DestImageIterator dest_upperleft, DestAccessor da,
                 Functor const & f)
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator1, class SrcAccessor1,
              class SrcImageIterator2, class SrcAccessor2,
              class DestImageIterator, class DestAccessor,
              class Functor>
        void
        combineTwoImages(triple<SrcImageIterator1, SrcImageIterator1, SrcAccessor1> src1,
                 pair<SrcImageIterator2, SrcAccessor2> src2,
                 pair<DestImageIterator, DestAccessor> dest,
                 Functor const & f)
    }

Usage:

#include <vigra/combineimages.hxx>
Namespace: vigra

    #include <functional>     // for plus

    vigra::combineTwoImages(
                srcIterRange(src1.upperLeft(), src1.lowerRight()), 
                srcIter(src2.upperLeft()), 
                destIter(dest.upperLeft()),  
                std::plus<SrcValueType>());

Note that SrcValueType must be replaced with the appropriate type (e.g. the promote type of the input images' pixel type, see also Numeric and Promotion Traits)

Required Interface:

    SrcImageIterator1 src1_upperleft, src1_lowerright;
    SrcImageIterator2 src2_upperleft;
    DestImageIterator dest_upperleft;
    SrcImageIterator1::row_iterator sx1 = src1_upperleft.rowIterator();
    SrcImageIterator2::row_iterator sx2 = src2_upperleft.rowIterator();
    DestImageIterator::row_iterator dx = dest_upperleft.rowIterator();
    
    SrcAccessor1 src1_accessor;
    SrcAccessor2 src2_accessor;
    DestAccessor dest_accessor;
    
    Functor functor;

    dest_accessor.set(
          functor(src1_accessor(sx1), src2_accessor(sx2)), 
          dx);

The transformation given by the functor is applied to all source pixels in the ROI (i.e. whenever the return value of the mask's accessor is not zero) and the result written into the corresponding destination pixel. This is typically used for operations like add and subtract. The function uses accessors to access the pixel data. Note that the binary functors of the STL can be used in addition to the functors specifically defined in Functors to Combine Images. Creation of new functors is easiest by using Functor Expressions.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcImageIterator1, class SrcAccessor1,
              class SrcImageIterator2, class SrcAccessor2,
              class MaskImageIterator, class MaskAccessor,
              class DestImageIterator, clas DestAccessor,
              class Functor>
        void
        combineTwoImagesIf(SrcImageIterator1 src1_upperleft, 
                   SrcImageIterator1 src1_lowerright, SrcAccessor1 sa1,
                   SrcImageIterator2 src2_upperleft, SrcAccessor2 sa2,
                   MaskImageIterator mask_upperleft, MaskAccessor ma,
                   DestImageIterator dest_upperleft, DestAccessor da,
                   Functor const & f)
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator1, class SrcAccessor1,
              class SrcImageIterator2, class SrcAccessor2,
              class MaskImageIterator, class MaskAccessor,
              class DestImageIterator, clas DestAccessor,
              class Functor>
        void
        combineTwoImagesIf(triple<SrcImageIterator1, SrcImageIterator1, SrcAccessor1> src1,
                   pair<SrcImageIterator2, SrcAccessor2> src2,
                   pair<MaskImageIterator, MaskAccessor> mask,
                   pair<DestImageIterator, DestAccessor> dest,
                   Functor const & f)
    }

Usage:

#include <vigra/combineimages.hxx>
Namespace: vigra

    #include <functional>     // for plus

    vigra::combineTwoImagesIf(
                srcIterRange(src1.upperLeft(), src1.lowerRight()), 
                srcIter(src2.upperLeft()), 
                maskIter(mask.upperLeft()), 
                destIter(dest.upperLeft()),
                std::plus<SrcValueType>());

Note that SrcValueType must be replaced with the appropriate type (e.g. the promote type of the input images' pixel type, see also Numeric and Promotion Traits)

Required Interface:

    SrcImageIterator1 src1_upperleft, src1_lowerright;
    SrcImageIterator2 src2_upperleft;
    MaskImageIterator mask_upperleft;
    DestImageIterator dest_upperleft;
    SrcImageIterator1::row_iterator sx1 = src1_upperleft.rowIterator();
    SrcImageIterator2::row_iterator sx2 = src2_upperleft.rowIterator();
    MaskImageIterator::row_iterator mx = mask_upperleft.rowIterator();
    DestImageIterator::row_iterator dx = dest_upperleft.rowIterator();
    
    
    SrcAccessor1 src1_accessor;
    SrcAccessor2 src2_accessor;
    MaskAccessor mask_accessor;
    DestAccessor dest_accessor;
    
    Functor functor;
    
    if(mask_accessor(mx))
       dest_accessor.set(
          functor(src1_accessor(sx1), src2_accessor(sx2)), 
          dx);

The transformation given by the functor is applied to the source pixels and the result written into the corresponding destination pixel. The function uses accessors to access the pixel data. Creation of new functors is easiest by using Functor Expressions.

Declarations:

pass arguments explicitly:

    namespace vigra {
        template <class SrcImageIterator1, class SrcAccessor1,
              class SrcImageIterator2, class SrcAccessor2,
              class SrcImageIterator3, class SrcAccessor3,
              class DestImageIterator, class DestAccessor,
              class Functor>
        void
        combineThreeImages(SrcImageIterator1 src1_upperleft, 
                   SrcImageIterator1 src1_lowerright, SrcAccessor1 sa1,
                   SrcImageIterator2 src2_upperleft, SrcAccessor2 sa2,
                   SrcImageIterator3 src2_upperleft, SrcAccessor3 sa3,
                   DestImageIterator dest_upperleft, DestAccessor da,
                   Functor const & f)
    }

use argument objects in conjunction with Argument Object Factories :

    namespace vigra {
        template <class SrcImageIterator1, class SrcAccessor1,
              class SrcImageIterator2, class SrcAccessor2,
              class SrcImageIterator3, class SrcAccessor3,
              class DestImageIterator, class DestAccessor,
              class Functor>
        void
        combineThreeImages(triple<SrcImageIterator1, SrcImageIterator1, SrcAccessor1> src1,
                 pair<SrcImageIterator2, SrcAccessor2> src2,
                 pair<SrcImageIterator3, SrcAccessor3> src3,
                 pair<DestImageIterator, DestAccessor> dest,
                 Functor const & f)
    }

Usage:

#include <vigra/combineimages.hxx>
Namespace: vigra

    vigra::combineThreeImages(
                srcIterRange(src1.upperLeft(), src1.lowerRight()), 
                srcIter(src2.upperLeft()), 
                srcIter(src3.upperLeft()), 
                destIter(dest.upperLeft()),  
                SomeThreeArgumentFunctor());

Required Interface:

    SrcImageIterator1 src1_upperleft, src1_lowerright;
    SrcImageIterator2 src2_upperleft;
    SrcImageIterator3 src3_upperleft;
    DestImageIterator dest_upperleft;
    SrcImageIterator1::row_iterator sx1 = src1_upperleft.rowIterator();
    SrcImageIterator2::row_iterator sx2 = src2_upperleft.rowIterator();
    SrcImageIterator3::row_iterator sx3 = src3_upperleft.rowIterator();
    DestImageIterator::row_iterator dx = dest_upperleft.rowIterator();
    
    SrcAccessor1 src1_accessor;
    SrcAccessor2 src2_accessor;
    SrcAccessor3 src3_accessor;
    DestAccessor dest_accessor;
    
    Functor functor;

    dest_accessor.set(
          functor(src1_accessor(sx1), 
                  src2_accessor(sx2), 
                  src3_accessor(sx3)), 
          dx);

© Ullrich Köthe (ullrich.koethe@iwr.uni-heidelberg.de)
Heidelberg Collaboratory for Image Processing, University of Heidelberg, Germany

html generated using doxygen and Python
VIGRA 1.6.0 (5 Nov 2009)