Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: downloads/OgreMain/src/OgrePixelConversions.h @ 3

Last change on this file since 3 was 3, checked in by anonymous, 17 years ago

=update

File size: 14.4 KB
Line 
1 /*
2-----------------------------------------------------------------------------
3This source file is part of OGRE
4    (Object-oriented Graphics Rendering Engine)
5For the latest info, see http://www.ogre3d.org/
6
7Copyright (c) 2000-2006 Torus Knot Software Ltd
8Also see acknowledgements in Readme.html
9
10This program is free software; you can redistribute it and/or modify it under
11the terms of the GNU Lesser General Public License as published by the Free Software
12Foundation; either version 2 of the License, or (at your option) any later
13version.
14
15This program is distributed in the hope that it will be useful, but WITHOUT
16ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
17FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
18
19You should have received a copy of the GNU Lesser General Public License along with
20this program; if not, write to the Free Software Foundation, Inc., 59 Temple
21Place - Suite 330, Boston, MA 02111-1307, USA, or go to
22http://www.gnu.org/copyleft/lesser.txt.
23
24You may alternatively use this source under the terms of a specific version of
25the OGRE Unrestricted License provided you have obtained such a license from
26Torus Knot Software Ltd.
27-----------------------------------------------------------------------------
28*/
29/** Internal include file -- do not use externally */
30using namespace Ogre;
31
32// NB VC6 can't handle these templates
33#if OGRE_COMPILER != OGRE_COMPILER_MSVC || OGRE_COMP_VER >= 1300
34
35#define FMTCONVERTERID(from,to) (((from)<<8)|(to))
36
37/**
38 * Convert a box of pixel from one type to another. Who needs automatic code
39 * generation when we have C++ templates and the policy design pattern.
40 *
41 * @param   U       Policy class to facilitate pixel-to-pixel conversion. This class
42 *    has at least two typedefs: SrcType and DstType. SrcType is the source element type,
43 *    dstType is the destination element type. It also has a static method, pixelConvert, that
44 *    converts a srcType into a dstType.
45 */
46
47template <class U> struct PixelBoxConverter
48{
49    static const int ID = U::ID;
50    static void conversion(const PixelBox &src, const PixelBox &dst)
51    {
52        typename U::SrcType *srcptr = static_cast<typename U::SrcType*>(src.data);
53        typename U::DstType *dstptr = static_cast<typename U::DstType*>(dst.data);
54        const size_t srcSliceSkip = src.getSliceSkip();
55        const size_t dstSliceSkip = dst.getSliceSkip();
56        const size_t k = src.right - src.left;
57        for(size_t z=src.front; z<src.back; z++) 
58        {
59            for(size_t y=src.top; y<src.bottom; y++)
60            {
61                for(size_t x=0; x<k; x++)
62                {
63                    dstptr[x] = U::pixelConvert(srcptr[x]);
64                }
65                srcptr += src.rowPitch;
66                dstptr += dst.rowPitch;
67            }
68            srcptr += srcSliceSkip;
69            dstptr += dstSliceSkip;
70        }   
71    }
72};
73
74template <typename T, typename U, int id> struct PixelConverter {
75    static const int ID = id;
76    typedef T SrcType;
77    typedef U DstType;   
78   
79    //inline static DstType pixelConvert(const SrcType &inp);
80};
81
82
83/** Type for PF_R8G8B8/PF_B8G8R8 */
84struct Col3b {
85    Col3b(unsigned int a, unsigned int b, unsigned int c): 
86        x((uint8)a), y((uint8)b), z((uint8)c) { }
87    uint8 x,y,z;
88};
89/** Type for PF_FLOAT32_RGB */
90struct Col3f {
91        Col3f(float r, float g, float b):
92                r(r), g(g), b(b) { }
93        float r,g,b;
94};
95/** Type for PF_FLOAT32_RGBA */
96struct Col4f {
97        Col4f(float r, float g, float b, float a):
98                r(r), g(g), b(b), a(a) { }
99        float r,g,b,a;
100};
101
102struct A8R8G8B8toA8B8G8R8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_A8R8G8B8, PF_A8B8G8R8)>
103{
104    inline static DstType pixelConvert(SrcType inp)
105    {
106        return ((inp&0x000000FF)<<16)|(inp&0xFF00FF00)|((inp&0x00FF0000)>>16);
107    }
108};
109
110struct A8R8G8B8toB8G8R8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_A8R8G8B8, PF_B8G8R8A8)>
111{
112    inline static DstType pixelConvert(SrcType inp)
113    {
114        return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24);
115    }
116};
117
118struct A8R8G8B8toR8G8B8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_A8R8G8B8, PF_R8G8B8A8)>
119{
120    inline static DstType pixelConvert(SrcType inp)
121    {
122        return ((inp&0x00FFFFFF)<<8)|((inp&0xFF000000)>>24);
123    }
124};
125
126struct A8B8G8R8toA8R8G8B8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_A8B8G8R8, PF_A8R8G8B8)>
127{
128    inline static DstType pixelConvert(SrcType inp)
129    {
130        return ((inp&0x000000FF)<<16)|(inp&0xFF00FF00)|((inp&0x00FF0000)>>16);
131    }
132};
133
134struct A8B8G8R8toB8G8R8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_A8B8G8R8, PF_B8G8R8A8)>
135{
136    inline static DstType pixelConvert(SrcType inp)
137    {
138        return ((inp&0x00FFFFFF)<<8)|((inp&0xFF000000)>>24);
139    }
140};
141
142struct A8B8G8R8toR8G8B8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_A8B8G8R8, PF_R8G8B8A8)>
143{
144    inline static DstType pixelConvert(SrcType inp)
145    {
146        return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24);
147    }
148};
149
150struct B8G8R8A8toA8R8G8B8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_B8G8R8A8, PF_A8R8G8B8)>
151{
152    inline static DstType pixelConvert(SrcType inp)
153    {
154        return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24);
155    }
156};
157
158struct B8G8R8A8toA8B8G8R8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_B8G8R8A8, PF_A8B8G8R8)>
159{
160    inline static DstType pixelConvert(SrcType inp)
161    {
162        return ((inp&0x000000FF)<<24)|((inp&0xFFFFFF00)>>8);
163    }
164};
165
166struct B8G8R8A8toR8G8B8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_B8G8R8A8, PF_R8G8B8A8)>
167{
168    inline static DstType pixelConvert(SrcType inp)
169    {
170        return ((inp&0x0000FF00)<<16)|(inp&0x00FF00FF)|((inp&0xFF000000)>>16);
171    }
172};
173
174struct R8G8B8A8toA8R8G8B8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_R8G8B8A8, PF_A8R8G8B8)>
175{
176    inline static DstType pixelConvert(SrcType inp)
177    {
178        return ((inp&0x000000FF)<<24)|((inp&0xFFFFFF00)>>8);
179    }
180};
181
182struct R8G8B8A8toA8B8G8R8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_R8G8B8A8, PF_A8B8G8R8)>
183{
184    inline static DstType pixelConvert(SrcType inp)
185    {
186        return ((inp&0x000000FF)<<24)|((inp&0x0000FF00)<<8)|((inp&0x00FF0000)>>8)|((inp&0xFF000000)>>24);
187    }
188};
189
190struct R8G8B8A8toB8G8R8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_R8G8B8A8, PF_B8G8R8A8)>
191{
192    inline static DstType pixelConvert(SrcType inp)
193    {
194        return ((inp&0x0000FF00)<<16)|(inp&0x00FF00FF)|((inp&0xFF000000)>>16);
195    }
196};
197
198struct A8B8G8R8toL8: public PixelConverter <uint32, uint8, FMTCONVERTERID(PF_A8B8G8R8, PF_L8)>
199{
200    inline static DstType pixelConvert(SrcType inp)
201    {
202        return (uint8)(inp&0x000000FF);
203    }
204};
205
206struct L8toA8B8G8R8: public PixelConverter <uint8, uint32, FMTCONVERTERID(PF_L8, PF_A8B8G8R8)>
207{
208    inline static DstType pixelConvert(SrcType inp)
209    {
210        return 0xFF000000|(((unsigned int)inp)<<0)|(((unsigned int)inp)<<8)|(((unsigned int)inp)<<16);
211    }
212};
213
214struct A8R8G8B8toL8: public PixelConverter <uint32, uint8, FMTCONVERTERID(PF_A8R8G8B8, PF_L8)>
215{
216    inline static DstType pixelConvert(SrcType inp)
217    {
218        return (uint8)((inp&0x00FF0000)>>16);
219    }
220};
221
222struct L8toA8R8G8B8: public PixelConverter <uint8, uint32, FMTCONVERTERID(PF_L8, PF_A8R8G8B8)>
223{
224    inline static DstType pixelConvert(SrcType inp)
225    {
226        return 0xFF000000|(((unsigned int)inp)<<0)|(((unsigned int)inp)<<8)|(((unsigned int)inp)<<16);
227    }
228};
229
230struct B8G8R8A8toL8: public PixelConverter <uint32, uint8, FMTCONVERTERID(PF_B8G8R8A8, PF_L8)>
231{
232    inline static DstType pixelConvert(SrcType inp)
233    {
234        return (uint8)((inp&0x0000FF00)>>8);
235    }
236};
237
238struct L8toB8G8R8A8: public PixelConverter <uint8, uint32, FMTCONVERTERID(PF_L8, PF_B8G8R8A8)>
239{
240    inline static DstType pixelConvert(SrcType inp)
241    {
242        return 0x000000FF|(((unsigned int)inp)<<8)|(((unsigned int)inp)<<16)|(((unsigned int)inp)<<24);
243    }
244};
245
246struct L8toL16: public PixelConverter <uint8, uint16, FMTCONVERTERID(PF_L8, PF_L16)>
247{
248    inline static DstType pixelConvert(SrcType inp)
249    {
250        return (uint16)((((unsigned int)inp)<<8)|(((unsigned int)inp)));
251    }
252};
253
254struct L16toL8: public PixelConverter <uint16, uint8, FMTCONVERTERID(PF_L16, PF_L8)>
255{
256    inline static DstType pixelConvert(SrcType inp)
257    {
258        return (uint8)(inp>>8);
259    }
260};
261
262struct R8G8B8toB8G8R8: public PixelConverter <Col3b, Col3b, FMTCONVERTERID(PF_R8G8B8, PF_B8G8R8)>
263{
264    inline static DstType pixelConvert(const SrcType &inp)
265    {
266        return Col3b(inp.z, inp.y, inp.x);
267    } 
268};
269
270struct B8G8R8toR8G8B8: public PixelConverter <Col3b, Col3b, FMTCONVERTERID(PF_B8G8R8, PF_R8G8B8)>
271{
272    inline static DstType pixelConvert(const SrcType &inp)
273    {
274        return Col3b(inp.z, inp.y, inp.x);
275    } 
276};
277
278// X8Y8Z8 ->  X8<<xshift Y8<<yshift Z8<<zshift A8<<ashift
279template <int id, unsigned int xshift, unsigned int yshift, unsigned int zshift, unsigned int ashift> struct Col3btoUint32swizzler:
280    public PixelConverter <Col3b, uint32, id>
281{
282    inline static uint32 pixelConvert(const Col3b &inp)
283    {
284#if OGRE_ENDIAN == OGRE_ENDIAN_BIG
285        return (0xFF<<ashift) | (((unsigned int)inp.x)<<xshift) | (((unsigned int)inp.y)<<yshift) | (((unsigned int)inp.z)<<zshift);
286#else
287        return (0xFF<<ashift) | (((unsigned int)inp.x)<<zshift) | (((unsigned int)inp.y)<<yshift) | (((unsigned int)inp.z)<<xshift);
288#endif
289    }
290};
291
292struct R8G8B8toA8R8G8B8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_R8G8B8, PF_A8R8G8B8), 16, 8, 0, 24> { };
293struct B8G8R8toA8R8G8B8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_B8G8R8, PF_A8R8G8B8), 0, 8, 16, 24> { };
294struct R8G8B8toA8B8G8R8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_R8G8B8, PF_A8B8G8R8), 0, 8, 16, 24> { };
295struct B8G8R8toA8B8G8R8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_B8G8R8, PF_A8B8G8R8), 16, 8, 0, 24> { };
296struct R8G8B8toB8G8R8A8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_R8G8B8, PF_B8G8R8A8), 8, 16, 24, 0> { };
297struct B8G8R8toB8G8R8A8: public Col3btoUint32swizzler<FMTCONVERTERID(PF_B8G8R8, PF_B8G8R8A8), 24, 16, 8, 0> { };
298
299struct A8R8G8B8toR8G8B8: public PixelConverter <uint32, Col3b, FMTCONVERTERID(PF_A8R8G8B8, PF_BYTE_RGB)>
300{
301    inline static DstType pixelConvert(uint32 inp)
302    {
303        return Col3b((uint8)((inp>>16)&0xFF), (uint8)((inp>>8)&0xFF), (uint8)((inp>>0)&0xFF));
304    }
305};
306struct A8R8G8B8toB8G8R8: public PixelConverter <uint32, Col3b, FMTCONVERTERID(PF_A8R8G8B8, PF_BYTE_BGR)>
307{
308    inline static DstType pixelConvert(uint32 inp)
309    {
310        return Col3b((uint8)((inp>>0)&0xFF), (uint8)((inp>>8)&0xFF), (uint8)((inp>>16)&0xFF));
311    }
312};
313
314// Only conversions from X8R8G8B8 to formats with alpha need to be defined, the rest is implicitly the same
315// as A8R8G8B8
316struct X8R8G8B8toA8R8G8B8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_A8R8G8B8)>
317{
318    inline static DstType pixelConvert(SrcType inp)
319    {
320        return inp | 0xFF000000;
321    }
322};
323struct X8R8G8B8toA8B8G8R8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_A8B8G8R8)>
324{
325    inline static DstType pixelConvert(SrcType inp)
326    {
327        return ((inp&0x0000FF)<<16)|((inp&0xFF0000)>>16)|(inp&0x00FF00)|0xFF000000;
328    }
329};
330struct X8R8G8B8toB8G8R8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_B8G8R8A8)>
331{
332    inline static DstType pixelConvert(SrcType inp)
333    {
334        return ((inp&0x0000FF)<<24)|((inp&0xFF0000)>>8)|((inp&0x00FF00)<<8)|0x000000FF;
335    }
336};
337struct X8R8G8B8toR8G8B8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8R8G8B8, PF_R8G8B8A8)>
338{
339    inline static DstType pixelConvert(SrcType inp)
340    {
341        return ((inp&0xFFFFFF)<<8)|0x000000FF;
342    }
343};
344
345// X8B8G8R8
346struct X8B8G8R8toA8R8G8B8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_A8R8G8B8)>
347{
348    inline static DstType pixelConvert(SrcType inp)
349    {
350        return ((inp&0x0000FF)<<16)|((inp&0xFF0000)>>16)|(inp&0x00FF00)|0xFF000000;
351    }
352};
353struct X8B8G8R8toA8B8G8R8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_A8B8G8R8)>
354{
355        inline static DstType pixelConvert(SrcType inp)
356    {
357        return inp | 0xFF000000;
358    }
359};
360struct X8B8G8R8toB8G8R8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_B8G8R8A8)>
361{
362    inline static DstType pixelConvert(SrcType inp)
363    {
364        return ((inp&0xFFFFFF)<<8)|0x000000FF;
365    }
366};
367struct X8B8G8R8toR8G8B8A8: public PixelConverter <uint32, uint32, FMTCONVERTERID(PF_X8B8G8R8, PF_R8G8B8A8)>
368{
369    inline static DstType pixelConvert(SrcType inp)
370    {
371        return ((inp&0x0000FF)<<24)|((inp&0xFF0000)>>8)|((inp&0x00FF00)<<8)|0x000000FF;
372    }
373};
374
375
376#define CASECONVERTER(type) case type::ID : PixelBoxConverter<type>::conversion(src, dst); return 1;
377
378inline int doOptimizedConversion(const PixelBox &src, const PixelBox &dst)
379{;
380    switch(FMTCONVERTERID(src.format, dst.format))
381    {
382        // Register converters here
383                CASECONVERTER(A8R8G8B8toA8B8G8R8);
384                CASECONVERTER(A8R8G8B8toB8G8R8A8);
385                CASECONVERTER(A8R8G8B8toR8G8B8A8);
386                CASECONVERTER(A8B8G8R8toA8R8G8B8);
387                CASECONVERTER(A8B8G8R8toB8G8R8A8);
388                CASECONVERTER(A8B8G8R8toR8G8B8A8);
389                CASECONVERTER(B8G8R8A8toA8R8G8B8);
390                CASECONVERTER(B8G8R8A8toA8B8G8R8);
391                CASECONVERTER(B8G8R8A8toR8G8B8A8);
392                CASECONVERTER(R8G8B8A8toA8R8G8B8);
393                CASECONVERTER(R8G8B8A8toA8B8G8R8);
394                CASECONVERTER(R8G8B8A8toB8G8R8A8);
395        CASECONVERTER(A8B8G8R8toL8);
396        CASECONVERTER(L8toA8B8G8R8);
397        CASECONVERTER(A8R8G8B8toL8);
398        CASECONVERTER(L8toA8R8G8B8);
399        CASECONVERTER(B8G8R8A8toL8);
400        CASECONVERTER(L8toB8G8R8A8);
401        CASECONVERTER(L8toL16);
402        CASECONVERTER(L16toL8);
403        CASECONVERTER(B8G8R8toR8G8B8);
404        CASECONVERTER(R8G8B8toB8G8R8);
405        CASECONVERTER(R8G8B8toA8R8G8B8);
406        CASECONVERTER(B8G8R8toA8R8G8B8);
407        CASECONVERTER(R8G8B8toA8B8G8R8);
408        CASECONVERTER(B8G8R8toA8B8G8R8);
409        CASECONVERTER(R8G8B8toB8G8R8A8);
410        CASECONVERTER(B8G8R8toB8G8R8A8);
411                CASECONVERTER(A8R8G8B8toR8G8B8);
412                CASECONVERTER(A8R8G8B8toB8G8R8);
413                CASECONVERTER(X8R8G8B8toA8R8G8B8);
414                CASECONVERTER(X8R8G8B8toA8B8G8R8);
415                CASECONVERTER(X8R8G8B8toB8G8R8A8);
416                CASECONVERTER(X8R8G8B8toR8G8B8A8);
417                CASECONVERTER(X8B8G8R8toA8R8G8B8);
418                CASECONVERTER(X8B8G8R8toA8B8G8R8);
419                CASECONVERTER(X8B8G8R8toB8G8R8A8);
420                CASECONVERTER(X8B8G8R8toR8G8B8A8);
421
422        default:
423            return 0;
424    }
425}
426#undef CASECONVERTER
427
428#endif // VC6 protection
Note: See TracBrowser for help on using the repository browser.