ImageTransforms.h

Go to the documentation of this file.
00001 // -*- c-basic-offset: 4 -*-
00027 #ifndef _VIGRA_EXT_IMAGETRANSFORMS_H
00028 #define _VIGRA_EXT_IMAGETRANSFORMS_H
00029 
00030 #include <fstream>
00031 
00032 #include <vigra/basicimage.hxx>
00033 #include <vigra_ext/ROIImage.h>
00034 #include <vigra_ext/Interpolators.h>
00035 #include <vigra/impex.hxx>
00036 #include <vigra_ext/impexalpha.hxx>
00037 
00038 #include <hugin_math/hugin_math.h>
00039 #include <hugin_utils/utils.h>
00040 #include <appbase/ProgressDisplayOld.h>
00041 
00042 #include "MultiThreadOperations.h"
00043 #include <boost/thread/thread.hpp>
00044 #include <boost/bind.hpp>
00045 #include <boost/function.hpp>
00046 
00047 
00048 namespace vigra_ext
00049 {
00050 
00052 template <class T>
00053 T zeroNegative(T p)
00054 {
00055     if (p < 0) {
00056         return vigra::NumericTraits<T>::zero();
00057     } else {
00058         return p;
00059     }
00060 }
00061 
00063 template <class T>
00064 vigra::RGBValue<T> zeroNegative(vigra::RGBValue<T> p)
00065 {
00066     if (p.red() < 0) p.setRed(vigra::NumericTraits<T>::zero());
00067     if (p.green() < 0) p.setGreen(vigra::NumericTraits<T>::zero());
00068     if (p.blue() < 0) p.setBlue(vigra::NumericTraits<T>::zero());
00069     return p;
00070 }
00071 
00072 
00097 template <class SrcImageIterator, class SrcAccessor,
00098           class DestImageIterator, class DestAccessor,
00099           class TRANSFORM,
00100           class PixelTransform,
00101           class AlphaImageIterator, class AlphaAccessor,
00102           class Interpolator>
00103 void transformImageIntern(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00104                           vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00105                           std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00106                           TRANSFORM & transform,
00107                           PixelTransform & pixelTransform,
00108                           vigra::Diff2D destUL,
00109                           Interpolator interp,
00110                           bool warparound,
00111                           AppBase::MultiProgressDisplay & prog)
00112 {
00113     vigra::Diff2D destSize = dest.second - dest.first;
00114 
00115     int xstart = destUL.x;
00116     int xend   = destUL.x + destSize.x;
00117     int ystart = destUL.y;
00118     int yend   = destUL.y + destSize.y;
00119 
00120     prog.pushTask(AppBase::ProgressTask("Remapping", "", 1.0/(yend-ystart)));
00121 
00122     vigra::Diff2D srcSize = src.second - src.first;
00123 
00124     vigra_ext::ImageInterpolator<SrcImageIterator, SrcAccessor, Interpolator>
00125                                  interpol (src, interp, warparound);
00126 
00127     // create dest y iterator
00128     DestImageIterator yd(dest.first);
00129     // create mask y iterator
00130     AlphaImageIterator ydm(alpha.first);
00131     // loop over the image and transform
00132     typename SrcAccessor::value_type tempval;
00133 
00134     for(int y=ystart; y < yend; ++y, ++yd.y, ++ydm.y)
00135     {
00136         // create x iterators
00137         DestImageIterator xd(yd);
00138         AlphaImageIterator xdm(ydm);
00139         for(int x=xstart; x < xend; ++x, ++xd.x, ++xdm.x)
00140         {
00141             double sx,sy;
00142             if (transform.transformImgCoord(sx,sy,x,y)) {
00143                 if (interpol.operator()(sx, sy, tempval)){
00144                     // apply pixel transform and write to output
00145                     dest.third.set( zeroNegative(pixelTransform(tempval, hugin_utils::FDiff2D(sx, sy))), xd);
00146                     alpha.second.set(pixelTransform.hdrWeight(tempval, vigra::UInt8(255)), xdm);
00147                 } else {
00148                     alpha.second.set(0, xdm);
00149                 }
00150             } else {
00151                 alpha.second.set(0, xdm);
00152             }
00153         }
00154         if (destSize.y > 100) {
00155             if ((y-ystart)%(destSize.y/20) == 0) {
00156                 prog.setProgress(((double)y-ystart)/destSize.y);
00157             }
00158         }
00159     }
00160     prog.popTask();
00161 }
00162 
00163 
00165 template <class SrcImageIterator, class SrcAccessor,
00166           class DestImageIterator, class DestAccessor,
00167           class TRANSFORM,
00168           class PixelTransform,
00169           class AlphaImageIterator, class AlphaAccessor,
00170           class Interpolator>
00171 struct TransformImageIntern
00172 {
00173     vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src;
00174     vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest;
00175     std::pair<AlphaImageIterator, AlphaAccessor> alpha;
00176     const TRANSFORM & transform;
00177     const PixelTransform & pixelTransform;
00178     vigra::Diff2D destUL;
00179     Interpolator interp;
00180     bool warparound;
00181     AppBase::MultiProgressDisplay & prog;
00182 
00183     TransformImageIntern(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00184                               vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00185                               std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00186                               const TRANSFORM & transform,
00187                               const PixelTransform & pixelTransform,
00188                               vigra::Diff2D destUL,
00189                               Interpolator interp,
00190                               bool warparound,
00191                               AppBase::MultiProgressDisplay & prog)
00192     : src(src), dest(dest), alpha(alpha), transform(transform), pixelTransform(pixelTransform), destUL(destUL), interp(interp), warparound(warparound),
00193       prog(prog)
00194     {
00195     }
00196 
00197     void operator()()
00198     {
00199         DEBUG_DEBUG("Starting threaded remap, destUL: " << destUL <<  " area: " << dest.second - dest.first);
00200         transformImageIntern(src, dest, alpha, transform, pixelTransform, destUL, interp, warparound, prog);
00201         DEBUG_DEBUG("Finished threaded remap, destUL: " << destUL <<  " area: " << dest.second - dest.first);
00202     }
00203 };
00204 
00205 
00207 template <class SrcImageIterator, class SrcAccessor,
00208           class SrcAlphaIterator, class SrcAlphaAccessor,
00209           class DestImageIterator, class DestAccessor,
00210           class TRANSFORM,
00211           class PixelTransform,
00212           class AlphaImageIterator, class AlphaAccessor,
00213           class Interpolator>
00214 void transformImageAlphaIntern(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00215                                std::pair<SrcAlphaIterator, SrcAlphaAccessor> srcAlpha,
00216                                vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00217                                std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00218                                TRANSFORM & transform,
00219                                PixelTransform & pixelTransform,
00220                                vigra::Diff2D destUL,
00221                                Interpolator interp,
00222                                bool warparound,
00223                                AppBase::MultiProgressDisplay & prog)
00224 {
00225     vigra::Diff2D destSize = dest.second - dest.first;
00226 
00227     int xstart = destUL.x;
00228     int xend   = destUL.x + destSize.x;
00229     int ystart = destUL.y;
00230     int yend   = destUL.y + destSize.y;
00231 
00232     prog.pushTask(AppBase::ProgressTask("Remapping", "", 1.0/(yend-ystart)));
00233 
00234     vigra::Diff2D srcSize = src.second - src.first;
00235 
00236     vigra_ext::ImageMaskInterpolator<SrcImageIterator, SrcAccessor, SrcAlphaIterator,
00237                                      SrcAlphaAccessor, Interpolator>
00238                                     interpol (src, srcAlpha, interp, warparound);
00239 
00240     // create dest y iterator
00241     DestImageIterator yd(dest.first);
00242     // create dist y iterator
00243     AlphaImageIterator ydist(alpha.first);
00244 
00245     typename SrcAccessor::value_type tempval;
00246 
00247     typename SrcAlphaAccessor::value_type alphaval;
00248 
00249     // loop over the image and transform
00250     for(int y=ystart; y < yend; ++y, ++yd.y, ++ydist.y)
00251     {
00252         // create x iterators
00253         DestImageIterator xd(yd);
00254         AlphaImageIterator xdist(ydist);
00255         for(int x=xstart; x < xend; ++x, ++xd.x, ++xdist.x)
00256         {
00257             double sx,sy;
00258             if (transform.transformImgCoord(sx,sy,x,y)) {
00259                 // try to interpolate.
00260                 if (interpol(sx, sy, tempval, alphaval)) {
00261                     dest.third.set(zeroNegative(pixelTransform(tempval, hugin_utils::FDiff2D(sx, sy))), xd);
00262                     alpha.second.set(pixelTransform.hdrWeight(tempval, alphaval), xdist);
00263                 } else {
00264                     // point outside of image or mask
00265                     alpha.second.set(0, xdist);
00266                 }
00267             } else {
00268                 alpha.second.set(0, xdist);
00269             }
00270         }
00271         if (destSize.y > 100) {
00272             if ((y-ystart)%(destSize.y/20) == 0) {
00273                 prog.setProgress(((double)y-ystart)/destSize.y);
00274             }
00275         }
00276     }
00277     prog.popTask();
00278 };
00279 
00280 
00282 template <class SrcImageIterator, class SrcAccessor,
00283           class SrcAlphaIterator, class SrcAlphaAccessor,
00284           class DestImageIterator, class DestAccessor,
00285           class TRANSFORM,
00286           class PixelTransform,
00287           class AlphaImageIterator, class AlphaAccessor,
00288           class Interpolator>
00289 struct TransformImageAlphaIntern
00290 {
00291     vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src;
00292     std::pair<SrcAlphaIterator, SrcAlphaAccessor> srcAlpha;
00293     vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest;
00294     std::pair<AlphaImageIterator, AlphaAccessor> alpha;
00295     const TRANSFORM & transform;
00296     const PixelTransform & pixelTransform;
00297     vigra::Diff2D destUL;
00298     Interpolator interp;
00299     bool warparound;
00300     AppBase::MultiProgressDisplay & prog;
00301 
00302     TransformImageAlphaIntern(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00303                               std::pair<SrcAlphaIterator, SrcAlphaAccessor> srcAlpha,
00304                               vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00305                               std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00306                               const TRANSFORM & transform,
00307                               const PixelTransform & pixelTransform,
00308                               vigra::Diff2D destUL,
00309                               Interpolator interp,
00310                               bool warparound,
00311                               AppBase::MultiProgressDisplay & prog)
00312     : src(src), srcAlpha(srcAlpha), dest(dest), alpha(alpha), transform(transform),
00313       pixelTransform(pixelTransform), destUL(destUL), interp(interp), warparound(warparound),
00314       prog(prog)
00315     {
00316     }
00317 
00318     void operator()()
00319     {
00320         DEBUG_DEBUG("Starting threaded remap, destUL: " << destUL <<  " area: " << dest.second - dest.first);
00321         transformImageAlphaIntern(src, srcAlpha, dest, alpha, transform, pixelTransform, destUL, interp, warparound, prog);
00322         DEBUG_DEBUG("Finished threaded remap, destUL: " << destUL <<  " area: " << dest.second - dest.first);
00323     }
00324 };
00325 
00326 
00351 template <class SrcImageIterator, class SrcAccessor,
00352           class DestImageIterator, class DestAccessor,
00353           class TRANSFORM,
00354           class DistImageIterator, class DistAccessor,
00355           class Interpolator>
00356 void transformImageDist(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00357                         vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00358                         vigra::Diff2D destUL,
00359                         TRANSFORM & transform,
00360                         vigra::triple<DistImageIterator, DistImageIterator, DistAccessor> centerDist,
00361                         Interpolator & interp,
00362                         AppBase::MultiProgressDisplay & prog)
00363 {
00364     vigra::Diff2D destSize = dest.second - dest.first;
00365     vigra::Diff2D distSize = centerDist.second - centerDist.first;
00366 
00367     bool calcDist=true;
00368     if (distSize.x == 0 && distSize.y == 0) {
00369         calcDist=false;
00370     }
00371 
00372     if (calcDist) {
00373         DEBUG_ASSERT(distSize == destSize);
00374     }
00375     int xstart = destUL.x;
00376     int xend   = destUL.x + destSize.x;
00377     int ystart = destUL.y;
00378     int yend   = destUL.y + destSize.y;
00379 
00380     prog.pushTask(AppBase::ProgressTask("Remapping", "", 1.0/(yend-ystart)));
00381 
00382     vigra::Diff2D srcSize = src.second - src.first;
00383     // FIXME: use d & e here.
00384     vigra::Diff2D srcMiddle = srcSize / 2;
00385 
00386 //    vigra::BilinearInterpolatingAccessor<SrcAccessor, typename SrcAccessor::value_type> interpol(src.third);
00387 
00388     //InterpolatingAccessor(src.third, interp);
00389     vigra_ext::InterpolatingAccessor<SrcAccessor,
00390                           typename SrcAccessor::value_type,
00391                           Interpolator> interpol(src.third, interp);
00392 
00393 
00394 //    vigra::BilinearInterpolatingAccessor<SrcAccessor, typename SrcAccessor::value_type> interpol(src.third);
00395 
00396 //    vigra::BilinearInterpolatingAccessor interpol(src.third);
00397 
00398     // create dest y iterator
00399     DestImageIterator yd(dest.first);
00400     // create dist y iterator
00401     DistImageIterator ydist(centerDist.first);
00402     // loop over the image and transform
00403     for(int y=ystart; y < yend; ++y, ++yd.y, ++ydist.y)
00404     {
00405         // create x iterators
00406         DestImageIterator xd(yd);
00407         DistImageIterator xdist(ydist);
00408         for(int x=xstart; x < xend; ++x, ++xd.x, ++xdist.x)
00409         {
00410             double sx,sy;
00411             if (transform.transformImgCoord(sx,sy,x,y)) {
00412                 // make sure that the interpolator doesn't
00413                 // access pixels outside.. Should we introduce
00414                 // some sort of border treatment?
00415                 if (sx < interp.size/2 -1
00416                     || sx > srcSize.x-interp.size/2 - 1
00417                     || sy < interp.size/2 - 1
00418                     || sy > srcSize.y-interp.size/2 - 1)
00419                 {
00420                     if (calcDist) {
00421                         // save an invalid distance
00422                         *xdist = FLT_MAX;
00423                     }
00424                     // nothing..
00425                 } else {
00426     //                cout << x << "," << y << " -> " << sx << "," << sy << " " << std::endl;
00427     
00428     //                nearest neighbour
00429     //                *xd = src.third(src.first, vigra::Diff2D((int)round(sx), (int)round(sy)));
00430                     // use given interpolator function.
00431                     *xd = interpol(src.first, sx, sy);
00432                     if (calcDist) {
00433                         double mx = sx - srcMiddle.x;
00434                         double my = sy - srcMiddle.y;
00435                         *xdist = sqrt(mx*mx + my*my);
00436                     }
00437                 }
00438             } else {
00439                 *xdist = FLT_MAX;
00440             }
00441         }
00442         if ((y-ystart)%100 == 0) {
00443             prog.setProgress(((double)y-ystart)/(yend-ystart));
00444         }
00445     }
00446     prog.popTask();
00447 }
00448 
00449 
00451 
00452 
00454 template <class SrcImageIterator, class SrcAccessor,
00455           class SrcAlphaIterator, class SrcAlphaAccessor,
00456           class DestImageIterator, class DestAccessor,
00457           class TRANSFORM,
00458           class PixelTransform,
00459           class AlphaImageIterator, class AlphaAccessor,
00460           class Interpolator>
00461 void transformImageAlphaInternMT(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00462                                  std::pair<SrcAlphaIterator, SrcAlphaAccessor> srcAlpha,
00463                                  vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00464                                  std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00465                                  TRANSFORM & transform,
00466                                  PixelTransform & pixelTransform,
00467                                  vigra::Diff2D destUL,
00468                                  Interpolator interp,
00469                                  bool warparound,
00470                                  AppBase::MultiProgressDisplay & prog)
00471 {
00472     // divide output image into multiple areas
00473     unsigned int nThreads = ThreadManager::get().getNThreads();
00474 
00475     vigra::Diff2D destSize = dest.second - dest.first;
00476 
00477     // limit amount of threads if only a few lines are given.
00478     if (destSize.y < (int) nThreads) {
00479         nThreads = destSize.y;
00480     }
00481 
00482     if (nThreads == 1) {
00483         transformImageAlphaIntern(src, srcAlpha, dest, alpha, transform, pixelTransform,
00484                                   destUL, interp, warparound, prog);
00485         return;
00486     }
00487 
00488     DEBUG_DEBUG("creating " << nThreads << " threads for remapping");
00489 
00490     unsigned int chunkSize = destSize.y / nThreads;
00491 // DGSW FIXME - Unreferenced
00492 //      unsigned int lastChunkSize = destSize.y - (nThreads-1) * chunkSize;
00493 
00494     // create a threads to remap each area
00495     boost::thread_group threads;
00496 
00497     // create first thread with progress counter
00498     DestImageIterator destStart = dest.first;
00499     DestImageIterator destEnd = dest.second;
00500     destEnd.y -= destSize.y - chunkSize;
00501     AlphaImageIterator destAStart = alpha.first;
00502 
00503     typedef TransformImageAlphaIntern<SrcImageIterator, SrcAccessor, SrcAlphaIterator, SrcAlphaAccessor, DestImageIterator, DestAccessor,
00504                                       TRANSFORM, PixelTransform, AlphaImageIterator, AlphaAccessor, Interpolator> RFunctor;
00505 
00506     std::vector< AppBase::DummyMultiProgressDisplay> dummyProgs(nThreads-1);
00507     unsigned int i;
00508     for (i = 0; i < nThreads-1; ++i) {
00509 
00510         RFunctor t(src, srcAlpha, vigra::triple<DestImageIterator, DestImageIterator, DestAccessor>(destStart, destEnd, dest.third),
00511                                                 vigra::pair<AlphaImageIterator, AlphaAccessor>(destAStart, alpha.second), 
00512                                                 transform, pixelTransform, destUL, interp, warparound, dummyProgs[i]);
00513         boost::function0<void> f;
00514         f = t;
00515         DEBUG_DEBUG("Starting thread " << i);
00516         threads.create_thread(f);
00517 
00518         destStart.y += chunkSize;
00519         destEnd.y += chunkSize;
00520         destAStart.y += chunkSize;
00521         destUL.y += chunkSize;
00522     }
00523     // last chunk
00524     destEnd = dest.second;
00525     // remap last chunk in current thread.
00526     if (i == nThreads-1) {
00527         DEBUG_DEBUG("remapping in main thread, destUL: " << destUL <<  " area: " << dest.second - dest.first);
00528         transformImageAlphaIntern( src, srcAlpha,
00529                                   vigra::triple<DestImageIterator, DestImageIterator, DestAccessor>(destStart, destEnd, dest.third),
00530                                   vigra::pair<AlphaImageIterator, AlphaAccessor>(destAStart, alpha.second), 
00531                                   transform, pixelTransform, destUL, interp, warparound, prog);
00532     }
00533 
00534     DEBUG_DEBUG("Waiting for threads to join");
00535     threads.join_all();
00536     DEBUG_DEBUG("Threads joined");
00537 }
00538 
00539 template <class SrcImageIterator, class SrcAccessor,
00540           class DestImageIterator, class DestAccessor,
00541           class TRANSFORM,
00542           class PixelTransform,
00543           class AlphaImageIterator, class AlphaAccessor,
00544           class Interpolator>
00545 void transformImageInternMT(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00546                             vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00547                             std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00548                             TRANSFORM & transform,
00549                             PixelTransform & pixelTransform,
00550                             vigra::Diff2D destUL,
00551                             Interpolator interp,
00552                             bool warparound,
00553                             AppBase::MultiProgressDisplay & prog)
00554 {
00555     // divide output image into multiple areas
00556     unsigned int nThreads = ThreadManager::get().getNThreads();
00557 
00558     vigra::Diff2D destSize = dest.second - dest.first;
00559 
00560     // limit amount of threads if only a few lines are given.
00561     if (destSize.y < (int) nThreads) {
00562         nThreads = destSize.y;
00563     }
00564 
00565     if (nThreads == 1) {
00566         transformImageIntern(src, dest, alpha, transform, pixelTransform,
00567                                   destUL, interp, warparound, prog);
00568         return;
00569     }
00570 
00571     DEBUG_DEBUG("creating " << nThreads << " threads for remapping");
00572 
00573     unsigned int chunkSize = destSize.y / nThreads;
00574 // DGSW FIXME - Unreferenced
00575 //      unsigned int lastChunkSize = destSize.y - (nThreads-1) * chunkSize;
00576 
00577     // create a threads to remap each area
00578     boost::thread_group threads;
00579 
00580     // create first thread with progress counter
00581     DestImageIterator destStart = dest.first;
00582     DestImageIterator destEnd = dest.second;
00583     destEnd.y -= destSize.y - chunkSize;
00584     AlphaImageIterator destAStart = alpha.first;
00585 
00586     typedef TransformImageIntern<SrcImageIterator, SrcAccessor, DestImageIterator, DestAccessor,
00587                                       TRANSFORM, PixelTransform, AlphaImageIterator, AlphaAccessor, Interpolator> RFunctor;
00588 
00589     std::vector< AppBase::DummyMultiProgressDisplay> dummyProgs(nThreads-1);
00590     unsigned int i;
00591     for (i = 0; i < nThreads-1; ++i) {
00592 
00593         RFunctor t(src, vigra::triple<DestImageIterator, DestImageIterator, DestAccessor>(destStart, destEnd, dest.third),
00594                    vigra::pair<AlphaImageIterator, AlphaAccessor>(destAStart, alpha.second), 
00595                    transform, pixelTransform, destUL, interp, warparound, dummyProgs[i]);
00596         boost::function0<void> f;
00597         f = t;
00598         DEBUG_DEBUG("Starting thread " << i);
00599         threads.create_thread(f);
00600 
00601         destStart.y += chunkSize;
00602         destEnd.y += chunkSize;
00603         destAStart.y += chunkSize;
00604         destUL.y += chunkSize;
00605     }
00606     // last chunk
00607     destEnd = dest.second;
00608     // remap last chunk in current thread.
00609     if (i == nThreads-1) {
00610         DEBUG_DEBUG("remapping in main thread, destUL: " << destUL <<  " area: " << dest.second - dest.first);
00611         transformImageIntern( src,
00612                               vigra::triple<DestImageIterator, DestImageIterator, DestAccessor>(destStart, destEnd, dest.third),
00613                               vigra::pair<AlphaImageIterator, AlphaAccessor>(destAStart, alpha.second), 
00614                               transform, pixelTransform, destUL, interp, warparound, prog);
00615     }
00616 
00617     DEBUG_DEBUG("Waiting for threads to join");
00618     threads.join_all();
00619     DEBUG_DEBUG("Threads joined");
00620 }
00621 
00622 
00647 template <class SrcImageIterator, class SrcAccessor,
00648           class DestImageIterator, class DestAccessor,
00649           class AlphaImageIterator, class AlphaAccessor,
00650           class TRANSFORM,
00651           class PixelTransform>
00652 void transformImage(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00653                     vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00654                     std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00655                     vigra::Diff2D destUL,
00656                     TRANSFORM & transform,
00657                     PixelTransform & pixelTransform,
00658                     bool warparound,
00659                     Interpolator interpol,
00660                     AppBase::MultiProgressDisplay & progress)
00661 {
00662     switch (interpol) {
00663     case INTERP_CUBIC:
00664         DEBUG_DEBUG("using cubic interpolator");
00665     transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00666                                  vigra_ext::interp_cubic(), warparound,
00667                                  progress);
00668         break;
00669     case INTERP_SPLINE_16:
00670         DEBUG_DEBUG("interpolator: spline16");
00671     transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00672                                  vigra_ext::interp_spline16(), warparound,
00673                                  progress);
00674         break;
00675     case INTERP_SPLINE_36:
00676         DEBUG_DEBUG("interpolator: spline36");
00677     transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00678                                  vigra_ext::interp_spline36(), warparound,
00679                                  progress);
00680         break;
00681     case INTERP_SPLINE_64:
00682         DEBUG_DEBUG("interpolator: spline64");
00683     transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00684                                  vigra_ext::interp_spline64(), warparound,
00685                                  progress);
00686         break;
00687     case INTERP_SINC_256:
00688         DEBUG_DEBUG("interpolator: sinc 256");
00689     transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00690                                  vigra_ext::interp_sinc<8>(), warparound,
00691                                  progress);
00692         break;
00693     case INTERP_BILINEAR:
00694         transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00695                                  vigra_ext::interp_bilin(), warparound,
00696                                  progress);
00697         break;
00698     case INTERP_NEAREST_NEIGHBOUR:
00699         transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00700                                  vigra_ext::interp_nearest(), warparound,
00701                                  progress);
00702         break;
00703     case INTERP_SINC_1024:
00704         transformImageInternMT(src, dest, alpha, transform, pixelTransform, destUL,
00705                                  vigra_ext::interp_sinc<32>(), warparound,
00706                                  progress);
00707         break;
00708     }
00709 }
00710 
00712 template <class SrcImageIterator, class SrcAccessor,
00713           class SrcAlphaIterator, class SrcAlphaAccessor,
00714           class DestImageIterator, class DestAccessor,
00715           class AlphaImageIterator, class AlphaAccessor,
00716           class TRANSFORM, class PixelTransform>
00717 void transformImageAlpha(vigra::triple<SrcImageIterator, SrcImageIterator, SrcAccessor> src,
00718                          std::pair<SrcAlphaIterator, SrcAlphaAccessor> srcAlpha,
00719                          vigra::triple<DestImageIterator, DestImageIterator, DestAccessor> dest,
00720                          std::pair<AlphaImageIterator, AlphaAccessor> alpha,
00721                          vigra::Diff2D destUL,
00722                          TRANSFORM & transform,
00723                          PixelTransform & pixelTransform,
00724                          bool warparound,
00725                          Interpolator interpol,
00726                          AppBase::MultiProgressDisplay & progress)
00727 {
00728     switch (interpol) {
00729     case INTERP_CUBIC:
00730         DEBUG_DEBUG("using cubic interpolator");
00731         transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00732                                               vigra_ext::interp_cubic(), warparound,
00733                               progress);
00734         break;
00735     case INTERP_SPLINE_16:
00736         DEBUG_DEBUG("interpolator: spline16");
00737     transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00738                               vigra_ext::interp_spline16(), warparound,
00739                                       progress);
00740         break;
00741     case INTERP_SPLINE_36:
00742         DEBUG_DEBUG("interpolator: spline36");
00743     transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00744                               vigra_ext::interp_spline36(),  warparound,
00745                                       progress);
00746         break;
00747     case INTERP_SPLINE_64:
00748         DEBUG_DEBUG("interpolator: spline64");
00749     transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00750                               vigra_ext::interp_spline64(),  warparound,
00751                                       progress);
00752         break;
00753     case INTERP_SINC_256:
00754         DEBUG_DEBUG("interpolator: sinc 256");
00755     transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00756                               vigra_ext::interp_sinc<8>(), warparound,
00757                                       progress);
00758         break;
00759     case INTERP_BILINEAR:
00760         transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00761                               vigra_ext::interp_bilin(), warparound,
00762                                       progress);
00763         break;
00764     case INTERP_NEAREST_NEIGHBOUR:
00765         transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00766                               vigra_ext::interp_nearest(), warparound,
00767                                       progress);
00768         break;
00769     case INTERP_SINC_1024:
00770         transformImageAlphaInternMT(src,srcAlpha, dest, alpha, transform, pixelTransform, destUL,
00771                               vigra_ext::interp_sinc<32>(), warparound,
00772                                       progress);
00773         break;
00774     }
00775 }
00776 
00777 template <class T, int nr>
00778 void fillVector(T vec[3], T &val, int len)
00779 {
00780     for (int i=0; i<len; i++) vec[i] = val;
00781 }
00782 
00783 
00784 }; // namespace
00785 
00786 #endif // _VIGRA_EXT_IMAGETRANSFORMS_H

Generated on Thu Oct 2 01:25:41 2014 for Hugintrunk by  doxygen 1.3.9.1