TuttleOFX
1
|
00001 #ifndef _TERRY_COLOR_TEMPERATURE_HPP_ 00002 #define _TERRY_COLOR_TEMPERATURE_HPP_ 00003 00004 #include <terry/copy.hpp> 00005 00006 namespace terry { 00007 namespace color { 00008 00009 /** 00010 * @bief All supported temperatures 00011 */ 00012 namespace temperature { 00013 struct T_A {}; 00014 struct T_B {}; 00015 struct T_C {}; 00016 struct T_D50 {}; 00017 struct T_D55 {}; 00018 struct T_D58 {}; 00019 struct T_D65 {}; 00020 struct T_D75 {}; 00021 struct T_9300 {}; 00022 struct T_E {}; 00023 struct T_F2 {}; 00024 struct T_F7 {}; 00025 struct T_F11 {}; 00026 struct T_DCIP3 {}; 00027 00028 // we use D65 as the intermediate temperature color 00029 typedef T_D65 T_INTER; 00030 } 00031 00032 00033 /// @brief change the color temperature 00034 template< typename Channel, 00035 class IN, 00036 class OUT > 00037 struct channel_color_temperature_t : public std::binary_function<Channel, Channel, Channel> 00038 { 00039 typedef typename floating_channel_type_t<Channel>::type T; 00040 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00041 typedef typename channel_traits<Channel>::reference ChannelRef; 00042 00043 // This class implementation must be used only: 00044 // * with IN != OUT 00045 BOOST_STATIC_ASSERT(( ! boost::is_same<IN, OUT>::value )); // Must use channel_color_temperature_t<Channel, INOUT> ! 00046 // * IN and OUT must be other temperature mode than T_INTER 00047 // For each temperature mode, you have to specialize: TemperatureMode -> T_INTER and T_INTER -> TemperatureMode 00048 BOOST_STATIC_ASSERT(( ! boost::is_same<IN, temperature::T_INTER>::value )); // The conversion IN to T_INTER is not implemented ! 00049 BOOST_STATIC_ASSERT(( ! boost::is_same<OUT, temperature::T_INTER>::value )); // The conversion T_INTER to OUT is not implemented ! 00050 00051 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00052 { 00053 Channel inter; 00054 // IN -> T_INTER 00055 channel_color_temperature_t<Channel, IN, temperature::T_INTER>( _in, temperature::T_INTER() )( src, inter ); 00056 // T_INTER -> OUT 00057 return channel_color_temperature_t<Channel, temperature::T_INTER, OUT>( temperature::T_INTER(), _out )( inter, dst ); 00058 } 00059 }; 00060 00061 template< typename Channel, 00062 class INOUT > 00063 struct channel_color_temperature_t<Channel, INOUT, INOUT> : public std::binary_function<Channel, Channel, Channel> 00064 { 00065 typedef typename floating_channel_type_t<Channel>::type T; 00066 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00067 typedef typename channel_traits<Channel>::reference ChannelRef; 00068 00069 const INOUT& _in; 00070 const INOUT& _out; 00071 00072 channel_color_temperature_t( const INOUT& in, const INOUT& out ) 00073 : _in(in) 00074 , _out(out) 00075 {} 00076 00077 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00078 { 00079 return dst = Channel(src); 00080 } 00081 }; 00082 00083 //////////////////////////////////////////////////////////////////////////////// 00084 // T_A // 00085 00086 /** 00087 * @brief 00088 */ 00089 template< typename Channel > 00090 struct channel_color_temperature_t<Channel, temperature::T_A, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00091 { 00092 typedef typename floating_channel_type_t<Channel>::type T; 00093 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00094 typedef typename channel_traits<Channel>::reference ChannelRef; 00095 00096 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00097 { 00098 get_color( dst, red_t() ) = 1.84520578f * get_color( src, red_t() ) + 0.00000009f * get_color( src, green_t() ) + 0.00000002 * get_color( src, blue_t() ); 00099 get_color( dst, green_t() ) = -0.00000005f * get_color( src, red_t() ) + 0.82607192f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00100 get_color( dst, blue_t() ) = 0.00000001f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.23326041 * get_color( src, blue_t() ); 00101 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00102 return dst; 00103 } 00104 }; 00105 00106 /** 00107 * @brief 00108 */ 00109 template< typename Channel > 00110 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_A> : public std::binary_function<Channel, Channel, Channel> 00111 { 00112 typedef typename floating_channel_type_t<Channel>::type T; 00113 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00114 typedef typename channel_traits<Channel>::reference ChannelRef; 00115 00116 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00117 { 00118 get_color( dst, red_t() ) = 0.54194504f * get_color( src, red_t() ) + 0.00000004f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00119 get_color( dst, green_t() ) = +0.00000008f * get_color( src, red_t() ) + 1.21054840f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00120 get_color( dst, blue_t() ) = -0.00000001f * get_color( src, red_t() ) - 0.00000006f * get_color( src, green_t() ) + 0.85470724 * get_color( src, blue_t() ); 00121 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00122 return dst; 00123 } 00124 00125 }; 00126 00127 00128 //////////////////////////////////////////////////////////////////////////////// 00129 // T_B // 00130 00131 /** 00132 * @brief 00133 */ 00134 template< typename Channel > 00135 struct channel_color_temperature_t<Channel, temperature::T_B, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00136 { 00137 typedef typename floating_channel_type_t<Channel>::type T; 00138 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00139 typedef typename channel_traits<Channel>::reference ChannelRef; 00140 00141 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00142 { 00143 get_color( dst, red_t() ) = 1.24874067f * get_color( src, red_t() ) + 0.00000004f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00144 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 0.95096886f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00145 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.75399793 * get_color( src, blue_t() ); 00146 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00147 return dst; 00148 } 00149 }; 00150 00151 /** 00152 * @brief 00153 */ 00154 template< typename Channel > 00155 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_B> : public std::binary_function<Channel, Channel, Channel> 00156 { 00157 typedef typename floating_channel_type_t<Channel>::type T; 00158 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00159 typedef typename channel_traits<Channel>::reference ChannelRef; 00160 00161 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00162 { 00163 get_color( dst, red_t() ) = 0.80080682f * get_color( src, red_t() ) + 0.00000004f * get_color( src, green_t() ) - 0.00000006 * get_color( src, blue_t() ); 00164 get_color( dst, green_t() ) = 0.00000008f * get_color( src, red_t() ) + 1.05155921f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00165 get_color( dst, blue_t() ) = 0.00000001f * get_color( src, red_t() ) + 0.00000003f * get_color( src, green_t() ) + 1.32802486 * get_color( src, blue_t() ); 00166 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00167 return dst; 00168 } 00169 00170 }; 00171 00172 00173 //////////////////////////////////////////////////////////////////////////////// 00174 // T_C // 00175 00176 /** 00177 * @brief 00178 */ 00179 template< typename Channel > 00180 struct channel_color_temperature_t<Channel, temperature::T_C, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00181 { 00182 typedef typename floating_channel_type_t<Channel>::type T; 00183 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00184 typedef typename channel_traits<Channel>::reference ChannelRef; 00185 00186 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00187 { 00188 get_color( dst, red_t() ) = 1.05152202f * get_color( src, red_t() ) + 0.00000017f * get_color( src, green_t() ) + 0.00000018 * get_color( src, blue_t() ); 00189 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 0.97455227f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00190 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 1.10034835 * get_color( src, blue_t() ); 00191 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00192 return dst; 00193 } 00194 }; 00195 00196 /** 00197 * @brief 00198 */ 00199 template< typename Channel > 00200 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_C> : public std::binary_function<Channel, Channel, Channel> 00201 { 00202 typedef typename floating_channel_type_t<Channel>::type T; 00203 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00204 typedef typename channel_traits<Channel>::reference ChannelRef; 00205 00206 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00207 { 00208 get_color( dst, red_t() ) = 0.95100260f * get_color( src, red_t() ) + 0.00000006f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00209 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 1.02611196f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00210 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000001f * get_color( src, green_t() ) + 0.90880305 * get_color( src, blue_t() ); 00211 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00212 return dst; 00213 } 00214 00215 }; 00216 00217 00218 00219 //////////////////////////////////////////////////////////////////////////////// 00220 // T_D50 // 00221 00222 /** 00223 * @brief 00224 */ 00225 template< typename Channel > 00226 struct channel_color_temperature_t<Channel, temperature::T_D50, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00227 { 00228 typedef typename floating_channel_type_t<Channel>::type T; 00229 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00230 typedef typename channel_traits<Channel>::reference ChannelRef; 00231 00232 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00233 { 00234 get_color( dst, red_t() ) = 1.17609382f * get_color( src, red_t() ) + 0.00000007f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00235 get_color( dst, green_t() ) = -0.00000006f * get_color( src, red_t() ) + 0.97570127f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00236 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 0.72197068 * get_color( src, blue_t() ); 00237 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00238 return dst; 00239 } 00240 }; 00241 00242 /** 00243 * @brief 00244 */ 00245 template< typename Channel > 00246 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_D50> : public std::binary_function<Channel, Channel, Channel> 00247 { 00248 typedef typename floating_channel_type_t<Channel>::type T; 00249 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00250 typedef typename channel_traits<Channel>::reference ChannelRef; 00251 00252 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00253 { 00254 get_color( dst, red_t() ) = 0.85027254f * get_color( src, red_t() ) + 0.00000001f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00255 get_color( dst, green_t() ) = -0.00000001f * get_color( src, red_t() ) + 1.02490389f * get_color( src, green_t() ) - 0.00000004 * get_color( src, blue_t() ); 00256 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000001f * get_color( src, green_t() ) + 1.38509774 * get_color( src, blue_t() ); 00257 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00258 return dst; 00259 } 00260 00261 }; 00262 00263 00264 //////////////////////////////////////////////////////////////////////////////// 00265 // T_D55 // 00266 00267 /** 00268 * @brief 00269 */ 00270 template< typename Channel > 00271 struct channel_color_temperature_t<Channel, temperature::T_D55, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00272 { 00273 typedef typename floating_channel_type_t<Channel>::type T; 00274 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00275 typedef typename channel_traits<Channel>::reference ChannelRef; 00276 00277 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00278 { 00279 get_color( dst, red_t() ) = 1.10405362f * get_color( src, red_t() ) + 0.00000012f * get_color( src, green_t() ) + 0.00000006 * get_color( src, blue_t() ); 00280 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 0.98688960f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00281 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.82335168 * get_color( src, blue_t() ); 00282 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00283 return dst; 00284 } 00285 }; 00286 00287 /** 00288 * @brief 00289 */ 00290 template< typename Channel > 00291 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_D55> : public std::binary_function<Channel, Channel, Channel> 00292 { 00293 typedef typename floating_channel_type_t<Channel>::type T; 00294 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00295 typedef typename channel_traits<Channel>::reference ChannelRef; 00296 00297 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00298 { 00299 get_color( dst, red_t() ) = 0.90575325f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00300 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 1.01328468f * get_color( src, green_t() ) - 0.00000004 * get_color( src, blue_t() ); 00301 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000001f * get_color( src, green_t() ) + 1.21454775 * get_color( src, blue_t() ); 00302 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00303 return dst; 00304 } 00305 00306 }; 00307 00308 00309 //////////////////////////////////////////////////////////////////////////////// 00310 // T_D58 // 00311 00312 /** 00313 * @brief 00314 */ 00315 template< typename Channel > 00316 struct channel_color_temperature_t<Channel, temperature::T_D58, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00317 { 00318 typedef typename floating_channel_type_t<Channel>::type T; 00319 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00320 typedef typename channel_traits<Channel>::reference ChannelRef; 00321 00322 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00323 { 00324 get_color( dst, red_t() ) = 1.06815648f * get_color( src, red_t() ) + 0.00000016f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00325 get_color( dst, green_t() ) = -0.00000004f * get_color( src, red_t() ) + 0.99201381f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00326 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 0.87833548 * get_color( src, blue_t() ); 00327 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00328 return dst; 00329 } 00330 }; 00331 00332 /** 00333 * @brief 00334 */ 00335 template< typename Channel > 00336 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_D58> : public std::binary_function<Channel, Channel, Channel> 00337 { 00338 typedef typename floating_channel_type_t<Channel>::type T; 00339 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00340 typedef typename channel_traits<Channel>::reference ChannelRef; 00341 00342 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00343 { 00344 get_color( dst, red_t() ) = 0.93619251f * get_color( src, red_t() ) + 0.00000009f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00345 get_color( dst, green_t() ) = 0.00000001f * get_color( src, red_t() ) + 1.00805032f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00346 get_color( dst, blue_t() ) = -0.00000001f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 1.13851726 * get_color( src, blue_t() ); 00347 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00348 return dst; 00349 } 00350 00351 }; 00352 00353 00354 00355 00356 //////////////////////////////////////////////////////////////////////////////// 00357 // T_D65 // 00358 00359 /** 00360 * @brief 00361 */ 00362 template< typename Channel > 00363 struct channel_color_temperature_t<Channel, temperature::T_D65, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00364 { 00365 typedef typename floating_channel_type_t<Channel>::type T; 00366 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00367 typedef typename channel_traits<Channel>::reference ChannelRef; 00368 00369 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00370 { 00371 get_color( dst, red_t() ) = get_color( src, red_t () ); 00372 get_color( dst, green_t() ) = get_color( src, green_t() ); 00373 get_color( dst, blue_t() ) = get_color( src, blue_t () ); 00374 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00375 return dst; 00376 } 00377 }; 00378 00379 /** 00380 * @brief 00381 */ 00382 template< typename Channel > 00383 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_D65> : public std::binary_function<Channel, Channel, Channel> 00384 { 00385 typedef typename floating_channel_type_t<Channel>::type T; 00386 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00387 typedef typename channel_traits<Channel>::reference ChannelRef; 00388 00389 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00390 { 00391 get_color( dst, red_t() ) = get_color( src, red_t () ); 00392 get_color( dst, green_t() ) = get_color( src, green_t() ); 00393 get_color( dst, blue_t() ) = get_color( src, blue_t () ); 00394 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00395 return dst; 00396 } 00397 00398 }; 00399 00400 00401 //////////////////////////////////////////////////////////////////////////////// 00402 // T_D75 // 00403 00404 /** 00405 * @brief 00406 */ 00407 template< typename Channel > 00408 struct channel_color_temperature_t<Channel, temperature::T_D75, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00409 { 00410 typedef typename floating_channel_type_t<Channel>::type T; 00411 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00412 typedef typename channel_traits<Channel>::reference ChannelRef; 00413 00414 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00415 { 00416 get_color( dst, red_t() ) = 0.92909920f * get_color( src, red_t() ) + 0.00000008f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00417 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 1.00641775f * get_color( src, green_t() ) + 0.00000001 * get_color( src, blue_t() ); 00418 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 1.14529049 * get_color( src, blue_t() ); 00419 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00420 return dst; 00421 } 00422 }; 00423 00424 /** 00425 * @brief 00426 */ 00427 template< typename Channel > 00428 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_D75> : public std::binary_function<Channel, Channel, Channel> 00429 { 00430 typedef typename floating_channel_type_t<Channel>::type T; 00431 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00432 typedef typename channel_traits<Channel>::reference ChannelRef; 00433 00434 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00435 { 00436 get_color( dst, red_t() ) = 1.07631159f * get_color( src, red_t() ) + 0.00000002f * get_color( src, green_t() ) + 0.00000006 * get_color( src, blue_t() ); 00437 get_color( dst, green_t() ) = 0.00000001f * get_color( src, red_t() ) + 0.99362320f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00438 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.87314081 * get_color( src, blue_t() ); 00439 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00440 return dst; 00441 } 00442 00443 }; 00444 00445 00446 //////////////////////////////////////////////////////////////////////////////// 00447 // T_9300 // 00448 00449 /** 00450 * @brief 00451 */ 00452 template< typename Channel > 00453 struct channel_color_temperature_t<Channel, temperature::T_9300, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00454 { 00455 typedef typename floating_channel_type_t<Channel>::type T; 00456 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00457 typedef typename channel_traits<Channel>::reference ChannelRef; 00458 00459 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00460 { 00461 get_color( dst, red_t() ) = 0.89304549f * get_color( src, red_t() ) + 0.00000012f * get_color( src, green_t() ) + 0.00000012 * get_color( src, blue_t() ); 00462 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 0.99430132f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00463 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 1.37155378 * get_color( src, blue_t() ); 00464 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00465 return dst; 00466 } 00467 }; 00468 00469 /** 00470 * @brief 00471 */ 00472 template< typename Channel > 00473 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_9300> : public std::binary_function<Channel, Channel, Channel> 00474 { 00475 typedef typename floating_channel_type_t<Channel>::type T; 00476 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00477 typedef typename channel_traits<Channel>::reference ChannelRef; 00478 00479 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00480 { 00481 get_color( dst, red_t() ) = 1.11976373f * get_color( src, red_t() ) - 0.00000004f * get_color( src, green_t() ) - 0.00000006 * get_color( src, blue_t() ); 00482 get_color( dst, green_t() ) = 0.00000000f * get_color( src, red_t() ) + 1.00573123f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00483 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.72909999 * get_color( src, blue_t() ); 00484 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00485 return dst; 00486 } 00487 00488 }; 00489 00490 00491 //////////////////////////////////////////////////////////////////////////////// 00492 // T_E // 00493 00494 /** 00495 * @brief 00496 */ 00497 template< typename Channel > 00498 struct channel_color_temperature_t<Channel, temperature::T_E, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00499 { 00500 typedef typename floating_channel_type_t<Channel>::type T; 00501 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00502 typedef typename channel_traits<Channel>::reference ChannelRef; 00503 00504 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00505 { 00506 get_color( dst, red_t() ) = 1.20491767f * get_color( src, red_t() ) + 0.00000008f * get_color( src, green_t() ) + 0.00000012 * get_color( src, blue_t() ); 00507 get_color( dst, green_t() ) = -0.00000003f * get_color( src, red_t() ) + 0.94827831f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00508 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.90876031 * get_color( src, blue_t() ); 00509 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00510 return dst; 00511 } 00512 }; 00513 00514 /** 00515 * @brief 00516 */ 00517 template< typename Channel > 00518 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_E> : public std::binary_function<Channel, Channel, Channel> 00519 { 00520 typedef typename floating_channel_type_t<Channel>::type T; 00521 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00522 typedef typename channel_traits<Channel>::reference ChannelRef; 00523 00524 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00525 { 00526 get_color( dst, red_t() ) = 0.82993227f * get_color( src, red_t() ) - 0.00000005f * get_color( src, green_t() ) - 0.00000009 * get_color( src, blue_t() ); 00527 get_color( dst, green_t() ) = 0.00000005f * get_color( src, red_t() ) + 1.05454266f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00528 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 1.10040021 * get_color( src, blue_t() ); 00529 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00530 return dst; 00531 } 00532 00533 }; 00534 00535 00536 //////////////////////////////////////////////////////////////////////////////// 00537 // T_F2 // 00538 00539 /** 00540 * @brief 00541 */ 00542 template< typename Channel > 00543 struct channel_color_temperature_t<Channel, temperature::T_F2, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00544 { 00545 typedef typename floating_channel_type_t<Channel>::type T; 00546 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00547 typedef typename channel_traits<Channel>::reference ChannelRef; 00548 00549 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00550 { 00551 get_color( dst, red_t() ) = 1.34113419f * get_color( src, red_t() ) + 0.00000007f * get_color( src, green_t() ) + 0.00000006 * get_color( src, blue_t() ); 00552 get_color( dst, green_t() ) = -0.00000004f * get_color( src, red_t() ) + 0.94260973f * get_color( src, green_t() ) - 0.00000000 * get_color( src, blue_t() ); 00553 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 0.56362498 * get_color( src, blue_t() ); 00554 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00555 return dst; 00556 } 00557 }; 00558 00559 /** 00560 * @brief 00561 */ 00562 template< typename Channel > 00563 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_F2> : public std::binary_function<Channel, Channel, Channel> 00564 { 00565 typedef typename floating_channel_type_t<Channel>::type T; 00566 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00567 typedef typename channel_traits<Channel>::reference ChannelRef; 00568 00569 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00570 { 00571 get_color( dst, red_t() ) = 0.74563771f * get_color( src, red_t() ) + 0.00000003f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00572 get_color( dst, green_t() ) = 0.00000002f * get_color( src, red_t() ) + 1.06088448f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00573 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000003f * get_color( src, green_t() ) + 1.77422941 * get_color( src, blue_t() ); 00574 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00575 return dst; 00576 } 00577 00578 }; 00579 00580 00581 00582 //////////////////////////////////////////////////////////////////////////////// 00583 // T_F7 // 00584 00585 /** 00586 * @brief 00587 */ 00588 template< typename Channel > 00589 struct channel_color_temperature_t<Channel, temperature::T_F7, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00590 { 00591 typedef typename floating_channel_type_t<Channel>::type T; 00592 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00593 typedef typename channel_traits<Channel>::reference ChannelRef; 00594 00595 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00596 { 00597 get_color( dst, red_t() ) = 1.00054073f * get_color( src, red_t() ) + 0.00000006f * get_color( src, green_t() ) + 0.00000012 * get_color( src, blue_t() ); 00598 get_color( dst, green_t() ) = -0.00000003f * get_color( src, red_t() ) + 0.99999511f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00599 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.99845666 * get_color( src, blue_t() ); 00600 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00601 return dst; 00602 } 00603 }; 00604 00605 /** 00606 * @brief 00607 */ 00608 template< typename Channel > 00609 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_F7> : public std::binary_function<Channel, Channel, Channel> 00610 { 00611 typedef typename floating_channel_type_t<Channel>::type T; 00612 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00613 typedef typename channel_traits<Channel>::reference ChannelRef; 00614 00615 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00616 { 00617 get_color( dst, red_t() ) = 0.99945968f * get_color( src, red_t() ) - 0.00000008f * get_color( src, green_t() ) - 0.00000003 * get_color( src, blue_t() ); 00618 get_color( dst, green_t() ) = 0.00000001f * get_color( src, red_t() ) + 1.00000501f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00619 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 1.00154579 * get_color( src, blue_t() ); 00620 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00621 return dst; 00622 } 00623 00624 }; 00625 00626 00627 00628 //////////////////////////////////////////////////////////////////////////////// 00629 // T_F11 // 00630 00631 /** 00632 * @brief 00633 */ 00634 template< typename Channel > 00635 struct channel_color_temperature_t<Channel, temperature::T_F11, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00636 { 00637 typedef typename floating_channel_type_t<Channel>::type T; 00638 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00639 typedef typename channel_traits<Channel>::reference ChannelRef; 00640 00641 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00642 { 00643 get_color( dst, red_t() ) = 1.20491767f * get_color( src, red_t() ) + 0.00000008f * get_color( src, green_t() ) + 0.00000012 * get_color( src, blue_t() ); 00644 get_color( dst, green_t() ) = -0.00000003f * get_color( src, red_t() ) + 0.94827831f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00645 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.90876031 * get_color( src, blue_t() ); 00646 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00647 return dst; 00648 } 00649 }; 00650 00651 /** 00652 * @brief 00653 */ 00654 template< typename Channel > 00655 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_F11> : public std::binary_function<Channel, Channel, Channel> 00656 { 00657 typedef typename floating_channel_type_t<Channel>::type T; 00658 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00659 typedef typename channel_traits<Channel>::reference ChannelRef; 00660 00661 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00662 { 00663 get_color( dst, red_t() ) = 0.70728123f * get_color( src, red_t() ) + 0.00000006f * get_color( src, green_t() ) + 0.00000006 * get_color( src, blue_t() ); 00664 get_color( dst, green_t() ) = -0.00000002f * get_color( src, red_t() ) + 1.08209848f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00665 get_color( dst, blue_t() ) = -0.00000001f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 1.87809896 * get_color( src, blue_t() ); 00666 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00667 return dst; 00668 } 00669 00670 }; 00671 00672 00673 00674 //////////////////////////////////////////////////////////////////////////////// 00675 // T_DCPI3 // 00676 00677 /** 00678 * @brief 00679 */ 00680 template< typename Channel > 00681 struct channel_color_temperature_t<Channel, temperature::T_DCIP3, temperature::T_INTER> : public std::binary_function<Channel, Channel, Channel> 00682 { 00683 typedef typename floating_channel_type_t<Channel>::type T; 00684 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00685 typedef typename channel_traits<Channel>::reference ChannelRef; 00686 00687 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00688 { 00689 get_color( dst, red_t() ) = 0.88602084f * get_color( src, red_t() ) + 0.00000013f * get_color( src, green_t() ) + 0.00000003 * get_color( src, blue_t() ); 00690 get_color( dst, green_t() ) = -0.00000003f * get_color( src, red_t() ) + 1.04855490f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00691 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) - 0.00000000f * get_color( src, green_t() ) + 0.85470724 * get_color( src, blue_t() ); 00692 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00693 return dst; 00694 } 00695 }; 00696 00697 /** 00698 * @brief 00699 */ 00700 template< typename Channel > 00701 struct channel_color_temperature_t<Channel, temperature::T_INTER, temperature::T_DCIP3> : public std::binary_function<Channel, Channel, Channel> 00702 { 00703 typedef typename floating_channel_type_t<Channel>::type T; 00704 typedef typename channel_traits<Channel>::const_reference ChannelConstRef; 00705 typedef typename channel_traits<Channel>::reference ChannelRef; 00706 00707 ChannelRef operator()( ChannelConstRef src, ChannelRef dst ) const 00708 { 00709 get_color( dst, red_t() ) = 1.12864172f * get_color( src, red_t() ) - 0.00000001f * get_color( src, green_t() ) + 0.00000000 * get_color( src, blue_t() ); 00710 get_color( dst, green_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.95369333f * get_color( src, green_t() ) - 0.00000001 * get_color( src, blue_t() ); 00711 get_color( dst, blue_t() ) = 0.00000000f * get_color( src, red_t() ) + 0.00000000f * get_color( src, green_t() ) + 1.16999125 * get_color( src, blue_t() ); 00712 copy_pixel_channel_if_exist<alpha_t>( src, dst ); 00713 return dst; 00714 } 00715 }; 00716 00717 00718 //////////////////////////////////////////////////////////////////////////////// 00719 //////////////////////////////////////////////////////////////////////////////// 00720 00721 00722 00723 template< typename Pixel, 00724 class IN, 00725 class OUT > 00726 struct pixel_color_temperature_t 00727 { 00728 typedef typename channel_type<Pixel>::type Channel; 00729 const IN& _in; 00730 const OUT& _out; 00731 00732 pixel_color_temperature_t( const IN& in, const OUT& out ) 00733 : _in(in) 00734 , _out(out) 00735 {} 00736 00737 Pixel& operator()( const Pixel& p1, 00738 Pixel& p2 ) const 00739 { 00740 static_for_each( 00741 p1, p2, 00742 channel_color_temperature_t< Channel, IN, OUT >( _in, _out ) 00743 ); 00744 return p2; 00745 } 00746 }; 00747 00748 template< class IN, 00749 class OUT > 00750 struct transform_pixel_color_temperature_t 00751 { 00752 const IN& _in; 00753 const OUT& _out; 00754 00755 transform_pixel_color_temperature_t( const IN& in, const OUT& out ) 00756 : _in(in) 00757 , _out(out) 00758 {} 00759 00760 template< typename Pixel> 00761 Pixel operator()( const Pixel& p1 ) const 00762 { 00763 Pixel p2; 00764 pixel_color_temperature_t<Pixel, IN, OUT>( _in, _out )( p1, p2 ); 00765 return p2; 00766 } 00767 }; 00768 00769 /** 00770 * @example temperature_convert_view( srcView, dstView, temperature::sRGB(), temperature::Gamma(5.0) ); 00771 */ 00772 template<class TemperatureIN, class TemperatureOUT, class View> 00773 void temperature_convert_view( const View& src, View& dst, const TemperatureIN& temperatureIn = TemperatureIN(), const TemperatureOUT& temperatureOut = TemperatureOUT() ) 00774 { 00775 boost::gil::transform_pixels( src, dst, transform_pixel_color_temperature_t<TemperatureIN, TemperatureOUT>( temperatureIn, temperatureOut ), *this ); 00776 } 00777 00778 /** 00779 * @example temperature_convert_pixel( srcPix, dstPix, temperature::sRGB(), temperature::Gamma(5.0) ); 00780 */ 00781 template<class TemperatureIN, class TemperatureOUT, class Pixel> 00782 void temperature_convert_pixel( const Pixel& src, Pixel& dst, const TemperatureIN& temperatureIn = TemperatureIN(), const TemperatureOUT& temperatureOut = TemperatureOUT() ) 00783 { 00784 pixel_color_temperature_t<TemperatureIN, TemperatureOUT>( temperatureIn, temperatureOut )( src, dst ); 00785 } 00786 00787 } 00788 } 00789 00790 #endif 00791