TuttleOFX  1
ColorCubeViewerProcess.hpp
Go to the documentation of this file.
00001 #ifndef _TUTTLE_PLUGIN_COLORCUBE_PROCESS_HPP_
00002 #define _TUTTLE_PLUGIN_COLORCUBE_PROCESS_HPP_
00003 
00004 #include "SelectionAverage.hpp"
00005 #include "GeodesicForm.hpp"
00006 #include <tuttle/plugin/ImageGilFilterProcessor.hpp>
00007 
00008 namespace tuttle {
00009 namespace plugin {
00010 namespace colorCubeViewer {
00011 
00012         
00013 struct Compute_alpha_pixel
00014 { 
00015         bool _isOutputBW;               //is output black & white (or alpha channel)
00016         GeodesicForm& _dataColor;       //color geodesic form
00017         GeodesicForm& _dataSpill;       //spill geodesic form
00018         
00019         Compute_alpha_pixel(bool isOutputBW, GeodesicForm& dataC, GeodesicForm& dataS):
00020         _isOutputBW(isOutputBW),
00021         _dataColor(dataC),
00022         _dataSpill(dataS)
00023         {               
00024         }
00025         
00026     template< typename Pixel>
00027     Pixel operator()( const Pixel& p )
00028     {
00029         using namespace boost::gil;
00030                 
00031         double alpha = 0.0;                     //define current pixel alpha (1 by default)
00032                 Ofx3DPointD testPoint;          //initialize test point 
00033                 testPoint.x = p[0];                     //x == red
00034                 testPoint.y = p[1];                     //y == green
00035                 testPoint.z = p[2];                     //z == blue
00036                 
00037                 if(_dataSpill.isIntoBoundingBox(testPoint))                                             //if current pixel is into spill bounding box
00038                 {
00039                         if(_dataColor.isIntoBoundingBox(testPoint))                                     //bounding box test (process optimization)
00040                         {
00041                                 if(_dataColor.isPointIntoGeodesicForm(testPoint))               //if current pixel is into the color geodesic form
00042                                 {
00043                                         alpha = 1.0;                                                                            //change alpha to 1
00044                                 }
00045                         }
00046                         if(alpha != 1.0 && _dataSpill.isPointIntoGeodesicForm(testPoint))
00047                         {
00048                                 //intersections test
00049                                 if(_dataColor.testIntersection2(testPoint,false,true)) //normal intersection
00050                                 {
00051                                         //computes vectors
00052                                         Ofx3DPointD vectMax;
00053                                         Ofx3DPointD vectMin;
00054                                         //compute min vector
00055                                         vectMin.x = testPoint.x - _dataColor._intersectionPoint.x; //x value
00056                                         vectMin.y = testPoint.y - _dataColor._intersectionPoint.y; //y value
00057                                         vectMin.z = testPoint.z - _dataColor._intersectionPoint.z;      //z value
00058                                         //compute max vector
00059                                         vectMax.x = _dataSpill._intersectionPoint.x - _dataColor._intersectionPoint.x; //x value
00060                                         vectMax.y = _dataSpill._intersectionPoint.y - _dataColor._intersectionPoint.y; //x value
00061                                         vectMax.z = _dataSpill._intersectionPoint.z - _dataColor._intersectionPoint.z; //x value
00062                                         //compute norms
00063                                         double normMin,normMax;                 //initialize
00064                                         normMin  = vectMin.x*vectMin.x; //add x*x
00065                                         normMin += vectMin.y*vectMin.y; //add y*y
00066                                         normMin += vectMin.z*vectMin.z; //add z*z
00067                                         normMin = sqrt(normMin);                //compute norm minimal
00068 
00069                                         normMax  = vectMax.x*vectMax.x; //add x*x
00070                                         normMax += vectMax.y*vectMax.y; //add y*y
00071                                         normMax += vectMax.z*vectMax.z; //add z*z
00072                                         normMax = sqrt(normMax);                //compute norm maximal
00073 
00074                                         //compute alpha value
00075                                         alpha = normMin/normMax;
00076                                 }
00077                         }
00078                 }
00079                 alpha = 1-alpha;                                //black is transparent and white is opaque
00080                 Pixel ret;                                              //declare returned pixel
00081                 if(_isOutputBW)                                 // output is gray scale image
00082                 {
00083                         gray32f_pixel_t inter;          // need a gray_pixel
00084                         inter[0] = alpha;                       // recopy value (black or white)
00085                         color_convert(inter,ret);       // convert gray_pixel to rgba_pixel
00086                 }
00087                 else // output is alpha channel
00088                 {
00089                         for(unsigned int i=0; i<boost::gil::num_channels<Pixel>::type::value -1; ++i)   //all RGB channels (not alpha)
00090                                 ret[i] = p[i];                                                                                                                          //recopy r,g and b channels
00091                         ret[3] = alpha;                                                                                                                                 //fill alpha channel up
00092                 }
00093                 return ret;
00094     }
00095 };      
00096         
00097 /**
00098  * @brief ColorCube process
00099  *
00100  */
00101 template<class View>
00102 class ColorCubeViewerProcess : public ImageGilFilterProcessor<View>
00103 {
00104 public:
00105         typedef typename View::value_type Pixel;
00106         typedef typename boost::gil::channel_type<View>::type Channel;
00107         typedef float Scalar;
00108 protected:
00109     ColorCubeViewerPlugin&    _plugin;            ///< Rendering plugin
00110         ColorCubeViewerProcessParams<Scalar> _params; ///< parameters
00111 public:
00112     ColorCubeViewerProcess( ColorCubeViewerPlugin& effect );
00113         void setup( const OFX::RenderArguments& args );
00114     void multiThreadProcessImages( const OfxRectI& procWindowRoW );
00115 };
00116 
00117 }
00118 }
00119 }
00120 
00121 #include "ColorCubeViewerProcess.tcc"
00122 
00123 #endif