00001 /* 00002 ----------------------------------------------------------------------------- 00003 This source file is part of OGRE 00004 (Object-oriented Graphics Rendering Engine) 00005 For the latest info, see http://www.ogre3d.org/ 00006 00007 Copyright (c) 2000-2006 Torus Knot Software Ltd 00008 Also see acknowledgements in Readme.html 00009 00010 This program is free software; you can redistribute it and/or modify it under 00011 the terms of the GNU Lesser General Public License as published by the Free Software 00012 Foundation; either version 2 of the License, or (at your option) any later 00013 version. 00014 00015 This program is distributed in the hope that it will be useful, but WITHOUT 00016 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 00017 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. 00018 00019 You should have received a copy of the GNU Lesser General Public License along with 00020 this program; if not, write to the Free Software Foundation, Inc., 59 Temple 00021 Place - Suite 330, Boston, MA 02111-1307, USA, or go to 00022 http://www.gnu.org/copyleft/lesser.txt. 00023 00024 You may alternatively use this source under the terms of a specific version of 00025 the OGRE Unrestricted License provided you have obtained such a license from 00026 Torus Knot Software Ltd. 00027 ----------------------------------------------------------------------------- 00028 */ 00030 using namespace Ogre; 00031 00032 // NB VC6 can't handle these templates 00033 #if OGRE_COMPILER != OGRE_COMPILER_MSVC || OGRE_COMP_VER >= 1300 00034 00035 #define FMTCONVERTERID(from,to) (((from)<<8)|(to)) 00036 00047 template <class U> struct PixelBoxConverter 00048 { 00049 static const int ID = U::ID; 00050 static void conversion(const PixelBox &src, const PixelBox &dst) 00051 { 00052 typename U::SrcType *srcptr = static_cast<typename U::SrcType*>(src.data) 00053 + (src.left + src.top * src.rowPitch + src.front * src.slicePitch); 00054 typename U::DstType *dstptr = static_cast<typename U::DstType*>(dst.data) 00055 + (dst.left + dst.top * dst.rowPitch + dst.front * dst.slicePitch); 00056 const size_t srcSliceSkip = src.getSliceSkip(); 00057 const size_t dstSliceSkip = dst.getSliceSkip(); 00058 const size_t k = src.right - src.left; 00059 for(size_t z=src.front; z<src.back; z++) 00060 { 00061 for(size_t y=src.top; y<src.bottom; y++) 00062 { 00063 for(size_t x=0; x<k; x++) 00064 { 00065 dstptr[x] = U::pixelConvert(srcptr[x]); 00066 } 00067 srcptr += src.rowPitch; 00068 dstptr += dst.rowPitch; 00069 } 00070 srcptr += srcSliceSkip; 00071 dstptr += dstSliceSkip; 00072 } 00073 } 00074 }; 00075 00076 template <typename T, typename U, int id> struct PixelConverter { 00077 static const int ID = id; 00078 typedef T SrcType; 00079 typedef U DstType; 00080 00081 //inline static DstType pixelConvert(const SrcType &inp); 00082 }; 00083 00084 00086 struct Col3b { 00087 Col3b(unsigned int a, unsigned int b, unsigned int c): 00088 x((Ogre::uint8)a), y((Ogre::uint8)b), z((Ogre::uint8)c) { } 00089 Ogre::uint8 x,y,z; 00090 }; 00092 struct Col3f { 00093 Col3f(float r, float g, float b): 00094 r(r), g(g), b(b) { } 00095 float r,g,b; 00096 }; 00098 struct Col4f { 00099 Col4f(float r, float g, float b, float a): 00100 r(r), g(g), b(b), a(a) { } 00101 float r,g,b,a; 00102 }; 00103 00104 struct A8R8G8B8toA8B8G8R8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_A8R8G8B8, PF_A8B8G8R8)> 00105 { 00106 inline static DstType pixelConvert(SrcType inp) 00107 { 00108 return ((inp&0x000000FF)<<16)|(inp&0xFF00FF00)|((inp&0x00FF0000)>>16); 00109 } 00110 }; 00111 00112 struct A8R8G8B8toB8G8R8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_A8R8G8B8, PF_B8G8R8A8)> 00113 { 00114 inline static DstType pixelConvert(SrcType inp) 00115 { 00116 return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24); 00117 } 00118 }; 00119 00120 struct A8R8G8B8toR8G8B8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_A8R8G8B8, PF_R8G8B8A8)> 00121 { 00122 inline static DstType pixelConvert(SrcType inp) 00123 { 00124 return ((inp&0x00FFFFFF)<<8)|((inp&0xFF000000)>>24); 00125 } 00126 }; 00127 00128 struct A8B8G8R8toA8R8G8B8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_A8B8G8R8, PF_A8R8G8B8)> 00129 { 00130 inline static DstType pixelConvert(SrcType inp) 00131 { 00132 return ((inp&0x000000FF)<<16)|(inp&0xFF00FF00)|((inp&0x00FF0000)>>16); 00133 } 00134 }; 00135 00136 struct A8B8G8R8toB8G8R8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_A8B8G8R8, PF_B8G8R8A8)> 00137 { 00138 inline static DstType pixelConvert(SrcType inp) 00139 { 00140 return ((inp&0x00FFFFFF)<<8)|((inp&0xFF000000)>>24); 00141 } 00142 }; 00143 00144 struct A8B8G8R8toR8G8B8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_A8B8G8R8, PF_R8G8B8A8)> 00145 { 00146 inline static DstType pixelConvert(SrcType inp) 00147 { 00148 return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24); 00149 } 00150 }; 00151 00152 struct B8G8R8A8toA8R8G8B8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_B8G8R8A8, PF_A8R8G8B8)> 00153 { 00154 inline static DstType pixelConvert(SrcType inp) 00155 { 00156 return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24); 00157 } 00158 }; 00159 00160 struct B8G8R8A8toA8B8G8R8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_B8G8R8A8, PF_A8B8G8R8)> 00161 { 00162 inline static DstType pixelConvert(SrcType inp) 00163 { 00164 return ((inp&0x000000FF)<<24)|((inp&0xFFFFFF00)>>8); 00165 } 00166 }; 00167 00168 struct B8G8R8A8toR8G8B8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_B8G8R8A8, PF_R8G8B8A8)> 00169 { 00170 inline static DstType pixelConvert(SrcType inp) 00171 { 00172 return ((inp&0x0000FF00)<<16)|(inp&0x00FF00FF)|((inp&0xFF000000)>>16); 00173 } 00174 }; 00175 00176 struct R8G8B8A8toA8R8G8B8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_R8G8B8A8, PF_A8R8G8B8)> 00177 { 00178 inline static DstType pixelConvert(SrcType inp) 00179 { 00180 return ((inp&0x000000FF)<<24)|((inp&0xFFFFFF00)>>8); 00181 } 00182 }; 00183 00184 struct R8G8B8A8toA8B8G8R8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_R8G8B8A8, PF_A8B8G8R8)> 00185 { 00186 inline static DstType pixelConvert(SrcType inp) 00187 { 00188 return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24); 00189 } 00190 }; 00191 00192 struct R8G8B8A8toB8G8R8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_R8G8B8A8, PF_B8G8R8A8)> 00193 { 00194 inline static DstType pixelConvert(SrcType inp) 00195 { 00196 return ((inp&0x0000FF00)<<16)|(inp&0x00FF00FF)|((inp&0xFF000000)>>16); 00197 } 00198 }; 00199 00200 struct A8B8G8R8toL8: public PixelConverter <Ogre::uint32, Ogre::uint8, FMTCONVERTERID(PF_A8B8G8R8, PF_L8)> 00201 { 00202 inline static DstType pixelConvert(SrcType inp) 00203 { 00204 return (Ogre::uint8)(inp&0x000000FF); 00205 } 00206 }; 00207 00208 struct L8toA8B8G8R8: public PixelConverter <Ogre::uint8, Ogre::uint32, FMTCONVERTERID(PF_L8, PF_A8B8G8R8)> 00209 { 00210 inline static DstType pixelConvert(SrcType inp) 00211 { 00212 return 0xFF000000|(((unsigned int)inp)<<0)|(((unsigned int)inp)<<8)|(((unsigned int)inp)<<16); 00213 } 00214 }; 00215 00216 struct A8R8G8B8toL8: public PixelConverter <Ogre::uint32, Ogre::uint8, FMTCONVERTERID(PF_A8R8G8B8, PF_L8)> 00217 { 00218 inline static DstType pixelConvert(SrcType inp) 00219 { 00220 return (Ogre::uint8)((inp&0x00FF0000)>>16); 00221 } 00222 }; 00223 00224 struct L8toA8R8G8B8: public PixelConverter <Ogre::uint8, Ogre::uint32, FMTCONVERTERID(PF_L8, PF_A8R8G8B8)> 00225 { 00226 inline static DstType pixelConvert(SrcType inp) 00227 { 00228 return 0xFF000000|(((unsigned int)inp)<<0)|(((unsigned int)inp)<<8)|(((unsigned int)inp)<<16); 00229 } 00230 }; 00231 00232 struct B8G8R8A8toL8: public PixelConverter <Ogre::uint32, Ogre::uint8, FMTCONVERTERID(PF_B8G8R8A8, PF_L8)> 00233 { 00234 inline static DstType pixelConvert(SrcType inp) 00235 { 00236 return (Ogre::uint8)((inp&0x0000FF00)>>8); 00237 } 00238 }; 00239 00240 struct L8toB8G8R8A8: public PixelConverter <Ogre::uint8, Ogre::uint32, FMTCONVERTERID(PF_L8, PF_B8G8R8A8)> 00241 { 00242 inline static DstType pixelConvert(SrcType inp) 00243 { 00244 return 0x000000FF|(((unsigned int)inp)<<8)|(((unsigned int)inp)<<16)|(((unsigned int)inp)<<24); 00245 } 00246 }; 00247 00248 struct L8toL16: public PixelConverter <Ogre::uint8, Ogre::uint16, FMTCONVERTERID(PF_L8, PF_L16)> 00249 { 00250 inline static DstType pixelConvert(SrcType inp) 00251 { 00252 return (Ogre::uint16)((((unsigned int)inp)<<8)|(((unsigned int)inp))); 00253 } 00254 }; 00255 00256 struct L16toL8: public PixelConverter <Ogre::uint16, Ogre::uint8, FMTCONVERTERID(PF_L16, PF_L8)> 00257 { 00258 inline static DstType pixelConvert(SrcType inp) 00259 { 00260 return (Ogre::uint8)(inp>>8); 00261 } 00262 }; 00263 00264 struct R8G8B8toB8G8R8: public PixelConverter <Col3b, Col3b, FMTCONVERTERID(PF_R8G8B8, PF_B8G8R8)> 00265 { 00266 inline static DstType pixelConvert(const SrcType &inp) 00267 { 00268 return Col3b(inp.z, inp.y, inp.x); 00269 } 00270 }; 00271 00272 struct B8G8R8toR8G8B8: public PixelConverter <Col3b, Col3b, FMTCONVERTERID(PF_B8G8R8, PF_R8G8B8)> 00273 { 00274 inline static DstType pixelConvert(const SrcType &inp) 00275 { 00276 return Col3b(inp.z, inp.y, inp.x); 00277 } 00278 }; 00279 00280 // X8Y8Z8 -> X8<<xshift Y8<<yshift Z8<<zshift A8<<ashift 00281 template <int id, unsigned int xshift, unsigned int yshift, unsigned int zshift, unsigned int ashift> struct Col3btoUint32swizzler: 00282 public PixelConverter <Col3b, Ogre::uint32, id> 00283 { 00284 inline static Ogre::uint32 pixelConvert(const Col3b &inp) 00285 { 00286 #if OGRE_ENDIAN == OGRE_ENDIAN_BIG 00287 return (0xFF<<ashift) | (((unsigned int)inp.x)<<xshift) | (((unsigned int)inp.y)<<yshift) | (((unsigned int)inp.z)<<zshift); 00288 #else 00289 return (0xFF<<ashift) | (((unsigned int)inp.x)<<zshift) | (((unsigned int)inp.y)<<yshift) | (((unsigned int)inp.z)<<xshift); 00290 #endif 00291 } 00292 }; 00293 00294 struct R8G8B8toA8R8G8B8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_R8G8B8, PF_A8R8G8B8), 16, 8, 0, 24> { }; 00295 struct B8G8R8toA8R8G8B8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_B8G8R8, PF_A8R8G8B8), 0, 8, 16, 24> { }; 00296 struct R8G8B8toA8B8G8R8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_R8G8B8, PF_A8B8G8R8), 0, 8, 16, 24> { }; 00297 struct B8G8R8toA8B8G8R8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_B8G8R8, PF_A8B8G8R8), 16, 8, 0, 24> { }; 00298 struct R8G8B8toB8G8R8A8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_R8G8B8, PF_B8G8R8A8), 8, 16, 24, 0> { }; 00299 struct B8G8R8toB8G8R8A8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_B8G8R8, PF_B8G8R8A8), 24, 16, 8, 0> { }; 00300 00301 struct A8R8G8B8toR8G8B8: public PixelConverter <Ogre::uint32, Col3b, FMTCONVERTERID(PF_A8R8G8B8, PF_BYTE_RGB)> 00302 { 00303 inline static DstType pixelConvert(Ogre::uint32 inp) 00304 { 00305 return Col3b((Ogre::uint8)((inp>>16)&0xFF), (Ogre::uint8)((inp>>8)&0xFF), (Ogre::uint8)((inp>>0)&0xFF)); 00306 } 00307 }; 00308 struct A8R8G8B8toB8G8R8: public PixelConverter <Ogre::uint32, Col3b, FMTCONVERTERID(PF_A8R8G8B8, PF_BYTE_BGR)> 00309 { 00310 inline static DstType pixelConvert(Ogre::uint32 inp) 00311 { 00312 return Col3b((Ogre::uint8)((inp>>0)&0xFF), (Ogre::uint8)((inp>>8)&0xFF), (Ogre::uint8)((inp>>16)&0xFF)); 00313 } 00314 }; 00315 00316 // Only conversions from X8R8G8B8 to formats with alpha need to be defined, the rest is implicitly the same 00317 // as A8R8G8B8 00318 struct X8R8G8B8toA8R8G8B8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_A8R8G8B8)> 00319 { 00320 inline static DstType pixelConvert(SrcType inp) 00321 { 00322 return inp | 0xFF000000; 00323 } 00324 }; 00325 struct X8R8G8B8toA8B8G8R8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_A8B8G8R8)> 00326 { 00327 inline static DstType pixelConvert(SrcType inp) 00328 { 00329 return ((inp&0x0000FF)<<16)|((inp&0xFF0000)>>16)|(inp&0x00FF00)|0xFF000000; 00330 } 00331 }; 00332 struct X8R8G8B8toB8G8R8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_B8G8R8A8)> 00333 { 00334 inline static DstType pixelConvert(SrcType inp) 00335 { 00336 return ((inp&0x0000FF)<<24)|((inp&0xFF0000)>>8)|((inp&0x00FF00)<<8)|0x000000FF; 00337 } 00338 }; 00339 struct X8R8G8B8toR8G8B8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_R8G8B8A8)> 00340 { 00341 inline static DstType pixelConvert(SrcType inp) 00342 { 00343 return ((inp&0xFFFFFF)<<8)|0x000000FF; 00344 } 00345 }; 00346 00347 // X8B8G8R8 00348 struct X8B8G8R8toA8R8G8B8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_A8R8G8B8)> 00349 { 00350 inline static DstType pixelConvert(SrcType inp) 00351 { 00352 return ((inp&0x0000FF)<<16)|((inp&0xFF0000)>>16)|(inp&0x00FF00)|0xFF000000; 00353 } 00354 }; 00355 struct X8B8G8R8toA8B8G8R8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_A8B8G8R8)> 00356 { 00357 inline static DstType pixelConvert(SrcType inp) 00358 { 00359 return inp | 0xFF000000; 00360 } 00361 }; 00362 struct X8B8G8R8toB8G8R8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_B8G8R8A8)> 00363 { 00364 inline static DstType pixelConvert(SrcType inp) 00365 { 00366 return ((inp&0xFFFFFF)<<8)|0x000000FF; 00367 } 00368 }; 00369 struct X8B8G8R8toR8G8B8A8: public PixelConverter <Ogre::uint32, Ogre::uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_R8G8B8A8)> 00370 { 00371 inline static DstType pixelConvert(SrcType inp) 00372 { 00373 return ((inp&0x0000FF)<<24)|((inp&0xFF0000)>>8)|((inp&0x00FF00)<<8)|0x000000FF; 00374 } 00375 }; 00376 00377 00378 #define CASECONVERTER(type) case type::ID : PixelBoxConverter<type>::conversion(src, dst); return 1; 00379 00380 inline int doOptimizedConversion(const PixelBox &src, const PixelBox &dst) 00381 {; 00382 switch(FMTCONVERTERID(src.format, dst.format)) 00383 { 00384 // Register converters here 00385 CASECONVERTER(A8R8G8B8toA8B8G8R8); 00386 CASECONVERTER(A8R8G8B8toB8G8R8A8); 00387 CASECONVERTER(A8R8G8B8toR8G8B8A8); 00388 CASECONVERTER(A8B8G8R8toA8R8G8B8); 00389 CASECONVERTER(A8B8G8R8toB8G8R8A8); 00390 CASECONVERTER(A8B8G8R8toR8G8B8A8); 00391 CASECONVERTER(B8G8R8A8toA8R8G8B8); 00392 CASECONVERTER(B8G8R8A8toA8B8G8R8); 00393 CASECONVERTER(B8G8R8A8toR8G8B8A8); 00394 CASECONVERTER(R8G8B8A8toA8R8G8B8); 00395 CASECONVERTER(R8G8B8A8toA8B8G8R8); 00396 CASECONVERTER(R8G8B8A8toB8G8R8A8); 00397 CASECONVERTER(A8B8G8R8toL8); 00398 CASECONVERTER(L8toA8B8G8R8); 00399 CASECONVERTER(A8R8G8B8toL8); 00400 CASECONVERTER(L8toA8R8G8B8); 00401 CASECONVERTER(B8G8R8A8toL8); 00402 CASECONVERTER(L8toB8G8R8A8); 00403 CASECONVERTER(L8toL16); 00404 CASECONVERTER(L16toL8); 00405 CASECONVERTER(B8G8R8toR8G8B8); 00406 CASECONVERTER(R8G8B8toB8G8R8); 00407 CASECONVERTER(R8G8B8toA8R8G8B8); 00408 CASECONVERTER(B8G8R8toA8R8G8B8); 00409 CASECONVERTER(R8G8B8toA8B8G8R8); 00410 CASECONVERTER(B8G8R8toA8B8G8R8); 00411 CASECONVERTER(R8G8B8toB8G8R8A8); 00412 CASECONVERTER(B8G8R8toB8G8R8A8); 00413 CASECONVERTER(A8R8G8B8toR8G8B8); 00414 CASECONVERTER(A8R8G8B8toB8G8R8); 00415 CASECONVERTER(X8R8G8B8toA8R8G8B8); 00416 CASECONVERTER(X8R8G8B8toA8B8G8R8); 00417 CASECONVERTER(X8R8G8B8toB8G8R8A8); 00418 CASECONVERTER(X8R8G8B8toR8G8B8A8); 00419 CASECONVERTER(X8B8G8R8toA8R8G8B8); 00420 CASECONVERTER(X8B8G8R8toA8B8G8R8); 00421 CASECONVERTER(X8B8G8R8toB8G8R8A8); 00422 CASECONVERTER(X8B8G8R8toR8G8B8A8); 00423 00424 default: 00425 return 0; 00426 } 00427 } 00428 #undef CASECONVERTER 00429 00430 #endif // VC6 protection
Copyright © 2008 Torus Knot Software Ltd
This work is licensed under a Creative Commons Attribution-ShareAlike 2.5 License.
Last modified Sun Sep 27 22:02:24 2009