TuttleOFX  1
WarpProcess.tcc
Go to the documentation of this file.
00001 #include "WarpAlgorithm.hpp"
00002 #include "WarpPlugin.hpp"
00003 
00004 #include <terry/sampler/resample_progress.hpp>
00005 #include <terry/algorithm/transform_pixels_progress.hpp>
00006 #include <tuttle/plugin/exceptions.hpp>
00007 
00008 #include <terry/globals.hpp>
00009 
00010 namespace tuttle {
00011 namespace plugin {
00012 namespace warp {
00013 
00014 template<class View>
00015 WarpProcess<View>::WarpProcess( WarpPlugin &effect )
00016 : ImageGilFilterProcessor<View>( effect, eImageOrientationFromTopToBottom )
00017 , _plugin( effect )
00018 {
00019         _clipSrcB = effect.fetchClip( kClipSourceB );
00020 }
00021 
00022 template<class View>
00023 void WarpProcess<View>::setup( const OFX::RenderArguments& args )
00024 {
00025         ImageGilFilterProcessor<View>::setup( args );
00026         _params = _plugin.getProcessParams( args.renderScale );
00027 
00028         if( this->_clipSrcB->isConnected( ) )
00029         {
00030                 // srcB initialization
00031                 this->_srcB.reset( _clipSrcB->fetchImage( args.time ) );
00032                 if( !this->_srcB.get( ) )
00033                 {
00034                         BOOST_THROW_EXCEPTION( exception::ImageNotReady( ) );
00035                 }
00036                 
00037                 // Commented because of a build error :
00038                 // getRowBytes( ) is not a method of OFX::Image
00039                 // TODO: Fix this
00040                 // if( this->_srcB->getRowBytes( ) == 0 )
00041                 // {
00042                 //      BOOST_THROW_EXCEPTION( exception::WrongRowBytes( ) );
00043                 // }
00044 
00045                 // _srcBPixelRod = _srcB->getRegionOfDefinition(); // bug in nuke, returns bounds
00046                 _srcBPixelRod = _clipSrcB->getPixelRod( args.time, args.renderScale );
00047                 this->_srcBView = this->getView( this->_srcB.get( ), _srcBPixelRod );
00048                 _tpsB.setup( _params._bezierOut, _params._bezierIn, _params._rigiditeTPS, _params._activateWarp, this->_srcBPixelRod.x2 - this->_srcBPixelRod.x1, this->_srcBPixelRod.y2 - this->_srcBPixelRod.y1, ( 1.0 - _params._transition ) );
00049         }
00050         //TPS_Morpher<Scalar> tps( _params._inPoints, _params._outPoints , _params._rigiditeTPS);
00051         _tpsA.setup( _params._bezierIn, _params._bezierOut, _params._rigiditeTPS, _params._activateWarp, this->_srcPixelRod.x2 - this->_srcPixelRod.x1, this->_srcPixelRod.y2 - this->_srcPixelRod.y1, _params._transition );
00052         //TUTTLE_TCOUT_VAR( _params._rigiditeTPS );
00053         //TUTTLE_TCOUT_VAR( _params._activateWarp );
00054 }
00055 
00056 /**
00057  * @brief Function called by rendering thread each time a process must be done.
00058  * @param[in] procWindowRoW  Processing window
00059  */
00060 template<class View>
00061 void WarpProcess<View>::multiThreadProcessImages( const OfxRectI& procWindowRoW )
00062 {
00063         using namespace boost::gil;
00064         using namespace terry::sampler;
00065         using namespace terry::algorithm;
00066         const OfxRectI procWindowOutput = translateRegion( procWindowRoW, this->_dstPixelRod );
00067         const OfxRectI procWindowSrcA = translateRegion( procWindowRoW, this->_srcPixelRod );
00068         const OfxRectI procWindowSrcB = translateRegion( procWindowRoW, this->_srcBPixelRod );
00069 
00070         OfxPointI procWindowSize = { procWindowRoW.x2 - procWindowRoW.x1,
00071                                                                 procWindowRoW.y2 - procWindowRoW.y1 };
00072 
00073         const EParamFilterOutOfImage outOfImageProcess = eParamFilterOutBlack; /// @todo expose as parameter
00074         
00075         if( this->_clipSrcB->isConnected( ) )
00076         {
00077                 Image imgA( procWindowSize.x, procWindowSize.y );
00078                 Image imgB( procWindowSize.x, procWindowSize.y );
00079                 View viewA = subimage_view(
00080                                                 view(imgA),
00081                                                 this->_srcPixelRod.x1-procWindowRoW.x1, this->_srcPixelRod.y1-procWindowRoW.y1,
00082                                                 this->_srcView.width(), this->_srcView.height() );
00083                 View viewB = subimage_view(
00084                                                 view(imgB),
00085                                                 this->_srcBPixelRod.x1-procWindowRoW.x1, this->_srcBPixelRod.y1-procWindowRoW.y1,
00086                                                 this->_srcBView.width(), this->_srcBView.height() );
00087 
00088                 resample_pixels_progress<terry::sampler::bilinear_sampler>( this->_srcView, viewA, _tpsA, procWindowSrcA, outOfImageProcess, this->getOfxProgress() );
00089                 resample_pixels_progress<terry::sampler::bilinear_sampler>( this->_srcBView, viewB, _tpsB, procWindowSrcB, outOfImageProcess, this->getOfxProgress() );
00090 
00091                 //fondu entre imgA et imgB = this->_dstView FAITEALAMAIN
00092                 View dst = subimage_view( this->_dstView, procWindowOutput.x1, procWindowOutput.y1,
00093                                                                   procWindowSize.x, procWindowSize.y );
00094                 transform_pixels_progress(
00095                                                                    view( imgA ),
00096                                                                    view( imgB ),
00097                                                                    dst,
00098                                                                    pixel_merge_t<Pixel > ( _params._transition ),
00099                                                                    this->getOfxProgress() );
00100         }
00101         else
00102         {
00103                 View dst = subimage_view(
00104                                                 this->_dstView,
00105                                                 this->_srcPixelRod.x1-this->_dstPixelRod.x1, this->_srcPixelRod.y1-this->_dstPixelRod.y1,
00106                                                 this->_srcView.width(), this->_srcView.height() );
00107                 resample_pixels_progress<terry::sampler::bilinear_sampler > ( this->_srcView, dst, _tpsA, procWindowSrcA, outOfImageProcess, this->getOfxProgress() );
00108         }
00109 }
00110 
00111 }
00112 }
00113 }