TuttleOFX
1
|
00001 #include "TrilinInterpolator.hpp" 00002 #include "Color.hpp" 00003 #include "AbstractLut.hpp" 00004 #include <cmath> 00005 00006 namespace tuttle { 00007 00008 Color TrilinInterpolator::interpolate( const AbstractLut* lut, const double x, const double y, const double z ) const 00009 { 00010 Color p000, p001, p010, p011, p100, p101, p110, p111; 00011 unsigned int x0, y0, z0, x1, y1, z1; 00012 unsigned int x1MinusX0, y1MinusY0, z1MinusZ0; 00013 double oneByX1MinusX0, oneByY1MinusY0, oneByZ1MinusZ0; 00014 double dx, dy, dz; 00015 Color c0, c1, c2, c3, c4, c5, c6, c7; 00016 Color black( 0., 0., 0. ); 00017 size_t dimSize = lut->dimSize(); 00018 00019 x0 = (unsigned int)std::floor( x * ( dimSize - 1 ) ); 00020 y0 = (unsigned int)std::floor( y * ( dimSize - 1 ) ); 00021 z0 = (unsigned int)std::floor( z * ( dimSize - 1 ) ); 00022 00023 x1 = x0 + 1; 00024 y1 = y0 + 1; 00025 z1 = z0 + 1; 00026 00027 if( x1 >= dimSize ) 00028 x1 = dimSize - 1; 00029 else if( x1 < 0 ) 00030 x1 = 0; 00031 if( y1 >= dimSize ) 00032 y1 = dimSize - 1; 00033 else if( y1 < 0 ) 00034 y1 = 0; 00035 if( z1 >= dimSize ) 00036 z1 = dimSize - 1; 00037 else if( z1 < 0 ) 00038 z1 = 0; 00039 00040 p000 = lut->getIndexedColor( x0, y0, z0 ); 00041 p001 = lut->getIndexedColor( x0, y0, z1 ); 00042 p010 = lut->getIndexedColor( x0, y1, z0 ); 00043 p011 = lut->getIndexedColor( x0, y1, z1 ); 00044 p100 = lut->getIndexedColor( x1, y0, z0 ); 00045 p101 = lut->getIndexedColor( x1, y0, z1 ); 00046 p110 = lut->getIndexedColor( x1, y1, z0 ); 00047 p111 = lut->getIndexedColor( x1, y1, z1 ); 00048 00049 dx = x * ( dimSize - 1.0 ) - (double)x0; 00050 dy = y * ( dimSize - 1.0 ) - (double)y0; 00051 dz = z * ( dimSize - 1.0 ) - (double)z0; 00052 00053 c0 = p000; 00054 x1MinusX0 = x1 - x0; 00055 y1MinusY0 = y1 - y0; 00056 z1MinusZ0 = z1 - z0; 00057 oneByX1MinusX0 = 1.0 / (double) x1MinusX0; 00058 oneByY1MinusY0 = 1.0 / (double) y1MinusY0; 00059 oneByZ1MinusZ0 = 1.0 / (double) z1MinusZ0; 00060 if( x1MinusX0 ) 00061 { 00062 c1 = ( p100 - p000 ) * oneByX1MinusX0; 00063 c1 *= dx; 00064 } 00065 else 00066 { 00067 c1 = black; 00068 00069 } 00070 if( y1MinusY0 ) 00071 { 00072 c2 = ( p010 - p000 ) * oneByY1MinusY0; 00073 c2 *= dy; 00074 } 00075 else 00076 c2 = black; 00077 if( z1MinusZ0 ) 00078 { 00079 c3 = ( p001 - p000 ) * oneByZ1MinusZ0; 00080 c3 *= dz; 00081 } 00082 else 00083 c3 = black; 00084 if( x1MinusX0 * y1MinusY0 ) 00085 { 00086 c4 = ( p110 - p010 - p100 + p000 ) * ( oneByX1MinusX0 * oneByY1MinusY0 ); 00087 c4 *= dx * dy; 00088 } 00089 else 00090 c4 = black; 00091 if( x1MinusX0 * z1MinusZ0 ) 00092 { 00093 c5 = ( p101 - p001 - p100 + p000 ) * ( oneByX1MinusX0 * oneByZ1MinusZ0 ); 00094 c5 *= dx * dz; 00095 } 00096 else 00097 c6 = black; 00098 if( y1MinusY0 * z1MinusZ0 ) 00099 { 00100 c6 = ( p011 - p001 - p010 + p000 ) * ( oneByY1MinusY0 * oneByZ1MinusZ0 ); 00101 c6 *= dy * dz; 00102 } 00103 else 00104 c6 = black; 00105 if( x1MinusX0 * y1MinusY0 * z1MinusZ0 ) 00106 { 00107 c7 = ( p111 - p011 - p101 - p110 + p100 + p001 + p010 - p000 ) * ( oneByX1MinusX0 * oneByY1MinusY0 * oneByZ1MinusZ0 ); 00108 c7 *= dx * dy * dz; 00109 } 00110 else 00111 c7 = black; 00112 00113 return Color( c0.x + c1.x + c2.x + c3.x + c4.x + c5.x + c6.x + c7.x, 00114 c0.y + c1.y + c2.y + c3.y + c4.y + c5.y + c6.y + c7.y, 00115 c0.z + c1.z + c2.z + c3.z + c4.z + c5.z + c6.z + c7.z ); 00116 } 00117 00118 };